{"record":{"id":"81ec0a5fbf2b2d8b","repo":"EllanJiang/GameFramework","slug":"file-system-is-not-writable","errorCode":null,"errorMessage":"File system is not writable.","messagePattern":"File system is not writable\\.","errorType":"exception","errorClass":"GameFrameworkException","httpStatus":null,"severity":"error","filePath":"GameFramework/FileSystem/FileSystem.cs","lineNumber":811,"sourceCode":"                throw new GameFrameworkException(\"Buffer is invalid.\");\n            }\n\n            return WriteFile(name, buffer, startIndex, buffer.Length - startIndex);\n        }\n\n        /// <summary>\n        /// 写入指定文件。\n        /// </summary>\n        /// <param name=\"name\">要写入的文件名称。</param>\n        /// <param name=\"buffer\">存储写入文件内容的二进制流。</param>\n        /// <param name=\"startIndex\">存储写入文件内容的二进制流的起始位置。</param>\n        /// <param name=\"length\">存储写入文件内容的二进制流的长度。</param>\n        /// <returns>是否写入指定文件成功。</returns>\n        public bool WriteFile(string name, byte[] buffer, int startIndex, int length)\n        {\n            if (m_Access != FileSystemAccess.Write && m_Access != FileSystemAccess.ReadWrite)\n            {\n                throw new GameFrameworkException(\"File system is not writable.\");\n            }\n\n            if (string.IsNullOrEmpty(name))\n            {\n                throw new GameFrameworkException(\"Name is invalid.\");\n            }\n\n            if (name.Length > byte.MaxValue)\n            {\n                throw new GameFrameworkException(Utility.Text.Format(\"Name '{0}' is too long.\", name));\n            }\n\n            if (buffer == null)\n            {\n                throw new GameFrameworkException(\"Buffer is invalid.\");\n            }\n\n            if (startIndex < 0 || length < 0 || startIndex + length > buffer.Length)","sourceCodeStart":793,"sourceCodeEnd":829,"githubUrl":"https://github.com/EllanJiang/GameFramework/blob/d0c010b05167c58e92350449d04864a91ca13fd2/GameFramework/FileSystem/FileSystem.cs#L793-L829","documentation":"WriteFile(string name, byte[] buffer, int startIndex, int length) throws this GameFrameworkException when the file system was opened with FileSystemAccess.Read only. Writing requires the file system to have been created/opened with Write or ReadWrite access. The guard fires before any name or buffer validation.","triggerScenarios":"Opening a FileSystem (FileSystem.Create / LoadFileSystem or via the helper with access parameter) with FileSystemAccess.Read, then calling any WriteFile overload. Common when the same open handle is reused for both reads and writes.","commonSituations":"A config or download flag opens the package read-only (e.g. shipped game data) but update code later tries to write into it; sharing one FileSystem instance between a read path and a write path; access enum changed during a refactor.","solutions":["Open the file system with FileSystemAccess.Write or FileSystemAccess.ReadWrite (e.g. via FileSystem.Create with access: FileSystemAccess.ReadWrite).","If the file system is already created, check fs.Access (m_Access) before writing and route writes to a writable instance.","Split usage: keep a read-only instance for shipped data and a separate ReadWrite instance for user-writable data."],"exampleFix":"// before\nvar fs = FileSystem.Create(fullPath, FileSystemAccess.Read, ...);\nfs.WriteFile(name, buffer, 0, buffer.Length); // throws\n// after\nvar fs = FileSystem.Create(fullPath, FileSystemAccess.ReadWrite, ...);\nfs.WriteFile(name, buffer, 0, buffer.Length);","handlingStrategy":"validation","validationCode":"if (fs.Access != FileSystemAccess.Write && fs.Access != FileSystemAccess.ReadWrite) throw new InvalidOperationException(\"File system opened read-only; cannot write.\");","typeGuard":"static bool IsWritable(FileSystem fs) => fs != null && (fs.Access == FileSystemAccess.Write || fs.Access == FileSystemAccess.ReadWrite);","tryCatchPattern":"try { fs.WriteFile(name, buffer, startIndex, length); } catch (GameFrameworkException ex) when (ex.Message == \"File system is not writable.\") { /* reopen with Write/ReadWrite access */ }","preventionTips":["Open with FileSystemAccess.ReadWrite whenever the same handle will read and write.","Assert access mode once at startup, not at every write.","Keep shipped read-only data and user data in separate file systems."],"tags":["gameframework","filesystem","access-mode","write","read-only"],"backgroundTag":"unsupported-operation","analyzedSha":"d0c010b05167c58e92350449d04864a91ca13fd2","analyzedAt":"2026-09-15T13:37:15.352Z","contentChangedAt":"2026-09-15T13:37:15.352Z","schemaVersion":2},"datasetVersion":"2026-09-16T04:17:20.429Z"}