Skip to content

Instantly share code, notes, and snippets.

@schanjr
Created May 27, 2024 21:55
Show Gist options
  • Save schanjr/6b9fea1f3c82778aa7358f8ac86b49c9 to your computer and use it in GitHub Desktop.
Save schanjr/6b9fea1f3c82778aa7358f8ac86b49c9 to your computer and use it in GitHub Desktop.
Migrate Bitbucket Repositories Under Project Keys to Github
#!/bin/bash
# Configuration
### Bitbucket configs
BITBUCKET_USERNAME="<fill this out>"
BITBUCKET_WORKSPACE="<fill this out>"
# Visit https://bitbucket.org/account/settings/app-passwords/
BITBUCKET_APP_PASSWORD="<fill this out>"
### Github Configs
GITHUB_USERNAME="<fill this out>"
# Visit https://github.com/settings/tokens
GITHUB_TOKEN="<fill this out>"
GITHUB_ORG="<fill this out>" # Or your GitHub username if not using an organization
# Directories
LOCAL_CLONE_DIR="./cloned_repos"
# Create directory for cloned repositories if it does not exist
mkdir -p "$LOCAL_CLONE_DIR"
# Function to list Bitbucket repositories for a given project key
list_bitbucket_repos() {
local project_key=$1
local url="https://api.bitbucket.org/2.0/repositories/$BITBUCKET_WORKSPACE"
local repos=()
local params="q=project.key=\"$project_key\""
while [ -n "$url" ]; do
response=$(curl -s -u "$BITBUCKET_USERNAME:$BITBUCKET_APP_PASSWORD" "$url" --get --data-urlencode "$params")
repos+=($(echo "$response" | jq -r '.values[].name'))
url=$(echo "$response" | jq -r '.next // empty')
done
echo "${repos[@]}"
}
# Function to clone a repository from Bitbucket
clone_repository() {
local repo_url=$1
local local_path=$2
if [ -d "$local_path" ]; then
echo "Repository already exists locally at $local_path, skipping clone."
else
echo "Cloning repository $repo_url into $local_path"
git clone "$repo_url" "$local_path" || { echo "Error cloning repository $repo_url"; return 1; }
fi
}
# Function to create a new GitHub repository
create_github_repo() {
local repo_name=$1
local project_key=$2
local payload="{\"name\":\"${project_key}-${repo_name}\",\"private\":true}"
local url="https://api.github.com/user/repos"
response=$(curl -s -o /dev/null -w "%{http_code}" -H "Authorization: token $GITHUB_TOKEN" -H "Content-Type: application/json" -d "$payload" "$url")
if [ "$response" -eq 201 ]; then
echo "Successfully created GitHub repository ${project_key}-${repo_name}"
elif [ "$response" -eq 422 ]; then
echo "GitHub repository ${project_key}-${repo_name} already exists, skipping creation."
else
echo "Error creating GitHub repository ${project_key}-${repo_name}: HTTP $response"
return 1
fi
}
# Function to push a local repository to GitHub
push_to_github() {
local local_repo_path=$1
local github_repo_url=$2
cd "$local_repo_path" || { echo "Error accessing local repository $local_repo_path"; return 1; }
git remote rm origin
git remote add origin "$github_repo_url"
git push -u origin --all || { echo "Error pushing repository $local_repo_path to $github_repo_url"; return 1; }
cd - > /dev/null
}
# Main migration function
migrate_repositories() {
local project_key=$1
local repos=$(list_bitbucket_repos "$project_key")
for repo_name in $repos; do
local bitbucket_repo_url="https://$BITBUCKET_USERNAME:[email protected]/$BITBUCKET_WORKSPACE/$repo_name.git"
local local_repo_path="$LOCAL_CLONE_DIR/$repo_name"
local github_repo_url="https://$GITHUB_USERNAME:[email protected]/$GITHUB_ORG/${project_key}-${repo_name}.git"
# Clone repository from Bitbucket
clone_repository "$bitbucket_repo_url" "$local_repo_path"
if [ $? -ne 0 ]; then
continue
fi
# Create repository on GitHub
create_github_repo "$repo_name" "$project_key"
if [ $? -ne 0 ]; then
continue
fi
# Push repository to GitHub
push_to_github "$local_repo_path" "$github_repo_url"
if [ $? -ne 0 ]; then
continue
fi
done
}
# Run the migration
# Ex: bash -x migrate_bb_github.sh <Bitbucket-ProjectKey>
migrate_repositories "$1"
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment