Another issue with Runbook step renaming and versioning strategy

Similar to This incident. We have a self-hosted Octopus server version 2021.3.8275. A user renamed a step in a runbook and the channels are no longer accessible. Via the api we can get to the project api/projects/Projects-4562 but not the project channels api/projects/Projects-4562/channels. The response to the channels is:
Looking at the channels in the database this is the json for one of them (outside of the tag they are identical)

UpdateNewIndex is the name of the RunBook that had the step renamed. The user is telling me that the package used in the runbook step that was renamed is different from the package used in the channel versioning, however I am unable to verify that.

To fix this last time we reset the DeploymentSettings for the project. What is the correct fix this time?



Hi @lbrody,

Thanks for reaching out on our community forum. It looks like you’ve run into the same issue posted on that help article you linked - Unable to load project after renaming runbook step if the step uses the same package as the step used for versioning strategy · Issue #7230 · OctopusDeploy/Issues · GitHub.

You should be able to fix this issue by resetting the deployment settings just as you have done previously.

The below script is designed to create a new project, copy the deployment settings, refactor those settings to match the broken project, PUT the refactored deployment settings over the broken project, and delete the newly created project.

The following variables are required to have their values modified:

$octopusURL - Your Octopus hostname
$octopusAPIKey - An API key for an account with access to create, edit and delete projects.
$spaceId - The ID of the space the project with the error is in. (example: Spaces-1)
$projectGroupName - A project group name that exists on the space provided in $spaceId.
$lifecycleName - A lifecycle name that exists on the space provided in $spaceId.
$brokenProjectId - The Id of the project experiencing the error. (example: Projects-1042)

The following variables can optionally have their values changed:

$newProjectName, $newProjectDescription - The name and description of the newly created project from which the deployment settings are taken (the project is deleted afterward anyway).

# Create Script Variables
$octopusUrl = "https://OctopusURL"
$header = @{ "X-Octopus-ApiKey" = $octopusAPIKey }

# Case Specific Variables | Customise Lifecycle Name and Project Group if necessary.
$spaceId = "Spaces-1"
$newProjectName = "Project_For_Template"
$newProjectDescription = "Project created for version template to fix broken references. Will be deleted after."
$projectGroupName = "Default Project Group"
$lifecycleName = "Default lifecycle"

$brokenProjectId = "Projects-XX"

# Get Project Group Id
$projectGroup = (Invoke-RestMethod -Method Get "$octopusURL/api/$($spaceId)/projectgroups/all" -Headers $header) | Where-Object {$_.Name -eq $projectGroupName}

# Get Lifecycle Id
$lifeCycle = (Invoke-RestMethod -Method Get "$octopusURL/api/$($spaceId)/lifecycles/all" -Headers $header) | Where-Object {$_.Name -eq $lifecycleName}

# JSON Payload for template project
$jsonPayload = @{
    Name = $newProjectName
    ProjectGroupId = $projectGroup.Id
    LifeCycleId = $lifeCycle.Id

# Create new project
$newProject = Invoke-RestMethod -Method Post -Uri "$octopusURL/api/$($spaceId)/projects" -Body ($jsonPayload | ConvertTo-Json -Depth 10) -Headers $header

# Gather deployment settings template
$depTemplate = Invoke-RestMethod -Method Get -Uri "$octopusURL$($newProject.Links.DeploymentSettings)" -Headers $header

# Copy and modify template to match broken project
$newDepSettings = $depTemplate
$newDepSettings.Id = $newDepSettings.Id.replace($newProject.Id, $brokenProjectId)
$newDepSettings.ProjectId = $newDepSettings.ProjectId.replace($newProject.Id, $brokenProjectId)

# Determine deployment settings URL for broken project
$newUrl = $newProject.Links.DeploymentSettings.replace($newProject.Id, $brokenProjectId)

# Upload newly created default deployment settings to broken project
Invoke-RestMethod -Method Put -Uri "$octopusURL$($newUrl)" -Headers $header -Body ($newDepSettings | ConvertTo-Json -Depth 10)

# Delete Template Project
Invoke-RestMethod -Method Delete -Uri "$octopusURL/api/$($spaceId)/projects/$($newProject.Id)" -Headers $header

I hope this helps! Please let me know if you have any questions or run into any issues running the script, and I’ll do my best to assist you further.

Kind Regards,

The last issue was with the versioning strategy for the project, so it made sense to me to update the DeploymentSettings. In this case it is the versioning for the channels, can you help me understand how updating the DeploymentSettings will help?

Looking at the deployment settings for the project in question. the versioning strategy is the same as a new project


Hey @lbrody,

Like with the versioning strategy, the values entered in the Channel rules cannot be found causing that error. You would need to enter blank values for that channel so it can be re-configured or deleted, and recreated. You can try to overwrite the channel settings to an empty value via the API, or that script should reset everything.

Let me know if you have additional questions.


I ran the script and replace the deployment settings on the project. This unfortunately has not fixed the problem with the channels.

Following similar logic to the script you provided I reset the channels via the api (HTTP Put) (I had the original information in the Audit trail) I left off the versioning rules when I did that and everything seems to be working now as intended.

I basically did a Get on a similar channel and replaced some of the values (many of our projects have similar structures.

For one of the channels (there were 2 affected)

    $channel = [Octo]::Get('api/Channels/Channels-3871')
    $channel.Id = 'Channels-5010'
    $channel.ProjectId = 'Projects-4562'
    $channel.LifecycleId = 'Lifecycles-4621'
    $channel.Rules = @()
    $channel.Links.Self = $channel.Links.Self.Replace('Channels-3871', 'Channels-5010')
    $channel.Links.Self = $channel.Links.Self.Replace('Projects-3661','Projects-4562')
    $channel.Links.Releases = $channel.Links.Releases.Replace('Channels-3871', 'Channels-5010')
    $channel.Links.Releases = $channel.Links.Releases.Replace('Projects-3661','Projects-4562')
    $channel.Links.Project = $channel.Links.Project.Replace('Channels-3871', 'Channels-5010')
    $channel.Links.Project = $channel.Links.Project.Replace('Projects-3661','Projects-4562')

    [Octo]::Put('api/Channels/Channels-5010', $channel)

[Octo] is a PowerShell class that we use internally that wraps the http calls and handles the header, api keys, etc.

Thanks for your help

Hey @lbrody,

I’m sorry to hear that didn’t work for you. You’ll need to overwrite the bad value in the channel to get past that error. I would run an API Put over the current channel and remove the ‘Rules’ section. The bad channel probably looks something like this:

    "Id": "Channels-103",
    "Name": "Test Channel",
    "Description": "",
    "ProjectId": "Projects-82",
    "LifecycleId": null,
    "IsDefault": false,
    "Rules": [
        "Id": "e8dfc17c-d4cc-4480-9c88-12b2a2117b17",
        "VersionRange": "",
        "Tag": "$^0",
        "ActionPackages": [
            "DeploymentAction": "Deploy to IIS",
            "PackageReference": null
        "Links": {},
        "Actions": [
          "Deploy to IIS"
    "TenantTags": [],
    "SpaceId": "Spaces-1",
    "Links": {
      "Self": "/api/Spaces-1/projects/Projects-82/channels/Channels-103",
      "Releases": "/api/Spaces-1/projects/Projects-82/channels/Channels-103/releases{?skip,take,searchByVersion}",
      "Project": "/api/Spaces-1/projects/Projects-82"

You’ll want to overwrite that with the ActionPackages like this:

    "Id": "Channels-105",
    "Name": "Test Channel2",
    "Description": "",
    "ProjectId": "Projects-82",
    "LifecycleId": null,
    "IsDefault": false,
    "Rules": [],
    "TenantTags": [],
    "SpaceId": "Spaces-1",
    "Links": {
      "Self": "/api/Spaces-1/projects/Projects-82/channels/Channels-105",
      "Releases": "/api/Spaces-1/projects/Projects-82/channels/Channels-105/releases{?skip,take,searchByVersion}",
      "Project": "/api/Spaces-1/projects/Projects-82"

Notice that the Rules is "Rules": [],
You should be able to pull all the channel info from your API, remove the Rules section, and PUT overtop of the bad data.

That should get you fixed. Let me know how you progress.


Looks like we had a similar line of thinking after that script didn’t work!! Glad you were able to figure it out. If anything else comes up, please don’t hesitate to reach out again.

Happy deployments!


This topic was automatically closed 31 days after the last reply. New replies are no longer allowed.