migrate-group-versioning
Skill916 starsChanged 8 days agoMITView on GitHub
**WORKFLOW SKILL** — Migrate an Azure resource group from legacy to hybrid versioning mode in ASO. USE FOR: moving a group (e.g., appconfiguration, cache, network) from VersionMigrationModeLegacy to VersionMigrationModeHybrid in the code generator, updating samples, renaming CRUD tests, and re-recording sample tests. DO NOT USE FOR: adding new resources (use new-resource.instructions.md), general debugging, or code review.
- Deletes or force-pushes
In this repository8 other files it gives its agents.
- AGENTS.mdAGENTS.md
- .github/copilot-instructions.mdCopilot instructions
- create-new-resourceSkill
- create-release-notesSkill
- create-releaseSkill
- diagnosing-vcr-failuresSkill
- migrate-json-golden-testsSkill
- testing-aso-recordingsSkill
The file
We split this skill into the rules it gives an agent
12 rules. About 0 are common, 5 are distinctive, and 7 are very specific to this project.
≈0
Common · estimate
Many files like this have a rule of this kind.
≈5
Distinctive · estimate
This author's own choices. Worth a look.
7
Very specific
Tied to their project's names, files or tools. Probably skip.
- Common
- Distinctive
- Very specific
- Very specific: line 49
Run the generator to produce the new v20XXXXXX packages alongside the existing v1api20XXXXXX packages:
- Distinctive: line 57
Verify the new directories were created:
- Very specific: line 96
All other fields remain identical — only the apiVersion line changes.
- Very specific: line 104
Only perform the steps below for tests that do have v1api in the test function name, file name, or import paths:
- Very specific: line 108
If the test file name contains v1api, rename it to drop the prefix:
- Distinctive: line 130
Do this for all imports in the file that reference the migrated group's legacy version packages.
- Distinctive: line 158
If the test function was renamed in Step 4, the old recording files no longer match.
- Very specific: line 180
Run the samples tests in record mode to create (or re-record) the sample test recordings for the new v<version> sample directories:
- Distinctive: line 201
After recording, tidy the recordings:
- Distinctive: line 209
Run the full verification sequence as specified in the project's copilot instructions:
- Very specific: line 233
Don't forget subtest helper functions: If a test file has helper functions like AppConfiguration_KeyValue_v1api20240601_CRUD(tc, cs), those …
- Very specific: line 235
Check all version directories: If a group has multiple API versions (e.g., v1api20220501 and v1api20240601), create hybrid samples and …
≈ “Common” is an estimate: at least 1 in 5 of the 350,495 skill files we read have a rule of the same kind, not the same words. “Very specific” is our guess from the words: it names a file, a command, a setting or the project itself.
Files
Skill: Migrate Resource Group from Legacy to Hybrid Versioning
This skill guides the migration of an Azure resource group from VersionMigrationModeLegacy to VersionMigrationModeHybrid in Azure Service Operator. Hybrid mode generates new-style version packages (v20XXXXXX) for all resources while retaining backward-compatible v1api20XXXXXX packages for resources introduced in v2.16.0 and earlier.
Prerequisites
- You know the group name (lowercase, e.g.,
appconfiguration,cache,web) to migrate. - You can run
taskcommands from the repository root. - For re-recording sample tests, you need Azure credentials configured (
AZURE_TENANT_ID,AZURE_SUBSCRIPTION_ID, etc.).
Step-by-Step Procedure
Step 1: Update legacy.go
File: v2/tools/generator/internal/astmodel/legacy.go
Find the target group's entry in the
versionMigrationModesmap and change it fromVersionMigrationModeLegacytoVersionMigrationModeHybrid.Example:
// Before "appconfiguration": VersionMigrationModeLegacy, // After "appconfiguration": VersionMigrationModeHybrid,Add an entry to the
versionMigrationHybridReleasesmap recording the upcoming ASO release in which this migration will ship. This ensures our documentation correctly reports the newv-prefixed variants as "Next Release" until they've actually shipped, and keeps thev1api-prefixed variants marked as active (not deprecated) until then.Example:
var versionMigrationHybridReleases = map[string]string{ "appconfiguration": "v2.21.0", // next unreleased ASO version "authorization": "v2.21.0", }
Important: Both maps are sorted alphabetically. Do not reorder entries.
Step 2: Run the Code Generator
Run the generator to produce the new v20XXXXXX packages alongside the existing v1api20XXXXXX packages:
task controller:generate-typesThis creates new version directories under v2/api/<group>/ (e.g., v2/api/appconfiguration/v20220501/ alongside the existing v2/api/appconfiguration/v1api20220501/).
Verify the new directories were created:
ls v2/api/<group>/You should see both v1api* and v* directories for each version.
Step 3: Copy and Update Samples
For each existing v1api<version>/ directory under v2/samples/<group>/:
- Create a new directory named
v<version>/(dropping thev1apiprefix, sov1api20220301becomesv20220301). - Copy all YAML files from the
v1api<version>/directory to the newv<version>/directory. - Rename each file from
v1api<version>_<resource>.yamltov<version>_<resource>.yaml. - Update the
apiVersionfield in each copied YAML file from<group>.azure.com/v1api<version>to<group>.azure.com/v<version>.
Example for web group, version 20220301:
# Create new directory
mkdir -p v2/samples/web/v20220301
# Copy and rename files
cp v2/samples/web/v1api20220301/v1api20220301_serverfarm.yaml v2/samples/web/v20220301/v20220301_serverfarm.yaml
cp v2/samples/web/v1api20220301/v1api20220301_site.yaml v2/samples/web/v20220301/v20220301_site.yaml
cp v2/samples/web/v1api20220301/v1api20220301_sitessourcecontrol.yaml v2/samples/web/v20220301/v20220301_sitessourcecontrol.yamlThen edit each new file to update apiVersion:
# Before
apiVersion: web.azure.com/v1api20220301
# After
apiVersion: web.azure.com/v20220301All other fields remain identical — only the apiVersion line changes.
Tip: If a group has multiple version directories (e.g.,
v1api20220301/,v1api20230101/), repeat this for each one.
Step 4: Rename CRUD Tests
Not all CRUD test files use the v1api prefix in their names or function signatures. Many tests already use the v20* naming convention (e.g., Test_Web_Site_v20220301_CRUD). If a test file and its function names do NOT contain v1api, no renaming is needed — skip to Step 5 for that test.
Only perform the steps below for tests that do have v1api in the test function name, file name, or import paths:
4a. Rename the test file
If the test file name contains v1api, rename it to drop the prefix:
# Example
mv v2/internal/controllers/appconfiguration_keyvalue_v1api20240601_crud_test.go \
v2/internal/controllers/appconfiguration_keyvalue_v20240601_crud_test.goNote: Some test files may already use the
v20*naming in the filename even though they havev1apireferences in the code. In that case, no file rename is needed — just update the contents.
4b. Update import paths
Change Go import paths from the v1api<version> package to the v<version> package:
// Before
appconfig "github.com/Azure/azure-service-operator/v2/api/appconfiguration/v1api20220501"
// After
appconfig "github.com/Azure/azure-service-operator/v2/api/appconfiguration/v20220501"Do this for all imports in the file that reference the migrated group's legacy version packages.
4c. Update test function names (if needed)
Rename all test function names and helper function names to drop the v1api prefix from the version:
// Before
func Test_AppConfiguration_KeyValue_v1api20240601_CRUD(t *testing.T) {
// After
func Test_AppConfiguration_KeyValue_v20240601_CRUD(t *testing.T) {Also update any helper functions or subtest references within the file:
// Before
AppConfiguration_KeyValue_v1api20240601_CRUD(tc, cs)
// After
AppConfiguration_KeyValue_v20240601_CRUD(tc, cs)Note: Some tests may already use the
v20*naming in the test name even though they havev1apireferences in the code. In that case, no test function rename is needed. You can also skip Step 5 as well.
Step 5: Re-record CRUD Tests
STOP: You MUST have the following environment variables set to record the tests:
AZURE_SUBSCRIPTION_ID,AZURE_TENANT_ID, andENTRA_APP_ID. If any are missing, do not proceed because the tests will fail. Tell the user what is missing and stop the process.
If the test function was renamed in Step 4, the old recording files no longer match. Delete the old recording files and re-record the tests by running them against Azure:
# Delete old recording(s)
rm -f "v2/internal/controllers/recordings/Test_AppConfiguration_KeyValue_v1api20240601_CRUD.yaml"
# If subtests exist, delete the directory too
rm -rf "v2/internal/controllers/recordings/Test_AppConfiguration_KeyValue_v1api20240601_CRUD/"
# Re-record with the new test name
TEST_FILTER=Test_AppConfiguration_KeyValue_v20240601_CRUD task controller:test-integration-envtestThe general pattern is:
TEST_FILTER=<NewTestFunctionName> task controller:test-integration-envtestImportant: If a test function name did NOT have
v1apiin it (some groups already usedv20*naming), no re-recording is needed.
Step 6: Run the Samples Tests
Run the samples tests in record mode to create (or re-record) the sample test recordings for the new v<version> sample directories:
TEST_FILTER='Test_Samples_CreationAndDeletion/Test_<GroupNameWithLeadingCapital>*' task controller:test-samplesExamples:
# For appconfiguration
TEST_FILTER='Test_Samples_CreationAndDeletion/Test_Appconfiguration*' task controller:test-samples
# For web
TEST_FILTER='Test_Samples_CreationAndDeletion/Test_Web*' task controller:test-samples
# For cache
TEST_FILTER='Test_Samples_CreationAndDeletion/Test_Cache*' task controller:test-samplesThe test name format is Test_<GroupNameWithLeadingCapital>_<version>_CreationAndDeletion. The group name is title-cased using cases.Title(language.English), which capitalizes only the first letter (e.g., appconfiguration → Appconfiguration). For groups with dots in the name (e.g., network.frontdoor), each dot-separated segment is title-cased independently (e.g., Test_NetworkFrontdoor_v20220501_CreationAndDeletion).
After recording, tidy the recordings:
task controller:tidy-samples-recordingsStep 7: Verify
Run the full verification sequence as specified in the project's copilot instructions:
task format-code
task generator:quick-checks
task controller:quick-checks
task doc:crd-apiFix any issues and re-run from the beginning if anything fails.
Summary of Changes
| Area | What Changes |
legacy.go | Group entry: VersionMigrationModeLegacy → VersionMigrationModeHybrid; new entry in versionMigrationHybridReleases for the upcoming release |
v2/api/<group>/ | New v<version>/ directories generated alongside existing v1api<version>/ |
v2/samples/<group>/ | New v<version>/ directories with copied+updated sample YAML files |
| CRUD test files | File names, import paths, function names updated to drop v1api prefix |
| Recording files | Renamed to match updated test function names |
| Sample test recordings | New recordings created for v<version> sample directories |
Common Mistakes
- Don't forget subtest helper functions. If a test file has helper functions like
AppConfiguration_KeyValue_v1api20240601_CRUD(tc, cs), those need renaming too. - Don't modify generated files by hand.
*_gen.gofiles are regenerated bytask controller:generate-types. Only editlegacy.goand non-generated files. - Check all version directories. If a group has multiple API versions (e.g.,
v1api20220501andv1api20240601), create hybrid samples and update tests for all of them. - Recording files must match test names exactly. The test framework looks up recordings by
t.Name(). A mismatch will cause tests to re-record or fail. - Title-case the group name correctly in
TEST_FILTER. The test name usescases.Title(language.English), which only capitalizes the first letter:appconfiguration→Appconfiguration,containerservice→Containerservice.
Does it work?
Reviews from people and from AI agents that ran it: what they used it for, and whether it worked.
No reviews yet
People and AI agents can review whether this works in practice. Say what you used it for, and whether it worked.
- It worked
- Partly
- It didn't
Using an agent? It can post a review for you after it has run the file: the MCP tool registry_write, action report. How to connect one.
Your trail
Files you open will collect here, so you can find them again.
Open two or more, and you can remix the rules you like from each into one list. Kept in this browser only.
Now do this for your own.
Bring your CLAUDE.md, AGENTS.md or skills. agentleFS shows which of your rules are common, which are yours and which only fit one project, and keeps one version your agents read everywhere.

