@@ -15,7 +15,6 @@ public class VersionCheckService : IVersionCheckService
1515{
1616 private const string NuGetApiUrl = "https://api.nuget.org/v3-flatcontainer/microsoft.agents.a365.devtools.cli/index.json" ;
1717 private const string PackageId = "Microsoft.Agents.A365.DevTools.Cli" ;
18- private const string UpdateCommand = "dotnet tool update -g Microsoft.Agents.A365.DevTools.Cli" ;
1918
2019 private readonly ILogger < VersionCheckService > _logger ;
2120 private readonly string _currentVersion ;
@@ -61,7 +60,10 @@ public async Task<VersionCheckResult> CheckForUpdatesAsync(CancellationToken can
6160 _logger . LogDebug ( "Running latest version: {CurrentVersion}" , _currentVersion ) ;
6261 }
6362
64- return new VersionCheckResult ( updateAvailable , _currentVersion , latestVersion , UpdateCommand ) ;
63+ // Generate update command based on whether the latest version is a preview
64+ var updateCommand = GetUpdateCommand ( latestVersion ) ;
65+
66+ return new VersionCheckResult ( updateAvailable , _currentVersion , latestVersion , updateCommand ) ;
6567 }
6668 catch ( OperationCanceledException )
6769 {
@@ -176,35 +178,54 @@ internal Version ParseVersion(string versionString)
176178 /// <summary>
177179 /// Tries to parse a semantic version string into a comparable Version object.
178180 /// Returns null if parsing fails.
179- ///
181+ ///
180182 /// Note: This parsing treats preview versions as comparable by their preview number.
181- /// For example, "1.1.0-preview.50" becomes "1.1.0.50" for comparison purposes.
182- /// This is appropriate since we're comparing preview-to-preview versions (the package is in preview).
183+ /// Handles two formats:
184+ /// - "1.1.52-preview" (version number includes preview iteration)
185+ /// - "1.1.0-preview.50" (preview number is separate)
183186 /// </summary>
184187 private Version ? TryParseVersion ( string versionString )
185188 {
186189 try
187190 {
188- // Remove any build metadata (+...) and pre-release tags (-...)
189- var cleanVersion = versionString . Split ( '+' ) [ 0 ] ; // Remove build metadata
191+ // Remove any build metadata (+...)
192+ var cleanVersion = versionString . Split ( '+' ) [ 0 ] ;
190193
191- // For preview versions, extract just the base version number
194+ // For preview versions, extract the version number
192195 if ( cleanVersion . Contains ( '-' ) )
193196 {
194197 var parts = cleanVersion . Split ( '-' ) ;
195- // Use the numeric part before the dash as base version
196- cleanVersion = parts [ 0 ] ;
198+ var baseVersion = parts [ 0 ] ; // e.g., "1.1.52" or "1.1.0"
197199
198- // If there's a preview number, append it as the fourth component
199- if ( parts . Length > 1 && parts [ 1 ] . StartsWith ( "preview." ) )
200+ // Check if there's a preview number after the dash
201+ if ( parts . Length > 1 )
200202 {
201- var previewNumber = parts [ 1 ] . Replace ( "preview." , "" ) ;
202- if ( int . TryParse ( previewNumber , out var preview ) )
203+ var previewPart = parts [ 1 ] ; // e.g., "preview" or "preview.50"
204+
205+ // Format 1: "1.1.0-preview.50" - append preview number as revision
206+ if ( previewPart . StartsWith ( "preview." ) && previewPart . Length > 8 )
207+ {
208+ var previewNumber = previewPart . Substring ( 8 ) ; // Get number after "preview."
209+ if ( int . TryParse ( previewNumber , out var preview ) )
210+ {
211+ cleanVersion = $ "{ baseVersion } .{ preview } ";
212+ }
213+ else
214+ {
215+ // If parsing fails, just use base version
216+ cleanVersion = baseVersion ;
217+ }
218+ }
219+ // Format 2: "1.1.52-preview" - version already includes iteration number
220+ else
203221 {
204- // Append preview number as revision component
205- cleanVersion = $ "{ cleanVersion } .{ preview } ";
222+ cleanVersion = baseVersion ;
206223 }
207224 }
225+ else
226+ {
227+ cleanVersion = baseVersion ;
228+ }
208229 }
209230
210231 // Ensure we have at least 3 components for Version constructor
@@ -223,6 +244,24 @@ internal Version ParseVersion(string versionString)
223244 }
224245 }
225246
247+ /// <summary>
248+ /// Generates the appropriate update command based on the version type.
249+ /// </summary>
250+ /// <param name="version">The version string to check for preview status.</param>
251+ /// <returns>The dotnet tool update command with or without --prerelease flag.</returns>
252+ private static string GetUpdateCommand ( string version )
253+ {
254+ var baseCommand = $ "dotnet tool update -g { PackageId } ";
255+
256+ // If the version contains "preview", add the --prerelease flag
257+ if ( version . Contains ( "preview" , StringComparison . OrdinalIgnoreCase ) )
258+ {
259+ return $ "{ baseCommand } --prerelease";
260+ }
261+
262+ return baseCommand ;
263+ }
264+
226265 /// <summary>
227266 /// Detects if the CLI is running in a CI/CD environment.
228267 /// </summary>
0 commit comments