@azure/identity 3.1.3 → 3.2.0-alpha.20230224.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of @azure/identity might be problematic. Click here for more details.

Files changed (66) hide show
  1. package/README.md +10 -1
  2. package/dist/index.js +360 -206
  3. package/dist/index.js.map +1 -1
  4. package/dist-esm/src/client/identityClient.js +9 -0
  5. package/dist-esm/src/client/identityClient.js.map +1 -1
  6. package/dist-esm/src/constants.js +1 -1
  7. package/dist-esm/src/constants.js.map +1 -1
  8. package/dist-esm/src/credentials/authorityValidationOptions.js +4 -0
  9. package/dist-esm/src/credentials/authorityValidationOptions.js.map +1 -0
  10. package/dist-esm/src/credentials/authorizationCodeCredentialOptions.js.map +1 -1
  11. package/dist-esm/src/credentials/azureApplicationCredential.js +0 -2
  12. package/dist-esm/src/credentials/azureApplicationCredential.js.map +1 -1
  13. package/dist-esm/src/credentials/azureDeveloperCliCredential.browser.js +23 -0
  14. package/dist-esm/src/credentials/azureDeveloperCliCredential.browser.js.map +1 -0
  15. package/dist-esm/src/credentials/azureDeveloperCliCredential.js +136 -0
  16. package/dist-esm/src/credentials/azureDeveloperCliCredential.js.map +1 -0
  17. package/dist-esm/src/credentials/azureDeveloperCliCredentialOptions.js +4 -0
  18. package/dist-esm/src/credentials/azureDeveloperCliCredentialOptions.js.map +1 -0
  19. package/dist-esm/src/credentials/chainedTokenCredential.js +0 -4
  20. package/dist-esm/src/credentials/chainedTokenCredential.js.map +1 -1
  21. package/dist-esm/src/credentials/clientAssertionCredentialOptions.js.map +1 -1
  22. package/dist-esm/src/credentials/clientCertificateCredentialOptions.js.map +1 -1
  23. package/dist-esm/src/credentials/clientSecretCredentialOptions.js.map +1 -1
  24. package/dist-esm/src/credentials/defaultAzureCredential.js +9 -2
  25. package/dist-esm/src/credentials/defaultAzureCredential.js.map +1 -1
  26. package/dist-esm/src/credentials/defaultAzureCredentialOptions.js.map +1 -1
  27. package/dist-esm/src/credentials/environmentCredentialOptions.js.map +1 -1
  28. package/dist-esm/src/credentials/interactiveBrowserCredentialOptions.js.map +1 -1
  29. package/dist-esm/src/credentials/interactiveCredentialOptions.js.map +1 -1
  30. package/dist-esm/src/credentials/managedIdentityCredential/appServiceMsi2017.js +1 -0
  31. package/dist-esm/src/credentials/managedIdentityCredential/appServiceMsi2017.js.map +1 -1
  32. package/dist-esm/src/credentials/managedIdentityCredential/appServiceMsi2019.js +1 -0
  33. package/dist-esm/src/credentials/managedIdentityCredential/appServiceMsi2019.js.map +1 -1
  34. package/dist-esm/src/credentials/managedIdentityCredential/arcMsi.js +1 -0
  35. package/dist-esm/src/credentials/managedIdentityCredential/arcMsi.js.map +1 -1
  36. package/dist-esm/src/credentials/managedIdentityCredential/cloudShellMsi.js +1 -0
  37. package/dist-esm/src/credentials/managedIdentityCredential/cloudShellMsi.js.map +1 -1
  38. package/dist-esm/src/credentials/managedIdentityCredential/fabricMsi.js +1 -0
  39. package/dist-esm/src/credentials/managedIdentityCredential/fabricMsi.js.map +1 -1
  40. package/dist-esm/src/credentials/managedIdentityCredential/imdsMsi.js +1 -0
  41. package/dist-esm/src/credentials/managedIdentityCredential/imdsMsi.js.map +1 -1
  42. package/dist-esm/src/credentials/managedIdentityCredential/index.js +7 -2
  43. package/dist-esm/src/credentials/managedIdentityCredential/index.js.map +1 -1
  44. package/dist-esm/src/credentials/managedIdentityCredential/models.js.map +1 -1
  45. package/dist-esm/src/credentials/managedIdentityCredential/tokenExchangeMsi.js +10 -65
  46. package/dist-esm/src/credentials/managedIdentityCredential/tokenExchangeMsi.js.map +1 -1
  47. package/dist-esm/src/credentials/onBehalfOfCredentialOptions.js.map +1 -1
  48. package/dist-esm/src/credentials/workloadIdentityCredential.browser.js +27 -0
  49. package/dist-esm/src/credentials/workloadIdentityCredential.browser.js.map +1 -0
  50. package/dist-esm/src/credentials/workloadIdentityCredential.js +55 -0
  51. package/dist-esm/src/credentials/workloadIdentityCredential.js.map +1 -0
  52. package/dist-esm/src/credentials/workloadIdentityCredentialOptions.js +4 -0
  53. package/dist-esm/src/credentials/workloadIdentityCredentialOptions.js.map +1 -0
  54. package/dist-esm/src/index.js +1 -0
  55. package/dist-esm/src/index.js.map +1 -1
  56. package/dist-esm/src/msal/browserFlows/msalBrowserCommon.js +1 -1
  57. package/dist-esm/src/msal/browserFlows/msalBrowserCommon.js.map +1 -1
  58. package/dist-esm/src/msal/flows.js.map +1 -1
  59. package/dist-esm/src/msal/nodeFlows/msalNodeCommon.js +1 -1
  60. package/dist-esm/src/msal/nodeFlows/msalNodeCommon.js.map +1 -1
  61. package/dist-esm/src/msal/utils.js +2 -2
  62. package/dist-esm/src/msal/utils.js.map +1 -1
  63. package/dist-esm/src/util/processMultiTenantRequest.js +1 -0
  64. package/dist-esm/src/util/processMultiTenantRequest.js.map +1 -1
  65. package/package.json +10 -8
  66. package/types/identity.d.ts +73 -13
package/dist/index.js CHANGED
@@ -3,7 +3,7 @@
3
3
  Object.defineProperty(exports, '__esModule', { value: true });
4
4
 
5
5
  var msalNode = require('@azure/msal-node');
6
- var logger$m = require('@azure/logger');
6
+ var logger$n = require('@azure/logger');
7
7
  var msalCommon = require('@azure/msal-common');
8
8
  var abortController = require('@azure/abort-controller');
9
9
  var coreUtil = require('@azure/core-util');
@@ -14,10 +14,11 @@ var coreTracing = require('@azure/core-tracing');
14
14
  var fs = require('fs');
15
15
  var os = require('os');
16
16
  var path = require('path');
17
- var util = require('util');
17
+ var promises = require('fs/promises');
18
18
  var https = require('https');
19
19
  var child_process = require('child_process');
20
20
  var crypto = require('crypto');
21
+ var util = require('util');
21
22
  var http = require('http');
22
23
  var open = require('open');
23
24
  var stoppable = require('stoppable');
@@ -177,7 +178,7 @@ class AuthenticationRequiredError extends Error {
177
178
  /**
178
179
  * The AzureLogger used for all clients within the identity package
179
180
  */
180
- const logger$l = logger$m.createClientLogger("identity");
181
+ const logger$m = logger$n.createClientLogger("identity");
181
182
  /**
182
183
  * Separates a list of environment variable names into a plain object with two arrays: an array of missing environment variables and another array with assigned environment variables.
183
184
  * @param supportedEnvVars - List of environment variable names
@@ -217,7 +218,7 @@ function formatError(scope, error) {
217
218
  * `[title] => [message]`
218
219
  *
219
220
  */
220
- function credentialLoggerInstance(title, parent, log = logger$l) {
221
+ function credentialLoggerInstance(title, parent, log = logger$m) {
221
222
  const fullTitle = parent ? `${parent.fullTitle} ${title}` : title;
222
223
  function info(message) {
223
224
  log.info(`${fullTitle} =>`, message);
@@ -246,7 +247,7 @@ function credentialLoggerInstance(title, parent, log = logger$l) {
246
247
  * `[title] => getToken() => [message]`
247
248
  *
248
249
  */
249
- function credentialLogger(title, log = logger$l) {
250
+ function credentialLogger(title, log = logger$m) {
250
251
  const credLogger = credentialLoggerInstance(title, undefined, log);
251
252
  return Object.assign(Object.assign({}, credLogger), { parent: log, getToken: credentialLoggerInstance("=> getToken()", credLogger, log) });
252
253
  }
@@ -256,7 +257,7 @@ function credentialLogger(title, log = logger$l) {
256
257
  /**
257
258
  * Current version of the `@azure/identity` package.
258
259
  */
259
- const SDK_VERSION = `3.1.2`;
260
+ const SDK_VERSION = `3.2.0-beta.1`;
260
261
  /**
261
262
  * The default client ID for authentication
262
263
  * @internal
@@ -355,8 +356,8 @@ function getAuthority(tenantId, host) {
355
356
  * by sending it within the known authorities in the MSAL configuration.
356
357
  * @internal
357
358
  */
358
- function getKnownAuthorities(tenantId, authorityHost) {
359
- if (tenantId === "adfs" && authorityHost) {
359
+ function getKnownAuthorities(tenantId, authorityHost, disableInstanceDiscovery) {
360
+ if ((tenantId === "adfs" && authorityHost) || disableInstanceDiscovery) {
360
361
  return [authorityHost];
361
362
  }
362
363
  return [];
@@ -553,6 +554,7 @@ function processMultiTenantRequest(tenantId, getTokenOptions, additionallyAllowe
553
554
  else {
554
555
  resolvedTenantId = (_a = getTokenOptions === null || getTokenOptions === void 0 ? void 0 : getTokenOptions.tenantId) !== null && _a !== void 0 ? _a : tenantId;
555
556
  }
557
+ console.log(resolvedTenantId);
556
558
  if (tenantId &&
557
559
  resolvedTenantId !== tenantId &&
558
560
  !additionallyAllowedTenantIds.includes("*") &&
@@ -724,9 +726,11 @@ class IdentityClient extends coreClient.ServiceClient {
724
726
  this.authorityHost = baseUri;
725
727
  this.abortControllers = new Map();
726
728
  this.allowLoggingAccountIdentifiers = (_b = options === null || options === void 0 ? void 0 : options.loggingOptions) === null || _b === void 0 ? void 0 : _b.allowLoggingAccountIdentifiers;
729
+ // used for WorkloadIdentity
730
+ this.tokenCredentialOptions = Object.assign({}, options);
727
731
  }
728
732
  async sendTokenRequest(request) {
729
- logger$l.info(`IdentityClient: sending token request to [${request.url}]`);
733
+ logger$m.info(`IdentityClient: sending token request to [${request.url}]`);
730
734
  const response = await this.sendRequest(request);
731
735
  if (response.bodyAsText && (response.status === 200 || response.status === 201)) {
732
736
  const parsedBody = JSON.parse(response.bodyAsText);
@@ -741,12 +745,12 @@ class IdentityClient extends coreClient.ServiceClient {
741
745
  },
742
746
  refreshToken: parsedBody.refresh_token,
743
747
  };
744
- logger$l.info(`IdentityClient: [${request.url}] token acquired, expires on ${token.accessToken.expiresOnTimestamp}`);
748
+ logger$m.info(`IdentityClient: [${request.url}] token acquired, expires on ${token.accessToken.expiresOnTimestamp}`);
745
749
  return token;
746
750
  }
747
751
  else {
748
752
  const error = new AuthenticationError(response.status, response.bodyAsText);
749
- logger$l.warning(`IdentityClient: authentication error. HTTP status: ${response.status}, ${error.errorResponse.errorDescription}`);
753
+ logger$m.warning(`IdentityClient: authentication error. HTTP status: ${response.status}, ${error.errorResponse.errorDescription}`);
750
754
  throw error;
751
755
  }
752
756
  }
@@ -754,7 +758,7 @@ class IdentityClient extends coreClient.ServiceClient {
754
758
  if (refreshToken === undefined) {
755
759
  return null;
756
760
  }
757
- logger$l.info(`IdentityClient: refreshing access token with client ID: ${clientId}, scopes: ${scopes} started`);
761
+ logger$m.info(`IdentityClient: refreshing access token with client ID: ${clientId}, scopes: ${scopes} started`);
758
762
  const refreshParams = {
759
763
  grant_type: "refresh_token",
760
764
  client_id: clientId,
@@ -780,7 +784,7 @@ class IdentityClient extends coreClient.ServiceClient {
780
784
  tracingOptions: updatedOptions.tracingOptions,
781
785
  });
782
786
  const response = await this.sendTokenRequest(request);
783
- logger$l.info(`IdentityClient: refreshed token for client ID: ${clientId}`);
787
+ logger$m.info(`IdentityClient: refreshed token for client ID: ${clientId}`);
784
788
  return response;
785
789
  }
786
790
  catch (err) {
@@ -789,11 +793,11 @@ class IdentityClient extends coreClient.ServiceClient {
789
793
  // It's likely that the refresh token has expired, so
790
794
  // return null so that the credential implementation will
791
795
  // initiate the authentication flow again.
792
- logger$l.info(`IdentityClient: interaction required for client ID: ${clientId}`);
796
+ logger$m.info(`IdentityClient: interaction required for client ID: ${clientId}`);
793
797
  return null;
794
798
  }
795
799
  else {
796
- logger$l.warning(`IdentityClient: failed refreshing token for client ID: ${clientId}: ${err}`);
800
+ logger$m.warning(`IdentityClient: failed refreshing token for client ID: ${clientId}: ${err}`);
797
801
  throw err;
798
802
  }
799
803
  }
@@ -869,6 +873,13 @@ class IdentityClient extends coreClient.ServiceClient {
869
873
  status: response.status,
870
874
  };
871
875
  }
876
+ /**
877
+ *
878
+ * @internal
879
+ */
880
+ getTokenCredentialOptions() {
881
+ return this.tokenCredentialOptions;
882
+ }
872
883
  /**
873
884
  * If allowLoggingAccountIdentifiers was set on the constructor options
874
885
  * we try to log the account identifiers by parsing the received access token.
@@ -895,10 +906,10 @@ class IdentityClient extends coreClient.ServiceClient {
895
906
  }
896
907
  const base64Metadata = accessToken.split(".")[1];
897
908
  const { appid, upn, tid, oid } = JSON.parse(Buffer.from(base64Metadata, "base64").toString("utf8"));
898
- logger$l.info(`[Authenticated account] Client ID: ${appid}. Tenant ID: ${tid}. User Principal Name: ${upn || unavailableUpn}. Object ID (user): ${oid}`);
909
+ logger$m.info(`[Authenticated account] Client ID: ${appid}. Tenant ID: ${tid}. User Principal Name: ${upn || unavailableUpn}. Object ID (user): ${oid}`);
899
910
  }
900
911
  catch (e) {
901
- logger$l.warning("allowLoggingAccountIdentifiers was set, but we couldn't log the account information. Error:", e.message);
912
+ logger$m.warning("allowLoggingAccountIdentifiers was set, but we couldn't log the account information. Error:", e.message);
902
913
  }
903
914
  }
904
915
  }
@@ -1088,7 +1099,7 @@ class MsalNode extends MsalBaseUtilities {
1088
1099
  auth: {
1089
1100
  clientId,
1090
1101
  authority,
1091
- knownAuthorities: getKnownAuthorities(tenantId, authority),
1102
+ knownAuthorities: getKnownAuthorities(tenantId, authority, options.disableInstanceDiscovery),
1092
1103
  clientCapabilities,
1093
1104
  },
1094
1105
  // Cache is defined in this.prepare();
@@ -1096,7 +1107,7 @@ class MsalNode extends MsalBaseUtilities {
1096
1107
  networkClient: this.identityClient,
1097
1108
  loggerOptions: {
1098
1109
  loggerCallback: defaultLoggerCallback(options.logger),
1099
- logLevel: getMSALLogLevel(logger$m.getLogLevel()),
1110
+ logLevel: getMSALLogLevel(logger$n.getLogLevel()),
1100
1111
  },
1101
1112
  },
1102
1113
  };
@@ -1254,7 +1265,7 @@ To work with multiple accounts for the same Client ID and Tenant ID, please prov
1254
1265
  // Copyright (c) Microsoft Corporation.
1255
1266
  const CommonTenantId = "common";
1256
1267
  const AzureAccountClientId = "aebc6443-996d-45c2-90f0-388ff96faa56"; // VSC: 'aebc6443-996d-45c2-90f0-388ff96faa56'
1257
- const logger$k = credentialLogger("VisualStudioCodeCredential");
1268
+ const logger$l = credentialLogger("VisualStudioCodeCredential");
1258
1269
  let findCredentials = undefined;
1259
1270
  const vsCodeCredentialControl = {
1260
1271
  setVsCodeCredentialFinder(finder) {
@@ -1307,7 +1318,7 @@ function getPropertyFromVSCode(property) {
1307
1318
  }
1308
1319
  }
1309
1320
  catch (e) {
1310
- logger$k.info(`Failed to load the Visual Studio Code configuration file. Error: ${e.message}`);
1321
+ logger$l.info(`Failed to load the Visual Studio Code configuration file. Error: ${e.message}`);
1311
1322
  return;
1312
1323
  }
1313
1324
  }
@@ -1340,7 +1351,7 @@ class VisualStudioCodeCredential {
1340
1351
  const authorityHost = mapVSCodeAuthorityHosts[this.cloudName];
1341
1352
  this.identityClient = new IdentityClient(Object.assign({ authorityHost }, options));
1342
1353
  if (options && options.tenantId) {
1343
- checkTenantId(logger$k, options.tenantId);
1354
+ checkTenantId(logger$l, options.tenantId);
1344
1355
  this.tenantId = options.tenantId;
1345
1356
  }
1346
1357
  else {
@@ -1395,7 +1406,7 @@ class VisualStudioCodeCredential {
1395
1406
  // Check to make sure the scope we get back is a valid scope
1396
1407
  if (!scopeString.match(/^[0-9a-zA-Z-.:/]+$/)) {
1397
1408
  const error = new Error("Invalid scope was specified by the user or calling client");
1398
- logger$k.getToken.info(formatError(scopes, error));
1409
+ logger$l.getToken.info(formatError(scopes, error));
1399
1410
  throw error;
1400
1411
  }
1401
1412
  if (scopeString.indexOf("offline_access") < 0) {
@@ -1415,18 +1426,18 @@ class VisualStudioCodeCredential {
1415
1426
  if (refreshToken) {
1416
1427
  const tokenResponse = await this.identityClient.refreshAccessToken(tenantId, AzureAccountClientId, scopeString, refreshToken, undefined);
1417
1428
  if (tokenResponse) {
1418
- logger$k.getToken.info(formatSuccess(scopes));
1429
+ logger$l.getToken.info(formatSuccess(scopes));
1419
1430
  return tokenResponse.accessToken;
1420
1431
  }
1421
1432
  else {
1422
1433
  const error = new CredentialUnavailableError("Could not retrieve the token associated with Visual Studio Code. Have you connected using the 'Azure Account' extension recently? To troubleshoot, visit https://aka.ms/azsdk/js/identity/vscodecredential/troubleshoot.");
1423
- logger$k.getToken.info(formatError(scopes, error));
1434
+ logger$l.getToken.info(formatError(scopes, error));
1424
1435
  throw error;
1425
1436
  }
1426
1437
  }
1427
1438
  else {
1428
1439
  const error = new CredentialUnavailableError("Could not retrieve the token associated with Visual Studio Code. Did you connect using the 'Azure Account' extension? To troubleshoot, visit https://aka.ms/azsdk/js/identity/vscodecredential/troubleshoot.");
1429
- logger$k.getToken.info(formatError(scopes, error));
1440
+ logger$l.getToken.info(formatError(scopes, error));
1430
1441
  throw error;
1431
1442
  }
1432
1443
  }
@@ -1475,11 +1486,11 @@ function useIdentityPlugin(plugin) {
1475
1486
 
1476
1487
  // Copyright (c) Microsoft Corporation.
1477
1488
  const msiName$6 = "ManagedIdentityCredential - AppServiceMSI 2017";
1478
- const logger$j = credentialLogger(msiName$6);
1489
+ const logger$k = credentialLogger(msiName$6);
1479
1490
  /**
1480
1491
  * Generates the options used on the request for an access token.
1481
1492
  */
1482
- function prepareRequestOptions$6(scopes, clientId) {
1493
+ function prepareRequestOptions$5(scopes, clientId) {
1483
1494
  const resource = mapScopesToResource(scopes);
1484
1495
  if (!resource) {
1485
1496
  throw new Error(`${msiName$6}: Multiple scopes are not supported.`);
@@ -1512,26 +1523,27 @@ function prepareRequestOptions$6(scopes, clientId) {
1512
1523
  * Defines how to determine whether the Azure App Service MSI is available, and also how to retrieve a token from the Azure App Service MSI.
1513
1524
  */
1514
1525
  const appServiceMsi2017 = {
1526
+ name: "appServiceMsi2017",
1515
1527
  async isAvailable({ scopes }) {
1516
1528
  const resource = mapScopesToResource(scopes);
1517
1529
  if (!resource) {
1518
- logger$j.info(`${msiName$6}: Unavailable. Multiple scopes are not supported.`);
1530
+ logger$k.info(`${msiName$6}: Unavailable. Multiple scopes are not supported.`);
1519
1531
  return false;
1520
1532
  }
1521
1533
  const env = process.env;
1522
1534
  const result = Boolean(env.MSI_ENDPOINT && env.MSI_SECRET);
1523
1535
  if (!result) {
1524
- logger$j.info(`${msiName$6}: Unavailable. The environment variables needed are: MSI_ENDPOINT and MSI_SECRET.`);
1536
+ logger$k.info(`${msiName$6}: Unavailable. The environment variables needed are: MSI_ENDPOINT and MSI_SECRET.`);
1525
1537
  }
1526
1538
  return result;
1527
1539
  },
1528
1540
  async getToken(configuration, getTokenOptions = {}) {
1529
1541
  const { identityClient, scopes, clientId, resourceId } = configuration;
1530
1542
  if (resourceId) {
1531
- logger$j.warning(`${msiName$6}: managed Identity by resource Id is not supported. Argument resourceId might be ignored by the service.`);
1543
+ logger$k.warning(`${msiName$6}: managed Identity by resource Id is not supported. Argument resourceId might be ignored by the service.`);
1532
1544
  }
1533
- logger$j.info(`${msiName$6}: Using the endpoint and the secret coming form the environment variables: MSI_ENDPOINT=${process.env.MSI_ENDPOINT} and MSI_SECRET=[REDACTED].`);
1534
- const request = coreRestPipeline.createPipelineRequest(Object.assign(Object.assign({ abortSignal: getTokenOptions.abortSignal }, prepareRequestOptions$6(scopes, clientId)), {
1545
+ logger$k.info(`${msiName$6}: Using the endpoint and the secret coming form the environment variables: MSI_ENDPOINT=${process.env.MSI_ENDPOINT} and MSI_SECRET=[REDACTED].`);
1546
+ const request = coreRestPipeline.createPipelineRequest(Object.assign(Object.assign({ abortSignal: getTokenOptions.abortSignal }, prepareRequestOptions$5(scopes, clientId)), {
1535
1547
  // Generally, MSI endpoints use the HTTP protocol, without transport layer security (TLS).
1536
1548
  allowInsecureConnection: true }));
1537
1549
  const tokenResponse = await identityClient.sendTokenRequest(request);
@@ -1541,11 +1553,11 @@ const appServiceMsi2017 = {
1541
1553
 
1542
1554
  // Copyright (c) Microsoft Corporation.
1543
1555
  const msiName$5 = "ManagedIdentityCredential - CloudShellMSI";
1544
- const logger$i = credentialLogger(msiName$5);
1556
+ const logger$j = credentialLogger(msiName$5);
1545
1557
  /**
1546
1558
  * Generates the options used on the request for an access token.
1547
1559
  */
1548
- function prepareRequestOptions$5(scopes, clientId, resourceId) {
1560
+ function prepareRequestOptions$4(scopes, clientId, resourceId) {
1549
1561
  const resource = mapScopesToResource(scopes);
1550
1562
  if (!resource) {
1551
1563
  throw new Error(`${msiName$5}: Multiple scopes are not supported.`);
@@ -1580,28 +1592,29 @@ function prepareRequestOptions$5(scopes, clientId, resourceId) {
1580
1592
  * Since Azure Managed Identities aren't available in the Azure Cloud Shell, we log a warning for users that try to access cloud shell using user assigned identity.
1581
1593
  */
1582
1594
  const cloudShellMsi = {
1595
+ name: "cloudShellMsi",
1583
1596
  async isAvailable({ scopes }) {
1584
1597
  const resource = mapScopesToResource(scopes);
1585
1598
  if (!resource) {
1586
- logger$i.info(`${msiName$5}: Unavailable. Multiple scopes are not supported.`);
1599
+ logger$j.info(`${msiName$5}: Unavailable. Multiple scopes are not supported.`);
1587
1600
  return false;
1588
1601
  }
1589
1602
  const result = Boolean(process.env.MSI_ENDPOINT);
1590
1603
  if (!result) {
1591
- logger$i.info(`${msiName$5}: Unavailable. The environment variable MSI_ENDPOINT is needed.`);
1604
+ logger$j.info(`${msiName$5}: Unavailable. The environment variable MSI_ENDPOINT is needed.`);
1592
1605
  }
1593
1606
  return result;
1594
1607
  },
1595
1608
  async getToken(configuration, getTokenOptions = {}) {
1596
1609
  const { identityClient, scopes, clientId, resourceId } = configuration;
1597
1610
  if (clientId) {
1598
- logger$i.warning(`${msiName$5}: user-assigned identities not supported. The argument clientId might be ignored by the service.`);
1611
+ logger$j.warning(`${msiName$5}: user-assigned identities not supported. The argument clientId might be ignored by the service.`);
1599
1612
  }
1600
1613
  if (resourceId) {
1601
- logger$i.warning(`${msiName$5}: user defined managed Identity by resource Id not supported. The argument resourceId might be ignored by the service.`);
1614
+ logger$j.warning(`${msiName$5}: user defined managed Identity by resource Id not supported. The argument resourceId might be ignored by the service.`);
1602
1615
  }
1603
- logger$i.info(`${msiName$5}: Using the endpoint coming form the environment variable MSI_ENDPOINT = ${process.env.MSI_ENDPOINT}.`);
1604
- const request = coreRestPipeline.createPipelineRequest(Object.assign(Object.assign({ abortSignal: getTokenOptions.abortSignal }, prepareRequestOptions$5(scopes, clientId, resourceId)), {
1616
+ logger$j.info(`${msiName$5}: Using the endpoint coming form the environment variable MSI_ENDPOINT = ${process.env.MSI_ENDPOINT}.`);
1617
+ const request = coreRestPipeline.createPipelineRequest(Object.assign(Object.assign({ abortSignal: getTokenOptions.abortSignal }, prepareRequestOptions$4(scopes, clientId, resourceId)), {
1605
1618
  // Generally, MSI endpoints use the HTTP protocol, without transport layer security (TLS).
1606
1619
  allowInsecureConnection: true }));
1607
1620
  const tokenResponse = await identityClient.sendTokenRequest(request);
@@ -1611,11 +1624,11 @@ const cloudShellMsi = {
1611
1624
 
1612
1625
  // Copyright (c) Microsoft Corporation.
1613
1626
  const msiName$4 = "ManagedIdentityCredential - IMDS";
1614
- const logger$h = credentialLogger(msiName$4);
1627
+ const logger$i = credentialLogger(msiName$4);
1615
1628
  /**
1616
1629
  * Generates the options used on the request for an access token.
1617
1630
  */
1618
- function prepareRequestOptions$4(scopes, clientId, resourceId, options) {
1631
+ function prepareRequestOptions$3(scopes, clientId, resourceId, options) {
1619
1632
  var _a;
1620
1633
  const resource = mapScopesToResource(scopes);
1621
1634
  if (!resource) {
@@ -1665,10 +1678,11 @@ const imdsMsiRetryConfig = {
1665
1678
  * Defines how to determine whether the Azure IMDS MSI is available, and also how to retrieve a token from the Azure IMDS MSI.
1666
1679
  */
1667
1680
  const imdsMsi = {
1681
+ name: "imdsMsi",
1668
1682
  async isAvailable({ scopes, identityClient, clientId, resourceId, getTokenOptions = {}, }) {
1669
1683
  const resource = mapScopesToResource(scopes);
1670
1684
  if (!resource) {
1671
- logger$h.info(`${msiName$4}: Unavailable. Multiple scopes are not supported.`);
1685
+ logger$i.info(`${msiName$4}: Unavailable. Multiple scopes are not supported.`);
1672
1686
  return false;
1673
1687
  }
1674
1688
  // if the PodIdentityEndpoint environment variable was set no need to probe the endpoint, it can be assumed to exist
@@ -1678,7 +1692,7 @@ const imdsMsi = {
1678
1692
  if (!identityClient) {
1679
1693
  throw new Error("Missing IdentityClient");
1680
1694
  }
1681
- const requestOptions = prepareRequestOptions$4(resource, clientId, resourceId, {
1695
+ const requestOptions = prepareRequestOptions$3(resource, clientId, resourceId, {
1682
1696
  skipMetadataHeader: true,
1683
1697
  skipQuery: true,
1684
1698
  });
@@ -1695,35 +1709,35 @@ const imdsMsi = {
1695
1709
  // This MSI uses the imdsEndpoint to get the token, which only uses http://
1696
1710
  request.allowInsecureConnection = true;
1697
1711
  try {
1698
- logger$h.info(`${msiName$4}: Pinging the Azure IMDS endpoint`);
1712
+ logger$i.info(`${msiName$4}: Pinging the Azure IMDS endpoint`);
1699
1713
  await identityClient.sendRequest(request);
1700
1714
  }
1701
1715
  catch (err) {
1702
1716
  // If the request failed, or Node.js was unable to establish a connection,
1703
1717
  // or the host was down, we'll assume the IMDS endpoint isn't available.
1704
1718
  if (coreUtil.isError(err)) {
1705
- logger$h.verbose(`${msiName$4}: Caught error ${err.name}: ${err.message}`);
1719
+ logger$i.verbose(`${msiName$4}: Caught error ${err.name}: ${err.message}`);
1706
1720
  }
1707
- logger$h.info(`${msiName$4}: The Azure IMDS endpoint is unavailable`);
1721
+ logger$i.info(`${msiName$4}: The Azure IMDS endpoint is unavailable`);
1708
1722
  return false;
1709
1723
  }
1710
1724
  // If we received any response, the endpoint is available
1711
- logger$h.info(`${msiName$4}: The Azure IMDS endpoint is available`);
1725
+ logger$i.info(`${msiName$4}: The Azure IMDS endpoint is available`);
1712
1726
  return true;
1713
1727
  });
1714
1728
  },
1715
1729
  async getToken(configuration, getTokenOptions = {}) {
1716
1730
  const { identityClient, scopes, clientId, resourceId } = configuration;
1717
1731
  if (process.env.AZURE_POD_IDENTITY_AUTHORITY_HOST) {
1718
- logger$h.info(`${msiName$4}: Using the Azure IMDS endpoint coming from the environment variable AZURE_POD_IDENTITY_AUTHORITY_HOST=${process.env.AZURE_POD_IDENTITY_AUTHORITY_HOST}.`);
1732
+ logger$i.info(`${msiName$4}: Using the Azure IMDS endpoint coming from the environment variable AZURE_POD_IDENTITY_AUTHORITY_HOST=${process.env.AZURE_POD_IDENTITY_AUTHORITY_HOST}.`);
1719
1733
  }
1720
1734
  else {
1721
- logger$h.info(`${msiName$4}: Using the default Azure IMDS endpoint ${imdsHost}.`);
1735
+ logger$i.info(`${msiName$4}: Using the default Azure IMDS endpoint ${imdsHost}.`);
1722
1736
  }
1723
1737
  let nextDelayInMs = imdsMsiRetryConfig.startDelayInMs;
1724
1738
  for (let retries = 0; retries < imdsMsiRetryConfig.maxRetries; retries++) {
1725
1739
  try {
1726
- const request = coreRestPipeline.createPipelineRequest(Object.assign(Object.assign({ abortSignal: getTokenOptions.abortSignal }, prepareRequestOptions$4(scopes, clientId, resourceId)), { allowInsecureConnection: true }));
1740
+ const request = coreRestPipeline.createPipelineRequest(Object.assign(Object.assign({ abortSignal: getTokenOptions.abortSignal }, prepareRequestOptions$3(scopes, clientId, resourceId)), { allowInsecureConnection: true }));
1727
1741
  const tokenResponse = await identityClient.sendTokenRequest(request);
1728
1742
  return (tokenResponse && tokenResponse.accessToken) || null;
1729
1743
  }
@@ -1742,11 +1756,11 @@ const imdsMsi = {
1742
1756
 
1743
1757
  // Copyright (c) Microsoft Corporation.
1744
1758
  const msiName$3 = "ManagedIdentityCredential - Azure Arc MSI";
1745
- const logger$g = credentialLogger(msiName$3);
1759
+ const logger$h = credentialLogger(msiName$3);
1746
1760
  /**
1747
1761
  * Generates the options used on the request for an access token.
1748
1762
  */
1749
- function prepareRequestOptions$3(scopes, clientId, resourceId) {
1763
+ function prepareRequestOptions$2(scopes, clientId, resourceId) {
1750
1764
  const resource = mapScopesToResource(scopes);
1751
1765
  if (!resource) {
1752
1766
  throw new Error(`${msiName$3}: Multiple scopes are not supported.`);
@@ -1780,7 +1794,7 @@ function prepareRequestOptions$3(scopes, clientId, resourceId) {
1780
1794
  * Retrieves the file contents at the given path using promises.
1781
1795
  * Useful since `fs`'s readFileSync locks the thread, and to avoid extra dependencies.
1782
1796
  */
1783
- function readFileAsync$2(path, options) {
1797
+ function readFileAsync$1(path, options) {
1784
1798
  return new Promise((resolve, reject) => fs.readFile(path, options, (err, data) => {
1785
1799
  if (err) {
1786
1800
  reject(err);
@@ -1812,15 +1826,16 @@ async function filePathRequest(identityClient, requestPrepareOptions) {
1812
1826
  * Defines how to determine whether the Azure Arc MSI is available, and also how to retrieve a token from the Azure Arc MSI.
1813
1827
  */
1814
1828
  const arcMsi = {
1829
+ name: "arc",
1815
1830
  async isAvailable({ scopes }) {
1816
1831
  const resource = mapScopesToResource(scopes);
1817
1832
  if (!resource) {
1818
- logger$g.info(`${msiName$3}: Unavailable. Multiple scopes are not supported.`);
1833
+ logger$h.info(`${msiName$3}: Unavailable. Multiple scopes are not supported.`);
1819
1834
  return false;
1820
1835
  }
1821
1836
  const result = Boolean(process.env.IMDS_ENDPOINT && process.env.IDENTITY_ENDPOINT);
1822
1837
  if (!result) {
1823
- logger$g.info(`${msiName$3}: The environment variables needed are: IMDS_ENDPOINT and IDENTITY_ENDPOINT`);
1838
+ logger$h.info(`${msiName$3}: The environment variables needed are: IMDS_ENDPOINT and IDENTITY_ENDPOINT`);
1824
1839
  }
1825
1840
  return result;
1826
1841
  },
@@ -1828,18 +1843,18 @@ const arcMsi = {
1828
1843
  var _a;
1829
1844
  const { identityClient, scopes, clientId, resourceId } = configuration;
1830
1845
  if (clientId) {
1831
- logger$g.warning(`${msiName$3}: user-assigned identities not supported. The argument clientId might be ignored by the service.`);
1846
+ logger$h.warning(`${msiName$3}: user-assigned identities not supported. The argument clientId might be ignored by the service.`);
1832
1847
  }
1833
1848
  if (resourceId) {
1834
- logger$g.warning(`${msiName$3}: user defined managed Identity by resource Id is not supported. Argument resourceId will be ignored.`);
1849
+ logger$h.warning(`${msiName$3}: user defined managed Identity by resource Id is not supported. Argument resourceId will be ignored.`);
1835
1850
  }
1836
- logger$g.info(`${msiName$3}: Authenticating.`);
1837
- const requestOptions = Object.assign(Object.assign({ disableJsonStringifyOnBody: true, deserializationMapper: undefined, abortSignal: getTokenOptions.abortSignal }, prepareRequestOptions$3(scopes, clientId, resourceId)), { allowInsecureConnection: true });
1851
+ logger$h.info(`${msiName$3}: Authenticating.`);
1852
+ const requestOptions = Object.assign(Object.assign({ disableJsonStringifyOnBody: true, deserializationMapper: undefined, abortSignal: getTokenOptions.abortSignal }, prepareRequestOptions$2(scopes, clientId, resourceId)), { allowInsecureConnection: true });
1838
1853
  const filePath = await filePathRequest(identityClient, requestOptions);
1839
1854
  if (!filePath) {
1840
1855
  throw new Error(`${msiName$3}: Failed to find the token file.`);
1841
1856
  }
1842
- const key = await readFileAsync$2(filePath, { encoding: "utf-8" });
1857
+ const key = await readFileAsync$1(filePath, { encoding: "utf-8" });
1843
1858
  (_a = requestOptions.headers) === null || _a === void 0 ? void 0 : _a.set("Authorization", `Basic ${key}`);
1844
1859
  const request = coreRestPipeline.createPipelineRequest(Object.assign(Object.assign({}, requestOptions), {
1845
1860
  // Generally, MSI endpoints use the HTTP protocol, without transport layer security (TLS).
@@ -1850,82 +1865,164 @@ const arcMsi = {
1850
1865
  };
1851
1866
 
1852
1867
  // Copyright (c) Microsoft Corporation.
1853
- const msiName$2 = "ManagedIdentityCredential - Token Exchange";
1854
- const logger$f = credentialLogger(msiName$2);
1855
- const readFileAsync$1 = util.promisify(fs__default["default"].readFile);
1856
1868
  /**
1857
- * Generates the options used on the request for an access token.
1869
+ * MSAL client assertion client. Calls to MSAL's confidential application's `acquireTokenByClientCredential` during `doGetToken`.
1870
+ * @internal
1858
1871
  */
1859
- function prepareRequestOptions$2(scopes, clientAssertion, clientId) {
1860
- var _a;
1861
- const bodyParams = {
1862
- scope: Array.isArray(scopes) ? scopes.join(" ") : scopes,
1863
- client_assertion: clientAssertion,
1864
- client_assertion_type: "urn:ietf:params:oauth:client-assertion-type:jwt-bearer",
1865
- client_id: clientId,
1866
- grant_type: "client_credentials",
1867
- };
1868
- const urlParams = new URLSearchParams(bodyParams);
1869
- const url = new URL(`${process.env.AZURE_TENANT_ID}/oauth2/v2.0/token`, (_a = process.env.AZURE_AUTHORITY_HOST) !== null && _a !== void 0 ? _a : DefaultAuthorityHost);
1870
- return {
1871
- url: url.toString(),
1872
- method: "POST",
1873
- body: urlParams.toString(),
1874
- headers: coreRestPipeline.createHttpHeaders({
1875
- Accept: "application/json",
1876
- }),
1877
- };
1872
+ class MsalClientAssertion extends MsalNode {
1873
+ constructor(options) {
1874
+ super(options);
1875
+ this.requiresConfidential = true;
1876
+ this.getAssertion = options.getAssertion;
1877
+ }
1878
+ async doGetToken(scopes, options = {}) {
1879
+ try {
1880
+ const assertion = await this.getAssertion();
1881
+ const result = await this.confidentialApp.acquireTokenByClientCredential({
1882
+ scopes,
1883
+ correlationId: options.correlationId,
1884
+ azureRegion: this.azureRegion,
1885
+ authority: options.authority,
1886
+ claims: options.claims,
1887
+ clientAssertion: assertion,
1888
+ });
1889
+ // The Client Credential flow does not return an account,
1890
+ // so each time getToken gets called, we will have to acquire a new token through the service.
1891
+ return this.handleResult(scopes, this.clientId, result || undefined);
1892
+ }
1893
+ catch (err) {
1894
+ let err2 = err;
1895
+ if (err === null || err === undefined) {
1896
+ err2 = new Error(JSON.stringify(err));
1897
+ }
1898
+ else {
1899
+ err2 = coreUtil.isError(err) ? err : new Error(String(err));
1900
+ }
1901
+ throw this.handleError(scopes, err2, options);
1902
+ }
1903
+ }
1878
1904
  }
1905
+
1906
+ // Copyright (c) Microsoft Corporation.
1907
+ const logger$g = credentialLogger("ClientAssertionCredential");
1879
1908
  /**
1880
- * Defines how to determine whether the token exchange MSI is available, and also how to retrieve a token from the token exchange MSI.
1909
+ * Authenticates a service principal with a JWT assertion.
1881
1910
  */
1882
- function tokenExchangeMsi() {
1883
- const azureFederatedTokenFilePath = process.env.AZURE_FEDERATED_TOKEN_FILE;
1884
- let azureFederatedTokenFileContent = undefined;
1885
- let cacheDate = undefined;
1886
- // Only reads from the assertion file once every 5 minutes
1887
- async function readAssertion() {
1911
+ class ClientAssertionCredential {
1912
+ /**
1913
+ * Creates an instance of the ClientAssertionCredential with the details
1914
+ * needed to authenticate against Azure Active Directory with a client
1915
+ * assertion provided by the developer through the `getAssertion` function parameter.
1916
+ *
1917
+ * @param tenantId - The Azure Active Directory tenant (directory) ID.
1918
+ * @param clientId - The client (application) ID of an App Registration in the tenant.
1919
+ * @param getAssertion - A function that retrieves the assertion for the credential to use.
1920
+ * @param options - Options for configuring the client which makes the authentication request.
1921
+ */
1922
+ constructor(tenantId, clientId, getAssertion, options = {}) {
1923
+ if (!tenantId || !clientId || !getAssertion) {
1924
+ throw new Error("ClientAssertionCredential: tenantId, clientId, and clientAssertion are required parameters.");
1925
+ }
1926
+ this.tenantId = tenantId;
1927
+ this.additionallyAllowedTenantIds = resolveAddionallyAllowedTenantIds(options === null || options === void 0 ? void 0 : options.additionallyAllowedTenants);
1928
+ this.clientId = clientId;
1929
+ this.options = options;
1930
+ this.msalFlow = new MsalClientAssertion(Object.assign(Object.assign({}, options), { logger: logger$g, clientId: this.clientId, tenantId: this.tenantId, tokenCredentialOptions: this.options, getAssertion }));
1931
+ }
1932
+ /**
1933
+ * Authenticates with Azure Active Directory and returns an access token if successful.
1934
+ * If authentication fails, a {@link CredentialUnavailableError} will be thrown with the details of the failure.
1935
+ *
1936
+ * @param scopes - The list of scopes for which the token will have access.
1937
+ * @param options - The options used to configure any requests this
1938
+ * TokenCredential implementation might make.
1939
+ */
1940
+ async getToken(scopes, options = {}) {
1941
+ return tracingClient.withSpan(`${this.constructor.name}.getToken`, options, async (newOptions) => {
1942
+ newOptions.tenantId = processMultiTenantRequest(this.tenantId, newOptions, this.additionallyAllowedTenantIds);
1943
+ const arrayScopes = Array.isArray(scopes) ? scopes : [scopes];
1944
+ return this.msalFlow.getToken(arrayScopes, newOptions);
1945
+ });
1946
+ }
1947
+ }
1948
+
1949
+ // Copyright (c) Microsoft Corporation.
1950
+ /**
1951
+ * WorkloadIdentityCredential supports Azure workload identity authentication on Kubernetes.
1952
+ * Refer to <a href="https://learn.microsoft.com/azure/aks/workload-identity-overview">Azure Active Directory Workload Identity</a>
1953
+ * for more information.
1954
+ */
1955
+ class WorkloadIdentityCredential {
1956
+ /**
1957
+ * WorkloadIdentityCredential supports Azure workload identity on Kubernetes.
1958
+ *
1959
+ * @param options - The identity client options to use for authentication.
1960
+ */
1961
+ constructor(options = {}) {
1962
+ this.azureFederatedTokenFileContent = undefined;
1963
+ this.cacheDate = undefined;
1964
+ if (!options.tenantId || !options.clientId || !options.federatedTokenFilePath) {
1965
+ throw new Error("WorkloadIdentityCredential: tenantId, clientId, and federatedTokenFilePath are required parameters.");
1966
+ }
1967
+ this.federatedTokenFilePath = options.federatedTokenFilePath;
1968
+ this.client = new ClientAssertionCredential(options.tenantId, options.clientId, this.readFileContents.bind(this), options);
1969
+ }
1970
+ /**
1971
+ * Authenticates with Azure Active Directory and returns an access token if successful.
1972
+ * If authentication fails, a {@link CredentialUnavailableError} will be thrown with the details of the failure.
1973
+ *
1974
+ * @param scopes - The list of scopes for which the token will have access.
1975
+ * @param options - The options used to configure any requests this
1976
+ * TokenCredential implementation might make.
1977
+ */
1978
+ getToken(scopes, options) {
1979
+ return this.client.getToken(scopes, options);
1980
+ }
1981
+ async readFileContents() {
1888
1982
  // Cached assertions expire after 5 minutes
1889
- if (cacheDate !== undefined && Date.now() - cacheDate >= 1000 * 60 * 5) {
1890
- azureFederatedTokenFileContent = undefined;
1983
+ if (this.cacheDate !== undefined && Date.now() - this.cacheDate >= 1000 * 60 * 5) {
1984
+ this.azureFederatedTokenFileContent = undefined;
1891
1985
  }
1892
- if (!azureFederatedTokenFileContent) {
1893
- const file = await readFileAsync$1(azureFederatedTokenFilePath, "utf8");
1986
+ if (!this.azureFederatedTokenFileContent) {
1987
+ const file = await promises.readFile(this.federatedTokenFilePath, "utf8");
1894
1988
  const value = file.trim();
1895
1989
  if (!value) {
1896
- throw new Error(`No content on the file ${azureFederatedTokenFilePath}, indicated by the environment variable AZURE_FEDERATED_TOKEN_FILE`);
1990
+ throw new Error(`No content on the file ${this.federatedTokenFilePath}.`);
1897
1991
  }
1898
1992
  else {
1899
- azureFederatedTokenFileContent = value;
1900
- cacheDate = Date.now();
1993
+ this.azureFederatedTokenFileContent = value;
1994
+ this.cacheDate = Date.now();
1901
1995
  }
1902
1996
  }
1903
- return azureFederatedTokenFileContent;
1997
+ return this.azureFederatedTokenFileContent;
1904
1998
  }
1999
+ }
2000
+
2001
+ // Copyright (c) Microsoft Corporation.
2002
+ const msiName$2 = "ManagedIdentityCredential - Token Exchange";
2003
+ const logger$f = credentialLogger(msiName$2);
2004
+ /**
2005
+ * Defines how to determine whether the token exchange MSI is available, and also how to retrieve a token from the token exchange MSI.
2006
+ */
2007
+ function tokenExchangeMsi() {
1905
2008
  return {
2009
+ name: "tokenExchangeMsi",
1906
2010
  async isAvailable({ clientId }) {
1907
2011
  const env = process.env;
1908
- const result = Boolean((clientId || env.AZURE_CLIENT_ID) && env.AZURE_TENANT_ID && azureFederatedTokenFilePath);
2012
+ const result = Boolean((clientId || env.AZURE_CLIENT_ID) &&
2013
+ env.AZURE_TENANT_ID &&
2014
+ process.env.AZURE_FEDERATED_TOKEN_FILE);
1909
2015
  if (!result) {
1910
2016
  logger$f.info(`${msiName$2}: Unavailable. The environment variables needed are: AZURE_CLIENT_ID (or the client ID sent through the parameters), AZURE_TENANT_ID and AZURE_FEDERATED_TOKEN_FILE`);
1911
2017
  }
1912
2018
  return result;
1913
2019
  },
1914
2020
  async getToken(configuration, getTokenOptions = {}) {
1915
- const { identityClient, scopes, clientId } = configuration;
1916
- logger$f.info(`${msiName$2}: Using the client assertion coming from environment variables.`);
1917
- let assertion;
1918
- try {
1919
- assertion = await readAssertion();
1920
- }
1921
- catch (err) {
1922
- throw new Error(`${msiName$2}: Failed to read ${azureFederatedTokenFilePath}, indicated by the environment variable AZURE_FEDERATED_TOKEN_FILE`);
1923
- }
1924
- const request = coreRestPipeline.createPipelineRequest(Object.assign(Object.assign({ abortSignal: getTokenOptions.abortSignal }, prepareRequestOptions$2(scopes, assertion, clientId || process.env.AZURE_CLIENT_ID)), {
1925
- // Generally, MSI endpoints use the HTTP protocol, without transport layer security (TLS).
1926
- allowInsecureConnection: true }));
1927
- const tokenResponse = await identityClient.sendTokenRequest(request);
1928
- return (tokenResponse && tokenResponse.accessToken) || null;
2021
+ const { scopes, clientId } = configuration;
2022
+ const identityClientTokenCredentialOptions = {};
2023
+ const workloadIdentityCredential = new WorkloadIdentityCredential(Object.assign(Object.assign({ clientId, tenantId: process.env.AZURE_TENANT_ID, federatedTokenFilePath: process.env.AZURE_FEDERATED_TOKEN_FILE }, identityClientTokenCredentialOptions), { disableInstanceDiscovery: true }));
2024
+ const token = await workloadIdentityCredential.getToken(scopes, getTokenOptions);
2025
+ return token;
1929
2026
  },
1930
2027
  };
1931
2028
  }
@@ -1982,6 +2079,7 @@ function prepareRequestOptions$1(scopes, clientId, resourceId) {
1982
2079
  * Defines how to determine whether the Azure Service Fabric MSI is available, and also how to retrieve a token from the Azure Service Fabric MSI.
1983
2080
  */
1984
2081
  const fabricMsi = {
2082
+ name: "fabricMsi",
1985
2083
  async isAvailable({ scopes }) {
1986
2084
  const resource = mapScopesToResource(scopes);
1987
2085
  if (!resource) {
@@ -2060,6 +2158,7 @@ function prepareRequestOptions(scopes, clientId, resourceId) {
2060
2158
  * Defines how to determine whether the Azure App Service MSI is available, and also how to retrieve a token from the Azure App Service MSI.
2061
2159
  */
2062
2160
  const appServiceMsi2019 = {
2161
+ name: "appServiceMsi2019",
2063
2162
  async isAvailable({ scopes }) {
2064
2163
  const resource = mapScopesToResource(scopes);
2065
2164
  if (!resource) {
@@ -2202,12 +2301,17 @@ class ManagedIdentityCredential {
2202
2301
  const appTokenParameters = {
2203
2302
  correlationId: this.identityClient.getCorrelationId(),
2204
2303
  tenantId: (options === null || options === void 0 ? void 0 : options.tenantId) || "organizations",
2205
- scopes: [...scopes],
2304
+ scopes: Array.isArray(scopes) ? scopes : [scopes],
2206
2305
  claims: options === null || options === void 0 ? void 0 : options.claims,
2207
2306
  };
2208
2307
  this.confidentialApp.SetAppTokenProvider(async (appTokenProviderParameters = appTokenParameters) => {
2209
2308
  logger$c.info(`SetAppTokenProvider invoked with parameters- ${JSON.stringify(appTokenProviderParameters)}`);
2210
- const resultToken = await this.authenticateManagedIdentity(scopes, Object.assign(Object.assign({}, updatedOptions), appTokenProviderParameters));
2309
+ const availableMSI = await this.cachedAvailableMSI(scopes, updatedOptions);
2310
+ const appTokenParams = Object.assign({}, appTokenProviderParameters);
2311
+ if (availableMSI.name === "tokenExchangeMsi") {
2312
+ appTokenParams.tenantId = process.env.AZURE_TENANT_ID;
2313
+ }
2314
+ const resultToken = await this.authenticateManagedIdentity(scopes, Object.assign(Object.assign({}, updatedOptions), appTokenParams));
2211
2315
  if (resultToken) {
2212
2316
  logger$c.info(`SetAppTokenProvider has saved the token in cache`);
2213
2317
  const expiresInSeconds = (resultToken === null || resultToken === void 0 ? void 0 : resultToken.expiresOnTimestamp)
@@ -2714,10 +2818,6 @@ class ChainedTokenCredential {
2714
2818
  * ```
2715
2819
  */
2716
2820
  constructor(...sources) {
2717
- /**
2718
- * The message to use when the chained token fails to get a token
2719
- */
2720
- this.UnavailableMessage = "ChainedTokenCredential => failed to retrieve a token from the included credentials";
2721
2821
  this._sources = [];
2722
2822
  this._sources = sources;
2723
2823
  }
@@ -3202,6 +3302,136 @@ class EnvironmentCredential {
3202
3302
  }
3203
3303
  }
3204
3304
 
3305
+ // Copyright (c) Microsoft Corporation.
3306
+ /**
3307
+ * Mockable reference to the Developer CLI credential cliCredentialFunctions
3308
+ * @internal
3309
+ */
3310
+ const developerCliCredentialInternals = {
3311
+ /**
3312
+ * @internal
3313
+ */
3314
+ getSafeWorkingDir() {
3315
+ if (process.platform === "win32") {
3316
+ if (!process.env.SystemRoot) {
3317
+ throw new Error("Azure Developer CLI credential expects a 'SystemRoot' environment variable");
3318
+ }
3319
+ return process.env.SystemRoot;
3320
+ }
3321
+ else {
3322
+ return "/bin";
3323
+ }
3324
+ },
3325
+ /**
3326
+ * Gets the access token from Azure Developer CLI
3327
+ * @param scopes - The scopes to use when getting the token
3328
+ * @internal
3329
+ */
3330
+ async getAzdAccessToken(scopes, tenantId) {
3331
+ let tenantSection = [];
3332
+ if (tenantId) {
3333
+ tenantSection = ["--tenant-id", tenantId];
3334
+ }
3335
+ return new Promise((resolve, reject) => {
3336
+ try {
3337
+ child_process__default["default"].execFile("azd", [
3338
+ "auth",
3339
+ "token",
3340
+ "--output",
3341
+ "json",
3342
+ ...scopes.reduce((previous, current) => previous.concat("--scope", current), []),
3343
+ ...tenantSection,
3344
+ ], { cwd: developerCliCredentialInternals.getSafeWorkingDir(), shell: true }, (error, stdout, stderr) => {
3345
+ resolve({ stdout, stderr, error });
3346
+ });
3347
+ }
3348
+ catch (err) {
3349
+ reject(err);
3350
+ }
3351
+ });
3352
+ },
3353
+ };
3354
+ const logger$4 = credentialLogger("AzureDeveloperCliCredential");
3355
+ /**
3356
+ * This credential will use the currently logged-in user login information
3357
+ * via the Azure Developer CLI ('az') commandline tool.
3358
+ * To do so, it will read the user access token and expire time
3359
+ * with Azure Developer CLI command "azd auth token".
3360
+ */
3361
+ class AzureDeveloperCliCredential {
3362
+ /**
3363
+ * Creates an instance of the {@link AzureDeveloperCliCredential}.
3364
+ *
3365
+ * To use this credential, ensure that you have already logged
3366
+ * in via the 'azd' tool using the command "azd login" from the commandline.
3367
+ *
3368
+ * @param options - Options, to optionally allow multi-tenant requests.
3369
+ */
3370
+ constructor(options) {
3371
+ this.tenantId = options === null || options === void 0 ? void 0 : options.tenantId;
3372
+ this.additionallyAllowedTenantIds = resolveAddionallyAllowedTenantIds(options === null || options === void 0 ? void 0 : options.additionallyAllowedTenants);
3373
+ }
3374
+ /**
3375
+ * Authenticates with Azure Active Directory and returns an access token if successful.
3376
+ * If authentication fails, a {@link CredentialUnavailableError} will be thrown with the details of the failure.
3377
+ *
3378
+ * @param scopes - The list of scopes for which the token will have access.
3379
+ * @param options - The options used to configure any requests this
3380
+ * TokenCredential implementation might make.
3381
+ */
3382
+ async getToken(scopes, options = {}) {
3383
+ const tenantId = processMultiTenantRequest(this.tenantId, options, this.additionallyAllowedTenantIds);
3384
+ let scopeList;
3385
+ if (typeof scopes === "string") {
3386
+ scopeList = [scopes];
3387
+ }
3388
+ else {
3389
+ scopeList = scopes;
3390
+ }
3391
+ logger$4.getToken.info(`Using the scopes ${scopes}`);
3392
+ return tracingClient.withSpan(`${this.constructor.name}.getToken`, options, async () => {
3393
+ var _a, _b, _c;
3394
+ try {
3395
+ const obj = await developerCliCredentialInternals.getAzdAccessToken(scopeList, tenantId);
3396
+ const isNotLoggedInError = (_a = obj.stderr) === null || _a === void 0 ? void 0 : _a.match("not logged in, run `azd login` to login");
3397
+ const isNotInstallError = ((_b = obj.stderr) === null || _b === void 0 ? void 0 : _b.match("azd:(.*)not found")) ||
3398
+ ((_c = obj.stderr) === null || _c === void 0 ? void 0 : _c.startsWith("'azd' is not recognized"));
3399
+ if (isNotInstallError || (obj.error && obj.error.code === "ENOENT")) {
3400
+ const error = new CredentialUnavailableError("Azure Developer CLI could not be found. Please visit https://aka.ms/azure-dev for installation instructions and then, once installed, authenticate to your Azure account using 'azd login'.");
3401
+ logger$4.getToken.info(formatError(scopes, error));
3402
+ throw error;
3403
+ }
3404
+ if (isNotLoggedInError) {
3405
+ const error = new CredentialUnavailableError("Please run 'azd login' from a command prompt to authenticate before using this credential.");
3406
+ logger$4.getToken.info(formatError(scopes, error));
3407
+ throw error;
3408
+ }
3409
+ try {
3410
+ const resp = JSON.parse(obj.stdout);
3411
+ logger$4.getToken.info(formatSuccess(scopes));
3412
+ return {
3413
+ token: resp.token,
3414
+ expiresOnTimestamp: new Date(resp.expiresOn).getTime(),
3415
+ };
3416
+ }
3417
+ catch (e) {
3418
+ if (obj.stderr) {
3419
+ throw new CredentialUnavailableError(obj.stderr);
3420
+ }
3421
+ throw e;
3422
+ }
3423
+ }
3424
+ catch (err) {
3425
+ const error = err.name === "CredentialUnavailableError"
3426
+ ? err
3427
+ : new CredentialUnavailableError(err.message || "Unknown error while trying to retrieve the access token");
3428
+ logger$4.getToken.info(formatError(scopes, error));
3429
+ throw error;
3430
+ }
3431
+ });
3432
+ }
3433
+ }
3434
+
3205
3435
  // Copyright (c) Microsoft Corporation.
3206
3436
  /**
3207
3437
  * A shim around ManagedIdentityCredential that adapts it to accept
@@ -3216,11 +3446,16 @@ class DefaultManagedIdentityCredential extends ManagedIdentityCredential {
3216
3446
  var _a;
3217
3447
  const managedIdentityClientId = (_a = options === null || options === void 0 ? void 0 : options.managedIdentityClientId) !== null && _a !== void 0 ? _a : process.env.AZURE_CLIENT_ID;
3218
3448
  const managedResourceId = options === null || options === void 0 ? void 0 : options.managedIdentityResourceId;
3449
+ const workloadFile = process.env.AZURE_FEDERATED_TOKEN_FILE;
3219
3450
  // ManagedIdentityCredential throws if both the resourceId and the clientId are provided.
3220
3451
  if (managedResourceId) {
3221
3452
  const managedIdentityResourceIdOptions = Object.assign(Object.assign({}, options), { resourceId: managedResourceId });
3222
3453
  super(managedIdentityResourceIdOptions);
3223
3454
  }
3455
+ else if (workloadFile) {
3456
+ const workloadIdentityCredentialOptions = Object.assign(Object.assign({}, options), { clientId: managedIdentityClientId, federatedTokenFilePath: workloadFile });
3457
+ super(workloadIdentityCredentialOptions);
3458
+ }
3224
3459
  else if (managedIdentityClientId) {
3225
3460
  const managedIdentityClientOptions = Object.assign(Object.assign({}, options), { clientId: managedIdentityClientId });
3226
3461
  super(managedIdentityClientOptions);
@@ -3232,7 +3467,9 @@ class DefaultManagedIdentityCredential extends ManagedIdentityCredential {
3232
3467
  }
3233
3468
  const defaultCredentials = [
3234
3469
  EnvironmentCredential,
3470
+ WorkloadIdentityCredential,
3235
3471
  DefaultManagedIdentityCredential,
3472
+ AzureDeveloperCliCredential,
3236
3473
  AzureCliCredential,
3237
3474
  AzurePowerShellCredential,
3238
3475
  ];
@@ -3243,90 +3480,6 @@ const defaultCredentials = [
3243
3480
  class DefaultAzureCredential extends ChainedTokenCredential {
3244
3481
  constructor(options) {
3245
3482
  super(...defaultCredentials.map((ctor) => new ctor(options)));
3246
- this.UnavailableMessage =
3247
- "DefaultAzureCredential => failed to retrieve a token from the included credentials. To troubleshoot, visit https://aka.ms/azsdk/js/identity/defaultazurecredential/troubleshoot.";
3248
- }
3249
- }
3250
-
3251
- // Copyright (c) Microsoft Corporation.
3252
- /**
3253
- * MSAL client assertion client. Calls to MSAL's confidential application's `acquireTokenByClientCredential` during `doGetToken`.
3254
- * @internal
3255
- */
3256
- class MsalClientAssertion extends MsalNode {
3257
- constructor(options) {
3258
- super(options);
3259
- this.requiresConfidential = true;
3260
- this.getAssertion = options.getAssertion;
3261
- }
3262
- async doGetToken(scopes, options = {}) {
3263
- try {
3264
- const assertion = await this.getAssertion();
3265
- const result = await this.confidentialApp.acquireTokenByClientCredential({
3266
- scopes,
3267
- correlationId: options.correlationId,
3268
- azureRegion: this.azureRegion,
3269
- authority: options.authority,
3270
- claims: options.claims,
3271
- clientAssertion: assertion,
3272
- });
3273
- // The Client Credential flow does not return an account,
3274
- // so each time getToken gets called, we will have to acquire a new token through the service.
3275
- return this.handleResult(scopes, this.clientId, result || undefined);
3276
- }
3277
- catch (err) {
3278
- let err2 = err;
3279
- if (err === null || err === undefined) {
3280
- err2 = new Error(JSON.stringify(err));
3281
- }
3282
- else {
3283
- err2 = coreUtil.isError(err) ? err : new Error(String(err));
3284
- }
3285
- throw this.handleError(scopes, err2, options);
3286
- }
3287
- }
3288
- }
3289
-
3290
- // Copyright (c) Microsoft Corporation.
3291
- const logger$4 = credentialLogger("ClientAssertionCredential");
3292
- /**
3293
- * Authenticates a service principal with a JWT assertion.
3294
- */
3295
- class ClientAssertionCredential {
3296
- /**
3297
- * Creates an instance of the ClientAssertionCredential with the details
3298
- * needed to authenticate against Azure Active Directory with a client
3299
- * assertion provided by the developer through the `getAssertion` function parameter.
3300
- *
3301
- * @param tenantId - The Azure Active Directory tenant (directory) ID.
3302
- * @param clientId - The client (application) ID of an App Registration in the tenant.
3303
- * @param getAssertion - A function that retrieves the assertion for the credential to use.
3304
- * @param options - Options for configuring the client which makes the authentication request.
3305
- */
3306
- constructor(tenantId, clientId, getAssertion, options = {}) {
3307
- if (!tenantId || !clientId || !getAssertion) {
3308
- throw new Error("ClientAssertionCredential: tenantId, clientId, and clientAssertion are required parameters.");
3309
- }
3310
- this.tenantId = tenantId;
3311
- this.additionallyAllowedTenantIds = resolveAddionallyAllowedTenantIds(options === null || options === void 0 ? void 0 : options.additionallyAllowedTenants);
3312
- this.clientId = clientId;
3313
- this.options = options;
3314
- this.msalFlow = new MsalClientAssertion(Object.assign(Object.assign({}, options), { logger: logger$4, clientId: this.clientId, tenantId: this.tenantId, tokenCredentialOptions: this.options, getAssertion }));
3315
- }
3316
- /**
3317
- * Authenticates with Azure Active Directory and returns an access token if successful.
3318
- * If authentication fails, a {@link CredentialUnavailableError} will be thrown with the details of the failure.
3319
- *
3320
- * @param scopes - The list of scopes for which the token will have access.
3321
- * @param options - The options used to configure any requests this
3322
- * TokenCredential implementation might make.
3323
- */
3324
- async getToken(scopes, options = {}) {
3325
- return tracingClient.withSpan(`${this.constructor.name}.getToken`, options, async (newOptions) => {
3326
- newOptions.tenantId = processMultiTenantRequest(this.tenantId, newOptions, this.additionallyAllowedTenantIds);
3327
- const arrayScopes = Array.isArray(scopes) ? scopes : [scopes];
3328
- return this.msalFlow.getToken(arrayScopes, newOptions);
3329
- });
3330
3483
  }
3331
3484
  }
3332
3485
 
@@ -3884,9 +4037,10 @@ exports.ManagedIdentityCredential = ManagedIdentityCredential;
3884
4037
  exports.OnBehalfOfCredential = OnBehalfOfCredential;
3885
4038
  exports.UsernamePasswordCredential = UsernamePasswordCredential;
3886
4039
  exports.VisualStudioCodeCredential = VisualStudioCodeCredential;
4040
+ exports.WorkloadIdentityCredential = WorkloadIdentityCredential;
3887
4041
  exports.deserializeAuthenticationRecord = deserializeAuthenticationRecord;
3888
4042
  exports.getDefaultAzureCredential = getDefaultAzureCredential;
3889
- exports.logger = logger$l;
4043
+ exports.logger = logger$m;
3890
4044
  exports.serializeAuthenticationRecord = serializeAuthenticationRecord;
3891
4045
  exports.useIdentityPlugin = useIdentityPlugin;
3892
4046
  //# sourceMappingURL=index.js.map