summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLauri Ojansivu <x@xet7.org>2017-05-18 10:45:26 +0300
committerLauri Ojansivu <x@xet7.org>2017-05-18 10:45:26 +0300
commit1ed7756d6c23e35d846cabbea3c3770e75a89c71 (patch)
tree1c32fb32517d1394c155d98bf184b0dbb5e5c5c0
parentfe94ab0dde213d40d5e6f11e086678c4425ba377 (diff)
parent8de6461cf7d944bdc056aabd28f28df4f7df28b0 (diff)
downloadwekan-1ed7756d6c23e35d846cabbea3c3770e75a89c71.tar.gz
wekan-1ed7756d6c23e35d846cabbea3c3770e75a89c71.tar.bz2
wekan-1ed7756d6c23e35d846cabbea3c3770e75a89c71.zip
Merge branch 'mayjs-rest-api-pr' into devel
-rw-r--r--models/boards.js26
-rw-r--r--models/cards.js4
-rw-r--r--models/lists.js5
-rw-r--r--models/users.js10
-rw-r--r--server/authentication.js31
5 files changed, 70 insertions, 6 deletions
diff --git a/models/boards.js b/models/boards.js
index 879dde84..8a7844e2 100644
--- a/models/boards.js
+++ b/models/boards.js
@@ -556,6 +556,28 @@ if (Meteor.isServer) {
//BOARDS REST API
if (Meteor.isServer) {
+ JsonRoutes.add('GET', '/api/users/:userId/boards', function (req, res, next) {
+ Authentication.checkLoggedIn(req.userId);
+ const paramUserId = req.params.userId;
+ // A normal user should be able to see their own boards,
+ // admins can access boards of any user
+ Authentication.checkAdminOrCondition(req.userId, req.userId === paramUserId);
+
+ const data = Boards.find({
+ archived: false,
+ 'members.userId': req.userId,
+ }, {
+ sort: ['title'],
+ }).map(function(board) {
+ return {
+ _id: board._id,
+ title: board.title,
+ };
+ });
+
+ JsonRoutes.sendResult(res, {code: 200, data});
+ });
+
JsonRoutes.add('GET', '/api/boards', function (req, res, next) {
Authentication.checkUserId(req.userId);
JsonRoutes.sendResult(res, {
@@ -570,8 +592,9 @@ if (Meteor.isServer) {
});
JsonRoutes.add('GET', '/api/boards/:id', function (req, res, next) {
- Authentication.checkUserId( req.userId);
const id = req.params.id;
+ Authentication.checkBoardAccess( req.userId, id);
+
JsonRoutes.sendResult(res, {
code: 200,
data: Boards.findOne({ _id: id }),
@@ -612,5 +635,4 @@ if (Meteor.isServer) {
},
});
});
-
}
diff --git a/models/cards.js b/models/cards.js
index bbe46b55..c48b4845 100644
--- a/models/cards.js
+++ b/models/cards.js
@@ -373,9 +373,9 @@ if (Meteor.isServer) {
//LISTS REST API
if (Meteor.isServer) {
JsonRoutes.add('GET', '/api/boards/:boardId/lists/:listId/cards', function (req, res, next) {
- Authentication.checkUserId( req.userId);
const paramBoardId = req.params.boardId;
const paramListId = req.params.listId;
+ Authentication.checkBoardAccess( req.userId, paramBoardId);
JsonRoutes.sendResult(res, {
code: 200,
data: Cards.find({ boardId: paramBoardId, listId: paramListId, archived: false }).map(function (doc) {
@@ -389,10 +389,10 @@ if (Meteor.isServer) {
});
JsonRoutes.add('GET', '/api/boards/:boardId/lists/:listId/cards/:cardId', function (req, res, next) {
- Authentication.checkUserId( req.userId);
const paramBoardId = req.params.boardId;
const paramListId = req.params.listId;
const paramCardId = req.params.cardId;
+ Authentication.checkBoardAccess( req.userId, paramBoardId);
JsonRoutes.sendResult(res, {
code: 200,
data: Cards.findOne({ _id: paramCardId, listId: paramListId, boardId: paramBoardId, archived: false }),
diff --git a/models/lists.js b/models/lists.js
index 7dbdc9f2..d9a5b8e2 100644
--- a/models/lists.js
+++ b/models/lists.js
@@ -132,8 +132,9 @@ if (Meteor.isServer) {
//LISTS REST API
if (Meteor.isServer) {
JsonRoutes.add('GET', '/api/boards/:boardId/lists', function (req, res, next) {
- Authentication.checkUserId( req.userId);
const paramBoardId = req.params.boardId;
+ Authentication.checkBoardAccess( req.userId, paramBoardId);
+
JsonRoutes.sendResult(res, {
code: 200,
data: Lists.find({ boardId: paramBoardId, archived: false }).map(function (doc) {
@@ -146,9 +147,9 @@ if (Meteor.isServer) {
});
JsonRoutes.add('GET', '/api/boards/:boardId/lists/:listId', function (req, res, next) {
- Authentication.checkUserId( req.userId);
const paramBoardId = req.params.boardId;
const paramListId = req.params.listId;
+ Authentication.checkBoardAccess( req.userId, paramBoardId);
JsonRoutes.sendResult(res, {
code: 200,
data: Lists.findOne({ _id: paramListId, boardId: paramBoardId, archived: false }),
diff --git a/models/users.js b/models/users.js
index aa870dca..29504aa8 100644
--- a/models/users.js
+++ b/models/users.js
@@ -527,6 +527,16 @@ if (Meteor.isServer) {
// USERS REST API
if (Meteor.isServer) {
+ JsonRoutes.add('GET', '/api/user', function(req, res, next) {
+ Authentication.checkLoggedIn(req.userId);
+ const data = Meteor.users.findOne({ _id: req.userId});
+ delete data.services;
+ JsonRoutes.sendResult(res, {
+ code: 200,
+ data,
+ });
+ });
+
JsonRoutes.add('GET', '/api/users', function (req, res, next) {
Authentication.checkUserId( req.userId);
JsonRoutes.sendResult(res, {
diff --git a/server/authentication.js b/server/authentication.js
index 816c4d4c..23ed8f56 100644
--- a/server/authentication.js
+++ b/server/authentication.js
@@ -17,5 +17,36 @@ Meteor.startup(() => {
};
+ // This will only check if the user is logged in.
+ // The authorization checks for the user will have to be done inside each API endpoint
+ Authentication.checkLoggedIn = function(userId) {
+ if(userId === undefined) {
+ const error = new Meteor.Error('Unauthorized', 'Unauthorized');
+ error.statusCode = 401;
+ throw error;
+ }
+ };
+
+ // An admin should be authorized to access everything, so we use a separate check for admins
+ // This throws an error if otherReq is false and the user is not an admin
+ Authentication.checkAdminOrCondition = function(userId, otherReq) {
+ if(otherReq) return;
+ const admin = Users.findOne({ _id: userId, isAdmin: true });
+ if (admin === undefined) {
+ const error = new Meteor.Error('Forbidden', 'Forbidden');
+ error.statusCode = 403;
+ throw error;
+ }
+ };
+
+ // Helper function. Will throw an error if the user does not have read only access to the given board
+ Authentication.checkBoardAccess = function(userId, boardId) {
+ Authentication.checkLoggedIn(userId);
+
+ const board = Boards.findOne({ _id: boardId });
+ const normalAccess = board.permission === 'public' || board.members.some((e) => e.userId === userId);
+ Authentication.checkAdminOrCondition(userId, normalAccess);
+ };
+
});