handlers: permisison check for all pages + retrieve user-specific permissions for pages (if any)

This commit is contained in:
Albert S. 2019-05-03 15:59:29 +02:00
parent e87c3a0f4d
commit 7630301168
23 changed files with 167 additions and 34 deletions

View File

@ -74,3 +74,19 @@ QueryOption Handler::queryOption(const Request &r) const
return result;
}
Response Handler::handle(const Request &r)
{
if(!canAccess(this->userSession->user.permissions))
{
return errorResponse("Permission denied", accessErrorMessage());
}
return handleRequest(r);
}
Permissions Handler::effectivePermissions(std::string page)
{
return this->database->createPermissionsDao()
->find(page, this->userSession->user.login)
.value_or(this->userSession->user.permissions);
}

View File

@ -18,6 +18,8 @@ class Handler
Session *userSession;
UrlProvider *urlProvider;
// TODO: may not to find a better place for this method
Permissions effectivePermissions(std::string page);
QueryOption queryOption(const Request &r) const;
public:
@ -29,7 +31,21 @@ class Handler
this->urlProvider = &provider;
this->cache = &cache;
}
virtual Response handle(const Request &r) = 0;
virtual Response handle(const Request &r);
virtual Response handleRequest(const Request &r)
{
return this->errorResponse("Invalid action", "This action is not implemented yet");
}
virtual bool canAccess(const Permissions &perms)
{
return false;
}
virtual std::string accessErrorMessage()
{
return "No permission for this action";
}
void setGeneralVars(TemplatePage &page);
virtual ~Handler()
{

View File

@ -21,7 +21,7 @@ SOFTWARE.
#include "handlerallcategories.h"
#include "../urlprovider.h"
#include "../logger.h"
Response HandlerAllCategories::handle(const Request &r)
Response HandlerAllCategories::handleRequest(const Request &r)
{
auto categoryDao = this->database->createCategoryDao();
QueryOption qo = queryOption(r);
@ -43,3 +43,13 @@ Response HandlerAllCategories::handle(const Request &r)
response.setStatus(200);
return response;
}
std::string HandlerAllCategories::accessErrorMessage()
{
return "You don't have permission to list all categories";
}
bool HandlerAllCategories::canAccess(const Permissions &perms)
{
return perms.canSeeCategoryList();
}

View File

@ -8,7 +8,9 @@ class HandlerAllCategories : public Handler
public:
HandlerAllCategories();
using Handler::Handler;
Response handle(const Request &r) override;
Response handleRequest(const Request &r) override;
std::string accessErrorMessage() override;
bool canAccess(const Permissions &perms) override;
};
#endif // HANDLERALLCATEGORIES_H

View File

@ -20,7 +20,7 @@ SOFTWARE.
*/
#include "handlerallpages.h"
Response HandlerAllPages::handle(const Request &r)
Response HandlerAllPages::handleRequest(const Request &r)
{
try
{
@ -46,3 +46,13 @@ Response HandlerAllPages::handle(const Request &r)
return errorResponse("Error", "An unknown error occured");
}
}
std::string HandlerAllPages::accessErrorMessage()
{
return "You don't permissions to list all pages";
}
bool HandlerAllPages::canAccess(const Permissions &perms)
{
return perms.canSeePageList();
}

View File

@ -7,7 +7,9 @@ class HandlerAllPages : public Handler
public:
HandlerAllPages();
using Handler::Handler;
Response handle(const Request &r) override;
Response handleRequest(const Request &r) override;
std::string accessErrorMessage() override;
bool canAccess(const Permissions &perms) override;
};
#endif // HANDLERALLPAGES_H

View File

@ -20,7 +20,7 @@ SOFTWARE.
*/
#include "handlercategory.h"
Response HandlerCategory::handle(const Request &r)
Response HandlerCategory::handleRequest(const Request &r)
{
try
{
@ -48,3 +48,13 @@ Response HandlerCategory::handle(const Request &r)
return errorResponse("Error", "An unknown error occured");
}
}
std::string HandlerCategory::accessErrorMessage()
{
return "You don't have permission to view categories";
}
bool HandlerCategory::canAccess(const Permissions &perms)
{
return perms.canRead(); // TODO: we may need a more specific permission
}

View File

@ -7,7 +7,9 @@ class HandlerCategory : public Handler
public:
HandlerCategory();
using Handler::Handler;
Response handle(const Request &r) override;
Response handleRequest(const Request &r) override;
std::string accessErrorMessage() override;
bool canAccess(const Permissions &perms) override;
};
#endif // HANDLERCATEGORY_H

View File

@ -20,7 +20,7 @@ SOFTWARE.
*/
#include "handlerdefault.h"
Response HandlerDefault::handle(const Request &r)
Response HandlerDefault::handleRequest(const Request &r)
{
return Response::redirectTemporarily(this->urlProvider->index());
}
@ -28,3 +28,8 @@ Response HandlerDefault::handle(const Request &r)
HandlerDefault::~HandlerDefault()
{
}
bool HandlerDefault::canAccess(const Permissions &perms)
{
return true;
}

View File

@ -5,9 +5,10 @@
class HandlerDefault : public Handler
{
public:
Response handle(const Request &r) override;
Response handleRequest(const Request &r) override;
~HandlerDefault() override;
using Handler::Handler;
bool canAccess(const Permissions &perms) override;
};
#endif // HANDLERDEFAULT_H

View File

@ -23,11 +23,27 @@ SOFTWARE.
#include "../htmllink.h"
#include "../logger.h"
#include "../database/exceptions.h"
Response HandlerHistory::handle(const Request &r)
Response HandlerHistory::handleRequest(const Request &r)
{
QueryOption qo = queryOption(r);
std::string page = r.get("page");
if(page.empty())
{
if(!this->userSession->user.permissions.canSeeGlobalHistory())
{
return errorResponse("Permission denied", "You can't see the changes history on this wiki", 403);
}
}
else
{
Permissions perms = effectivePermissions(page);
if(!perms.canSeePageHistory())
{
return errorResponse("Permission denied", "You cannot see the changes history of this page", 403);
}
}
unsigned int count = 0;
std::vector<Revision> resultList;
auto revisionDao = this->database->createRevisionDao();
@ -102,3 +118,8 @@ Response HandlerHistory::handle(const Request &r)
response.setStatus(200);
return response;
}
bool HandlerHistory::canAccess(const Permissions &perms)
{
return true; // This is a lie but we need to this a little more fine grained here, which we do in the handleRequest
}

View File

@ -8,7 +8,8 @@ class HandlerHistory : public Handler
public:
HandlerHistory();
using Handler::Handler;
Response handle(const Request &r) override;
Response handleRequest(const Request &r) override;
bool canAccess(const Permissions &perms) override;
};
#endif // HANDLERHISTORY_H

View File

@ -20,7 +20,12 @@ SOFTWARE.
*/
#include "handlerinvalidaction.h"
Response HandlerInvalidAction::handle(const Request &r)
Response HandlerInvalidAction::handleRequest(const Request &r)
{
return errorResponse("Invalid action", "No action defined for this action");
}
bool HandlerInvalidAction::canAccess(const Permissions &perms)
{
return true;
}

View File

@ -5,10 +5,11 @@
class HandlerInvalidAction : public Handler
{
public:
Response handle(const Request &r) override;
Response handleRequest(const Request &r) override;
~HandlerInvalidAction() override
{
}
bool canAccess(const Permissions &perms) override;
using Handler::Handler;
};

View File

@ -64,7 +64,7 @@ std::vector<char> HandlerLogin::pbkdf5(std::string password, const std::vector<c
return result;
}
Response HandlerLogin::handle(const Request &r)
Response HandlerLogin::handleRequest(const Request &r)
{
auto createErrorReesponse = [&]() {
return errorResponse("Login error", "The supplied credenetials are incorrect");
@ -85,6 +85,10 @@ Response HandlerLogin::handle(const Request &r)
{
return createErrorReesponse();
}
if(!user->enabled)
{
return errorResponse("Login failed", "The user account has been disabled");
}
auto hashresult = pbkdf5(password, user.value().salt);
// TODO: timing attack
@ -116,3 +120,8 @@ Response HandlerLogin::handle(const Request &r)
result.setBody(loginTemplatePage.render());
return result;
}
bool HandlerLogin::canAccess(const Permissions &perms)
{
return true;
}

View File

@ -12,10 +12,11 @@ class HandlerLogin : public Handler
public:
HandlerLogin();
Response handle(const Request &r) override;
Response handleRequest(const Request &r) override;
~HandlerLogin() override
{
}
bool canAccess(const Permissions &perms) override;
using Handler::Handler;
};

View File

@ -18,6 +18,7 @@ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
*/
#include <optional>
#include "handlerpage.h"
Response HandlerPage::handle(const Request &r)

View File

@ -21,6 +21,21 @@ SOFTWARE.
#include "handlerpagedelete.h"
#include "../database/exceptions.h"
bool HandlerPageDelete::pageMustExist()
{
return true;
}
bool HandlerPageDelete::canAccess(std::string page)
{
return effectivePermissions(page).canDelete();
}
std::string HandlerPageDelete::accessErrorMessage()
{
return "You don't have permission to delete pages";
}
Response HandlerPageDelete::handleRequest(PageDao &pageDao, std::string pagename, const Request &r)
{
try

View File

@ -4,20 +4,11 @@
class HandlerPageDelete : public HandlerPage
{
bool pageMustExist() override
{
return true;
}
bool pageMustExist() override;
bool canAccess(std::string page) override
{
return this->userSession->user.permissions.canDelete();
}
bool canAccess(std::string page) override;
std::string accessErrorMessage() override
{
return "You don't have permission to delete pages";
}
std::string accessErrorMessage() override;
public:
Response handleRequest(PageDao &pageDao, std::string pagename, const Request &r) override;

View File

@ -26,7 +26,12 @@ SOFTWARE.
bool HandlerPageView::canAccess(std::string page)
{
return this->userSession->user.permissions.canRead();
return effectivePermissions(page).canRead();
}
std::string HandlerPageView::accessErrorMessage()
{
return "You don't have permission to view this page";
}
std::string HandlerPageView::createIndexContent(IParser &parser, std::string content)

View File

@ -9,10 +9,7 @@ class HandlerPageView : public HandlerPage
{
protected:
bool canAccess(std::string page) override;
std::string accessErrorMessage() override
{
return "You don't have permission to view this page";
}
std::string accessErrorMessage() override;
std::string createIndexContent(IParser &parser, std::string content);
public:

View File

@ -19,7 +19,7 @@ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
*/
#include "handlersearch.h"
Response HandlerSearch::handle(const Request &r)
Response HandlerSearch::handleRequest(const Request &r)
{
Response response;
std::string q = r.get("q");
@ -61,3 +61,13 @@ Response HandlerSearch::handle(const Request &r)
return errorResponse("Technical Error", "The system failed to perform your search");
}
}
bool HandlerSearch::canAccess(const Permissions &perms)
{
return perms.canSearch();
}
std::string HandlerSearch::accessErrorMessage()
{
return "You are not allowed to search this wiki";
}

View File

@ -7,7 +7,9 @@ class HandlerSearch : public Handler
public:
HandlerSearch();
using Handler::Handler;
Response handle(const Request &r) override;
Response handleRequest(const Request &r) override;
bool canAccess(const Permissions &perms) override;
std::string accessErrorMessage();
};
#endif // HANDLERSEARCH_H