/**
* Questmate Custom Item - Slack Member Picker
*
* Permissions:
* @UseApp {SLACK}
*
* Changelog:
* v0.1 Initial release
*/
return defineCustomItem((Questmate) => {
Questmate.registerView("ITEM_RUN_VIEW", ({ useRunData }) => {
const [selectedMember, setSelectedMember] = useRunData("memberId", null);
return {
components: [
{
id: "member",
type: "dropdown",
icon: "person",
value: selectedMember,
onSelect: setSelectedMember,
getOptions: async () =>
(await membersDataSource.retrieve())
.sort((a, b) => {
// switch to `localeCompare` when supported
if (a.name < b.name) return -1;
if (a.name > b.name) return 1;
return 0;
})
.map(({ name, id }) => ({
label: name,
value: id,
})),
optionNoun: "Member",
optionPluralNoun: "Members",
},
],
};
});
const membersDataSource = Questmate.registerDataSource({
id: "members",
initialData: [],
refreshInterval: 10 * 60,
aggregator: ({ results, staleResults }) =>
[...results, ...staleResults]
.flatMap((result) => result.data)
.filter(
(member, index, self) =>
self.findIndex((m) => m.id === member.id) === index
),
fetcher:
({ nextPageMarker }) =>
async () => {
const response = await fetch(
`https://slack.com/api/users.list?limit=200${
nextPageMarker ? `&cursor=${nextPageMarker}` : ""
}`
);
const responseData = await response.json();
if (!responseData.ok) {
let retryAfter = undefined;
if (response.status === 429) {
try {
retryAfter = parseInt(response.headers.get("Retry-After"));
} catch (e) {
console.log(
"Failed to parse Retry-After header",
response.headers.get("Retry-After"),
e
);
}
}
return {
error: {
message: "Failed to load Slack members",
details: responseData,
...(retryAfter ? { retryAfter } : {}),
},
};
}
return {
data: responseData.members
.filter(
(member) =>
!member.is_bot && member.name !== "slackbot" && !member.deleted
)
.map(({ profile, id }) => ({
id,
name:
profile.real_name_normalized || profile.display_name_normalized,
})),
nextPageMarker: responseData.response_metadata.next_cursor,
};
},
});
});
Copyright © Questmate Pty Ltd.