mirror of
https://github.com/claude-code-best/claude-code.git
synced 2026-06-15 12:55:51 +00:00
feat: 添加 GBK 编码自动检测支持,文件读写工具透明处理非 UTF-8 文件
新增 encoding.ts 核心模块实现三层编码检测(BOM → UTF-8 fatal → GBK 回退), 改造同步/异步读取路径和写入路径,使 FileReadTool/FileEditTool/FileWriteTool 能正确处理 GBK 编码文件。包含完整单元测试和 spec 文档。 Co-Authored-By: glm-5-turbo <zai-org@claude-code-best.win>
This commit is contained in:
@@ -29,6 +29,7 @@ import { extractClaudeCodeHints } from 'src/utils/claudeCodeHints.js';
|
||||
import { detectCodeIndexingFromCommand } from 'src/utils/codeIndexing.js';
|
||||
import { isEnvTruthy } from 'src/utils/envUtils.js';
|
||||
import { isENOENT, ShellError } from 'src/utils/errors.js';
|
||||
import { decodeBuffer } from 'src/utils/encoding.js';
|
||||
import { detectFileEncoding, detectLineEndings, getFileModificationTime, writeTextContent } from 'src/utils/file.js';
|
||||
import { fileHistoryEnabled, fileHistoryTrackEdit } from 'src/utils/fileHistory.js';
|
||||
import { truncate } from 'src/utils/format.js';
|
||||
@@ -511,7 +512,8 @@ async function applySedEdit(
|
||||
const encoding = detectFileEncoding(absoluteFilePath);
|
||||
let originalContent: string;
|
||||
try {
|
||||
originalContent = await fs.readFile(absoluteFilePath, { encoding });
|
||||
const rawBuffer = await fs.readFileBytes(absoluteFilePath);
|
||||
originalContent = decodeBuffer(rawBuffer, encoding);
|
||||
} catch (e) {
|
||||
if (isENOENT(e)) {
|
||||
return {
|
||||
|
||||
@@ -34,6 +34,11 @@ import {
|
||||
type LineEndingType,
|
||||
readFileSyncWithMetadata,
|
||||
} from 'src/utils/fileRead.js'
|
||||
import {
|
||||
detectEncoding,
|
||||
decodeBuffer,
|
||||
type FileEncoding,
|
||||
} from 'src/utils/encoding.js'
|
||||
import { formatFileSize } from 'src/utils/format.js'
|
||||
import { getFsImplementation } from 'src/utils/fsOperations.js'
|
||||
import { fetchSingleFileGitDiff, type ToolUseDiff } from 'src/utils/gitDiff.js'
|
||||
@@ -202,13 +207,8 @@ export const FileEditTool = buildTool({
|
||||
let fileContent: string | null
|
||||
try {
|
||||
const fileBuffer = await fs.readFileBytes(fullFilePath)
|
||||
const encoding: BufferEncoding =
|
||||
fileBuffer.length >= 2 &&
|
||||
fileBuffer[0] === 0xff &&
|
||||
fileBuffer[1] === 0xfe
|
||||
? 'utf16le'
|
||||
: 'utf8'
|
||||
fileContent = fileBuffer.toString(encoding).replaceAll('\r\n', '\n')
|
||||
const encoding: FileEncoding = detectEncoding(fileBuffer)
|
||||
fileContent = decodeBuffer(fileBuffer, encoding).replaceAll('\r\n', '\n')
|
||||
} catch (e) {
|
||||
if (isENOENT(e)) {
|
||||
fileContent = null
|
||||
@@ -584,7 +584,7 @@ export const FileEditTool = buildTool({
|
||||
function readFileForEdit(absoluteFilePath: string): {
|
||||
content: string
|
||||
fileExists: boolean
|
||||
encoding: BufferEncoding
|
||||
encoding: FileEncoding
|
||||
lineEndings: LineEndingType
|
||||
} {
|
||||
try {
|
||||
|
||||
Reference in New Issue
Block a user