[Azure REST API Guidelines] Provide a default table of generic error codes for usage errors
We should provide a suggested starting point for common error code values in the Considerations for Service Design doc. I've often pointed other services at Storage for an example (Common, Blobs, Queues, Files, Tables), but it would be even more helpful to have a generic table that's not specific to any service. Imagine something like:
| Status Code | Error Code | Error Message |
|---|---|---|
400 |
InvalidValue |
The value provided for the [query parameter/header/property/etc.] [name] was invalid. [Details about what was invalid and how to fix.] |
400 |
MissingRequiredValue |
The required [query parameter/header/property/etc.] [name] was not specified for this request. |
403 |
AuthenticationFailed |
Server failed to authenticate the request. Make sure the value of the Authorization header is valid. |
| ... | ... | ... |
For unknown params/props, I propose an Error Code of "UnrecognizedParamOrProperty" with an Error Message of: "Unrecognized query parameter or property: qp1, prop2, prop2."
where qp1, and prop# are the names of the properties passed by the client to the service so the customer knows how to fix the issue.
I'd rename "MissingRequiredValue" to "MissingRequiredProperty" with an Error Message of: "Missing required property: prop1, prop2"
Discussion regarding text for api-version errors here: https://github.com/microsoft/api-guidelines/issues/395
| Status Code | Error Code | Error Message |
|---|---|---|
404 |
ApiNotSupported |
The API at this path is not supported by api-version YYYY-MM-DD. [It is supported by api-versions greater/less than or requal to YYYY-MM-DD.] [It was deprecated following api-version YYYY-MM-DD.] |
I have a hard time returning 404 for an unrecognized api-version if the resource actually exists. Instead, I think I'd consider this a Bad Request (400) from the client. I also think the error message should be more like "API version YYYY-MM-DD is not supported; see the supported versions at <some-URL>. Ex: https://docs.microsoft.com/en-us/rest/api/storageservices/previous-azure-storage-service-versions.
I think whether it's 400/404/405 might depend on how they get it wrong (i.e., if I make a request for GET /{resource-id}/children when resource-id exists but the hardcoded children subresource did not until a later api-version, I don't think a 404 is unreasonable. I'd also be fine with a 405 if the service didn't start supporting a given verb like PATCH until a later version). All of that also assumes someone's doing the work to to verify the request would have access to the resource had it been used with the right version, but otherwise should probably send a different type of 404. It will be a lot of work to implement correctly, but less work overall than supporting an undiagnosable service for its lifetime.
Per our discussion today about extensible enums - and perhaps a specialization of the 400 InvalidValue @tg-msft mentioned in his OP - is that passing an extensible enum values not supported in an API version should return 400 as well - perhaps even InvalidValue.
E.g.,
[v1] kind = foo | bar (modelAsString: true)
[v2] kind = boo | bar | baz (modelAsString: true)
If a user passes baz to v1 (or, really, any value since it's not defined in v1) we recommend a 400.