Skip to content

Commit a87ae51

Browse files
authored
Fix context.teamId for view interactions in a Slack Connect channel (#1068)
1 parent 5f62ed9 commit a87ae51

File tree

4 files changed

+188
-8
lines changed

4 files changed

+188
-8
lines changed

bolt/src/main/java/com/slack/api/bolt/request/builtin/ViewClosedRequest.java

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,13 @@ public ViewClosedRequest(
2828
} else if (payload.getTeam() != null) {
2929
getContext().setEnterpriseId(payload.getTeam().getEnterpriseId());
3030
}
31-
if (payload.getTeam() != null && payload.getTeam().getId() != null) {
31+
if (payload.getView() != null && payload.getView().getAppInstalledTeamId() != null) {
32+
// view_submission payloads can have `view.app_installed_team_id` when a modal view that was opened
33+
// in a different workspace via some operations inside a Slack Connect channel.
34+
// Note that the same for enterprise_id does not exist. When you need to know the enterprise_id as well,
35+
// you have to run some query toward your InstallationStore to know the org where the team_id belongs to.
36+
getContext().setTeamId(payload.getView().getAppInstalledTeamId());
37+
} else if (payload.getTeam() != null && payload.getTeam().getId() != null) {
3238
getContext().setTeamId(payload.getTeam().getId());
3339
} else if (payload.getView() != null && payload.getView().getTeamId() != null) {
3440
getContext().setTeamId(payload.getView().getTeamId());

bolt/src/main/java/com/slack/api/bolt/request/builtin/ViewSubmissionRequest.java

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,13 @@ public ViewSubmissionRequest(
2828
} else if (payload.getTeam() != null) {
2929
getContext().setEnterpriseId(payload.getTeam().getEnterpriseId());
3030
}
31-
if (payload.getTeam() != null && payload.getTeam().getId() != null) {
31+
if (payload.getView() != null && payload.getView().getAppInstalledTeamId() != null) {
32+
// view_submission payloads can have `view.app_installed_team_id` when a modal view that was opened
33+
// in a different workspace via some operations inside a Slack Connect channel.
34+
// Note that the same for enterprise_id does not exist. When you need to know the enterprise_id as well,
35+
// you have to run some query toward your InstallationStore to know the org where the team_id belongs to.
36+
getContext().setTeamId(payload.getView().getAppInstalledTeamId());
37+
} else if (payload.getTeam() != null && payload.getTeam().getId() != null) {
3238
getContext().setTeamId(payload.getTeam().getId());
3339
} else if (payload.getView() != null && payload.getView().getTeamId() != null) {
3440
getContext().setTeamId(payload.getView().getTeamId());

bolt/src/test/java/test_locally/request/ViewClosedRequestTest.java

Lines changed: 87 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -19,13 +19,13 @@ public class ViewClosedRequestTest {
1919
" \"id\": \"W111\",\n" +
2020
" \"username\": \"primary-owner\",\n" +
2121
" \"name\": \"primary-owner\",\n" +
22-
" \"team_id\": \"T_expected\"\n" +
22+
" \"team_id\": \"T_unexpected\"\n" +
2323
" },\n" +
2424
" \"api_app_id\": \"A111\",\n" +
2525
" \"token\": \"fixed-value\",\n" +
2626
" \"view\": {\n" +
2727
" \"id\": \"V111\",\n" +
28-
" \"team_id\": \"T_expected\",\n" +
28+
" \"team_id\": \"T_unexpected\",\n" +
2929
" \"type\": \"modal\",\n" +
3030
" \"blocks\": [\n" +
3131
" {\n" +
@@ -72,7 +72,7 @@ public class ViewClosedRequestTest {
7272
" \"root_view_id\": \"V111\",\n" +
7373
" \"app_id\": \"A111\",\n" +
7474
" \"external_id\": \"\",\n" +
75-
" \"app_installed_team_id\": \"E111\",\n" +
75+
" \"app_installed_team_id\": \"T_expected\",\n" +
7676
" \"bot_id\": \"B0302M47727\"\n" +
7777
" },\n" +
7878
" \"is_cleared\": false,\n" +
@@ -89,4 +89,88 @@ public void orgWideInstallation() throws UnsupportedEncodingException {
8989
ViewClosedRequest req = new ViewClosedRequest("payload=" + URLEncoder.encode(orgWideInstallationPayload, "UTF-8"), orgWideInstallationPayload, headers);
9090
assertEquals("T_expected", req.getContext().getTeamId());
9191
}
92+
93+
String sharedChannelPayload = "{\n" +
94+
" \"type\": \"view_closed\",\n" +
95+
" \"team\": {\n" +
96+
" \"id\": \"T-other-side\",\n" +
97+
" \"domain\": \"other-side\",\n" +
98+
" \"enterprise_id\": \"E-other-side\",\n" +
99+
" \"enterprise_name\": \"Kaz Sandbox Org\"\n" +
100+
" },\n" +
101+
" \"user\": {\n" +
102+
" \"id\": \"W111\",\n" +
103+
" \"username\": \"kaz\",\n" +
104+
" \"name\": \"kaz\",\n" +
105+
" \"team_id\": \"T-other-side\"\n" +
106+
" },\n" +
107+
" \"api_app_id\": \"A1111\",\n" +
108+
" \"token\": \"legacy-fixed-token\",\n" +
109+
" \"trigger_id\": \"111.222.xxx\",\n" +
110+
" \"view\": {\n" +
111+
" \"id\": \"V11111\",\n" +
112+
" \"team_id\": \"T-other-side\",\n" +
113+
" \"type\": \"modal\",\n" +
114+
" \"blocks\": [\n" +
115+
" {\n" +
116+
" \"type\": \"input\",\n" +
117+
" \"block_id\": \"zniAM\",\n" +
118+
" \"label\": {\n" +
119+
" \"type\": \"plain_text\",\n" +
120+
" \"text\": \"Label\"\n" +
121+
" },\n" +
122+
" \"element\": {\n" +
123+
" \"type\": \"plain_text_input\",\n" +
124+
" \"dispatch_action_config\": {\n" +
125+
" \"trigger_actions_on\": [\n" +
126+
" \"on_enter_pressed\"\n" +
127+
" ]\n" +
128+
" },\n" +
129+
" \"action_id\": \"qEJr\"\n" +
130+
" }\n" +
131+
" }\n" +
132+
" ],\n" +
133+
" \"private_metadata\": \"\",\n" +
134+
" \"callback_id\": \"view-id\",\n" +
135+
" \"state\": {\n" +
136+
" \"values\": {\n" +
137+
" \"zniAM\": {\n" +
138+
" \"qEJr\": {\n" +
139+
" \"type\": \"plain_text_input\",\n" +
140+
" \"value\": \"Hi there!\"\n" +
141+
" }\n" +
142+
" }\n" +
143+
" }\n" +
144+
" },\n" +
145+
" \"hash\": \"1664950703.CmTS8F7U\",\n" +
146+
" \"title\": {\n" +
147+
" \"type\": \"plain_text\",\n" +
148+
" \"text\": \"My App\"\n" +
149+
" },\n" +
150+
" \"close\": {\n" +
151+
" \"type\": \"plain_text\",\n" +
152+
" \"text\": \"Cancel\"\n" +
153+
" },\n" +
154+
" \"submit\": {\n" +
155+
" \"type\": \"plain_text\",\n" +
156+
" \"text\": \"Submit\"\n" +
157+
" },\n" +
158+
" \"root_view_id\": \"V00000\",\n" +
159+
" \"app_id\": \"A1111\",\n" +
160+
" \"external_id\": \"\",\n" +
161+
" \"app_installed_team_id\": \"T-installed-workspace\",\n" +
162+
" \"bot_id\": \"B1111\"\n" +
163+
" },\n" +
164+
" \"enterprise\": {\n" +
165+
" \"id\": \"E-other-side\",\n" +
166+
" \"name\": \"Kaz Sandbox Org\"\n" +
167+
" }\n" +
168+
"}\n";
169+
170+
@Test
171+
public void sharedChannels() throws UnsupportedEncodingException {
172+
RequestHeaders headers = new RequestHeaders(Collections.emptyMap());
173+
ViewClosedRequest req = new ViewClosedRequest("payload=" + URLEncoder.encode(sharedChannelPayload, "UTF-8"), sharedChannelPayload, headers);
174+
assertEquals("T-installed-workspace", req.getContext().getTeamId());
175+
}
92176
}

bolt/src/test/java/test_locally/request/ViewSubmissionRequestTest.java

Lines changed: 87 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -175,14 +175,14 @@ public void responseUrl_single() throws UnsupportedEncodingException {
175175
" \"id\": \"W111\",\n" +
176176
" \"username\": \"primary-owner\",\n" +
177177
" \"name\": \"primary-owner\",\n" +
178-
" \"team_id\": \"T_expected\"\n" +
178+
" \"team_id\": \"T_unexpected\"\n" +
179179
" },\n" +
180180
" \"api_app_id\": \"A111\",\n" +
181181
" \"token\": \"fixed-value\",\n" +
182182
" \"trigger_id\": \"1111.222.xxx\",\n" +
183183
" \"view\": {\n" +
184184
" \"id\": \"V111\",\n" +
185-
" \"team_id\": \"T_expected\",\n" +
185+
" \"team_id\": \"T_unexpected\",\n" +
186186
" \"type\": \"modal\",\n" +
187187
" \"blocks\": [\n" +
188188
" {\n" +
@@ -238,7 +238,7 @@ public void responseUrl_single() throws UnsupportedEncodingException {
238238
" \"root_view_id\": \"V111\",\n" +
239239
" \"app_id\": \"A111\",\n" +
240240
" \"external_id\": \"\",\n" +
241-
" \"app_installed_team_id\": \"E111\",\n" +
241+
" \"app_installed_team_id\": \"T_expected\",\n" +
242242
" \"bot_id\": \"B111\"\n" +
243243
" },\n" +
244244
" \"response_urls\": [],\n" +
@@ -255,4 +255,88 @@ public void orgWideInstallation() throws UnsupportedEncodingException {
255255
ViewSubmissionRequest req = new ViewSubmissionRequest("payload=" + URLEncoder.encode(orgWideInstallationPayload, "UTF-8"), orgWideInstallationPayload, headers);
256256
assertEquals("T_expected", req.getContext().getTeamId());
257257
}
258+
259+
String sharedChannelPayload = "{\n" +
260+
" \"type\": \"view_submission\",\n" +
261+
" \"team\": {\n" +
262+
" \"id\": \"T-other-side\",\n" +
263+
" \"domain\": \"other-side\",\n" +
264+
" \"enterprise_id\": \"E-other-side\",\n" +
265+
" \"enterprise_name\": \"Kaz Sandbox Org\"\n" +
266+
" },\n" +
267+
" \"user\": {\n" +
268+
" \"id\": \"W111\",\n" +
269+
" \"username\": \"kaz\",\n" +
270+
" \"name\": \"kaz\",\n" +
271+
" \"team_id\": \"T-other-side\"\n" +
272+
" },\n" +
273+
" \"api_app_id\": \"A1111\",\n" +
274+
" \"token\": \"legacy-fixed-token\",\n" +
275+
" \"trigger_id\": \"111.222.xxx\",\n" +
276+
" \"view\": {\n" +
277+
" \"id\": \"V11111\",\n" +
278+
" \"team_id\": \"T-other-side\",\n" +
279+
" \"type\": \"modal\",\n" +
280+
" \"blocks\": [\n" +
281+
" {\n" +
282+
" \"type\": \"input\",\n" +
283+
" \"block_id\": \"zniAM\",\n" +
284+
" \"label\": {\n" +
285+
" \"type\": \"plain_text\",\n" +
286+
" \"text\": \"Label\"\n" +
287+
" },\n" +
288+
" \"element\": {\n" +
289+
" \"type\": \"plain_text_input\",\n" +
290+
" \"dispatch_action_config\": {\n" +
291+
" \"trigger_actions_on\": [\n" +
292+
" \"on_enter_pressed\"\n" +
293+
" ]\n" +
294+
" },\n" +
295+
" \"action_id\": \"qEJr\"\n" +
296+
" }\n" +
297+
" }\n" +
298+
" ],\n" +
299+
" \"private_metadata\": \"\",\n" +
300+
" \"callback_id\": \"view-id\",\n" +
301+
" \"state\": {\n" +
302+
" \"values\": {\n" +
303+
" \"zniAM\": {\n" +
304+
" \"qEJr\": {\n" +
305+
" \"type\": \"plain_text_input\",\n" +
306+
" \"value\": \"Hi there!\"\n" +
307+
" }\n" +
308+
" }\n" +
309+
" }\n" +
310+
" },\n" +
311+
" \"hash\": \"1664950703.CmTS8F7U\",\n" +
312+
" \"title\": {\n" +
313+
" \"type\": \"plain_text\",\n" +
314+
" \"text\": \"My App\"\n" +
315+
" },\n" +
316+
" \"close\": {\n" +
317+
" \"type\": \"plain_text\",\n" +
318+
" \"text\": \"Cancel\"\n" +
319+
" },\n" +
320+
" \"submit\": {\n" +
321+
" \"type\": \"plain_text\",\n" +
322+
" \"text\": \"Submit\"\n" +
323+
" },\n" +
324+
" \"root_view_id\": \"V00000\",\n" +
325+
" \"app_id\": \"A1111\",\n" +
326+
" \"external_id\": \"\",\n" +
327+
" \"app_installed_team_id\": \"T-installed-workspace\",\n" +
328+
" \"bot_id\": \"B1111\"\n" +
329+
" },\n" +
330+
" \"enterprise\": {\n" +
331+
" \"id\": \"E-other-side\",\n" +
332+
" \"name\": \"Kaz Sandbox Org\"\n" +
333+
" }\n" +
334+
"}\n";
335+
336+
@Test
337+
public void sharedChannels() throws UnsupportedEncodingException {
338+
RequestHeaders headers = new RequestHeaders(Collections.emptyMap());
339+
ViewSubmissionRequest req = new ViewSubmissionRequest("payload=" + URLEncoder.encode(sharedChannelPayload, "UTF-8"), sharedChannelPayload, headers);
340+
assertEquals("T-installed-workspace", req.getContext().getTeamId());
341+
}
258342
}

0 commit comments

Comments
 (0)