@microsoft/teamsfx 0.4.1-alpha.fa070464.0 → 0.4.2-alpha.01a113d2.0

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.
@@ -1,9 +1,8 @@
1
1
  import { __extends, __awaiter, __generator } from 'tslib';
2
2
  import jwt_decode from 'jwt-decode';
3
3
  import * as microsoftTeams from '@microsoft/teams-js';
4
- import axios from 'axios';
4
+ import { PublicClientApplication } from '@azure/msal-browser';
5
5
  import { Client } from '@microsoft/microsoft-graph-client';
6
- import { ManagedIdentityCredential } from '@azure/identity';
7
6
 
8
7
  // Copyright (c) Microsoft Corporation.
9
8
  /**
@@ -56,6 +55,10 @@ var ErrorCode;
56
55
  * Operation failed.
57
56
  */
58
57
  ErrorCode["FailedOperation"] = "FailedOperation";
58
+ /**
59
+ * Version of SDK and project does not match.
60
+ */
61
+ ErrorCode["ProjectNeedUpgrade"] = "ProjectNeedUpgrade";
59
62
  })(ErrorCode || (ErrorCode = {}));
60
63
  /**
61
64
  * @internal
@@ -176,7 +179,7 @@ function getLogLevel() {
176
179
  return internalLogger.level;
177
180
  }
178
181
  var InternalLogger = /** @class */ (function () {
179
- function InternalLogger() {
182
+ function InternalLogger(name, logLevel) {
180
183
  this.level = undefined;
181
184
  this.defaultLogger = {
182
185
  verbose: console.debug,
@@ -184,6 +187,8 @@ var InternalLogger = /** @class */ (function () {
184
187
  warn: console.warn,
185
188
  error: console.error,
186
189
  };
190
+ this.name = name;
191
+ this.level = logLevel;
187
192
  }
188
193
  InternalLogger.prototype.error = function (message) {
189
194
  this.log(LogLevel.Error, function (x) { return x.error; }, message);
@@ -202,7 +207,13 @@ var InternalLogger = /** @class */ (function () {
202
207
  return;
203
208
  }
204
209
  var timestamp = new Date().toUTCString();
205
- var logHeader = "[" + timestamp + "] : @microsoft/teamsfx : " + LogLevel[logLevel] + " - ";
210
+ var logHeader;
211
+ if (this.name) {
212
+ logHeader = "[" + timestamp + "] : @microsoft/teamsfx - " + this.name + " : " + LogLevel[logLevel] + " - ";
213
+ }
214
+ else {
215
+ logHeader = "[" + timestamp + "] : @microsoft/teamsfx : " + LogLevel[logLevel] + " - ";
216
+ }
206
217
  var logMessage = "" + logHeader + message;
207
218
  if (this.level !== undefined && this.level <= logLevel) {
208
219
  if (this.customLogger) {
@@ -311,6 +322,57 @@ function getUserInfoFromSsoToken(ssoToken) {
311
322
  }
312
323
  return userInfo;
313
324
  }
325
+ /**
326
+ * @internal
327
+ */
328
+ function getTenantIdAndLoginHintFromSsoToken(ssoToken) {
329
+ if (!ssoToken) {
330
+ var errorMsg = "SSO token is undefined.";
331
+ internalLogger.error(errorMsg);
332
+ throw new ErrorWithCode(errorMsg, ErrorCode.InvalidParameter);
333
+ }
334
+ var tokenObject = parseJwt(ssoToken);
335
+ var userInfo = {
336
+ tid: tokenObject.tid,
337
+ loginHint: tokenObject.ver === "2.0"
338
+ ? tokenObject.preferred_username
339
+ : tokenObject.upn,
340
+ };
341
+ return userInfo;
342
+ }
343
+ /**
344
+ * @internal
345
+ */
346
+ function parseAccessTokenFromAuthCodeTokenResponse(tokenResponse) {
347
+ try {
348
+ var tokenResponseObject = typeof tokenResponse == "string"
349
+ ? JSON.parse(tokenResponse)
350
+ : tokenResponse;
351
+ if (!tokenResponseObject || !tokenResponseObject.accessToken) {
352
+ var errorMsg = "Get empty access token from Auth Code token response.";
353
+ internalLogger.error(errorMsg);
354
+ throw new Error(errorMsg);
355
+ }
356
+ var token = tokenResponseObject.accessToken;
357
+ var tokenObject = parseJwt(token);
358
+ if (tokenObject.ver !== "1.0" && tokenObject.ver !== "2.0") {
359
+ var errorMsg = "SSO token is not valid with an unknown version: " + tokenObject.ver;
360
+ internalLogger.error(errorMsg);
361
+ throw new Error(errorMsg);
362
+ }
363
+ var accessToken = {
364
+ token: token,
365
+ expiresOnTimestamp: tokenObject.exp * 1000,
366
+ };
367
+ return accessToken;
368
+ }
369
+ catch (error) {
370
+ var errorMsg = "Parse access token failed from Auth Code token response in node env with error: " +
371
+ error.message;
372
+ internalLogger.error(errorMsg);
373
+ throw new ErrorWithCode(errorMsg, ErrorCode.InternalError);
374
+ }
375
+ }
314
376
  /**
315
377
  * Format string template with replacements
316
378
  *
@@ -565,46 +627,10 @@ var OnBehalfOfUserCredential = /** @class */ (function () {
565
627
  }());
566
628
 
567
629
  // Copyright (c) Microsoft Corporation.
568
- // Licensed under the MIT license.
569
- /**
570
- * Configuration used in initialization.
571
- * @internal
572
- */
573
- var Cache = /** @class */ (function () {
574
- function Cache() {
575
- }
576
- Cache.get = function (key) {
577
- return sessionStorage.getItem(key);
578
- };
579
- Cache.set = function (key, value) {
580
- sessionStorage.setItem(key, value);
581
- };
582
- Cache.remove = function (key) {
583
- sessionStorage.removeItem(key);
584
- };
585
- return Cache;
586
- }());
587
-
588
- // Copyright (c) Microsoft Corporation.
589
- // Licensed under the MIT license.
590
- /**
591
- * @internal
592
- */
593
- var GrantType;
594
- (function (GrantType) {
595
- GrantType["authCode"] = "authorization_code";
596
- GrantType["ssoToken"] = "sso_token";
597
- })(GrantType || (GrantType = {}));
598
-
599
- // Copyright (c) Microsoft Corporation.
600
- var accessTokenCacheKeyPrefix = "accessToken";
601
- var separator = "-";
602
630
  var tokenRefreshTimeSpanInMillisecond = 5 * 60 * 1000;
603
631
  var initializeTeamsSdkTimeoutInMillisecond = 5000;
604
632
  var loginPageWidth = 600;
605
633
  var loginPageHeight = 535;
606
- var maxRetryCount = 3;
607
- var retryTimeSpanInMillisecond = 3000;
608
634
  /**
609
635
  * Represent Teams current user's identity, and it is used within Teams tab application.
610
636
  *
@@ -622,7 +648,6 @@ var TeamsUserCredential = /** @class */ (function () {
622
648
  * ```typescript
623
649
  * const config = {
624
650
  * authentication: {
625
- * runtimeConnectorEndpoint: "https://xxx.xxx.com",
626
651
  * initiateLoginEndpoint: "https://localhost:3000/auth-start.html",
627
652
  * clientId: "xxx"
628
653
  * }
@@ -640,6 +665,7 @@ var TeamsUserCredential = /** @class */ (function () {
640
665
  internalLogger.info("Create teams user credential");
641
666
  this.config = this.loadAndValidateConfig();
642
667
  this.ssoToken = null;
668
+ this.initialized = false;
643
669
  }
644
670
  /**
645
671
  * Popup login page to get user's access token with specific scopes.
@@ -657,7 +683,6 @@ var TeamsUserCredential = /** @class */ (function () {
657
683
  * @param scopes - The list of scopes for which the token will have access, before that, we will request user to consent.
658
684
  *
659
685
  * @throws {@link ErrorCode|InternalError} when failed to login with unknown error.
660
- * @throws {@link ErrorCode|ServiceError} when simple auth server failed to exchange access token.
661
686
  * @throws {@link ErrorCode|ConsentFailed} when user canceled or failed to consent.
662
687
  * @throws {@link ErrorCode|InvalidParameter} when scopes is not a valid string or string array.
663
688
  * @throws {@link ErrorCode|RuntimeNotSupported} when runtime is nodeJS.
@@ -669,57 +694,73 @@ var TeamsUserCredential = /** @class */ (function () {
669
694
  var scopesStr;
670
695
  var _this = this;
671
696
  return __generator(this, function (_a) {
672
- validateScopesType(scopes);
673
- scopesStr = typeof scopes === "string" ? scopes : scopes.join(" ");
674
- internalLogger.info("Popup login page to get user's access token with scopes: " + scopesStr);
675
- return [2 /*return*/, new Promise(function (resolve, reject) {
676
- microsoftTeams.initialize(function () {
677
- microsoftTeams.authentication.authenticate({
678
- url: _this.config.initiateLoginEndpoint + "?clientId=" + _this.config.clientId + "&scope=" + encodeURI(scopesStr),
679
- width: loginPageWidth,
680
- height: loginPageHeight,
681
- successCallback: function (result) { return __awaiter(_this, void 0, void 0, function () {
682
- var errorMsg, authCodeResult, err_1;
683
- return __generator(this, function (_a) {
684
- switch (_a.label) {
685
- case 0:
686
- if (!result) {
687
- errorMsg = "Get empty authentication result from Teams";
688
- internalLogger.error(errorMsg);
689
- reject(new ErrorWithCode(errorMsg, ErrorCode.InternalError));
690
- return [2 /*return*/];
691
- }
692
- authCodeResult = JSON.parse(result);
693
- _a.label = 1;
694
- case 1:
695
- _a.trys.push([1, 3, , 4]);
696
- return [4 /*yield*/, this.exchangeAccessTokenFromSimpleAuthServer(scopesStr, authCodeResult)];
697
- case 2:
698
- _a.sent();
697
+ switch (_a.label) {
698
+ case 0:
699
+ validateScopesType(scopes);
700
+ scopesStr = typeof scopes === "string" ? scopes : scopes.join(" ");
701
+ internalLogger.info("Popup login page to get user's access token with scopes: " + scopesStr);
702
+ if (!!this.initialized) return [3 /*break*/, 2];
703
+ return [4 /*yield*/, this.init()];
704
+ case 1:
705
+ _a.sent();
706
+ _a.label = 2;
707
+ case 2: return [2 /*return*/, new Promise(function (resolve, reject) {
708
+ microsoftTeams.initialize(function () {
709
+ microsoftTeams.authentication.authenticate({
710
+ url: _this.config.initiateLoginEndpoint + "?clientId=" + _this.config.clientId + "&scope=" + encodeURI(scopesStr) + "&loginHint=" + _this.loginHint,
711
+ width: loginPageWidth,
712
+ height: loginPageHeight,
713
+ successCallback: function (result) { return __awaiter(_this, void 0, void 0, function () {
714
+ var errorMsg, resultJson, failedToParseResult, helpLink, usingPreviousAuthPage;
715
+ return __generator(this, function (_a) {
716
+ if (!result) {
717
+ errorMsg = "Get empty authentication result from MSAL";
718
+ internalLogger.error(errorMsg);
719
+ reject(new ErrorWithCode(errorMsg, ErrorCode.InternalError));
720
+ return [2 /*return*/];
721
+ }
722
+ resultJson = {};
723
+ try {
724
+ resultJson = JSON.parse(result);
725
+ }
726
+ catch (error) {
727
+ failedToParseResult = "Failed to parse result to Json.";
728
+ internalLogger.verbose(failedToParseResult);
699
729
  resolve();
700
- return [3 /*break*/, 4];
701
- case 3:
702
- err_1 = _a.sent();
703
- reject(this.generateAuthServerError(err_1));
704
- return [3 /*break*/, 4];
705
- case 4: return [2 /*return*/];
706
- }
707
- });
708
- }); },
709
- failureCallback: function (reason) {
710
- var errorMsg = "Consent failed for the scope " + scopesStr + " with error: " + reason;
711
- internalLogger.error(errorMsg);
712
- reject(new ErrorWithCode(errorMsg, ErrorCode.ConsentFailed));
713
- },
730
+ return [2 /*return*/];
731
+ }
732
+ // If code exists in result, user may using previous auth-start and auth-end page.
733
+ if (resultJson.code) {
734
+ helpLink = "https://aka.ms/teamsfx-auth-code-flow";
735
+ usingPreviousAuthPage = "Found auth code in response. You may be using the latest TeamsFx SDK on an old project." +
736
+ ("Please refer to the help link for how to fix the issue: " + helpLink + ".");
737
+ reject(new ErrorWithCode(usingPreviousAuthPage, ErrorCode.ProjectNeedUpgrade));
738
+ }
739
+ // If sessionStorage exists in result, set the values in current session storage.
740
+ if (resultJson.sessionStorage) {
741
+ this.setSessionStorage(resultJson.sessionStorage);
742
+ }
743
+ resolve();
744
+ return [2 /*return*/];
745
+ });
746
+ }); },
747
+ failureCallback: function (reason) {
748
+ var errorMsg = "Consent failed for the scope " + scopesStr + " with error: " + reason;
749
+ internalLogger.error(errorMsg);
750
+ reject(new ErrorWithCode(errorMsg, ErrorCode.ConsentFailed));
751
+ },
752
+ });
714
753
  });
715
- });
716
- })];
754
+ })];
755
+ }
717
756
  });
718
757
  });
719
758
  };
720
759
  /**
721
760
  * Get access token from credential.
722
761
  *
762
+ * Important: Access tokens are stored in sessionStorage, read more here: https://aka.ms/teamsfx-session-storage-notice
763
+ *
723
764
  * @example
724
765
  * ```typescript
725
766
  * await credential.getToken([]) // Get SSO token using empty string array
@@ -739,7 +780,6 @@ var TeamsUserCredential = /** @class */ (function () {
739
780
  *
740
781
  * @throws {@link ErrorCode|InternalError} when failed to get access token with unknown error.
741
782
  * @throws {@link ErrorCode|UiRequiredError} when need user consent to get access token.
742
- * @throws {@link ErrorCode|ServiceError} when failed to get access token from simple auth server.
743
783
  * @throws {@link ErrorCode|InvalidParameter} when scopes is not a valid string or string array.
744
784
  * @throws {@link ErrorCode|RuntimeNotSupported} when runtime is nodeJS.
745
785
  *
@@ -752,7 +792,7 @@ var TeamsUserCredential = /** @class */ (function () {
752
792
  */
753
793
  TeamsUserCredential.prototype.getToken = function (scopes, options) {
754
794
  return __awaiter(this, void 0, void 0, function () {
755
- var ssoToken, scopeStr, cachedKey, cachedToken, accessToken;
795
+ var ssoToken, scopeStr, tokenResponse, scopesArray, domain, account, scopesRequestForAcquireTokenSilent, error_1, acquireTokenSilentFailedMessage, scopesRequestForSsoSilent, error_2, ssoSilentFailedMessage, errorMsg, accessToken;
756
796
  return __generator(this, function (_a) {
757
797
  switch (_a.label) {
758
798
  case 0:
@@ -766,25 +806,59 @@ var TeamsUserCredential = /** @class */ (function () {
766
806
  return [2 /*return*/, ssoToken];
767
807
  case 2:
768
808
  internalLogger.info("Get access token with scopes: " + scopeStr);
769
- return [4 /*yield*/, this.getAccessTokenCacheKey(scopeStr)];
809
+ if (!!this.initialized) return [3 /*break*/, 4];
810
+ return [4 /*yield*/, this.init()];
770
811
  case 3:
771
- cachedKey = _a.sent();
772
- cachedToken = this.getTokenCache(cachedKey);
773
- if (cachedToken) {
774
- if (!this.isAccessTokenNearExpired(cachedToken)) {
775
- internalLogger.verbose("Get access token from cache");
776
- return [2 /*return*/, cachedToken];
777
- }
778
- else {
779
- internalLogger.verbose("Cached access token is expired");
780
- }
781
- }
782
- else {
783
- internalLogger.verbose("No cached access token");
784
- }
785
- return [4 /*yield*/, this.getAndCacheAccessTokenFromSimpleAuthServer(scopeStr)];
812
+ _a.sent();
813
+ _a.label = 4;
786
814
  case 4:
787
- accessToken = _a.sent();
815
+ tokenResponse = void 0;
816
+ scopesArray = typeof scopes === "string" ? scopes.split(" ") : scopes;
817
+ domain = window.location.origin;
818
+ _a.label = 5;
819
+ case 5:
820
+ _a.trys.push([5, 7, , 8]);
821
+ account = this.msalInstance.getAccountByUsername(this.loginHint);
822
+ scopesRequestForAcquireTokenSilent = {
823
+ scopes: scopesArray,
824
+ account: account !== null && account !== void 0 ? account : undefined,
825
+ redirectUri: domain + "/blank-auth-end.html",
826
+ };
827
+ return [4 /*yield*/, this.msalInstance.acquireTokenSilent(scopesRequestForAcquireTokenSilent)];
828
+ case 6:
829
+ tokenResponse = _a.sent();
830
+ return [3 /*break*/, 8];
831
+ case 7:
832
+ error_1 = _a.sent();
833
+ acquireTokenSilentFailedMessage = "Failed to call acquireTokenSilent. Reason: " + (error_1 === null || error_1 === void 0 ? void 0 : error_1.message) + ". ";
834
+ internalLogger.verbose(acquireTokenSilentFailedMessage);
835
+ return [3 /*break*/, 8];
836
+ case 8:
837
+ if (!!tokenResponse) return [3 /*break*/, 12];
838
+ _a.label = 9;
839
+ case 9:
840
+ _a.trys.push([9, 11, , 12]);
841
+ scopesRequestForSsoSilent = {
842
+ scopes: scopesArray,
843
+ loginHint: this.loginHint,
844
+ redirectUri: domain + "/blank-auth-end.html",
845
+ };
846
+ return [4 /*yield*/, this.msalInstance.ssoSilent(scopesRequestForSsoSilent)];
847
+ case 10:
848
+ tokenResponse = _a.sent();
849
+ return [3 /*break*/, 12];
850
+ case 11:
851
+ error_2 = _a.sent();
852
+ ssoSilentFailedMessage = "Failed to call ssoSilent. Reason: " + (error_2 === null || error_2 === void 0 ? void 0 : error_2.message) + ". ";
853
+ internalLogger.verbose(ssoSilentFailedMessage);
854
+ return [3 /*break*/, 12];
855
+ case 12:
856
+ if (!tokenResponse) {
857
+ errorMsg = "Failed to get access token cache silently, please login first: you need login first before get access token.";
858
+ internalLogger.error(errorMsg);
859
+ throw new ErrorWithCode(errorMsg, ErrorCode.UiRequiredError);
860
+ }
861
+ accessToken = parseAccessTokenFromAuthCodeTokenResponse(tokenResponse);
788
862
  return [2 /*return*/, accessToken];
789
863
  }
790
864
  });
@@ -821,91 +895,29 @@ var TeamsUserCredential = /** @class */ (function () {
821
895
  });
822
896
  });
823
897
  };
824
- TeamsUserCredential.prototype.exchangeAccessTokenFromSimpleAuthServer = function (scopesStr, authCodeResult) {
825
- var _a, _b;
898
+ TeamsUserCredential.prototype.init = function () {
826
899
  return __awaiter(this, void 0, void 0, function () {
827
- var axiosInstance, retryCount, response, tokenResult, key, err_2;
828
- return __generator(this, function (_c) {
829
- switch (_c.label) {
830
- case 0: return [4 /*yield*/, this.getAxiosInstance()];
831
- case 1:
832
- axiosInstance = _c.sent();
833
- retryCount = 0;
834
- _c.label = 2;
835
- case 2:
836
- _c.label = 3;
837
- case 3:
838
- _c.trys.push([3, 6, , 9]);
839
- return [4 /*yield*/, axiosInstance.post("/auth/token", {
840
- scope: scopesStr,
841
- code: authCodeResult.code,
842
- code_verifier: authCodeResult.codeVerifier,
843
- redirect_uri: authCodeResult.redirectUri,
844
- grant_type: GrantType.authCode,
845
- })];
846
- case 4:
847
- response = _c.sent();
848
- tokenResult = response.data;
849
- return [4 /*yield*/, this.getAccessTokenCacheKey(scopesStr)];
850
- case 5:
851
- key = _c.sent();
852
- this.setTokenCache(key, {
853
- token: tokenResult.access_token,
854
- expiresOnTimestamp: tokenResult.expires_on,
855
- });
856
- return [2 /*return*/];
857
- case 6:
858
- err_2 = _c.sent();
859
- if (!(((_b = (_a = err_2.response) === null || _a === void 0 ? void 0 : _a.data) === null || _b === void 0 ? void 0 : _b.type) && err_2.response.data.type === "AadUiRequiredException")) return [3 /*break*/, 8];
860
- internalLogger.warn("Exchange access token failed, retry...");
861
- if (!(retryCount < maxRetryCount)) return [3 /*break*/, 8];
862
- return [4 /*yield*/, this.sleep(retryTimeSpanInMillisecond)];
863
- case 7:
864
- _c.sent();
865
- retryCount++;
866
- return [3 /*break*/, 2];
867
- case 8: throw err_2;
868
- case 9: return [3 /*break*/, 2];
869
- case 10: return [2 /*return*/];
870
- }
871
- });
872
- });
873
- };
874
- /**
875
- * Get access token cache from authentication server
876
- * @returns Access token
877
- */
878
- TeamsUserCredential.prototype.getAndCacheAccessTokenFromSimpleAuthServer = function (scopesStr) {
879
- return __awaiter(this, void 0, void 0, function () {
880
- var axiosInstance, response, accessTokenResult, accessToken, cacheKey, err_3;
900
+ var ssoToken, info, msalConfig;
881
901
  return __generator(this, function (_a) {
882
902
  switch (_a.label) {
883
- case 0:
884
- _a.trys.push([0, 4, , 5]);
885
- internalLogger.verbose("Get access token from authentication server with scopes: " + scopesStr);
886
- return [4 /*yield*/, this.getAxiosInstance()];
903
+ case 0: return [4 /*yield*/, this.getSSOToken()];
887
904
  case 1:
888
- axiosInstance = _a.sent();
889
- return [4 /*yield*/, axiosInstance.post("/auth/token", {
890
- scope: scopesStr,
891
- grant_type: GrantType.ssoToken,
892
- })];
893
- case 2:
894
- response = _a.sent();
895
- accessTokenResult = response.data;
896
- accessToken = {
897
- token: accessTokenResult.access_token,
898
- expiresOnTimestamp: accessTokenResult.expires_on,
905
+ ssoToken = _a.sent();
906
+ info = getTenantIdAndLoginHintFromSsoToken(ssoToken.token);
907
+ this.loginHint = info.loginHint;
908
+ this.tid = info.tid;
909
+ msalConfig = {
910
+ auth: {
911
+ clientId: this.config.clientId,
912
+ authority: "https://login.microsoftonline.com/" + this.tid,
913
+ },
914
+ cache: {
915
+ cacheLocation: "sessionStorage",
916
+ },
899
917
  };
900
- return [4 /*yield*/, this.getAccessTokenCacheKey(scopesStr)];
901
- case 3:
902
- cacheKey = _a.sent();
903
- this.setTokenCache(cacheKey, accessToken);
904
- return [2 /*return*/, accessToken];
905
- case 4:
906
- err_3 = _a.sent();
907
- throw this.generateAuthServerError(err_3);
908
- case 5: return [2 /*return*/];
918
+ this.msalInstance = new PublicClientApplication(msalConfig);
919
+ this.initialized = true;
920
+ return [2 /*return*/];
909
921
  }
910
922
  });
911
923
  });
@@ -979,16 +991,13 @@ var TeamsUserCredential = /** @class */ (function () {
979
991
  internalLogger.error(ErrorMessage.AuthenticationConfigurationNotExists);
980
992
  throw new ErrorWithCode(ErrorMessage.AuthenticationConfigurationNotExists, ErrorCode.InvalidConfiguration);
981
993
  }
982
- if (config.initiateLoginEndpoint && config.simpleAuthEndpoint && config.clientId) {
994
+ if (config.initiateLoginEndpoint && config.clientId) {
983
995
  return config;
984
996
  }
985
997
  var missingValues = [];
986
998
  if (!config.initiateLoginEndpoint) {
987
999
  missingValues.push("initiateLoginEndpoint");
988
1000
  }
989
- if (!config.simpleAuthEndpoint) {
990
- missingValues.push("simpleAuthEndpoint");
991
- }
992
1001
  if (!config.clientId) {
993
1002
  missingValues.push("clientId");
994
1003
  }
@@ -996,129 +1005,20 @@ var TeamsUserCredential = /** @class */ (function () {
996
1005
  internalLogger.error(errorMsg);
997
1006
  throw new ErrorWithCode(errorMsg, ErrorCode.InvalidConfiguration);
998
1007
  };
999
- /**
1000
- * Get axios instance with sso token bearer header
1001
- * @returns AxiosInstance
1002
- */
1003
- TeamsUserCredential.prototype.getAxiosInstance = function () {
1004
- return __awaiter(this, void 0, void 0, function () {
1005
- var ssoToken, axiosInstance;
1006
- return __generator(this, function (_a) {
1007
- switch (_a.label) {
1008
- case 0: return [4 /*yield*/, this.getSSOToken()];
1009
- case 1:
1010
- ssoToken = _a.sent();
1011
- axiosInstance = axios.create({
1012
- baseURL: this.config.simpleAuthEndpoint,
1013
- });
1014
- axiosInstance.interceptors.request.use(function (config) {
1015
- config.headers.Authorization = "Bearer " + ssoToken.token;
1016
- return config;
1017
- });
1018
- return [2 /*return*/, axiosInstance];
1019
- }
1020
- });
1021
- });
1022
- };
1023
- /**
1024
- * Set access token to cache
1025
- * @param key
1026
- * @param token
1027
- */
1028
- TeamsUserCredential.prototype.setTokenCache = function (key, token) {
1029
- Cache.set(key, JSON.stringify(token));
1030
- };
1031
- /**
1032
- * Get access token from cache.
1033
- * If there is no cache or cannot be parsed, then it will return null
1034
- * @param key
1035
- * @returns Access token or null
1036
- */
1037
- TeamsUserCredential.prototype.getTokenCache = function (key) {
1038
- var value = Cache.get(key);
1039
- if (value === null) {
1040
- return null;
1041
- }
1042
- var accessToken = this.validateAndParseJson(value);
1043
- return accessToken;
1044
- };
1045
- /**
1046
- * Parses passed value as JSON access token, if value is not a valid json string JSON.parse() will throw an error.
1047
- * @param jsonValue
1048
- */
1049
- TeamsUserCredential.prototype.validateAndParseJson = function (jsonValue) {
1008
+ TeamsUserCredential.prototype.setSessionStorage = function (sessonStorageValues) {
1050
1009
  try {
1051
- var parsedJson = JSON.parse(jsonValue);
1052
- /**
1053
- * There are edge cases in which JSON.parse will successfully parse a non-valid JSON object
1054
- * (e.g. JSON.parse will parse an escaped string into an unescaped string), so adding a type check
1055
- * of the parsed value is necessary in order to be certain that the string represents a valid JSON object.
1056
- *
1057
- */
1058
- return parsedJson && typeof parsedJson === "object" ? parsedJson : null;
1059
- }
1060
- catch (error) {
1061
- return null;
1062
- }
1063
- };
1064
- /**
1065
- * Generate cache key
1066
- * @param scopesStr
1067
- * @returns Access token cache key, a key example: accessToken-userId-clientId-tenantId-scopes
1068
- */
1069
- TeamsUserCredential.prototype.getAccessTokenCacheKey = function (scopesStr) {
1070
- return __awaiter(this, void 0, void 0, function () {
1071
- var ssoToken, ssoTokenObj, clientId, userObjectId, tenantId, key;
1072
- return __generator(this, function (_a) {
1073
- switch (_a.label) {
1074
- case 0: return [4 /*yield*/, this.getSSOToken()];
1075
- case 1:
1076
- ssoToken = _a.sent();
1077
- ssoTokenObj = parseJwt(ssoToken.token);
1078
- clientId = this.config.clientId;
1079
- userObjectId = ssoTokenObj.oid;
1080
- tenantId = ssoTokenObj.tid;
1081
- key = [accessTokenCacheKeyPrefix, userObjectId, clientId, tenantId, scopesStr]
1082
- .join(separator)
1083
- .replace(/" "/g, "_");
1084
- return [2 /*return*/, key];
1085
- }
1010
+ var sessionStorageKeys = Object.keys(sessonStorageValues);
1011
+ sessionStorageKeys.forEach(function (key) {
1012
+ sessionStorage.setItem(key, sessonStorageValues[key]);
1086
1013
  });
1087
- });
1088
- };
1089
- /**
1090
- * Check whether the token is about to expire (within 5 minutes)
1091
- * @returns Boolean value indicate whether the token is about to expire
1092
- */
1093
- TeamsUserCredential.prototype.isAccessTokenNearExpired = function (token) {
1094
- var expireDate = new Date(token.expiresOnTimestamp);
1095
- if (expireDate.getTime() - Date.now() > tokenRefreshTimeSpanInMillisecond) {
1096
- return false;
1097
1014
  }
1098
- return true;
1099
- };
1100
- TeamsUserCredential.prototype.generateAuthServerError = function (err) {
1101
- var _a, _b;
1102
- var errorMessage = err.message;
1103
- if ((_b = (_a = err.response) === null || _a === void 0 ? void 0 : _a.data) === null || _b === void 0 ? void 0 : _b.type) {
1104
- errorMessage = err.response.data.detail;
1105
- if (err.response.data.type === "AadUiRequiredException") {
1106
- var fullErrorMsg_1 = "Failed to get access token from authentication server, please login first: " +
1107
- errorMessage;
1108
- internalLogger.warn(fullErrorMsg_1);
1109
- return new ErrorWithCode(fullErrorMsg_1, ErrorCode.UiRequiredError);
1110
- }
1111
- else {
1112
- var fullErrorMsg_2 = "Failed to get access token from authentication server: " + errorMessage;
1113
- internalLogger.error(fullErrorMsg_2);
1114
- return new ErrorWithCode(fullErrorMsg_2, ErrorCode.ServiceError);
1115
- }
1015
+ catch (error) {
1016
+ // Values in result.sessionStorage can not be set into session storage.
1017
+ // Throw error since this may block user.
1018
+ var errorMessage = "Failed to set values in session storage. Error: " + error.message;
1019
+ internalLogger.error(errorMessage);
1020
+ throw new ErrorWithCode(errorMessage, ErrorCode.InternalError);
1116
1021
  }
1117
- var fullErrorMsg = "Failed to get access token with error: " + errorMessage;
1118
- return new ErrorWithCode(fullErrorMsg, ErrorCode.InternalError);
1119
- };
1120
- TeamsUserCredential.prototype.sleep = function (ms) {
1121
- return new Promise(function (resolve) { return setTimeout(resolve, ms); });
1122
1022
  };
1123
1023
  return TeamsUserCredential;
1124
1024
  }());
@@ -1256,201 +1156,31 @@ function createMicrosoftGraphClient(credential, scopes) {
1256
1156
  return graphClient;
1257
1157
  }
1258
1158
 
1259
- // Copyright (c) Microsoft Corporation.
1260
1159
  /**
1261
- * SQL connection configuration instance.
1160
+ * Generate connection configuration consumed by tedious.
1262
1161
  * @remarks
1263
1162
  * Only works in in server side.
1264
- *
1265
1163
  * @beta
1266
- *
1267
1164
  */
1268
1165
  var DefaultTediousConnectionConfiguration = /** @class */ (function () {
1269
1166
  function DefaultTediousConnectionConfiguration() {
1270
- /**
1271
- * MSSQL default scope
1272
- * https://docs.microsoft.com/en-us/azure/app-service/app-service-web-tutorial-connect-msi
1273
- */
1274
- this.defaultSQLScope = "https://database.windows.net/";
1167
+ throw new ErrorWithCode(formatString(ErrorMessage.BrowserRuntimeNotSupported, "DefaultTediousConnectionConfiguration"), ErrorCode.RuntimeNotSupported);
1275
1168
  }
1276
1169
  /**
1277
1170
  * Generate connection configuration consumed by tedious.
1278
- *
1279
- * @returns Connection configuration of tedious for the SQL.
1280
- *
1281
- * @throws {@link ErrorCode|InvalidConfiguration} when SQL config resource configuration is invalid.
1282
- * @throws {@link ErrorCode|InternalError} when get user MSI token failed or MSI token is invalid.
1283
- * @throws {@link ErrorCode|RuntimeNotSupported} when runtime is browser.
1284
- *
1171
+ * @remarks
1172
+ * Only works in in server side.
1285
1173
  * @beta
1286
1174
  */
1287
- DefaultTediousConnectionConfiguration.prototype.getConfig = function () {
1288
- return __awaiter(this, void 0, void 0, function () {
1289
- var configuration, errMsg, configWithUPS, configWithToken, error_1;
1290
- return __generator(this, function (_a) {
1291
- switch (_a.label) {
1292
- case 0:
1293
- internalLogger.info("Get SQL configuration");
1294
- configuration = getResourceConfiguration(ResourceType.SQL);
1295
- if (!configuration) {
1296
- errMsg = "SQL resource configuration not exist";
1297
- internalLogger.error(errMsg);
1298
- throw new ErrorWithCode(errMsg, ErrorCode.InvalidConfiguration);
1299
- }
1300
- try {
1301
- this.isSQLConfigurationValid(configuration);
1302
- }
1303
- catch (err) {
1304
- throw err;
1305
- }
1306
- if (!this.isMsiAuthentication()) {
1307
- configWithUPS = this.generateDefaultConfig(configuration);
1308
- internalLogger.verbose("SQL configuration with username and password generated");
1309
- return [2 /*return*/, configWithUPS];
1310
- }
1311
- _a.label = 1;
1312
- case 1:
1313
- _a.trys.push([1, 3, , 4]);
1314
- return [4 /*yield*/, this.generateTokenConfig(configuration)];
1315
- case 2:
1316
- configWithToken = _a.sent();
1317
- internalLogger.verbose("SQL configuration with MSI token generated");
1318
- return [2 /*return*/, configWithToken];
1319
- case 3:
1320
- error_1 = _a.sent();
1321
- throw error_1;
1322
- case 4: return [2 /*return*/];
1323
- }
1324
- });
1325
- });
1326
- };
1327
- /**
1328
- * Check SQL use MSI identity or username and password.
1329
- *
1330
- * @returns false - login with SQL MSI identity, true - login with username and password.
1331
- * @internal
1332
- */
1333
- DefaultTediousConnectionConfiguration.prototype.isMsiAuthentication = function () {
1334
- internalLogger.verbose("Check connection config using MSI access token or username and password");
1335
- var configuration = getResourceConfiguration(ResourceType.SQL);
1336
- if ((configuration === null || configuration === void 0 ? void 0 : configuration.sqlUsername) != null && (configuration === null || configuration === void 0 ? void 0 : configuration.sqlPassword) != null) {
1337
- internalLogger.verbose("Login with username and password");
1338
- return false;
1339
- }
1340
- internalLogger.verbose("Login with MSI identity");
1341
- return true;
1342
- };
1343
- /**
1344
- * check configuration is an available configurations.
1345
- * @param { SqlConfiguration } sqlConfig
1346
- *
1347
- * @returns true - SQL configuration has a valid SQL endpoints, SQL username with password or identity ID.
1348
- * false - configuration is not valid.
1349
- * @internal
1350
- */
1351
- DefaultTediousConnectionConfiguration.prototype.isSQLConfigurationValid = function (sqlConfig) {
1352
- internalLogger.verbose("Check SQL configuration if valid");
1353
- if (!sqlConfig.sqlServerEndpoint) {
1354
- internalLogger.error("SQL configuration is not valid without SQL server endpoint exist");
1355
- throw new ErrorWithCode("SQL configuration error without SQL server endpoint exist", ErrorCode.InvalidConfiguration);
1356
- }
1357
- if (!(sqlConfig.sqlUsername && sqlConfig.sqlPassword) && !sqlConfig.sqlIdentityId) {
1358
- var errMsg = "SQL configuration is not valid without " + (sqlConfig.sqlIdentityId ? "" : "identity id ") + " " + (sqlConfig.sqlUsername ? "" : "SQL username ") + " " + (sqlConfig.sqlPassword ? "" : "SQL password") + " exist";
1359
- internalLogger.error(errMsg);
1360
- throw new ErrorWithCode(errMsg, ErrorCode.InvalidConfiguration);
1361
- }
1362
- internalLogger.verbose("SQL configuration is valid");
1363
- };
1364
- /**
1365
- * Generate tedious connection configuration with default authentication type.
1366
- *
1367
- * @param { SqlConfiguration } SQL configuration with username and password.
1368
- *
1369
- * @returns Tedious connection configuration with username and password.
1370
- * @internal
1371
- */
1372
- DefaultTediousConnectionConfiguration.prototype.generateDefaultConfig = function (sqlConfig) {
1373
- internalLogger.verbose("SQL server " + sqlConfig.sqlServerEndpoint + ", user name " + sqlConfig.sqlUsername + ", database name " + sqlConfig.sqlDatabaseName);
1374
- var config = {
1375
- server: sqlConfig.sqlServerEndpoint,
1376
- authentication: {
1377
- type: TediousAuthenticationType.default,
1378
- options: {
1379
- userName: sqlConfig.sqlUsername,
1380
- password: sqlConfig.sqlPassword,
1381
- },
1382
- },
1383
- options: {
1384
- database: sqlConfig.sqlDatabaseName,
1385
- encrypt: true,
1386
- },
1387
- };
1388
- return config;
1389
- };
1390
- /**
1391
- * Generate tedious connection configuration with azure-active-directory-access-token authentication type.
1392
- *
1393
- * @param { SqlConfiguration } SQL configuration with AAD access token.
1394
- *
1395
- * @returns Tedious connection configuration with access token.
1396
- * @internal
1397
- */
1398
- DefaultTediousConnectionConfiguration.prototype.generateTokenConfig = function (sqlConfig) {
1175
+ DefaultTediousConnectionConfiguration.prototype.getConfig = function (databaseName) {
1399
1176
  return __awaiter(this, void 0, void 0, function () {
1400
- var token, credential, errMsg, config;
1401
1177
  return __generator(this, function (_a) {
1402
- switch (_a.label) {
1403
- case 0:
1404
- internalLogger.verbose("Generate tedious config with MSI token");
1405
- _a.label = 1;
1406
- case 1:
1407
- _a.trys.push([1, 3, , 4]);
1408
- credential = new ManagedIdentityCredential(sqlConfig.sqlIdentityId);
1409
- return [4 /*yield*/, credential.getToken(this.defaultSQLScope)];
1410
- case 2:
1411
- token = _a.sent();
1412
- return [3 /*break*/, 4];
1413
- case 3:
1414
- _a.sent();
1415
- errMsg = "Get user MSI token failed";
1416
- internalLogger.error(errMsg);
1417
- throw new ErrorWithCode(errMsg, ErrorCode.InternalError);
1418
- case 4:
1419
- if (token) {
1420
- config = {
1421
- server: sqlConfig.sqlServerEndpoint,
1422
- authentication: {
1423
- type: TediousAuthenticationType.MSI,
1424
- options: {
1425
- token: token.token,
1426
- },
1427
- },
1428
- options: {
1429
- database: sqlConfig.sqlDatabaseName,
1430
- encrypt: true,
1431
- },
1432
- };
1433
- internalLogger.verbose("Generate token configuration success, server endpoint is " + sqlConfig.sqlServerEndpoint + ", database name is " + sqlConfig.sqlDatabaseName);
1434
- return [2 /*return*/, config];
1435
- }
1436
- internalLogger.error("Generate token configuration, server endpoint is " + sqlConfig.sqlServerEndpoint + ", MSI token is not valid");
1437
- throw new ErrorWithCode("MSI token is not valid", ErrorCode.InternalError);
1438
- }
1178
+ throw new ErrorWithCode(formatString(ErrorMessage.BrowserRuntimeNotSupported, "DefaultTediousConnectionConfiguration"), ErrorCode.RuntimeNotSupported);
1439
1179
  });
1440
1180
  });
1441
1181
  };
1442
1182
  return DefaultTediousConnectionConfiguration;
1443
- }());
1444
- /**
1445
- * tedious connection config authentication type.
1446
- * https://tediousjs.github.io/tedious/api-connection.html
1447
- * @internal
1448
- */
1449
- var TediousAuthenticationType;
1450
- (function (TediousAuthenticationType) {
1451
- TediousAuthenticationType["default"] = "default";
1452
- TediousAuthenticationType["MSI"] = "azure-active-directory-access-token";
1453
- })(TediousAuthenticationType || (TediousAuthenticationType = {}));
1183
+ }());
1454
1184
 
1455
1185
  // Copyright (c) Microsoft Corporation.
1456
1186
  /**