Вот руководство по тому, как я помог клиенту перейти от внутреннего, на премию установки Атласского Stash для Azure DEVOPS с использованием PowerShell и Azure CLI. Не уверены, если это полезно для других, но это может в свете последнего объявления Atlassians на Прекратите свои серверные продукты к началу 2024 года. Я не уверен, что система Stash является частью этого, но вот иначе поправка.
Чтобы использовать это, вам понадобится PowerShell, Git и Azure CLI. Кроме того, нужно добавить расширение Azure DEVOPS на Azure CLI
d:\repos>az extension add --name azure-devops
Далее вам нужно сделать, это войти в свою организацию Azure DevOps и генерировать личный токен доступа (PAT). Вы можете найти это здесь: https://dev.azure.com/{your_organization}/_usersSettings/tokens
d:\repos>az devops login Token:
Вставить в PAT в подсказке «Токен», и вы вошли в DevOps через CLI.
Организация, с которой я работал, имел много проектов в Stash, с несколькими репозиториями в каждом проекте. Мне нужно только сделать это для одного проекта, поэтому не было необходимости делать это на более высоком уровне, но расширяя это, чтобы добавить функцию для обработки всех проектов в Stash, а затем добавить функцию для создания новых проектов в Azure DEVOPS Сопоставить проекты Stash должны быть незначительными изменениями. Кроме того, я не добавил никакой обработки ошибок, так что это все счастливый кодирующий путь Поэтому, если вы не уверены в вашей среде, вы, вероятно, должны добавить некоторую обработку ошибок и проверять код.
Моя первая функция предназначена для получения списка всех REPOS для проекта в Stash, используя встроенные в Stash API. Я не уверен, как это работает на разных версиях Stash, поэтому может потребоваться изменения, если у вас есть новые/старые версии. Кроме того, если у вас более 50 REPOS в проекте увеличивайте количество с предельным параметром в URL.
function GetStashReposForProject($user, $pass, $stashHost, $projectKey)
{
$pair = "$($user):$($pass)"
$encodedCreds = [System.Convert]::ToBase64String([System.Text.Encoding]::ASCII.GetBytes($pair))
$basicAuthValue = "Basic $encodedCreds"
$Headers = @{
Authorization = $basicAuthValue
}
$uri = $stashHost + "/rest/api/1.0/projects/"+ $projectKey + "/repos?limit=50"
$request = Invoke-WebRequest -Uri $uri -Headers $Headers
$repos = $request.Content | ConvertFrom-Json
return $repos.values
}
С помощью этого метода мы получим полную полезную нагрузку со всеми REPOS, перечисленными в рамках возвращаемой стоимости @ REPOS.Values.
Следующая функция клонирует stash Repo на рабочую станцию и устанавливает Stash $ Clone_uri в качестве пульты/начала по умолчанию. Функция создает папку для репо. Он основан на том, где вы выполняете код, поэтому убедитесь, что вы находятся на диске с достаточным количеством пространства и имеют чистую папку «root» для работы.
function CloneStashRepository($clone_url, $repo_name)
{
mkdir $repo_name
cd $repo_name
$gitclone = "/c git clone " + $clone_url + " ."
Start-Process cmd -Argument $gitclone -Wait
}
Далее нам нужна функция, которая проверяет все филиалы в репозитории, чтобы позже она может быть подтолкнута к DEVOPS.
function CheckoutAllBranches()
{
$branches = git branch --all
foreach($branch in $branches)
{
if ($branch -like "*remotes/*")
{
$branchName = $branch -replace "remotes/origin/" -replace ""
$gitCheckout = "/c git checkout " + $branchName
Start-Process cmd -Argument $gitCheckout -Wait
Write-Host('checkedout branch: '+ $branchName )
}
}
}
Теперь, когда у меня есть все филиалы для репо, локально на моей машине, мне нужно выбрать, какой проект в Azure DevOps их следует оттолкнуть.
function SelectAzureDevOpsProject($devOpsOrg)
{
$projects = $(az devops project list --org $devOpsOrg -o json) | ConvertFrom-Json
$count = 1
foreach($p in $projects.value)
{
Write-Host $count ") " $p.name
$count++
}
$index = Read-Host "Chooose project (enter number)"
#Write-Host "Selected inde is: " $index
$sp = $projects.value[$index-1]
$arr = @($sp.id, $sp.name)
Write-Host "Selected Project name: " $arr[1]
return $arr
}
Эта функция возвращает массив, который имеет GUID и имя проекта, который мы хотим использовать.
Небольшая функция обрабатывает создание нового репо в Azure DevOps
function CreateRepoInDevOpsProject($slug, $projectId, $devOpsOrg)
{
az repos create --name $slug --project $projectId --organization $devOpsOrg
}
Функция последней рабочей силы добавляет DEVOPS REPO в качестве дистанционного названия DEVOPS в локальном репозитории. Затем петли через все локальные ветви и подталкивает их к дистанционному репопсу.
function PushToDevops($orgPath, $project_name, $repo_name)
{
$projectName = [uri]::EscapeDataString($project_name)
$slug = [uri]::EscapeDataString($repo_name)
$remoteUrl = "https://$orgPath@dev.azure.com/$orgPath/$projectName/_git/$slug"
$makeRemote = git remote add devops $remoteUrl
$branches = git branch
foreach($branch in $branches)
{
$gitCheckout = "/c git push devops " + $branch
Start-Process cmd -Argument $gitCheckout -Wait
Write-Host('pushed branch: '+ $branch )
}
}
Наконец, блок кода выполняется при выполнении файла PS1.
$user = Read-Host "Enter Stash Username"
$pass = Read-Host -AsSecureString "Enter Stash Password "
$stashHost = Read-Host "http://domain:port"
$projectKey = Read-Host "Enter stash project key"
$devOpsOrg = Read-Host "https://dev.azure.com/"
$orgUri = "https://dev.azure.com/" + $devOpsOrg
$selectedDevOpsProject = SelectAzureDevOpsProject $orgUri
$selectedDevOpsProjectId = $selectedDevOpsProject[0]
$selectedDevOpsProjectName = $selectedDevOpsProject[1]
foreach($repos in GetStashReposForProject $user $pass $stashHost $projectKey -Wait)
{
$slug = $repos.slug
CloneStashRepository $repos.cloneUrl $slug -Wait
CheckoutAllBranches -Wait
CreateRepoInDevOpsProject $slug $selectedDevOpsProjectId $orgUri -Wait
PushToDevops $devOpsOrg $selectedDevOpsProjectName $slug -Wait
#Jump out of working folder and back to root so the loop know where to start.
cd ..
}
Write-Host "*********************************** IMPORT COMPLETE ***********************************"
Полный скрипт должен выглядеть что-то подобное. Вы можете скопировать код и сохранить его в файл PS1. Чтобы запустить его, вам, вероятно, нужно изменить свою политику выполнения или подписать сценарий.
function CheckoutAllBranches()
{
$branches = git branch --all
foreach($branch in $branches)
{
if ($branch -like "*remotes/*")
{
$branchName = $branch -replace "remotes/origin/" -replace ""
$gitCheckout = "/c git checkout " + $branchName
Start-Process cmd -Argument $gitCheckout -Wait
Write-Host('checkedout branch: '+ $branchName )
}
}
}
function CloneStashRepository($clone_url, $repo_name)
{
mkdir $repo_name
cd $repo_name
$gitclone = "/c git clone " + $clone_url + " ."
Start-Process cmd -Argument $gitclone -Wait
}
function PushToDevops($orgPath, $project_name, $repo_name)
{
$projectName = [uri]::EscapeDataString($project_name)
$slug = [uri]::EscapeDataString($repo_name)
$remoteUrl = "https://$orgPath@dev.azure.com/$orgPath/$projectName/_git/$slug"
$makeRemote = git remote add devops $remoteUrl
$branches = git branch
foreach($branch in $branches)
{
$gitCheckout = "/c git push devops " + $branch
Start-Process cmd -Argument $gitCheckout -Wait
Write-Host('pushed branch: '+ $branch )
}
}
function GetStashReposForProject($user, $pass, $stashHost, $projectKey)
{
$pair = "$($user):$($pass)"
$encodedCreds = [System.Convert]::ToBase64String([System.Text.Encoding]::ASCII.GetBytes($pair))
$basicAuthValue = "Basic $encodedCreds"
$Headers = @{
Authorization = $basicAuthValue
}
$uri = $stashHost + "/rest/api/1.0/projects/"+ $projectKey + "/repos?limit=50"
$request = Invoke-WebRequest -Uri $uri -Headers $Headers
$repos = $request.Content | ConvertFrom-Json
return $repos.values
}
function SelectAzureDevOpsProject($devOpsOrg)
{
$projects = $(az devops project list --org $devOpsOrg -o json) | ConvertFrom-Json
$count = 1
foreach($p in $projects.value)
{
Write-Host $count ") " $p.name
$count++
}
$index = Read-Host "Chooose project (enter number)"
#Write-Host "Selected inde is: " $index
$sp = $projects.value[$index-1]
$arr = @($sp.id, $sp.name)
Write-Host "Selected Project name: " $arr[1]
return $arr
}
function CreateRepoInDevOpsProject($slug, $projectId, $devOpsOrg)
{
az repos create --name $slug --project $projectId --organization $devOpsOrg
}
$user = Read-Host "Enter Stash Username: "
$pass = Read-Host "Enter Stash Password: "
$stashHost = Read-Host "htp://domain:port"
$projectKey = Read-Host "Enter stash project key"
$devOpsOrg = Read-Host "https://dev.azure.com/"
$orgUri = "https://dev.azure.com/" + $devOpsOrg
$selectedDevOpsProject = SelectAzureDevOpsProject $orgUri
$selectedDevOpsProjectId = $selectedDevOpsProject[0]
$selectedDevOpsProjectName = $selectedDevOpsProject[1]
foreach($repos in GetStashReposForProject $user $pass $stashHost $projectKey -Wait)
{
$slug = $repos.slug
CloneStashRepository $repos.cloneUrl $slug -Wait
CheckoutAllBranches -Wait
CreateRepoInDevOpsProject $slug $selectedDevOpsProjectId $orgUri -Wait
PushToDevops $devOpsOrg $selectedDevOpsProjectName $slug -Wait
#Jump out of working folder and back to root so the loop know where to start.
cd ..
}
Write-Host "*********************************** IMPORT COMPLETE ***********************************"
Отказ от ответственности
Все код здесь предоставляется как есть. Я несу никакой ответственности за любой ущерб, который может возникнуть, экономические и технические, если вы решите его использовать. Добавьте проверку и обработку ошибок, если вы планируете использовать это в автоматизации.
Оригинал: «https://dev.to/megatherion/migrating-repos-from-atlassian-stash-to-azure-devops-2006»