diff --git a/keyserver/src/push/providers.js b/keyserver/src/push/providers.js --- a/keyserver/src/push/providers.js +++ b/keyserver/src/push/providers.js @@ -5,6 +5,7 @@ import fcmAdmin from 'firebase-admin'; import type { FirebaseApp } from 'firebase-admin'; import invariant from 'invariant'; +import fetch from 'node-fetch'; import webpush from 'web-push'; import type { PlatformDetails } from 'lib/types/device-types'; @@ -121,6 +122,57 @@ await getWebPushConfig(); } +type WNSConfig = { +tenantID: string, +appID: string, +secret: string }; +type WNSAccessToken = { +token: string, +expires: number }; +let wnsAccessToken: ?WNSAccessToken = null; +async function getWNSToken(): Promise { + const expiryWindowInMs = 10_000; + if ( + wnsAccessToken && + wnsAccessToken.expires >= Date.now() - expiryWindowInMs + ) { + return wnsAccessToken.token; + } + + const config = await getCommConfig({ + folder: 'secrets', + name: 'wns_config', + }); + + if (!config) { + return null; + } + + const params = new URLSearchParams(); + params.append('grant_type', 'client_credentials'); + params.append('client_id', config.appID); + params.append('client_secret', config.secret); + params.append('scope', 'https://wns.windows.com/.default'); + + try { + const response = await fetch( + `https://login.microsoftonline.com/${config.tenantID}/oauth2/v2.0/token`, + { method: 'POST', body: params }, + ); + + if (!response.ok) { + console.error('Failure when getting the WNS token: ', response); + return null; + } + + const responseJson = await response.json(); + wnsAccessToken = { + token: responseJson['access_token'], + expires: Date.now() + responseJson['expires_in'] * 1000, + }; + } catch (err) { + console.error('Failure when getting the WNS token: ', err); + return null; + } + + return wnsAccessToken?.token; +} + export { getAPNPushProfileForCodeVersion, getFCMPushProfileForCodeVersion, @@ -131,4 +183,5 @@ getAPNsNotificationTopic, getWebPushConfig, ensureWebPushInitialized, + getWNSToken, };