Mengedit profil di aplikasi web Node.js
Berlaku untuk: Penyewa Tenaga Kerja Penyewa eksternal (pelajari lebih lanjut)
Artikel ini adalah bagian 2 dari seri yang menunjukkan cara menambahkan logika pengeditan profil di aplikasi web Node.js. Di bagian 1 seri ini, Anda menyiapkan aplikasi untuk pengeditan profil.
Dalam panduan cara ini, Anda mempelajari cara memanggil Microsoft Graph API untuk pengeditan profil.
Prasyarat
- Selesaikan langkah-langkah di bagian kedua dari seri panduan ini, Siapkan aplikasi web Node.js untuk pengeditan profil.
Menyelesaikan aplikasi web klien
Di bagian ini, Anda menambahkan kode terkait identitas untuk aplikasi web klien.
Memperbarui file authConfig.js
Perbarui file authConfig.js untuk aplikasi web klien:
Di editor kode Anda, buka file App/authConfig.js , lalu tambahkan tiga variabel baru,
GRAPH_API_ENDPOINT
,GRAPH_ME_ENDPOINT
daneditProfileScope
. Pastikan untuk mengekspor tiga variabel://... const GRAPH_API_ENDPOINT = process.env.GRAPH_API_ENDPOINT || "https://graph.microsoft.com/"; // https://learn.microsoft.com/graph/api/user-update?tabs=http const GRAPH_ME_ENDPOINT = GRAPH_API_ENDPOINT + "v1.0/me"; const editProfileScope = process.env.EDIT_PROFILE_FOR_CLIENT_WEB_APP || 'api://{clientId}/EditProfileService.ReadWrite'; module.exports = { //... editProfileScope, GRAPH_API_ENDPOINT, GRAPH_ME_ENDPOINT, //... };
Variabel
editProfileScope
mewakili sumber daya yang dilindungi MFA, yaitu aplikasi tingkat menengah (aplikasi EditProfileService).GRAPH_ME_ENDPOINT
adalah titik akhir Microsoft Graph API.
Ganti tempat penampung
{clientId}
dengan ID Aplikasi (klien) dari aplikasi tingkat menengah (aplikasi EditProfileService) yang Anda daftarkan sebelumnya.
Memperoleh token akses di aplikasi web klien
Di editor kode Anda, buka file App/auth/AuthProvider.js , lalu perbarui getToken
metode di AuthProvider
kelas :
class AuthProvider {
//...
getToken(scopes, redirectUri = "http://localhost:3000/") {
return async function (req, res, next) {
const msalInstance = authProvider.getMsalInstance(authProvider.config.msalConfig);
try {
msalInstance.getTokenCache().deserialize(req.session.tokenCache);
const silentRequest = {
account: req.session.account,
scopes: scopes,
};
const tokenResponse = await msalInstance.acquireTokenSilent(silentRequest);
req.session.tokenCache = msalInstance.getTokenCache().serialize();
req.session.accessToken = tokenResponse.accessToken;
next();
} catch (error) {
if (error instanceof msal.InteractionRequiredAuthError) {
req.session.csrfToken = authProvider.cryptoProvider.createNewGuid();
const state = authProvider.cryptoProvider.base64Encode(
JSON.stringify({
redirectTo: redirectUri,
csrfToken: req.session.csrfToken,
})
);
const authCodeUrlRequestParams = {
state: state,
scopes: scopes,
};
const authCodeRequestParams = {
state: state,
scopes: scopes,
};
authProvider.redirectToAuthCodeUrl(
req,
res,
next,
authCodeUrlRequestParams,
authCodeRequestParams,
msalInstance
);
}
next(error);
}
};
}
}
//...
Metode ini getToken
menggunakan cakupan yang ditentukan untuk memperoleh token akses. Parameter redirectUri
adalah URL pengalihan setelah aplikasi memperoleh token akses.
Memperbarui file users.js
Di editor kode Anda, buka file App/routes/users.js , lalu tambahkan rute berikut:
//...
var { fetch } = require("../fetch");
const { GRAPH_ME_ENDPOINT, editProfileScope } = require('../authConfig');
//...
router.get(
"/gatedUpdateProfile",
isAuthenticated,
authProvider.getToken(["User.Read"]), // check if user is authenticated
async function (req, res, next) {
const graphResponse = await fetch(
GRAPH_ME_ENDPOINT,
req.session.accessToken,
);
if (!graphResponse.id) {
return res
.status(501)
.send("Failed to fetch profile data");
}
res.render("gatedUpdateProfile", {
profile: graphResponse,
});
},
);
router.get(
"/updateProfile",
isAuthenticated, // check if user is authenticated
authProvider.getToken(
["User.Read", editProfileScope],
"http://localhost:3000/users/updateProfile",
),
async function (req, res, next) {
const graphResponse = await fetch(
GRAPH_ME_ENDPOINT,
req.session.accessToken,
);
if (!graphResponse.id) {
return res
.status(501)
.send("Failed to fetch profile data");
}
res.render("updateProfile", {
profile: graphResponse,
});
},
);
router.post(
"/update",
isAuthenticated,
authProvider.getToken([editProfileScope]),
async function (req, res, next) {
try {
if (!!req.body) {
let body = req.body;
fetch(
"http://localhost:3001/updateUserInfo",
req.session.accessToken,
"POST",
{
displayName: body.displayName,
givenName: body.givenName,
surname: body.surname,
},
)
.then((response) => {
if (response.status === 204) {
return res.redirect("/");
} else {
next("Not updated");
}
})
.catch((error) => {
console.log("error,", error);
});
} else {
throw { error: "empty request" };
}
} catch (error) {
next(error);
}
},
);
//...
Anda memicu
/gatedUpdateProfile
rute saat pengguna pelanggan memilih tautan Pengeditan profil. Aplikasi:- Memperoleh token akses dengan izin User.Read .
- Lakukan panggilan ke Microsoft Graph API untuk membaca profil pengguna yang masuk.
- Menampilkan detail pengguna di UI gatedUpdateProfile.hbs .
Anda memicu
/updateProfile
rute saat pengguna ingin memperbarui nama tampilan mereka, yaitu, mereka memilih tombol Edit profil . Aplikasi:- Melakukan panggilan ke aplikasi tingkat menengah (aplikasi EditProfileService) menggunakan cakupan editProfileScope . Dengan melakukan panggilan ke aplikasi tingkat menengah (aplikasi EditProfileService), pengguna harus menyelesaikan tantangan MFA jika mereka belum melakukannya.
- Menampilkan detail pengguna di antarmuka pengguna updateProfile.hbs .
Anda memicu
/update
rute saat pengguna memilih tombol Simpan di gatedUpdateProfile.hbs atau updateProfile.hbs. Aplikasi:- Mengambil token akses untuk sesi aplikasi. Anda mempelajari bagaimana aplikasi tingkat menengah (aplikasi EditProfileService) memperoleh token akses di bagian berikutnya.
- Mengumpulkan semua detail pengguna.
- Lakukan panggilan ke Microsoft Graph API untuk memperbarui profil pengguna.
Memperbarui file fetch.js
Aplikasi ini menggunakan file App/fetch.js untuk melakukan panggilan API aktual.
Di editor kode Anda, buka file App/fetch.js , lalu tambahkan opsi operasi PATCH. Setelah Anda memperbarui file, file yang dihasilkan akan terlihat mirip dengan kode berikut:
var axios = require('axios');
var authProvider = require("./auth/AuthProvider");
/**
* Makes an Authorization "Bearer" request with the given accessToken to the given endpoint.
* @param endpoint
* @param accessToken
* @param method
*/
const fetch = async (endpoint, accessToken, method = "GET", data = null) => {
const options = {
headers: {
Authorization: `Bearer ${accessToken}`,
},
};
console.log(`request made to ${endpoint} at: ` + new Date().toString());
switch (method) {
case 'GET':
const response = await axios.get(endpoint, options);
return await response.data;
case 'POST':
return await axios.post(endpoint, data, options);
case 'DELETE':
return await axios.delete(endpoint + `/${data}`, options);
case 'PATCH':
return await axios.patch(endpoint, ReqBody = data, options);
default:
return null;
}
};
module.exports = { fetch };
Menyelesaikan aplikasi tingkat menengah
Di bagian ini, Anda menambahkan kode terkait identitas untuk aplikasi tingkat menengah (aplikasi EditProfileService).
Di editor kode Anda, buka file Api/authConfig.js , lalu tambahkan kode berikut:
require("dotenv").config({ path: ".env.dev" }); const TENANT_SUBDOMAIN = process.env.TENANT_SUBDOMAIN || "Enter_the_Tenant_Subdomain_Here"; const TENANT_ID = process.env.TENANT_ID || "Enter_the_Tenant_ID_Here"; const REDIRECT_URI = process.env.REDIRECT_URI || "http://localhost:3000/auth/redirect"; const POST_LOGOUT_REDIRECT_URI = process.env.POST_LOGOUT_REDIRECT_URI || "http://localhost:3000"; /** * Configuration object to be passed to MSAL instance on creation. * For a full list of MSAL Node configuration parameters, visit: * https://github.com/AzureAD/microsoft-authentication-library-for-js/blob/dev/lib/msal-node/docs/configuration.md */ const msalConfig = { auth: { clientId: process.env.CLIENT_ID || "Enter_the_Edit_Profile_Service_Application_Id_Here", // 'Application (client) ID' of the Edit_Profile Service App registration in Microsoft Entra admin center - this value is a GUID authority: process.env.AUTHORITY || `https://${TENANT_SUBDOMAIN}.ciamlogin.com/`, // Replace the placeholder with your external tenant name }, system: { loggerOptions: { loggerCallback(loglevel, message, containsPii) { console.log(message); }, piiLoggingEnabled: false, logLevel: "Info", }, }, }; const GRAPH_API_ENDPOINT = process.env.GRAPH_API_ENDPOINT || "graph_end_point"; // Refers to the user that is single user singed in. // https://learn.microsoft.com/en-us/graph/api/user-update?tabs=http const GRAPH_ME_ENDPOINT = GRAPH_API_ENDPOINT + "v1.0/me"; module.exports = { msalConfig, REDIRECT_URI, POST_LOGOUT_REDIRECT_URI, TENANT_SUBDOMAIN, GRAPH_API_ENDPOINT, GRAPH_ME_ENDPOINT, TENANT_ID, };
Temukan tempat penampung:
Enter_the_Tenant_Subdomain_Here
dan ganti dengan subdomain Direktori (penyewa). Misalnya, jika domain utama penyewa Anda adalahcontoso.onmicrosoft.com
, gunakancontoso
. Jika Anda tidak memiliki nama penyewa, pelajari cara membaca detail penyewa Anda.Enter_the_Tenant_ID_Here
dan ganti dengan ID Penyewa. Jika Anda tidak memiliki ID Penyewa, pelajari cara membaca detail penyewa Anda.Enter_the_Edit_Profile_Service_Application_Id_Here
dan menggantinya dengan adalah nilai ID Aplikasi (klien) dari EditProfileService yang Anda daftarkan sebelumnya.Enter_the_Client_Secret_Here
dan ganti dengan nilai rahasia aplikasi EditProfileService yang Anda salin sebelumnya.graph_end_point
dan ganti dengan titik akhir Microsoft Graph API, yaituhttps://graph.microsoft.com/
.
Di editor kode Anda, buka file Api/fetch.js , lalu tempelkan kode dari file Api/fetch.js . Fungsi ini
fetch
menggunakan token akses dan titik akhir sumber daya untuk melakukan panggilan API aktual.Di editor kode Anda, buka file Api/index.js , lalu tempelkan kode dari file Api/index.js .
Memperoleh token akses dengan menggunakan acquireTokenOnBehalfOf
Dalam file Api/index.js, aplikasi tingkat menengah (aplikasi EditProfileService) memperoleh token akses menggunakan fungsi acquireTokenOnBehalfOf, yang digunakannya untuk memperbarui profil atas nama pengguna tersebut.
async function getAccessToken(tokenRequest) {
try {
const response = await cca.acquireTokenOnBehalfOf(tokenRequest);
return response.accessToken;
} catch (error) {
console.error("Error acquiring token:", error);
throw error;
}
}
Parameter tokenRequest
didefinisikan seperti yang ditunjukkan kode berikut:
const tokenRequest = {
oboAssertion: req.headers.authorization.replace("Bearer ", ""),
authority: `https://${TENANT_SUBDOMAIN}.ciamlogin.com/${TENANT_ID}`,
scopes: ["User.ReadWrite"],
correlationId: `${uuidv4()}`,
};
Dalam file yang sama, API/index.js, aplikasi tingkat menengah (aplikasi EditProfileService) melakukan panggilan ke Microsoft Graph API untuk memperbarui profil pengguna:
let accessToken = await getAccessToken(tokenRequest);
fetch(GRAPH_ME_ENDPOINT, accessToken, "PATCH", req.body)
.then((response) => {
if (response.status === 204) {
res.status(response.status);
res.json({ message: "Success" });
} else {
res.status(502);
res.json({ message: "Failed, " + response.body });
}
})
.catch((error) => {
res.status(502);
res.json({ message: "Failed, " + error });
});
Menguji aplikasi Anda
Untuk menguji aplikasi Anda, gunakan langkah-langkah berikut:
Untuk menjalankan aplikasi klien, bentuk jendela terminal, navigasikan ke direktori Aplikasi , lalu jalankan perintah berikut:
npm start
Untuk menjalankan aplikasi klien, bentuk jendela terminal, navigasikan ke direktori API , lalu jalankan perintah berikut:
npm start
Buka browser Anda, lalu buka http://localhost:3000. Jika Anda mengalami kesalahan sertifikat SSL, buat
.env
file, lalu tambahkan konfigurasi berikut:# Use this variable only in the development environment. # Remove the variable when you move the app to the production environment. NODE_TLS_REJECT_UNAUTHORIZED='0'
Pilih tombol Masuk , lalu Anda masuk.
Pada halaman masuk, ketik alamat Email Anda, pilih Berikutnya, ketik Kata Sandi Anda, lalu pilih Masuk. Jika Anda tidak memiliki akun, pilih Tidak ada akun? Buat satu tautan, yang memulai alur pendaftaran.
Untuk memperbarui profil, pilih tautan Pengeditan profil. Anda melihat halaman yang mirip dengan cuplikan layar berikut:
Untuk mengedit profil, pilih tombol Edit Profil . Jika Anda belum melakukannya, aplikasi akan meminta Anda untuk menyelesaikan tantangan MFA.
Buat perubahan pada salah satu detail profil, lalu pilih tombol Simpan .
Konten terkait
- Pelajari selengkapnya tentang platform identitas Microsoft dan alur Atas Nama OAuth 2.0.