iOS 多个APP沙盒数据共享
我们都知道,APP的沙盒是用来存储这个APP的本地数据的。其实,同一个开发者开发的多个APP的沙盒数据是可以共享,也就是你可以拿到另一个应用的沙盒数据。
如果你开发的是一系列的产品,例如:国寿i系列的产品,就可以应用这个技术实现免登录,共享用户信息,共享活动数据等。
有两种方式,第一种 App Groups, 第二种 Keychain Sharing
第一种方式在你把所有这个加入了这个组的app都删了以后,这个数据就么得了!!!
第二种方式其实相当于手机中钥匙串,卸载app以后依然保持,重新安装APP以后仍然能够获取。
前面说了很多废话,那我们废话不多说,马上开始!得,又是句废话。
一、 App Groups
1. 在两个项目中打开App Groups开关,并设置group名称
group的名称一般是 group. 开头,然后跟上你的bundleID前面的共同部分,在跟上系列名称。
例如:group.cn.jiangwei.i
两个项目的group保持一致!
2. 在第一个项目中保存需要共享的数据
我们通常都是用 [NSUserDefaults standardUserDefaults]
来获取单例对象,但是这里需要你使用group名称去init。然后根据字段存数据。
- (IBAction)saveUserID:(id)sender {
NSUserDefaults *groupDefaults = [[NSUserDefaults alloc]
initWithSuiteName:@"group.cn.jiangwei.i"];
[groupDefaults setObject:self.textField.text forKey:@"group.cn.jiangwei.userid"];
}
3. 在第二个项目中获取该数据
- (IBAction)getUserid:(id)sender {
NSUserDefaults *groupDefaults = [[NSUserDefaults alloc]
initWithSuiteName:@"group.cn.jiangwei.i"];
self.label.text = [groupDefaults objectForKey:@"group.cn.jiangwei.userid"];
}
搞定,就是这么简单。但是没有第二种好呀,原因上面说过了,快看下一种。
二、 Keychain Sharing
1. 在两个项目中均导入KeychainItemWrapper
- 下载苹果官方文档的项目:
https://developer.apple.com/library/ios/samplecode/generickeychain/Introduction/Intro.html - 把工程文件keychainItemWrapper.h/m两个件添加进自己的工程;
- 添加security.framework到工程;
本文最后面的Demo里面有,可以直接使用。
但是由于文档年代久远,是mrc的,所以需要混编。
给 keychainItemWrapper.m
设置上 -fno-objc-arc
2. 获取 bundleSeedID
不同开发者的bundleSeedID 是不一样的,通过这个方法获取到,后面会用到
- (NSString *)bundleSeedID {
NSDictionary *query = [NSDictionary dictionaryWithObjectsAndKeys:kSecClassGenericPassword, kSecClass,@"bundleSeedID", kSecAttrAccount,@"", kSecAttrService,(id)kCFBooleanTrue, kSecReturnAttributes,nil];
CFDictionaryRef result = nil;
OSStatus status = SecItemCopyMatching((CFDictionaryRef)query, (CFTypeRef *)&result);
if (status == errSecItemNotFound)status = SecItemAdd((CFDictionaryRef)query, (CFTypeRef *)&result);
if (status != errSecSuccess)return nil;
NSString *accessGroup = [(__bridge NSDictionary *)result objectForKey:kSecAttrAccessGroup];
NSArray *components = [accessGroup componentsSeparatedByString:@"."];
NSString *bundleSeedID = [[components objectEnumerator] nextObject];CFRelease(result);return bundleSeedID;
}
3. 在两个项目中打开Keychain Sharing开关,并设置group名称
group的名称一般你的bundleID前面的共同部分开头,再跟上系列名称。
例如:cn.jiangwei.i
两个项目的group保持一致!
4. 在第一个项目中保存需要共享的数据
导入文件
#import "KeychainItemWrapper.h"
- (IBAction)saveAccount:(id)sender {
KeychainItemWrapper *wrapper = [[KeychainItemWrapper alloc]
initWithIdentifier:@"Ixilie_User" accessGroup:@"3BPVDYRLER.cn.jiangwei.i"];
NSString *username = self.userTextField.text;
NSString *password = self.passwordTextField.text;
[wrapper setObject:username forKey:(id)kSecAttrAccount];
[wrapper setObject:password forKey:(id)kSecValueData];
}
-
⚠️注意:这里面的accessGroup 的组成就是 第3步获取的bundleSeedID + . + 你设置的group名称
设置错误会导致崩溃 -
key是预设的,你可以存到这写字段中去,取也是按照相同字段取。
5. 在第二个项目中获取该数据
- (IBAction)getAccount:(id)sender {
KeychainItemWrapper *wrapper = [[KeychainItemWrapper alloc] initWithIdentifier:@"Ixilie_User" accessGroup:@"3BPVDYRLER.cn.jiangwei.i"];
NSString *username = [wrapper objectForKey:(id)kSecAttrAccount];
NSString *password = [wrapper objectForKey:(id)kSecValueData];
self.userLabel.text = username;
self.passwordLabel.text = password;
}
大功告成!即使卸载了这个账号的全部APP,你都能在这台手机上保存你想保留的数据。
效果图
第一个APP.jpeg 第二个APP.jpegDemo 地址:https://github.com/muyan091115/App-Groups-Keychain-Sharing
里面的iDong项目是用来存的,iChe用来取的