npm install express-restify-mongoose --save
This snippet...
var express = require('express')
var bodyParser = require('body-parser')
var methodOverride = require('method-override')
var mongoose = require('mongoose')
var restify = require('express-restify-mongoose')
var app = express()
var router = express.Router()
app.use(bodyParser.json())
app.use(methodOverride())
mongoose.connect('mongodb://localhost/database')
restify.serve(router, mongoose.model('Customer', new mongoose.Schema({
name: { type: String, required: true },
comment: { type: String }
})))
app.use(router)
app.listen(3000, function () {
console.log('Express server listening on port 3000')
})
...automatically generates those endpoints.
GET http://localhost/api/v1/Customers/count
GET http://localhost/api/v1/Customers
PUT http://localhost/api/v1/Customers
POST http://localhost/api/v1/Customers
DELETE http://localhost/api/v1/Customers
GET http://localhost/api/v1/Customers/:id
GET http://localhost/api/v1/Customers/:id/shallow
PUT http://localhost/api/v1/Customers/:id
POST http://localhost/api/v1/Customers/:id
DELETE http://localhost/api/v1/Customers/:id
var query = {
$or: [{
name: '~Another'
}, {
$and: [{
name: '~Product'
}, {
price: '<=10'
}]
}],
price: 20
}
request({
url: '/api/v1/Model',
qs: {
query: encodeURIComponent(JSON.stringify(query))
}
})
GET http://localhost/api/v1/Customers?name=~regex
GET http://localhost/api/v1/Customers?name=value
GET http://localhost/api/v1/Customers?name=>value
GET http://localhost/api/v1/Customers?name=>=value
GET http://localhost/api/v1/Customers?name=<value
GET http://localhost/api/v1/Customers?name=<=value
GET http://localhost/api/v1/Customers?name=!=value
GET http://localhost/api/v1/Customers?select=name
GET http://localhost/api/v1/Customers?select=-name
GET http://localhost/api/v1/Customers?sort=name
GET http://localhost/api/v1/Customers?sort=-name
GET http://localhost/api/v1/Customers?skip=10&limit=10
Populated fields will not have any effect on select fields as supported by Mongoose, they will be fetched along with select fields.
GET http://localhost/api/v1/Invoices?populate=customer
GET http://localhost/api/v1/Invoices?populate=customer&select=amount
GET http://localhost/api/v1/Invoices?populate=customer&select=customer.name
GET http://localhost/api/v1/Invoices?populate=customer&select=customer,amount
GET http://localhost/api/v1/Invoices?populate=customer&select=customer.name,amount
restify.serve(router, model[, options])
router: express.Router() instance (Express 4), app object (Express 3) or server object (restify)
model: mongoose model
options: object type default version
Path to prefix to the REST endpoint.
API version that will be prefixed to the rest path.
If prefix or version contains /:id
, then that will be used as the location to search for the id.
version: '/v1/Entities/:id'
generates /api/v1/Entities/:id/Model
and /api/v1/Entities/Model
for all pertinent methods
findById
and findByIdAnd*
methods will query on the given property
An Express middleware or an array of Express middlewares that will be called after prereq and before access.
middleware: function (req, res, next) {
console.log('Incoming %s request', req.method)
}
Returns or yields true or false. It is called on POST, PUT and DELETE requests and sends 403 (Forbidden) on false.
Sync
prereq: function (req) {
if (req.isAuthenticated()) {
return true
}
return false
}
Async
prereq: function (req, cb) {
performAsyncLogic(function (err, result) {
cb(err, true)
})
}
Returns or yields 'private', 'protected' or 'public'. It is called on GET, POST and PUT requests and filters out the fields defined in private and protected.
Sync:
access: function (req) {
if (req.isAuthenticated()) {
return req.user.isAdmin ? 'private' : 'protected'
} else {
return 'public'
}
}
Async
access: function (req, cb) {
performAsyncLogic(function (err, result) {
cb(err, 'public')
})
}
Enable support for restify instead of Express.
Automatically pluralize the model's name using inflection.
Whether to call .toLowerCase()
on the model's name before generating the routes.
The endpoint's name.
Set a hard limit on the number of documents to return. Cannot be overriden by the client.
A function with the signature function (err, req, res, next)
that is used to output an error. err
is the error object that is returned by mongoose.
onError: function (err, req, res, next) {
next(err)
}
A function with the signature function (req, res, result)
that is used to output the result. res
is a restify or express response object and result
is the data returned by mongoose.
outputFn: function (req, res, result) {
if (result.length > 100) {
result.length = 100
}
res.status(200).json(result)
}
Array of fields which are only to be returned by queries that have private access.
private: ['topSecret', 'fields']
Array of fields which are only to be returned by queries that have private or protected access.
private: ['somewhatSecret', 'keys']
A middleware to be called after a successful response has been sent. If an error is sent to the client, this is not called.
postProcess: function (req, res, next) {
console.log('Successful %s request', req.method)
}
Whether or not mongoose should use .lean()
to convert results to plain old JavaScript objects. This is bad for performance, but allows returning virtuals, getters and setters.
If false
, will first find documents by id and then call save, allowing document middleware to be called. For more information regarding mongoose middleware, read the docs.
If false
, will first find documents by id and then call remove, allowing document middleware to be called. For more information regarding mongoose middleware, read the docs.
A function with the signature function (model, req, cb)
that allows request specific filtering.
contextFilter: function (model, req, cb) {
cb(model.find({
user: req.user._id
}))
}
A function with the signature function (res, result, done)
which is run after creating a document.
A function with the signature function (res, result, done)
which is run after updating a document.
A function with the signature function (res, result, done)
which is run after deleting a document.
restify.defaults(options)
options: same as above, sets this object as the defaults for anything you .serve()
afterwards.