From 4e42d34aa90b6b8a86bd88fb05ef09a9b3bb8177 Mon Sep 17 00:00:00 2001 From: isra-fel <11371776+isra-fel@users.noreply.github.com> Date: Tue, 26 Aug 2025 02:06:38 +1000 Subject: [PATCH 1/2] Generate Generic Breaking Change Attribute --- powershell/cmdlets/class.ts | 133 ++++++++++++++++----------- powershell/llcsharp/clientruntime.ts | 2 +- 2 files changed, 78 insertions(+), 57 deletions(-) diff --git a/powershell/cmdlets/class.ts b/powershell/cmdlets/class.ts index 935214c5dd3..b2145154fd8 100644 --- a/powershell/cmdlets/class.ts +++ b/powershell/cmdlets/class.ts @@ -1307,11 +1307,11 @@ export class CmdletClass extends Class { description: `the body result as a ${each.language.csharp?.responseType} from the remote call` })); } - + if (isBinary) { parameters.push(new Parameter('response', System.Threading.Tasks.Task({ declaration: 'global::System.IO.Stream' }), { description: 'the body result as a from the remote call' })); } - + if (each.language.csharp?.headerType) { parameters.push(new Parameter('headers', System.Threading.Tasks.Task({ declaration: each.language.csharp.headerType }), { description: `the header result as a from the remote call` })); } @@ -2251,60 +2251,9 @@ export class CmdletClass extends Class { //add breaking change attributes for cmdlet, variant, output type if (operation.details.csharp.breakingChange) { const breakingChange = operation.details.csharp.breakingChange; - if (breakingChange.cmdlet) { - const parameters = []; - if (!breakingChange.cmdlet.deprecateByVersion || !breakingChange.cmdlet.deprecateByAzVersion) { - throw new Error('Cmdlet breaking change requires both \'deprecateByVersion\' and \'deprecateByAzVersion\', please refer to https://github.com/Azure/azure-powershell/blob/main/documentation/development-docs/breakingchange-for-autogen-module.md for more details.'); - } - parameters.push(`"${breakingChange.cmdlet.deprecateByAzVersion}"`); - parameters.push(`"${breakingChange.cmdlet.deprecateByVersion}"`); - if (breakingChange.cmdlet.changeInEfectByDate) parameters.push(`"${breakingChange.cmdlet.changeInEfectByDate}"`); - if (breakingChange.cmdlet.replacement) parameters.push(`ReplacementCmdletName = "${breakingChange.cmdlet.replacement}"`); - if (breakingChange.cmdlet.changeDescription) parameters.push(`ChangeDescription = "${breakingChange.cmdlet.changeDescription}"`); - - this.add(new Attribute(ClientRuntime.CmdletBreakingChangeAttribute, { parameters: parameters })); - } - if (breakingChange.variant) { - const parameters = []; - parameters.push(`new string[] {"${breakingChange.variant.name}"}`); - if (!breakingChange.variant.deprecateByVersion || !breakingChange.variant.deprecateByAzVersion) { - throw new Error('Cmdlet breaking change requires both \'deprecateByVersion\' and \'deprecateByAzVersion\', please refer to https://github.com/Azure/azure-powershell/blob/main/documentation/development-docs/breakingchange-for-autogen-module.md for more details.'); - } - parameters.push(`"${breakingChange.variant.deprecateByAzVersion}"`); - parameters.push(`"${breakingChange.variant.deprecateByVersion}"`); - if (breakingChange.variant.changeInEfectByDate) parameters.push(`"${breakingChange.variant.changeInEfectByDate}"`); - if (breakingChange.variant.changeDescription) parameters.push(`ChangeDescription = "${breakingChange.variant.changeDescription}"`); - - this.add(new Attribute(ClientRuntime.ParameterSetBreakingChangeAttribute, { parameters: parameters })); - } - if (breakingChange.output) { - const parameters = []; - // if deprecated output types are set in directive, use it - if (breakingChange.output.deprecatedCmdLetOutputType) { - parameters.push(`"${breakingChange.output.deprecatedCmdLetOutputType}"`); - } else { - parameters.push(`"${outputTypes.values().next().value.replace(/typeof\((.*)\)/, '$1')}"`); - } - if (!breakingChange.output.deprecateByVersion || !breakingChange.output.deprecateByAzVersion) { - throw new Error('Cmdlet breaking change requires both \'deprecateByVersion\' and \'deprecateByAzVersion\', please refer to https://github.com/Azure/azure-powershell/blob/main/documentation/development-docs/breakingchange-for-autogen-module.md for more details.'); - } - parameters.push(`"${breakingChange.output.deprecateByAzVersion}"`); - parameters.push(`"${breakingChange.output.deprecateByVersion}"`); - if (breakingChange.output.changeInEfectByDate) parameters.push(`"${breakingChange.output.changeInEfectByDate}"`); - if (breakingChange.output.replacement) parameters.push(`ReplacementCmdletOutputType = "${breakingChange.output.replacement}"`); - if (breakingChange.output.deprecatedOutputProperties) { - const properties: Array = Object.assign([], breakingChange.output.deprecatedOutputProperties); - properties.forEach((element, index) => properties[index] = '"' + element + '"'); - parameters.push(`DeprecatedOutputProperties = new string[] {${properties.join(',')}}`); - } - if (breakingChange.output.newOutputProperties) { - const properties: Array = Object.assign([], breakingChange.output.newOutputProperties); - properties.forEach((element, index) => properties[index] = '"' + element + '"'); - parameters.push(`NewOutputProperties = new string[] {${properties.join(',')} } `); - } - if (breakingChange.output.changeDescription) parameters.push(`ChangeDescription = "${breakingChange.output.changeDescription}"`); - - this.add(new Attribute(ClientRuntime.OutputBreakingChangeAttribute, { parameters: parameters })); + const breakingChangeAttribute = this.inferBreakingChangeAttribute(breakingChange, outputTypes); + if (breakingChangeAttribute) { + this.add(breakingChangeAttribute); } } @@ -2350,4 +2299,76 @@ export class CmdletClass extends Class { this.add(new Attribute(NotSuggestDefaultParameterSetAttribute)); } } + + private inferBreakingChangeAttribute(breakingChange: any, outputTypes: Set) : Attribute | null { + if (breakingChange.cmdlet) { + const parameters = []; + if (!breakingChange.cmdlet.deprecateByVersion || !breakingChange.cmdlet.deprecateByAzVersion) { + throw new Error('Cmdlet breaking change requires both \'deprecateByVersion\' and \'deprecateByAzVersion\', please refer to https://github.com/Azure/azure-powershell/blob/main/documentation/development-docs/breakingchange-for-autogen-module.md for more details.'); + } + + if (!breakingChange.cmdlet.replacement && breakingChange.cmdlet.changeDescription) { + // use GenericBreakingChangeAttribute because CmdletBreakingChangeAttribute has a predefined message that's weired + // when the change description is present https://github.com/Azure/autorest.powershell/issues/1487 + parameters.push(`""`); + parameters.push(`"${breakingChange.cmdlet.deprecateByAzVersion}"`); + parameters.push(`"${breakingChange.cmdlet.deprecateByVersion}"`); + parameters.push(`ChangeDescription = "${breakingChange.cmdlet.changeDescription}"`); + if (breakingChange.cmdlet.changeInEfectByDate) parameters.push(`"${breakingChange.cmdlet.changeInEfectByDate}"`); + return new Attribute(ClientRuntime.GenericBreakingChangeAttribute, { parameters: parameters }); + } else { + // use CmdletBreakingChangeAttribute + parameters.push(`"${breakingChange.cmdlet.deprecateByAzVersion}"`); + parameters.push(`"${breakingChange.cmdlet.deprecateByVersion}"`); + if (breakingChange.cmdlet.changeInEfectByDate) parameters.push(`"${breakingChange.cmdlet.changeInEfectByDate}"`); + if (breakingChange.cmdlet.replacement) parameters.push(`ReplacementCmdletName = "${breakingChange.cmdlet.replacement}"`); + if (breakingChange.cmdlet.changeDescription) parameters.push(`ChangeDescription = "${breakingChange.cmdlet.changeDescription}"`); + + return new Attribute(ClientRuntime.CmdletBreakingChangeAttribute, { parameters: parameters }); + } + } + if (breakingChange.variant) { + const parameters = []; + parameters.push(`new string[] {"${breakingChange.variant.name}"}`); + if (!breakingChange.variant.deprecateByVersion || !breakingChange.variant.deprecateByAzVersion) { + throw new Error('Cmdlet breaking change requires both \'deprecateByVersion\' and \'deprecateByAzVersion\', please refer to https://github.com/Azure/azure-powershell/blob/main/documentation/development-docs/breakingchange-for-autogen-module.md for more details.'); + } + parameters.push(`"${breakingChange.variant.deprecateByAzVersion}"`); + parameters.push(`"${breakingChange.variant.deprecateByVersion}"`); + if (breakingChange.variant.changeInEfectByDate) parameters.push(`"${breakingChange.variant.changeInEfectByDate}"`); + if (breakingChange.variant.changeDescription) parameters.push(`ChangeDescription = "${breakingChange.variant.changeDescription}"`); + + return new Attribute(ClientRuntime.ParameterSetBreakingChangeAttribute, { parameters: parameters }); + } + if (breakingChange.output) { + const parameters = []; + // if deprecated output types are set in directive, use it + if (breakingChange.output.deprecatedCmdLetOutputType) { + parameters.push(`"${breakingChange.output.deprecatedCmdLetOutputType}"`); + } else { + parameters.push(`"${outputTypes.values().next().value.replace(/typeof\((.*)\)/, '$1')}"`); + } + if (!breakingChange.output.deprecateByVersion || !breakingChange.output.deprecateByAzVersion) { + throw new Error('Cmdlet breaking change requires both \'deprecateByVersion\' and \'deprecateByAzVersion\', please refer to https://github.com/Azure/azure-powershell/blob/main/documentation/development-docs/breakingchange-for-autogen-module.md for more details.'); + } + parameters.push(`"${breakingChange.output.deprecateByAzVersion}"`); + parameters.push(`"${breakingChange.output.deprecateByVersion}"`); + if (breakingChange.output.changeInEfectByDate) parameters.push(`"${breakingChange.output.changeInEfectByDate}"`); + if (breakingChange.output.replacement) parameters.push(`ReplacementCmdletOutputType = "${breakingChange.output.replacement}"`); + if (breakingChange.output.deprecatedOutputProperties) { + const properties: Array = Object.assign([], breakingChange.output.deprecatedOutputProperties); + properties.forEach((element, index) => properties[index] = '"' + element + '"'); + parameters.push(`DeprecatedOutputProperties = new string[] {${properties.join(',')}}`); + } + if (breakingChange.output.newOutputProperties) { + const properties: Array = Object.assign([], breakingChange.output.newOutputProperties); + properties.forEach((element, index) => properties[index] = '"' + element + '"'); + parameters.push(`NewOutputProperties = new string[] {${properties.join(',')} } `); + } + if (breakingChange.output.changeDescription) parameters.push(`ChangeDescription = "${breakingChange.output.changeDescription}"`); + + return new Attribute(ClientRuntime.OutputBreakingChangeAttribute, { parameters: parameters }); + } + return null; + } } diff --git a/powershell/llcsharp/clientruntime.ts b/powershell/llcsharp/clientruntime.ts index a69a231207e..e8fe49c0fcd 100644 --- a/powershell/llcsharp/clientruntime.ts +++ b/powershell/llcsharp/clientruntime.ts @@ -36,7 +36,7 @@ export const ClientRuntime = intersect(clientRuntimeNamespace, { InfoAttribute: new ClassType(clientRuntimeNamespace, 'Info'), CompleterInfoAttribute: new ClassType(clientRuntimeNamespace, 'CompleterInfo'), DefaultInfoAttribute: new ClassType(clientRuntimeNamespace, 'DefaultInfo'), - GeneraricBreakingChangeAttribute: new ClassType(clientRuntimeNamespace, 'GeneraricBreakingChange'), + GenericBreakingChangeAttribute: new ClassType(clientRuntimeNamespace, 'GenericBreakingChange'), CmdletBreakingChangeAttribute: new ClassType(clientRuntimeNamespace, 'CmdletBreakingChange'), ParameterSetBreakingChangeAttribute: new ClassType(clientRuntimeNamespace, 'ParameterSetBreakingChange'), OutputBreakingChangeAttribute: new ClassType(clientRuntimeNamespace, 'OutputBreakingChange'), From b10b0c351c854a580b0dd7015a3739e5181aa8ec Mon Sep 17 00:00:00 2001 From: isra-fel <11371776+isra-fel@users.noreply.github.com> Date: Tue, 26 Aug 2025 02:26:46 +1000 Subject: [PATCH 2/2] try addressing lint error autorest.powershell\powershell\cmdlets\class.ts 2313:25 error Strings must use singlequote quotes --- powershell/cmdlets/class.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/powershell/cmdlets/class.ts b/powershell/cmdlets/class.ts index b2145154fd8..04adc6f6945 100644 --- a/powershell/cmdlets/class.ts +++ b/powershell/cmdlets/class.ts @@ -2310,7 +2310,7 @@ export class CmdletClass extends Class { if (!breakingChange.cmdlet.replacement && breakingChange.cmdlet.changeDescription) { // use GenericBreakingChangeAttribute because CmdletBreakingChangeAttribute has a predefined message that's weired // when the change description is present https://github.com/Azure/autorest.powershell/issues/1487 - parameters.push(`""`); + parameters.push('""'); parameters.push(`"${breakingChange.cmdlet.deprecateByAzVersion}"`); parameters.push(`"${breakingChange.cmdlet.deprecateByVersion}"`); parameters.push(`ChangeDescription = "${breakingChange.cmdlet.changeDescription}"`);