私の OS X アプリには、ユーザーが選択したディレクトリへの永続的なアクセスが必要です。value
アプリ サンドボックスを有効にする前は、UIにはデータ モデルへのバインディングを備えた NSPathControl がありました。モデルのデータ型は でNSData
あり、バインディングはNSKeyedUnarchiveFromData
値トランスフォーマーを使用しました。それはうまくいきました。
アプリのサンドボックス化がオンになっていると、NSURL がセキュリティ スコープではないため、これは明らかに失敗します。これを改善するためにNSKeyedUnarchiveFromData
、以下に示すように、バインディングのトランスフォーマーを独自のトランスフォーマーに置き換えました。
残念ながら、常に正しく機能するとは限りません。私 (ユーザーとして行動) が NSPathControl からファイルを選択すると、transformedValue:
渡された NSData 引数が非 nil であっても nil を返すことがあります。つまり、NSURL はブックマーク データを解決しません。ここで何が起こっているか知っている人はいますか?失敗した場合、によって返されるエラーURLByResolvingBookmarkData:options:relativeToURL:bookmarkDataIsStale:error:
は
エラー Domain=NSCocoaErrorDomain Code=259 「ファイルの形式が正しくないため、ファイルを開くことができませんでした。」
@implementation URLFromBookmarkDataTransformer
+ (BOOL)allowsReverseTransformation {
return YES;
}
+ (Class)transformedValueClass {
return [NSURL class];
}
- (id)transformedValue:(id)value {
if (value == nil) {
return nil;
}
NSAssert([value isKindOfClass:[NSData class]], @"value must be NSData");
return [NSURL URLByResolvingBookmarkData:value options:NSURLBookmarkResolutionWithSecurityScope relativeToURL:nil bookmarkDataIsStale:NULL error:NULL];
}
- (id)reverseTransformedValue:(id)value {
if (value == nil) {
return nil;
}
NSAssert([value isKindOfClass:[NSURL class]], @"value must be NSURL");
return [value bookmarkDataWithOptions:NSURLBookmarkCreationWithSecurityScope includingResourceValuesForKeys:nil relativeToURL:nil error:NULL];
}
@end