@microsoft/windows-admin-center-sdk
Version:
Microsoft - Windows Admin Center Shell
138 lines (136 loc) • 4.5 kB
JavaScript
/* eslint-disable unused-imports/no-unused-vars */
import { Subject } from 'rxjs';
import { filter, map, timeout } from 'rxjs/operators';
import { headerConstants } from '../data/http-constants';
import { Net } from '../data/net';
/**
* Manage Signed HTTP Request token (Proof of possession token) handling.
*/
export class SignOnManager {
/**
* Wait for one minute to respond by the portal.
*/
portalMaxWaitTimeout = 60 * 1000;
/**
* The PoP Authorization Token.
*/
signedHttpRequestToken;
/**
* The sign on token awaiter subject.
*/
signOnTokenAwaiter;
/**
* The sign on token requester subject.
*/
signOnTokenRefresh;
/**
* The refresh request to the authorization manager.
*/
refreshCall;
/**
* Initializes a new instance of the SignOnManager class.
*/
constructor(refreshCall) {
this.refreshCall = refreshCall;
if (MsftSme.isShell()) {
this.signOnTokenAwaiter = new Subject();
this.signOnTokenRefresh = new Subject();
}
}
/**
* Gets a valude indicating whethere sign on token is active and configured.
*/
get isSignOnTokenEnabled() {
return !!this.signedHttpRequestToken;
}
/**
* Gets the sign on token request observable by Shell.
*/
get signOnTokenRefreshTarget() {
if (this.signOnTokenRefresh == null) {
throw new Error('Request object is only for Shell.');
}
return this.signOnTokenRefresh.asObservable();
}
/**
* Apply signed http request token.
*/
applySignedHttpRequestToken(token) {
if (token) {
const time = Date.now();
this.signedHttpRequestToken = token;
this.signOnTokenAwaiter.next({ time, token });
}
}
/**
* Request sign on token to refresh.
* @returns success void.
*/
requestSignOnRefresh() {
const now = Date.now();
const awaiter = this.signOnTokenAwaiter
.pipe(filter(token => token.time > now), timeout(this.portalMaxWaitTimeout));
this.signOnTokenRefresh.next({ time: now });
return awaiter;
}
/**
* Check if it can handle unauthorized login case.
* @param code the error code.
* @param error the ajax error response.
* @returns true if it can handle.
*/
canHandleUnauthorizedLogin(code, error) {
// unauthorized login was observed.
return Net.isUnauthorizedLogin(error);
}
/**
* Handles the unauthorized login case.
* @param code the error code.
* @param request the ajax request.
* @param error the ajex error reponse.
* @returns success if it could handled.
*/
// eslint-disable-next-line @typescript-eslint/no-unused-vars
handleUnauthorizedLogin(code, request, error) {
// request new Sign On token to the parent frame which is Azure Compute VM UI.
return this.refreshCall()
.pipe(map(() => {
// update with newly aquired PoP jwt token.
this.SetAadAuthorizationHeader(request.headers);
return request;
}));
}
/**
* Check if it can handle unauthorized login case.
* @param response the response of CIM stream query.
*/
canHandleStreamUnauthorizedLogin(response) {
// access denied case.
const responseObject = response && response.response;
if (!responseObject) {
return false;
}
return responseObject.statusCode === 401 /* HttpStatusCode.Unauthorized */ && responseObject.forbidden && responseObject.forbidden === 'UnauthorizedLogin';
}
/**
* Handle returns true for an ajax error, this method can be called to handle that error.
*/
handleStreamUnauthorizedLogin(options, response) {
let message = response.response.error && response.response.error.message;
if (!message) {
const errors = response.response.errors;
if (errors && errors.length > 0) {
message = errors[0].message;
}
}
return this.refreshCall().pipe(map(() => options));
}
/**
* Set AAD authorization header.
* @param headers the headers.
*/
SetAadAuthorizationHeader(headers) {
headers[headerConstants.SME_AAD_AUTHORIZATION] = `WAC;PAS ${this.signedHttpRequestToken.jwt}`;
}
}
//# sourceMappingURL=sign-on-manager.js.map