A tool for migrating LaunchDarkly projects from US-hosted accounts to EU-hosted ones. The supported resources include: environments, flags, segments
This tool helps you migrate your LaunchDarkly projects from US-hosted accounts (app.launchdarkly.com) to EU-hosted accounts (app.eu.launchdarkly.com). Features that are currently supported:
- Project & environment configuration and settings
- Feature flags and their configurations
- Segments and targeting rules
- Maintainer mapping acros the different account instances
root/
├── src/ # Source code
│ ├── scripts/ # Main migration scripts
│ ├── utils/ # Utility functions
│ └── types/ # TypeScript type definitions
├── config/ # Configuration files
├── data/ # Data directory
│ ├── source/ # Downloaded source project data
│ └── mappings/ # Mapping files (e.g., maintainer IDs)
- Deno installed
- If you use Homebrew:
brew install deno
- If you use Homebrew:
- LaunchDarkly API key with appropriate permissions
- US account API key for source project with at least Reader access
- EU account API key for destination project with at least Writer access
- Access to both US and EU LaunchDarkly instances
-
Create a configuration file for your API keys:
# Copy the example config file cp config/api_keys.json.example config/api_keys.json # Edit the file with your API keys # config/api_keys.json { "us_api_key": "your_us_api_key_here", "eu_api_key": "your_eu_api_key_here" }
Note: The
config/api_keys.json
file is ignored by git to prevent accidental exposure of API keys.
-
Download Source Project Data from US Instance
Download source project data to
data/source/project/SOURCE_PROJECT_KEY/
.# Using deno task (recommended) deno task source -p SOURCE_PROJECT_KEY # Or using deno run directly deno run --allow-net --allow-read --allow-write src/scripts/source.ts -p SOURCE_PROJECT_KEY
-
Create Member ID Mapping
Automatically create a mapping between US and EU member IDs based on email addresses.
# Using deno task (recommended) deno task map-members # Or using deno run directly deno run --allow-net --allow-read --allow-write src/scripts/map_members.ts
This will:
- Fetch all members from both US and EU instances
- Match members based on their email addresses
- Create a mapping file at
data/mappings/maintainer_mapping.json
- Show a summary of mapped and unmapped members
-
(Optional) Estimate Migration Time
Before running the migration, you can estimate how long it will take based on your project's size and the API rate limits:
deno task estimate -p SOURCE_PROJECT_KEY -d DESTINATION_PROJECT_KEY
This will analyze your source project and provide:
- Total estimated migration time
- Resource breakdown (flags, segments, environments)
- Time breakdown by resource type
The estimate is based on the following rate limits:
- Flag operations (create/patch): 5 requests per 10 seconds
- Segment operations: No rate limit
Note: The actual migration time may vary due to network conditions and API response times.
-
Migrate Project to EU Instance
Creates a new project in the target account or migrates resources into an existing project. If you want to preserve flag maintainers, use the
-m
flag to automatically map US maintainer IDs to their EU counterparts.# Using deno task (recommended) # To create a new project and migrate everything: deno task migrate -p SOURCE_PROJECT_KEY -d NEW_PROJECT_KEY -m # To migrate into an existing project: deno task migrate -p SOURCE_PROJECT_KEY -d EXISTING_PROJECT_KEY -m # To skip segment migration: deno task migrate -p SOURCE_PROJECT_KEY -d DESTINATION_PROJECT_KEY -m -s=false # Or using deno run directly: deno run --allow-net --allow-read --allow-write src/scripts/migrate.ts -p SOURCE_PROJECT_KEY -d DESTINATION_PROJECT_KEY -m
When migrating into an existing project:
- The script will check if the target project exists
- If it exists, it will skip project creation
- It will verify that environments in the source project exist in the target project
- Resources will only be migrated for environments that exist in both projects
- A warning will be shown for any environments that don't exist in the target project
For more information about using Deno tasks, see Using Deno Tasks below.
The project includes predefined Deno tasks for easier execution. These tasks are
configured in deno.json
and include all necessary permissions.
{
"tasks": {
"source": "deno run --allow-net --allow-read --allow-write src/scripts/source.ts",
"map-members": "deno run --allow-net --allow-read --allow-write src/scripts/map_members.ts",
"migrate": "deno run --allow-net --allow-read --allow-write src/scripts/migrate.ts",
"estimate": "deno run --allow-net --allow-read --allow-write src/scripts/estimate_time.ts"
}
}
-
source: Downloads all project data (flags, segments, environments) from the source project
- Requires network access for API calls
- Requires file system access to save downloaded data
- Creates directory structure in
data/source/project/
-
map-members: Creates a mapping between US and EU member IDs
- Fetches members from both US and EU instances
- Matches members based on email addresses
- Creates a mapping file in
data/mappings/maintainer_mapping.json
- Shows a summary of mapped and unmapped members
-
migrate: Creates a new project or migrates into an existing project
- Requires network access for API calls
- Requires file system access to read source data
- Can create a new project or use an existing one
- Verifies environment compatibility when using existing projects
- Creates flags, segments, and environments (if creating new project)
- Can optionally map US maintainer IDs to EU maintainer IDs is the mapping was done (step 2) maintainers if mapping was done
-
estimate: (Optional) Estimates the time needed for migration
- Analyzes source project to count resources
- Tests rate limits in target account
- Calculates estimated time based on resource counts and rate limits
- Shows detailed breakdown of the estimate
- Helps plan migration timing and resource allocation
Each task includes the necessary permissions:
--allow-net
: Required for API calls to LaunchDarkly--allow-read
: Required for reading local files--allow-write
: Required for writing downloaded data
These permissions are automatically included in the task definitions, so you don't need to specify them manually.
-p, --projKey
: Source project key
-o, --output
: (Optional) Output file path, defaults to "data/mappings/maintainer_mapping.json"
-p, --projKeySource
: Source project key-d, --projKeyDest
: Destination project key-m, --assignMaintainerIds
: (Optional) Whether to assign maintainer IDs from source project, defaults to false. Requires maintainer mapping to be done first.-s, --migrateSegments
: (Optional) Whether to migrate segments, defaults to true. Set to false to skip segment migration.
- The migration process is one-way and cannot be reversed automatically
- Maintainer IDs are different between US and EU instances and must be mapped
using the
map-members
script before migration - Environment names and keys must match between source and destination projects when migrating to an existing project
- The destination project can either be new or existing:
- For new projects: All environments will be created automatically
- For existing projects: Only environments that exist in both projects will be migrated
- Segment migration can be skipped using the
-s=false
flag if needed - Unbounded (big) segments are automatically skipped during migration
- The tool uses a fixed API version (20240415) which may need to be updated for future LaunchDarkly API changes
- The tool includes rate limiting to comply with LaunchDarkly API limits. This
means it can take some time before the migration script finishes executing if
there is a large number of resources to be migrated. You can use the
estimate
task to get an estimate of how long the migration will take.
-
Data Assessment
- What flags and segments need to be migrated?
- Can you use this as an opportunity to clean up unused resources?
- Experiments, guarded or randomised (percentage-based) rollouts can't be migrated while maintaining consistent variation bucketing. These types of releases should ideally be completed before the migration takes place.
-
Access and Permissions
- Do you have API access to both US and EU instances?
- Have you created the necessary API keys?
- Do you have sufficient access to create projects in the EU instance?
-
Maintainer Mapping
- Have all the members who are set as maintainers in the US account been added to the EU instance?
- Have you created the maintainer ID mapping file?
-
Timing and Execution
- When is the best time to perform the migration?
- How will you handle ongoing changes during migration?
- Do you need to maintain consistent state between two two account instances after the migration? If so, for how long?
- TypeScript types are loose due to API client limitations, particularly in
handling API responses. The tool uses
any
type in several places due to LaunchDarkly API response structure variations - Custom integrations and webhooks need to be manually reconfigured for EU endpoints after migration
- The tool does not support the migration of experiments or percentage-based rollouts while maintaining consistent variation assignment pre- & post-migration
If you came across any issues while using these migration scripts or if you have suggestions for additional enhancements, please create an issue in this repository.