Skip to main content

Tool for migrating Slack exports to Google Chat

Project description

Slack to Google Chat Migration Tool

Migrates Slack workspace JSON exports into Google Chat spaces via the Google Chat Import API.

Features

  • Imports all messages (including threaded replies)
  • Uploads attachments into Google Drive with name+MD5 deduplication
  • Migrates emoji reactions using per-user impersonation
  • Posts channel metadata (purpose/topic) from channels.json
  • Retries API calls on transient errors with exponential backoff
  • Logs in structured JSON for easy Cloud Logging ingestion
  • Filters channels via config.yaml
  • Automatically generates user mapping from users.json
  • Maps external emails to internal workspace emails
  • Includes comprehensive reports for both validation runs and actual migrations
  • Identifies users without email addresses for mapping
  • Automatic permission checking before migration
  • Checkpoint-based resumption for interrupted migrations

How It Works

This tool uses the Google Chat Import API to migrate Slack data into Google Chat. Important things to know about import mode:

  • Spaces are created in import mode — they are hidden from users until import is completed
  • 90-day deadline — Google automatically deletes spaces that remain in import mode for more than 90 days
  • No notifications — messages imported in import mode don't trigger notifications for users
  • No link previews — URLs in imported messages won't generate link previews
  • Drive-preferred attachments — file attachments are uploaded to a shared Google Drive and linked in messages (Google recommends Drive for imported content)
  • Archival limitations — Google Chat's space archive/read-only features are not available during import mode; spaces become fully active once import completes
flowchart LR
    A[Slack Export] --> B[Validate]
    B --> C[Create Spaces\nin Import Mode]
    C --> D[Import Messages\n& Attachments]
    D --> E[Complete Import\nMode]
    E --> F[Add Members]
    F --> G[Spaces Visible\nto Users]

Prerequisites

Note: Using a Python virtual environment is recommended for Python dependency management. The Google Cloud SDK is a system-level component that cannot be installed via pip.

Installation

# Clone the repository
git clone https://github.com/nicklamont/slack-chat-migrator.git
cd slack-chat-migrator

# Create and activate a virtual environment (recommended)
python -m venv venv
source venv/bin/activate  # On Windows: venv\Scripts\activate

# Install the Python package in development mode
pip install -e .

# Or install directly from repository (still recommended to use a virtual environment)
pip install git+https://github.com/nicklamont/slack-chat-migrator.git

Note: Build configuration is defined in pyproject.toml. Install the package with pip install -e . rather than running any build files directly.

Quick Start

# 1. Set up GCP permissions (one-time, interactive wizard)
pip install -e ".[setup]"   # from a repo clone
# pip install "slack-chat-migrator[setup]"  # or from PyPI
slack-chat-migrator setup
# Then complete domain-wide delegation in Google Workspace Admin Console

# 2. Generate config from your export (interactive)
slack-chat-migrator init --export_path ./slack_export

# 3. Validate (dry run — no credentials needed)
slack-chat-migrator validate \
  --export_path ./slack_export

# 4. Migrate (credentials required for live migration)
slack-chat-migrator migrate \
  --creds_path /path/to/key.json \
  --export_path ./slack_export \
  --workspace_admin admin@company.com

Configuration

Create a config.yaml file (or copy from config.yaml.example):

# Shared Drive configuration for storing attachments
# Using a shared drive is recommended for organization-wide access
shared_drive:
  # Option 1: Specify an existing shared drive by ID
  # id: "0AInA6b6Ej1Q2Uk9PVA"  # Replace with your shared drive ID

  # Option 2: Specify a shared drive by name (will be created if it doesn't exist)
  name: "Imported Slack Attachments"

  # If neither id nor name is specified, a new shared drive will be created
  # with the name "Imported Slack Attachments"

# Optional: Channels to exclude from migration (by name)
exclude_channels:
  - "random"
  - "shitposting"

# Optional: Channels to include in migration (if specified, only these will be processed)
include_channels: []

# Optional: Override email domains for user mapping
# If not specified, emails from users.json will be used directly
email_domain_override: ""  # e.g. "company.com"

# Optional: User mapping overrides
# Use this to manually map specific Slack user IDs to Google Workspace emails
# This takes precedence over the automatic mapping from users.json
# You can also use this to map external emails to internal ones
user_mapping_overrides:
  # Map Slack user IDs to emails
  "U12345678": "user@example.com"
  # Map bot accounts that don't have emails
  "U87654321": "slackbot@company.com"

# User handling options
# Whether to skip importing bot messages and reactions
# When true, all bot messages and reactions will be excluded from migration
# When false (default), bot messages will be migrated if user mappings exist
ignore_bots: false

# Error handling configuration
# Whether to abort the entire migration if errors are encountered in a channel
abort_on_error: false

# Maximum percentage of message failures allowed per channel before skipping
# If more than this percentage of messages fail in a channel, the channel will be skipped
max_failure_percentage: 10

# Strategy for completing import mode when errors occur
# Options:
#   - "skip_on_error" (default): Skip completing import mode if channel had errors
#   - "force_complete": Complete import mode even if errors occurred
import_completion_strategy: "skip_on_error"

# Whether to delete spaces that had errors during migration
# If true, spaces with errors will be deleted during cleanup
cleanup_on_error: false

# Maximum number of retries for API calls
max_retries: 3

# Delay between retries (in seconds)
retry_delay: 2

Space Mapping

When using --resume to resume a migration, the tool discovers existing spaces by name. If multiple Google Chat spaces have the same name (e.g., multiple "Slack #general" spaces from previous attempts), you need to specify which space to use for each channel:

space_mapping:
  "general": "AAAAAgcE123"  # Use this space ID for the general channel
  "random": "AAAABbTr456"   # Use this space ID for the random channel

When duplicate spaces are found, the tool will:

  1. Skip those specific channels (not abort the entire migration)
  2. Mark these channels as failed in the migration report
  3. Log detailed information about each space to help you choose
  4. Provide exact configuration entries to copy into your config file

Note: Debug and logging options are controlled via command-line flags (--verbose and --debug_api) rather than configuration file settings. This ensures consistent logging behavior across all migration runs.

Command-Line Reference

The slack-chat-migrator command provides six subcommands:

slack-chat-migrator setup             # Interactive GCP setup wizard (one-time)
slack-chat-migrator init              # Generate config.yaml from your Slack export
slack-chat-migrator validate          # Dry-run validation of export data
slack-chat-migrator migrate           # Run the full migration
slack-chat-migrator check-permissions # Validate API permissions (deprecated — use validate)
slack-chat-migrator cleanup           # Complete import mode (deprecated — use migrate --complete)

Backwards compatibility: Running slack-chat-migrator --creds_path ... (flags without a subcommand) automatically routes to migrate, but this implicit routing is deprecated. Use slack-chat-migrator migrate ... instead.

Subcommands

setup

Interactive wizard that guides you through GCP project setup: creating a project, enabling APIs, creating a service account, downloading credentials, configuring the Chat app, and testing domain-wide delegation. Progress is saved between runs so you can resume if interrupted.

Requires the optional setup dependencies:

pip install "slack-chat-migrator[setup]"
init

Generate a config.yaml file interactively by analysing your Slack export. Walks through channel selection, user mapping overrides, and error handling preferences.

Option Required Description
--export_path Yes Path to the Slack export directory
--output No Output path for generated config file (default: config.yaml)
validate

Dry-run validation of export data, user mappings, and channels. Equivalent to migrate --dry_run but expressed as an explicit command. Credentials are optional — you can run a full validation with only --export_path. When --creds_path is provided, permission checks are also performed.

Option Required Description
--creds_path No Path to the service account credentials JSON file
--export_path Yes Path to the Slack export directory
--workspace_admin No Email of workspace admin to impersonate
--config No Path to config YAML (default: config.yaml)
--verbose or -v No Enable verbose console logging
--debug_api No Enable detailed API request/response logging
migrate

Run the full Slack-to-Google-Chat migration.

Option Required Description
--creds_path Live only Path to the service account credentials JSON file (optional with --dry_run)
--export_path Yes Path to the Slack export directory
--workspace_admin Live only Email of workspace admin to impersonate (optional with --dry_run)
--config No Path to config YAML (default: config.yaml)
--dry_run No Validation-only mode - performs comprehensive validation without making changes
--resume No Resume an interrupted migration - finds existing spaces and imports only newer messages
--complete No Complete import mode on all spaces without running a migration
--verbose or -v No Enable verbose console logging (shows DEBUG level messages)
--debug_api No Enable detailed API request/response logging (creates very large log files)
--skip_permission_check No Skip permission checks (not recommended)
check-permissions (deprecated)

Deprecated: Use validate --creds_path instead, which performs both data validation and permission checking.

Validate that the service account has all required API scopes.

Option Required Description
--creds_path Yes Path to the service account credentials JSON file
--workspace_admin Yes Email of workspace admin to impersonate
--config No Path to config YAML (default: config.yaml)
--verbose or -v No Enable verbose console logging
--debug_api No Enable detailed API request/response logging
cleanup (deprecated)

Deprecated: Use migrate --complete instead.

Complete import mode on spaces that are stuck.

Option Required Description
--creds_path Yes Path to the service account credentials JSON file
--workspace_admin Yes Email of workspace admin to impersonate
--config No Path to config YAML (default: config.yaml)
--yes or -y No Skip the confirmation prompt
--verbose or -v No Enable verbose console logging
--debug_api No Enable detailed API request/response logging

Logging and Debug Options

The migration tool provides two levels of debug logging:

  • --verbose / -v: Enables verbose console output showing DEBUG level messages. Useful for understanding the migration flow and troubleshooting issues.
  • --debug_api: Enables detailed HTTP API request/response logging to files. This creates very large log files but is invaluable for diagnosing API-related issues or developing the tool. Only enable this when specifically needed.

Both options are independent and can be used together for maximum debugging information.

Note: The --skip_permission_check option (on migrate) bypasses validation of service account permissions. Only use this if you're certain your service account is properly configured and you're encountering false positives in the permission check.

Examples

# One-time GCP setup (interactive wizard)
slack-chat-migrator setup

# Generate config.yaml from your Slack export
slack-chat-migrator init --export_path ./slack_export

# Validate export data without making changes (no credentials needed)
slack-chat-migrator validate \
  --export_path ./slack_export

# Validate with credentials (also tests impersonation permissions)
slack-chat-migrator validate \
  --creds_path /path/to/key.json \
  --export_path ./slack_export \
  --workspace_admin admin@company.com

# Execute the full migration
slack-chat-migrator migrate \
  --creds_path /path/to/key.json \
  --export_path ./slack_export \
  --workspace_admin admin@company.com

# Resume an interrupted migration
slack-chat-migrator migrate \
  --creds_path /path/to/key.json \
  --export_path ./slack_export \
  --workspace_admin admin@company.com \
  --resume

# Complete import mode on stuck spaces (no export needed)
slack-chat-migrator migrate \
  --creds_path /path/to/key.json \
  --workspace_admin admin@company.com \
  --complete

# Debug a problematic migration with detailed logging
slack-chat-migrator migrate \
  --creds_path /path/to/key.json \
  --export_path ./slack_export \
  --workspace_admin admin@company.com \
  --verbose --debug_api

Migration Workflow

For a successful migration, follow this recommended workflow:

Note: Using a Python virtual environment is recommended for Python package dependencies, but the Google Cloud SDK must be installed as a system component outside of any virtual environment.

  1. Set up GCP permissions (one-time, interactive wizard):

    pip install "slack-chat-migrator[setup]"
    slack-chat-migrator setup
    

    The wizard walks you through creating a GCP project, enabling APIs, creating a service account, and downloading credentials. After the wizard, complete domain-wide delegation in Google Workspace Admin Console as instructed.

    Alternative: You can also use the setup_permissions.sh script or set up permissions manually (see Manual Google Cloud Setup below).

  2. Generate config from your export (interactive):

    slack-chat-migrator init --export_path ./slack_export
    

    The init command analyses your Slack export and walks through channel selection, user mapping, and error handling preferences to generate a config.yaml file.

    Alternative: Copy config.yaml.example and edit manually.

  3. Run comprehensive validation (automatically performed before every migration):

    # Quick validation (no credentials needed):
    slack-chat-migrator validate \
      --export_path ./slack_export
    
    # Full validation with permission testing:
    slack-chat-migrator validate \
      --creds_path /path/to/credentials.json \
      --export_path ./slack_export \
      --workspace_admin admin@domain.com
    

    The validation identifies potential issues before any changes are made:

    • Validates all user mappings and detects unmapped users
    • Checks file attachments and permissions
    • Verifies channel structure and memberships
    • Tests message formatting and content
    • Estimates migration scope and requirements
  4. Execute the migration (validation runs automatically first):

    # The migration process includes automatic validation:
    # Step 1: Comprehensive validation (dry run)
    # Step 2: User confirmation to proceed
    # Step 3: Actual migration
    
    slack-chat-migrator migrate \
      --creds_path /path/to/credentials.json \
      --export_path ./slack_export \
      --workspace_admin admin@domain.com
    
  5. If migration is interrupted (optional):

    # Resume migration from where it left off
    slack-chat-migrator migrate \
      --creds_path /path/to/credentials.json \
      --export_path ./slack_export \
      --workspace_admin admin@domain.com \
      --resume
    

    Resume mode will find existing spaces and only import messages that are newer than the last message in each space. This approach is simple and reliable but has a known limitation: thread replies to older messages may be posted as new standalone messages instead of being properly threaded.

    If multiple Google Chat spaces exist with the same name (e.g., multiple "Slack #general" spaces), the tool will detect this conflict and provide guidance. See Space Mapping above.

  6. If spaces are stuck in import mode (optional):

    # Complete import mode on stuck spaces without needing the export
    slack-chat-migrator migrate \
      --creds_path /path/to/credentials.json \
      --workspace_admin admin@domain.com \
      --complete
    

Migration Process and Cleanup

Per-Channel Process

The migration processes each channel through the following stages:

flowchart TD
    A[Create Space in Import Mode] --> B[Add Historical Members]
    B --> C[Post Channel Intro\npurpose / topic]
    C --> D[Import Messages\nattachments & reactions]
    D --> E{Errors?}
    E -->|No| F[Complete Import Mode]
    E -->|Yes| G{import_completion_strategy}
    G -->|skip_on_error| H[Leave in Import Mode]
    G -->|force_complete| F
    F --> I[Add Regular Members]
    I --> J[Channel Complete]
    H --> K[Channel Skipped\nneeds cleanup]
  1. Create Space: Creates a Google Chat space in import mode
  2. Add Historical Members: Adds users who were in the Slack channel (with createTime/deleteTime for accurate membership history)
  3. Send Intro: Posts channel metadata (purpose/topic) as the first message
  4. Import Messages: Migrates all messages with their attachments and reactions
  5. Complete Import: Finishes the import mode for the space
  6. Add Regular Members: Adds all members back to the space as regular members

Error Handling

The tool provides several configurable options for handling errors during migration:

  1. Abort on Error: When enabled (abort_on_error: true), the migration will stop after encountering errors in a channel. When disabled (default), the migration will continue processing other channels even if errors occur.

  2. Maximum Failure Percentage: Controls how many message failures are tolerated within a channel before skipping the rest of that channel (max_failure_percentage: 10 by default). If the failure rate exceeds this percentage, the channel processing will stop.

  3. Import Completion Strategy: Determines how to handle import mode completion when errors occur:

    • skip_on_error (default): Don't complete import mode if there were errors
    • force_complete: Complete import mode even if there were errors
  4. Cleanup on Error: When enabled (cleanup_on_error: true), spaces with errors will be deleted during cleanup. When disabled (default), spaces with errors will be kept (allowing manual completion).

  5. API Retry Settings: Configure how API calls are retried when errors occur:

    • max_retries: 3 (default): Maximum number of retry attempts for failed API calls
    • retry_delay: 2 (default): Initial delay in seconds between retry attempts

These options can be configured in your config.yaml file:

# Error handling configuration
abort_on_error: false
max_failure_percentage: 10
import_completion_strategy: "skip_on_error"
cleanup_on_error: false

# API retry settings
max_retries: 3
retry_delay: 2

Cleanup Process

After all channels are processed, a cleanup process runs to ensure all spaces are properly out of import mode. This cleanup:

  1. Lists all spaces created by the migration tool
  2. Identifies any spaces still in "import mode" that weren't properly completed
  3. Completes the import mode for these spaces with retry logic
  4. Preserves external user access settings where applicable
  5. Adds regular members to these spaces

The cleanup process is important because spaces in import mode have limitations and will be automatically deleted after 90 days if not properly completed.

Checkpoint and Resumption

The migration tool writes a checkpoint file (.migration_checkpoint.json) in the Slack export directory to track progress. This file records:

  • Which channels have been fully processed (with completion timestamps)
  • When the migration started
  • When the checkpoint was last updated

If a migration is interrupted (e.g., by a crash or Ctrl+C), the checkpoint allows the tool to skip already-completed channels on the next run. The checkpoint file is automatically removed after a successful migration completes.

Note: The checkpoint tracks channel-level progress only. If a migration is interrupted mid-channel, that channel will be reprocessed from the beginning on the next run.

Output Directory and Log Files

The migration tool automatically creates a timestamped output directory for each migration run to store logs, reports, and other output files:

migration_logs/
├── run_20250806_153200/          # Timestamped run directory
│   ├── migration.log             # Main migration log
│   ├── migration_report.yaml     # Summary report
│   ├── channel_logs/            # Per-channel detailed logs
│   │   ├── general_migration.log
│   │   └── random_migration.log
│   └── failed_messages.txt       # Failed messages (if any)

Log File Types:

  • migration.log: Main log file containing overall migration progress, errors, and system messages
  • channel_logs/*.log: Per-channel detailed logs with message-level details (when --debug_api is enabled)
  • migration_report.yaml: Structured summary report with statistics and recommendations
  • failed_messages.txt: Details of any messages that failed to migrate (created only if there are failures)

Note: When using --debug_api, channel logs can become quite large as they include complete API request/response data.

Migration Reports

The tool generates comprehensive reports in both validation mode and after actual migrations:

  1. Validation Report: Generated when running with the --dry_run flag, shows comprehensive validation results including:

    • User mapping validation and unmapped user detection
    • File attachment accessibility checks
    • Channel structure verification
    • Message formatting validation
    • Migration scope estimation
  2. Migration Summary: Generated after a real migration, shows what actually happened

The reports include:

  1. Channels: Which channels were/will be processed and how many spaces were/will be created
  2. Messages: Count of messages and reactions migrated/to be migrated
  3. Files: Count of files uploaded/to be uploaded
  4. Users:
    • External emails detected and suggested mappings
    • Users without email addresses that need mapping
  5. Recommendations: Actionable suggestions to improve the migration

Example report:

report_type: dry_run  # or migration_summary
timestamp: "2023-06-26T17:54:05.596Z"
workspace_admin: admin@company.com
export_path: /path/to/export
channels:
  to_process:
  - general
  - random
  total_count: 2
  spaces_to_create: 2
messages:
  to_create: 1250
  reactions_to_add: 78
files:
  to_upload: 15
users:
  external_emails:
    personal@gmail.com: personal@company.com
  external_email_count: 1
  users_without_email:
    U12345678:
      name: slackbot
      real_name: Slackbot
      type: Bot
      suggested_email: slackbot@company.com
  users_without_email_count: 1
recommendations:
- type: users_without_email
  message: Found 1 users without email addresses. Add them to user_mapping_overrides in your config.yaml.
  severity: warning
- type: external_emails
  message: Found 1 external email addresses. Consider mapping them to internal workspace emails using user_mapping_overrides in your config.yaml.
  severity: info

User Mapping

The tool maps Slack users to Google Workspace users in several ways:

  1. Automatic mapping: Uses the email addresses from Slack's users.json file
  2. Domain override: Replaces the domain of all email addresses with a specified domain
  3. User mapping overrides: Manually map specific Slack user IDs to Google Workspace emails

When users sign up for Slack with personal emails (like personal@gmail.com) but have a corresponding internal workspace email (like work@company.com), or when bots/integrations don't have email addresses, you can map them using user_mapping_overrides.

To identify users that need mapping:

  1. Run comprehensive validation to generate a report:

    slack-chat-migrator validate \
      --export_path ./slack_export
    

    This validates user mappings, file access, and content formatting. No credentials are needed for validation.

  2. Review the validation report and add any required mappings to your config.yaml file under user_mapping_overrides

  3. Run the migration with the updated config (validation runs automatically first)

Known Limitations

Google Chat Import API Constraints

These are limitations of the Google Chat Import API itself, not specific to this tool:

  • 90-day import mode limit — spaces left in import mode for more than 90 days are automatically deleted by Google
  • No link previews — URLs in imported messages don't generate link previews
  • No duplicate createTime — two messages in the same space cannot have the same createTime timestamp; the tool handles this by incrementing timestamps when collisions occur
  • No notifications during import — users don't receive any notifications for messages imported in import mode
  • External user limitations — external users (outside your Google Workspace domain) cannot be impersonated via domain-wide delegation; their messages are attributed to the workspace admin with sender annotation
  • No native attachments — the Import API doesn't support native file attachments on messages; files are uploaded to Google Drive and linked in message text (this is Google's recommended approach for imported content)

Tool-Specific Limitations

  • Thread Continuity in Resume Mode: When using --resume to resume an interrupted migration, messages that are part of threads started in the previous migration may not be correctly threaded with their parent thread. This occurs because the tool only imports messages newer than the last message in each space, and thread replies to older messages are posted as new standalone messages instead of being properly attached to their original thread context.

  • Limited External User Support: The migration tool has several limitations when dealing with external users (users outside your Google Workspace domain):

    • External users cannot be impersonated due to Google Chat API restrictions, so their messages are posted by the workspace admin with attribution text indicating the original sender
    • Emoji reactions from external users are dropped and not migrated
    • External users are not automatically added to migrated spaces — only internal workspace users receive space memberships during migration
  • Attachment Handling: When Slack attachment files are uploaded to Google Drive during migration, a link to the Google Drive file is appended to the end of the message content rather than being attached as a native Google Chat attachment. This preserves access to the files but changes how they appear in the migrated conversations.

  • Formatting Limitations: Caveats related to migrating Markdown formatting from Slack to Google Chat, including:

    • Nested bullet lists may not indent correctly in Google Chat, causing subbullets to appear as manually indented bullets that do not wrap correctly.
    • Bold styling around user mentions (e.g., *<@USER>*) is not supported by Google Chat and will display literal asterisks.

Troubleshooting

Google Cloud SDK Issues

  • Error: "No matching distribution found for google-cloud-sdk":

    • The Google Cloud SDK cannot be installed via pip in a virtual environment
    • Install the SDK using system package managers:
    • After installation, run gcloud init to configure your environment
  • Permission denied when running setup_permissions.sh:

    • Make the script executable: chmod +x setup_permissions.sh
    • Run as: ./setup_permissions.sh

Manual Google Cloud Setup (Without Using the Script)

If you prefer not to use the setup script, follow these steps manually:

  1. Enable required APIs in Google Cloud Console:

    • Go to Google Cloud Console
    • Navigate to "APIs & Services" > "Library"
    • Search for and enable these APIs:
      • Google Chat API
      • Google Drive API
      • Admin SDK API
  2. Create a Service Account:

    • Go to "IAM & Admin" > "Service Accounts"
    • Click "Create Service Account"
    • Give it a name (e.g., "slack-chat-migrator")
    • No project-level IAM roles are needed (permissions come from delegation)
  3. Create and Download a Key:

    • In the service account details page, go to the "Keys" tab
    • Click "Add Key" > "Create new key"
    • Select JSON format and download it
    • Save this file as slack-chat-migrator-sa-key.json in your project directory
  4. Configure the Chat App:

    • Go to the Chat API Configuration page in the GCP Console
    • Set an App name (e.g. "Slack Migrator")
    • Set Avatar URL (e.g. https://developers.google.com/chat/images/quickstart-app-avatar.png)
    • Set Description (e.g. "Slack to Google Chat migration")
    • Leave Interactive features disabled (the migration uses server-to-server API calls, not a bot)
    • Click Save
  5. Set Up Domain-Wide Delegation:

    • Go to your Google Workspace Admin Console
    • Navigate to Security > API Controls > Domain-wide Delegation
    • Add a new API client with the client ID from your service account key file
    • Grant these OAuth scopes:
      • https://www.googleapis.com/auth/chat.import
      • https://www.googleapis.com/auth/chat.spaces
      • https://www.googleapis.com/auth/chat.messages
      • https://www.googleapis.com/auth/chat.spaces.readonly
      • https://www.googleapis.com/auth/chat.memberships.readonly
      • https://www.googleapis.com/auth/drive

Migration Issues

  • Permission Errors during migration:

    • Ensure the service account has proper domain-wide delegation configured
    • Check that all required APIs are enabled
    • Verify your config.yaml has the correct service account key file path
    • Run slack-chat-migrator validate --creds_path ... --workspace_admin ... to validate permissions
  • Files/Attachments Not Migrating:

    • Ensure you have the drive scope in your service account permissions
    • Check for errors in the migration log related to file access
    • Verify shared drive settings if using a shared drive for storage

Project Structure

src/slack_chat_migrator/
├── __init__.py                    # Package initialization and version
├── __main__.py                    # Entry point (python -m slack_chat_migrator)
├── constants.py                   # Shared constants
├── exceptions.py                  # Custom exception types
├── types.py                       # Shared type definitions
├── cli/                           # CLI entry points and report generation
│   ├── commands.py                # CLI facade — re-exports from sub-modules
│   ├── common.py                  # Shared CLI infrastructure (DefaultGroup, options)
│   ├── init_cmd.py                # init command (interactive config generator)
│   ├── migrate_cmd.py             # migrate command and MigrationOrchestrator
│   ├── setup_cmd.py               # setup command (GCP setup wizard)
│   ├── validate_cmd.py            # validate command
│   ├── cleanup_cmd.py             # cleanup command (deprecated)
│   ├── permissions_cmd.py         # check-permissions command (deprecated)
│   ├── renderers/                 # Terminal output renderers
│   │   ├── plain_renderer.py      # Plain text renderer (non-TTY)
│   │   └── rich_renderer.py       # Rich live progress renderer (TTY)
│   └── report.py                  # Migration report formatting
├── core/                          # Core logic
│   ├── channel_processor.py       # Per-channel migration orchestration
│   ├── checkpoint.py              # Checkpoint persistence for resumable migrations
│   ├── cleanup.py                 # Post-migration cleanup (import mode, members)
│   ├── config.py                  # YAML config loading and validation
│   ├── context.py                 # MigrationContext frozen dataclass (immutable config)
│   ├── migration_logging.py       # Migration success/failure logging
│   ├── migrator.py                # Composition root — wires all deps, owns lifecycle
│   ├── progress.py                # ProgressTracker event emitter
│   └── state.py                   # MigrationState with typed sub-states
├── services/                      # External API integrations
│   ├── chat/                      # Google Chat API
│   │   ├── chat_uploader.py       # Chat-based media upload
│   │   └── dry_run_service.py     # No-op Chat API for dry-run mode
│   ├── chat_adapter.py            # Typed wrapper over raw Chat API service
│   ├── drive/                     # Google Drive API
│   │   ├── drive_uploader.py      # Drive file upload logic
│   │   ├── dry_run_service.py     # No-op Drive API for dry-run mode
│   │   ├── folder_manager.py      # Drive folder creation and management
│   │   └── shared_drive_manager.py # Shared drive creation and management
│   ├── drive_adapter.py           # Typed wrapper over raw Drive API service
│   ├── export_inspector.py        # Slack export analysis (channel/user/message stats)
│   ├── files/                     # Slack file handling
│   │   ├── file.py                # FileHandler class (delegates to download/permissions)
│   │   ├── file_download.py       # Slack file download logic
│   │   └── file_permissions.py    # Drive file ownership/sharing
│   ├── messages/                  # Message migration pipeline
│   │   ├── message_attachments.py # Attachment processing
│   │   ├── message_builder.py     # Message payload construction (Slack → Chat format)
│   │   ├── message_sender.py      # Message send logic, error handling, stats
│   │   └── reaction_processor.py  # Batch reaction processing
│   ├── setup/                     # GCP setup wizard services
│   │   ├── api_enablement.py      # Enable required Google APIs
│   │   ├── delegation.py          # Test domain-wide delegation
│   │   ├── gcp_project.py         # GCP project creation/selection
│   │   ├── service_account.py     # Service account creation and key management
│   │   └── setup_service.py       # Setup state persistence and orchestration
│   ├── spaces/                    # Space lifecycle management
│   │   ├── discovery.py           # Space discovery and mapping for resumption
│   │   ├── historical_membership.py # Historical member import (createTime/deleteTime)
│   │   ├── regular_membership.py  # Regular member addition (post-import)
│   │   └── space_creator.py       # Space creation, listing, import mode cleanup
│   ├── user.py                    # User mapping (Slack → Google)
│   └── user_resolver.py           # User identity resolution and impersonation
└── utils/                         # Shared utilities
    ├── api.py                     # API retry logic, credential handling
    ├── formatting.py              # Message formatting utilities
    ├── logging.py                 # Logging setup and utilities
    ├── mime.py                    # MIME type detection
    ├── permissions.py             # Permission validation
    └── user_validation.py         # User data validation
tests/
├── unit/                          # Fast, isolated tests
└── integration/                   # Tests requiring external services

Setting Up Permissions

Before running your first migration, you need to set up the Google Cloud permissions. The recommended approach is the interactive setup command:

pip install "slack-chat-migrator[setup]"
slack-chat-migrator setup

The wizard guides you through six steps:

  1. GCP project — create or select a project
  2. Enable APIs — enable Chat, Drive, and Admin APIs
  3. Service account — create a service account for delegation
  4. Download key — download credentials JSON (saved with restricted permissions)
  5. Configure Chat app — set up the Chat app in GCP Console (required by the Chat API)
  6. Test delegation — verify domain-wide delegation works

Progress is saved between runs, so you can resume if interrupted.

Alternative approaches:

  • Use the setup_permissions.sh script (requires Google Cloud SDK installed as a system component)
  • Follow the manual setup steps in the Troubleshooting section

Note: After any setup method, you still need to complete domain-wide delegation in your Google Workspace Admin Console.

License

MIT

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

slack_chat_migrator-0.4.0.tar.gz (182.7 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

slack_chat_migrator-0.4.0-py3-none-any.whl (197.6 kB view details)

Uploaded Python 3

File details

Details for the file slack_chat_migrator-0.4.0.tar.gz.

File metadata

  • Download URL: slack_chat_migrator-0.4.0.tar.gz
  • Upload date:
  • Size: 182.7 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for slack_chat_migrator-0.4.0.tar.gz
Algorithm Hash digest
SHA256 063742c95f39b3eb756dbdc8ab040facb056dcacff3eec4222c6d5103c96ae06
MD5 e0b987bf6f3a7356377c3438172d682e
BLAKE2b-256 962ca62a500e38cb914c3b83d26ef0ef8931a0c2f8975077405305816b61b43f

See more details on using hashes here.

Provenance

The following attestation bundles were made for slack_chat_migrator-0.4.0.tar.gz:

Publisher: python-publish.yml on nicklamont/slack-chat-migrator

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file slack_chat_migrator-0.4.0-py3-none-any.whl.

File metadata

File hashes

Hashes for slack_chat_migrator-0.4.0-py3-none-any.whl
Algorithm Hash digest
SHA256 254a2ffc32154f66a30494da549509bacfee16a0813789e5b4c1cc712cec968a
MD5 d7c50a041b3b83ed0496c02bcd311906
BLAKE2b-256 0699256e7c656706e16376c87de654c1a3668864a8c8f4a628279d1a80db6f4c

See more details on using hashes here.

Provenance

The following attestation bundles were made for slack_chat_migrator-0.4.0-py3-none-any.whl:

Publisher: python-publish.yml on nicklamont/slack-chat-migrator

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page