TypeORM
你的 models
看起来如下:ActiveRecord
模式,也可以这样用:npm
安装:npm install typeorm --save
reflect-metadata
:npm install reflect-metadata --save
app.ts
中)import "reflect-metadata";
npm install @types/node --save
npm install mysql --save
(也可以安装 mysql2
)npm install pg --save
npm install sqlite3 --save
npm install mssql --save
npm install sql.js --save
npm install mongodb --save
tsconfig.json
中启用了以下设置:lib
中启用 es6
,或者安装 es6-shim
的 @types
。name
是项目的名称,database
是将使用的数据库。mysql
、 mariadb
、 postgres
、 sqlite
、 mssql
、 oracle
、 mongodb
、 cordova
、 react-native
、 expo
、 nativescript
.MyProject
目录中生成一个包含以下文件的新项目:你还可以在现有 node 项目上运行typeorm init
,但要注意,此操作可能会覆盖已有的某些文件。
ormconfig.json
文件并在其中编辑自己的数据库连接配置选项:host
, username
, password
, database
或者 port
即可。你可以通过运行typeorm init --name MyProject --database mysql --express
来生成一个更高级的 Express 项目
Photo
模型:@Entity
装饰器装饰的模型。将为此类模型创建数据库表。你可以使用 TypeORM 处理各处的实体,可以使用它们 load/insert/update/remove 并执行其他操作。Photo
模型作为一个实体Photo
实体创建一个数据库表,我们将能够在应用程序中的任何位置使用它。 我们已经创建了一个数据库表,但是没有指明哪个字段属于哪一列,下面让我们在数据库表中创建列。@Column
装饰器。id
, name
, description
, filename
, views
和 isPublished
列将会被添加到 photo
表中。 数据库中的列类型是根据你使用的属性类型推断的,例如: number
将被转换为 integer
,string
将转换为 varchar
,boolean
转换为 bool
等。但你也可以通过 @Column
装饰器中隐式指定列类型来使用数据库支持的任何列类型。@PrimaryColumn
装饰器。@PrimaryColumn
装饰器更改为 @PrimaryGeneratedColumn
装饰器:index.ts
(或app.ts
,无论你怎么命名)文件,并配置数据库连接::type
更改为希望使用的数据库类型:mysql
,mariadb
,postgres
,sqlite
,mssql
,oracle
,cordova
,nativescript
,react-native
,expo
或 mongodb
。同时还要确保 host
, port
, username
, password
和 database
正确设置。synchronize
可确保每次运行应用程序时实体都将与数据库同步。ts-node
,则需要指定 .ts
文件的路径。 如果使用的是 outDir
,那么需要在 outDir
目录中指定 .js
文件的路径。 如果使用 outDir
,当你删除或重命名实体时,请确保清除 outDir
目录并再次重新编译项目,因为当你删除 .ts
源文件时,其编译的 .js
文件不会从输出目录中删除,并且 TypeORM 依然会从 outDir
中加载这些文件,从而导致异常。app.ts
,启动后可以发现数据库自动被初始化,并且 Photo 这个表也会创建出来。save
方法返回传递给它的同一对象的实例,但并不是对象的新副本,只是修改了它的"id"并返回。EntityManager
你可以操纵应用中的任何实体。savedPhotos
是一个 Photo 对象数组,其中包含从数据库加载的数据。Repository
替代 EntityManager
。每个实体都有自己的repository,可以处理其实体的所有操作。当你经常处理实体时,Repositories 比 EntityManagers 更方便使用:id = 1
的 photo 在数据库中就成功更新了。id = 1
的 photo 在数据库中被移除了。PhotoMetadata.ts
中创建一个新类。此 PhotoMetadata 类应包含 photo 的其他元信息:@OneToOne
的新装饰器,它允许我们在两个实体之间创建一对一的关系。 type => Photo
是一个函数,返回我们想要与之建立关系的实体的类。由于特定于语言的关系,我们只能使用一个返回类的函数,而不是直接使用该类。 同时也可以把它写成 ()=> Photo
,但是 type => Photo
显得代码更有可读性。type 变量本身不包含任何内容。@JoinColumn
装饰器,表明实体键的对应关系。关系可以是单向的或双向的。但是只有一方可以拥有。在关系的所有者方需要使用 @JoinColumn
装饰器。photo => photo.metadata
是用来指定反向关系的名称。Photo 类的元数据属性是在 Photo 类中存储 PhotoMetadata 的地方。你可以选择简单地将字符串传递给 @OneToOne
装饰器,而不是传递返回 photo 属性的函数,例如 "metadata"
。这种函数类型的方法使我们的重构更容易。@JoinColumn
装饰器。你把这个装饰者放在哪一方将是这段关系的拥有方。关系的拥有方包含数据库中具有外键的列。find *
或使用 QueryBuilder
。我们先使用 find *
方法。 find *
方法允许你使用 FindOneOptions
/ FindManyOptions
接口指定对象。QueryBuilder
。 QueryBuilder
使用更优雅的方式执行更复杂的查询:QueryBuilder
允许你创建和执行几乎任何复杂性的 SQL 查询。使用 QueryBuilder
时,请考虑创建 SQL 查询。在此示例中,"photo"和"metadata"是应用于所选 photos 的别名。你可以使用别名来访问所选数据的列和属性。cascade
选项,这时就可以在保存其他对象的同时保存相关对象。让我们更改一下的 photo 的 @OneToOne
装饰器:cascade
允许就不需要边存 photo 边存元数据对象。我们可以简单地保存一个 photo 对象,由于使用了 cascade,metadata 也将自动保存。Author
类:Author
包含反向关系。 OneToMany
总是反向的, 并且总是与 ManyToOne
一起出现。@ManyToOne
的类将存储相关对象的 id。 运行应用程序后,ORM 将创建author
表:photo
表,添加新的author
列并为其创建外键:Album
类:@JoinTable
需要指定这是关系的所有者方。Photo
类:Album
类:loadedPhoto
如下所示: