Aspects is a delightful, simple library for aspect oriented programming.
YLHook enables Aspects to support functional programming.
We often write a lot of code to print logs or carry out statistical information everywhere. AOP provides a concise way to solve those Cross-cutting Concerns.
Aspects Demo:
[UIViewController aspect_hookSelector:@selector(viewWillAppear:) withOptions:AspectPositionBefore usingBlock:^(id<AspectInfo> aspectInfo, BOOL animated) {
NSLog(@"[%@]before viewWillAppear",[[aspectInfo instance] class]);
} error:NULL];
It's really very simple. But it's not clean when we need hook a lot of methods at one class.
It will be like this:
[UIViewController aspect_hookSelector:@selector(viewWillAppear:) withOptions:AspectPositionAfter usingBlock:^(id<AspectInfo> aspectInfo, BOOL animated) {
NSLog(@"[%@]after viewWillAppear",[[aspectInfo instance] class]);
} error:NULL];
[UIViewController aspect_hookSelector:@selector(viewDidLoad:) withOptions:AspectPositionBefore usingBlock:^(id<AspectInfo> aspectInfo, BOOL animated) {
NSLog(@"[%@]before viewDidLoad",[[aspectInfo instance] class]);
} error:NULL];
[UIViewController aspect_hookSelector:@selector(viewDidAppear:) withOptions:AspectPositionBefore usingBlock:^(id<AspectInfo> aspectInfo, BOOL animated) {
NSLog(@"[%@]before viewDidAppear",[[aspectInfo instance] class]);
} error:NULL];
Now, you can hook methods by this way:
[UIViewController yl_makeEvents:^(YLHookEventMaker *make) {
make.after.sel(viewDidLoad).block(^(id<AspectInfo> aspectInfo){
NSLog(@"[%@]after viewDidLoad",[[aspectInfo instance] class]);
});
make.before.sel(viewWillAppear:).block(^(id<AspectInfo> aspectInfo){
NSLog(@"[%@]before viewWillAppear",[[aspectInfo instance] class]);
});
make.before.sel(viewDidAppear:).block(^(id<AspectInfo> aspectInfo){
NSLog(@"[%@]before viewDidAppear",[[aspectInfo instance] class]);
});
}];
This style is like Masonry. In fact, I did refer to Masonry's realization.
You can easy to get an instance of YLHook by static method below:
+ (YLHook *)hookClass:(Class)cls;
+ (YLHook *)hookClassByName:(NSString *)name;
+ (YLHook *)hookInstance:(id)instance;
[[YLHook hookClassByName:@"UIViewController"] makeEvents:^(YLHookEventMaker *make) {
make.before.sel(viewDidAppear:).block(^(id<AspectInfo> aspectInfo){
NSLog(@"[%@]before viewDidAppear",[[aspectInfo instance] class]);
});
}];
\\ or
[UIViewController yl_makeEvents:^(YLHookEventMaker *make) {
make.before.sel(viewDidAppear:).block(^(id<AspectInfo> aspectInfo){
NSLog(@"[%@]before viewDidAppear",[[aspectInfo instance] class]);
});
}];
The excute
of YLHookEvent
is an optional semantic filler just like with
in Masonry.
If you use Cocoapods, add pod 'YLHook', '~> 1.0.2'
to your Podfile.
If not, drag the two files YLHook.h/m
into your project. This library relies on Aspects. And you also need drag Aspects.h/m
into your project.
YLHook is released under the MIT license. See LICENSE for details.
catch
sel
instead of selector
. And don't need to wirte @""
any more.