Kache.m 7.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262
  1. //
  2. // Kache.m
  3. // KacheDemo
  4. //
  5. // Created by jiajun on 7/25/12.
  6. // Copyright (c) 2012 __MyCompanyName__. All rights reserved.
  7. //
  8. #define KACHE_DEFAULT_POOL_NAME @"kache_default_pool_name_LKJHGFDWQSFASRTYUIOP:"
  9. #define KACHE_DEFAULT_QUEUE_NAME @"kache_default_queue_name_QWEDFVHUIOPPLMUYTRDX:"
  10. #import "KConfig.h"
  11. #import "KHolder.h"
  12. #import "KPool.h"
  13. #import "KQueue.h"
  14. #import "Kache.h"
  15. @interface Kache ()
  16. @property (strong, nonatomic) KHolder *holder;
  17. @property (strong, nonatomic) NSMutableDictionary *pools;
  18. @property (strong, nonatomic) NSMutableDictionary *queues;
  19. @end
  20. @implementation Kache
  21. @synthesize filetoken = _filetoken;
  22. @synthesize holder = _holder;
  23. @synthesize pools = _pools;
  24. @synthesize queues = _queues;
  25. #pragma mark static for default
  26. + (Kache *)instance {
  27. static Kache *obj = nil;
  28. if (nil == obj) {
  29. obj = [[Kache alloc] init];
  30. }
  31. return obj;
  32. }
  33. + (void)setValue:(id)value forKey:(NSString *)key expiredAfter:(NSInteger)duration {
  34. return [[Kache instance] setValue:value forKey:key expiredAfter:duration];
  35. }
  36. + (void)setValue:(id)value inDefaultPoolForKey:(NSString *)key expiredAfter:(NSInteger)duration {
  37. return [[Kache instance] setValue:value inPool:nil forKey:key expiredAfter:duration];
  38. }
  39. + (void)pushValue:(id)value {
  40. return [[Kache instance] pushValue:value toQueue:nil];
  41. }
  42. + (id)popValue {
  43. return [[Kache instance] popFromQueue:nil];
  44. }
  45. + (id)valueForKey:(NSString *)key {
  46. return [[Kache instance] valueForKey:key];
  47. }
  48. // Make sure the Pool exsists. Use newPoolWithName:size: to create a new Pool.
  49. + (void)setValue:(id)value inPool:(NSString *)name forKey:(NSString *)key expiredAfter:(NSInteger)duration {
  50. return [[Kache instance] setValue:value inPool:name forKey:key expiredAfter:duration];
  51. }
  52. // Make sure the Queue exsists. Use newQueueWithName:size: to create a new Queue.
  53. + (void)pushValue:(id)value toQueue:(NSString *)name {
  54. return [[Kache instance] pushValue:value toQueue:name];
  55. }
  56. + (id)popFromQueue:(NSString *)name {
  57. return [[Kache instance] popFromQueue:name];
  58. }
  59. + (void)newQueueWithName:(NSString *)name size:(NSInteger)size {
  60. return [[Kache instance] newQueueWithName:name size:size];
  61. }
  62. + (void)newPoolWithName:(NSString *)name size:(NSInteger)size {
  63. return [[Kache instance] newPoolWithName:name size:size];
  64. }
  65. + (void)saveToStorage {
  66. return [[Kache instance] save];
  67. }
  68. + (void)loadFromStorage {
  69. return [[Kache instance] load];
  70. }
  71. #pragma mark - init
  72. - (id)init
  73. {
  74. return [self initWithFiletoken:@""];
  75. }
  76. // Spcify a FileToken, Kache will save the data into a different place.
  77. - (id)initWithFiletoken:(NSString *)aFiletoken
  78. {
  79. self = [super init];
  80. if (self) {
  81. self.queues = [[NSMutableDictionary alloc] init];
  82. self.pools = [[NSMutableDictionary alloc] init];
  83. self.holder = [[KHolder alloc] init];
  84. [self newPoolWithName:nil size:0];
  85. [self newQueueWithName:nil size:0];
  86. self.filetoken = aFiletoken;
  87. return self;
  88. }
  89. return nil;
  90. }
  91. #pragma mark - public
  92. - (void)setValue:(id)value forKey:(NSString *)key expiredAfter:(NSInteger)duration
  93. {
  94. [self.holder setValue:value forKey:key expiredAfter:duration];
  95. }
  96. // Make sure the Pool exsists. Use newPoolWithName:size: to create a new Pool.
  97. - (void)setValue:(id)value inPool:(NSString *)name forKey:(NSString *)key expiredAfter:(NSInteger)duration
  98. {
  99. if (nil == name || 0 >= [name length]) {
  100. name = KACHE_DEFAULT_POOL_NAME;
  101. }
  102. if ([[self.pools allKeys] containsObject:name]) {
  103. KPool *pool = [self.pools objectForKey:name];
  104. [pool setValue:value forKey:key expiredAfter:duration];
  105. }
  106. }
  107. // Make sure the Queue exsists. Use newQueueWithName:size: to create a new Queue.
  108. - (void)pushValue:(id)value toQueue:(NSString *)name
  109. {
  110. if (nil == name || 0 >= [name length]) {
  111. name = KACHE_DEFAULT_QUEUE_NAME;
  112. }
  113. if ([[self.queues allKeys] containsObject:name]) {
  114. KQueue *queue = [self.queues objectForKey:name];
  115. [queue push:value];
  116. }
  117. }
  118. - (id)popFromQueue:(NSString *)name
  119. {
  120. if (nil == name || 0 >= [name length]) {
  121. name = KACHE_DEFAULT_QUEUE_NAME;
  122. }
  123. if ([[self.queues allKeys] containsObject:name]) {
  124. KQueue *queue = [self.queues objectForKey:name];
  125. return [queue pop];
  126. }
  127. return nil;
  128. }
  129. - (id)valueForKey:(NSString *)key
  130. {
  131. return [self.holder valueForKey:key];
  132. }
  133. - (void)newQueueWithName:(NSString *)name size:(NSInteger)size
  134. {
  135. if (nil == name || 0 >= [name length]) {
  136. name = KACHE_DEFAULT_QUEUE_NAME;
  137. }
  138. if (! [[self.queues allKeys] containsObject:name]) {
  139. KQueue *queue = [[KQueue alloc] initWithHolder:self.holder];
  140. if (0 < size) {
  141. queue.size = size;
  142. }
  143. queue.name = name;
  144. [self.queues setValue:queue
  145. forKey:name];
  146. }
  147. }
  148. - (void)newPoolWithName:(NSString *)name size:(NSInteger)size;
  149. {
  150. if (nil == name || 0 >= [name length]) {
  151. name = KACHE_DEFAULT_POOL_NAME;
  152. }
  153. if (! [[self.pools allKeys] containsObject:name]) {
  154. KPool *pool = [[KPool alloc] initWithHolder:self.holder];
  155. if (0 < size) {
  156. pool.size = size;
  157. }
  158. pool.name = name;
  159. [self.pools setValue:pool
  160. forKey:name];
  161. }
  162. }
  163. - (void)save {
  164. NSMutableArray *queueArray = [[NSMutableArray alloc] init];
  165. NSMutableArray *poolArray = [[NSMutableArray alloc] init];
  166. for (KQueue *queue in [self.queues objectEnumerator]) {
  167. [queueArray addObject:[queue serialize]];
  168. }
  169. for (KPool *pool in [self.pools objectEnumerator]) {
  170. [poolArray addObject:[pool serialize]];
  171. }
  172. NSDictionary *kacheDict = [[NSDictionary alloc] initWithObjectsAndKeys:
  173. [self.holder serialize], @"holder",
  174. queueArray, @"queues",
  175. poolArray, @"pools",
  176. nil];
  177. NSArray *paths = NSSearchPathForDirectoriesInDomains(NSLibraryDirectory, NSUserDomainMask, YES);
  178. NSString *libDirectory = [paths objectAtIndex:0];
  179. NSString *path = @"Caches/KACHE_STORAGE_FILE_QERFCVBJKOL:";
  180. if (self.filetoken) {
  181. path = [path stringByAppendingString:self.filetoken];
  182. }
  183. NSString *filePath = [libDirectory stringByAppendingPathComponent:path];
  184. NSData *d = [NSKeyedArchiver archivedDataWithRootObject:kacheDict];
  185. [d writeToFile:filePath atomically:YES];
  186. }
  187. - (void)load {
  188. NSArray *paths = NSSearchPathForDirectoriesInDomains(NSLibraryDirectory, NSUserDomainMask, YES);
  189. NSString *libDirectory = [paths objectAtIndex:0];
  190. NSString *path = @"Caches/KACHE_STORAGE_FILE_QERFCVBJKOL:";
  191. if (self.filetoken) {
  192. path = [path stringByAppendingString:self.filetoken];
  193. }
  194. NSString *filePath = [libDirectory stringByAppendingPathComponent:path];
  195. NSData *d = [NSData dataWithContentsOfFile:filePath];
  196. NSDictionary *kacheDict = [NSDictionary dictionaryWithDictionary:
  197. [NSKeyedUnarchiver unarchiveObjectWithData:d]];
  198. if (kacheDict && 0 < [kacheDict count]) {
  199. [self.holder unserializeFrom:[kacheDict objectForKey:@"holder"]];
  200. for (NSDictionary *queueDict in [kacheDict objectForKey:@"queues"]) {
  201. KQueue *queue = [[KQueue alloc] initWithHolder:self.holder];
  202. [queue unserializeFrom:queueDict];
  203. [self.queues setValue:queue forKey:[queueDict objectForKey:@"name"]];
  204. }
  205. for (NSDictionary *poolDict in [kacheDict objectForKey:@"pools"]) {
  206. KPool *pool = [[KPool alloc] initWithHolder:self.holder];
  207. [pool unserializeFrom:poolDict];
  208. [self.pools setValue:pool forKey:[poolDict objectForKey:@"name"]];
  209. }
  210. }
  211. }
  212. @end