@@ -27,8 +27,8 @@ - (void)syncTagsForBlog:(Blog *)blog
2727 [self handleError: error forBlog: blog withFailure: failure];
2828 return ;
2929 }
30-
31- NSArray *tags = [self mergeTagsWithRemoteTags : remoteTags blog : blog];
30+
31+ NSArray *tags = [self saveRemoteTags : remoteTags toBlog : blog];
3232 [[ContextManager sharedInstance ] saveContext: self .managedObjectContext];
3333
3434 if (success) {
@@ -58,10 +58,10 @@ - (void)syncTagsForBlog:(Blog *)blog
5858 [self handleError: error forBlog: blog withFailure: failure];
5959 return ;
6060 }
61-
62- NSArray *tags = [self mergeTagsWithRemoteTags : remoteTags blog : blog];
61+
62+ NSArray *tags = [self saveRemoteTags : remoteTags toBlog : blog];
6363 [[ContextManager sharedInstance ] saveContext: self .managedObjectContext];
64-
64+
6565 if (success) {
6666 success (tags);
6767 }
@@ -80,9 +80,9 @@ - (void)getTopTagsForBlog:(Blog *)blog
8080 [remote getTagsWithPaging: paging
8181 success: ^(NSArray <RemotePostTag *> *remoteTags) {
8282 [self .managedObjectContext performBlock: ^{
83- NSArray * tags = [remoteTags wp_map: ^PostTag *(RemotePostTag *remoteTag) {
84- return [ self tagFromRemoteTag: remoteTag blog: blog ];
85- }];
83+ NSArray <PostTag *> * tags = [self saveRemoteTags: remoteTags toBlog: blog];
84+ [[ContextManager sharedInstance ] saveContext: self .managedObjectContext ];
85+
8686 if (success) {
8787 success (tags);
8888 }
@@ -107,7 +107,7 @@ - (void)searchTagsWithName:(NSString *)nameQuery
107107 return ;
108108 }
109109
110- NSArray *tags = [self mergeTagsWithRemoteTags : remoteTags blog : blog];
110+ NSArray *tags = [self saveRemoteTags : remoteTags toBlog : blog];
111111 [[ContextManager sharedInstance ] saveContext: self .managedObjectContext];
112112
113113 if (success) {
@@ -169,55 +169,56 @@ - (void)saveTag:(PostTag*)tag
169169 return nil ;
170170}
171171
172- - (nullable NSArray <PostTag *> *)mergeTagsWithRemoteTags:(NSArray <RemotePostTag *> *)remoteTags
173- blog:(Blog *)blog
172+ - (NSArray <PostTag *> *)saveRemoteTags:(NSArray <RemotePostTag *> *)tags toBlog:(Blog *)blog
174173{
175- if (!remoteTags.count ) {
176- return nil ;
177- }
178-
179- NSMutableArray *tags = [NSMutableArray arrayWithCapacity: remoteTags.count];
180- for (RemotePostTag *remoteTag in remoteTags) {
181- [tags addObject: [self tagFromRemoteTag: remoteTag blog: blog]];
174+ if (tags.count == 0 ) {
175+ return [NSArray array ];
182176 }
183-
184- return [NSArray arrayWithArray: tags];
185- }
186177
187- - (PostTag *)tagFromRemoteTag:(RemotePostTag *)remoteTag
188- blog:(Blog *)blog
189- {
190- PostTag *tag = [self existingTagForRemoteTag: remoteTag blog: blog];
191- if (!tag) {
192- NSEntityDescription *entityDescription = [NSEntityDescription entityForName: [PostTag entityName ]
193- inManagedObjectContext: self .managedObjectContext];
194- tag = [[PostTag alloc ] initWithEntity: entityDescription insertIntoManagedObjectContext: self .managedObjectContext];
195- tag.tagID = remoteTag.tagID ;
196- tag.tagDescription = remoteTag.tagDescription ;
197- tag.blog = blog;
178+ NSManagedObjectContext *context = blog.managedObjectContext ;
179+ if (context == nil ) {
180+ return [NSArray array ];
198181 }
199-
200- tag.name = remoteTag.name ;
201- tag.slug = remoteTag.slug ;
202- tag.tagDescription = remoteTag.tagDescription ;
203- tag.postCount = remoteTag.postCount ;
204-
205- return tag;
206- }
207182
208- - (nullable PostTag *)existingTagForRemoteTag:(RemotePostTag *)remoteTag
209- blog:(Blog *)blog
210- {
183+ NSArray <NSNumber *> *remoteTagIDs = [tags wp_map: ^NSNumber *(RemotePostTag *remoteTag) {
184+ return remoteTag.tagID ;
185+ }];
186+
211187 NSFetchRequest *request = [NSFetchRequest fetchRequestWithEntityName: [PostTag entityName ]];
212- request.predicate = [NSPredicate predicateWithFormat: @" blog = %@ AND tagID = %@" , blog, remoteTag.tagID];
188+ request.predicate = [NSPredicate predicateWithFormat: @" blog = %@ AND tagID IN %@" , blog, remoteTagIDs];
189+
213190 NSError *error;
214- NSArray *tags = [self .managedObjectContext executeFetchRequest: request error: &error];
191+ NSArray <PostTag *> *existingTags = [context executeFetchRequest: request error: &error];
215192 if (error) {
216- DDLogError (@" Error when retrieving PostTag by tagID : %@ " , error);
217- return nil ;
193+ DDLogError (@" Error when retrieving PostTags by tagIDs : %@ " , error);
194+ return [ NSArray array ] ;
218195 }
219-
220- return [tags firstObject ];
196+
197+ NSMutableDictionary <NSNumber *, PostTag *> *existingTagsLookup = [NSMutableDictionary dictionaryWithCapacity: existingTags.count];
198+ for (PostTag *tag in existingTags) {
199+ existingTagsLookup[tag.tagID] = tag;
200+ }
201+
202+ NSMutableArray <PostTag *> *savedTags = [NSMutableArray array ];
203+ for (RemotePostTag *remote in tags) {
204+ PostTag *tag = existingTagsLookup[remote.tagID];
205+ if (tag == nil ) {
206+ NSEntityDescription *entityDescription = [NSEntityDescription entityForName: [PostTag entityName ]
207+ inManagedObjectContext: context];
208+ tag = [[PostTag alloc ] initWithEntity: entityDescription insertIntoManagedObjectContext: context];
209+ }
210+
211+ tag.tagID = remote.tagID ;
212+ tag.name = remote.name ;
213+ tag.slug = remote.slug ;
214+ tag.tagDescription = remote.tagDescription ;
215+ tag.postCount = remote.postCount ;
216+ tag.blog = blog;
217+
218+ [savedTags addObject: tag];
219+ }
220+
221+ return savedTags;
221222}
222223
223224- (void )saveNewTag:(PostTag *)tag
@@ -229,7 +230,7 @@ - (void)saveNewTag:(PostTag *)tag
229230 NSObject <TaxonomyServiceRemote> *remote = [self remoteForBlog: blog];
230231 [remote createTag: remoteTag success: ^(RemotePostTag * _Nonnull tag) {
231232 if (success) {
232- PostTag *localTag = [self tagFromRemoteTag: tag blog : blog];
233+ PostTag *localTag = [[ self saveRemoteTags: @[ tag] toBlog : blog] firstObject ];
233234 [[ContextManager sharedInstance ] saveContextAndWait: self .managedObjectContext];
234235 success (localTag);
235236 }
0 commit comments