2018-03-07 07:41:23 +00:00
|
|
|
// Copyright 2018 The Chromium Authors. All rights reserved.
|
|
|
|
// Use of this source code is governed by a BSD-style license that can be
|
|
|
|
// found in the LICENSE file.
|
2017-08-23 08:55:35 +00:00
|
|
|
|
2018-05-30 14:51:25 +00:00
|
|
|
import 'dart:async';
|
|
|
|
|
2018-03-07 07:41:23 +00:00
|
|
|
import 'package:file/memory.dart';
|
2018-05-25 21:53:10 +00:00
|
|
|
import 'package:flutter_tools/src/artifacts.dart';
|
2018-03-07 07:41:23 +00:00
|
|
|
import 'package:flutter_tools/src/base/file_system.dart';
|
|
|
|
import 'package:flutter_tools/src/base/io.dart';
|
2017-08-23 08:55:35 +00:00
|
|
|
import 'package:flutter_tools/src/build_info.dart';
|
|
|
|
import 'package:flutter_tools/src/ios/xcodeproj.dart';
|
2018-07-09 17:36:17 +00:00
|
|
|
import 'package:flutter_tools/src/project.dart';
|
2018-03-07 07:41:23 +00:00
|
|
|
import 'package:mockito/mockito.dart';
|
|
|
|
import 'package:platform/platform.dart';
|
|
|
|
import 'package:process/process.dart';
|
|
|
|
|
2018-08-15 03:33:58 +00:00
|
|
|
import '../src/common.dart';
|
2018-03-07 07:41:23 +00:00
|
|
|
import '../src/context.dart';
|
2018-09-04 16:12:24 +00:00
|
|
|
import '../src/pubspec_schema.dart';
|
2018-03-07 07:41:23 +00:00
|
|
|
|
|
|
|
const String xcodebuild = '/usr/bin/xcodebuild';
|
2017-08-23 08:55:35 +00:00
|
|
|
|
|
|
|
void main() {
|
2018-03-07 07:41:23 +00:00
|
|
|
group('xcodebuild versioning', () {
|
|
|
|
MockProcessManager mockProcessManager;
|
|
|
|
XcodeProjectInterpreter xcodeProjectInterpreter;
|
|
|
|
FakePlatform macOS;
|
|
|
|
FileSystem fs;
|
|
|
|
|
|
|
|
setUp(() {
|
2018-09-12 06:29:29 +00:00
|
|
|
mockProcessManager = MockProcessManager();
|
|
|
|
xcodeProjectInterpreter = XcodeProjectInterpreter();
|
2018-03-07 07:41:23 +00:00
|
|
|
macOS = fakePlatform('macos');
|
2018-09-12 06:29:29 +00:00
|
|
|
fs = MemoryFileSystem();
|
2018-03-07 07:41:23 +00:00
|
|
|
fs.file(xcodebuild).createSync(recursive: true);
|
|
|
|
});
|
|
|
|
|
|
|
|
void testUsingOsxContext(String description, dynamic testMethod()) {
|
|
|
|
testUsingContext(description, testMethod, overrides: <Type, Generator>{
|
|
|
|
ProcessManager: () => mockProcessManager,
|
|
|
|
Platform: () => macOS,
|
|
|
|
FileSystem: () => fs,
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
|
|
|
testUsingOsxContext('versionText returns null when xcodebuild is not installed', () {
|
|
|
|
when(mockProcessManager.runSync(<String>[xcodebuild, '-version']))
|
2018-08-02 10:02:32 +00:00
|
|
|
.thenThrow(const ProcessException(xcodebuild, <String>['-version']));
|
2018-03-07 07:41:23 +00:00
|
|
|
expect(xcodeProjectInterpreter.versionText, isNull);
|
|
|
|
});
|
|
|
|
|
|
|
|
testUsingOsxContext('versionText returns null when xcodebuild is not fully installed', () {
|
|
|
|
when(mockProcessManager.runSync(<String>[xcodebuild, '-version'])).thenReturn(
|
2018-09-12 06:29:29 +00:00
|
|
|
ProcessResult(
|
2018-03-07 07:41:23 +00:00
|
|
|
0,
|
|
|
|
1,
|
|
|
|
"xcode-select: error: tool 'xcodebuild' requires Xcode, "
|
|
|
|
"but active developer directory '/Library/Developer/CommandLineTools' "
|
|
|
|
'is a command line tools instance',
|
|
|
|
'',
|
|
|
|
),
|
|
|
|
);
|
|
|
|
expect(xcodeProjectInterpreter.versionText, isNull);
|
|
|
|
});
|
|
|
|
|
|
|
|
testUsingOsxContext('versionText returns formatted version text', () {
|
|
|
|
when(mockProcessManager.runSync(<String>[xcodebuild, '-version']))
|
2018-09-12 06:29:29 +00:00
|
|
|
.thenReturn(ProcessResult(1, 0, 'Xcode 8.3.3\nBuild version 8E3004b', ''));
|
2018-03-07 07:41:23 +00:00
|
|
|
expect(xcodeProjectInterpreter.versionText, 'Xcode 8.3.3, Build version 8E3004b');
|
|
|
|
});
|
|
|
|
|
|
|
|
testUsingOsxContext('versionText handles Xcode version string with unexpected format', () {
|
|
|
|
when(mockProcessManager.runSync(<String>[xcodebuild, '-version']))
|
2018-09-12 06:29:29 +00:00
|
|
|
.thenReturn(ProcessResult(1, 0, 'Xcode Ultra5000\nBuild version 8E3004b', ''));
|
2018-03-07 07:41:23 +00:00
|
|
|
expect(xcodeProjectInterpreter.versionText, 'Xcode Ultra5000, Build version 8E3004b');
|
|
|
|
});
|
|
|
|
|
|
|
|
testUsingOsxContext('majorVersion returns major version', () {
|
|
|
|
when(mockProcessManager.runSync(<String>[xcodebuild, '-version']))
|
2018-09-12 06:29:29 +00:00
|
|
|
.thenReturn(ProcessResult(1, 0, 'Xcode 8.3.3\nBuild version 8E3004b', ''));
|
2018-03-07 07:41:23 +00:00
|
|
|
expect(xcodeProjectInterpreter.majorVersion, 8);
|
|
|
|
});
|
|
|
|
|
|
|
|
testUsingOsxContext('majorVersion is null when version has unexpected format', () {
|
|
|
|
when(mockProcessManager.runSync(<String>[xcodebuild, '-version']))
|
2018-09-12 06:29:29 +00:00
|
|
|
.thenReturn(ProcessResult(1, 0, 'Xcode Ultra5000\nBuild version 8E3004b', ''));
|
2018-03-07 07:41:23 +00:00
|
|
|
expect(xcodeProjectInterpreter.majorVersion, isNull);
|
|
|
|
});
|
|
|
|
|
|
|
|
testUsingOsxContext('minorVersion returns minor version', () {
|
|
|
|
when(mockProcessManager.runSync(<String>[xcodebuild, '-version']))
|
2018-09-12 06:29:29 +00:00
|
|
|
.thenReturn(ProcessResult(1, 0, 'Xcode 8.3.3\nBuild version 8E3004b', ''));
|
2018-03-07 07:41:23 +00:00
|
|
|
expect(xcodeProjectInterpreter.minorVersion, 3);
|
|
|
|
});
|
|
|
|
|
|
|
|
testUsingOsxContext('minorVersion returns 0 when minor version is unspecified', () {
|
|
|
|
when(mockProcessManager.runSync(<String>[xcodebuild, '-version']))
|
2018-09-12 06:29:29 +00:00
|
|
|
.thenReturn(ProcessResult(1, 0, 'Xcode 8\nBuild version 8E3004b', ''));
|
2018-03-07 07:41:23 +00:00
|
|
|
expect(xcodeProjectInterpreter.minorVersion, 0);
|
|
|
|
});
|
|
|
|
|
|
|
|
testUsingOsxContext('minorVersion is null when version has unexpected format', () {
|
|
|
|
when(mockProcessManager.runSync(<String>[xcodebuild, '-version']))
|
2018-09-12 06:29:29 +00:00
|
|
|
.thenReturn(ProcessResult(1, 0, 'Xcode Ultra5000\nBuild version 8E3004b', ''));
|
2018-03-07 07:41:23 +00:00
|
|
|
expect(xcodeProjectInterpreter.minorVersion, isNull);
|
|
|
|
});
|
|
|
|
|
|
|
|
testUsingContext('isInstalled is false when not on MacOS', () {
|
|
|
|
fs.file(xcodebuild).deleteSync();
|
|
|
|
expect(xcodeProjectInterpreter.isInstalled, isFalse);
|
|
|
|
}, overrides: <Type, Generator>{
|
2019-03-01 07:17:55 +00:00
|
|
|
Platform: () => fakePlatform('notMacOS'),
|
2018-03-07 07:41:23 +00:00
|
|
|
});
|
|
|
|
|
|
|
|
testUsingOsxContext('isInstalled is false when xcodebuild does not exist', () {
|
|
|
|
fs.file(xcodebuild).deleteSync();
|
|
|
|
expect(xcodeProjectInterpreter.isInstalled, isFalse);
|
|
|
|
});
|
|
|
|
|
|
|
|
testUsingOsxContext('isInstalled is false when Xcode is not fully installed', () {
|
|
|
|
when(mockProcessManager.runSync(<String>[xcodebuild, '-version'])).thenReturn(
|
2018-09-12 06:29:29 +00:00
|
|
|
ProcessResult(
|
2018-03-07 07:41:23 +00:00
|
|
|
0,
|
|
|
|
1,
|
|
|
|
"xcode-select: error: tool 'xcodebuild' requires Xcode, "
|
|
|
|
"but active developer directory '/Library/Developer/CommandLineTools' "
|
|
|
|
'is a command line tools instance',
|
|
|
|
'',
|
|
|
|
),
|
|
|
|
);
|
|
|
|
expect(xcodeProjectInterpreter.isInstalled, isFalse);
|
|
|
|
});
|
|
|
|
|
|
|
|
testUsingOsxContext('isInstalled is false when version has unexpected format', () {
|
|
|
|
when(mockProcessManager.runSync(<String>[xcodebuild, '-version']))
|
2018-09-12 06:29:29 +00:00
|
|
|
.thenReturn(ProcessResult(1, 0, 'Xcode Ultra5000\nBuild version 8E3004b', ''));
|
2018-03-07 07:41:23 +00:00
|
|
|
expect(xcodeProjectInterpreter.isInstalled, isFalse);
|
|
|
|
});
|
|
|
|
|
|
|
|
testUsingOsxContext('isInstalled is true when version has expected format', () {
|
|
|
|
when(mockProcessManager.runSync(<String>[xcodebuild, '-version']))
|
2018-09-12 06:29:29 +00:00
|
|
|
.thenReturn(ProcessResult(1, 0, 'Xcode 8.3.3\nBuild version 8E3004b', ''));
|
2018-03-07 07:41:23 +00:00
|
|
|
expect(xcodeProjectInterpreter.isInstalled, isTrue);
|
|
|
|
});
|
|
|
|
});
|
2017-08-23 08:55:35 +00:00
|
|
|
group('Xcode project properties', () {
|
|
|
|
test('properties from default project can be parsed', () {
|
2018-02-01 06:51:26 +00:00
|
|
|
const String output = '''
|
2017-08-23 08:55:35 +00:00
|
|
|
Information about project "Runner":
|
|
|
|
Targets:
|
|
|
|
Runner
|
|
|
|
|
|
|
|
Build Configurations:
|
|
|
|
Debug
|
|
|
|
Release
|
|
|
|
|
|
|
|
If no build configuration is specified and -scheme is not passed then "Release" is used.
|
|
|
|
|
|
|
|
Schemes:
|
|
|
|
Runner
|
|
|
|
|
|
|
|
''';
|
2018-09-12 06:29:29 +00:00
|
|
|
final XcodeProjectInfo info = XcodeProjectInfo.fromXcodeBuildOutput(output);
|
2017-08-23 08:55:35 +00:00
|
|
|
expect(info.targets, <String>['Runner']);
|
|
|
|
expect(info.schemes, <String>['Runner']);
|
|
|
|
expect(info.buildConfigurations, <String>['Debug', 'Release']);
|
|
|
|
});
|
|
|
|
test('properties from project with custom schemes can be parsed', () {
|
2018-02-01 06:51:26 +00:00
|
|
|
const String output = '''
|
2017-08-23 08:55:35 +00:00
|
|
|
Information about project "Runner":
|
|
|
|
Targets:
|
|
|
|
Runner
|
|
|
|
|
|
|
|
Build Configurations:
|
|
|
|
Debug (Free)
|
|
|
|
Debug (Paid)
|
|
|
|
Release (Free)
|
|
|
|
Release (Paid)
|
|
|
|
|
|
|
|
If no build configuration is specified and -scheme is not passed then "Release (Free)" is used.
|
|
|
|
|
|
|
|
Schemes:
|
|
|
|
Free
|
|
|
|
Paid
|
|
|
|
|
|
|
|
''';
|
2018-09-12 06:29:29 +00:00
|
|
|
final XcodeProjectInfo info = XcodeProjectInfo.fromXcodeBuildOutput(output);
|
2017-08-23 08:55:35 +00:00
|
|
|
expect(info.targets, <String>['Runner']);
|
|
|
|
expect(info.schemes, <String>['Free', 'Paid']);
|
|
|
|
expect(info.buildConfigurations, <String>['Debug (Free)', 'Debug (Paid)', 'Release (Free)', 'Release (Paid)']);
|
|
|
|
});
|
|
|
|
test('expected scheme for non-flavored build is Runner', () {
|
|
|
|
expect(XcodeProjectInfo.expectedSchemeFor(BuildInfo.debug), 'Runner');
|
|
|
|
expect(XcodeProjectInfo.expectedSchemeFor(BuildInfo.profile), 'Runner');
|
|
|
|
expect(XcodeProjectInfo.expectedSchemeFor(BuildInfo.release), 'Runner');
|
|
|
|
});
|
|
|
|
test('expected build configuration for non-flavored build is derived from BuildMode', () {
|
|
|
|
expect(XcodeProjectInfo.expectedBuildConfigurationFor(BuildInfo.debug, 'Runner'), 'Debug');
|
2018-10-31 23:37:53 +00:00
|
|
|
expect(XcodeProjectInfo.expectedBuildConfigurationFor(BuildInfo.profile, 'Runner'), 'Profile');
|
2017-08-23 08:55:35 +00:00
|
|
|
expect(XcodeProjectInfo.expectedBuildConfigurationFor(BuildInfo.release, 'Runner'), 'Release');
|
|
|
|
});
|
|
|
|
test('expected scheme for flavored build is the title-cased flavor', () {
|
|
|
|
expect(XcodeProjectInfo.expectedSchemeFor(const BuildInfo(BuildMode.debug, 'hello')), 'Hello');
|
|
|
|
expect(XcodeProjectInfo.expectedSchemeFor(const BuildInfo(BuildMode.profile, 'HELLO')), 'HELLO');
|
|
|
|
expect(XcodeProjectInfo.expectedSchemeFor(const BuildInfo(BuildMode.release, 'Hello')), 'Hello');
|
|
|
|
});
|
|
|
|
test('expected build configuration for flavored build is Mode-Flavor', () {
|
|
|
|
expect(XcodeProjectInfo.expectedBuildConfigurationFor(const BuildInfo(BuildMode.debug, 'hello'), 'Hello'), 'Debug-Hello');
|
2018-10-31 23:37:53 +00:00
|
|
|
expect(XcodeProjectInfo.expectedBuildConfigurationFor(const BuildInfo(BuildMode.profile, 'HELLO'), 'Hello'), 'Profile-Hello');
|
2017-08-23 08:55:35 +00:00
|
|
|
expect(XcodeProjectInfo.expectedBuildConfigurationFor(const BuildInfo(BuildMode.release, 'Hello'), 'Hello'), 'Release-Hello');
|
|
|
|
});
|
|
|
|
test('scheme for default project is Runner', () {
|
2018-09-12 06:29:29 +00:00
|
|
|
final XcodeProjectInfo info = XcodeProjectInfo(<String>['Runner'], <String>['Debug', 'Release'], <String>['Runner']);
|
2017-08-23 08:55:35 +00:00
|
|
|
expect(info.schemeFor(BuildInfo.debug), 'Runner');
|
|
|
|
expect(info.schemeFor(BuildInfo.profile), 'Runner');
|
|
|
|
expect(info.schemeFor(BuildInfo.release), 'Runner');
|
|
|
|
expect(info.schemeFor(const BuildInfo(BuildMode.debug, 'unknown')), isNull);
|
|
|
|
});
|
|
|
|
test('build configuration for default project is matched against BuildMode', () {
|
2018-10-31 23:37:53 +00:00
|
|
|
final XcodeProjectInfo info = XcodeProjectInfo(<String>['Runner'], <String>['Debug', 'Profile', 'Release'], <String>['Runner']);
|
2017-08-23 08:55:35 +00:00
|
|
|
expect(info.buildConfigurationFor(BuildInfo.debug, 'Runner'), 'Debug');
|
2018-10-31 23:37:53 +00:00
|
|
|
expect(info.buildConfigurationFor(BuildInfo.profile, 'Runner'), 'Profile');
|
2017-08-23 08:55:35 +00:00
|
|
|
expect(info.buildConfigurationFor(BuildInfo.release, 'Runner'), 'Release');
|
|
|
|
});
|
|
|
|
test('scheme for project with custom schemes is matched against flavor', () {
|
2018-09-12 06:29:29 +00:00
|
|
|
final XcodeProjectInfo info = XcodeProjectInfo(
|
2017-08-23 08:55:35 +00:00
|
|
|
<String>['Runner'],
|
|
|
|
<String>['Debug (Free)', 'Debug (Paid)', 'Release (Free)', 'Release (Paid)'],
|
|
|
|
<String>['Free', 'Paid'],
|
|
|
|
);
|
|
|
|
expect(info.schemeFor(const BuildInfo(BuildMode.debug, 'free')), 'Free');
|
|
|
|
expect(info.schemeFor(const BuildInfo(BuildMode.profile, 'Free')), 'Free');
|
|
|
|
expect(info.schemeFor(const BuildInfo(BuildMode.release, 'paid')), 'Paid');
|
|
|
|
expect(info.schemeFor(const BuildInfo(BuildMode.debug, null)), isNull);
|
|
|
|
expect(info.schemeFor(const BuildInfo(BuildMode.debug, 'unknown')), isNull);
|
|
|
|
});
|
|
|
|
test('build configuration for project with custom schemes is matched against BuildMode and flavor', () {
|
2018-09-12 06:29:29 +00:00
|
|
|
final XcodeProjectInfo info = XcodeProjectInfo(
|
2017-08-23 08:55:35 +00:00
|
|
|
<String>['Runner'],
|
2018-10-31 23:37:53 +00:00
|
|
|
<String>['debug (free)', 'Debug paid', 'profile - Free', 'Profile-Paid', 'release - Free', 'Release-Paid'],
|
2017-08-23 08:55:35 +00:00
|
|
|
<String>['Free', 'Paid'],
|
|
|
|
);
|
|
|
|
expect(info.buildConfigurationFor(const BuildInfo(BuildMode.debug, 'free'), 'Free'), 'debug (free)');
|
|
|
|
expect(info.buildConfigurationFor(const BuildInfo(BuildMode.debug, 'Paid'), 'Paid'), 'Debug paid');
|
2018-10-31 23:37:53 +00:00
|
|
|
expect(info.buildConfigurationFor(const BuildInfo(BuildMode.profile, 'FREE'), 'Free'), 'profile - Free');
|
2017-08-23 08:55:35 +00:00
|
|
|
expect(info.buildConfigurationFor(const BuildInfo(BuildMode.release, 'paid'), 'Paid'), 'Release-Paid');
|
|
|
|
});
|
|
|
|
test('build configuration for project with inconsistent naming is null', () {
|
2018-09-12 06:29:29 +00:00
|
|
|
final XcodeProjectInfo info = XcodeProjectInfo(
|
2017-08-23 08:55:35 +00:00
|
|
|
<String>['Runner'],
|
|
|
|
<String>['Debug-F', 'Dbg Paid', 'Rel Free', 'Release Full'],
|
|
|
|
<String>['Free', 'Paid'],
|
|
|
|
);
|
|
|
|
expect(info.buildConfigurationFor(const BuildInfo(BuildMode.debug, 'Free'), 'Free'), null);
|
|
|
|
expect(info.buildConfigurationFor(const BuildInfo(BuildMode.profile, 'Free'), 'Free'), null);
|
|
|
|
expect(info.buildConfigurationFor(const BuildInfo(BuildMode.release, 'Paid'), 'Paid'), null);
|
|
|
|
});
|
|
|
|
});
|
2018-05-25 21:53:10 +00:00
|
|
|
|
|
|
|
group('updateGeneratedXcodeProperties', () {
|
|
|
|
MockLocalEngineArtifacts mockArtifacts;
|
|
|
|
MockProcessManager mockProcessManager;
|
|
|
|
FakePlatform macOS;
|
|
|
|
FileSystem fs;
|
|
|
|
|
|
|
|
setUp(() {
|
2018-09-12 06:29:29 +00:00
|
|
|
fs = MemoryFileSystem();
|
|
|
|
mockArtifacts = MockLocalEngineArtifacts();
|
|
|
|
mockProcessManager = MockProcessManager();
|
2018-05-25 21:53:10 +00:00
|
|
|
macOS = fakePlatform('macos');
|
|
|
|
fs.file(xcodebuild).createSync(recursive: true);
|
|
|
|
});
|
|
|
|
|
|
|
|
void testUsingOsxContext(String description, dynamic testMethod()) {
|
|
|
|
testUsingContext(description, testMethod, overrides: <Type, Generator>{
|
|
|
|
Artifacts: () => mockArtifacts,
|
|
|
|
ProcessManager: () => mockProcessManager,
|
|
|
|
Platform: () => macOS,
|
|
|
|
FileSystem: () => fs,
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
2018-05-30 14:51:25 +00:00
|
|
|
testUsingOsxContext('sets ARCHS=armv7 when armv7 local engine is set', () async {
|
2019-04-16 04:02:20 +00:00
|
|
|
when(mockArtifacts.getArtifactPath(Artifact.flutterFramework,
|
|
|
|
platform: TargetPlatform.ios, mode: anyNamed('mode'))).thenReturn('engine');
|
2018-05-25 21:53:10 +00:00
|
|
|
when(mockArtifacts.engineOutPath).thenReturn(fs.path.join('out', 'ios_profile_arm'));
|
2018-06-28 12:35:00 +00:00
|
|
|
|
2019-06-10 20:16:09 +00:00
|
|
|
const BuildInfo buildInfo = BuildInfo(BuildMode.debug, null);
|
2019-04-29 15:21:32 +00:00
|
|
|
final FlutterProject project = FlutterProject.fromPath('path/to/project');
|
2018-07-20 06:00:30 +00:00
|
|
|
await updateGeneratedXcodeProperties(
|
|
|
|
project: project,
|
2018-05-25 21:53:10 +00:00
|
|
|
buildInfo: buildInfo,
|
|
|
|
);
|
|
|
|
|
|
|
|
final File config = fs.file('path/to/project/ios/Flutter/Generated.xcconfig');
|
|
|
|
expect(config.existsSync(), isTrue);
|
|
|
|
|
|
|
|
final String contents = config.readAsStringSync();
|
|
|
|
expect(contents.contains('ARCHS=armv7'), isTrue);
|
|
|
|
});
|
|
|
|
|
2018-05-30 21:53:35 +00:00
|
|
|
testUsingOsxContext('sets TRACK_WIDGET_CREATION=true when trackWidgetCreation is true', () async {
|
2019-04-16 04:02:20 +00:00
|
|
|
when(mockArtifacts.getArtifactPath(Artifact.flutterFramework,
|
|
|
|
platform: TargetPlatform.ios, mode: anyNamed('mode'))).thenReturn('engine');
|
2018-05-30 21:53:35 +00:00
|
|
|
when(mockArtifacts.engineOutPath).thenReturn(fs.path.join('out', 'ios_profile_arm'));
|
2019-06-10 20:16:09 +00:00
|
|
|
const BuildInfo buildInfo = BuildInfo(BuildMode.debug, null, trackWidgetCreation: true);
|
2019-04-29 15:21:32 +00:00
|
|
|
final FlutterProject project = FlutterProject.fromPath('path/to/project');
|
2018-07-20 06:00:30 +00:00
|
|
|
await updateGeneratedXcodeProperties(
|
|
|
|
project: project,
|
2018-05-30 21:53:35 +00:00
|
|
|
buildInfo: buildInfo,
|
|
|
|
);
|
|
|
|
|
|
|
|
final File config = fs.file('path/to/project/ios/Flutter/Generated.xcconfig');
|
|
|
|
expect(config.existsSync(), isTrue);
|
|
|
|
|
|
|
|
final String contents = config.readAsStringSync();
|
|
|
|
expect(contents.contains('TRACK_WIDGET_CREATION=true'), isTrue);
|
|
|
|
});
|
|
|
|
|
|
|
|
testUsingOsxContext('does not set TRACK_WIDGET_CREATION when trackWidgetCreation is false', () async {
|
2019-04-16 04:02:20 +00:00
|
|
|
when(mockArtifacts.getArtifactPath(Artifact.flutterFramework,
|
|
|
|
platform: TargetPlatform.ios, mode: anyNamed('mode'))).thenReturn('engine');
|
2018-05-30 21:53:35 +00:00
|
|
|
when(mockArtifacts.engineOutPath).thenReturn(fs.path.join('out', 'ios_profile_arm'));
|
2019-06-10 20:16:09 +00:00
|
|
|
const BuildInfo buildInfo = BuildInfo(BuildMode.debug, null);
|
2019-04-29 15:21:32 +00:00
|
|
|
final FlutterProject project = FlutterProject.fromPath('path/to/project');
|
2018-07-20 06:00:30 +00:00
|
|
|
await updateGeneratedXcodeProperties(
|
|
|
|
project: project,
|
2018-05-30 21:53:35 +00:00
|
|
|
buildInfo: buildInfo,
|
|
|
|
);
|
|
|
|
|
|
|
|
final File config = fs.file('path/to/project/ios/Flutter/Generated.xcconfig');
|
|
|
|
expect(config.existsSync(), isTrue);
|
|
|
|
|
|
|
|
final String contents = config.readAsStringSync();
|
|
|
|
expect(contents.contains('TRACK_WIDGET_CREATION=true'), isFalse);
|
|
|
|
});
|
|
|
|
|
2018-05-30 14:51:25 +00:00
|
|
|
testUsingOsxContext('sets ARCHS=armv7 when armv7 local engine is set', () async {
|
2019-04-16 04:02:20 +00:00
|
|
|
when(mockArtifacts.getArtifactPath(Artifact.flutterFramework,
|
|
|
|
platform: TargetPlatform.ios, mode: anyNamed('mode'))).thenReturn('engine');
|
2018-05-25 21:53:10 +00:00
|
|
|
when(mockArtifacts.engineOutPath).thenReturn(fs.path.join('out', 'ios_profile'));
|
2019-06-10 20:16:09 +00:00
|
|
|
const BuildInfo buildInfo = BuildInfo(BuildMode.debug, null);
|
2018-06-28 12:35:00 +00:00
|
|
|
|
2019-04-29 15:21:32 +00:00
|
|
|
final FlutterProject project = FlutterProject.fromPath('path/to/project');
|
2018-07-20 06:00:30 +00:00
|
|
|
await updateGeneratedXcodeProperties(
|
|
|
|
project: project,
|
2018-05-25 21:53:10 +00:00
|
|
|
buildInfo: buildInfo,
|
|
|
|
);
|
|
|
|
|
|
|
|
final File config = fs.file('path/to/project/ios/Flutter/Generated.xcconfig');
|
|
|
|
expect(config.existsSync(), isTrue);
|
|
|
|
|
|
|
|
final String contents = config.readAsStringSync();
|
|
|
|
expect(contents.contains('ARCHS=arm64'), isTrue);
|
|
|
|
});
|
2018-05-30 14:51:25 +00:00
|
|
|
|
|
|
|
String propertyFor(String key, File file) {
|
|
|
|
final List<String> properties = file
|
|
|
|
.readAsLinesSync()
|
|
|
|
.where((String line) => line.startsWith('$key='))
|
|
|
|
.map((String line) => line.split('=')[1])
|
|
|
|
.toList();
|
|
|
|
return properties.isEmpty ? null : properties.first;
|
|
|
|
}
|
|
|
|
|
|
|
|
Future<void> checkBuildVersion({
|
2018-06-28 12:35:00 +00:00
|
|
|
String manifestString,
|
2018-05-30 14:51:25 +00:00
|
|
|
BuildInfo buildInfo,
|
|
|
|
String expectedBuildName,
|
|
|
|
String expectedBuildNumber,
|
|
|
|
}) async {
|
2019-04-16 04:02:20 +00:00
|
|
|
when(mockArtifacts.getArtifactPath(Artifact.flutterFramework,
|
|
|
|
platform: TargetPlatform.ios, mode: anyNamed('mode'))).thenReturn('engine');
|
2018-07-09 17:36:17 +00:00
|
|
|
when(mockArtifacts.engineOutPath).thenReturn(fs.path.join('out', 'ios'));
|
|
|
|
|
|
|
|
final File manifestFile = fs.file('path/to/project/pubspec.yaml');
|
|
|
|
manifestFile.createSync(recursive: true);
|
|
|
|
manifestFile.writeAsStringSync(manifestString);
|
|
|
|
|
|
|
|
// write schemaData otherwise pubspec.yaml file can't be loaded
|
2018-09-04 16:12:24 +00:00
|
|
|
writeEmptySchemaFile(fs);
|
2018-05-30 14:51:25 +00:00
|
|
|
|
2018-07-20 06:00:30 +00:00
|
|
|
await updateGeneratedXcodeProperties(
|
2019-04-29 15:21:32 +00:00
|
|
|
project: FlutterProject.fromPath('path/to/project'),
|
2018-05-30 14:51:25 +00:00
|
|
|
buildInfo: buildInfo,
|
|
|
|
);
|
|
|
|
|
2018-07-09 17:36:17 +00:00
|
|
|
final File localPropertiesFile = fs.file('path/to/project/ios/Flutter/Generated.xcconfig');
|
2018-05-30 14:51:25 +00:00
|
|
|
expect(propertyFor('FLUTTER_BUILD_NAME', localPropertiesFile), expectedBuildName);
|
|
|
|
expect(propertyFor('FLUTTER_BUILD_NUMBER', localPropertiesFile), expectedBuildNumber);
|
|
|
|
}
|
|
|
|
|
2018-07-09 17:36:17 +00:00
|
|
|
testUsingOsxContext('extract build name and number from pubspec.yaml', () async {
|
2018-05-30 14:51:25 +00:00
|
|
|
const String manifest = '''
|
|
|
|
name: test
|
|
|
|
version: 1.0.0+1
|
|
|
|
dependencies:
|
|
|
|
flutter:
|
|
|
|
sdk: flutter
|
|
|
|
flutter:
|
|
|
|
''';
|
|
|
|
|
2018-08-02 10:02:32 +00:00
|
|
|
const BuildInfo buildInfo = BuildInfo(BuildMode.release, null);
|
2018-05-30 14:51:25 +00:00
|
|
|
await checkBuildVersion(
|
2018-06-28 12:35:00 +00:00
|
|
|
manifestString: manifest,
|
2018-05-30 14:51:25 +00:00
|
|
|
buildInfo: buildInfo,
|
|
|
|
expectedBuildName: '1.0.0',
|
|
|
|
expectedBuildNumber: '1',
|
|
|
|
);
|
|
|
|
});
|
|
|
|
|
2018-07-09 17:36:17 +00:00
|
|
|
testUsingOsxContext('extract build name from pubspec.yaml', () async {
|
2018-05-30 14:51:25 +00:00
|
|
|
const String manifest = '''
|
|
|
|
name: test
|
|
|
|
version: 1.0.0
|
|
|
|
dependencies:
|
|
|
|
flutter:
|
|
|
|
sdk: flutter
|
|
|
|
flutter:
|
|
|
|
''';
|
2018-08-02 10:02:32 +00:00
|
|
|
const BuildInfo buildInfo = BuildInfo(BuildMode.release, null);
|
2018-05-30 14:51:25 +00:00
|
|
|
await checkBuildVersion(
|
2018-06-28 12:35:00 +00:00
|
|
|
manifestString: manifest,
|
2018-05-30 14:51:25 +00:00
|
|
|
buildInfo: buildInfo,
|
|
|
|
expectedBuildName: '1.0.0',
|
|
|
|
expectedBuildNumber: null,
|
|
|
|
);
|
|
|
|
});
|
|
|
|
|
2018-07-09 17:36:17 +00:00
|
|
|
testUsingOsxContext('allow build info to override build name', () async {
|
2018-05-30 14:51:25 +00:00
|
|
|
const String manifest = '''
|
|
|
|
name: test
|
|
|
|
version: 1.0.0+1
|
|
|
|
dependencies:
|
|
|
|
flutter:
|
|
|
|
sdk: flutter
|
|
|
|
flutter:
|
|
|
|
''';
|
2018-08-02 10:02:32 +00:00
|
|
|
const BuildInfo buildInfo = BuildInfo(BuildMode.release, null, buildName: '1.0.2');
|
2018-05-30 14:51:25 +00:00
|
|
|
await checkBuildVersion(
|
2018-06-28 12:35:00 +00:00
|
|
|
manifestString: manifest,
|
2018-05-30 14:51:25 +00:00
|
|
|
buildInfo: buildInfo,
|
|
|
|
expectedBuildName: '1.0.2',
|
|
|
|
expectedBuildNumber: '1',
|
|
|
|
);
|
|
|
|
});
|
|
|
|
|
2018-07-09 17:36:17 +00:00
|
|
|
testUsingOsxContext('allow build info to override build number', () async {
|
2018-05-30 14:51:25 +00:00
|
|
|
const String manifest = '''
|
|
|
|
name: test
|
|
|
|
version: 1.0.0+1
|
|
|
|
dependencies:
|
|
|
|
flutter:
|
|
|
|
sdk: flutter
|
|
|
|
flutter:
|
|
|
|
''';
|
2019-02-13 15:48:03 +00:00
|
|
|
const BuildInfo buildInfo = BuildInfo(BuildMode.release, null, buildNumber: '3');
|
2018-05-30 14:51:25 +00:00
|
|
|
await checkBuildVersion(
|
2018-06-28 12:35:00 +00:00
|
|
|
manifestString: manifest,
|
2018-05-30 14:51:25 +00:00
|
|
|
buildInfo: buildInfo,
|
|
|
|
expectedBuildName: '1.0.0',
|
|
|
|
expectedBuildNumber: '3',
|
|
|
|
);
|
|
|
|
});
|
|
|
|
|
2018-07-09 17:36:17 +00:00
|
|
|
testUsingOsxContext('allow build info to override build name and number', () async {
|
2018-05-30 14:51:25 +00:00
|
|
|
const String manifest = '''
|
|
|
|
name: test
|
|
|
|
version: 1.0.0+1
|
|
|
|
dependencies:
|
|
|
|
flutter:
|
|
|
|
sdk: flutter
|
|
|
|
flutter:
|
|
|
|
''';
|
2019-02-13 15:48:03 +00:00
|
|
|
const BuildInfo buildInfo = BuildInfo(BuildMode.release, null, buildName: '1.0.2', buildNumber: '3');
|
2018-05-30 14:51:25 +00:00
|
|
|
await checkBuildVersion(
|
2018-06-28 12:35:00 +00:00
|
|
|
manifestString: manifest,
|
2018-05-30 14:51:25 +00:00
|
|
|
buildInfo: buildInfo,
|
|
|
|
expectedBuildName: '1.0.2',
|
|
|
|
expectedBuildNumber: '3',
|
|
|
|
);
|
|
|
|
});
|
|
|
|
|
2018-07-09 17:36:17 +00:00
|
|
|
testUsingOsxContext('allow build info to override build name and set number', () async {
|
2018-05-30 14:51:25 +00:00
|
|
|
const String manifest = '''
|
|
|
|
name: test
|
|
|
|
version: 1.0.0
|
|
|
|
dependencies:
|
|
|
|
flutter:
|
|
|
|
sdk: flutter
|
|
|
|
flutter:
|
|
|
|
''';
|
2019-02-13 15:48:03 +00:00
|
|
|
const BuildInfo buildInfo = BuildInfo(BuildMode.release, null, buildName: '1.0.2', buildNumber: '3');
|
2018-05-30 14:51:25 +00:00
|
|
|
await checkBuildVersion(
|
2018-06-28 12:35:00 +00:00
|
|
|
manifestString: manifest,
|
2018-05-30 14:51:25 +00:00
|
|
|
buildInfo: buildInfo,
|
|
|
|
expectedBuildName: '1.0.2',
|
|
|
|
expectedBuildNumber: '3',
|
|
|
|
);
|
|
|
|
});
|
|
|
|
|
2018-07-09 17:36:17 +00:00
|
|
|
testUsingOsxContext('allow build info to set build name and number', () async {
|
2018-05-30 14:51:25 +00:00
|
|
|
const String manifest = '''
|
|
|
|
name: test
|
|
|
|
dependencies:
|
|
|
|
flutter:
|
|
|
|
sdk: flutter
|
|
|
|
flutter:
|
|
|
|
''';
|
2019-02-13 15:48:03 +00:00
|
|
|
const BuildInfo buildInfo = BuildInfo(BuildMode.release, null, buildName: '1.0.2', buildNumber: '3');
|
2018-05-30 14:51:25 +00:00
|
|
|
await checkBuildVersion(
|
2018-06-28 12:35:00 +00:00
|
|
|
manifestString: manifest,
|
2018-05-30 14:51:25 +00:00
|
|
|
buildInfo: buildInfo,
|
|
|
|
expectedBuildName: '1.0.2',
|
|
|
|
expectedBuildNumber: '3',
|
|
|
|
);
|
|
|
|
});
|
|
|
|
});
|
2017-08-23 08:55:35 +00:00
|
|
|
}
|
2018-03-07 07:41:23 +00:00
|
|
|
|
|
|
|
Platform fakePlatform(String name) {
|
2018-09-12 06:29:29 +00:00
|
|
|
return FakePlatform.fromPlatform(const LocalPlatform())..operatingSystem = name;
|
2018-03-07 07:41:23 +00:00
|
|
|
}
|
|
|
|
|
2018-05-25 21:53:10 +00:00
|
|
|
class MockLocalEngineArtifacts extends Mock implements LocalEngineArtifacts {}
|
2018-03-07 07:41:23 +00:00
|
|
|
class MockProcessManager extends Mock implements ProcessManager {}
|
|
|
|
class MockXcodeProjectInterpreter extends Mock implements XcodeProjectInterpreter { }
|