question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

Support inheritance for models

See original GitHub issue

This needs to be supported and tested:

class Base extends Model {}
Base.init({ whatever: DataTypes.STRING }, { tableName: 'base_table' })

class Derived extends Base {}
Derived.init({ second: DataTypes.INTEGER }, { tableName: 'derived_table' })

Derived.options.__proto__ === Base.options
Derived.attributes.__proto___ === Base.attributes

Derived inherits all attributes and options from Base.

Model.init() should do something like

this.options = Object.assign(Object.create(this.options), options)

Issue Analytics

  • State:open
  • Created 7 years ago
  • Reactions:12
  • Comments:9 (8 by maintainers)

github_iconTop GitHub Comments

2reactions
felixfbeckercommented, Jul 24, 2017

That means that if the derivative doesn’t explicitly overwrites tableName in it’s options than options.tableName === ‘base_table’ will always be true and will be set as the model table name

All that needs to be done is default tableName to the model name. It’s really not an issue. We can check options.tableName before you seting up the new object with inheritance or use hasOwnProperty().

init in itself is not as bad. But we have a weird situation where a Model class actually creates Row instances instead of Models. Think about calling New Buffer(); and instead of getting a Buffer you’ll get a 16bit value. So effectively Sequelize doesn’t have a Model class and that is why inheritance is so messy or why your decorators doesn’t really work. It is too late to fix now but it is something we should be aware of and aim to fix when possible.

I think you are misunderstanding the “Model” term in Sequelize. Sequelize uses the Active Record pattern. The Model is the class, instances are concrete rows. This is not a mistake, it’s a design choice. After all, classes in JavaScript are just objects themselves, so there is no reason to separate them like in v3 where there was an Instance class and a Model class. It didn’t have any benefit. The Model class is abstract, it could just as well be named Entity or Row, it’s just naming. A different name doesn’t make inheritance messy or decorators not work.

How many users actually use history tables ? more than having multiple tables with ids and timestamps and other properties ? More than people having multiple servers and connections they might have to attach identical models to ?

The use case is huge. Any application that stores data of legal importance needs to keep a change history. Comparing the number of these users to the number of users needing “abstract” models for inheritance doesn’t make sense because they don’t contradict each other. With the way I suggest it, you can easily support both use cases. With your way it only supports the abstract model use case.

Any way doing inheritance properly you could use them for both history tables and other solutions, but by forcing it to be part of the init process you are basically locking it to one use case.

What’s the problem with abstract: true?

I think this is enough reason for wanting the inheritance process to be decoupled from the init. We should look at init as way to instantiating a Model object as if we actually had a class for it.

I don’t understand this paragraph, could you explain? init is a static constructor. It initialises the static side of the class. Models are classes and in JavaScript, classes are objects. Instantiating the concrete Model (e.g. User) is done by new User() and gives you a User instance/row.

1reaction
schieck0commented, Apr 16, 2022

5 years later…

Read more comments on GitHub >

github_iconTop Results From Across the Web

Inheritance Object Model Concept - Service Architecture
Inheritance in the object model is a means of defining one class in terms of another. This is common usage for most of...
Read more >
Modeling Inheritance - Overview - Documentation
Modeling Inheritance - Overview. This article is relevant to entity models that utilize the deprecated Visual Studio integration of Telerik Data Access.
Read more >
How to model inheritance in Prisma | Basedash
Relational databases don't support inheritance per-se, but with some effort we can arrange things with Prisma to give a pretty good ...
Read more >
Modeling Inheritance - Apache Cayenne
Inheritance is a familiar and a very useful concept to any Java developer. There are three common ways of mapping it to a...
Read more >
Inheritance
Inheritance is an object-oriented programming concept used to model an "is-a" relationship between two classes. It allows one class (the derived class or ......
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found