Node的關系型數據庫ORM庫:bookshelf


NodeJs 關系數據庫ORM庫:Bookshelf.js

bookshelf.js是基於knex的一個關系型數據庫的ORM庫。簡單易用,內置了Promise的支持。這里主要羅列一些使用的例子,例子就是最好的教程。下面就是用mysql作為實例數據庫表明bookshelf如何使用。其他的幾個關系型數據庫使用上基本一致,只是配置等地方需要使用的名稱各自不同。為了更加貼近實際全部的例子都會放在Express打造的RESTful服務里。

安裝bookshelf和knex

首先需要安裝庫knex和bookshelf,其次還需要安裝你的數據庫對應的包:

npm install knex --save
npm install bookshelf --save

接下來,安裝對應於你要使用的數據庫的driver包。下面列出了三個比較典型的,只需要選擇一個安裝就可以。

npm install pg --save       // PostgreSQL
npm install mysql --save    // MySQL
npm install sqlite3 --save  // SQLite

連接數據庫

連接數據庫就是非常的簡單的,只需要傳入一個JSON格式的配置:

var knex        = require('knex'),
    db;    // 數據庫連接

// 數據庫連接配置
var config = {
    client: 'mysql',        // 其他可以是pg、sqlite3
    connection: {
        host: 'localhost',
        user: 'root',
        password: '123456',
        database: 'petshop', // 數據庫名稱
        charset: 'utf8'
    }
};

// 保證數據庫連接只初始化一次。
if (!db) {
    db = knex(config);
}

接下來就該讓bookshelf出馬了:

var bookshelf = require('bookshelf')(db);

正式開始前,假設你現在有這么兩個表Pet和User,分別存儲寵物和寵物店的用戶數據:

--pet
CREATE TABLE `pet` (
  `petId` int(11) NOT NULL AUTO_INCREMENT,
  `name` varchar(45) DEFAULT NULL,
  `type` int(11) DEFAULT NULL,
  `quantity` int(11) DEFAULT NULL,
  `userId` int(11) NOT NULL,    -- 外鍵,和哪個用戶關聯
  PRIMARY KEY (`petId`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;


--user
CREATE TABLE `user` (
  `userId` int(11) NOT NULL AUTO_INCREMENT,
  `username` varchar(45) DEFAULT NULL,
  `password` varchar(45) DEFAULT NULL,
  `email` varchar(105) DEFAULT NULL,
  PRIMARY KEY (`userId`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;

Express打造的RESTful服務代碼:

var Promise     = require('bluebird'),
    express     = require('express'),
    bodyParser  = require('body-parser'),
    session     = require('express-session');

var app = express();

app.use(bodyParser.json());
app.use(bodyParser.urlencoded({extended: true}));

app.use(session({
    secret: 'abcdefghijklmnopqrstuvwxyz1234567890',
    resave: false,
    saveUninitialized: true
    // cookie: {secure: true}
}));

var models = require('./bookshelf');
var router = express.Router();

router.get('/', function(req, res) {
    res.send('Hello bookshelf');
});

/**
 * 添加
 */
router.route('/add').post(function(req, res) {
    // ...
});

/** 
 * 更新
 */
router.route('/update').post(function(req, res) {
    // ...
});

app.use('/bookshelf', router);

app.listen(4000, function(){
    console.log('express is running on http://localhost:4000');
});

為了正常使用還需要安裝某些包body-parser,這個包用來解析post發送上來的數據。bluebirdexpress-session什么的可以選擇不裝,不影響。

Model

ORM,這model是必須不可以少的。如何讓model來對應於數據庫的table呢:

var Pet = bookshelf.Model.extend({
    tableName: 'pet',
});

現在就可以使用Pet來處理pet表的數據了。

上面是理論上的。回到本例中。首先在根目錄下創建一個文件夾bookshelf,然后添加文件model.js

添加數據

給表添加一條記錄:

new Pet({
    name: 'King',
    type: 1, // 1: dog, 2: cat...
    quantity: 10,
    userId: 123456
}).save().then(function(model){
    console.log(model);
}).catch(function(err) {
    console.log(err);
});

放在RESTful API里:

router.route('/add').post(function(req, res) {
    var pet = new models.Pet({
        name: req.body.name,
        type: req.body.type,
        quantity: req.body.quantity,
        userId: req.body.userId
    });

    pet.save().then(function(model){
        res.json({message:'done', data: pet});
    }).catch(function(err){
        res.json({message: 'error', data: err});
    });
});

在處理數據的時候可以使用bookshelf提供的很多“靜態方法”。上面的extend就是這些靜態方法中的一個。創建新的model的時候就可以是用靜態方法里的一個forge,這樣就不用new的方式了。

    models.Pet.forge({
        name: req.body.name,
        type: req.body.type,
        quantity: req.body.quantity,
        userId: req.body.userId
    }).save().then(function(pet){
        res.json({message:'done', data: pet});
    }).catch(function(err){
        res.json({message: 'error', data: err});
    });

查找數據

添加了數據就可以查找出來了。

查找全部

查找全部的數據:

router.route('/findall').get(function(req, res) {
    models.Pet.forge().fetchAll().then(function(pets) {
        res.json({message: 'done', data: pets});
    }).catch(function(err) {
        res.json({message: 'error', data: err});
    });
});

在瀏覽器里輸入地址:http://localhost:4000/bookshelf/findall可以查找出全部的pet數據。

查找某一個Pet

router.route('/find/:petId').get(function(req, res) {
    models.Pet.forge({
        petId: req.params.petId
    }).fetch().then(function(pet) {
        res.json({message: 'done', data: pet});
    }).catch(function(err) {
        res.json({message: 'error', data: err});
    });
});

在瀏覽器里輸入地址:http://localhost:4000/bookshelf/find/1可以查找出petId為1的數據。

我們在上一個例子中已經創建了一條記錄,所以現在可以搜出來一條記錄。

更多的更復雜的查找可以使用方法query,查看這里了解更多。

更新數據

更新和創建一條新紀錄,在寫法上沒什么太大的區別。只不過你需要在save方法里設置需要更新的數據。但是有一個限制條件,就是需要在forge方法里給出id,必須是這個詞id。如果你的Primary key不是這個名稱,那么就稍微復雜一點了。必須給出where條件,比如:

router.route('/update/:petId').post(function(req, res) {
    models.Pet.forge()
    .where('petId', '=', req.params.petId)
    .save({
        name: req.body.name,
        type: req.body.type,
        quantity: req.body.quantity,
        userId: req.body.userId
    }, {patch: true}).then(function(pet) {
        res.json({message: 'done', data: pet});
    }).catch(function(err) {
        res.json({message: 'error', data: err});
    });
});

更多關於where內容可以查看這里

刪除記錄

最后可以刪除記錄。

router.route('/delete/:petId').get(function(req, res) {
    models.Pet.forge()
    .where('petId', '=', req.params.petId)
    .destroy()
    .then(function(pet) {
        res.json({message: 'done', data: pet});
    })
    .catch(function(err) {
        res.json({message: 'error', data: err});
    });
});

最后

bookshelf這個庫非常好用。不過這些還只是比較常用的一部分功能。還有很多的關系數據庫的一對一、一對多以及多對多的關系的處理。
這些都可以在官方文檔中查找到。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM