Skip to content
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

How is the "app_installed_team_id" in a slack request payload set? #1229

Open
RubberDuckyToyFactory opened this issue Dec 18, 2024 · 2 comments
Labels
question Further information is requested

Comments

@RubberDuckyToyFactory
Copy link

I have a question about how app_installed_team_id is set in the slack request payload.

According to the source code mentioned here, https://github.com/slackapi/bolt-python/blob/v1.20.1/slack_bolt/request/internals.py#L90, the team_id is extracted based on what is present in the payload. I have a situation where I have a user that is a member of two workspaces in an organization. An app is installed in both workspaces by the same user, i.e. separate installation records are created with different team_ids. When I receive an event like app_home_open the payload will extract the team_id from the first authorization record, which in my case ends up being the correct team_id of the workspace that the app home tab is being loaded in. When I start an interaction, like clicking a button in the home tab, it results in an action payload and the team_id is extracted from the ["view"]["app_installed_team_id"] which has the value of the other workspace, being the workspace that the app was first installed in.

Why is it sending that value instead of the team_id of the workspace I am in? This results in the other team_id being set in the context and used by the client. I can override this, but am curious why this is the case and is it the expected behaviour?

TL;DR: when an app is installed in multiple workspaces in an org by the same user the app_installed_team_id seems to always be the team_id of the first workspace the app was installed in. Depending on the action being handled, the team_id that is being set in the context may not always be the team_id of the workspace you are using, resulting in the webclient making requests against the wrong workspace unless you manually override it.

Reproducible in:

The slack_bolt version

slack_bolt==1.20.1
slack_sdk==3.27.1

Python runtime version

Python 3.12.3

Steps to reproduce:

  1. Create two workspaces in an org and install an app in both workspaces by the same user.
  2. Open app home tab in the second workspace and review the app_installed_team_id in the request body.

Expected result:

Expected the app_installed_team_id to be the team_id of the workspace the action was initiated in.

Actual result:

It sets the team_id to the first workspace that the app was installed into.

####Logs:

{
  "type": "block_actions",
  "user": {
   <<redacted>>
    "team_id": "T07LF8EHX7V"
  },
  "api_app_id": "A02FZN4GRGA",
  <<redacted>>
  "team": {
    "id": "T07LF8EHX7V",
    <<redacted>>
    "enterprise_id": "E07L8N9AQES",
    <<redacted>>
  },
  <<redacted>>
  "is_enterprise_install": false,
  "view": {
        <<redacted>>
        "app_installed_team_id": "T07M45HCWF2",
}

I would expect the app_installed_team_id to equal T07LF8EHX7V, not T07M45HCWF2.

@seratch seratch added the question Further information is requested label Dec 19, 2024
@seratch
Copy link
Member

seratch commented Dec 19, 2024

Hi @RubberDuckyToyFactory, thanks for asking the question.

I understand that this might be a bit confusing, but here are some important points to note about the Events API for multiple workspaces within the same Grid organization.

Firstly, when an app is installed across multiple workspaces to receive the same event, only one of those workspaces will receive it, and your app doesn't have the way to specify which workspace should be prioritized. This means that, even if bolt-python skips app_installed_team_id for this scenario, authorizations[0].team_id could randomly represent any of them (= it won't be the workspace where the user is using). If your app needs to know the list of installed workspaces, you can perform apps.event.authorizations.list API call with sufficient scopes. This Events API's behavior applies to any workspaces, not just those under an organization.

When your app is installed in multiple workspaces within an organization, 1:1 DMs and the Home tab do not belong to any specific workspace, and the Events API payload does not indicate which workspace the user's at. The latest Slack client UI combines all workspaces into a single view, removing the concept of being in a specific workspace. Although you still can filter the workspace in the UI, this does not affect the Events API payload sent to your app.

Therefore, please design your app without assuming your app can know which specific workspace a user is in during event delivery. As a workaround, you might consider opening a modal view to ask the user which workspace to be considered for app interactions (but I know this isn't ideal).

I hope this clarifies things and is helpful to you.

@RubberDuckyToyFactory
Copy link
Author

Thanks, @seratch.

I appreciate your thorough response. It was very helpful.

Could you clarify one other thing for me? The Slack API Docs for App Home says:

The app_home_opened event is accurately named — it tells your app when the user has opened the App Home. Your app can listen for this event and respond accordingly.

A payload will be delivered to your app via the Events API, containing actionable and contextual information about the event. This information will include the user that opened the App Home, the workspace that the event happened in, and more.

Is suggests that the payload will include the workspace that the event happened in. I guess this is where my confusion came from.

If I understand you correctly, when dealing with workspaces that are in an Enterprise Grid the behaviour is less straightforward. The Enterprise Docs says:

Look for the authed_teams node that arrives as part of the "wrapper" around delivered events. It contains a collection of team IDs within an organization that this delivery is on behalf of.

It gives an example of an event payload:

{
    "token": "ecto1EZslimer",
    "team_id": "T111AAA111",
    "api_app_id": "A123ABC456",
    "event": {
        "type": "message",
        "user": "W123ABC456",
        "text": "It's time to slacktivate!",
        "team": "T111AAA111",
        "source_team": "T111AAA111",
        "user_team": "T111AAA111",
        "user_profile": {
            "avatar_hash": "g56821b98743",
            "image_72": "https://...png",
            "first_name": "Jesse",
            "real_name": "Jesse Slacksalot",
            "name": "jesse.slacksalot"
        },
        "ts": "1485371714.000002",
        "channel": "C123ABC456",
        "event_ts": "1485371714.000002"
    },
    "type": "event_callback",
    "authed_users": [
        "W3MBP5799"
    ],
    "authed_teams": [
        "T222BBB222",
        "T111AAA111"
    ]
}

and says that The message originates from team T111AAA111 and is delivered as a single event for both teams, including T222BBB222.

Am I understanding you correctly that for an app_home_open event there is no way I can confidently know where the event originated from as suggested above?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
question Further information is requested
Projects
None yet
Development

No branches or pull requests

2 participants