diff --git a/bin/templates/scripts/cordova/lib/build.js b/bin/templates/scripts/cordova/lib/build.js
index 3c8bd278b..a72038756 100644
--- a/bin/templates/scripts/cordova/lib/build.js
+++ b/bin/templates/scripts/cordova/lib/build.js
@@ -61,24 +61,6 @@ function createProjectObject (projectPath, projectName) {
return projectFile.parse(locations);
}
-/**
- * Gets the resolved bundle identifier from a project.
- * Resolves the variable set in INFO.plist, if any (simple case)
- *
- * @param {*} projectObject
- */
-function getBundleIdentifier (projectObject) {
- const packageName = projectObject.getPackageName();
- let bundleIdentifier = packageName;
-
- const variables = packageName.match(/\$\((\w+)\)/); // match $(VARIABLE), if any
- if (variables && variables.length >= 2) {
- bundleIdentifier = projectObject.xcode.getBuildProperty(variables[1]);
- }
-
- return bundleIdentifier;
-}
-
/**
* Returns a promise that resolves to the default simulator target; the logic here
* matches what `cordova emulate ios` does.
@@ -233,7 +215,7 @@ module.exports.run = buildOpts => {
}
const project = createProjectObject(projectPath, projectName);
- const bundleIdentifier = getBundleIdentifier(project);
+ const bundleIdentifier = project.getPackageName();
const exportOptions = { compileBitcode: false, method: 'development' };
if (buildOpts.packageType) {
diff --git a/bin/templates/scripts/cordova/lib/projectFile.js b/bin/templates/scripts/cordova/lib/projectFile.js
index b836e966d..3e1e83048 100644
--- a/bin/templates/scripts/cordova/lib/projectFile.js
+++ b/bin/templates/scripts/cordova/lib/projectFile.js
@@ -77,7 +77,15 @@ function parseProjectFile (locations) {
fs.writeFileSync(frameworks_file, JSON.stringify(this.frameworks, null, 4));
},
getPackageName: function () {
- return plist.parse(fs.readFileSync(plist_file, 'utf8')).CFBundleIdentifier;
+ const packageName = plist.parse(fs.readFileSync(plist_file, 'utf8')).CFBundleIdentifier;
+ let bundleIdentifier = packageName;
+
+ const variables = packageName.match(/\$\((\w+)\)/); // match $(VARIABLE), if any
+ if (variables && variables.length >= 2) {
+ bundleIdentifier = xcodeproj.getBuildProperty(variables[1]);
+ }
+
+ return bundleIdentifier.replace(/^"/, '').replace(/"$/, '');
},
getInstaller: function (name) {
return pluginHandlers.getInstaller(name);
diff --git a/tests/spec/unit/fixtures/ios-config-xml/SampleApp/SampleApp-Info.plist b/tests/spec/unit/fixtures/ios-config-xml/SampleApp/SampleApp-Info.plist
index 612eeaa77..35624fa76 100644
--- a/tests/spec/unit/fixtures/ios-config-xml/SampleApp/SampleApp-Info.plist
+++ b/tests/spec/unit/fixtures/ios-config-xml/SampleApp/SampleApp-Info.plist
@@ -13,7 +13,7 @@
CFBundleIcons~ipad
CFBundleIdentifier
- com.example.friendstring
+ $(PRODUCT_BUNDLE_IDENTIFIER)
CFBundleInfoDictionaryVersion
6.0
CFBundleName
diff --git a/tests/spec/unit/fixtures/org.test.plugins.dummyplugin/plugin.xml b/tests/spec/unit/fixtures/org.test.plugins.dummyplugin/plugin.xml
index 308f856f0..58ad1e526 100644
--- a/tests/spec/unit/fixtures/org.test.plugins.dummyplugin/plugin.xml
+++ b/tests/spec/unit/fixtures/org.test.plugins.dummyplugin/plugin.xml
@@ -40,6 +40,9 @@
+
+
+
@@ -48,6 +51,11 @@
value="DummyPluginCommand"/>
+
+
+
+
+
diff --git a/tests/spec/unit/pluginAdd.spec.js b/tests/spec/unit/pluginAdd.spec.js
new file mode 100644
index 000000000..1d4d69441
--- /dev/null
+++ b/tests/spec/unit/pluginAdd.spec.js
@@ -0,0 +1,63 @@
+/**
+ 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.
+ */
+
+const path = require('path');
+const fs = require('fs-extra');
+const EventEmitter = require('events').EventEmitter;
+const ConfigParser = require('cordova-common').ConfigParser;
+const PluginInfo = require('cordova-common').PluginInfo;
+const Api = require('../../../bin/templates/scripts/cordova/Api');
+
+const FIXTURES = path.join(__dirname, 'fixtures');
+const DUMMY_PLUGIN = 'org.test.plugins.dummyplugin';
+
+const iosProjectFixture = path.join(FIXTURES, 'ios-config-xml');
+const iosProject = path.join(FIXTURES, 'dummyProj');
+const iosPlatform = path.join(iosProject, 'platforms/ios');
+const dummyPlugin = path.join(FIXTURES, DUMMY_PLUGIN);
+
+describe('plugin add', () => {
+ let api;
+
+ beforeEach(() => {
+ fs.ensureDirSync(iosPlatform);
+ fs.copySync(iosProjectFixture, iosPlatform);
+ api = new Api('ios', iosPlatform, new EventEmitter());
+ });
+
+ afterEach(() => {
+ fs.removeSync(iosPlatform);
+ });
+
+ it('should handle plugin preference default values', () => {
+ return api.addPlugin(new PluginInfo(dummyPlugin))
+ .then(() => {
+ const cfg = new ConfigParser(api.locations.configXml);
+ expect(cfg.getPreference('PluginPackageName', 'ios')).toEqual('com.example.friendstring');
+ });
+ });
+
+ it('should handle plugin preference provided values', () => {
+ return api.addPlugin(new PluginInfo(dummyPlugin), { variables: { NAME_SPACE: 'com.mycompany.myapp' } })
+ .then(() => {
+ const cfg = new ConfigParser(api.locations.configXml);
+ expect(cfg.getPreference('PluginNameSpace', 'ios')).toEqual('com.mycompany.myapp');
+ });
+ });
+});