From fd84b3cc5efcdf3cb660215e1eec69c97c78c5f2 Mon Sep 17 00:00:00 2001 From: michael starke Date: Thu, 17 Mar 2016 17:16:06 +0100 Subject: [PATCH] More stubbs on model proxies --- MacPass.xcodeproj/project.pbxproj | 12 ++++- MacPass/MPEntryProxy.h | 2 + MacPass/MPEntryProxy.m | 87 +++++++++++++++++++++++-------- 3 files changed, 78 insertions(+), 23 deletions(-) diff --git a/MacPass.xcodeproj/project.pbxproj b/MacPass.xcodeproj/project.pbxproj index c33937fe..c3acee05 100644 --- a/MacPass.xcodeproj/project.pbxproj +++ b/MacPass.xcodeproj/project.pbxproj @@ -965,8 +965,7 @@ 4C6B7C7C18BE7EB0001D5D77 /* MPDocument+HistoryBrowsing.m */, 4C0AF62D195C1F2B009E658D /* MPEntrySearchContext.h */, 4C0AF62E195C1F2B009E658D /* MPEntrySearchContext.m */, - 4CCCD83C1C8DFF20002B77B6 /* MPEntryProxy.h */, - 4CCCD83D1C8DFF20002B77B6 /* MPEntryProxy.m */, + 4CB44EEE1C972BFD00EE2D60 /* Proxies */, ); name = Model; sourceTree = ""; @@ -1299,6 +1298,15 @@ name = Protocolls; sourceTree = ""; }; + 4CB44EEE1C972BFD00EE2D60 /* Proxies */ = { + isa = PBXGroup; + children = ( + 4CCCD83C1C8DFF20002B77B6 /* MPEntryProxy.h */, + 4CCCD83D1C8DFF20002B77B6 /* MPEntryProxy.m */, + ); + name = Proxies; + sourceTree = ""; + }; 4CCFA12C1BF0CC7A0078E0A1 /* Databases */ = { isa = PBXGroup; children = ( diff --git a/MacPass/MPEntryProxy.h b/MacPass/MPEntryProxy.h index 448ecafc..e136cdbd 100644 --- a/MacPass/MPEntryProxy.h +++ b/MacPass/MPEntryProxy.h @@ -18,6 +18,8 @@ NS_ASSUME_NONNULL_BEGIN @interface MPEntryProxy : NSProxy +@property (strong, readonly) KPKEntry *entry; + - (instancetype)initWithEntry:(KPKEntry *)entry; @end diff --git a/MacPass/MPEntryProxy.m b/MacPass/MPEntryProxy.m index f07628fd..98b4cd7a 100644 --- a/MacPass/MPEntryProxy.m +++ b/MacPass/MPEntryProxy.m @@ -9,47 +9,92 @@ #import "MPEntryProxy.h" #import +@interface MPSubEntryProxy : NSProxy + +@property (weak) MPEntryProxy *entryProxy; +@property (nonatomic, readonly) id target; + +- (instancetype)initWithEntryProxy:(MPEntryProxy *)entryProxy; + +@end + +@implementation MPSubEntryProxy + +- (instancetype)initWithEntryProxy:(MPEntryProxy *)entryProxy { + _entryProxy = entryProxy; + return self; +} + +- (id)target { + return nil; +} + +@end + + +@interface MPAutotypeProxy : MPSubEntryProxy +@end + +@implementation MPAutotypeProxy + +- (id)target { + return self.entryProxy.entry.autotype; +} + +@end + +@interface MPTimeInfoProxy : MPSubEntryProxy +@end + +@implementation MPTimeInfoProxy + +- (id)target { + return self.entryProxy.entry.timeInfo; +} + +@end + +#pragma mark - + @interface MPEntryProxy () @property (strong) KPKEntry *entry; -@property (strong) NSMutableDictionary *valueStore; +@property (strong) KPKEntry *changedEntry; @end @implementation MPEntryProxy +- (NSSet *)mutatingSelectors { + static NSSet *set; + static dispatch_once_t onceToken; + dispatch_once(&onceToken, ^{ + set = [NSSet setWithArray:@[ [NSValue valueWithPointer:@selector(addCustomAttribute:)], + [NSValue valueWithPointer:@selector(removeCustomAttribute:)], + [NSValue valueWithPointer:@selector(addBinary:)], + [NSValue valueWithPointer:@selector(removeBinary:)], + [NSValue valueWithPointer:@selector(addAssociation:)], + [NSValue valueWithPointer:@selector(removeAssociation:)] ]]; + }); + return set; +} + - (instancetype)initWithEntry:(KPKEntry *)entry { if(!entry) { @throw [NSException exceptionWithName:NSInvalidArgumentException reason:nil userInfo:nil]; } _entry = entry; - _valueStore = [[NSMutableDictionary alloc] init]; return self; } - (void)forwardInvocation:(NSInvocation *)invocation { - NSLog(@"forwardInvocation: %@", NSStringFromSelector(invocation.selector)); NSString *seletor = NSStringFromSelector(invocation.selector); + if([[self mutatingSelectors] containsObject:[NSValue valueWithPointer:invocation.selector]]) { + NSLog(@"Mutation detected."); + } + if([seletor hasPrefix:@"set"]) { NSLog(@"forwardInvocation: setter detected"); - NSString *property = [seletor substringFromIndex:3].lowercaseString; // lowercase fist letter!!! - if(invocation.methodSignature.numberOfArguments == 3) { - id value; - [invocation getArgument:&value atIndex:2]; - NSLog(@"forwardInvocation: captured value %@", value); - if(value) { - self.valueStore[property] = value; - } - return; // captures getter, just return - } - } - id change = self.valueStore[seletor.lowercaseString]; - if(change) { - NSLog(@"forwardInvocation: hit cached value. Returning cache!"); - [invocation setReturnValue:&change]; - } - else { - [invocation invokeWithTarget:self.entry]; } }