Renaming an Azure Pipeline task in an existing Azure DevOps extension

I have many Azure DevOps Extensions. Some recent, but also tasks dating back to 2015 when the extensibility model for build tasks forst appeared. Over time much has changed in Azure Pipeline Land...

A picture of a sanding block and a dust mask, tools that one uses when renovating.
A picture of a sanding block and a dust mask, tools that one uses when renovating.
<TL;DR> It can't be done...

The biggest changes happened when we moved from UI based pipelines to YAML based pipelines. Some hidden internals of the tasks made their way into the light.

In the past a user would only see the Task's Friendly Name and Description and Team Foundation Server would keep track of the real identify of the task through its TaskID, a GUID that was never supposed to change.

See a sample below:

  "id": "3ca44a28-62de-4c60-8d77-a99065b95a8a",
  "name": "VariableSetTask",
  "friendlyName": "Set Variable",
  "description": "Sets a variable.",
  "category": "Utility",
  "author": "Jesse Houwing",

With the release of TFS 2017, tasks could be packaged into an extension which caused another identifying element to be created, the extension's publisher, extension id and the contribution ID:

{
  "manifestVersion": 1,
  "id": "jessehouwing-vsts-variable-tasks",
  "name": "Variable Toolbox",
  "version": "2.0.0",
  "publisher": "jessehouwing",
  "contributions": [
    {
      "id": "vsts-variable-set",
      "type": "ms.vss-distributed-task.task",
      "targets": [
        "ms.vss-distributed-task.tasks"
      ],
      "properties": {
        "name": "vsts-variable-set"
      }
    }
  ]
}

These elements were also hidden in the age of UI based pipelines, but also made it to the surface when YAML came around.

steps:
- task: jessehouwing.jessehouwing-vsts-variable-tasks-dev.vsts-variable-set.VariableSetTask@2

As you can see the publisher, extensionid, contributionId and TaskName are now used to reference a Task, when you insert them through the "View YAML" button:

enter image description here
Sample YAML code generated by the View YAML helper.

When using the YAML assistant this will only happen when you have 2 tasks registered in your organization that have the same TaskName property.

Because these values are now publicly visible, I've wanted to get rid of some of the bad naming I used in the past:

  • Get rid of the vsts- in the contribution-id
  • Remove Task from the TaskName property
  • Make everything lowercase to match Microsoft's own tasks
  • I'd love it even more if I could update the extensionId, which also references vsts- still.
  • And remove jessehouwing from the extensionId.

Changing names will of course have impact for existing YAML users, since all tasks are referenced by name, not by Id, but it would make my tasks easier to use for new users and for users moving from UI based pipelines to YAML.

Unfortunately, there are protections in place in the marketplace to prevent people from hijacking other people's extensions. This enforces a number of things with regards to the Task's Id: The Guid.

  • The Guid must be the same for all versions of a task published in an extension (for backwards compat one can publish a v1, v2, v3 etc in a single extension vsix so users get to choose when they move from A to B.
  • The Guid must be published in only a single public extension (no restriction applies to private extensions).
  • The Guid, for some reason, is tied to the ContributionId, whenever you change the ContributionId, you must change the TaskID.
  • You can't change the TaskID and the TaskName at the same time.

This blocks people from changing the public identity of a Task once published in an extension it seems. When you try, the marketplace will fail to validate your extension with an error message:

ERROR: Contribution Microsoft.VisualStudio.Services.TaskId.VARIABLE-TRANSFORM 
is re-using task ID of some other contribution from earlier version. 
To publish the extension, change the task ID.

or

ERROR: All the task versions belonging to Contribution variable-transform should have the same task id. 
The tasks at variable-transform/v1 (version 1.4.41) and variable-transform/v2 (version 2.0.41) do not have the same ids.

A possible workaround I see is to publish a new extension with a new Id, new Contribution Id's, new Task Ids and new TaskName, but that would require admin approval and installation of that new extension into any and all of the 6000+ users of the extension. That's an impossible ask.

I could accept that the ExtensionId is going to be impossible to fix and just add new tasks into the existing extensions, with new names, new Id's and all, but that will break the auto-update feature for all of the UI based users (I have no telemetry on how many of these there are), my guess is many, cause many of my tasks provide a UI to make working with script and command lines easier. The ability to seamlessly upgrade from one extension to the next is one of the things I've spent a lot of time on in the past. Adding aliases and sensible default values to input fields causes minimal fuss when upgrading from v1 to v2 for the Variable Tasks for example.

See the example below:

enter image description here
Changing between versions happens seamlessly

The input type changes from a input field to a dropdown, the YAML representation changes to a lower case for a number of fields and a number of new options appear based on the reflected value in the dropdown. All without the user having to do anything to get access to these new features.

If TFS/Azure DevOps doesn't recognize the Task as a new version of something in the pipeline, users of the UI based pipelines and old Release pipelines (and basically all TFVC users) will need to add a new copy of the task, copy all of the values from A to B and then remove the old task. I do not want to cause them that much pain.

I'm guessing the answer is going to be no, but have I missed any option to allow my users to seamlessly upgrade, yet allow me to keep improving the way new users have to type YAML to access these tasks? I'm not aware of any way to provide an alias identity for the Task itself (previous names, guids), nor for the contribution id... Similarly, I'm not aware of a way to get an extension containing build tasks renamed on the marketplace...

Photo credit