Flutter Engine
FlutterEngineTest.mm
Go to the documentation of this file.
1 // Copyright 2013 The Flutter Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #import <OCMock/OCMock.h>
6 #import <XCTest/XCTest.h>
7 
8 #import "flutter/shell/platform/darwin/common/framework/Headers/FlutterMacros.h"
9 #import "flutter/shell/platform/darwin/ios/framework/Source/FlutterBinaryMessengerRelay.h"
10 #import "flutter/shell/platform/darwin/ios/framework/Source/FlutterEngine_Test.h"
11 
13 
14 @interface FlutterEngineTest : XCTestCase
15 @end
16 
17 @implementation FlutterEngineTest
18 
19 - (void)setUp {
20 }
21 
22 - (void)tearDown {
23 }
24 
25 - (void)testCreate {
26  id project = OCMClassMock([FlutterDartProject class]);
27  FlutterEngine* engine = [[FlutterEngine alloc] initWithName:@"foobar" project:project];
28  XCTAssertNotNil(engine);
29 }
30 
31 - (void)testDeallocated {
32  __weak FlutterEngine* weakEngine = nil;
33  {
34  FlutterEngine* engine = [[FlutterEngine alloc] initWithName:@"foobar"];
35  weakEngine = engine;
36  [engine run];
37  XCTAssertNotNil(weakEngine);
38  }
39  XCTAssertNil(weakEngine);
40 }
41 
42 - (void)testSendMessageBeforeRun {
43  id project = OCMClassMock([FlutterDartProject class]);
44  FlutterEngine* engine = [[FlutterEngine alloc] initWithName:@"foobar" project:project];
45  XCTAssertNotNil(engine);
46  XCTAssertThrows([engine.binaryMessenger
47  sendOnChannel:@"foo"
48  message:[@"bar" dataUsingEncoding:NSUTF8StringEncoding]
49  binaryReply:nil]);
50 }
51 
52 - (void)testSetMessageHandlerBeforeRun {
53  id project = OCMClassMock([FlutterDartProject class]);
54  FlutterEngine* engine = [[FlutterEngine alloc] initWithName:@"foobar" project:project];
55  XCTAssertNotNil(engine);
56  XCTAssertThrows([engine.binaryMessenger
57  setMessageHandlerOnChannel:@"foo"
58  binaryMessageHandler:^(NSData* _Nullable message, FlutterBinaryReply _Nonnull reply){
59 
60  }]);
61 }
62 
63 - (void)testNilSetMessageHandlerBeforeRun {
64  id project = OCMClassMock([FlutterDartProject class]);
65  FlutterEngine* engine = [[FlutterEngine alloc] initWithName:@"foobar" project:project];
66  XCTAssertNotNil(engine);
67  XCTAssertNoThrow([engine.binaryMessenger setMessageHandlerOnChannel:@"foo"
68  binaryMessageHandler:nil]);
69 }
70 
71 - (void)testNotifyPluginOfDealloc {
72  id plugin = OCMProtocolMock(@protocol(FlutterPlugin));
73  OCMStub([plugin detachFromEngineForRegistrar:[OCMArg any]]);
74  {
75  id project = OCMClassMock([FlutterDartProject class]);
76  FlutterEngine* engine = [[FlutterEngine alloc] initWithName:@"engine" project:project];
77  NSObject<FlutterPluginRegistrar>* registrar = [engine registrarForPlugin:@"plugin"];
78  [registrar publish:plugin];
79  engine = nil;
80  }
81  OCMVerify([plugin detachFromEngineForRegistrar:[OCMArg any]]);
82 }
83 
84 - (void)testRunningInitialRouteSendsNavigationMessage {
85  id mockBinaryMessenger = OCMClassMock([FlutterBinaryMessengerRelay class]);
86 
87  FlutterEngine* engine = [[FlutterEngine alloc] init];
88  [engine setBinaryMessenger:mockBinaryMessenger];
89 
90  // Run with an initial route.
91  [engine runWithEntrypoint:FlutterDefaultDartEntrypoint initialRoute:@"test"];
92 
93  // Now check that an encoded method call has been made on the binary messenger to set the
94  // initial route to "test".
95  FlutterMethodCall* setInitialRouteMethodCall =
96  [FlutterMethodCall methodCallWithMethodName:@"setInitialRoute" arguments:@"test"];
97  NSData* encodedSetInitialRouteMethod =
98  [[FlutterJSONMethodCodec sharedInstance] encodeMethodCall:setInitialRouteMethodCall];
99  OCMVerify([mockBinaryMessenger sendOnChannel:@"flutter/navigation"
100  message:encodedSetInitialRouteMethod]);
101 }
102 
103 - (void)testWaitForFirstFrameTimeout {
104  FlutterEngine* engine = [[FlutterEngine alloc] initWithName:@"foobar"];
105  [engine run];
106  XCTestExpectation* timeoutFirstFrame = [self expectationWithDescription:@"timeoutFirstFrame"];
107  [engine waitForFirstFrame:0.1
108  callback:^(BOOL didTimeout) {
109  if (timeoutFirstFrame) {
110  [timeoutFirstFrame fulfill];
111  }
112  }];
113  [self waitForExpectationsWithTimeout:1 handler:nil];
114 }
115 
116 @end
void waitForFirstFrame:callback:(NSTimeInterval timeout, [callback] void(^ callback)(BOOL didTimeout))
NSObject< FlutterBinaryMessenger > * binaryMessenger
NS_ASSUME_NONNULL_BEGIN typedef void(^ FlutterBinaryReply)(NSData *_Nullable reply)
instancetype methodCallWithMethodName:arguments:(NSString *method, [arguments] id _Nullable arguments)
void setBinaryMessenger:(FlutterBinaryMessengerRelay *binaryMessenger)
#define FLUTTER_ASSERT_ARC
Definition: FlutterMacros.h:44
BOOL runWithEntrypoint:initialRoute:(nullable NSString *entrypoint, [initialRoute] nullable NSString *initialRoute)