1"use strict";
2
3Object.defineProperty(exports, "__esModule", {
4  value: true
5});
6exports.addBlockedPermissions = addBlockedPermissions;
7exports.addPermission = addPermission;
8exports.addPermissionToManifest = addPermissionToManifest;
9exports.ensurePermission = ensurePermission;
10exports.ensurePermissionNameFormat = ensurePermissionNameFormat;
11exports.ensurePermissions = ensurePermissions;
12exports.getAndroidPermissions = getAndroidPermissions;
13exports.getPermissions = getPermissions;
14exports.isPermissionAlreadyRequested = isPermissionAlreadyRequested;
15exports.removePermissions = removePermissions;
16exports.setAndroidPermissions = setAndroidPermissions;
17exports.withPermissions = exports.withInternalBlockedPermissions = exports.withBlockedPermissions = void 0;
18
19function _androidPlugins() {
20  const data = require("../plugins/android-plugins");
21
22  _androidPlugins = function () {
23    return data;
24  };
25
26  return data;
27}
28
29function _Manifest() {
30  const data = require("./Manifest");
31
32  _Manifest = function () {
33    return data;
34  };
35
36  return data;
37}
38
39const USES_PERMISSION = 'uses-permission';
40
41const withPermissions = (config, permissions) => {
42  if (Array.isArray(permissions)) {
43    permissions = permissions.filter(Boolean);
44    if (!config.android) config.android = {};
45    if (!config.android.permissions) config.android.permissions = [];
46    config.android.permissions = [// @ts-ignore
47    ...new Set(config.android.permissions.concat(permissions))];
48  }
49
50  return (0, _androidPlugins().withAndroidManifest)(config, async config => {
51    config.modResults = await setAndroidPermissions(config, config.modResults);
52    return config;
53  });
54};
55/** Given a permission or list of permissions, block permissions in the final `AndroidManifest.xml` to ensure no installed library or plugin can add them. */
56
57
58exports.withPermissions = withPermissions;
59
60const withBlockedPermissions = (config, permissions) => {
61  var _config$android;
62
63  const resolvedPermissions = (Array.isArray(permissions) ? permissions : [permissions]).filter(Boolean);
64
65  if (config !== null && config !== void 0 && (_config$android = config.android) !== null && _config$android !== void 0 && _config$android.permissions && Array.isArray(config.android.permissions)) {
66    // Remove any static config permissions
67    config.android.permissions = config.android.permissions.filter(permission => !resolvedPermissions.includes(permission));
68  }
69
70  return (0, _androidPlugins().withAndroidManifest)(config, async config => {
71    config.modResults = (0, _Manifest().ensureToolsAvailable)(config.modResults);
72    config.modResults = addBlockedPermissions(config.modResults, resolvedPermissions);
73    return config;
74  });
75};
76
77exports.withBlockedPermissions = withBlockedPermissions;
78
79const withInternalBlockedPermissions = config => {
80  var _config$android2, _config$android2$bloc;
81
82  // Only add permissions if the user defined the property and added some values
83  // this ensures we don't add the `tools:*` namespace extraneously.
84  if ((_config$android2 = config.android) !== null && _config$android2 !== void 0 && (_config$android2$bloc = _config$android2.blockedPermissions) !== null && _config$android2$bloc !== void 0 && _config$android2$bloc.length) {
85    return withBlockedPermissions(config, config.android.blockedPermissions);
86  }
87
88  return config;
89};
90
91exports.withInternalBlockedPermissions = withInternalBlockedPermissions;
92
93function addBlockedPermissions(androidManifest, permissions) {
94  if (!Array.isArray(androidManifest.manifest['uses-permission'])) {
95    androidManifest.manifest['uses-permission'] = [];
96  }
97
98  for (const permission of permissions) {
99    androidManifest.manifest['uses-permission'] = ensureBlockedPermission(androidManifest.manifest['uses-permission'], permission);
100  }
101
102  return androidManifest;
103}
104/**
105 * Filter any existing permissions matching the provided permission name, then add a
106 * restricted permission to overwrite any extra permissions that may be added in a
107 * third-party package's AndroidManifest.xml.
108 *
109 * @param manifestPermissions manifest `uses-permissions` array.
110 * @param permission `android:name` of the permission to restrict
111 * @returns
112 */
113
114
115function ensureBlockedPermission(manifestPermissions, permission) {
116  // Remove permission if it currently exists
117  manifestPermissions = manifestPermissions.filter(e => e.$['android:name'] !== permission); // Add a permission with tools:node to overwrite any existing permission and ensure it's removed upon building.
118
119  manifestPermissions.push({
120    $: {
121      'android:name': permission,
122      'tools:node': 'remove'
123    }
124  });
125  return manifestPermissions;
126}
127
128function prefixAndroidPermissionsIfNecessary(permissions) {
129  return permissions.map(permission => {
130    if (!permission.includes('.')) {
131      return `android.permission.${permission}`;
132    }
133
134    return permission;
135  });
136}
137
138function getAndroidPermissions(config) {
139  var _config$android$permi, _config$android3;
140
141  return (_config$android$permi = (_config$android3 = config.android) === null || _config$android3 === void 0 ? void 0 : _config$android3.permissions) !== null && _config$android$permi !== void 0 ? _config$android$permi : [];
142}
143
144function setAndroidPermissions(config, androidManifest) {
145  var _androidManifest$mani;
146
147  const permissions = getAndroidPermissions(config);
148  const providedPermissions = prefixAndroidPermissionsIfNecessary(permissions);
149  const permissionsToAdd = [...providedPermissions];
150
151  if (!androidManifest.manifest.hasOwnProperty('uses-permission')) {
152    androidManifest.manifest['uses-permission'] = [];
153  } // manifest.manifest['uses-permission'] = [];
154
155
156  const manifestPermissions = (_androidManifest$mani = androidManifest.manifest['uses-permission']) !== null && _androidManifest$mani !== void 0 ? _androidManifest$mani : [];
157  permissionsToAdd.forEach(permission => {
158    if (!isPermissionAlreadyRequested(permission, manifestPermissions)) {
159      addPermissionToManifest(permission, manifestPermissions);
160    }
161  });
162  return androidManifest;
163}
164
165function isPermissionAlreadyRequested(permission, manifestPermissions) {
166  return manifestPermissions.some(e => e.$['android:name'] === permission);
167}
168
169function addPermissionToManifest(permission, manifestPermissions) {
170  manifestPermissions.push({
171    $: {
172      'android:name': permission
173    }
174  });
175  return manifestPermissions;
176}
177
178function removePermissions(androidManifest, permissionNames) {
179  const targetNames = permissionNames ? permissionNames.map(ensurePermissionNameFormat) : null;
180  const permissions = androidManifest.manifest[USES_PERMISSION] || [];
181  const nextPermissions = [];
182
183  for (const attribute of permissions) {
184    if (targetNames) {
185      // @ts-ignore: name isn't part of the type
186      const value = attribute.$['android:name'] || attribute.$.name;
187
188      if (!targetNames.includes(value)) {
189        nextPermissions.push(attribute);
190      }
191    }
192  }
193
194  androidManifest.manifest[USES_PERMISSION] = nextPermissions;
195}
196
197function addPermission(androidManifest, permissionName) {
198  const usesPermissions = androidManifest.manifest[USES_PERMISSION] || [];
199  usesPermissions.push({
200    $: {
201      'android:name': permissionName
202    }
203  });
204  androidManifest.manifest[USES_PERMISSION] = usesPermissions;
205}
206
207function ensurePermissions(androidManifest, permissionNames) {
208  const permissions = getPermissions(androidManifest);
209  const results = {};
210
211  for (const permissionName of permissionNames) {
212    const targetName = ensurePermissionNameFormat(permissionName);
213
214    if (!permissions.includes(targetName)) {
215      addPermission(androidManifest, targetName);
216      results[permissionName] = true;
217    } else {
218      results[permissionName] = false;
219    }
220  }
221
222  return results;
223}
224
225function ensurePermission(androidManifest, permissionName) {
226  const permissions = getPermissions(androidManifest);
227  const targetName = ensurePermissionNameFormat(permissionName);
228
229  if (!permissions.includes(targetName)) {
230    addPermission(androidManifest, targetName);
231    return true;
232  }
233
234  return false;
235}
236
237function ensurePermissionNameFormat(permissionName) {
238  if (permissionName.includes('.')) {
239    const com = permissionName.split('.');
240    const name = com.pop();
241    return [...com, name.toUpperCase()].join('.');
242  } else {
243    // If shorthand form like `WRITE_CONTACTS` is provided, expand it to `android.permission.WRITE_CONTACTS`.
244    return ensurePermissionNameFormat(`android.permission.${permissionName}`);
245  }
246}
247
248function getPermissions(androidManifest) {
249  const usesPermissions = androidManifest.manifest[USES_PERMISSION] || [];
250  const permissions = usesPermissions.map(permissionObject => {
251    return permissionObject.$['android:name'] || permissionObject.$.name;
252  });
253  return permissions;
254}
255//# sourceMappingURL=Permissions.js.map