Skip to content

Commit 8c0532d

Browse files
authored
Add org-wide installation test patterns (#578)
1 parent cb3891b commit 8c0532d

2 files changed

Lines changed: 225 additions & 0 deletions

File tree

slack_bolt/request/internals.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -78,6 +78,8 @@ def extract_enterprise_id(payload: Dict[str, Any]) -> Optional[str]:
7878

7979
def extract_team_id(payload: Dict[str, Any]) -> Optional[str]:
8080
if payload.get("team") is not None:
81+
# With org-wide installations, payload.team in interactivity payloads can be None
82+
# You need to extract either payload.user.team_id or payload.view.team_id as below
8183
team = payload.get("team")
8284
if isinstance(team, str):
8385
return team
@@ -93,6 +95,8 @@ def extract_team_id(payload: Dict[str, Any]) -> Optional[str]:
9395
return extract_team_id(payload["event"])
9496
if payload.get("user") is not None:
9597
return payload.get("user")["team_id"]
98+
if payload.get("view") is not None:
99+
return payload.get("view")["team_id"]
96100
return None
97101

98102

tests/slack_bolt/request/test_request.py

Lines changed: 221 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
from urllib.parse import quote
2+
13
from slack_bolt.request.request import BoltRequest
24

35

@@ -21,3 +23,222 @@ def test_all_none_inputs_socket_mode(self):
2123
assert req is not None
2224
assert req.raw_body == ""
2325
assert req.body == {}
26+
27+
def test_org_wide_installations_block_actions(self):
28+
payload = """
29+
{
30+
"type": "block_actions",
31+
"user": {
32+
"id": "W111",
33+
"username": "primary-owner",
34+
"name": "primary-owner",
35+
"team_id": "T_expected"
36+
},
37+
"api_app_id": "A111",
38+
"token": "fixed-value",
39+
"container": {
40+
"type": "message",
41+
"message_ts": "1643113871.000700",
42+
"channel_id": "C111",
43+
"is_ephemeral": true
44+
},
45+
"trigger_id": "111.222.xxx",
46+
"team": null,
47+
"enterprise": {
48+
"id": "E111",
49+
"name": "Sandbox Org"
50+
},
51+
"is_enterprise_install": true,
52+
"channel": {
53+
"id": "C111",
54+
"name": "random"
55+
},
56+
"state": {
57+
"values": {}
58+
},
59+
"response_url": "https://hooks.slack.com/actions/E111/111/xxx",
60+
"actions": [
61+
{
62+
"action_id": "a",
63+
"block_id": "b",
64+
"text": {
65+
"type": "plain_text",
66+
"text": "Button"
67+
},
68+
"value": "click_me_123",
69+
"type": "button",
70+
"action_ts": "1643113877.645417"
71+
}
72+
]
73+
}
74+
"""
75+
req = BoltRequest(body=f"payload={quote(payload)}")
76+
assert req is not None
77+
assert req.context.team_id == "T_expected"
78+
assert req.context.user_id == "W111"
79+
80+
def test_org_wide_installations_view_submission(self):
81+
payload = """
82+
{
83+
"type": "view_submission",
84+
"team": null,
85+
"user": {
86+
"id": "W111",
87+
"username": "primary-owner",
88+
"name": "primary-owner",
89+
"team_id": "T_expected"
90+
},
91+
"api_app_id": "A111",
92+
"token": "fixed-value",
93+
"trigger_id": "1111.222.xxx",
94+
"view": {
95+
"id": "V111",
96+
"team_id": "T_expected",
97+
"type": "modal",
98+
"blocks": [
99+
{
100+
"type": "input",
101+
"block_id": "+5B",
102+
"label": {
103+
"type": "plain_text",
104+
"text": "Label",
105+
"emoji": true
106+
},
107+
"optional": false,
108+
"dispatch_action": false,
109+
"element": {
110+
"type": "plain_text_input",
111+
"dispatch_action_config": {
112+
"trigger_actions_on": [
113+
"on_enter_pressed"
114+
]
115+
},
116+
"action_id": "MMKH"
117+
}
118+
}
119+
],
120+
"private_metadata": "",
121+
"callback_id": "view-id",
122+
"state": {
123+
"values": {
124+
"+5B": {
125+
"MMKH": {
126+
"type": "plain_text_input",
127+
"value": "test"
128+
}
129+
}
130+
}
131+
},
132+
"hash": "111.xxx",
133+
"title": {
134+
"type": "plain_text",
135+
"text": "My App"
136+
},
137+
"clear_on_close": false,
138+
"notify_on_close": false,
139+
"close": {
140+
"type": "plain_text",
141+
"text": "Cancel"
142+
},
143+
"submit": {
144+
"type": "plain_text",
145+
"text": "Submit",
146+
"emoji": true
147+
},
148+
"previous_view_id": null,
149+
"root_view_id": "V111",
150+
"app_id": "A111",
151+
"external_id": "",
152+
"app_installed_team_id": "E111",
153+
"bot_id": "B111"
154+
},
155+
"response_urls": [],
156+
"is_enterprise_install": true,
157+
"enterprise": {
158+
"id": "E111",
159+
"name": "Sandbox Org"
160+
}
161+
}
162+
"""
163+
req = BoltRequest(body=f"payload={quote(payload)}")
164+
assert req is not None
165+
assert req.context.team_id == "T_expected"
166+
assert req.context.user_id == "W111"
167+
168+
def test_org_wide_installations_view_closed(self):
169+
payload = """
170+
{
171+
"type": "view_closed",
172+
"team": null,
173+
"user": {
174+
"id": "W111",
175+
"username": "primary-owner",
176+
"name": "primary-owner",
177+
"team_id": "T_expected"
178+
},
179+
"api_app_id": "A111",
180+
"token": "fixed-value",
181+
"view": {
182+
"id": "V111",
183+
"team_id": "T_expected",
184+
"type": "modal",
185+
"blocks": [
186+
{
187+
"type": "input",
188+
"block_id": "M2r2p",
189+
"label": {
190+
"type": "plain_text",
191+
"text": "Label"
192+
},
193+
"optional": false,
194+
"dispatch_action": false,
195+
"element": {
196+
"type": "plain_text_input",
197+
"dispatch_action_config": {
198+
"trigger_actions_on": [
199+
"on_enter_pressed"
200+
]
201+
},
202+
"action_id": "xB+"
203+
}
204+
}
205+
],
206+
"private_metadata": "",
207+
"callback_id": "view-id",
208+
"state": {
209+
"values": {}
210+
},
211+
"hash": "1643113987.gRY6ROtt",
212+
"title": {
213+
"type": "plain_text",
214+
"text": "My App"
215+
},
216+
"clear_on_close": false,
217+
"notify_on_close": true,
218+
"close": {
219+
"type": "plain_text",
220+
"text": "Cancel"
221+
},
222+
"submit": {
223+
"type": "plain_text",
224+
"text": "Submit"
225+
},
226+
"previous_view_id": null,
227+
"root_view_id": "V111",
228+
"app_id": "A111",
229+
"external_id": "",
230+
"app_installed_team_id": "E111",
231+
"bot_id": "B0302M47727"
232+
},
233+
"is_cleared": false,
234+
"is_enterprise_install": true,
235+
"enterprise": {
236+
"id": "E111",
237+
"name": "Sandbox Org"
238+
}
239+
}
240+
"""
241+
req = BoltRequest(body=f"payload={quote(payload)}")
242+
assert req is not None
243+
assert req.context.team_id == "T_expected"
244+
assert req.context.user_id == "W111"

0 commit comments

Comments
 (0)