如何检查用户选择的文件是不是我的沙盒应用程序具有写入权限?
Posted
技术标签:
【中文标题】如何检查用户选择的文件是不是我的沙盒应用程序具有写入权限?【英文标题】:How to check if user selected file(s) my Sandboxed app has permission to write?如何检查用户选择的文件是否我的沙盒应用程序具有写入权限? 【发布时间】:2012-06-01 06:30:24 【问题描述】:我正在我的 OS X 应用程序中启用沙盒以重新提交到应用程序商店,并且我正在尝试找到最优雅的方式来确保用户只能选择我的应用程序有权更改的资源。
精简场景:
-
用户通过
NSOpenPanel
选择文件系统上的图片
用户点击应用上的Process Picture
按钮
应用从互联网上检索信息
应用程序更改图片的元数据。
用户选择完图片后,我要确保每张图片都位于图片文件夹下,否则我对物理文件的写入将简单地失败。
苹果recommends the following to determine the Pictures folder's location:
图片目录包含用户的图像和照片。要得到 此目录的路径使用 NSPicturesDirectory 搜索路径键 使用 NSUserDomainMask 域。
实现上述内容为我提供了一条如下所示的路径:
/Users/thomas/Library/Containers/com.blazingfrog.latipics/Data/Pictures/picture1.jpg
但是当我想查看用户选择了哪些图片时,[myOpenPanel URLs]
返回/Users/thomas/Pictures/picture1.jpg
这两条路径在逻辑上是相同的,但看起来却截然不同。如何以每次都有效的方式比较它们?
如果有帮助,为了准备我的应用以进行沙盒处理,我做了以下操作
在 XCode 中启用权利 启用应用沙盒 启用文件系统(读取) 启用允许传入/传出网络连接 启用图片文件夹访问(读/写)【问题讨论】:
“否则我对物理文件的写入将简单地失败”你能解释一下吗?当您尝试打开文件(用于写入)时会发生什么?那会失败吗?如果你使用像fopen
这样的 libc 函数之一呢?
我使用第三方实用程序创建一个临时文件(非破坏性编辑),该文件在图片处理成功后最终被删除。所以为了回答你的问题,我的应用程序不会直接打开文件。
【参考方案1】:
您几乎应该永远不要默默地失败。如果出现问题,请尽可能向用户报告。这正是 NSError
的设计目的。
您几乎应该永远不要在尝试之前尝试确定操作是否会成功。这样做会使您对竞争条件持开放态度。而是继续尝试操作;如果失败,请优雅地处理。
听起来您实际上想要com.apple.security.files.user-selected.read-write
权利。这将为您提供对用户使用打开面板选择的任何文件的写入权限。
【讨论】:
无声写入失败不是我的选择。 “沙盒”进程拒绝写入:(Jun 1 09:28:39 Mika sandboxd[1113] ([1112]): perl5.12(1112) deny file-write-create /Users/thomas/Desktop/IMG_4679.JPG_tmp ) 但我的应用没有得到任何反馈。这正是我想抢占用户选择他最终无法处理的资源的原因。我不能真正使用您建议的权利,因为我在写入用户选择的文件(非破坏性编辑)之前实际上创建了一个临时文件。 如果沙盒守护进程拒绝文件系统访问,则无论尝试访问的任何内容都会被告知它调用的方法/函数失败。该故障应该作为第三方实用程序的客户端传播给您。其他任何事情都是令人震惊的设计失败 通过临时文件尝试写入并不重要。这正是 Cocoa 为其“原子”写作支持所做的。这个临时文件写在哪里? 我没有收到来自 3rd-party 实用程序的失败消息,这是我的一个疏忽。我同意你的看法,我会修复它。为了回答你最后一个问题,临时文件是在所选图片所在的同一文件夹中创建的。因此,如果用户从 ~/Pictures" 中选择图片 那就没问题了。如果用户从另一个我没有权利的文件夹中选择一张图片,它会失败。【参考方案2】:[[NSFileManager defaultManager] isWritableFileAtPath:path]
【讨论】:
以上是关于如何检查用户选择的文件是不是我的沙盒应用程序具有写入权限?的主要内容,如果未能解决你的问题,请参考以下文章
将文件存储在 iphone 的沙盒之外或通过其他应用程序访问文件系统