Schema 정의하기
https://mongoosejs.com/docs/guide.html#definition
몽구스에 있는 모든것은 Schema로 시작한다.
각각의 shema들은 MongoDB collection에 연결되어있고,
그 collection안에서 문서의 모양을 정의한다.
import mongoose from 'mongoose';
const { Schema } = mongoose;
const blogSchema = new Schema({
title: String, // String is shorthand for {type: String}
author: String,
body: String,
comments: [{ body: String, date: Date }],
date: { type: Date, default: Date.now },
hidden: Boolean,
meta: {
votes: Number,
favs: Number
}
});
blogSchema의 각 key는 연관된 SchemaType에 던져질 우리 문서 내부의 속성을 정의한다.
만일 type한가지만 필요하다면 위 예시의 title key처럼 단축속성으로 정의할 수 있다.
반면 date key는 아니다.
중복된 object로도 정의할 수 있다.
type key
type은 Mongoose schemas의 특별한 속성이다. mongoose가 중첩되어있는 type을 schema에서 발견하면
주어진 타입으로 schema type을 정의할 필요가 있다는 것을 가정할 것이다.
// 3 string SchemaTypes: 'name', 'nested.firstName', 'nested.lastName'
const schema = new Schema({
name: { type: String },
nested: {
firstName: { type: String },
lastName: { type: String }
}
});
만일 중첩되어있는 key의 type이라는 속성을 따로 생성하고 싶다면 어떻게 해야할까?
아래와 같이 하면 된다.
const holdingSchema = new Schema({
asset: {
// Workaround to make sure Mongoose knows `asset` is an object
// and `asset.type` is a string, rather than thinking `asset`
// is a string.
type: { type: String },
ticker: String
}
});
허용되는 Schema type
모든 스키마 타입들
모델 생성
https://mongoosejs.com/docs/guide.html#models
Schema 정의를 사용하려면 위의 blogSchema를 Model로 변경해야 한다.
const Blog = mongoose.model('Blog', blogSchema);
schema에서 mongoose.model을 부를때 mongoose는 우리를 위해 모델을 쌓아준다.
mongoose는 복수의, 소문자 버전의 model 이름을 찾는다.
아래 예시에서는 데이터베이스의 컬렉션 중 tanks라는 이름을 가지고 있는 것이 model Tank이다.
const schema = new mongoose.Schema({ name: String, size: String });
const Tank = mongoose.model('Tank', schema);
* 중요 : .model()함수는 schema의 복사본을 만들어준다.
.model()을 부르기 전에 schema에 원하는 모든 것을 반드시 추가해야 한다.
id
https://mongoosejs.com/docs/guide.html#_id
mongoose는 기본적으로 _id 속성을 우리의 schema에 추가해준다.
type은 ObjectId가 된다.
const schema = new Schema();
schema.path('_id'); // ObjectId { ... }
schema.path메서드
https://mongoosejs.com/docs/api/schema.html#Schema.prototype.path()
schema.path메서드는 인자로 주어진 path의 인스턴스된 schema type을 반환해준다.
schema type을 변경해주려고 할 때는 아래와 같이 두번째 인자에 type을 주면 된다.
schema.path('name') // returns a SchemaType
schema.path('name', Number) // changes the schemaType of `name` to Number
직접 _id속성을 덮어쓰기 할 수도 있으나, 그럴 때 _id가 없는 경우에는 저장하기를 거절할 것이므로 유의해야 한다.
const Model = mongoose.model('Test', schema);
const doc = new Model();
doc._id instanceof mongoose.Types.ObjectId; // true
인스턴스 메소드
https://mongoosejs.com/docs/guide.html#methods
model의 인스턴스들은 문서다. 문서는 많은 자신만의 빌트인 인스턴스 메소드를 많이 가지고 있다.
우리만의 커스텀 인스턴스 메소드를 정의할 수 있는 것이다.
// define a schema
const animalSchema = new Schema({ name: String, type: String },
{
// Assign a function to the "methods" object of our animalSchema through schema options.
// By following this approach, there is no need to create a separate TS type to define the type of the instance functions.
methods: {
findSimilarTypes(cb) {
return mongoose.model('Animal').find({ type: this.type }, cb);
}
}
});
// Or, assign a function to the "methods" object of our animalSchema
animalSchema.methods.findSimilarTypes = function(cb) {
return mongoose.model('Animal').find({ type: this.type }, cb);
};
schema 옵션을 통해 methods object라는 animalSchema의 object를 할당할 수 있다.
인스턴스 함수의 타입을 따로 TS타입으로 생성할 필요는 없다.
const Animal = mongoose.model('Animal', animalSchema);
const dog = new Animal({ type: 'dog' });
dog.findSimilarTypes((err, dogs) => {
console.log(dogs); // woof
});
SchemaType.prototype.default()
https://mongoosejs.com/docs/api/schematype.html#SchemaType.prototype.default()
// values are cast:
const schema = new Schema({ aNumber: { type: Number, default: 4.815162342 }})
const M = db.model('M', schema)
const m = new M;
console.log(m.aNumber) // 4.815162342
// default unique objects for Mixed types:
const schema = new Schema({ mixed: Schema.Types.Mixed });
schema.path('mixed').default(function () {
return {};
});
// if we don't use a function to return object literals for Mixed defaults,
// each document will receive a reference to the same object literal creating
// a "shared" object instance:
const schema = new Schema({ mixed: Schema.Types.Mixed });
schema.path('mixed').default({});
const M = db.model('M', schema);
const m1 = new M;
m1.mixed.added = 1;
console.log(m1.mixed); // { added: 1 }
const m2 = new M;
console.log(m2.mixed); // { added: 1 }
mongoose.connect()로 mongoDB에 연결하기
mongoose.connect('mongodb://127.0.0.1:27017/myapp');
mongoose는 mongoose가 mongoDB로의 연결을 수립하는걸 기다리지 않고
모델을 즉각적으로 사용하게 한다.
mongoose bufers 모델 함수가 내부적으로 실행되기 때문이다.
편리하지만 약간의 혼란을 줄 수있다.
기본적으로 연결이 없이 모델을 사용하더라도 에러를 내뿜지 않을 것이다.
mongoose connection error handling 두가지 방법
mongoose.connect('mongodb://127.0.0.1:27017/test').
catch(error => handleError(error));
// Or:
try {
await mongoose.connect('mongodb://127.0.0.1:27017/test');
} catch (error) {
handleError(error);
}
초기 커넥션이 완료된 후 error events listen하기
mongoose.connection.on('error', err => {
logError(err);
});
Documents 구성하기
model의 인스턴스를 document라고 부른다.
document를 만들고 database에 저장하는 것은 매우 간단하다.
아래의 예시에서
model이 사용하고 있는 connection이 열려있을 때는
tank 중 아무것도 삭제되거나 추가되지 않는다.
모든 model은 connection이 결합되어있다.
mongoose.model()을 사용하면 기본적인 mongoose connection을 사용할 것이다.
const Tank = mongoose.model('Tank', yourSchema);
const small = new Tank({ size: 'small' });
await small.save();
// or
await Tank.create({ size: 'small' });
// or, for inserting large batches of documents
await Tank.insertMany([{ size: 'small' }]);
또다른 커스텀 커넥션을 만들고 싶으면 connection의 모델 함수를 사용하면 된다.
const connection = mongoose.createConnection('mongodb://127.0.0.1:27017/test');
const Tank = connection.model('Tank', yourSchema);
질의하기 (Querying)
await Tank.find({ size: 'small' }).where('createdDate').gt(oneYearAgo).exec();
mongoose의 query
mongoose model은 CRUD operation의 정적 헬퍼 함수를 제공해준다.
https://mongoosejs.com/docs/queries.html
실행 Executing
쿼리를 실행할 때 Query를 JSON 문서로 명시해야 한다.
mongoDB shell 과 JSON 문서의 문법은 동일하다.
const Person = mongoose.model('Person', yourSchema);
// find each person with a last name matching 'Ghost', selecting the `name` and `occupation` fields
const person = await Person.findOne({ 'name.last': 'Ghost' }, 'name occupation');
// Prints "Space Ghost is a talk show host".
console.log('%s %s is a %s.', person.name.first, person.name.last, person.occupation);
'공부기록 > Mongodb' 카테고리의 다른 글
mongodb 툴 compass 설치하기 (Ubuntu)와 초기설정 (0) | 2023.04.14 |
---|---|
mongodb 초기설정하기 (0) | 2023.04.14 |