about 2 years ago

系列文一
系列文二
系列文三

Sequelize

Sequelize是個很棒的MySQL ORM,抽象化Database的操作,不用寫SQL就可以輕鬆操作指令,大幅增加開發速度與可維護性,目前Sequelize支援關聯式DB-Postgres、MySQL、MariaDB、Sqlite,以下採用MySQL。
源碼參考-index.js

1.安裝
npm install sequelize mysql --save
2.連結DB

我是使用Docker創建MySQL container,指令參考

docker pull mysql
docker run --name mysql -p 3306:3306 -e MYSQL_ROOT_PASSWORD=password -d mysql

接著編輯index.js,全部就這一個JS file
參數設定應該蠻直覺的,補充最後一個loggin,Sequelize會將每一步都轉成SQL打印出來,可以選擇關掉

var Sequelize = require("sequelize");
// DB name , username, password
let sequelize = new Sequelize('test', 'root', 'test1', {
    host: '192.168.99.100',
    dialect: 'mysql',
    pool: {
        max: 10,
        min: 0,
        idle: 10000
    },
    logging: false
});

記得要先創建Databse,才能接續下面的動作。OS:DB圖形化Client可以參考Sequel Pro

3.創建table

創建Table可以說是很重要的一步,Sequelize提供非常非常大量的設定與支援,以下逐一介紹
a. 最基本的欄位設定(MySQL支援的)typeprimaryKeyautoIncrementdefaultValueallowNull,這幾個是我覺得比較常用到的,另外field則代表在DB中欄位值(ex.first_name),但是操作sequelize object還是要用前面設定的名稱('firstname')
b. Validate:Sequelize結合validator.js,透過簡單的定義就可以做欄位值的確認,支援正規語法、Email確認、字串長度、最大小值,相當方便啊!同時提供客製化錯誤訊息(見firstname欄位)
另外有個tricky是 如果你沒有設定allowNull為false,那假設使用者輸入null那validation都不會被觸發!
c. Setter和Getter:Sequelize提供相當強大且貼心的服務,我目前是將setter應用在欄位password上,當設定password時會自動轉成hmac;getter則應用在firstname上,每次呼叫自動將值轉為大寫,但這不影響DB裡的值!
d. Options:基本參數設定

參數 說明
freezeTableName Sequelize會自動在table名稱後加s,如果不想要Sequelize亂動table名稱就設為false
timestamps Sequelize會自動加上createAt和updateAt,並自動帶上系統時間
getterMethods/setterMethods 我是copy官網範例,這裡設定的fullname是不會出現在DB中,設定的目的在於讓Sequelize object更方便操作,實際情況參考下方範例
var User = sequelize.define('user', {
  id:{
    type: Sequelize.INTEGER,
    autoIncrement: true,
    primaryKey: true
  },
  account: {
    type: Sequelize.STRING,
    allowNull: false,
    unique: true
  },
  password: {
    type: Sequelize.STRING,
    set: function(val) {
      hmac.update(val);
      this.setDataValue('password', hmac.digest('hex'));
    }
  },
  createAtTime:{
    type: Sequelize.DATE,
    defaultValue: Sequelize.NOW
  },
  firstname:{
    type: Sequelize.STRING,
    field: 'first_name',
    validate:{
      len:{
        args:[2,10],
        msg:"length of firstname is not allowed"
      }
    },
    get : function()  {
      return this.getDataValue('firstname').toUpperCase();
    },
  },
  lastname:{
    type: Sequelize.STRING,
    validate:{
      notEmpty: true
    }
  }
}, {
  freezeTableName: true,
  timestamps: false,
  getterMethods   : {
    fullName       : function()  { return this.firstname + ' ' + this.lastname }
  },
  setterMethods   : {
    fullName       : function(value) {
        var names = value.split(' ');
        this.setDataValue('firstname', names.slice(0, -1).join(' '));
        this.setDataValue('lastname', names.slice(-1).join(' '));
    },
  }
});
4.創建欄位

建立好table接著就是創建欄位了,

  1. User.sync({force:true})翻譯成SQL=>DROP TABLE IF EXISTS 'user' CREATE TABLE IF NOT EXISTS 'user',每次都會刪除在建立,去掉force:true就不會刪除。
  2. User.create創立欄位,回傳promise
  3. 在then function接到創立成功的user json object,透過操做get和set了解上面的設定
  4. 如果要更新則使用 user.save(),此時DB的值才會跟著更新喔!
User.sync({force: true})
.then(()=>{
    return User.create({account:'test1',password:'test1',firstname:'cheng',lastname:'yj'});
}).then((user)=>{
    console.log(user.get('firstname')); //全大寫
    console.log(user.get('fullName'));  //可以看到 firstname也是大寫顯示
    user.set('fullName', 'hello world'); //改名
    console.log(user.get('fullName'));
    user.save(); //儲存回DB
}).catch((err)=>{
    console.log(err);
});

創建完成後,接著就看基本的CRUD操作囉~

← Oauth2-Gihub/Google+/Facebook登入實戰-使用NodeJS 從RSA加密原理到實踐: 使用OpenSSL →
 
comments powered by Disqus