Lock in $30 Savings on PRO—Offer Ends Soon! ⏳
Speaker Deck
Features
Speaker Deck
PRO
Sign in
Sign up for free
Search
Search
Typhoon Explained
Search
Egor Tolstoy
June 04, 2016
Technology
1
230
Typhoon Explained
Slides for Mobius Conference 2016.
Egor Tolstoy
June 04, 2016
Tweet
Share
More Decks by Egor Tolstoy
See All by Egor Tolstoy
Как подсидеть тимлида
etolstoy
0
410
OKR без хайпа
etolstoy
1
340
OKR: инструкция по применению
etolstoy
0
570
Avito Mobile: State of the Union
etolstoy
0
170
Developer Experience: The Art of Building Spaceships
etolstoy
1
670
Выступайте
etolstoy
0
200
Улучшая performance review
etolstoy
0
1.6k
May the Code Review be with you [English]
etolstoy
1
260
May the Code Review be with you [Russian]
etolstoy
1
220
Other Decks in Technology
See All in Technology
Power of Kiro : あなたの㌔はパワステ搭載ですか?
r3_yamauchi
PRO
0
180
NIKKEI Tech Talk #41: セキュア・バイ・デザインからクラウド管理を考える
sekido
PRO
0
160
AI時代の新規LLMプロダクト開発: Findy Insightsを3ヶ月で立ち上げた舞台裏と振り返り
dakuon
0
230
AWS運用を効率化する!AWS Organizationsを軸にした一元管理の実践/nikkei-tech-talk-202512
nikkei_engineer_recruiting
0
110
マイクロサービスへの5年間 ぶっちゃけ何をしてどうなったか
joker1007
17
6.7k
AI-DLCを現場にインストールしてみた:プロトタイプ開発で分かったこと・やめたこと
recruitengineers
PRO
2
160
初めてのDatabricks AI/BI Genie
taka_aki
0
210
文字列の並び順 / Unicode Collation
tmtms
3
610
20251218_AIを活用した開発生産性向上の全社的な取り組みの進め方について / How to proceed with company-wide initiatives to improve development productivity using AI
yayoi_dd
0
140
Reinforcement Fine-tuning 基礎〜実践まで
ch6noota
0
190
mairuでつくるクレデンシャルレス開発環境 / Credential-less development environment using Mailru
mirakui
5
550
MySQLとPostgreSQLのコレーション / Collation of MySQL and PostgreSQL
tmtms
1
1k
Featured
See All Featured
Agile Leadership in an Agile Organization
kimpetersen
PRO
0
45
Exploring the relationship between traditional SERPs and Gen AI search
raygrieselhuber
PRO
2
3.4k
We Are The Robots
honzajavorek
0
110
Build your cross-platform service in a week with App Engine
jlugia
234
18k
The World Runs on Bad Software
bkeepers
PRO
72
12k
Helping Users Find Their Own Way: Creating Modern Search Experiences
danielanewman
31
3k
How to Grow Your eCommerce with AI & Automation
katarinadahlin
PRO
0
66
Max Prin - Stacking Signals: How International SEO Comes Together (And Falls Apart)
techseoconnect
PRO
0
46
For a Future-Friendly Web
brad_frost
180
10k
Visualization
eitanlees
150
16k
Code Reviewing Like a Champion
maltzj
527
40k
VelocityConf: Rendering Performance Case Studies
addyosmani
333
24k
Transcript
T yphoon explained Egor T olstoy @igrekde
2
3
4 Creating new project
5
6
7
8 - loadBarbershops - cacheBarbershops - reloadTableData - loadBarbershops -
cacheBarbershops - reloadTableData
9 BarberService
10 BarberService FakeBarberService
11 BarberService FakeBarberService VC 3 VC 4 VC 5 VC
6
12 @interface BarberListViewController() @property (nonatomic, strong) BarberServiceMain *service; @end
13 <BarberService> BarberServiceMain BarberServiceFake
14 @interface BarberListViewController() @property (nonatomic, strong) id<BarberService> service; @end
15 <BarberService> BarberServiceMain Assembly содержат создает создает VC 3 VC
4 VC 5
16 <BarberService> FakeBarberService Assembly содержат создает создает VC 3 VC
4 VC 5
Assembly Typhoon
18 Устройство Typhoon на трех пальцах Юзкейсы Легенды и мифы
19 Under the Hood
20 BarberViewController MapViewController BarberServiceMain BarberServiceFake Typhoon Component Factory componentForKey: Объект
21 BarberServiceMain type: (Class)BarberServiceMain key: barberServiceMainDefinition
22 BarberServiceMain type: (Class)BarberServiceMain key: barberServiceMainDefinition NetworkClient type: (Class)NetworkClient key:
networkClientDefinition BarberParser type: (Class)BarberParser key: networkClientDefinition
23 [BarberServiceMain new] [NetworkClient new] [BarberParser new] [BarberViewController new] [storyboard
instantiateViewController:]
24 Property Injection
25 <BarberService> BarberServiceMain
26 BarberListViewController type: (Class)BarberListViewController key: barberListViewControllerDefinition BarberService type: (Class)BarberServiceMain key:
barberServiceMainDefinition BarberListAssembly
27 @implementation BarberListAssembly - (BarberListViewController *)barberListViewControllerDefinition { return [TyphoonDefinition withClass:[BarberListViewController
class] configuration:^(TyphoonDefinition *definition) { [definition injectProperty:@selector(service) with:[self barberService]]; }]; } - (id<BarberService>)barberServiceMainDefinition { return [TyphoonDefinition withClass:[BarberServiceMain class]]; } @end
28 Modularizing Assemblies
29 <BarberService> BarberServiceMain <BarberService> BarberServiceMain
30 BarberListViewController BarberService BarberListAssembly BarberMapViewController BarberService BarberMapAssembly BarberService ServiceAssembly
31 @interface BarberListAssembly @property (nonatomic, strong) TyphoonAssembly<ServiceAssembly> *serviceAssembly; @end @implementation
BarberListAssembly - (BarberListViewController *)barberListViewControllerDefinition { return [TyphoonDefinition withClass:[BarberListViewController class] configuration:^(TyphoonDefinition *definition) { [definition injectProperty:@selector(service) with:[self.serviceAssembly barberService]]; }]; } @end
32 Scopes
33 <LocationService> LocationServiceMain CLLocationManager
34 BarberListViewController LocationService BarberListAssembly BarberMapViewController LocationService BarberMapAssembly LocationService ServiceAssembly scope:
TyphoonScopeSingleton
35 TyphoonScopeObjectGraph TyphoonScopePrototype TyphoonScopeSingleton TyphoonScopeLazySingleton TyphoonScopeWeakSingleton
36 @implementation ServiceAssembly - (id<BarberService>)barberServiceMainDefinition { return [TyphoonDefinition withClass:[BarberServiceMain class]
configuration:^(TyphoonDefinition *definition) { definition.scope = TyphoonScopeSingleton; }]; } @end
37 UI Injections
38 BarberViewController MapViewController BarberServiceMain BarberServiceFake Typhoon Component Factory componentForClass: [BarberViewController
class] [BarberViewController new]
39 JiggleAnimator Calculator1 Calculator2
40
41 @implementation ReusableViewAssembly - (MoustacheView *)moustacheView { return [TyphoonDefinition withClass:[MoustacheView
class] configuration:^(TyphoonDefinition *definition) { [definition useInitializer:@selector(view)]; [definition injectProperty:[self animator]]; }]; } @end @implementation MoustacheView + (MoustacheView *)view { return [[[NSBundle mainBundle] loadNibNamed:@"MoustacheView"]; } @end
42 Method Injection
43 MoustacheManager
44 @implementation ReusableViewAssembly - (MoustacheView *)moustacheView { return [TyphoonDefinition withClass:[MoustacheView
class] configuration:^(TyphoonDefinition *definition) { ... [definition injectProperty:[self manager]]; [definition injectMethod: @selector(subscribeToManager)]; }]; } @end @implementation MoustacheView - (void)subscribeToManager { [self.manager addMoustache:self]; } @end
45 Factories, attributes, options
46 Москва Питер
47 <ServiceFactory> BarberServiceMoscow BarberServicePiter ServiceAssembly Москва Питер
48 <ServiceFactory> BarberServiceMoscow BarberServicePiter ServiceAssembly Москва Питер
49 <ServiceFactory> BarberServiceMoscow BarberServicePiter ServiceAssembly
50 @interface BarberListAssembly @property (nonatomic, strong) TyphoonAssembly<ServiceAssembly> *serviceAssembly; @end @implementation
BarberListAssembly - (BarberListViewController *)barberListViewControllerDefinition { return [TyphoonDefinition withClass:[BarberListViewController class] configuration:^(TyphoonDefinition *definition) { [definition injectProperty:@selector(factory) with:[self.serviceAssembly]]; }]; } @end
51 @implementation ServiceAssembly - (id<BarberService>)barberServiceForCity:(NSString *)city { return [TyphoonDefinition withOption:city
matcher:^(TyphoonOptionMatcher *matcher) { [matcher caseEqual:@"Moscow" use:[self moscowBarberService]]; [matcher caseEqual:@"Piter" use:[self piterBarberService]]; }]; } @end
52 [matcher caseEqual:@"Moscow" use:[self moscowBarberService]]; [matcher caseEqual:@"Piter" use:[self piterBarberService]];
53 Config
54 AppDelegate TyphoonConfig(flurryKey) ApplicationAssembly TyphoonConfig(googleKey) { "config": { "flurryKey": "abcdef",
"googleKey" : "ghijkl" } } config.plist
55 @implementation ApplicationAssembly - (AppDelegate *)appDelegate { return [TyphoonDefinition withClass:[AppDelegate
class] configuration:^(TyphoonDefinition *definition) { [definition injectProperty:@selector(flurryKey) with:TyphoonConfig(@"config.flurryKey")]; [definition injectProperty:@selector(googleKey) with:TyphoonConfig(@"config.googleKey")]; }]; } @end
56 NSURL(http://mobiusconf.ru) MyStyle(#8732A9;17;HelveticeNeue-Regular)
57 PostCategories(top#cyr,0,cyr,cyr| top#noncyr,1,noncyr,noncyr)
58 Instance Postprocessor
59
60 BarberListRouter <Router> -openScreenWithIdentifier:(NSString *)identifier
61 RouterDecorator BarberListRouter Flurry/Google <Router> identifier identifier
62 @implementation AnalyticsPostProcessor - (id)postProcessInstance:(id)instance { if ([instance conformsToProtocol:@protocol(Router)]) {
return [DecoratedRouter decoratedRouterWith:instance]; } return instance; } @end
63 Integration T esting
64 <BarberService> BarberServiceMain <NetworkClient> NetworkClientMain
65 <BarberService> BarberServiceMain <NetworkClient> NetworkClientFake
66 BarberListViewController BarberService BarberListAssembly BarberService ServiceAssembly NetworkClient NetworkClientMain NetworkAssembly
67 BarberListViewController BarberService BarberListAssembly BarberService ServiceAssembly NetworkClient NetworkClientFake NetworkAssembly
68 - (void)setUp { ... TyphoonPatcher *patcher = [[TyphoonPatcher alloc]
init]; [patcher patchDefinitionWithSelector:@selector(networkClient) withObject:^id{ return [NetworkClientFake new]; }]; [barberListAssembly attachPostProcessor:patcher]; }
69 Autowiring
70 @interface BarberListViewControllerTests @property (nonatomic, strong) BarberListViewController *viewController; @property (nonatomic,
strong) id<BarberService> service; @property (nonatomic, strong) MoustacheView *view; @end - (void)setUp { ... self.viewController = [barberListAssembly viewController]; self.service = [serviceAssembly barberService]; self.view = [moustacheViewAssembly moustacheView]; }
71 @interface BarberListViewControllerTests @property (nonatomic, strong) InjectedClass(BarberListViewController) viewController; @property (nonatomic,
strong) InjectedProtocol(BarberService) service; @property (nonatomic, strong) InjectedClass(MoustacheView) view; @end - (void)setUp { ... [barberListAssembly inject:self]; }
72 Assembly Unit T ests
73 - (void)testThatAssemblyCreatesRouter { // given Class targetClass = [SettingsRouter
class]; NSArray *dependencies = @[ RamblerSelector(transitionHandler) ]; // when id result = [self.assembly routerSettingsModule]; // then [self verifyTargetDependency:result withClass:targetClass dependencies:dependencies]; }
74 https://github.com/rambler-ios/ RamblerTyphoonUtils
75 Legends
76 Typhoon работает со Swift
77 Но… там же свиззлинг!
78 Высокий порог вхождения
79 Сильное влияние на отладку
80 Но я же могу велосипедить... %
81 Finally
82 Устройство Typhoon на трех пальцах Юзкейсы Легенды и мифы
Egor T olstoy @igrekde Any magic, sufficiently analyzed is indistinguishable
from technology
[email protected]