Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions slack_bolt/authorization/async_authorize.py
Original file line number Diff line number Diff line change
Expand Up @@ -194,7 +194,10 @@ async def __call__(

if latest_installation.user_id != user_id:
# First off, remove the user token as the installer is a different user
user_token = None
latest_installation.user_token = None
latest_installation.user_refresh_token = None
latest_installation.user_token_expires_at = None
latest_installation.user_scopes = []

# try to fetch the request user's installation
Expand Down
3 changes: 3 additions & 0 deletions slack_bolt/authorization/authorize.py
Original file line number Diff line number Diff line change
Expand Up @@ -194,7 +194,10 @@ def __call__(

if latest_installation.user_id != user_id:
# First off, remove the user token as the installer is a different user
user_token = None
latest_installation.user_token = None
latest_installation.user_refresh_token = None
latest_installation.user_token_expires_at = None
latest_installation.user_scopes = []

# try to fetch the request user's installation
Expand Down
28 changes: 15 additions & 13 deletions tests/mock_web_api_server.py
Original file line number Diff line number Diff line change
Expand Up @@ -155,19 +155,21 @@ def _handle(self):
self.logger.info(f"request body: {request_body}")

if request_body.get("grant_type") == "refresh_token":
if "bot-valid" in request_body.get("refresh_token"):
self.send_response(200)
self.set_common_headers()
body = self.oauth_v2_access_bot_refresh_response
self.wfile.write(body.encode("utf-8"))
return
if "user-valid" in request_body.get("refresh_token"):
self.send_response(200)
self.set_common_headers()
body = self.oauth_v2_access_user_refresh_response
self.wfile.write(body.encode("utf-8"))
return
if request_body.get("code") is not None:
refresh_token = request_body.get("refresh_token")
if refresh_token is not None:
if "bot-valid" in refresh_token:
self.send_response(200)
self.set_common_headers()
body = self.oauth_v2_access_bot_refresh_response
self.wfile.write(body.encode("utf-8"))
return
if "user-valid" in refresh_token:
self.send_response(200)
self.set_common_headers()
body = self.oauth_v2_access_user_refresh_response
self.wfile.write(body.encode("utf-8"))
return
elif request_body.get("code") is not None:
self.send_response(200)
self.set_common_headers()
self.wfile.write(self.oauth_v2_access_response.encode("utf-8"))
Expand Down
49 changes: 49 additions & 0 deletions tests/slack_bolt/authorization/test_authorize.py
Original file line number Diff line number Diff line change
Expand Up @@ -245,6 +245,55 @@ def test_fetch_different_user_token_with_rotation(self):
assert result.user_token == "xoxp-valid-refreshed"
assert_auth_test_count(self, 1)

def test_remove_latest_user_token_if_it_is_not_relevant(self):
installation_store = ValidUserTokenInstallationStore()
authorize = InstallationStoreAuthorize(
logger=installation_store.logger, installation_store=installation_store
)
context = BoltContext()
context["client"] = WebClient(base_url=self.mock_api_server_base_url)
result = authorize(
context=context, enterprise_id="E111", team_id="T0G9PQBBK", user_id="W333"

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The installation store does not return tokens for user ID "W333"

)
assert result.bot_id == "BZYBOTHED"
assert result.bot_user_id == "W23456789"
assert result.bot_token == "xoxb-valid"
assert result.user_token is None

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Before the change in this PR, this is not absent.

assert_auth_test_count(self, 1)

def test_rotate_only_bot_token(self):
context = BoltContext()
mock_client = WebClient(base_url=self.mock_api_server_base_url)
context["client"] = mock_client

installation_store = ValidUserTokenRotationInstallationStore()
invalid_authorize = InstallationStoreAuthorize(
logger=installation_store.logger, installation_store=installation_store
)
with pytest.raises(BoltError):
invalid_authorize(
context=context,
enterprise_id="E111",
team_id="T0G9PQBBK",
user_id="W333",
)

authorize = InstallationStoreAuthorize(
client_id="111.222",
client_secret="secret",
client=mock_client,
logger=installation_store.logger,
installation_store=installation_store,
)
result = authorize(
context=context, enterprise_id="E111", team_id="T0G9PQBBK", user_id="W333"
)
assert result.bot_id == "BZYBOTHED"
assert result.bot_user_id == "W23456789"
assert result.bot_token == "xoxb-valid-refreshed"
assert result.user_token is None

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

same here

assert_auth_test_count(self, 1)


class LegacyMemoryInstallationStore(InstallationStore):
@property
Expand Down
51 changes: 51 additions & 0 deletions tests/slack_bolt_async/authorization/test_async_authorize.py
Original file line number Diff line number Diff line change
Expand Up @@ -272,6 +272,57 @@ async def test_fetch_different_user_token_with_rotation(self):
assert result.user_token == "xoxp-valid-refreshed"
await assert_auth_test_count_async(self, 1)

@pytest.mark.asyncio
async def test_remove_latest_user_token_if_it_is_not_relevant(self):
installation_store = ValidUserTokenInstallationStore()
authorize = AsyncInstallationStoreAuthorize(
logger=installation_store.logger, installation_store=installation_store
)
context = AsyncBoltContext()
context["client"] = AsyncWebClient(base_url=self.mock_api_server_base_url)
result = await authorize(
context=context, enterprise_id="E111", team_id="T0G9PQBBK", user_id="W333"
)
assert result.bot_id == "BZYBOTHED"
assert result.bot_user_id == "W23456789"
assert result.bot_token == "xoxb-valid"
assert result.user_token is None
await assert_auth_test_count_async(self, 1)

@pytest.mark.asyncio
async def test_rotate_only_bot_token(self):
context = AsyncBoltContext()
mock_client = AsyncWebClient(base_url=self.mock_api_server_base_url)
context["client"] = mock_client

installation_store = ValidUserTokenRotationInstallationStore()
invalid_authorize = AsyncInstallationStoreAuthorize(
logger=installation_store.logger, installation_store=installation_store
)
with pytest.raises(BoltError):
await invalid_authorize(
context=context,
enterprise_id="E111",
team_id="T0G9PQBBK",
user_id="W333",
)

authorize = AsyncInstallationStoreAuthorize(
client_id="111.222",
client_secret="secret",
client=mock_client,
logger=installation_store.logger,
installation_store=installation_store,
)
result = await authorize(
context=context, enterprise_id="E111", team_id="T0G9PQBBK", user_id="W333"
)
assert result.bot_id == "BZYBOTHED"
assert result.bot_user_id == "W23456789"
assert result.bot_token == "xoxb-valid-refreshed"
assert result.user_token is None
await assert_auth_test_count_async(self, 1)


class LegacyMemoryInstallationStore(AsyncInstallationStore):
@property
Expand Down