Archived
2

model routes

This commit is contained in:
VLE2FE
2020-08-13 12:07:40 +02:00
parent d363064dba
commit 08a9a12372
8 changed files with 273 additions and 11 deletions

197
src/routes/model.spec.ts Normal file
View File

@ -0,0 +1,197 @@
import should from 'should/as-function';
import ModelModel from '../models/model';
import TestHelper from "../test/helper";
describe('/model', () => {
let server;
before(done => TestHelper.before(done));
beforeEach(done => server = TestHelper.beforeEach(server, done));
afterEach(done => TestHelper.afterEach(server, done));
after(done => TestHelper.after(done));
describe('GET /model/{name}', (() => {
it('returns the binary data', done => {
TestHelper.request(server, done, {
method: 'get',
url: '/model/modela',
auth: {basic: 'admin'},
httpStatus: 200,
contentType: 'application/octet-stream; charset=utf-8',
}).end((err, res) => {
if (err) return done (err);
should(res.body.toString()).be.eql('binary data');
done();
});
});
it('returns the binary data for an API key', done => {
TestHelper.request(server, done, {
method: 'get',
url: '/model/modela',
auth: {key: 'admin'},
httpStatus: 200,
contentType: 'application/octet-stream; charset=utf-8',
}).end((err, res) => {
if (err) return done (err);
should(res.body.toString()).be.eql('binary data');
done();
});
});
it('returns 404 for an unknown name', done => {
TestHelper.request(server, done, {
method: 'get',
url: '/model/modelx',
auth: {basic: 'admin'},
httpStatus: 404
})
});
it('rejects requests from a write user', done => {
TestHelper.request(server, done, {
method: 'get',
url: '/model/modela',
auth: {basic: 'janedoe'},
httpStatus: 403
})
});
it('rejects unauthorized requests', done => {
TestHelper.request(server, done, {
method: 'get',
url: '/model/modela',
httpStatus: 401
})
});
}));
describe('POST /model/{name}', () => {
it('stores the data', done => {
TestHelper.request(server, done, {
method: 'post',
url: '/model/modelb',
auth: {basic: 'admin'},
httpStatus: 200,
reqContentType: 'application/octet-stream',
req: 'another binary data'
}).end((err, res) => {
if (err) return done (err);
should(res.body).be.eql({status: 'OK'});
ModelModel.find({name: 'modelb'}).lean().exec((err, data) => {
if (err) return done (err);
should(data).have.lengthOf(1);
should(data[0]).have.only.keys('_id', 'name', 'data', '__v');
should(data[0]).have.property('name', 'modelb');
should(data[0].data.buffer.toString()).be.eql('another binary data');
done();
});
});
});
it('stores the data with an API key', done => {
TestHelper.request(server, done, {
method: 'post',
url: '/model/modelb',
auth: {key: 'admin'},
httpStatus: 200,
reqContentType: 'application/octet-stream',
req: 'another binary data'
}).end((err, res) => {
if (err) return done (err);
should(res.body).be.eql({status: 'OK'});
ModelModel.find({name: 'modelb'}).lean().exec((err, data) => {
if (err) return done (err);
should(data).have.lengthOf(1);
should(data[0]).have.only.keys('_id', 'name', 'data', '__v');
should(data[0]).have.property('name', 'modelb');
should(data[0].data.buffer.toString()).be.eql('another binary data');
done();
});
});
});
it('overwrites existing data', done => {
TestHelper.request(server, done, {
method: 'post',
url: '/model/modela',
auth: {basic: 'admin'},
httpStatus: 200,
reqContentType: 'application/octet-stream',
req: 'another binary data'
}).end((err, res) => {
if (err) return done (err);
should(res.body).be.eql({status: 'OK'});
ModelModel.find({name: 'modela'}).lean().exec((err, data) => {
if (err) return done (err);
should(data).have.lengthOf(1);
should(data[0]).have.only.keys('_id', 'name', 'data', '__v');
should(data[0]).have.property('name', 'modela');
should(data[0].data.buffer.toString()).be.eql('another binary data');
done();
});
});
});
it('rejects requests from a write user', done => {
TestHelper.request(server, done, {
method: 'post',
url: '/model/modelb',
auth: {basic: 'janedoe'},
httpStatus: 403,
req: 'another binary data'
});
});
it('rejects unauthorized requests', done => {
TestHelper.request(server, done, {
method: 'post',
url: '/model/modelb',
httpStatus: 401,
req: 'another binary data'
});
});
});
describe('DELETE /model/{name}', () => {
it('deletes the data', done => {
TestHelper.request(server, done, {
method: 'delete',
url: '/model/modela',
auth: {basic: 'admin'},
httpStatus: 200
}).end((err, res) => {
if (err) return done(err);
should(res.body).be.eql({status: 'OK'});
ModelModel.find({name: 'modela'}).lean().exec((err, data) => {
if (err) return done(err);
should(data).have.lengthOf(0);
done();
});
});
});
it('returns 404 for an unknown name', done => {
TestHelper.request(server, done, {
method: 'delete',
url: '/model/modelx',
auth: {basic: 'admin'},
httpStatus: 404
});
});
it('rejects an API key', done => {
TestHelper.request(server, done, {
method: 'delete',
url: '/model/modela',
auth: {key: 'admin'},
httpStatus: 401
});
});
it('rejects a write user', done => {
TestHelper.request(server, done, {
method: 'delete',
url: '/model/modela',
auth: {basic: 'janedoe'},
httpStatus: 403
});
});
it('rejects an unauthorized request', done => {
TestHelper.request(server, done, {
method: 'delete',
url: '/model/modela',
httpStatus: 401
});
});
});
});

47
src/routes/model.ts Normal file
View File

@ -0,0 +1,47 @@
import express from 'express';
import bodyParser from 'body-parser';
import ModelModel from '../models/model';
const router = express.Router();
router.get('/model/:name', (req, res, next) => {
if (!req.auth(res, ['dev', 'admin'], 'all')) return;
ModelModel.findOne({name: req.params.name}).lean().exec((err, data) => {
if (err) return next(err);
if (data) {
res.set('Content-Type', 'application/octet-stream');
res.send(data.data.buffer);
}
else {
res.status(404).json({status: 'Not found'});
}
});
});
router.post('/model/:name', bodyParser.raw({limit: '500kb'}), (req, res, next) => {
if (!req.auth(res, ['dev', 'admin'], 'all')) return;
ModelModel.replaceOne({name: req.params.name}, {name: req.params.name, data: req.body}).setOptions({upsert: true})
.lean().exec(err => {
if (err) return next(err);
res.json({status: 'OK'});
});
});
router.delete('/model/:name', (req, res, next) => {
if (!req.auth(res, ['dev', 'admin'], 'basic')) return;
ModelModel.findOneAndDelete({name: req.params.name}).lean().exec((err, data) => {
if (err) return next(err);
if (data) {
res.json({status: 'OK'});
}
else {
res.status(404).json({status: 'Not found'});
}
});
});
module.exports = router;