microsoft/teams.net

Public

mirrored fromhttps://github.com/microsoft/teams.netAvailable

CodeCommitsIssuesPull requestsActionsInsightsSecurity
v2.0.8

Branches

Tags

  • No tags available.
0Branches0Tags
Go to file
Add file
Code

Clone

HTTPS

Download ZIP

core/test/IntegrationTests/CreateConversationTests.cs

369lines · modecode

1// Copyright (c) Microsoft Corporation.
2// Licensed under the MIT License.
3
4using Microsoft.Teams.Apps.Api.Clients;
5using Microsoft.Teams.Core;
6using Microsoft.Teams.Core.Schema;
7using Xunit.Abstractions;
8
9namespace IntegrationTests;
10
11/// <summary>
12/// Integration tests for creating conversations with different ConversationParameters.
13/// Tests personal chats, group chats, and channel thread creation via both
14/// core <see cref="ConversationClient"/> and the <see cref="ApiClient"/> facade.
15/// </summary>
16public class CreateConversationTests : IClassFixture<IntegrationTestFixture>
17{
18 private readonly IntegrationTestFixture _f;
19 private readonly ITestOutputHelper _output;
20 private readonly ApiClient _api;
21
22 public CreateConversationTests(IntegrationTestFixture fixture, ITestOutputHelper output)
23 {
24 _f = fixture;
25 _f.OutputHelper = output;
26 _output = output;
27 _api = _f.ScopedApiClient;
28 }
29
30 /// <summary>
31 /// Gets MRI-format member IDs by fetching the conversation members list.
32 /// The API requires MRI IDs (e.g., "29:1abc..."), not pairwise bot framework IDs.
33 /// </summary>
34 private async Task<(string first, string? second)> GetMemberMrisAsync()
35 {
36 IList<ConversationAccount> members = await _f.ConversationClient.GetConversationMembersAsync(
37 _f.ConversationId, _f.ServiceUrl, _f.AgenticIdentity);
38
39 Assert.True(members.Count >= 1, "Need at least 1 member in the test conversation");
40
41 string first = members[0].Id!;
42 string? second = members.Count >= 2 ? members[1].Id : null;
43
44 _output.WriteLine($"Using member MRIs: first={first}, second={second ?? "(none)"}");
45 return (first, second);
46 }
47
48 #region Personal Chat (1:1) — Core ConversationClient
49
50 [Fact(Timeout = 5000)]
51 public async Task Core_CreatePersonalChat()
52 {
53 (string memberMri, _) = await GetMemberMrisAsync();
54
55 ConversationParameters parameters = new()
56 {
57 IsGroup = false,
58 Members = [new() { Id = memberMri }],
59 TenantId = _f.TenantId
60 };
61
62 CreateConversationResponse response = await _f.ConversationClient.CreateConversationAsync(
63 parameters, _f.ServiceUrl, _f.AgenticIdentity);
64
65 Assert.NotNull(response);
66 Assert.NotNull(response.Id);
67 _output.WriteLine($"Created 1:1 conversation: {response.Id}");
68 }
69
70 [Fact(Timeout = 5000)]
71 public async Task Core_CreatePersonalChat_AndSendMessage()
72 {
73 (string memberMri, _) = await GetMemberMrisAsync();
74
75 ConversationParameters parameters = new()
76 {
77 IsGroup = false,
78 Members = [new() { Id = memberMri }],
79 TenantId = _f.TenantId
80 };
81
82 CreateConversationResponse response = await _f.ConversationClient.CreateConversationAsync(
83 parameters, _f.ServiceUrl, _f.AgenticIdentity);
84
85 Assert.NotNull(response?.Id);
86
87 CoreActivity activity = CoreActivity.CreateBuilder()
88 .WithType(ActivityType.Message)
89 .WithFrom(IntegrationTestFixture.GetConversationAccountWithAgenticProperties())
90 .WithServiceUrl(_f.ServiceUrl)
91 .WithConversation(new(response.Id))
92 .WithProperty("text", $"[Core] 1:1 message at `{DateTime.UtcNow:s}`")
93 .Build();
94
95 SendActivityResponse? sent = await _f.ConversationClient.SendActivityAsync(activity);
96 Assert.NotNull(sent?.Id);
97 _output.WriteLine($"Created 1:1 conversation {response.Id} and sent activity {sent.Id}");
98 }
99
100 [Fact(Timeout = 5000)]
101 public async Task Core_CreatePersonalChat_WithInitialActivity()
102 {
103 (string memberMri, _) = await GetMemberMrisAsync();
104
105 ConversationParameters parameters = new()
106 {
107 IsGroup = false,
108 Members = [new() { Id = memberMri }],
109 TenantId = _f.TenantId,
110 Activity = CoreActivity.CreateBuilder()
111 .WithType(ActivityType.Message)
112 .WithProperty("text", $"[Core] Initial message at `{DateTime.UtcNow:s}`")
113 .Build()
114 };
115
116 CreateConversationResponse response = await _f.ConversationClient.CreateConversationAsync(
117 parameters, _f.ServiceUrl, _f.AgenticIdentity);
118
119 Assert.NotNull(response);
120 Assert.NotNull(response.Id);
121 _output.WriteLine($"Created 1:1 conversation with initial activity: {response.Id}, activityId: {response.ActivityId}");
122 }
123
124 #endregion
125
126 #region Group Chat — Core ConversationClient
127
128 [Fact]
129 public async Task Core_CreateGroupChat()
130 {
131 (string first, string? second) = await GetMemberMrisAsync();
132 if (second is null)
133 {
134 _output.WriteLine("Skipping: need at least 2 members in conversation");
135 return;
136 }
137
138 ConversationParameters parameters = new()
139 {
140 //IsGroup = true,
141 Bot = new() { Id = $"28:{_f.BotAppId}" },
142 Members =
143 [
144 //new() { Id = first },
145 new() { Id = second }
146 ],
147 TenantId = _f.TenantId,
148 //TopicName = $"Integration Test Group - {DateTime.UtcNow:s}",
149 ChannelData = new { tenant = new { id = _f.TenantId } }
150 };
151
152 CreateConversationResponse response = await _f.ConversationClient.CreateConversationAsync(
153 parameters, _f.ServiceUrl, _f.AgenticIdentity);
154
155 Assert.NotNull(response);
156 Assert.NotNull(response.Id);
157 _output.WriteLine($"Created group conversation: {response.Id}");
158 }
159
160 [Fact]
161 public async Task Core_CreateGroupChat_AndSendMessage()
162 {
163 (string first, string? second) = await GetMemberMrisAsync();
164 if (second is null)
165 {
166 _output.WriteLine("Skipping: need at least 2 members in conversation");
167 return;
168 }
169
170 ConversationParameters parameters = new()
171 {
172 IsGroup = false,
173 Bot = new() { Id = $"28:{_f.BotAppId}" },
174 Members =
175 [
176 //new() { Id = first },
177 new() { Id = second }
178 ],
179 TenantId = _f.TenantId,
180 ChannelData = new { tenant = new { id = _f.TenantId } }
181 };
182
183 CreateConversationResponse response = await _f.ConversationClient.CreateConversationAsync(
184 parameters, _f.ServiceUrl, _f.AgenticIdentity);
185
186 Assert.NotNull(response?.Id);
187
188 CoreActivity activity = CoreActivity.CreateBuilder()
189 .WithType(ActivityType.Message)
190 .WithFrom(IntegrationTestFixture.GetConversationAccountWithAgenticProperties())
191 .WithServiceUrl(_f.ServiceUrl)
192 .WithConversation(new(response.Id))
193 .WithProperty("text", $"[Core] Group message at `{DateTime.UtcNow:s}`")
194 .Build();
195
196 SendActivityResponse? sent = await _f.ConversationClient.SendActivityAsync(activity);
197 Assert.NotNull(sent?.Id);
198 _output.WriteLine($"Created group {response.Id} and sent activity {sent.Id}");
199 }
200
201 #endregion
202
203 #region Channel Thread — Core ConversationClient
204
205 [Fact(Timeout = 5000)]
206 public async Task Core_CreateChannelThread()
207 {
208 ConversationParameters parameters = new()
209 {
210 IsGroup = true,
211 ChannelData = new { channel = new { id = _f.ChannelId } },
212 Activity = CoreActivity.CreateBuilder()
213 .WithType(ActivityType.Message)
214 .WithProperty("text", $"[Core] New channel thread at `{DateTime.UtcNow:s}`")
215 .Build(),
216 TenantId = _f.TenantId
217 };
218
219 CreateConversationResponse response = await _f.ConversationClient.CreateConversationAsync(
220 parameters, _f.ServiceUrl, _f.AgenticIdentity);
221
222 Assert.NotNull(response);
223 Assert.NotNull(response.Id);
224 _output.WriteLine($"Created channel thread: {response.Id}, activityId: {response.ActivityId}");
225 }
226
227 #endregion
228
229 #region Personal Chat — ApiClient
230
231 [Fact(Timeout = 5000)]
232 public async Task ApiClient_CreatePersonalChat()
233 {
234 (string memberMri, _) = await GetMemberMrisAsync();
235
236 ConversationParameters parameters = new()
237 {
238 IsGroup = false,
239 Members = [new() { Id = memberMri }],
240 TenantId = _f.TenantId
241 };
242
243 CreateConversationResponse response = await _api.Conversations.CreateAsync(parameters, _f.AgenticIdentity);
244
245 Assert.NotNull(response);
246 Assert.NotNull(response.Id);
247 _output.WriteLine($"[ApiClient] Created 1:1 conversation: {response.Id}");
248 }
249
250 [Fact(Timeout = 5000)]
251 public async Task ApiClient_CreatePersonalChat_AndSendViaActivities()
252 {
253 (string memberMri, _) = await GetMemberMrisAsync();
254
255 ConversationParameters parameters = new()
256 {
257 IsGroup = false,
258 Members = [new() { Id = memberMri }],
259 TenantId = _f.TenantId
260 };
261
262 CreateConversationResponse response = await _api.Conversations.CreateAsync(parameters, _f.AgenticIdentity);
263 Assert.NotNull(response?.Id);
264
265 CoreActivity activity = CoreActivity.CreateBuilder()
266 .WithType(ActivityType.Message)
267 .WithFrom(IntegrationTestFixture.GetConversationAccountWithAgenticProperties())
268 .WithProperty("text", $"[ApiClient] 1:1 via Activities.Create at `{DateTime.UtcNow:s}`")
269 .Build();
270
271 SendActivityResponse? sent = await _api.Conversations.Activities.CreateAsync(response.Id, activity);
272 Assert.NotNull(sent?.Id);
273 _output.WriteLine($"[ApiClient] Created 1:1 {response.Id}, sent activity {sent.Id}");
274 }
275
276 #endregion
277
278 #region Group Chat — ApiClient
279
280 [Fact]
281 public async Task ApiClient_CreateGroupChat()
282 {
283 (string first, string? second) = await GetMemberMrisAsync();
284 if (second is null)
285 {
286 _output.WriteLine("Skipping: need at least 2 members in conversation");
287 return;
288 }
289
290 ConversationParameters parameters = new()
291 {
292 //IsGroup = true,
293 Bot = new() { Id = $"28:{_f.BotAppId}" },
294 Members =
295 [
296 new() { Id = first },
297 new() { Id = second }
298 ],
299 TenantId = _f.TenantId,
300 TopicName = $"[ApiClient] Group - {DateTime.UtcNow:s}",
301 ChannelData = new { tenant = new { id = _f.TenantId } }
302 };
303
304 CreateConversationResponse response = await _api.Conversations.CreateAsync(parameters, _f.AgenticIdentity);
305
306 Assert.NotNull(response);
307 Assert.NotNull(response.Id);
308 _output.WriteLine($"[ApiClient] Created group conversation: {response.Id}");
309 }
310
311 #endregion
312
313 #region Channel Thread — ApiClient
314
315 [Fact(Timeout = 5000)]
316 public async Task ApiClient_CreateChannelThread()
317 {
318 ConversationParameters parameters = new()
319 {
320 IsGroup = true,
321 ChannelData = new { channel = new { id = _f.ChannelId } },
322 Activity = CoreActivity.CreateBuilder()
323 .WithType(ActivityType.Message)
324 .WithProperty("text", $"[ApiClient] New channel thread at `{DateTime.UtcNow:s}`")
325 .Build(),
326 TenantId = _f.TenantId
327 };
328
329 CreateConversationResponse response = await _api.Conversations.CreateAsync(parameters, _f.AgenticIdentity);
330
331 Assert.NotNull(response);
332 Assert.NotNull(response.Id);
333 _output.WriteLine($"[ApiClient] Created channel thread: {response.Id}, activityId: {response.ActivityId}");
334 }
335
336 [Fact(Timeout = 5000)]
337 public async Task ApiClient_CreateChannelThread_AndReply()
338 {
339 ConversationParameters parameters = new()
340 {
341 IsGroup = true,
342 ChannelData = new { channel = new { id = _f.ChannelId } },
343 Activity = CoreActivity.CreateBuilder()
344 .WithType(ActivityType.Message)
345 .WithProperty("text", $"[ApiClient] Thread root at `{DateTime.UtcNow:s}`")
346 .Build(),
347 TenantId = _f.TenantId
348 };
349
350 CreateConversationResponse response = await _api.Conversations.CreateAsync(parameters, _f.AgenticIdentity);
351 Assert.NotNull(response?.Id);
352 Assert.NotNull(response.ActivityId);
353
354 // Reply to the thread
355 CoreActivity reply = CoreActivity.CreateBuilder()
356 .WithType(ActivityType.Message)
357 .WithFrom(IntegrationTestFixture.GetConversationAccountWithAgenticProperties())
358 .WithProperty("text", $"[ApiClient] Thread reply at `{DateTime.UtcNow:s}`")
359 .Build();
360
361 SendActivityResponse? replyResponse = await _api.Conversations.Activities.ReplyAsync(
362 response.Id, response.ActivityId, reply);
363
364 Assert.NotNull(replyResponse);
365 _output.WriteLine($"[ApiClient] Created thread {response.Id}, root activity {response.ActivityId}, reply {replyResponse?.Id}");
366 }
367
368 #endregion
369}
370