@@ -56,6 +56,14 @@ variables:
5656 value : next
5757 ${{ else }} :
5858 value : latest
59+ - name : AzureArtifactsFeedUrl
60+ value : ' https://pkgs.dev.azure.com/azure-public/vside/_packaging/python-environments/npm/registry/'
61+ # Same URL without the https:// prefix (used in .npmrc auth lines)
62+ - name : AzureArtifactsFeedUrlNoProtocol
63+ value : ' pkgs.dev.azure.com/azure-public/vside/_packaging/python-environments/npm/registry/'
64+ # Managed Identity service connection for Azure Artifacts auth (shared with Pylance)
65+ - name : AzureServiceConnection
66+ value : ' PylanceSecureVsIdePublishWithManagedIdentity'
5967
6068extends :
6169 template : azure-pipelines/MicroBuild.1ES.Official.yml@MicroBuildTemplate
@@ -97,30 +105,66 @@ extends:
97105 targetFolder : $(Build.ArtifactStagingDirectory)
98106
99107 - stage : Publish
100- displayName : Publish to npm
108+ displayName : Publish to Azure Artifacts
101109 dependsOn : Build
102110 condition : and(succeeded(), eq('${{ parameters.publishPackage }}', 'true'))
103111 jobs :
104112 - job : PublishPackage
105113 displayName : Publish $(PackageName)
106- steps :
107- - task : DownloadPipelineArtifact@2
108- displayName : Download build artifact
109- inputs :
114+ templateContext :
115+ type : releaseJob
116+ isProduction : true
117+ inputs :
118+ - input : pipelineArtifact
110119 artifactName : npm-package
111- targetPath : $(Build.ArtifactStagingDirectory)/npm-package
120+ targetPath : $(Pipeline.Workspace)/npm-package
121+ steps :
122+ - checkout : none
112123
113124 - task : NodeTool@0
114125 inputs :
115126 versionSpec : ' 22.21.1'
116127 displayName : Select Node version
117128
118- - bash : echo '//registry.npmjs.org/:_authToken=${NODE_AUTH_TOKEN}' > .npmrc
119- workingDirectory : $(Build.SourcesDirectory)/pythonEnvironmentsApi
120- displayName : Configure npm auth
121-
122- - bash : npm publish $(Build.ArtifactStagingDirectory)/npm-package/*.tgz --tag $(npmTag) --access public --ignore-scripts
123- displayName : Publish to npm (${{ parameters.quality }})
124- workingDirectory : $(Build.SourcesDirectory)/pythonEnvironmentsApi
129+ # Acquire a short-lived AAD token via Managed Identity (no stored secrets)
130+ # SEE https://eng.ms/docs/cloud-ai-platform/devdiv/one-engineering-system-1es/1es-docs/1es-security-configuration/configuration-guides/pat-burndown-guidance
131+ - task : AzureCLI@2
132+ displayName : Acquire AAD token via Managed Identity
133+ inputs :
134+ azureSubscription : ' $(AzureServiceConnection)'
135+ scriptType : ' pscore'
136+ scriptLocation : ' inlineScript'
137+ inlineScript : |
138+ $token = az account get-access-token --query accessToken --resource 499b84ac-1321-427f-aa17-267ca6975798 -o tsv
139+ Write-Host "##vso[task.setvariable variable=AzdoToken;issecret=true]$token"
140+
141+ - powershell : |
142+ @"
143+ registry=$(AzureArtifactsFeedUrl)
144+ always-auth=true
145+ "@ | Out-File -FilePath .npmrc
146+
147+ @"
148+ ; begin auth token
149+ //$(AzureArtifactsFeedUrlNoProtocol):username=VssSessionToken
150+ //$(AzureArtifactsFeedUrlNoProtocol):_authToken=$env:AZDO_TOKEN
151+ //$(AzureArtifactsFeedUrlNoProtocol):email=not-used@example.com
152+ ; end auth token
153+ "@ | Out-File -FilePath $HOME/.npmrc
125154 env:
126- NODE_AUTH_TOKEN : $(NpmAuthToken)
155+ AZDO_TOKEN: $(AzdoToken)
156+ displayName: Create .npmrc files
157+
158+ - powershell : |
159+ $tgz = Get-ChildItem "$(Pipeline.Workspace)/npm-package/*.tgz" | Select-Object -First 1
160+ if (-not $tgz) {
161+ Write-Error "No .tgz file found in $(Pipeline.Workspace)/npm-package/"
162+ exit 1
163+ }
164+ Write-Host "Publishing: $($tgz.FullName)"
165+ if ("$(npmTag)" -eq "next") {
166+ npm publish $tgz.FullName --registry $(AzureArtifactsFeedUrl) --tag next --ignore-scripts
167+ } else {
168+ npm publish $tgz.FullName --registry $(AzureArtifactsFeedUrl) --ignore-scripts
169+ }
170+ displayName: npm publish (${{ parameters.quality }})
0 commit comments