title: TypeORM connection with Jest unit test
body: <p>I have 2 db, one for development, one for testing. I want to connect to test db when running jest test, I set up 2 <code>.env</code> config, development use <code>.env</code>, testing use <code>.env.test</code>. But unit test can't connect db through <code>connection.ts</code>.</p>
  <h2 id="update-directory-schema-zebi">Update directory schema</h2>
  <pre><code>app
  ├── .env
  ├── .env.test
  ├── loadEnv.ts
  ├── package.json
  ├── ormconfig-cli.ts
  ├── src
  │     ├── connection.ts
  │     ├── app.module.ts
  │     ├── user
  │     │    ├── entities
  │     │    │     └──  user.entity.ts
  │     │    ├── user.module.ts
  │     │    ├── user.resolver.spec.ts
  │     │    ├── user.resolver.ts
  │     │    ├── user.service.spec.ts
  │     │    └── user.service.ts
  </code></pre>
  <h2 id="update-connection-error-r5x7">Update connection error</h2>
  <p>Can't create connection, <code>getConnection().isConnected = false</code> and
  <code>getConnection('test')</code> (or <code>'default'</code>) throw &quot;Connection was not found.&quot; error.</p>
  <pre class="lang-js prettyprint-override"><code>//connection.ts
  
  import { loadEnv } from '../loadEnv';
  import connectionOptions from '../ormconfig-cli';
  loadEnv();
  
    async create(): Promise&lt;Connection&gt; {
      const connOptions: ConnectionOptions = connectionOptions.find(option =&gt; option.name == process.env.NODE_ENV);
      return await createConnection({ ...connOptions, name: 'default' });
    },
  </code></pre>
  <p>Here's the setting:</p>
  <pre class="lang-json prettyprint-override"><code>// package.json
  
  {
    ...,
    &quot;scripts&quot;: {
      ...,
      &quot;test&quot;: &quot;NODE_ENV=test jest&quot;,
      &quot;test:watch&quot;: &quot;jest --watch&quot;,
      &quot;test:cov&quot;: &quot;jest --coverage&quot;,
      &quot;test:debug&quot;: &quot;node --inspect-brk -r tsconfig-paths/register -r ts-node/register node_modules/.bin/jest --runInBand&quot;,
      &quot;test:e2e&quot;: &quot;jest --config ./test/jest-e2e.json&quot;,
    }, {...},
    &quot;jest&quot;: {
      &quot;moduleFileExtensions&quot;: [
        &quot;js&quot;,
        &quot;json&quot;,
        &quot;ts&quot;
      ],
      &quot;rootDir&quot;: &quot;src&quot;,
      &quot;testRegex&quot;: &quot;.*\\.spec\\.ts$&quot;,
      &quot;transform&quot;: {
        &quot;^.+\\.(t|j)s$&quot;: &quot;ts-jest&quot;
      },
      &quot;collectCoverageFrom&quot;: [
        &quot;**/*.(t|j)s&quot;
      ],
      &quot;coverageDirectory&quot;: &quot;../coverage&quot;,
      &quot;testEnvironment&quot;: &quot;node&quot;,
      &quot;clearMocks&quot;: true
    }
  }
  </code></pre>
  <pre><code>// .env.test
  
  NODE_ENV=test
  
  TYPEORM_HOST=localhost
  TYPEORM_PORT=5432
  TYPEORM_USERNAME=root
  TYPEORM_PASSWORD=test
  TYPEORM_DATABASE=test
  
  # TEST_DATABASE=&quot;postgres://root:test@localhost:5432/test jest&quot;
  </code></pre>
  <pre class="lang-js prettyprint-override"><code>// loadEnv.ts
  
  import * as dotenv from 'dotenv';
  
  export const loadEnv = () =&gt; {
    const loadFile = () =&gt; {
      if (process.env.NODE_ENV === 'test') return '.env.test';
      return '.env';
    };
  
    return dotenv.config({
      path: loadFile(),
    });
  };
  </code></pre>
  <pre class="lang-js prettyprint-override"><code>// ormconfig.ts
  
  import { loadEnv } from './loadEnv';
  import { ConnectionOptions } from 'typeorm';
  
  loadEnv();
  
  const SnakeNamingStrategy = require('typeorm-naming-strategies')
    .SnakeNamingStrategy;
  
  const connectionOptions: ConnectionOptions[] = [
    {
      name: 'development',
      type: 'postgres',
      host: String(process.env.TYPEORM_HOST),
      port: Number(process.env.TYPEORM_PORT),
      username: String(process.env.TYPEORM_USERNAME),
      password: String(process.env.TYPEORM_PASSWORD),
      database: String(process.env.TYPEORM_DATABASE),
      synchronize: false,
      logging: true,
      cli: {
        migrationsDir: 'src/migrations',
      },
      namingStrategy: new SnakeNamingStrategy(),
      entities: ['dist/**/*.entity{.ts,.js}'],
      migrations: ['dist/src/migrations/*.{js,ts}'],
      migrationsTransactionMode: 'each',
    },
    {
      name: 'test',
      type: 'postgres',
      host: String(process.env.TYPEORM_HOST),
      port: Number(process.env.TYPEORM_PORT),
      username: String(process.env.TYPEORM_USERNAME),
      password: String(process.env.TYPEORM_PASSWORD),
      database: String(process.env.TYPEORM_DATABASE),
      synchronize: false,
      dropSchema: true,
      logging: true,
      cli: {
        migrationsDir: 'src/migrations',
      },
      namingStrategy: new SnakeNamingStrategy(),
      entities: ['dist/**/*.entity{.ts,.js}'],
      migrations: ['dist/src/migrations/*.{js,ts}'],
      migrationsTransactionMode: 'each',
    },
  ];
  
  export = connectionOptions;
  </code></pre>
  <pre class="lang-js prettyprint-override"><code>// app.module.ts
  
  @Module({
    imports: [
      TypeOrmModule.forRoot({
        name: 'development',
        type: 'postgres',
        host: process.env.TYPEORM_HOST,
        username: process.env.TYPEORM_USERNAME,
        password: process.env.TYPEORM_PASSWORD,
        database: process.env.TYPEORM_DATABASE,
        migrationsRun: true,
        synchronize: false,
        migrationsTransactionMode: 'each',
        migrations: ['dist/src/migrations/*.{js,ts}'],
        namingStrategy: new SnakeNamingStrategy(),
        autoLoadEntities: true,
      }),
      TypeOrmModule.forRoot({
        name: 'test',
        type: 'postgres',
        host: process.env.TYPEORM_HOST,
        username: process.env.TYPEORM_USERNAME,
        password: process.env.TYPEORM_PASSWORD,
        database: process.env.TYPEORM_DATABASE,
        logging: false,
        dropSchema: true,
        migrationsRun: true,
        synchronize: false,
        migrationsTransactionMode: 'each',
        migrations: ['dist/src/migrations/*.{js,ts}'],
        namingStrategy: new SnakeNamingStrategy(),
        autoLoadEntities: true,
      }),
      ...,
    ],
  })
  export class AppModule {}
  </code></pre>
  <pre class="lang-js prettyprint-override"><code>// connection.ts
  
  import { Connection, createConnection, getConnection, getConnectionOptions } from 'typeorm';
  import { loadEnv } from '../loadEnv';
  
  loadEnv();
  
  export const connection = {
    async create(): Promise&lt;Connection&gt; {
      const connectionOptions = await getConnectionOptions(process.env.NODE_ENV);
      return await createConnection({ ...connectionOptions, name: 'default' });
    },
  
    async close() {
      await getConnection().close();
    },
  
    async clear() {
      const connection = getConnection();
      const entities = connection.entityMetadatas;
  
      entities.forEach(async (entity) =&gt; {
        const repo = connection.getRepository(entity.name);
        await repo.query(`DELETE FROM ${entity.tableName}`);
      });
    },
  
    async isConnected() {
      return getConnection().isConnected;
    },
  };
  
  </code></pre>
  <p>If run <code>npm test src/test/user.service.spec.ts</code>, will get error: No connection options were found in any orm configuration files.
  The log <code>console.log(&quot;connection.isConnected(): &quot;, connection.isConnected());</code> get error:
  ConnectionNotFoundError: Connection &quot;default&quot; was not found.</p>
  <p>Here's the test case:</p>
  <pre class="lang-js prettyprint-override"><code>import { getConnection, Repository } from 'typeorm';
  import { createMock } from '@golevelup/nestjs-testing';
  import { User } from '../user/user.entity';
  import { connection } from '../connection';
  
  describe('UserService', () =&gt; {
  
    beforeAll(async () =&gt; {
      await connection.create();
    });
  
    afterAll(async () =&gt; {
      await connection.clear();
      await connection.close();
    });
  
    describe('beforeAll connection.create()', async () =&gt; {
      const repo = createMock&lt;Repository&lt;User&gt;&gt;();
  
      it('should create user', function() {
        console.log('env: ', process.env.NODE_ENV); // env: test
        console.log(&quot;connection.isConnected(): &quot;, connection.isConnected());
        const user = {
          id: 'uuid',
          avatar: 'avatar',
          name: 'user A',
          createdAt: new Date(),
          updatedAt: new Date(),
          deletedAt: new Date(),
        };
        console.log(user);
        repo.create(user);
        repo.find.mockResolvedValue([user]);
      });
    });
  
  });
  
  </code></pre>
  <p>If not using <code>connection.create()</code> to connect, <code>connection.isConnected()</code> will be true.</p>
  <pre class="lang-js prettyprint-override"><code>...
  
    beforeAll(async () =&gt; {
       await createConnection({
        type: &quot;postgres&quot;,
        host: &quot;localhost&quot;,
        port: 5432,
        username: &quot;root&quot;,
        password: &quot;test&quot;,
        database: &quot;test&quot;,
        logging: false,
      });
    });
  
  ...
  </code></pre>
  <p>How could I update my setting and connect database through my test config?</p>