הגדרת Azure AD ואימות Microsoft Graph
Aspose.Email for Java מציע אינטגרציה מלאה עם Microsoft Graph, מאפשר למפתחים לנהל הודעות, אנשי קשר, לוחות שנה ומשימות מחשבונות Microsoft 365. מדריך זה יוביל אותך בתהליך יצירת אפליקציית Azure AD והגדרת אימות כדי להתחיל לתכנת עם Aspose.Email GraphClient.
לפני השימוש בממשקי ה-API של Microsoft Graph עם Aspose.Email, עליך לרשום אפליקציה ב-Azure Active Directory (Azure AD) ולהגדיר אימות. דף זה מכסה:
-
יצירת אפליקציית Azure AD (פרויקט).
-
הקצאת הרשאות Microsoft Graph הנדרשות.
-
יצירת פרטי זיהוי (client ID, client secret, tenant ID).
-
אימות ב-Java באמצעות ספקי אסימונים של Aspose.Email.
לאחר השלמת התהליך, תהיה מוכן לתקשר עם Microsoft Graph מתוך אפליקציית Java שלך.
1. יצירת אפליקציית Azure AD
עקוב אחרי הצעדים הבאים כדי לרשום את האפליקציה שלך בפורטל Azure:
- היכנס אל פורטל Azure.
- נווט אל Azure Active Directory → App Registrations → New Registration.

- הזן Name עבור האפליקציה שלך (למשל, AsposeEmailGraphApp).
- בחר סוגי חשבונות נתמכים:
- שוכר יחיד (אם רק הארגון שלך ישתמש בו)
- רב‑שוכרת (אם מספר ארגונים צריכים גישה)
- אופציונלי, הגדר Redirect URI (נדרש לאימות אינטראקטיבי או אינטרנטי).
- לחץ על Register.

2. יצירת סוד לקוח
- לאחר הרישום, עבור אל Certificates & Secrets → New Client Secret.
- הוסף תיאור ומשך תוקף.

- העתק את ערך הסוד שנוצר - לא תראה אותו שוב.
שמור את client secret באופן מאובטח; הוא נדרש לאימות לקוח סודי.
אתה צריך לראות את הלוח של האפליקציות שנרשמו לאחרונה.

3. קביעת הרשאות Microsoft Graph
- נווט אל API Permissions → Add a Permission → Microsoft Graph.
- בחר את סוג ההרשאות: Delegated או Application, בהתאם לתרחיש שלך.
- הוסף את ההרשאות הנדרשות לפעולות Aspose.Email:
- Contacts.ReadWrite – לניהול אנשי קשר
- Calendars.ReadWrite – לניהול לוחות שנה
- Mail.ReadWrite – לקריאת והעברת הודעות
- Tasks.ReadWrite – לניהול משימות
- לחץ על Grant Admin Consent אם נדרש.

4. אפשר זרימות של לקוחות ציבוריים
ציין האם האפליקציה היא לקוח ציבורי. מתאים לאפליקציות המשתמשות בזרימות הענקת אסימונים שאינן משתמשות ב-URI הפניה.

5. אימות Microsoft Graph
שיטות אימות נתמכות ב-Aspose.Email
| ספק אסימון | מקרה שימוש | | ——————————– | ————————————————————————————— | | AzureConfidentialTokenProvider | לקוח סודי (client ID + secret) לאפליקציות צד שרת | | AzureROPCConfiguration | אישורי בעלות משאבים (שם משתמש + סיסמה) לתרחישים לא אינטראקטיביים | | AzurePublicTokenProvider | לקוח ציבורי (כניסה אינטראקטיבית) | | AzureTokenProviderBase | מחלקת בסיס למימושי אימות מותאמים אישית |
אימות באמצעות לקוח סודי
השתמש ב- AzureConfidentialTokenProvider לאימות כאשר יש לך client ID, client secret ו-tenant ID:
AzureConfidentialTokenProvider provider = new AzureConfidentialTokenProvider(
tenantId,
clientId,
clientSecret
);
IGraphClient client = GraphClient.getClient(provider, tenantId);
client.setResource(ResourceType.Users);
client.setResourceId(username);
client.setEndpoint("https://graph.microsoft.com");
זה מגדיר IGraphClient מאומת במלואו ומוכן לתקשר עם Microsoft Graph.
אימות באמצעות ROPC (שם משתמש וסיסמה)
במקרים שבהם יש לך שם משתמש וסיסמה, השתמש ב- AzureROPCConfiguration:
AzureROPCConfiguration ropcConfig = new AzureROPCConfiguration(
tenantId,
clientId,
clientSecret,
username,
password
);
IGraphClient client = GraphClient.getClient(ropcConfig, tenantId);
client.setResource(ResourceType.Users);
client.setResourceId(username);
client.setEndpoint("https://graph.microsoft.com");
ספקי אסימונים מותאמים אישית ל-Microsoft Graph
Aspose.Email for Java משולב עם Microsoft Graph דרך IGraphClient ממשק. כדי לאמת בקשות, מימוש של ITokenProvider נדרש. בעוד מרבית המפתחים ישתמשו בספקי אימות מובנים, יש מצבים שבהם תרצה ליצור ספק משלך, לדוגמה, כאשר עובדים עם זרימת Resource Owner Password Credentials (ROPC).
1. מימוש ITokenProvider באמצעות AzureROPCTokenProvider
מחלקה זו מספקת מימוש של ITokenProvider באמצעות זרימת Azure Resource Owner Password Credentials (ROPC). הדוגמה הבאה היא לצרכי הדגמה בלבד. בייצור, אנו ממליצים להשתמש בזרימות מאובטחות יותר כגון אישורי לקוח או קוד אימות עם PKCE.
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.io.UnsupportedEncodingException;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLDecoder;
import java.net.URLEncoder;
import java.nio.charset.StandardCharsets;
import java.util.HashMap;
import java.util.Map;
/**
* <p>
* Azure resource owner password credential (ROPC) token provider
* https://docs.microsoft.com/en-us/azure/active-directory/develop/v2-oauth-ropc
* https://docs.microsoft.com/en-us/exchange/client-developer/exchange-web-services/how-to-authenticate-an-ews-application-by-using-oauth
* https://portal.azure.com
* https://developer.microsoft.com/en-us/graph/graph-explorer/#
* token parser https://jwt.io
* </p>
*/
class AzureROPCTokenProvider implements ITokenProvider {
private static final String GRANT_TYPE = "password";
private final String clientId;
private final String clientSecret;
private final String userName;
private final String password;
private final String tenant;
private final String scope;
private OAuthToken token;
public AzureROPCTokenProvider(String tenant, String clientId, String clientSecret,
String userName, String password, String[] scopeAr) {
this.tenant = tenant;
this.clientId = clientId;
this.clientSecret = clientSecret;
this.userName = userName;
this.password = password;
this.scope = joinToStr(scopeAr, " ");
}
public synchronized OAuthToken getAccessToken(boolean ignoreExistingToken) {
if (this.token != null && !this.token.getExpired() && !ignoreExistingToken)
return this.token;
token = null;
Map<String, String> tokenArgs = getToken();
java.util.Calendar c = java.util.Calendar.getInstance();
c.add(java.util.Calendar.SECOND, Integer.parseInt(tokenArgs.get("expires_in")));
token = new OAuthToken(tokenArgs.get("access_token"), TokenType.AccessToken, c.getTime());
return token;
}
public final OAuthToken getAccessToken() {
return getAccessToken(false);
}
public void dispose() {
}
private String getEncodedParameters() {
return "client_id=" + urlEncode(clientId) + "&scope=" + urlEncode(scope) + "&username=" + urlEncode(userName)
+ "&password=" + urlEncode(password) + "&grant_type="
+ urlEncode(GRANT_TYPE);
}
private String getUri() {
if (tenant == null || tenant.trim().isEmpty())
return "https://login.microsoftonline.com/common/oauth2/v2.0/token";
else
return "https://login.microsoftonline.com/" + tenant + "/oauth2/v2.0/token";
}
private Map<String, String> getToken() {
try {
HttpURLConnection connection = (HttpURLConnection) new URL(getUri()).openConnection();
connection.setRequestMethod("POST");
byte[] requestData = getEncodedParameters().getBytes(StandardCharsets.UTF_8);
connection.setUseCaches(false);
connection.setDoInput(true);
connection.setDoOutput(true);
connection.setRequestProperty("Content-Type", "application/x-www-form-urlencoded");
connection.setRequestProperty("Content-Length", "" + requestData.length);
final OutputStream st = connection.getOutputStream();
try {
st.write(requestData, 0, requestData.length);
} finally {
st.flush();
st.close();
}
connection.connect();
if (connection.getResponseCode() >= HttpURLConnection.HTTP_BAD_REQUEST) {
throw new IllegalAccessError("Operation failed: " + connection.getResponseCode() + "/" +
connection.getResponseMessage() + "\r\nDetails:\r\n{2}"
+ readInputStream(connection.getErrorStream()));
}
String responseText = readInputStream(connection.getInputStream());
Map<String, String> result = new HashMap<>();
String[] fromJsonToKeyValue = responseText.replace("{", "").replace("}", "")
.replace("\"", "").replace("\r", "")
.replace("\n", "").split(",");
for (String keyValue : fromJsonToKeyValue) {
String[] pair = keyValue.split(":");
String name = pair[0].trim().toLowerCase();
String value = urlDecode(pair[1].trim());
result.put(name, value);
}
return result;
} catch (IOException e) {
throw new IllegalAccessError(e.getMessage());
}
}
static String urlEncode(String value) {
try {
return URLEncoder.encode(value, StandardCharsets.UTF_8.toString());
} catch (UnsupportedEncodingException e) {
throw new IllegalAccessError(e.getMessage());
}
}
static String urlDecode(String value) {
try {
return URLDecoder.decode(value, StandardCharsets.UTF_8.toString());
} catch (UnsupportedEncodingException e) {
throw new IllegalAccessError(e.getMessage());
}
}
static String readInputStream(InputStream is) {
if (is == null)
return "";
BufferedReader reader = new BufferedReader(new InputStreamReader(is));
StringBuilder result = new StringBuilder();
String line;
try {
while ((line = reader.readLine()) != null) {
result.append(line);
}
} catch (IOException e) {
// ignore
}
return result.toString();
}
static String joinToStr(String[] arr, String sep) {
StringBuilder sb = new StringBuilder();
for (int i = 0; i < arr.length; i++) {
if (i > 0)
sb.append(sep);
sb.append(arr[i]);
}
return sb.toString();
}
}
2. יצירת אובייקט ITokenProvider
ה IGraphClient הממשק אחראי לבנייה של בקשות, שליחתן ל-Microsoft Graph, וטיפול בתגובות. כדי ליצור מופע של IGraphClient, עליך לספק מימוש של ITokenProvider. ספק האסימונים מאמת בקשות על ידי אספקת אסימון גישה תקף של OAuth.
דוגמת הקוד הבאה מדגימה כיצד ליצור מימוש פנימי בסיסי של ITokenProvider ממשק, הנדרש לאימות בקשות Microsoft Graph:
ITokenProvider tokenProvider = new ITokenProvider() {
Date expirationDate = null;
@Override
public void dispose() {
// Clean up resources if necessary
}
@Override
public OAuthToken getAccessToken(boolean ignoreExistingToken) {
// Retrieve an OAuth access token.
// If ignoreExistingToken is true, always request a new token.
// Otherwise, return the existing token if it is valid, or request a new one.
return null;
}
@Override
public OAuthToken getAccessToken() {
// Return a valid OAuth token.
// If no valid token exists, request a new one.
return new OAuthToken("token", expirationDate);
}
};
3. שימוש בספק אסימון מותאם אישית
לאחר שה ITokenProvider מוגדר, ניתן ליצור GraphClient מופע. לקוח זה ישתמש במספק הטוקן שסופק לאימות בעת קריאה ל‑Microsoft Graph.
ITokenProvider provider = new AzureROPCTokenProvider(
tenantId,
clientId,
clientSecret,
userName,
password,
new String[] {"https://graph.microsoft.com/.default"}
);
IGraphClient client = GraphClient.getClient(provider, tenantId);
client.setResource(ResourceType.Users);
client.setResourceId(userName);
client.setEndpoint("https://graph.microsoft.com");
// Now you can call Microsoft Graph APIs
var folders = client.listFolders(null);
for (GraphFolderInfo folder : folders) {
System.out.println(folder.getDisplayName());
}
לאחר יצירת הלקוח והאמתתו, ניתן להתחיל לבצע בקשות לשירותי Microsoft Graph.