-
-
Notifications
You must be signed in to change notification settings - Fork 500
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Generates invalid types when API paths are nested #1752
Comments
Here's one scenario I can think of: type BasePath = string & { __id: 'BasePath' };
type SchemaOne = {
case_name: string;
};
type SchemaTwo = {
case_summary: string;
};
type Paths = {
[path: `/api/internal/cases/${BasePath}`]: SchemaOne;
[path: `/api/internal/cases/${BasePath}/summary`]: SchemaTwo;
};
const caseDetail: Paths[`/api/internal/cases/${BasePath}`] = {
case_name: 'example-case',
};
const caseSummary: Paths[`/api/internal/cases/${BasePath}/summary`] = {
case_summary: 'example-summary',
};
@drwpow @mat-certn I want to know what you think? |
i think for my use-case I want to find the type definition from the URL, e.g. I want to be able to do this:
which doesn't work with the above: |
Are there any good solutions for this in ts? |
Yeah this is a tricky one! I will admit this flag has always had some rough edges for reasons like this. Loose pattern-matching in TS isn’t as robust as runtime equivalents. I’m sure there are ways to solve it, but they may not be straightforward. Either way, would welcome PRs on improving this. |
Hello ! I've got the same problem on my side, any restful crud app is unable to work as without --path-params-as-types, but this flag always generates errors. My solution for this was to separate paths and dynamic path, to keep types without getting interference between static and dynamic paths. Here's an example : export type dynamicPaths = {
[path: `/api/mydata/${string}`]: {
...
}
}
export interface paths extends dynamicPaths {
'/api/mydata': {
...
}
} I am creating a PR tonight when i finished to comply to CONTRIBUTING.md, hope this will help and not break any existing code. Thank you |
@walid-mos, thanks a lot for contributing. I'm commenting here on your proposed approach (rather than on #2106) in attempt to keep all relevant bits of the conversation together. I'm afraid splitting static / dynamic paths will only solve the issue for some use cases. If However, consider the OP's example:
Both of these will end up in the TBH, I'm not sure there is a good solution to this (unless we get something like microsoft/TypeScript#41160). |
Hello @gzm0 ! I see your concerns, for my case, this did not conflict, as the problem is really between dynamic and non dynamic paths. Here is the example i am using myself :
As you can see, |
Oh, I understand now. This was about generating invalid types, not the usage of the types being invalid. I think what "fixes" it in your example is the additional intersection type (see on TS playground). type DynamicPathsTypechecks = {
[path: `/api/tenant/${string}`]: A
} & {
[path: `/api/tenant/${string}/data-sources`]: B
};
type DynamicPathsDoesNotTypecheck = {
[path: `/api/tenant/${string}`]: A
[path: `/api/tenant/${string}/data-sources`]: B
}; I think splitting off the static paths is a red herring. So, we could chose to do this, but IIUC it would simply push the problem later when we actually try to use these types: // Type usage is still broken.
const x: A = { a: 1 }
// This assignment fails: Type 'A' is not assignable to type 'A & B'.
const y: DynamicPathsTypechecks["/api/tenant/1/data-sources"] = x It's not entirely clear to me if using intersection types will make overall usability better or worse :-/ |
Ok i see your point, thank you for the explanation, i was mislead by the fact that every types are the same between paths (of type :
) So as i was infering values inside paths interface (like this :
So i was working as it's the same structure, but it's not a valable global solution as it could maybe lead to errors. Thank you for your time ! |
Description
We have multiple paths in our schema that are "nested" below each other, like so:
openapi-typescript using the argument --path-params-as-types generates the following:
which conflicts with the error
this is because technically
/some/path/${string}/summary
is generated as incorrectly assignable to/some/path/${string}
- instead of ${string} it should be some sort of type that cannot include "/"openapi-typescript
7.0.2
5.3.3
or5.5.3
(have tried a few versions)18.18.2
macOS 14.5
Reproduction
Generate types using the following schema:
npx openapi-typescript example.yml --output example.ts --path-params-as-types
Expected result
A more complex type than ${string} that prevents both endpoints from matching each other.
Checklist
npx @redocly/cli@latest lint
)The text was updated successfully, but these errors were encountered: