MongoDBメモリサーバによるテスト
29531 ワード
私は最近テストに深く飛び込んできた.私は合理的なコードの信頼性を持っているプロジェクトを作成するために時間を取っている.目標を作成し、適切にテストされ、まともなコードカバレッジを持っているアプリケーションを展開することです.
私が見つけたことの一つは、データベースをテストすることは簡単ではないということです.私が私のプロジェクトの1つでそうした方法の概要は、ここにあります.
私が取り組んでいるプロジェクトはOnLearn . それは本質的にeラーニング管理システムのためのPOCです.それは潜在的なユーザーがコースを置くか、コースを取ることができるプラットフォームとして機能します.UDEMY、Skallshare、またはMOOCプラットフォームのいずれか、実際には非常に似ています.
アプリケーションのスタックはノードです.J . MongoDB(マングースODM)、ビューのハンドルを使用します.Jestはテストフレームワークです.
それ自身を発表した最初の課題の一つはMongoDBのテストだった.私は、データベースロジックのために単位テストを書くことができました.
別の解決策を調べた後、私はMongoDBを見ている2つの記事に遭遇しました.
☝️ In-memory MongoDB for Testing .
✌️ そば
両方の記事ではnodkz's
MongoDBメモリサーバとは
それは本当のMongoDBサーバを紡ぐパッケージです.これは、メモリ内のデータを格納するMongodプロセスを開始することができます.
メモリデータベースでは、アプリケーションのメインメモリ自体で、ラン、および閉じられます.彼らはハードドライブに触れることはないとして高速にすると、彼らが閉じて即座に破壊されるようにテストに適しています.
ここでは、どのようにMongoDBメモリサーバーは、私はOnLearningアプリケーションのモデルのいずれかのユニットテストを書くのに役立ちます:
1️⃣ Install dependencies .
2️⃣ Configure Jest .
3️⃣ Setup in-memory database .
4️⃣ Create a model .
5️⃣ Write unit tests .
以下のコマンドがインストールされます
👉 テストスクリプト
加える
👉 テスト環境
jestのデフォルト環境は
別のファイルは
ここでは、アプリケーションからユーザーモデルです.
ユーザーはパスポートを使用して確認されますlocal & google 戦略
このように、ユーザースキーマは以下を含みます:
最後に、作成した操作を使用して
ユーザーモデルがアプリケーションでテストされた方法の例を示します.備品やアサーションは別々のモジュールに配置されます.
👉 器具
👉 ユーザモデルユニットテスト
すべてのテストと実装を見つけることができますhere
最後に
私はあなたがこれについてどう思いますか?
そして、これのためにどんな改善ヒントも共有するために自由に感じてください.✌️
MongoDBメモリサーバリポジトリ👉 here 👈
オンリーレポ👉 here 👈
私が見つけたことの一つは、データベースをテストすることは簡単ではないということです.私が私のプロジェクトの1つでそうした方法の概要は、ここにあります.
バックストーリー🔙
私が取り組んでいるプロジェクトはOnLearn . それは本質的にeラーニング管理システムのためのPOCです.それは潜在的なユーザーがコースを置くか、コースを取ることができるプラットフォームとして機能します.UDEMY、Skallshare、またはMOOCプラットフォームのいずれか、実際には非常に似ています.
アプリケーションのスタックはノードです.J . MongoDB(マングースODM)、ビューのハンドルを使用します.Jestはテストフレームワークです.
問題🤔
それ自身を発表した最初の課題の一つはMongoDBのテストだった.私は、データベースロジックのために単位テストを書くことができました.
別の解決策を調べた後、私はMongoDBを見ている2つの記事に遭遇しました.
☝️ In-memory MongoDB for Testing .
✌️ そば
両方の記事ではnodkz's
mongodb-memory-server
パッケージ.MongoDBメモリサーバとは
それは本当のMongoDBサーバを紡ぐパッケージです.これは、メモリ内のデータを格納するMongodプロセスを開始することができます.
メモリデータベースでは、アプリケーションのメインメモリ自体で、ラン、および閉じられます.彼らはハードドライブに触れることはないとして高速にすると、彼らが閉じて即座に破壊されるようにテストに適しています.
解決策💡
ここでは、どのようにMongoDBメモリサーバーは、私はOnLearningアプリケーションのモデルのいずれかのユニットテストを書くのに役立ちます:
1️⃣ Install dependencies .
2️⃣ Configure Jest .
3️⃣ Setup in-memory database .
4️⃣ Create a model .
5️⃣ Write unit tests .
1️⃣ 依存関係をインストールします。
以下のコマンドがインストールされます
jest
and mongodb-memory-server
同時に.npm i jest mongodb-memory-server
2️⃣ Jestの設定
👉 テストスクリプト
加える
test
へのスクリプトpackage.json
を返します."scripts": {
"test": "jest --runInBand --detectOpenHandles",
}
CLIオプションの概要"test"
- テストを実行するためのスクリプト名を参照します.jest
- すべてのテストを実行する既定のコマンドです.--runInBand
- テストを実行する子プロセスのワーカープールを作成するのではなく、すべてのテストを現在のプロセスでシリアルに実行するコマンドです.--detectOpenHandles
- JESTがきれいに終了するのを防ぐオープンハンドルを収集して印刷しようとするコマンド.jestのデフォルト環境は
jsdom.
ノードアプリケーションでは、代わりにノードのような環境を指定する必要があります."jest": {
"testEnvironment": "node",
}
3️⃣ メモリデータベースのセットアップ。
別のファイルは
mongodb-memory-server
接続して切断する関数を使用します.// utils/test-utils/dbHandler.utils.js
const mongoose = require('mongoose');
const { MongoMemoryServer } = require('mongodb-memory-server');
const mongoServer = new MongoMemoryServer();
exports.dbConnect = async () => {
const uri = await mongoServer.getUri();
const mongooseOpts = {
useNewUrlParser: true,
useCreateIndex: true,
useUnifiedTopology: true,
useFindAndModify: false,
};
await mongoose.connect(uri, mongooseOpts);
};
exports.dbDisconnect = async () => {
await mongoose.connection.dropDatabase();
await mongoose.connection.close();
await mongoServer.stop();
};
何が起こっているかを詳しく見るImport
mongoose
andmongodb-memory-server.
const mongoose = require('mongoose'); const { MongoMemoryServer } = require('mongodb-memory-> server');
New
mongodb-memory-server
instance that will be used to run operations on in-memory db.const mongoServer = new MongoMemoryServer();
A function to connect the in-memory database.
exports.dbConnect = async () => { const uri = await mongoServer.getUri(); const mongooseOpts = { useNewUrlParser: true, useCreateIndex: true, useUnifiedTopology: true, useFindAndModify: false, }; await mongoose.connect(uri, mongooseOpts); };
A function to disconnect the in-memory database.
exports.dbDisconnect = async () => { await mongoose.connection.dropDatabase(); await mongoose.connection.close(); await mongoServer.stop(); };
4️⃣ モデルを作成します。
ここでは、アプリケーションからユーザーモデルです.
ユーザーはパスポートを使用して確認されますlocal & google 戦略
このように、ユーザースキーマは以下を含みます:
local
and google
認証データのフィールド.profilePictureUrl
ユーザーのアバター.role
ユーザーの型.// database/models/user.model.js
const { Schema, model } = require('mongoose');
const userSchema = new Schema({
local: {
firstName: {
type: String,
trim: true,
},
lastName: {
type: String,
trim: true,
},
username: {
type: String,
trim: true,
unique: true,
},
email: {
type: String,
match: [/^\S+@\S+\.\S+$/, 'Please use a valid email address.'],
unique: true,
lowercase: true,
trim: true,
},
password: { type: String },
},
google: {
id: String,
token: String,
email: String,
name: String,
},
profilePictureUrl: {
type: 'String',
default: 'https://via.placeholder.com/150',
},
role: {
type: String,
enum: ['student', 'instructor', 'admin'],
default: 'student',
},
});
module.exports = model('User', userSchema);
5️⃣ 書き込み単位のテスト。
最後に、作成した操作を使用して
mongo-memory-server
単体テストユーザーモデルがアプリケーションでテストされた方法の例を示します.備品やアサーションは別々のモジュールに配置されます.
👉 器具
// database/fixtures/index.js
exports.fakeUserData = {
firstName: 'Dummy',
lastName: 'User',
username: 'dummyUser',
email: '[email protected]',
password: '********',
role: 'student',
};
👉 テストアサーションヘルパー// utils/test-utils/validators.utils.js
exports.validateNotEmpty = (received) => {
expect(received).not.toBeNull();
expect(received).not.toBeUndefined();
expect(received).toBeTruthy();
};
...
exports.validateStringEquality = (received, expected) => {
expect(received).not.toEqual('dummydfasfsdfsdfasdsd');
expect(received).toEqual(expected);
};
...
exports.validateMongoDuplicationError = (name, code) => {
expect(name).not.toEqual(/dummy/i);
expect(name).toEqual('MongoError');
expect(code).not.toBe(255);
expect(code).toBe(11000);
};
最後に、フィクスチャ、アサーションヘルパー、およびDB操作がテストで使用されます.🥳🥳🥳👉 ユーザモデルユニットテスト
const User = require('../user.model');
const { fakeUserData } = require('../../fixtures');
const {
validateNotEmpty,
validateStringEquality,
validateMongoDuplicationError,
} = require('../../../utils/test-utils/validators.utils');
const {
dbConnect,
dbDisconnect,
} = require('../../../utils/test-utils/dbHandler.utils');
beforeAll(async () => dbConnect());
afterAll(async () => dbDisconnect());
describe('User Model Test Suite', () => {
test('should validate saving a new student user successfully', async () => {
const validStudentUser = new User({
local: fakeUserData,
role: fakeUserData.role,
});
const savedStudentUser = await validStudentUser.save();
validateNotEmpty(savedStudentUser);
validateStringEquality(savedStudentUser.role, fakeUserData.role);
validateStringEquality(savedStudentUser.local.email, fakeUserData.email);
validateStringEquality(
savedStudentUser.local.username,
fakeUserData.username
);
validateStringEquality(
savedStudentUser.local.password,
fakeUserData.password
);
validateStringEquality(
savedStudentUser.local.firstName,
fakeUserData.firstName
);
validateStringEquality(
savedStudentUser.local.lastName,
fakeUserData.lastName
);
});
test('should validate MongoError duplicate error with code 11000', async () => {
expect.assertions(4);
const validStudentUser = new User({
local: fakeUserData,
role: fakeUserData.role,
});
try {
await validStudentUser.save();
} catch (error) {
const { name, code } = error;
validateMongoDuplicationError(name, code);
}
});
});
合格テストすべてのテストと実装を見つけることができますhere
結論🏁
最後に
mongodb-memory-server
パッケージは私のテストのためにたくさんのデータベースを重くしました.私はdbConnect
and dbDisconnect
操作と私のアプリケーションのモデルをテストしてもservices associated with those models .私はあなたがこれについてどう思いますか?
そして、これのためにどんな改善ヒントも共有するために自由に感じてください.✌️
MongoDBメモリサーバリポジトリ👉 here 👈
オンリーレポ👉 here 👈
Reference
この問題について(MongoDBメモリサーバによるテスト), 我々は、より多くの情報をここで見つけました https://dev.to/remrkabledev/testing-with-mongodb-memory-server-4ja2テキストは自由に共有またはコピーできます。ただし、このドキュメントのURLは参考URLとして残しておいてください。
Collection and Share based on the CC Protocol