Mongoose学習全面理解(推奨)

14421 ワード

一、作成schemas
schemasを作成する方法:

 var userSchema = new mongoose.Schema({
   name: String,
   email: String,
   createdOn: Date
 });

schemasのデータの種類は以下の通りです。
  •  String
  •  Number
  •  Date
  •  ボロア
  •  Buffer
  •  ObjectId
  •  Mixed
  •  Aray
  • 特にObjectIdタイプとMixedタイプとArayタイプを説明したいですが、schemasでこれらのタイプを宣言する方法は以下の通りです。
    
    //ObjectId        
    projectSchema.add({
      owner: mongoose.Schema.Types.ObjectId
    });
    //    ,    ,                ,            
    //   :             
    vardjSchema= new mongoose.Schema({
      mixedUp: {}
    });
    //   :  Schemas.Types     
    vardjSchema= new mongoose.Schema({
      mixedUp: Schema.Types.Mixed
    });
    //Array           ,         :
    var userSchema = new mongoose.Schema({
      name: String,
      emailAddresses: [String]
    });
    //               ,                 schemas:
    var emailSchema = new mongoose.Schema({
      email: String,
      verified: Boolean
    });
    var userSchema = new mongoose.Schema({
      name: String,
      emailAddresses: [emailSchema]
    });
    //  :            ,                :
    var emailSchema = new mongoose.Schema({
      email: String,
      verified: Boolean
    });
    var userSchema = new mongoose.Schema({
      name: String,
      emailAddresses: [emailSchema]
    });
    
    schemaに静的な方法を作成することができます。この静的な方法は将来Modelで使用されます。この静的な方法を作成するにはschemaを作成した後、Modelコンパイルの前に必要です。
    
     projectSchema.statics.findByUserID = function (userid, callback) {
      this.find({ createdBy: userid }, '_id projectName', {sort: 'modifiedOn'}, callback);
     };
    その対応するモデルを作成してコンパイルした後、以下のように静的方法を呼び出すことができます。
    
    Model.findByUserID(userid,callback);
    この静的な方法はJSON形式のデータを返します。これはAJAX技術を使ってウェブページのデータをロードする時に便利です。次のように。
    
    //    :app.get('/project/byuser/:userid', project.byUser);
    exports.byUser = function (req, res) {
      console.log("Getting user projects");
      if (req.params.userid){
        Project.findByUserID(req.params.userid,function (err, projects) {
          if(!err){
            console.log(projects);
            res.json(projects);
          }else{
            console.log(err);
            res.json({"status":"error", "error":"Error finding projects"});
          }
        });
      }else{
        console.log("No user id supplied");
        res.json({"status":"error", "error":"No user id supplied"});
      }
    };
    
    二、Modelを作成する
    Modelを作成するのは簡単です。
    
    Mongoose.Model('User', userSchema);
    一つはModelの名前で、二つはModelを生成するために必要なschemaで、Modelはschemaでコンパイルされたようです。
    モングースのデータベース接続には2つの方法があります。
    
    //   :
    var dbURI = 'mongodb://localhost/mydatabase';
    mongoose.connect(dbURI);
    //   :
    var dbURI = 'mongodb://localhost/myadmindatabase';
    var adminConnection = mongoose.createConnection(dbURI);
    //         :
    var dbURI = 'mongodb://localhost:27018/mydatabase';
    //            :
    var dbURI = 'mongodb://username:password@localhost/mydatabase';
    //                  :
    var dbURI = 'mongodb://localhost/mydatabase';
    var dbOptions = {'user':'db_username','pass':'db_password'};
    mongoose.connect(dbURI, dbOptions);
    
    データベースを接続する方式によって、私達は第二のModelを作成する方式を得ることができます。データベース接続を使用した引用名来の作成です。
    
    adminConnection.model( 'User', userSchema );
    デフォルトでは、monogoogleは私たちが伝えたModelの名前によって、collectionの名前を生成します。上のコードからusersというcollectionが生成されます。
    私達にcollectionの名前をカスタマイズできる二つの方法があります。
    
    //   ,   schema     collection   :
    var userSchema = new mongoose.Schema({
      name: String,
      email: {type: String, unique:true}
    },
    {
      collection: 'myuserlist'
    });
    //   ,   Model     collection   :
    mongoose.model( 'User', userSchema, 'myuserlist' );
    
    Modelのインスタンスを作成:
    
    var user = new User({ name: 'Simon' });
    userはモデルUserの一例であり、monogoogleにおけるモデルが有するいくつかの方法、例えば保存例を有する。
    
     user.save(function (err) {
       if (err) return handleError(err);
     });
    
    
    モデルもいくつかの常用的な添削の方法を持っています。
    
    User.findOne({'name' : 'Sally', function(err,user) {
      if(!err){
        console.log(user);
      }
    });
    User.find({}, function(err, users) {
      if(!err){
        console.log(users);
      }
    });
    
    これらの方法は、例えば、チェーン方式を用いて使用されてもよい。
    
    var newUser = new User({
      name: 'Simon Holmes',
      email: '[email protected]',
      lastLogin : Date.now()
    }).save( function( err ){
      if(!err){
        console.log('User saved!');
      }
    });
    
    上のコードはモデルのインスタンスを作成して保存します。私たちはもっと簡単な方法でこの仕事を完成することができます。
    
    User.create({
      name: 'Simon Holmes',
      email: '[email protected]',
      lastLogin : Date.now()
    }, function( err, user ){
      if(!err){
        console.log('User saved!');
        console.log('Saved user name: ' + user.name);
        console.log('_id of saved user: ' + user._id);
      }
    });
    
    三、データの検索とデータの読み込み方法
    1.QueryBuiderインターフェースを使ってデータを検索する
    まず次のコードを見てください。
    
    var myQuery = User.find({'name' : 'Simon Holmes'});
    myQuery.where('age').gt(18);
    myQuery.sort('-lastLogin');
    myQuery.select('_id name email');
    myQuery.exec(function (err, users){
      if (!err){
        console.log(users); // output array of users found
      }
    });
    
    コードの中で、名前は「シモンHolmes」で、年齢は18歳以上で、検索結果はlastLogin降順で並べられています。この中の_だけを取得します。id、name、emailの3つのフィールドの値は、上のコードはexecメソッドを呼び出した後にのみ、データベースのクエリを実行します。
    もちろん、チェーン式で上のコードを書き換えることができます。コードはもっと簡潔になります。
    
    User.find({'name' : 'Simon Holmes'})
    .where('age').gt(18)
    .sort('-lastLogin')
    .select('_id name email')
    .exec(function (err, users){
      if (!err){
        console.log(users); // output array of users found
      }
    });
    
    上のコードの最初の行はqueryBuiderを作成しました。このqueryBuilderを使うことによって、いくつかの比較的複雑な検索作業を実行できます。このqueryBuiderを作成した後、クエリ操作はすぐに実行されません。exec方法を実行する時にデータベースの検索を実行します。
    もちろん、データベースを直接検索することができるもう一つの方法があります。検索方法に直接にコールバック関数を追加します。
    
    Model.find(conditions, [fields], [options], [callback])
    簡単な例を以下に挙げます。
    
     User.find({'name', 'simon holmes'}, function(err, user) {});
    もう一つのやや複雑な例:
    
     User.find({'name', 'simon holmes'}, 'name email',function(err, user) {
       //console.log('some thing');
     });
    もう一つのより複雑な例は、クエリー結果の並べ替えを含む。
    
    User.find({'name' : 'Simon Holmes'},
      null, //     null,          
      {sort : {lastLogin : -1}}, //     
      function (err, users){
        if (!err){console.log(users);}
      });
    
    いくつかの比較的実用的な検索方法を列挙します。
    
     Model.find(query);
     Model.findOne(query);//              
     Model.findById(ObjectID);//  ObjectId       
    
    
    たとえば:
    
     User.findOne({'email' : req.body.Email},
     '_id name email',
     function(err, user) {
       //todo
     });
    
    
     2.データの更新
    データを更新する3つの方法があります。
    (1)udate(conditions、udate、options、calback)
    この方法は検索された内容にマッチして更新され、データに戻りません。
    (2)findOneAndUpdate(conditions、udate、options、calback)
    この方法は検索によってデータベースを更新します。また、検索された変更されていないデータを返します。
    (3)findByIdAndUpdate(conditions、udate、options、calback)
    この方法は上のfindOneAndUpdateの方法機能と同じですが、彼はIDに基づいてドキュメントを探して更新しました。
    三つの方法には四つのパラメータが含まれています。いくつかのパラメータの意味を説明します。
  • conditions:クエリー条件
  • udate:更新されたデータオブジェクトは、キーパッドペアを含むオブジェクト
  • である。
  • options:動作の種類を宣言するオプションです。このパラメータについては以下に詳しく説明します。
  • calback:コールバック関数
  • optionsパラメータについては、udate方法において、findOneAndUpdate、findByIdAndUpdateの2つの方法のオプション設定が異なります。
    
    // update   ,options      :
    {
    safe:true|false, //          ,  true
    upsert:false|true, //                ,           ,  false
    multi:false|true, //              ,  false
    strict:true|false //               schema         ,  true
    }
    //  findOneAndUpdate、findByIdAndUpdate     ,   options      :
    {
    new:true|false, //                  ,   true       ,  true
    upsert:false|trure, 
    sort:javascriptObject, //            ,       ,         javascript object      
    select:String //          ,       
    }
    
    以下の例を挙げます。
    
     User.update({_id:user._id},{$set: {lastLogin: Date.now()}},function(){});
    3.データ削除
    データの更新と同じように、データを削除する3つの方法があります。
    
    remove();
    findOneAndRemove();
    findByIdAndRemove();
    remove法には2つの使用方法があり、1つはモデルに使用されるもので、もう1つはモデルのインスタンスに使用されるもので、例えば:
    
    User.remove({ name : /Simon/ } , function (err){
      if (!err){
        //        simon     
      }
    });
    
    User.findOne({ email : '[email protected]'},function (err,user){
      if (!err){
        user.remove( function(err){
          //               
        });
      }
    });
    
    
    次にfindOneAndRemoveの方法を見ます。
    
    User.findOneAndRemove({name : /Simon/},{sort : 'lastLogin', select : 'name email'},function (err, user){
      if (!err) {
        console.log(user.name + " removed");
        // Simon Holmes removed
      };
    });
    
    もう一つのfindByIdAndRemove方法は同じです。
    
    User.findByIdAndRemove(req.body._id,function (err, user) {
      if(err){
        console.log(err);
        return;
      }
      console.log("User deleted:", user);
    });
    
    四、データ検証
    1.モングース内蔵データの検証
    monogoogleでは、データ検証の層はschemaに置かれています。monogoogleはすでに多くの内蔵データの検証をしてくれました。いくつかの検証はいくつかのデータの種類に対して行われています。すべてのデータの種類に対してもいくつかの検証があります。
    すべてのデータタイプに作用することができる検証には、requireがあります。このフィールドが必要かどうか、例えば、
    
    email: { type: String, unique: true, required: true }
    上のコードはemailを定義しました。必要なschemaです。
    次に、それぞれのデータ検証の種類を紹介します。
    デジタルタイプschemasTypeは、Numberタイプのデータに対してminがあり、maxは最大最小値を定義するために提供されます。
    
     var teenSchema = new Schema({
       age : {type: Number, min: 13, max:19}
     });
    文字列タイプSchmastypeは、このタイプのデータに対して、monogoogleは2つの検証器を提供します。
  • match:正規表現を使用して、文字列が正規表現に適合しているかどうかを確認することができる
  • enum:一枚は文字列の使うことができるいくつか値を挙げます。
  • それぞれの例は以下の通りです。
    
    var weekdaySchema = new Schema({
      day : {type: String, match: /^(mon|tues|wednes|thurs|fri)day$/i}
    });
    
    var weekdays = ['monday', 'tuesday', 'wednesday', 'thursday','friday'];
    var weekdaySchema = new Schema({
      day : {type: String, enum: weekdays}
    });
    
    
    いくつかのデータベースを実行するとき、エラーがあったら、いくつかのエラーメッセージを返すかもしれません。これらの情報は一つのオブジェクトにパッケージされています。このオブジェクトのデータフォーマットは大体以下の通りです。
    
    { 
      message: 'Validation failed',
      name: 'ValidationError',
      errors:{ 
        email:{
          message: 'Validator "required" failed for path email',
          name: 'ValidatorError',
          path: 'email',
          type: 'required' 
        },
        name:{ 
          message: 'Validator "required" failed for path name',
          name: 'ValidatorError',
          path: 'name',
          type: 'required' 
        } 
      } 
    }
    
    このエラー情報の具体的なフォーマットを知ってから、私達はそこから私達の欲しい情報を得てコンソールにフィードバックすることができます。
    
    if(err){
      Object.keys(err.errors).forEach(function(key) {
        var message = err.errors[key].message;
        console.log('Validation error for "%s": %s', key, message);
      });
    }
    
    2.カスタムデータ検証
    最も簡単なカスタムデータ検証方式はデータ検証の関数を定義してschemaに渡すことです。
    
    var lengthValidator = function(val) {
      if (val && val.length >= 5){
        return true;
      }
      return false;
    };
    //usage:
    name: {type: String, required: true, validate: lengthValidator }
    
    私たちはschemaにvalidateキーを追加するだけでいいです。validateの対応する値は私たちのユーザー定義の検証方法です。
    しかし、この形式のデータ検証は私達に完全なエラー情報を提供できません。例えば、errors情報から戻ってきたtype値はundefinedになります。
    この上で、エラー情報の中でエラーの説明を返したいなら、少し修正してもいいです。
    
    //code 1
    validate: { validator: lengthValidator, msg: 'Too short' }
    
    //code 2
    var weekdaySchema = new Schema({
      day : {type: String, validate: {validator:/^(mon|tues|wednes|thurs|fri)day$/i, msg: 'Not a day' }
    });
    
    
    validateの値をオブジェクトに変更し、このオブジェクトは検証とエラー記述を含む。
    私たちはまた、これらの検証器を書いている他の方法を使ってもいいです。例えば、schemaの外部にベリファイアをアンインストールすることです。
    
     var validateLength = [lengthValidator, 'Too short' ];
     var validateDay = [/^(mon|tues|wednes|thurs|fri)day$/i, 'Not a day' ];
     //usage:
     name: {type: String, required: true, validate: validateLength }
     day : {type: String, validate: validateDay }
    
    
    目を大きくして、もう一度見てください。間違いなくvalidateに入ってきたのは行列です。元の対象ではありません。
    実はvalidateLengthというもので、彼は簡単に書いたものです。あなたも次のように変えられます。
    
     var validateLength = [
       {validator: lengthValidator, msg: 'Too short'}
     ];
    
    
    はい、ここに来たら、対象を配列に変えてから、複数の検証器が私達に与えたschemaを伝えられます。確かにそうです。
    
     var validateUsername = [
       {validator: lengthValidator, msg: 'Too short'} ,
       {validator: /^[a-z]+$/i, msg: 'Letters only'}
     ];
    
    
    もう一つの方法があります。私たちのschemaに検証器を提供します。
    
    userSchema.path('name').validate(lengthValidator, 'Too short');
    userSchema.path('name').validate(/^[a-z]+$/i, 'Letters only');
    以上が本文の全部です。皆さんの勉強に役に立つように、私たちを応援してください。