You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

如何替换Bundle中已打包文件内容?为何修改未生效?

无法修改Bundle中shared.json内容的问题分析与解决

嘿,这个坑我之前也踩过!核心原因其实很直白:App的主Bundle是只读的。当你的App安装到设备或模拟器后,系统会把Bundle里的所有资源文件保护起来,不允许直接修改。你的代码看起来没抛出错误,大概率是因为系统悄悄拦截了写入操作,或者你写入的其实是一个临时副本,根本没碰到底层的原文件。

下面是具体的解决步骤:

1. 先把Bundle里的JSON文件复制到可读写的目录

App的Documents目录是系统允许我们自由读写的区域,所以第一步要做的是把初始的shared.json从Bundle复制到这里(只需要做一次,比如App首次启动时):

// 获取Documents目录的URL
func getDocumentsDirectory() -> URL {
    let paths = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask)
    return paths[0]
}

// 处理文件复制逻辑
let bundleJsonURL = Bundle.main.url(forResource: "shared", withExtension: "json")!
let targetJsonURL = getDocumentsDirectory().appendingPathComponent("shared.json")

// 如果Documents里还没有这个文件,就从Bundle复制过去
if !FileManager.default.fileExists(atPath: targetJsonURL.path) {
    do {
        try FileManager.default.copyItem(at: bundleJsonURL, to: targetJsonURL)
        print("初始文件已复制到Documents目录")
    } catch {
        print("复制初始文件失败:\(error.localizedDescription)")
    }
}

2. 所有读写操作都针对Documents里的文件

把你原来的代码里的fileUrl替换成上面的targetJsonURL,之后的读写就都能生效了:

do {
    // 写入数据到Documents目录的文件
    try jsonData.write(to: targetJsonURL, atomically: true, encoding: .utf8)
    
    // 验证写入结果
    let newData = try String(contentsOf: targetJsonURL, encoding: .utf8)
    print("更新后的文件内容:\(newData)")
} catch {
    print("文件操作失败:\(error.localizedDescription)")
}

补充说明:为什么之前的代码没报错?

有些情况下,系统会允许你写入Bundle路径,但实际上是写入到了一个临时的沙箱副本里——你当时读取的时候能看到修改后的内容,但原Bundle文件根本没变化,等App重启后,一切又会回到初始状态。所以一定要把文件放到可读写的目录里操作才行。

内容的提问来源于stack exchange,提问作者Darrell Brogdon

火山引擎 最新活动