Typeorm 连接多个数据库

Posted

技术标签:

【中文标题】Typeorm 连接多个数据库【英文标题】:Typeorm connect to multiple database 【发布时间】:2019-07-10 07:09:39 【问题描述】:

我使用 node.js 、 TS 和 typeorm 做后端项目。

我需要根据我发送的参数连接到中间件中不同的数据库。 我必须将查询发送到数据库。

ormconfig

[
  
    "name": "default",
    "type": "postgres",
    "host": "localhost",
    "port": 5432,
    "username": "postgres",
    "password": "12345",
    "database": "dbOne"
  ,
  
    "name": "second-connection",
    "type": "postgres",
    "host": "localhost",
    "port": 5432,
    "username": "postgres",
    "password": "12345",
    "database": "dbTwo"
  
]

这是我的连接设置。 完成此操作后,我正在尝试连接到中间件。

   const connectionOptions = await getConnectionOptions("second-connection");
   const conTwo = await createConnection(connectionOptions);

   const managerTwo = getManager("second-connection");

   const resultTwo = await managerTwo
      .createQueryBuilder(SysCompany, "company")
      .getOne();

   console.log(resultTwo);

我想我可以连接到数据库,但是我在存储库时遇到了问题。

错误

EntityMetadataNotFound:找不到“SysCompany”的元数据。

@Entity()
export class SysCompany extends CoreEntityWithTimestamp 

  @Column( length: 100 )
  name: string;

  // FK
  // SysPersonnel
  @OneToMany(type => SysPersonnel, personnel => personnel.sysCompany)
  sysPersonnels: SysPersonnel[];


【问题讨论】:

您确定 SysCompany 表已创建吗? 【参考方案1】:

使用多个数据库的最简单方法是创建不同的连接:

import createConnections from "typeorm";

const connections = await createConnections([
    name: "db1Connection",
    type: "mysql",
    host: "localhost",
    port: 3306,
    username: "root",
    password: "admin",
    database: "db1",
    entities: [__dirname + "/entity/*.js,.ts"],
    synchronize: true
, 
    name: "db2Connection",
    type: "mysql",
    host: "localhost",
    port: 3306,
    username: "root",
    password: "admin",
    database: "db2",
    entities: [__dirname + "/entity/*.js,.ts"],
    synchronize: true
]);

这种方法允许您连接到您拥有的任意数量的数据库,并且每个数据库都有自己的配置、自己的实体和整体 ORM 范围和设置。 对于每个连接,都会创建一个新的 Connection 实例。您必须为您创建的每个连接指定一个唯一名称。 连接选项也可以从 ormconfig 文件中加载。您可以从 ormconfig 文件加载所有连接:

import createConnections from "typeorm";

const connections = await createConnections();

或者您可以通过名称指定要创建的连接:

import createConnection from "typeorm";

const connection = await createConnection("db2Connection");

使用连接时,您必须指定连接名称以获取特定连接:

import getConnection from "typeorm";

const db1Connection = getConnection("db1Connection");
// you can work with "db1" database now...

const db2Connection = getConnection("db2Connection");
// you can work with "db2" database now...

使用这种方法的好处是您可以使用不同的登录凭据、主机、端口甚至数据库类型本身配置多个连接。缺点可能是您需要管理和使用多个连接实例。

【讨论】:

【参考方案2】:

也许 typeORM 找不到您的 javascript 实体。我前段时间遇到过这个问题。您可以执行以下操作:

在构建项目后检查您的目标文件夹。你的SysCompany.js 有空吗? 在配置中设置entities 属性。它必须包含您的 JS 实体的路径。 typeORM 文档声明“必须在您的连接选项中注册每个实体”。

 "name": "second-connection",
 "type": "postgres",
 "host": "localhost",
 "port": 5432,
 "username": "postgres",
 "password": "12345",
 "database": "dbTwo"
 "entities": ["<path to entities>/**/*.js"]

我还建议使用 JavaScript 配置文件。然后您的ormconfig.js 可以使用__dirname(当前模块的目录名)来设置路径。因此,如果您的目录如下所示:

project/ormconfig.js
project/dist/entity/SysCompany.js
project/dist/entity/OtherEntity.js

你可以使用这样的配置:

import join from "path";
...
  entities: [
    join(__dirname, "dist/entity/**/*.js")
  ],
...

您还可以通过使用基本配置对象来防止重复。

import join from "path";

const baseOptions = 
  type: "postgres",
  host: "localhost",
  port: 5432,
  username: "postgres",
  password: "12345",
  entities: [
    join(__dirname, "dist/entity/**/*.js")
  ]


const defaultConfig = Object.assign(
  name: "default",
  database: "dbOne",
, baseOptions);

const secondConfig = Object.assign(
  name: "second-connection",
  database: "dbTwo",
, baseOptions);

module.exports = [ defaultConfig, secondConfig ];

在您打开连接的文件中,您可以使用导入:

import  secondConfig  from "<path to file>/ormconfig";

const conTwo = await createConnection(secondConfig);

【讨论】:

尝试使用这段代码,编译时出错(打字稿):import join from "path"; SyntaxError: Unexpected token

以上是关于Typeorm 连接多个数据库的主要内容,如果未能解决你的问题,请参考以下文章

使用带有 TypeOrm 的 NestJS 连接 MySQL 数据库时出现问题

TypeORM 无关联关系的mysql多表连接查询

未找到连接“默认”-TypeORM、NestJS 和外部 NPM 包

NestJS + MySQL:如何在不设置实体的情况下连接多个数据库

过滤从查询参数传递的数组。 NestJS,TypeORM

什么是 nestjs typeorm 中的 getRepositoryToken 以及何时使用它?