How do I print out the table name of a sequelize instance?
Note: the short answer is in the first part! You can skim down more to see more details! And interseting elements! And the tests i made! To clear all! You can skim and check the big titles!
From v4 to v6
It works in them all the same
Using the Model class
If we take the Model for example as User
!
User.name // => Model name => `User` (you don't need that!
// unless you are doing something dynamic!)
User.tableName // => Users
User.getTableName()
// => Users (no schema)
// or `"AmASchema"."Users"` (pg), `AmASchema.Users` (MySql) (schema)
// or { tableName: 'Users', schema: 'AmASchema', ... } (schema)
We can see in the type definition
public static getTableName(): string | {
tableName: string;
schema: string;
delimiter: string;
};
Using Model instance
const user = User.build(...)
user.constructor.name // => User
user.constructor.tableName // => Users
user.constructor.getTableName()
// => Users (no schema)
// or `"AmASchema"."Users"` (pg), `AmASchema.Users` (MySql) (schema)
// or { tableName: 'Users', schema: 'AmASchema', ... } (schema)
What Doesn't work
instance.name // => undefined
instance.tableName // => undefined
// tested in v4.0, v4.28.10 and v6
I had a wrong assumption and consideration! Where that may be in some versions! instance.name
works! And not the constructor
version! But no! So far my tests show that it is not! All the above work in all the versions from V4 to V6! And this what doesn't, doesn't in them all!
Know too that I checked in V6, the typescript definition doesn't expose any modeInstance.name
or modelInstance.tableName
properties!
You can check that in the sequelize model.d.ts
type file Line:1527 (Link will take to the line directly! You can CTRL + F and search tableName
(within Model class, you'll find only: L1553, L1658, L1679 14 finding, 8 in class Model, different one in comments only!)! [Static property are denoted with Static
! Don't confuse them! With instance properties])
instance.Model.name // Error (instance.Model => undefined)
instance.Model.tableName // Error (instance.Model = undefined)
// tested in both v4.0, v4.28.10 and v6
Doesn't work too!
What i tested
All was tested in:
- v4.0.0
- v4.28.10
- v6!
And for instances! instance.constructor.tableName
is what works !
And it works the same in all of them!
class User extends Model vs sequelize.define()
In V6: I tried against boht class User extends Model
and sequelize.define()
! Both works the same!
Typescript and transpilation
I tested against different targets:
- ES5 (only sequelize.define()! ES5 transpilation doesn't support full ES6 classes (check the why section at the end of the Stackoverflow answer here to know the why))
- ES6
- ES2021
=> All works the same! And the above is valid for all!
Log of my results
V6 (Target ES2021, ES6, ES5)
--------------- Testing Models Classes -----------------------
Static access using getTableName() (without Schema) :
Course.getTableName(): Courses
Static access using getTableName() (with Schema) :
User.getTableName(): "AmASchema"."Users"
And ::::
Course.name: Course
Course.tableName: Courses
User.name: User
User.tableName: Users
----
---------------------- Testing Models instances ----------------
Testing using Class Extends Model definition ::::
Instance access using instance.name and instance.tableName
course.name: undefined
course.tableName: undefined
Instance access using instance.constructor.name and instance.constructor.tableName and getTableName()
course.constructor.name: Course
course.constructor.tableName: Courses
course.constructor.getTableName(): Courses
Testing using sequelize.define() definition ::::
Instance access using instance.name and instance.tableName
user.name: undefined
user.tableName: undefined
Instance access using instance.constructor.name and instance.constructor.tableName and getTableName()
user.constructor.name: User
user.constructor.tableName: Users
user.constructor.getTableName(): "AmASchema"."Users"
V4 (The same)
---------------------- Testing Models Classes ----------------
Static access using getTableName() (without Schema) :
Course.getTableName(): Courses
Static access using getTableName() (with Schema) :
User.getTableName(): "AmASchema"."Users"
And ::::
Course.name: Course
Course.tableName: Courses
User.name: User
User.tableName: Users
----
--------------- Testing Models instances -----------------------
Testing using sequelize.define() definition ::::
Instance access using instance.name and instance.tableName
user.name: undefined
user.tableName: undefined
Instance access using instance.constructor.name and instance.constructor.tableName and getTableName()
user.constructor.name: User
user.constructor.tableName: Users
user.constructor.getTableName(): "AmASchema"."Users"
Repo to Check and test for yourself
I shared the test repo publicly! If you like to test quickly! On your machine! You can check the test repo bellow:
https://github.com/MohamedLamineAllal/sequelize-name-and-tableName-test
There is two branches:
- sequelize/v4
- sequelize/v6
Master is the latest version! (v6 now)
Detail about Using model Class getTableName()
https://sequelize.org/master/class/lib/model.js~Model.html#static-method-getTableName
public static getTableName(): string | object
Get the table name of the model, taking schema into account. The method will return The name as a string if the model has no schema, or an object with tableName, schema and delimiter properties.
Doesn't have schema => return tableName string
Have schema => return { tableName, schema, delimter } object.
Depending on that we can access in one of the way:
// model has no schema
const tableName = Course.getTableName();
// or
// model has schema
const tableName = Course.getTableName().tableName;
That's statically from the model class directly.
The doc say so! But my tests returned a string even with a schema!
We can see too a mention in the code source type file L1658!
Note: I tried and setup a schema! But the result came as a string!
`"AmASchema"."Users"`
You can check that in the shared logs above!
If any one know what type of schema that may trigger the object return format! Let me know so i add it in the answer!
Note the definition of getTablename()
:
lib/model.js#L1440
lib/dialects/abstract/query-generator.js#L50
getTableName() vs tableName
Model.getTableName() // No schema: return => `Users`
// Schema:
// return => `"MySchema"."Users"` (Postgres),
// `MySchema.Users` (Mysql)
// Or { tableName: 'Users', schema: 'MySchema', ... }
instance.constructor.getTableName() // same as above
=> will return the schema if there is along with the table name!
While
Model.tableName // return => `Users`
// or
user.constructor.tableName // return => `Users`
=> Will return only the table name
Extra: Note about automatic table naming
By default, when the table name is not given, Sequelize automatically pluralizes the model name and uses that as the table name. This pluralization is done under the hood by a library called inflection, so that irregular plurals (such as
Person -> People
) are computed correctly.
Of course, this behavior is easily configurable.
User -> Users
Class -> Classes
Person -> People
Child -> Children
Course -> Courses
https://sequelize.org/master/manual/model-basics.html
You can also inforce using the same name as the module (reference)!
piotrbienias' answer is for v3, in v4 you do:
user.constructor.getTableName()
or user.constructor.tableName
for table name and user.constructor.name
for the Model name
ref: Breaking Changes in V4
Took me a while to figure that out so though't I'd post it here in case somebody else comes looking for this answer.
Table name: user.Model.getTableName()
or user.Model.tableName
Model name: user.Model.name
Sequelize v4
For the table name
user.constructor.getTableName()
works great. For the type(the name you give as first param to .define()) you can:
user._modelOptions.name.plural
user._modelOptions.name.singular