Авторизация с помощью MSAL для функции в статическом веб-приложении Azure
Я пытаюсь аутентифицировать и авторизовать пользователя для функции Azure, созданной и предоставленной с помощью статического веб-приложения Azure, с использованием Azure AD и MSAL. Пользователь сможет успешно получить доступ к API, если я настрою приложение для использования более старого потока AAD v1, но не с MSAL. Вариант установки / использования:
- одностраничное приложение (SPA), развернутое и размещенное как статическое веб-приложение Azure с использованием базового HTML и JS (это демонстрационное приложение Hello World)
- В приложение встроена аутентификация с использованием MSAL. В частности, msal-browser.js версии 2.6.1. Идентификационный токен извлекается с помощью:
msal.PublicClientApplication(msalConfig).loginPopup(loginRequest)
где msalConfig содержит:
```
auth: {
clientId: "<CLIENTID>",
authority: "https://login.microsoftonline.com/<TENANT_ID>"
}
```
Пользователь аутентифицирован и возвращается токен идентификации.
Статическое веб-приложение предоставляет пример функции GetMessage, которая возвращает фиктивный текст.
Если путь к функции не защищен, SPA может успешно вызвать функцию, и текст будет возвращен в браузер /SPA.
Если путь к функции защищен через routes.json, запрос функции (правильно) возвращает 401, если пользователь не аутентифицирован и не авторизован.
{ "routes": [ { "route": "/api/*", "allowedRoles": ["Authenticated"] } ] }
Чтобы аутентифицировать пользователя через MSAL, я пытаюсь получить токен доступа, который я помещаю в заголовок Bearer вызова функции:
```
async function getAPI() {
const currentAcc = myMSALObj.getAccountByHomeId(accountId);
if (currentAcc) {
const response = await getTokenPopup(silentRequest, currentAcc).catch(error => {
console.log(error);
});
console.log("Got token " + response.accessToken)
const accToke = response.accessToken
const headers = new Headers();
const bearer = `Bearer ${accToke}`;
headers.append("Authorization", bearer);
const options = {
method: "GET",
headers: headers
};
let { text } = await( await fetch('/api/GetMessage',options)).json();
document.querySelector('#name').textContent = text;
}
}
```
Токен извлекается и проверяется в jwt.ms, но функция всегда возвращает 403 - запрещено. Кажется, нет никакой разницы, если меняются области действия или роли пользователей, хотя, возможно, есть волшебная комбинация, которую мне не хватает.
Этот процесс работает отлично, если функция, которую я вызываю, - это Micrsoft Graph, то есть https://graph.microsoft.com/v1.0/me - она не работает только с нашей собственной функцией статических веб-приложений. Я не вижу способа получить доступ к журналам на стороне сервера Azure, чтобы понять, почему он может давать сбой.
Использование потока AAD v1, т.е. вызов http://APP_URL/.auth/login/aad, работает отлично, но не использует токен доступа. Он использует файл cookie под названием StaticWebAppsAuthCookie (для аутентификации и авторизации пользователя достаточно одного вызова APP_URL/.auth / login / aad). Пример этого можно найти здесь
Я понял, что MSAL - это поток, к которому движется Azure AD, поэтому есть ли способ авторизовать пользователя через поток MSAL? Официально с использованием Azure AD, статического веб-приложения и функции, представленной в статическом веб-приложении (а не как отдельное приложение-функция Azure).
1 ответ
Я полагаю, что при вызове API-интерфейса функций Azure, содержащегося в вашем статическом веб-приложении, служба вставляет в заголовок собственный токен аутентификации. Если вы полагаетесь на заголовок Authorization Bearer для передачи вашего токена из приложения в API, он может быть перезаписан.
В моем случае я отправлял токен:
{
"typ": "JWT",
"alg": "RS256",
"kid": "{key value}"
}
{
"iss": "https://{domain}.b2clogin.com/{tenant ID}/v2.0/",
"aud": "{client ID}",
...
}
но мой API функций Azure получал токен:
{
"typ": "JWT",
"alg": "HS256",
}
{
"iss": "https://{ID}.scm.azurewebsites.net",
"aud": "https://{ID}.azurewebsites.net/azurefunctions",
...
}
Эта проблема отслеживается здесь: https://github.com/Azure/static-web-apps/issues/34.