💻

Microsoft Graph でログイン ユーザーが組織アカウントか Microsoft アカウントかどうかを識別する

2022/01/01に公開

/me で判断する

とりあえず思いつく /me ではあまり違いがわかりません。

組織アカウントの場合

{
    "@odata.context": "https://graph.microsoft.com/v1.0/$metadata#users/$entity",
    "id": "00000000-0000-0000-0000-000000000000",
    "businessPhones": [],
    "displayName": "Example User",
    "givenName": "",
    "jobTitle": null,
    "mail": "example@example.onmicrosoft.com",
    "mobilePhone": null,
    "officeLocation": null,
    "preferredLanguage": "ja-JP",
    "surname": "",
    "userPrincipalName": "user@example.onmicrosoft.com"
}

Microsoft アカウントの場合

{
    "@odata.context": "https://graph.microsoft.com/v1.0/$metadata#users/$entity",
    "displayName": "Example User",
    "surname": "",
    "givenName": "",
    "id": "0000000000000000",
    "userPrincipalName": "example@outlook.com",
    "businessPhones": [],
    "jobTitle": null,
    "mail": null,
    "mobilePhone": null,
    "officeLocation": null,
    "preferredLanguage": null
}

userPrincipalName のドメイン名で判別するか、id が CID (ULong?) か GUID かで判断するか、どちらにしてもあまり美しくない感じがします。

/organization で判断する

/organization は Microsoft アカウントの場合は空の配列を返します。こっちのほうがよさそう。

組織アカウントの場合

{
    "@odata.context": "https://graph.microsoft.com/v1.0/$metadata#organization",
    "value": [
        {
            "id": "00000000-0000-0000-0000-000000000000",
            "deletedDateTime": null,
            "businessPhones": [],
            "city": null,
            "country": null,
            "countryLetterCode": null,
            "displayName": "example",
            "marketingNotificationEmails": [],
            "onPremisesLastSyncDateTime": null,
            "onPremisesSyncEnabled": null,
            "postalCode": null,
            "preferredLanguage": null,
            "privacyProfile": null,
            "securityComplianceNotificationMails": [],
            "securityComplianceNotificationPhones": [],
            "state": null,
            "street": null,
            "technicalNotificationMails": [],
            "assignedPlans": [],
            "provisionedPlans": [],
            "verifiedDomains": [
                {
                    "capabilities": "Email, OfficeCommunicationsOnline",
                    "isDefault": false,
                    "isInitial": true,
                    "name": "example.onmicrosoft.com",
                    "type": "Managed"
                }
            ]
        }
    ]
}

Microsoft アカウントの場合

{
    "@odata.context": "https://graph.microsoft.com/beta/$metadata#organization",
    "value": []
}

そもそも判断する必要なんてないんだよ

アカウントでサポートされていない API の場合はエラーが返ります。たとえば Microsoft アカウントで /me/manager を実行した場合は 404 エラーになります。

{
    "error": {
        "code": "",
        "message": "No HTTP resource was found that matches the request URI 'https://outlook.office365.com:444/profile/v1.0/users('CID:0000000000000000')/profile/manager?api-version=AGSV1-internal'.",
        "innerError": {
            "request-id": "00000000-0000-0000-0000-000000000000",
            "date": "2018-07-10T00:00:00"
        }
    }
}

呼んでみてエラーだったら諦める、というのも考え方としてはアリかもしれません。

Discussion