API Management Swagger 2.0 import fails with duplicate signature operations validation error

Ville Simpanen 20 Reputation points
2026-09-18T13:55:22.31+00:00

We have an existing APIM API containing these two operations:

GET /api/v1/objects/{objectId}/energy-consumptions/{consumptionType}
GET /api/v1/objects/{objectId}/energy-consumptions/{aggregateTimePeriod}?startTime={startTime}&endTime={endTime}&consumptionItems={consumptionItems}

The API was previously imported successfully from a Swagger 2.0 definition using Bicep.

The Swagger definition marks startTime, endTime, and consumptionItems as required query parameters for the second operation.

Now updating/importing the API fails with:

Importing API has duplicate signature operations: 2 operations with signature 'GET /api/v1/objects/{objectid}/energy-consumptions/{consumptiontype}'

translateRequiredQueryParameters is set to template.

Is it possible that the duplicate-signature validation behavior has recently changed?

Azure API Management
Azure API Management

An Azure service that provides a hybrid, multi-cloud management platform for APIs.

0 comments No comments

Answer accepted by question author
Fabian Zankl 265 Reputation points
2026-09-18T16:25:23.16+00:00

Hi @Ville Simpanen ,

You have two GET operations that share the same path shape, /api/v1/objects/{objectId}/energy-consumptions/{segment}, and differ only in the three required query parameters of the second one. The API imported fine before, and now the same Swagger 2.0 definition, imported through Bicep with translateRequiredQueryParameters set to template, is rejected as a duplicate signature.

I did not find a documented change in this area, but the error is not consistent with the documented effect of translateRequiredQueryParameters: template. Switching the setting to query, as the AI-generated answer suggests, is therefore not the right first fix: it removes the query parameters from the operation template and leaves the two GET operations with the same path signature. Here is why, and what to check instead.

How the duplicate check reads your two operations

API Management compares operations by method plus URL template, and template parameters are matched by position, not by name. Two operations whose templates differ only in the name of a parameter at the same position are the same signature. Microsoft does not document this rule in one sentence, but it is visible in the error you received: the reported signature GET /api/v1/objects/{objectid}/energy-consumptions/{consumptiontype} covers both {consumptionType} and {aggregateTimePeriod}, and the same collision on differently named path parameters is what Jessy Visch hit in an earlier Microsoft Q&A thread with /api/group-users/{id} versus /api/group-users/{guidId}.

What API Management does offer, beyond OpenAPI, is discrimination by query parameters. The import restrictions article states that operations can be discriminated by both path and query parameters, and that this is the reason parameter names must be unique across the whole URL template. With translateRequiredQueryParameters set to template (the default), the import moves required query parameters into the operation template. In your case the second operation becomes GET /api/v1/objects/{objectId}/energy-consumptions/{aggregateTimePeriod}?startTime={startTime}&endTime={endTime}&consumptionItems={consumptionItems}, which is exactly the template you quoted from the existing API. That query suffix is the only thing that has ever distinguished the two operations.

Why query would make it worse

With translateRequiredQueryParameters set to query, the required query parameters stay query parameters and are not part of the template. Both operations would then be plain GET /api/v1/objects/{objectId}/energy-consumptions/{x} and would therefore have the same operation signature. The query setting addresses the separate behavior around missing required query parameters; it does not resolve this signature collision, it creates one.

What the error tells you

The signature in the error message has no query component. That strongly suggests the required query parameters were not contributing to the operation signature during this import. Two explanations fit:

  1. The setting did not take effect on this import. translateRequiredQueryParameters is a property of Microsoft.ApiManagement/service/apis and is applied when the API is created or updated from value and format. Check that the property sits under properties of the same resource that carries the Swagger content, that the API version of the Bicep resource exposes the property, and that the Swagger still marks startTime, endTime and consumptionItems with required: true and in: query. If any of these is off, the parameters are imported as plain query parameters and the collision follows.
  2. The service-side check changed. I could not find a documented change: the API Management release notes for March and June 2026 list management API validation changes, but nothing about duplicate-signature detection or query parameter translation, and the September 2025 release tightened OpenAPI import validation without mentioning this case. Absence from the notes is not proof of absence, so the way to settle it is a controlled test: create a fresh API in the portal from the same Swagger file with Include query parameters in operation templates enabled. If that import fails with the same message, the platform behavior has changed and it is worth a support request or an issue on the release notes repository with the two-operation Swagger as the repro. If it succeeds, the cause is in the Bicep deployment, and you can compare the resulting operation templates with what the deployment produces.

A possible way to make the discrimination explicit

The import restrictions article lists x-ms-paths as a supported extension for paths that are differentiated by query parameters; the extension itself is defined in the AutoRest documentation, where the query part of the path key serves only disambiguation and the query parameters must still be declared under parameters. In principle this lets you spell out the second operation as .../{aggregateTimePeriod}?startTime={startTime}&endTime={endTime}&consumptionItems={consumptionItems} in the Swagger file instead of relying on import-time translation. I have not verified how the current importer combines x-ms-paths with translateRequiredQueryParameters: template, so treat this as something to try on a test API rather than as a confirmed workaround.

References


Drafted with help from Claude, disclosed per the Q&A AI usage policy. All technical claims checked against the API Management import restrictions article, the Bicep resource reference, the AutoRest extensions documentation and the API Management release notes.

Was this answer helpful?

2 people found this answer helpful.
0 comments No comments

1 additional answer

Sort by: Newest
  1. AI answer

    2026-09-18T13:55:40.4266667+00:00

    Yes. The failure is consistent with API Management import rules, not necessarily a recent behavior change.

    API Management requires parameter names to be unique within the entire URL template, and names are case-insensitive. It also allows operations to be discriminated by both path and query parameters, but OpenAPI does not support that discrimination in the same way. When translateRequiredQueryParameters is set to template, required query parameters are converted into required template parameters during import.

    That means this operation:

    GET /api/v1/objects/{objectId}/energy-consumptions/{aggregateTimePeriod}?startTime={startTime}&endTime={endTime}&consumptionItems={consumptionItems}

    is effectively treated during import as an operation template that includes the required query parameters as part of the template. In your case, APIM is resolving the two GET operations as having the same signature:

    GET /api/v1/objects/{objectid}/energy-consumptions/{consumptiontype}

    So the import fails with a duplicate-signature validation error.

    Supported facts from the product behavior:

    1. During OpenAPI import, API Management checks required query string parameters.
    2. By default, it converts required query parameters to required template parameters.
    3. If required query parameters should remain query parameters, disable Include query parameters in operation templates when creating the API, or set translateRequiredQueryParameters to query in the API create/update call.
    4. API Management requires unique parameter names within the full URL template, case-insensitively.

    For this API, the practical fix is to import with translateRequiredQueryParameters set to query instead of template. That prevents the required query parameters from being folded into the operation template and avoids this duplicate-signature collision.

    If the goal is also to return 400 Bad Request instead of APIM treating missing required query parameters as part of routing, keeping them as query parameters is the relevant setting.


    References:

    AI-generated content may be incorrect. Read our transparency notes for more information.

    Was this answer helpful?

Your answer

Answers can be marked as 'Accepted' by the question author and 'Recommended' by moderators, which helps users know the answer solved the author's problem.