Skip to content
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

fix(types): allow use of sequelize.define models in types #13834

Closed
wants to merge 3 commits into from

Conversation

hsource
Copy link
Contributor

@hsource hsource commented Dec 27, 2021

Pull Request Checklist

Please make sure to review and check all of these items:

  • Have you added new tests to prevent regressions?
  • Does npm run test or npm run test-DIALECT pass with this change (including linting)?
  • Is a documentation update included (if this change modifies existing APIs, or introduces new ones)?
  • Did you update the typescript typings accordingly (if applicable)?
  • Does the description below contain a link to an existing issue (Closes #[issue]) or a description of the issue you are solving?
  • Did you follow the commit message conventions explained in CONTRIBUTING.md?

Description Of Change

Motivation

#13010 had fixed an issue where class-based Models with explicit types couldn't be used in includes and other places that expect static models, but it had inadvertently broken the same for Models created with sequelize.define(), which were the standard before it.

This is because it created a new ModelType type, that required explicit properties. sequelize.define outputs a ModelCtor type that doesn't conform to that:

Code with error:

  const commonQuestionOptions: FindOptions<QuestionAttributes> = {
    include: [
      { model: Answer },
    ],
  };

Error: TS2322: Type 'ModelCtor' is not assignable to type 'ModelType<any, any> | undefined'.

Fix

I wrote the original Typescript typings for v6 (#12405), but didn't document it really well. This change better documents how the types should be used and swaps out most uses of ModelType with ModelStatic, which is compatible with both class and sequelize.define Models.

Here's what I did:

  1. Document when to use ModelCtor and ModelStatic in the typings file
  2. Switch all uses of ModelType to use ModelStatic, which works with both class and sequelize.define models
  3. Add Typescript tests to ensure that using both class and function components type-check in User.ts

Todos

None

@WikiRik WikiRik added the type: typescript For issues and PRs. Things that involve typescript, such as typings and intellisense. label Dec 28, 2021
Copy link
Member

@ephys ephys left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good to me, thank you for the extra jsdoc too

Comment on lines +2931 to +2933
* Do not switch the order of `typeof Model` and `{ new(): M }`. For
* instances created by `sequelize.define` to typecheck well, `typeof Model`
* must come first for unknown reasons.
Copy link
Member

@wbourne0 wbourne0 Dec 31, 2021

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is probably because typeof Model is a constructor and as such, its new function would take precedence over the constructor of { new(): M }.

@ephys
Copy link
Member

ephys commented Jan 3, 2022

Please don't merge this yet. This issue is related to a problem I've been trying to solve for the past year (ModelCtor not acting just right) and I think I've just solved it by changing ModelCtor to this definition

// remove the existing constructor that tries to return `Model<{},{}>` which would be incompatible with models that have typing defined & replace with proper constructor.
export type ModelCtor<M extends Model> = Omit<typeof Model, 'new'> & { new(): M };

Checking if tests pass, brb

@ephys
Copy link
Member

ephys commented Jan 3, 2022

Tests have passed in #13890

@hsource would you mind taking a look at it too?

@hsource
Copy link
Contributor Author

hsource commented Jan 3, 2022

@ephys and @AllAwesome the fix in #13890 looks better. Ship it!

@WikiRik
Copy link
Member

WikiRik commented Jan 3, 2022

I guess this one can be closed then, right?

@ephys
Copy link
Member

ephys commented Jan 4, 2022

Thanks @hsource :) I'll close this one then

@ephys ephys closed this Jan 4, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
type: typescript For issues and PRs. Things that involve typescript, such as typings and intellisense.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

5 participants