Skip to content

Commit 614e31d

Browse files
authored
Merge pull request #191062 from yoelhor/patch-249
Update to new Azure Identity auth library
2 parents 7a789b2 + 7d3f98d commit 614e31d

File tree

1 file changed

+113
-125
lines changed

1 file changed

+113
-125
lines changed

articles/active-directory/external-identities/code-samples.md

Lines changed: 113 additions & 125 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ services: active-directory
66
ms.service: active-directory
77
ms.subservice: B2B
88
ms.topic: sample
9-
ms.date: 04/11/2017
9+
ms.date: 03/14/2022
1010

1111
ms.author: mimart
1212
author: msmimart
@@ -19,7 +19,8 @@ ms.collection: M365-identity-device-management
1919
# Azure Active Directory B2B collaboration code and PowerShell samples
2020

2121
## PowerShell example
22-
You can bulk-invite external users to an organization from email addresses that you have stored in a .CSV file.
22+
23+
You can bulk-invite external users to an organization from email addresses that you've stored in a .CSV file.
2324

2425
1. Prepare the .CSV file
2526
Create a new CSV file and name it invitations.csv. In this example, the file is saved in C:\data, and contains the following information:
@@ -49,49 +50,49 @@ You can bulk-invite external users to an organization from email addresses that
4950
foreach ($email in $invitations) {New-AzureADMSInvitation -InvitedUserEmailAddress $email.InvitedUserEmailAddress -InvitedUserDisplayName $email.Name -InviteRedirectUrl https://wingtiptoysonline-dev-ed.my.salesforce.com -InvitedUserMessageInfo $messageInfo -SendInvitationMessage $true}
5051
```
5152

52-
This cmdlet sends an invitation to the email addresses in invitations.csv. Additional features of this cmdlet include:
53+
This cmdlet sends an invitation to the email addresses in invitations.csv. More features of this cmdlet include:
54+
5355
- Customized text in the email message
5456
- Including a display name for the invited user
5557
- Sending messages to CCs or suppressing email messages altogether
5658

5759
## Code sample
58-
Here we illustrate how to call the invitation API, in "app-only" mode, to get the redemption URL for the resource to which you are inviting the B2B user. The goal is to send a custom invitation email. The email can be composed with an HTTP client, so you can customize how it looks and send it through the Microsoft Graph API.
60+
61+
The code sample illustrates how to call the invitation API and get the redemption URL. Use the redemption URL to send a custom invitation email. The email can be composed with an HTTP client, so you can customize how it looks and send it through the Microsoft Graph API.
62+
63+
64+
# [HTTP](#tab/http)
65+
66+
```http
67+
POST https://graph.microsoft.com/v1.0/invitations
68+
Content-type: application/json
69+
{
70+
"invitedUserEmailAddress": "[email protected]",
71+
"invitedUserDisplayName": "David",
72+
"inviteRedirectUrl": "https://myapp.contoso.com",
73+
"sendInvitationMessage": true
74+
}
75+
```
76+
77+
# [C#](#tab/csharp)
5978

6079
```csharp
80+
using System;
81+
using System.Threading.Tasks;
82+
using Microsoft.Graph;
83+
using Azure.Identity;
84+
6185
namespace SampleInviteApp
6286
{
63-
using System;
64-
using System.Linq;
65-
using System.Net.Http;
66-
using System.Net.Http.Headers;
67-
using Microsoft.IdentityModel.Clients.ActiveDirectory;
68-
using Newtonsoft.Json;
6987
class Program
7088
{
7189
/// <summary>
72-
/// Microsoft Graph resource.
73-
/// </summary>
74-
static readonly string GraphResource = "https://graph.microsoft.com";
75-
76-
/// <summary>
77-
/// Microsoft Graph invite endpoint.
78-
/// </summary>
79-
static readonly string InviteEndPoint = "https://graph.microsoft.com/v1.0/invitations";
80-
81-
/// <summary>
82-
///  Authentication endpoint to get token.
83-
/// </summary>
84-
static readonly string EstsLoginEndpoint = "https://login.microsoftonline.com";
85-
86-
/// <summary>
87-
/// This is the tenantid of the tenant you want to invite users to.
90+
/// This is the tenant ID of the tenant you want to invite users to.
8891
/// </summary>
8992
private static readonly string TenantID = "";
9093

9194
/// <summary>
9295
/// This is the application id of the application that is registered in the above tenant.
93-
/// The required scopes are available in the below link.
94-
/// https://developer.microsoft.com/graph/docs/api-reference/v1.0/api/invitation_post
9596
/// </summary>
9697
private static readonly string TestAppClientId = "";
9798

@@ -114,119 +115,106 @@ namespace SampleInviteApp
114115
/// Main method.
115116
/// </summary>
116117
/// <param name="args">Optional arguments</param>
117-
static void Main(string[] args)
118-
{
119-
Invitation invitation = CreateInvitation();
120-
SendInvitation(invitation);
121-
}
122-
123-
/// <summary>
124-
/// Create the invitation object.
125-
/// </summary>
126-
/// <returns>Returns the invitation object.</returns>
127-
private static Invitation CreateInvitation()
118+
static async Task Main(string[] args)
128119
{
129-
// Set the invitation object.
130-
Invitation invitation = new Invitation();
131-
invitation.InvitedUserDisplayName = InvitedUserDisplayName;
132-
invitation.InvitedUserEmailAddress = InvitedUserEmailAddress;
133-
invitation.InviteRedirectUrl = "https://www.microsoft.com";
134-
invitation.SendInvitationMessage = true;
135-
return invitation;
120+
string InviteRedeemUrl = await SendInvitation();
136121
}
137122

138123
/// <summary>
139124
/// Send the guest user invite request.
140125
/// </summary>
141-
/// <param name="invitation">Invitation object.</param>
142-
private static void SendInvitation(Invitation invitation)
126+
private static async string SendInvitation()
143127
{
144-
string accessToken = GetAccessToken();
128+
/// Get the access token for our application to talk to Microsoft Graph.
129+
var scopes = new[] { "https://graph.microsoft.com/.default" };
130+
var clientSecretCredential = new ClientSecretCredential(TenantID, TestAppClientId, TestAppClientSecret);
131+
var graphClient = new GraphServiceClient(clientSecretCredential, scopes);
145132

146-
HttpClient httpClient = GetHttpClient(accessToken);
147-
148-
// Make the invite call.
149-
HttpContent content = new StringContent(JsonConvert.SerializeObject(invitation));
150-
content.Headers.Add("ContentType", "application/json");
151-
var postResponse = httpClient.PostAsync(InviteEndPoint, content).Result;
152-
string serverResponse = postResponse.Content.ReadAsStringAsync().Result;
153-
Console.WriteLine(serverResponse);
133+
// Create the invitation object.
134+
var invitation = new Invitation
135+
{
136+
InvitedUserEmailAddress = InvitedUserEmailAddress,
137+
InvitedUserDisplayName = InvitedUserDisplayName,
138+
InviteRedirectUrl = "https://www.microsoft.com",
139+
SendInvitationMessage = true
140+
};
141+
142+
// Send the invitation
143+
var GraphResponse = await graphClient.Invitations
144+
.Request()
145+
.AddAsync(invitation);
146+
147+
// Return the invite redeem URL
148+
return GraphResponse.InviteRedeemUrl;
154149
}
150+
}
151+
}
152+
```
155153

156-
/// <summary>
157-
/// Get the HTTP client.
158-
/// </summary>
159-
/// <param name="accessToken">Access token</param>
160-
/// <returns>Returns the Http Client.</returns>
161-
private static HttpClient GetHttpClient(string accessToken)
162-
{
163-
// setup http client.
164-
HttpClient httpClient = new HttpClient();
165-
httpClient.Timeout = TimeSpan.FromSeconds(300);
166-
httpClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", accessToken);
167-
httpClient.DefaultRequestHeaders.Add("client-request-id", Guid.NewGuid().ToString());
168-
Console.WriteLine(
169-
"CorrelationID for the request: {0}",
170-
httpClient.DefaultRequestHeaders.GetValues("client-request-id").Single());
171-
return httpClient;
172-
}
154+
# [JavaScript](#tab/javascript)
173155

174-
/// <summary>
175-
/// Get the access token for our application to talk to Microsoft Graph.
176-
/// </summary>
177-
/// <returns>Returns the access token for our application to talk to Microsoft Graph.</returns>
178-
private static string GetAccessToken()
179-
{
180-
string accessToken = null;
156+
Install the following npm packages:
181157

182-
// Get the access token for our application to talk to Microsoft Graph.
183-
try
184-
{
185-
AuthenticationContext testAuthContext =
186-
new AuthenticationContext(string.Format("{0}/{1}", EstsLoginEndpoint, TenantID));
187-
AuthenticationResult testAuthResult = testAuthContext.AcquireTokenAsync(
188-
GraphResource,
189-
new ClientCredential(TestAppClientId, TestAppClientSecret)).Result;
190-
accessToken = testAuthResult.AccessToken;
191-
}
192-
catch (AdalException ex)
193-
{
194-
Console.WriteLine("An exception was thrown while fetching the token: {0}.", ex);
195-
throw;
196-
}
197-
198-
return accessToken;
199-
}
158+
```bash
159+
npm install express
160+
npm install isomorphic-fetch
161+
npm install @azure/identity
162+
npm install @microsoft/microsoft-graph-client
163+
```
200164

201-
/// <summary>
202-
/// Invitation class.
203-
/// </summary>
204-
public class Invitation
205-
{
206-
/// <summary>
207-
/// Gets or sets display name.
208-
/// </summary>
209-
public string InvitedUserDisplayName { get; set; }
210-
211-
/// <summary>
212-
/// Gets or sets display name.
213-
/// </summary>
214-
public string InvitedUserEmailAddress { get; set; }
215-
216-
/// <summary>
217-
/// Gets or sets a value indicating whether Invitation Manager should send the email to InvitedUser.
218-
/// </summary>
219-
public bool SendInvitationMessage { get; set; }
220-
221-
/// <summary>
222-
/// Gets or sets invitation redirect URL
223-
/// </summary>
224-
public string InviteRedirectUrl { get; set; }
225-
}
226-
}
165+
```javascript
166+
const express = require('express')
167+
const app = express()
168+
169+
const { Client } = require("@microsoft/microsoft-graph-client");
170+
const { TokenCredentialAuthenticationProvider } = require("@microsoft/microsoft-graph-client/authProviders/azureTokenCredentials");
171+
const { ClientSecretCredential } = require("@azure/identity");
172+
require("isomorphic-fetch");
173+
174+
// This is the application id of the application that is registered in the above tenant.
175+
const CLIENT_ID = ""
176+
177+
// Client secret of the application.
178+
const CLIENT_SECRET = ""
179+
180+
// This is the tenant ID of the tenant you want to invite users to. For example fabrikam.onmicrosoft.com
181+
const TENANT_ID = ""
182+
183+
async function sendInvite() {
184+
185+
// Initialize a confidential client application. For more info, visit: https://github.com/Azure/azure-sdk-for-js/blob/main/sdk/identity/identity/samples/AzureIdentityExamples.md#authenticating-a-service-principal-with-a-client-secret
186+
const credential = new ClientSecretCredential(TENANT_ID, CLIENT_ID, CLIENT_SECRET);
187+
188+
// Initialize the Microsoft Graph authentication provider. For more info, visit: https://docs.microsoft.com/en-us/graph/sdks/choose-authentication-providers?tabs=Javascript#using--for-server-side-applications
189+
const authProvider = new TokenCredentialAuthenticationProvider(credential, { scopes: ['https://graph.microsoft.com/.default'] });
190+
191+
// Create MS Graph client instance. For more info, visit: https://github.com/microsoftgraph/msgraph-sdk-javascript/blob/dev/docs/CreatingClientInstance.md
192+
const client = Client.initWithMiddleware({
193+
debugLogging: true,
194+
authProvider,
195+
});
196+
197+
// Create invitation object
198+
const invitation = {
199+
invitedUserEmailAddress: '[email protected]',
200+
invitedUserDisplayName: 'David',
201+
inviteRedirectUrl: 'https://www.microsoft.com',
202+
sendInvitationMessage: true
203+
};
204+
205+
// Execute the MS Graph command. For more information, visit: https://docs.microsoft.com/en-us/graph/api/invitation-post
206+
graphResponse = await client.api('/invitations')
207+
.post(invitation);
208+
209+
// Return the invite redeem URL
210+
return graphResponse.inviteRedeemUrl
227211
}
212+
213+
const inviteRedeemUrl = await sendInvite();
214+
228215
```
229216

217+
---
230218

231219
## Next steps
232220

0 commit comments

Comments
 (0)