通常情况下,每个沙盒包含以下目录及文件:
目录结构如下图所示:
补充1:对于上述描述可以这样举例理解,一个记事本应用,用户写的东西需要保存起来,这些东西是用户自行生成的,则需要放在 Documents 目录里。一个新闻应用,如果需要从服务器下载东西展示给用户看,下载的东西就放在 Library/Caches 目录里。苹果审核对这个要求很严格,主要原因是 iCloud 的同步问题。
补充2:如果想知道真机或者模拟器 App 沙盒路径,可通过在项目中执行下述代码打印获取:
NSString *homeDirectoryPath = NSHomeDirectory();
// 获取沙盒根目录路径
NSString *homeDirectoryPath = NSHomeDirectory();
// 获取 Applications 路径
NSString *appDirectoryPath = [NSSearchPathForDirectoriesInDomains(NSApplicationDirectory, NSUserDomainMask, YES) objectAtIndex:0];
// 获取 Documents 路径
NSString *documentDirectoryPath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) objectAtIndex:0];
// 获取 Caches 路径
NSString *cachesDirectoryPath = [NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES) objectAtIndex:0];
// 获取 tmp 路径
NSString *tmpDirectoryPath = NSTemporaryDirectory();
使用 FileManager 可以对沙盒中的目录、文件进行操作。通过如下方式可以获取 NSFileManager 的单例:
[NSFileManager defaultManager]
iOS 应用都是通过 bundle 进行封装的,可以狭隘地将 bundle 理解为上述沙盒中的 AppName.app 文件。在 Finder 中,会把 bundle 当做一个文件显示从而防止用户误操作导致程序文件损坏,但其实内部是一个目录,包含了图像、媒体资源、编译好的代码、nib 文件等,这个目录称为 main bundle。
Cocaoa 提供了 NSBundle 类封装了 bundle 操作。
// 获取应用程序的 main bundle
NSBundle *mainBundle = NSBundle.mainBundle;
// 使用 main bundle 获取资源路径
NSString *filePath = [mainBundle pathForResource:@"logo" ofType:@"png"];
#import
@interface FileUtil : NSObject
/**
* 获取 home 路径
*
* @return
*/
+ (NSString *)homeDirectoryPath;
/**
* 获取 app 路径
*
* @return
*/
+ (NSString *)appDirectoryPath;
/**
* 获取 document 路径
*
* @return
*/
+ (NSString *)documentDirectoryPath;
/**
* 获取 caches 路径
*
* @return
*/
+ (NSString *)cachesDirectoryPath;
/**
* 获取 tmp 路径
*
* @return
*/
+ (NSString *)tmpDirectoryPath;
/**
* 判断目录是否存在
*
* @param directoryPath 目录路径
*
* @return
*/
+ (BOOL)directoryExist:(NSString *)directoryPath;
/**
* 判断文件是否存在
*
* @param filePath 文件路径
*
* @return
*/
+ (BOOL)fileExist:(NSString *)filePath;
/**
* 在父目录下创建子目录
*
* @param parentDirectoryPath 父目录路径
* @param directoryName 子目录名称
*
* @return
*/
+ (BOOL)createDirectoryAtParentDirectory:(NSString *)parentDirectoryPath directoryName:(NSString *)directoryName;
/**
* 在父目录下创建子文件
*
* @param parentDirectoryPath 父目录路径
* @param fileName 子文件名称
*
* @return
*/
+ (BOOL)createFileAtParentDirectory:(NSString *)parentDirectoryPath fileName:(NSString *)fileName;
/**
* 删除目录
*
* @param directoryPath 目录路径
*
* @return
*/
+ (BOOL)deleteDirectoryAtPath:(NSString *)directoryPath;
/**
* 删除文件
*
* @param filePath 文件路径
*
* @return
*/
+ (BOOL)deleteFileAtPath:(NSString *)filePath;
/**
* 获取父目录下的子内容(包含目录和文件)
*
* @param parentDirectoryPath 父目录路径
*
* @return
*/
+ (NSArray *)contentsAtParentDirectory:(NSString *)parentDirectoryPath;
/**
* 获取父目录下的所有子目录名称
*
* @param parentDirectoryPath 父目录路径
*
* @return
*/
+ (NSArray *)directoryNamesAtParentDirectory:(NSString *)parentDirectoryPath;
/**
* 获取父目录下的所有子目录路径
*
* @param parentDirectoryPath 父目录路径
*
* @return
*/
+ (NSArray *)directoryPathsAtParentDirectory:(NSString *)parentDirectoryPath;
/**
* 获取父目录下的所有子文件名称
*
* @param parentDirectoryPath 父目录路径
*
* @return
*/
+ (NSArray *)fileNamesAtParentDirectoryPath:(NSString *)parentDirectoryPath;
/**
* 获取父目录下的所有子文件路径
*
* @param parentDirectoryPath 父目录路径
*
* @return
*/
+ (NSArray *)filePathsAtParentDirectoryPath:(NSString *)parentDirectoryPath;
@end
FileUtil.m
#import "FileUtil.h"
@interface FileUtil ()
@end
@implementation FileUtil
+ (NSString *)homeDirectoryPath
{
return NSHomeDirectory();
}
+ (NSString *)appDirectoryPath
{
NSArray *array = NSSearchPathForDirectoriesInDomains(NSApplicationDirectory, NSUserDomainMask, YES);
return [array objectAtIndex:0];
}
+ (NSString *)documentDirectoryPath
{
NSArray *array = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
return [array objectAtIndex:0];
}
+ (NSString *)cachesDirectoryPath
{
NSArray *array = NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES);
return [array objectAtIndex:0];
}
+ (NSString *)tmpDirectoryPath
{
return NSTemporaryDirectory();
}
+ (BOOL)directoryExist:(NSString *)directoryPath
{
NSFileManager *fileManager = [NSFileManager defaultManager];
BOOL isDirectory = NO;
BOOL exist = [fileManager fileExistsAtPath:directoryPath isDirectory:&isDirectory];
if (isDirectory && exist) {
return YES;
}
return NO;
}
+ (BOOL)fileExist:(NSString *)filePath
{
NSFileManager *fileManager = [NSFileManager defaultManager];
return [fileManager fileExistsAtPath:filePath];
}
+ (BOOL)createDirectoryAtParentDirectory:(NSString *)parentDirectoryPath directoryName:(NSString *)directoryName
{
NSFileManager *fileManager = [NSFileManager defaultManager];
NSString *directoryPath = [NSString stringWithFormat:@"%@/%@", parentDirectoryPath, directoryName];
return [fileManager createDirectoryAtPath:directoryPath withIntermediateDirectories:YES attributes:nil error:nil];
}
+ (BOOL)createFileAtParentDirectory:(NSString *)parentDirectoryPath fileName:(NSString *)fileName
{
NSFileManager *fileManager = [NSFileManager defaultManager];
NSString *filePath = [NSString stringWithFormat:@"%@/%@", parentDirectoryPath, fileName];
return [fileManager createFileAtPath:filePath contents:nil attributes:nil];
}
+ (BOOL)deleteDirectoryAtPath:(NSString *)directoryPath
{
NSFileManager *fileManager = [NSFileManager defaultManager];
if ([self directoryExist:directoryPath]) {
return [fileManager removeItemAtPath:directoryPath error:nil];
}
return NO;
}
+ (BOOL)deleteFileAtPath:(NSString *)filePath
{
NSFileManager *fileManager = [NSFileManager defaultManager];
if ([self fileExist:filePath]) {
return [fileManager removeItemAtPath:filePath error:nil];
}
return NO;
}
+ (NSArray *)contentsAtParentDirectory:(NSString *)parentDirectoryPath
{
NSFileManager *fileManager = [NSFileManager defaultManager];
return [fileManager contentsOfDirectoryAtPath:parentDirectoryPath error:nil];
}
+ (NSArray *)directoryNamesAtParentDirectory:(NSString *)parentDirectoryPath
{
NSFileManager *fileManager = [NSFileManager defaultManager];
BOOL isDirectory = NO;
NSMutableArray *directoryPaths = [[NSMutableArray alloc] init];
for (NSString *content in [self contentsAtParentDirectory:parentDirectoryPath]) {
NSString *path = [NSString stringWithFormat:@"%@/%@", parentDirectoryPath, content];
if ([fileManager fileExistsAtPath:path isDirectory:&isDirectory]) {
if (isDirectory) {
[directoryPaths addObject:content];
}
}
}
return [directoryPaths copy];
}
+ (NSArray *)directoryPathsAtParentDirectory:(NSString *)parentDirectoryPath
{
NSFileManager *fileManager = [NSFileManager defaultManager];
BOOL isDirectory = NO;
NSMutableArray *directoryPaths = [[NSMutableArray alloc] init];
for (NSString *content in [self contentsAtParentDirectory:parentDirectoryPath]) {
NSString *path = [NSString stringWithFormat:@"%@/%@", parentDirectoryPath, content];
if ([fileManager fileExistsAtPath:path isDirectory:&isDirectory]) {
if (isDirectory) {
[directoryPaths addObject:path];
}
}
}
return [directoryPaths copy];
}
+ (NSArray *)fileNamesAtParentDirectoryPath:(NSString *)parentDirectoryPath
{
NSFileManager *fileManager = [NSFileManager defaultManager];
BOOL isDirectory = NO;
NSMutableArray *filePaths = [[NSMutableArray alloc] init];
for (NSString *content in [self contentsAtParentDirectory:parentDirectoryPath]) {
NSString *path = [NSString stringWithFormat:@"%@/%@", parentDirectoryPath, content];
if ([fileManager fileExistsAtPath:path isDirectory:&isDirectory]) {
if (!isDirectory) {
[filePaths addObject:content];
}
}
}
return [filePaths copy];
}
+ (NSArray *)filePathsAtParentDirectoryPath:(NSString *)parentDirectoryPath
{
NSFileManager *fileManager = [NSFileManager defaultManager];
BOOL isDirectory = NO;
NSMutableArray *filePaths = [[NSMutableArray alloc] init];
for (NSString *content in [self contentsAtParentDirectory:parentDirectoryPath]) {
NSString *path = [NSString stringWithFormat:@"%@/%@", parentDirectoryPath, content];
if ([fileManager fileExistsAtPath:path isDirectory:&isDirectory]) {
if (!isDirectory) {
[filePaths addObject:path];
}
}
}
return [filePaths copy];
}
@end
参考资料如下:
About Files and Directories
NSFileManager Class Reference
NSBundle Class Reference