MyUUIDManager.h

#import <Foundation/Foundation.h>

NS_ASSUME_NONNULL_BEGIN

@interface MyUUIDManager : NSObject
+(void)saveUUID:(NSString *)uuid; +(NSString *)getUUID; +(void)deleteUUID;
@end NS_ASSUME_NONNULL_END

MyUUIDManager.m

#import "MyUUIDManager.h"
#import "MyKeyChainManager.h"
@implementation MyUUIDManager
static NSString * const KEY_IN_KEYCHAIN = @"com.myuuid.uuid"; +(void)saveUUID:(NSString *)uuid{
if (uuid && uuid.length > 0) {
[MyKeyChainManager save:KEY_IN_KEYCHAIN data:uuid];
}
} +(NSString *)getUUID{
//先获取keychain里面的UUID字段,看是否存在
NSString *uuid = (NSString *)[MyKeyChainManager load:KEY_IN_KEYCHAIN]; //如果不存在则为首次获取UUID,所以获取保存。
if (!uuid || uuid.length == 0) {
CFUUIDRef puuid = CFUUIDCreate( nil ); CFStringRef uuidString = CFUUIDCreateString( nil, puuid ); uuid = [NSString stringWithFormat:@"%@", uuidString]; [self saveUUID:uuid]; CFRelease(puuid); CFRelease(uuidString);
} return uuid;
} +(void)deleteUUID{
[MyKeyChainManager delete:KEY_IN_KEYCHAIN];
} @end

MyKeyChainManager.h

#import <Foundation/Foundation.h>

NS_ASSUME_NONNULL_BEGIN

@interface MyKeyChainManager : NSObject

+ (void)save:(NSString *)service data:(id)data;
+ (id)load:(NSString *)service ;
+ (void)delete:(NSString *)service ;
@end NS_ASSUME_NONNULL_END

MyKeyChainManager.m

#import "MyKeyChainManager.h"

@implementation MyKeyChainManager

+ (NSMutableDictionary *)getKeychainQuery:(NSString *)service {
return [NSMutableDictionary dictionaryWithObjectsAndKeys:
(__bridge_transfer id)kSecClassGenericPassword,(__bridge_transfer id)kSecClass,
service, (__bridge_transfer id)kSecAttrService,
service, (__bridge_transfer id)kSecAttrAccount,
(__bridge_transfer id)kSecAttrAccessibleAfterFirstUnlock,(__bridge_transfer id)kSecAttrAccessible,
nil];
} + (void)save:(NSString *)service data:(id)data {
//Get search dictionary
NSMutableDictionary *keychainQuery = [self getKeychainQuery:service];
//Delete old item before add new item
SecItemDelete((__bridge_retained CFDictionaryRef)keychainQuery);
//Add new object to search dictionary(Attention:the data format)
[keychainQuery setObject:[NSKeyedArchiver archivedDataWithRootObject:data] forKey:(__bridge_transfer id)kSecValueData];
//Add item to keychain with the search dictionary
SecItemAdd((__bridge_retained CFDictionaryRef)keychainQuery, NULL);
} + (id)load:(NSString *)service {
id ret = nil;
NSMutableDictionary *keychainQuery = [self getKeychainQuery:service];
//Configure the search setting
[keychainQuery setObject:(id)kCFBooleanTrue forKey:(__bridge_transfer id)kSecReturnData];
[keychainQuery setObject:(__bridge_transfer id)kSecMatchLimitOne forKey:(__bridge_transfer id)kSecMatchLimit];
CFDataRef keyData = NULL;
if (SecItemCopyMatching((__bridge_retained CFDictionaryRef)keychainQuery, (CFTypeRef *)&keyData) == noErr) {
@try {
ret = [NSKeyedUnarchiver unarchiveObjectWithData:(__bridge_transfer NSData *)keyData];
} @catch (NSException *e) { } @finally {
}
}
return ret;
} + (void)delete:(NSString *)service {
NSMutableDictionary *keychainQuery = [self getKeychainQuery:service];
SecItemDelete((__bridge_retained CFDictionaryRef)keychainQuery);
} @end

使用:NSLog(@"%@",[MyUUIDManager getUUID]);

//如果uuid为空

if(!uuid){
// 获取UUID 这个是要引入<AdSupport/AdSupport.h>的
if ( [[ASIdentifierManager sharedManager] isAdvertisingTrackingEnabled] ) {
uuid = [[[ASIdentifierManager sharedManager] advertisingIdentifier] UUIDString];
return uuid;
}else{
return @"";
}
}

oc唯一标时一部设备的更多相关文章

  1. SYN1610型B码时统设备

       SYN1610型B码时统设备 产品概述 SYN1610型B码时统设备是由西安同步电子科技有限公司精心设计.自行研发生产的一款模块化配置的通用性时统终端,可接收北斗/ GPS信号/ IRIG-B码 ...

  2. 痞子衡嵌入式:可通过USB Device Path来唯一指定i.MXRT设备进行ROM/Flashloader通信

    大家好,我是痞子衡,是正经搞技术的痞子.今天痞子衡给大家介绍的是通过USB Device Path来唯一指定i.MXRT设备进行ROM/Flashloader通信. i.MXRT系列高性能微控制器从2 ...

  3. SYN3305A型 小型时统设备

       SYN3305A型  小型时统设备 产品概述 SYN3305A型小型时统设备是由西安同步电子科技有限公司精心设计.自行研发生产的一款高准确度的锁相石英频率标准.内装OCX0恒温晶体振荡器,利用G ...

  4. iOS开发——底层OC篇&运行时常用

    运行时常用 什么是Runtime(前面的文章已经说的很清楚了,这里就简单的介绍一下) 我们写的代码在程序运行过程中都会被转化成runtime的C代码执行,例如[target doSomething]; ...

  5. iOS OC环信实时语音切换听筒免提听不到声音报错:AVAudioSessionErrorCodeBadParam

    出现这个报错:AVAudioSessionErrorCodeBadParam 先看看你的问题是不是在切换听筒免提的时候 听不到声音了, 不是的可以继续搜索去了   问题在这里 把圈住的那个货换成这个就 ...

  6. 为什么说OC是运行时语言?什么是动态类型、动态绑定、动态加载?

    转载:https://www.cnblogs.com/dxb123456/p/5525343.html 动态: 主要是将数据类型的确定由编译时,推迟到了运行时. 这个问题其实浅涉及到两个概念,运行时和 ...

  7. oc的运行时系统

    Objective-C is a class-based object system. Each object is an instance of some class; the object's i ...

  8. Mysql使用Java UUID作为唯一值时使用前缀索引测试

    Mysql可以使用字符串前缀 作为索引 以节约空间. 下面我们以 Java的UUID 生成的 32位(移除UUID中的 中划线)字符串 来做一下 测试. 表结构: CREATE TABLE `test ...

  9. linux 在 open 时复制设备

    管理存取控制的另一个技术是创建设备的不同的私有拷贝, 根据打开它的进程. 明显地, 这只当设备没有绑定到一个硬件实体时有可能; scull 是一个这样的"软件"设备 的例子. /d ...

随机推荐

  1. 安装webstrom,免激活长久使用

    1.在jetbrain官网下载最新版webstrom, 2.安装webstrom,不建议安装在c盘 3.安装时选择试用三十天 接下来就很重要: 首先将系统时间改到未来的某天,或者你未来写不动代码的一天 ...

  2. log设置

    1.log的设置方式 .在 runtime setting中可以设置log的生成方式:默认的log方式:Enable logging选中,log option是Send messages only w ...

  3. thinkphp 注册验证

    遇到用户注册等情况时,如果等用户输入所有信息,点击注册按钮提交后,再验证输入是否正确,体验很不好,而且很浪费用户的时间,增加注册成本,这里提供一个例子,演示了怎么使用ajax进行单步验证,使用thin ...

  4. JS 点击复制Copy

    1.实现点击按钮,复制文本框中的的内容 1 <script type="text/javascript"> 2 function copyUrl2() 3 { 4 va ...

  5. 网页SEO内容

    关于网页根目录下的robots.txt文件的部分疑问 robots.txt书写语法:第一条:User-agent,后接搜索引擎的蜘蛛名称第二条:Disallow,填写要拦截的部分经典语法:User-a ...

  6. MVC3+EF4.1学习系列(二)-------基础的增删改查和持久对象的生命周期变化

    上篇文章中 我们已经创建了EF4.1基于code first的例子  有了数据库 并初始化了一些数据  今天这里写基础的增删改查和持久对象的生命周期变化 学习下原文先把运行好的原图贴来上~~ 一.创建 ...

  7. tomcat下获取当前路径的url中含有空格解决方法

    参考博文(http://www.360doc.com/content/11/1009/17/4602013_154657565.shtml) web项目发布到Tomcat之后,如果tomcat是安装在 ...

  8. NOIP2012-普及组复赛-第一题-质因数分解

    题目描述 Description 已知正整数n是两个不同的质数的乘积,试求出两者中较大的那个质数.  输入输出格式 Input/output 输入格式:输入只有一行,包含一个正整数n.输出格式:输出只 ...

  9. Openjudge-计算概论(A)-找和为K的两个元素

    描述: 在一个长度为n(n < 1000)的整数序列中,判断是否存在某两个元素之和为k. 输入第一行输入序列的长度n和k,用空格分开.第二行输入序列中的n个整数,用空格分开.输出如果存在某两个元 ...

  10. 一把刀终极配置Win7/8版 v2.0 绿色版

    软件名称: 一把刀终极配置Win7/8版 软件语言: 简体中文 授权方式: 免费软件 运行环境: Win8 / Win7 软件大小: 1.3MB 图片预览: 软件简介: 一把刀终极配置 For Win ...