Repository: cordova-ios Updated Branches: refs/heads/master 32a9eca36 -> 6e1d376a7
CB-12287: Remove hardcoded sim build destination Edited title as was >50char; original was CB-12287: Remove hardcoded simulator build destination This closes #286 Project: http://git-wip-us.apache.org/repos/asf/cordova-ios/repo Commit: http://git-wip-us.apache.org/repos/asf/cordova-ios/commit/6e1d376a Tree: http://git-wip-us.apache.org/repos/asf/cordova-ios/tree/6e1d376a Diff: http://git-wip-us.apache.org/repos/asf/cordova-ios/diff/6e1d376a Branch: refs/heads/master Commit: 6e1d376a7a093ca958a27178dd036a9331cd5b43 Parents: 32a9eca Author: Kerri Shotts <ksho...@apache.org> Authored: Mon Jan 9 23:29:00 2017 -0600 Committer: Kerri Shotts <kerrisho...@gmail.com> Committed: Tue Jan 24 22:33:52 2017 -0600 ---------------------------------------------------------------------- bin/templates/scripts/cordova/lib/build.js | 60 +++++++++-- .../cordova/lib/list-emulator-build-targets | 108 +++++++++++++++++++ tests/spec/unit/build.spec.js | 4 +- 3 files changed, 162 insertions(+), 10 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/cordova-ios/blob/6e1d376a/bin/templates/scripts/cordova/lib/build.js ---------------------------------------------------------------------- diff --git a/bin/templates/scripts/cordova/lib/build.js b/bin/templates/scripts/cordova/lib/build.js index c40bfe8..c276424 100644 --- a/bin/templates/scripts/cordova/lib/build.js +++ b/bin/templates/scripts/cordova/lib/build.js @@ -53,7 +53,33 @@ var buildFlagMatchers = { 'shared_precomps_dir' : /^(SHARED_PRECOMPS_DIR=.*)/ }; +/** + * Returns a promise that resolves to the default simulator target; the logic here + * matches what `cordova emulate ios` does. + * + * The return object has two properties: `name` (the Xcode destination name), + * `identifier` (the simctl identifier), and `simIdentifier` (essentially the cordova emulate target) + * + * @return {Promise} + */ +function getDefaultSimulatorTarget() { + return require('./list-emulator-build-targets').run() + .then(function (emulators) { + var targetEmulator; + if (emulators.length > 0) { + targetEmulator = emulators[0]; + } + emulators.forEach(function (emulator) { + if (emulator.name.indexOf('iPhone') === 0) { + targetEmulator = emulator; + } + }); + return targetEmulator; + }); +} + module.exports.run = function (buildOpts) { + var emulatorTarget = ''; buildOpts = buildOpts || {}; @@ -93,6 +119,22 @@ return require('./list-devices').run() return check_reqs.check_ios_deploy(); } }).then(function () { + // CB-12287: Determine the device we should target when building for a simulator + if (!buildOpts.device) { + var promise; + if (buildOpts.target) { + // a target was given to us, find the matching Xcode destination name + promise = require('./list-emulator-build-targets').targetForSimIdentifier(buildOpts.target); + } else { + // no target provided, pick a default one (matching our emulator logic) + promise = getDefaultSimulatorTarget(); + } + return promise.then(function(theTarget) { + emulatorTarget = theTarget.name; + events.emit('log', 'Building for ' + emulatorTarget + ' Simulator'); + }); + } + }).then(function () { return check_reqs.run(); }).then(function () { return findXCodeProjectIn(projectPath); @@ -125,7 +167,7 @@ return require('./list-devices').run() // remove the build/device folder before building return spawn('rm', [ '-rf', buildOutputDir ], projectPath) .then(function() { - var xcodebuildArgs = getXcodeBuildArgs(projectName, projectPath, configuration, buildOpts.device, buildOpts.buildFlag); + var xcodebuildArgs = getXcodeBuildArgs(projectName, projectPath, configuration, buildOpts.device, buildOpts.buildFlag, emulatorTarget); return spawn('xcodebuild', xcodebuildArgs, projectPath); }); @@ -224,13 +266,15 @@ module.exports.findXCodeProjectIn = findXCodeProjectIn; /** * Returns array of arguments for xcodebuild - * @param {String} projectName Name of xcode project - * @param {String} projectPath Path to project file. Will be used to set CWD for xcodebuild - * @param {String} configuration Configuration name: debug|release - * @param {Boolean} isDevice Flag that specify target for package (device/emulator) - * @return {Array} Array of arguments that could be passed directly to spawn method + * @param {String} projectName Name of xcode project + * @param {String} projectPath Path to project file. Will be used to set CWD for xcodebuild + * @param {String} configuration Configuration name: debug|release + * @param {Boolean} isDevice Flag that specify target for package (device/emulator) + * @param {Array} buildFlags + * @param {String} emulatorTarget Target for emulator (rather than default) + * @return {Array} Array of arguments that could be passed directly to spawn method */ -function getXcodeBuildArgs(projectName, projectPath, configuration, isDevice, buildFlags) { +function getXcodeBuildArgs(projectName, projectPath, configuration, isDevice, buildFlags, emulatorTarget) { var xcodebuildArgs; var options; var buildActions; @@ -274,7 +318,7 @@ function getXcodeBuildArgs(projectName, projectPath, configuration, isDevice, bu '-scheme', customArgs.scheme || projectName, '-configuration', customArgs.configuration || configuration, '-sdk', customArgs.sdk || 'iphonesimulator', - '-destination', customArgs.destination || 'platform=iOS Simulator,name=iPhone 5s' + '-destination', customArgs.destination || 'platform=iOS Simulator,name=' + emulatorTarget ]; buildActions = [ 'build' ]; settings = [ http://git-wip-us.apache.org/repos/asf/cordova-ios/blob/6e1d376a/bin/templates/scripts/cordova/lib/list-emulator-build-targets ---------------------------------------------------------------------- diff --git a/bin/templates/scripts/cordova/lib/list-emulator-build-targets b/bin/templates/scripts/cordova/lib/list-emulator-build-targets new file mode 100755 index 0000000..d17fc8c --- /dev/null +++ b/bin/templates/scripts/cordova/lib/list-emulator-build-targets @@ -0,0 +1,108 @@ +#!/usr/bin/env node + +/* + Licensed to the Apache Software Foundation (ASF) under one + or more contributor license agreements. See the NOTICE file + distributed with this work for additional information + regarding copyright ownership. The ASF licenses this file + to you under the Apache License, Version 2.0 (the + "License"); you may not use this file except in compliance + with the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, + software distributed under the License is distributed on an + "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + KIND, either express or implied. See the License for the + specific language governing permissions and limitations + under the License. +*/ + +/*jshint node: true*/ + +var Q = require('q'), + exec = require('child_process').exec; + +/** + * Returns a list of available simulator build targets of the form + * + * [ + * { name: <xcode-destination-name>, + * identifier: <simctl-identifier>, + * simIdentifier: <cordova emulate target> + * } + * ] + * + */ +function listEmulatorBuildTargets () { + return Q.nfcall(exec, 'xcrun simctl list --json') + .then(function(stdio) { + return JSON.parse(stdio[0]); + }) + .then(function(simInfo) { + var devices = simInfo.devices; + var deviceTypes = simInfo.devicetypes; + return deviceTypes.reduce(function (typeAcc, deviceType) { + if (!deviceType.name.match(/^[iPad|iPhone]/)) { + // ignore targets we don't support (like Apple Watch or Apple TV) + return typeAcc; + } + var availableDevices = Object.keys(devices).reduce(function (availAcc, deviceCategory) { + var availableDevicesInCategory = devices[deviceCategory]; + availableDevicesInCategory.forEach(function (device) { + if (device.name === deviceType.name.replace(/\-inch/g, ' inch') && + device.availability.toLowerCase().indexOf('unavailable') < 0) { + availAcc.push(device); + } + }); + return availAcc; + }, []); + // we only want device types that have at least one available device + // (regardless of OS); this filters things out like iPhone 4s, which + // is present in deviceTypes, but probably not available on the user's + // system. + if (availableDevices.length > 0) { + typeAcc.push(deviceType); + } + return typeAcc; + }, []); + }) + .then(function(filteredTargets) { + // the simIdentifier, or cordova emulate target name, is the very last part + // of identifier. + return filteredTargets.map(function (target) { + var identifierPieces = target.identifier.split("."); + target.simIdentifier = identifierPieces[identifierPieces.length-1]; + return target; + }); + }); +} + +exports.run = listEmulatorBuildTargets; + +/** + * Given a simIdentifier, return the matching target. + * + * @param {string} simIdentifier a target, like "iPhone-SE" + * @return {Object} the matching target, or undefined if no match + */ +exports.targetForSimIdentifier = function(simIdentifier) { + return listEmulatorBuildTargets() + .then(function(targets) { + return targets.reduce(function(acc, target) { + if (!acc && target.simIdentifier.toLowerCase() === simIdentifier.toLowerCase()) { + acc = target; + } + return acc; + }, undefined); + }); +} + +// Check if module is started as separate script. +// If so, then invoke main method and print out results. +if (!module.parent) { + listEmulatorBuildTargets().then(function (targets) { + console.log(JSON.stringify(targets, null, 2)); + }); +} http://git-wip-us.apache.org/repos/asf/cordova-ios/blob/6e1d376a/tests/spec/unit/build.spec.js ---------------------------------------------------------------------- diff --git a/tests/spec/unit/build.spec.js b/tests/spec/unit/build.spec.js index f2c2da3..7d04966 100644 --- a/tests/spec/unit/build.spec.js +++ b/tests/spec/unit/build.spec.js @@ -110,7 +110,7 @@ describe('build', function () { it('should generate appropriate args for simulator', function(done) { var isDevice = false; - var args = getXcodeBuildArgs('TestProjectName', testProjectPath, 'TestConfiguration', isDevice, null); + var args = getXcodeBuildArgs('TestProjectName', testProjectPath, 'TestConfiguration', isDevice, null, 'iPhone 5s'); expect(args[0]).toEqual('-xcconfig'); expect(args[1]).toEqual(path.join('/test', 'build-testconfiguration.xcconfig')); expect(args[2]).toEqual('-workspace'); @@ -160,7 +160,7 @@ describe('build', function () { var isDevice = false; var buildFlags = '-archivePath TestArchivePathFlag'; - var args = getXcodeBuildArgs('TestProjectName', testProjectPath, 'TestConfiguration', isDevice, buildFlags); + var args = getXcodeBuildArgs('TestProjectName', testProjectPath, 'TestConfiguration', isDevice, buildFlags, 'iPhone 5s'); expect(args[0]).toEqual('-xcconfig'); expect(args[1]).toEqual(path.join('/test', 'build-testconfiguration.xcconfig')); expect(args[2]).toEqual('-workspace'); --------------------------------------------------------------------- To unsubscribe, e-mail: commits-unsubscr...@cordova.apache.org For additional commands, e-mail: commits-h...@cordova.apache.org