-
Notifications
You must be signed in to change notification settings - Fork 5.3k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Updating Chat prop to include support for external users. #14711
base: master
Are you sure you want to change the base?
Changes from 2 commits
5a3adea
2c5e1c3
a0dc9a4
bf6fd91
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change | ||||||||||||||||||||||||||||||||||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|
@@ -5,7 +5,7 @@ import constants from "./common/constants.mjs"; | |||||||||||||||||||||||||||||||||||||||||||||
export default { | ||||||||||||||||||||||||||||||||||||||||||||||
type: "app", | ||||||||||||||||||||||||||||||||||||||||||||||
app: "microsoft_teams", | ||||||||||||||||||||||||||||||||||||||||||||||
description: "**Personal accounts are not currently supported by Microsoft Teams.** Refer to Microsoft's documentation [here](https://learn.microsoft.com/en-us/graph/permissions-reference#remarks-7) to learn more.", | ||||||||||||||||||||||||||||||||||||||||||||||
description: "Connect and interact with Microsoft Teams, supporting both internal and external communications.", | ||||||||||||||||||||||||||||||||||||||||||||||
propDefinitions: { | ||||||||||||||||||||||||||||||||||||||||||||||
team: { | ||||||||||||||||||||||||||||||||||||||||||||||
type: "string", | ||||||||||||||||||||||||||||||||||||||||||||||
|
@@ -58,16 +58,50 @@ export default { | |||||||||||||||||||||||||||||||||||||||||||||
chat: { | ||||||||||||||||||||||||||||||||||||||||||||||
type: "string", | ||||||||||||||||||||||||||||||||||||||||||||||
label: "Chat", | ||||||||||||||||||||||||||||||||||||||||||||||
description: "Team Chat within the organization (No external Contacts)", | ||||||||||||||||||||||||||||||||||||||||||||||
description: "Team Chat (internal and external contacts)", | ||||||||||||||||||||||||||||||||||||||||||||||
async options({ prevContext }) { | ||||||||||||||||||||||||||||||||||||||||||||||
const response = prevContext.nextLink | ||||||||||||||||||||||||||||||||||||||||||||||
? await this.makeRequest({ | ||||||||||||||||||||||||||||||||||||||||||||||
path: prevContext.nextLink, | ||||||||||||||||||||||||||||||||||||||||||||||
}) | ||||||||||||||||||||||||||||||||||||||||||||||
: await this.listChats(); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
const myTenantId = await this.getAuthenticatedUserTenant(); | ||||||||||||||||||||||||||||||||||||||||||||||
const options = []; | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
for (const chat of response.value) { | ||||||||||||||||||||||||||||||||||||||||||||||
const members = chat.members.map((member) => member.displayName); | ||||||||||||||||||||||||||||||||||||||||||||||
const messages = await this.makeRequest({ | ||||||||||||||||||||||||||||||||||||||||||||||
path: `/chats/${chat.id}/messages?$top=50`, | ||||||||||||||||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
const members = await Promise.all(chat.members.map(async (member) => { | ||||||||||||||||||||||||||||||||||||||||||||||
let displayName = member.displayName; | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
if (!displayName && messages.value.length > 0) { | ||||||||||||||||||||||||||||||||||||||||||||||
const userMessage = messages.value.find((msg) => | ||||||||||||||||||||||||||||||||||||||||||||||
msg.from?.user?.id === member.userId); | ||||||||||||||||||||||||||||||||||||||||||||||
if (userMessage?.from?.user?.displayName) { | ||||||||||||||||||||||||||||||||||||||||||||||
displayName = userMessage.from.user.displayName; | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
if (!displayName) { | ||||||||||||||||||||||||||||||||||||||||||||||
try { | ||||||||||||||||||||||||||||||||||||||||||||||
const userDetails = await this.makeRequest({ | ||||||||||||||||||||||||||||||||||||||||||||||
path: `/users/${member.userId}`, | ||||||||||||||||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||||||||||||||||
displayName = userDetails.displayName; | ||||||||||||||||||||||||||||||||||||||||||||||
} catch (err) { | ||||||||||||||||||||||||||||||||||||||||||||||
displayName = "Unknown User"; | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
const isExternal = member.tenantId !== myTenantId || !member.tenantId; | ||||||||||||||||||||||||||||||||||||||||||||||
return isExternal | ||||||||||||||||||||||||||||||||||||||||||||||
? `${displayName} (External)` | ||||||||||||||||||||||||||||||||||||||||||||||
: displayName; | ||||||||||||||||||||||||||||||||||||||||||||||
})); | ||||||||||||||||||||||||||||||||||||||||||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🛠️ Refactor suggestion Enhance error handling and performance The member resolution logic has several areas for improvement:
Consider implementing these improvements: const members = await Promise.all(chat.members.map(async (member) => {
- let displayName = member.displayName;
+ // Cache key using userId
+ const cacheKey = `user_${member.userId}`;
+ let displayName = member.displayName || this._userCache?.get(cacheKey);
- if (!displayName && messages.value.length > 0) {
+ if (!displayName) {
const userMessage = messages.value.find((msg) =>
msg.from?.user?.id === member.userId);
if (userMessage?.from?.user?.displayName) {
displayName = userMessage.from.user.displayName;
}
- }
- if (!displayName) {
try {
const userDetails = await this.makeRequest({
path: `/users/${member.userId}`,
});
displayName = userDetails.displayName;
+ // Cache the result
+ this._userCache?.set(cacheKey, displayName);
} catch (err) {
- displayName = "Unknown User";
+ if (err.statusCode === 404) {
+ displayName = "User Not Found";
+ } else if (err.statusCode === 403) {
+ displayName = "Access Denied";
+ } else {
+ displayName = "Unknown User";
+ }
+ console.error(`Failed to fetch user details for ${member.userId}:`, err);
}
}
|
||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
options.push({ | ||||||||||||||||||||||||||||||||||||||||||||||
label: members.join(", "), | ||||||||||||||||||||||||||||||||||||||||||||||
value: chat.id, | ||||||||||||||||||||||||||||||||||||||||||||||
|
@@ -144,6 +178,12 @@ export default { | |||||||||||||||||||||||||||||||||||||||||||||
: reduction; | ||||||||||||||||||||||||||||||||||||||||||||||
}, api); | ||||||||||||||||||||||||||||||||||||||||||||||
}, | ||||||||||||||||||||||||||||||||||||||||||||||
async getAuthenticatedUserTenant() { | ||||||||||||||||||||||||||||||||||||||||||||||
const { value } = await this.client() | ||||||||||||||||||||||||||||||||||||||||||||||
.api("/organization") | ||||||||||||||||||||||||||||||||||||||||||||||
.get(); | ||||||||||||||||||||||||||||||||||||||||||||||
return value[0].id; | ||||||||||||||||||||||||||||||||||||||||||||||
}, | ||||||||||||||||||||||||||||||||||||||||||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🛠️ Refactor suggestion Add error handling to tenant ID retrieval The method assumes the organization API will always return results. Add proper error handling for edge cases. async getAuthenticatedUserTenant() {
- const { value } = await this.client()
- .api("/organization")
- .get();
- return value[0].id;
+ try {
+ const { value } = await this.client()
+ .api("/organization")
+ .get();
+
+ if (!value || value.length === 0) {
+ throw new Error("No organization found");
+ }
+
+ return value[0].id;
+ } catch (error) {
+ console.error("Failed to fetch tenant ID:", error);
+ throw new Error("Unable to determine tenant ID");
+ }
}, 📝 Committable suggestion
Suggested change
|
||||||||||||||||||||||||||||||||||||||||||||||
async authenticatedUserId() { | ||||||||||||||||||||||||||||||||||||||||||||||
const { id } = await this.client() | ||||||||||||||||||||||||||||||||||||||||||||||
.api("/me") | ||||||||||||||||||||||||||||||||||||||||||||||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I assume removing the dcumentation link is intentional here