Compare commits
6 Commits
aa362331a5
...
c0049fc7b6
Author | SHA1 | Date | |
---|---|---|---|
c0049fc7b6 | |||
fe533a5076 | |||
ec3cbe3f76 | |||
1095d38b02 | |||
234db99ef5 | |||
32af0e2857 |
30
cache/nocache.h
vendored
Normal file
30
cache/nocache.h
vendored
Normal file
@ -0,0 +1,30 @@
|
|||||||
|
#include "icache.h"
|
||||||
|
|
||||||
|
class NoCache : public ICache
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
NoCache(std::string p)
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
virtual std::optional<std::string> get(std::string_view key) const
|
||||||
|
{
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
virtual void put(std::string_view key, std::string val)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
virtual void remove(std::string_view key)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
virtual void removePrefix(std::string_view prefix)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
virtual void clear()
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
};
|
@ -13,7 +13,7 @@
|
|||||||
#include "permissionsdao.h"
|
#include "permissionsdao.h"
|
||||||
class Database
|
class Database
|
||||||
{
|
{
|
||||||
private:
|
protected:
|
||||||
std::string connnectionstring;
|
std::string connnectionstring;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
@ -54,7 +54,7 @@ void SessionDaoSqlite::fillSession(int userid, Session &sess)
|
|||||||
{
|
{
|
||||||
if(userid > -1)
|
if(userid > -1)
|
||||||
{
|
{
|
||||||
UserDaoSqlite userDao{this->db};
|
UserDaoSqlite userDao{*this->db};
|
||||||
auto u = userDao.find(userid);
|
auto u = userDao.find(userid);
|
||||||
if(u)
|
if(u)
|
||||||
{
|
{
|
||||||
|
@ -18,23 +18,43 @@ 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
|
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
SOFTWARE.
|
SOFTWARE.
|
||||||
*/
|
*/
|
||||||
|
#include <atomic>
|
||||||
#include "sqlite.h"
|
#include "sqlite.h"
|
||||||
#include "../logger.h"
|
|
||||||
#include "pagedaosqlite.h"
|
#include "pagedaosqlite.h"
|
||||||
#include "revisiondaosqlite.h"
|
#include "revisiondaosqlite.h"
|
||||||
#include "sessiondaosqlite.h"
|
#include "sessiondaosqlite.h"
|
||||||
|
#include "sqlite_modern_cpp.h"
|
||||||
#include "userdaosqlite.h"
|
#include "userdaosqlite.h"
|
||||||
#include "categorydaosqlite.h"
|
#include "categorydaosqlite.h"
|
||||||
#include "exceptions.h"
|
|
||||||
#include "permissionsdaosqlite.h"
|
#include "permissionsdaosqlite.h"
|
||||||
|
|
||||||
|
thread_local sqlite::database *Sqlite::db = nullptr;
|
||||||
|
|
||||||
|
std::atomic<int> instances = 0;
|
||||||
Sqlite::Sqlite(std::string path) : Database(path)
|
Sqlite::Sqlite(std::string path) : Database(path)
|
||||||
{
|
{
|
||||||
this->db = std::make_shared<sqlite::database>(path);
|
instances++;
|
||||||
|
if(instances.load() > 1)
|
||||||
*db << "PRAGMA journal_mode=WAL;";
|
{
|
||||||
|
std::cerr << "temporal (yeah, right) HACK... only one instance allowed" << std::endl;
|
||||||
|
abort();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
std::mutex dbmutex;
|
||||||
|
sqlite::database &Sqlite::database() const
|
||||||
|
{
|
||||||
|
if(Sqlite::db == nullptr)
|
||||||
|
{
|
||||||
|
sqlite::sqlite_config config;
|
||||||
|
config.flags = config.flags | sqlite::OpenFlags::FULLMUTEX;
|
||||||
|
std::lock_guard<std::mutex> dbguard(dbmutex);
|
||||||
|
Sqlite::db = new sqlite::database(this->connnectionstring, config);
|
||||||
|
*Sqlite::db << "PRAGMA journal_mode=WAL;";
|
||||||
|
*Sqlite::db << "PRAGMA busy_timeout=10000;";
|
||||||
|
}
|
||||||
|
return *Sqlite::db;
|
||||||
|
}
|
||||||
std::unique_ptr<RevisionDao> Sqlite::createRevisionDao() const
|
std::unique_ptr<RevisionDao> Sqlite::createRevisionDao() const
|
||||||
{
|
{
|
||||||
return create<RevisionDaoSqlite>();
|
return create<RevisionDaoSqlite>();
|
||||||
@ -67,27 +87,20 @@ std::unique_ptr<PermissionsDao> Sqlite::createPermissionsDao() const
|
|||||||
|
|
||||||
void Sqlite::beginTransaction()
|
void Sqlite::beginTransaction()
|
||||||
{
|
{
|
||||||
if(!inTransaction)
|
*db << "begin;";
|
||||||
{
|
|
||||||
*db << "begin;";
|
|
||||||
inTransaction = true;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void Sqlite::rollbackTransaction()
|
void Sqlite::rollbackTransaction()
|
||||||
{
|
{
|
||||||
if(inTransaction)
|
*db << "rollback;";
|
||||||
{
|
|
||||||
*db << "rollback;";
|
|
||||||
inTransaction = false;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void Sqlite::commitTransaction()
|
void Sqlite::commitTransaction()
|
||||||
{
|
{
|
||||||
if(inTransaction)
|
*db << "commit;";
|
||||||
{
|
}
|
||||||
*db << "commit;";
|
|
||||||
inTransaction = false;
|
Sqlite::~Sqlite()
|
||||||
}
|
{
|
||||||
|
delete this->db;
|
||||||
}
|
}
|
||||||
|
@ -8,14 +8,15 @@
|
|||||||
class Sqlite : public Database
|
class Sqlite : public Database
|
||||||
{
|
{
|
||||||
private:
|
private:
|
||||||
bool inTransaction = false;
|
static thread_local sqlite::database *db;
|
||||||
std::shared_ptr<sqlite::database> db;
|
|
||||||
|
|
||||||
template <class T> std::unique_ptr<T> create() const
|
template <class T> std::unique_ptr<T> create() const
|
||||||
{
|
{
|
||||||
return std::make_unique<T>(db);
|
return std::make_unique<T>(database());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
sqlite::database &database() const;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
Sqlite(std::string path);
|
Sqlite(std::string path);
|
||||||
std::unique_ptr<PageDao> createPageDao() const;
|
std::unique_ptr<PageDao> createPageDao() const;
|
||||||
@ -27,6 +28,7 @@ class Sqlite : public Database
|
|||||||
void beginTransaction();
|
void beginTransaction();
|
||||||
void commitTransaction();
|
void commitTransaction();
|
||||||
void rollbackTransaction();
|
void rollbackTransaction();
|
||||||
|
virtual ~Sqlite();
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // SQLITE_H
|
#endif // SQLITE_H
|
||||||
|
@ -12,20 +12,20 @@
|
|||||||
class SqliteDao
|
class SqliteDao
|
||||||
{
|
{
|
||||||
protected:
|
protected:
|
||||||
std::shared_ptr<sqlite::database> db;
|
sqlite::database *db = nullptr;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
SqliteDao()
|
SqliteDao()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
SqliteDao(std::shared_ptr<sqlite::database> db)
|
SqliteDao(sqlite::database &db)
|
||||||
{
|
{
|
||||||
this->db = db;
|
this->db = &db;
|
||||||
}
|
}
|
||||||
void setDb(std::shared_ptr<sqlite::database> db)
|
void setDb(sqlite::database &db)
|
||||||
{
|
{
|
||||||
this->db = db;
|
this->db = &db;
|
||||||
}
|
}
|
||||||
|
|
||||||
inline void throwFrom(const sqlite::sqlite_exception &e) const
|
inline void throwFrom(const sqlite::sqlite_exception &e) const
|
||||||
|
@ -1,8 +1,9 @@
|
|||||||
#include "dynamiccontent.h"
|
#include "dynamiccontent.h"
|
||||||
|
|
||||||
DynamicContent::DynamicContent(Template &templ, Database &database, UrlProvider &provider)
|
DynamicContent::DynamicContent(Template &templ, Database &database, UrlProvider &provider, Session &session)
|
||||||
{
|
{
|
||||||
this->templ = &templ;
|
this->templ = &templ;
|
||||||
this->database = &database;
|
this->database = &database;
|
||||||
this->urlProvider = &provider;
|
this->urlProvider = &provider;
|
||||||
|
this->userSession = &session;
|
||||||
}
|
}
|
||||||
|
@ -10,11 +10,12 @@ class DynamicContent
|
|||||||
Template *templ;
|
Template *templ;
|
||||||
Database *database;
|
Database *database;
|
||||||
UrlProvider *urlProvider;
|
UrlProvider *urlProvider;
|
||||||
|
Session *userSession;
|
||||||
|
|
||||||
std::string argument;
|
std::string argument;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
DynamicContent(Template &templ, Database &database, UrlProvider &urlProvider);
|
DynamicContent(Template &templ, Database &database, UrlProvider &urlProvider, Session &session);
|
||||||
virtual std::string render() = 0;
|
virtual std::string render() = 0;
|
||||||
virtual void setArgument(std::string argument)
|
virtual void setArgument(std::string argument)
|
||||||
{
|
{
|
||||||
|
@ -9,18 +9,20 @@ private:
|
|||||||
Template *templ;
|
Template *templ;
|
||||||
Database *db;
|
Database *db;
|
||||||
UrlProvider *urlProvider;
|
UrlProvider *urlProvider;
|
||||||
|
Session *session;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
DynamicContentFactory(Template &templ, Database &db, UrlProvider &urlProvider)
|
DynamicContentFactory(Template &templ, Database &db, UrlProvider &urlProvider, Session &session)
|
||||||
{
|
{
|
||||||
this->templ = &templ;
|
this->templ = &templ;
|
||||||
this->db = &db;
|
this->db = &db;
|
||||||
this->urlProvider = &urlProvider;
|
this->urlProvider = &urlProvider;
|
||||||
|
this->session = &session;
|
||||||
}
|
}
|
||||||
|
|
||||||
template <class T> inline std::shared_ptr<T> createDynamicContent()
|
template <class T> inline std::shared_ptr<T> createDynamicContent()
|
||||||
{
|
{
|
||||||
return std::make_shared<T>(*this->templ, *this->db, *this->urlProvider);
|
return std::make_shared<T>(*this->templ, *this->db, *this->urlProvider, *this->session);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -6,14 +6,21 @@ std::string DynamicContentPostList::render()
|
|||||||
auto categoryDao = this->database->createCategoryDao();
|
auto categoryDao = this->database->createCategoryDao();
|
||||||
auto pageDao = this->database->createPageDao();
|
auto pageDao = this->database->createPageDao();
|
||||||
auto revisionDao = this->database->createRevisionDao();
|
auto revisionDao = this->database->createRevisionDao();
|
||||||
|
auto permissionDao = this->database->createPermissionsDao();
|
||||||
|
|
||||||
QueryOption option;
|
QueryOption option;
|
||||||
option.includeInvisible = false;
|
option.includeInvisible = false;
|
||||||
auto members = categoryDao->fetchMembers(this->argument, option);
|
auto members = categoryDao->fetchMembers(this->argument, option);
|
||||||
std::vector<std::pair<std::string, time_t>> pageList;
|
std::vector<std::pair<std::string, time_t>> pageList;
|
||||||
for(const Page &member : members)
|
for(const Page &member : members)
|
||||||
{
|
{
|
||||||
auto revision = revisionDao->getRevisionForPage(member.name, 1);
|
Permissions perms = permissionDao->find(member.name, this->userSession->user.login)
|
||||||
pageList.push_back({member.name, revision->timestamp});
|
.value_or(this->userSession->user.permissions);
|
||||||
|
if(perms.canRead()) /* TODO: Maybe add canList() */
|
||||||
|
{
|
||||||
|
auto revision = revisionDao->getRevisionForPage(member.name, 1);
|
||||||
|
pageList.push_back({member.name, revision->timestamp});
|
||||||
|
}
|
||||||
}
|
}
|
||||||
std::sort(pageList.begin(), pageList.end(),
|
std::sort(pageList.begin(), pageList.end(),
|
||||||
[](std::pair<std::string, time_t> &a, std::pair<std::string, time_t> &b) { return a.second > b.second; });
|
[](std::pair<std::string, time_t> &a, std::pair<std::string, time_t> &b) { return a.second > b.second; });
|
||||||
|
@ -98,7 +98,10 @@ Response Handler::handle(const Request &r)
|
|||||||
|
|
||||||
Permissions Handler::effectivePermissions(std::string page)
|
Permissions Handler::effectivePermissions(std::string page)
|
||||||
{
|
{
|
||||||
return this->database->createPermissionsDao()
|
Permissions &userPerms = this->userSession->user.permissions;
|
||||||
->find(page, this->userSession->user.login)
|
if(userPerms.isAdmin())
|
||||||
.value_or(this->userSession->user.permissions);
|
{
|
||||||
|
return userPerms;
|
||||||
|
}
|
||||||
|
return this->database->createPermissionsDao()->find(page, this->userSession->user.login).value_or(userPerms);
|
||||||
}
|
}
|
||||||
|
@ -1,11 +1,11 @@
|
|||||||
#include "handlerfeedgenerator.h"
|
#include "handlerfeedgenerator.h"
|
||||||
#include "../parser.h"
|
|
||||||
#include "../revisionrenderer.h"
|
#include "../revisionrenderer.h"
|
||||||
std::vector<HandlerFeedGenerator::EntryRevisionPair> HandlerFeedGenerator::fetchEntries(
|
std::vector<HandlerFeedGenerator::EntryRevisionPair> HandlerFeedGenerator::fetchEntries(
|
||||||
std::vector<std::string> categories)
|
std::vector<std::string> categories)
|
||||||
{
|
{
|
||||||
auto revisionDao = this->database->createRevisionDao();
|
auto revisionDao = this->database->createRevisionDao();
|
||||||
auto pageDao = this->database->createPageDao();
|
auto pageDao = this->database->createPageDao();
|
||||||
|
auto permissionDao = this->database->createPermissionsDao();
|
||||||
|
|
||||||
std::vector<EntryRevisionPair> result;
|
std::vector<EntryRevisionPair> result;
|
||||||
QueryOption option;
|
QueryOption option;
|
||||||
@ -13,7 +13,7 @@ std::vector<HandlerFeedGenerator::EntryRevisionPair> HandlerFeedGenerator::fetch
|
|||||||
// option.limit = 20;
|
// option.limit = 20;
|
||||||
|
|
||||||
auto comppage = [](const Page &a, const Page &b) { return a.name < b.name; };
|
auto comppage = [](const Page &a, const Page &b) { return a.name < b.name; };
|
||||||
std::set<Page, decltype(comppage)> members (comppage);
|
std::set<Page, decltype(comppage)> members(comppage);
|
||||||
if(categories.empty())
|
if(categories.empty())
|
||||||
{
|
{
|
||||||
auto pages = pageDao->getPageList(option);
|
auto pages = pageDao->getPageList(option);
|
||||||
@ -34,8 +34,13 @@ std::vector<HandlerFeedGenerator::EntryRevisionPair> HandlerFeedGenerator::fetch
|
|||||||
}
|
}
|
||||||
for(const Page &member : members)
|
for(const Page &member : members)
|
||||||
{
|
{
|
||||||
auto revision = revisionDao->getRevisionForPage(member.name, 1).value();
|
Permissions perms = permissionDao->find(member.name, this->userSession->user.login)
|
||||||
result.push_back({member, revision});
|
.value_or(this->userSession->user.permissions);
|
||||||
|
if(perms.canRead())
|
||||||
|
{
|
||||||
|
auto revision = revisionDao->getRevisionForPage(member.name, 1).value();
|
||||||
|
result.push_back({member, revision});
|
||||||
|
}
|
||||||
}
|
}
|
||||||
std::sort(result.begin(), result.end(),
|
std::sort(result.begin(), result.end(),
|
||||||
[](EntryRevisionPair &a, EntryRevisionPair &b) { return a.second.timestamp > b.second.timestamp; });
|
[](EntryRevisionPair &a, EntryRevisionPair &b) { return a.second.timestamp > b.second.timestamp; });
|
||||||
@ -68,7 +73,7 @@ std::string HandlerFeedGenerator::generateAtom(const std::vector<HandlerFeedGene
|
|||||||
subtitle = "All pages";
|
subtitle = "All pages";
|
||||||
}
|
}
|
||||||
|
|
||||||
RevisionRenderer revisionRenderer { *this->templ, *this->database, *this->urlProvider };
|
RevisionRenderer revisionRenderer{*this->templ, *this->database, *this->urlProvider, *this->userSession};
|
||||||
|
|
||||||
for(const EntryRevisionPair &entry : entries)
|
for(const EntryRevisionPair &entry : entries)
|
||||||
{
|
{
|
||||||
|
@ -24,6 +24,7 @@ SOFTWARE.
|
|||||||
|
|
||||||
#include "../parser.h"
|
#include "../parser.h"
|
||||||
#include "../revisionrenderer.h"
|
#include "../revisionrenderer.h"
|
||||||
|
|
||||||
bool HandlerPageEdit::canAccess([[maybe_unused]] std::string page)
|
bool HandlerPageEdit::canAccess([[maybe_unused]] std::string page)
|
||||||
{
|
{
|
||||||
return effectivePermissions(page).canEdit();
|
return effectivePermissions(page).canEdit();
|
||||||
@ -56,7 +57,8 @@ Response HandlerPageEdit::handleRequest(PageDao &pageDao, std::string pagename,
|
|||||||
{
|
{
|
||||||
if(!effectivePermissions(from).canRead())
|
if(!effectivePermissions(from).canRead())
|
||||||
{
|
{
|
||||||
return this->errorResponse("Permission denied", "No access permissions, so you can't use this page as a template");
|
return this->errorResponse("Permission denied",
|
||||||
|
"No access permissions, so you can't use this page as a template");
|
||||||
}
|
}
|
||||||
body = revisiondao->getCurrentForPage(from)->content;
|
body = revisiondao->getCurrentForPage(from)->content;
|
||||||
}
|
}
|
||||||
@ -77,6 +79,7 @@ Response HandlerPageEdit::handleRequest(PageDao &pageDao, std::string pagename,
|
|||||||
std::string visiblecmd = parser.extractCommand("visible", newContent);
|
std::string visiblecmd = parser.extractCommand("visible", newContent);
|
||||||
std::string rename = parser.extractCommand("rename", newContent);
|
std::string rename = parser.extractCommand("rename", newContent);
|
||||||
std::string customtitle = parser.extractCommand("pagetitle", newContent);
|
std::string customtitle = parser.extractCommand("pagetitle", newContent);
|
||||||
|
std::vector<std::string> perms = parser.extractCommands("permissions", newContent);
|
||||||
Page page;
|
Page page;
|
||||||
std::optional<Page> currentPage = pageDao.find(pagename);
|
std::optional<Page> currentPage = pageDao.find(pagename);
|
||||||
if(currentPage)
|
if(currentPage)
|
||||||
@ -91,6 +94,33 @@ Response HandlerPageEdit::handleRequest(PageDao &pageDao, std::string pagename,
|
|||||||
}
|
}
|
||||||
pagename = rename;
|
pagename = rename;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for(const std::string &perm : perms)
|
||||||
|
{
|
||||||
|
auto splitted = utils::split(perm, '|');
|
||||||
|
if(splitted.size() != 2)
|
||||||
|
{
|
||||||
|
return this->errorResponse("Invalid command", "permissions command is misformated");
|
||||||
|
}
|
||||||
|
auto permissionDao = this->database->createPermissionsDao();
|
||||||
|
auto currentPermission = permissionDao->find(pagename, splitted[0]);
|
||||||
|
|
||||||
|
Permissions newPermissions = Permissions{splitted[1]};
|
||||||
|
if(!currentPermission || newPermissions != currentPermission.value())
|
||||||
|
{
|
||||||
|
if(this->userSession->user.permissions.canSetPagePerms())
|
||||||
|
{
|
||||||
|
permissionDao->save(pagename, splitted[0], newPermissions);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
this->database->rollbackTransaction();
|
||||||
|
return errorResponse("Invalid permissions",
|
||||||
|
"You don't have permission to change page permissions");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
page.current_revision = current_revision;
|
page.current_revision = current_revision;
|
||||||
page.listed = !(visiblecmd == "0");
|
page.listed = !(visiblecmd == "0");
|
||||||
page.name = pagename;
|
page.name = pagename;
|
||||||
@ -115,6 +145,7 @@ Response HandlerPageEdit::handleRequest(PageDao &pageDao, std::string pagename,
|
|||||||
}
|
}
|
||||||
catch(const DatabaseException &e)
|
catch(const DatabaseException &e)
|
||||||
{
|
{
|
||||||
|
this->database->rollbackTransaction();
|
||||||
Logger::debug() << "Error saving revision: " << e.what();
|
Logger::debug() << "Error saving revision: " << e.what();
|
||||||
return errorResponse("Database error", "A database error occured while trying to save this revision");
|
return errorResponse("Database error", "A database error occured while trying to save this revision");
|
||||||
}
|
}
|
||||||
@ -129,7 +160,7 @@ Response HandlerPageEdit::handleRequest(PageDao &pageDao, std::string pagename,
|
|||||||
TemplatePage templatePage = this->templ->getPage("page_creation_preview");
|
TemplatePage templatePage = this->templ->getPage("page_creation_preview");
|
||||||
templatePage.setVar("actionurl", urlProvider->editPage(pagename));
|
templatePage.setVar("actionurl", urlProvider->editPage(pagename));
|
||||||
|
|
||||||
RevisionRenderer revisionRenderer { *this->templ, *this->database, *this->urlProvider };
|
RevisionRenderer revisionRenderer{*this->templ, *this->database, *this->urlProvider, *this->userSession};
|
||||||
|
|
||||||
templatePage.setVar("preview_content", revisionRenderer.renderContent(newContent));
|
templatePage.setVar("preview_content", revisionRenderer.renderContent(newContent));
|
||||||
templatePage.setVar("content", newContent);
|
templatePage.setVar("content", newContent);
|
||||||
|
@ -138,8 +138,7 @@ Response HandlerPageView::handleRequest(PageDao &pageDao, std::string pagename,
|
|||||||
Response result;
|
Response result;
|
||||||
result.setStatus(200);
|
result.setStatus(200);
|
||||||
|
|
||||||
RevisionRenderer revisionRenderer { *this->templ, *this->database, *this->urlProvider };
|
RevisionRenderer revisionRenderer{*this->templ, *this->database, *this->urlProvider, *this->userSession};
|
||||||
|
|
||||||
|
|
||||||
std::string customtitle = parser.extractCommand("pagetitle", revision->content);
|
std::string customtitle = parser.extractCommand("pagetitle", revision->content);
|
||||||
std::string parsedcontent = revisionRenderer.renderContent(revision.value(), customtitle);
|
std::string parsedcontent = revisionRenderer.renderContent(revision.value(), customtitle);
|
||||||
|
@ -16,6 +16,8 @@ class IParser
|
|||||||
|
|
||||||
public:
|
public:
|
||||||
virtual std::string extractCommand(std::string cmdname, const std::string &content) const = 0;
|
virtual std::string extractCommand(std::string cmdname, const std::string &content) const = 0;
|
||||||
|
virtual std::vector<std::string> extractCommands(std::string cmdname, const std::string &content) const = 0;
|
||||||
|
|
||||||
virtual std::vector<Headline> extractHeadlines(const std::string &content) const = 0;
|
virtual std::vector<Headline> extractHeadlines(const std::string &content) const = 0;
|
||||||
virtual inline std::string parse(const PageDao &pagedao, UrlProvider &provider, const std::string &content) const
|
virtual inline std::string parse(const PageDao &pagedao, UrlProvider &provider, const std::string &content) const
|
||||||
{
|
{
|
||||||
|
26
parser.cpp
26
parser.cpp
@ -82,6 +82,28 @@ std::string Parser::extractCommand(std::string cmdname, const std::string &conte
|
|||||||
}
|
}
|
||||||
return "";
|
return "";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
std::vector<std::string> Parser::extractCommands(std::string cmdname, const std::string &content) const
|
||||||
|
{
|
||||||
|
std::vector<std::string> result;
|
||||||
|
|
||||||
|
std::string cmd = "[cmd:" + cmdname + "]";
|
||||||
|
std::string cmdend = "[/cmd:" + cmdname + "]";
|
||||||
|
|
||||||
|
std::string_view view = content;
|
||||||
|
size_t pos = 0;
|
||||||
|
while((pos = view.find(cmd)) != std::string::npos)
|
||||||
|
{
|
||||||
|
view.remove_prefix(pos);
|
||||||
|
view.remove_prefix(cmd.size());
|
||||||
|
if((pos = view.find(cmdend)) != std::string::npos)
|
||||||
|
{
|
||||||
|
result.emplace_back(view.substr(0, pos));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
std::string Parser::processLink(const PageDao &pageDao, UrlProvider &urlProvider, std::smatch &match) const
|
std::string Parser::processLink(const PageDao &pageDao, UrlProvider &urlProvider, std::smatch &match) const
|
||||||
{
|
{
|
||||||
std::string linktag = match.str(1);
|
std::string linktag = match.str(1);
|
||||||
@ -148,7 +170,7 @@ std::string Parser::parse(const PageDao &pagedao, UrlProvider &provider, const s
|
|||||||
std::string result;
|
std::string result;
|
||||||
// we don't care about commands, but we nevertheless replace them with empty strings
|
// we don't care about commands, but we nevertheless replace them with empty strings
|
||||||
std::regex tagfinder(
|
std::regex tagfinder(
|
||||||
R"(\[(b|i|u|s|li||ul|ol|code|blockquote|img|link|wikilink|h\d|cmd:visible|cmd:rename|cmd:redirect|cmd:pagetitle|cmd:allowinclude|category|dynamic:postlist|dynamic:includepage|dynamic:getvar|dynamic:setvar)*?\]((\s|\S)*?)\[/\1])");
|
R"(\[(b|i|u|s|li||ul|ol|code|blockquote|img|link|wikilink|h\d|cmd:visible|cmd:rename|cmd:redirect|cmd:pagetitle|cmd:allowinclude|cmd:permissions|category|dynamic:postlist|dynamic:includepage|dynamic:getvar|dynamic:setvar)*?\]((\s|\S)*?)\[/\1])");
|
||||||
result = utils::regex_callback_replacer(
|
result = utils::regex_callback_replacer(
|
||||||
tagfinder, content,
|
tagfinder, content,
|
||||||
[&](std::smatch &match)
|
[&](std::smatch &match)
|
||||||
@ -180,7 +202,7 @@ std::string Parser::parse(const PageDao &pagedao, UrlProvider &provider, const s
|
|||||||
}
|
}
|
||||||
if(tag == "code" || tag == "blockquote")
|
if(tag == "code" || tag == "blockquote")
|
||||||
{
|
{
|
||||||
return "<pre><" + tag + ">"+ utils::strreplace(content, "\r\n", "\n") + "</"+tag+"></pre>";
|
return "<pre><" + tag + ">" + utils::strreplace(content, "\r\n", "\n") + "</" + tag + "></pre>";
|
||||||
}
|
}
|
||||||
return callback(tag, content);
|
return callback(tag, content);
|
||||||
});
|
});
|
||||||
|
3
parser.h
3
parser.h
@ -9,7 +9,8 @@ class Parser : public IParser
|
|||||||
std::string processImage(std::smatch &match) const;
|
std::string processImage(std::smatch &match) const;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
std::string extractCommand(std::string cmdname, const std::string &content) const;
|
std::string extractCommand(std::string cmdname, const std::string &content) const override;
|
||||||
|
std::vector<std::string> extractCommands(std::string cmdname, const std::string &content) const override;
|
||||||
std::vector<Headline> extractHeadlines(const std::string &content) const override;
|
std::vector<Headline> extractHeadlines(const std::string &content) const override;
|
||||||
std::vector<std::string> extractCategories(const std::string &content) const override;
|
std::vector<std::string> extractCategories(const std::string &content) const override;
|
||||||
using IParser::parse;
|
using IParser::parse;
|
||||||
|
@ -20,7 +20,8 @@ SOFTWARE.
|
|||||||
*/
|
*/
|
||||||
#include "permissions.h"
|
#include "permissions.h"
|
||||||
|
|
||||||
static const std::map<std::string, int> permmap = {{"can_read", PERM_CAN_READ},
|
static const std::map<std::string, int> permmap = {{"can_nothing", PERM_CAN_NOTHING},
|
||||||
|
{"can_read", PERM_CAN_READ},
|
||||||
{"can_edit", PERM_CAN_EDIT},
|
{"can_edit", PERM_CAN_EDIT},
|
||||||
{"can_page_history", PERM_CAN_PAGE_HISTORY},
|
{"can_page_history", PERM_CAN_PAGE_HISTORY},
|
||||||
{"can_global_history", PERM_CAN_GLOBAL_HISTORY},
|
{"can_global_history", PERM_CAN_GLOBAL_HISTORY},
|
||||||
@ -29,7 +30,8 @@ static const std::map<std::string, int> permmap = {{"can_read", PERM_CAN_READ},
|
|||||||
{"can_create", PERM_CAN_CREATE},
|
{"can_create", PERM_CAN_CREATE},
|
||||||
{"can_see_category_list", PERM_CAN_SEE_CATEGORY_LIST},
|
{"can_see_category_list", PERM_CAN_SEE_CATEGORY_LIST},
|
||||||
{"can_see_links_here", PERM_CAN_SEE_LINKS_HERE},
|
{"can_see_links_here", PERM_CAN_SEE_LINKS_HERE},
|
||||||
{"can_search", PERM_CAN_SEARCH}};
|
{"can_search", PERM_CAN_SEARCH},
|
||||||
|
{"can_set_page_perms", PERM_CAN_SET_PAGE_PERMS}};
|
||||||
|
|
||||||
Permissions::Permissions(int permissions)
|
Permissions::Permissions(int permissions)
|
||||||
{
|
{
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
#ifndef PERMISSIONS_H
|
#ifndef PERMISSIONS_H
|
||||||
#define PERMISSIONS_H
|
#define PERMISSIONS_H
|
||||||
|
|
||||||
|
#define PERM_CAN_NOTHING 0
|
||||||
#define PERM_CAN_READ 1 << 0
|
#define PERM_CAN_READ 1 << 0
|
||||||
#define PERM_CAN_EDIT 1 << 1
|
#define PERM_CAN_EDIT 1 << 1
|
||||||
#define PERM_CAN_PAGE_HISTORY 1 << 2
|
#define PERM_CAN_PAGE_HISTORY 1 << 2
|
||||||
@ -11,6 +12,8 @@
|
|||||||
#define PERM_CAN_SEE_CATEGORY_LIST 1 << 7
|
#define PERM_CAN_SEE_CATEGORY_LIST 1 << 7
|
||||||
#define PERM_CAN_SEE_LINKS_HERE 1 << 8
|
#define PERM_CAN_SEE_LINKS_HERE 1 << 8
|
||||||
#define PERM_CAN_SEARCH 1 << 9
|
#define PERM_CAN_SEARCH 1 << 9
|
||||||
|
#define PERM_CAN_SET_PAGE_PERMS 1 << 10
|
||||||
|
#define PERM_IS_ADMIN (1L<<31)-1
|
||||||
|
|
||||||
#include <string>
|
#include <string>
|
||||||
#include <map>
|
#include <map>
|
||||||
@ -54,10 +57,16 @@ class Permissions
|
|||||||
return this->permissions;
|
return this->permissions;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool canNothing() const
|
||||||
|
{
|
||||||
|
return this->permissions == PERM_CAN_NOTHING;
|
||||||
|
}
|
||||||
|
|
||||||
bool canRead() const
|
bool canRead() const
|
||||||
{
|
{
|
||||||
return this->permissions & PERM_CAN_READ;
|
return this->permissions & PERM_CAN_READ;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool canEdit() const
|
bool canEdit() const
|
||||||
{
|
{
|
||||||
return this->permissions & PERM_CAN_EDIT;
|
return this->permissions & PERM_CAN_EDIT;
|
||||||
@ -95,12 +104,27 @@ class Permissions
|
|||||||
return this->permissions & PERM_CAN_SEE_PAGE_LIST;
|
return this->permissions & PERM_CAN_SEE_PAGE_LIST;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool canSetPagePerms() const
|
||||||
|
{
|
||||||
|
return this->permissions & PERM_CAN_SET_PAGE_PERMS;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool isAdmin() const
|
||||||
|
{
|
||||||
|
return this->permissions == PERM_IS_ADMIN;
|
||||||
|
}
|
||||||
|
|
||||||
std::string toString() const
|
std::string toString() const
|
||||||
{
|
{
|
||||||
return Permissions::toString(this->permissions);
|
return Permissions::toString(this->permissions);
|
||||||
}
|
}
|
||||||
|
|
||||||
static std::string toString(int perms);
|
static std::string toString(int perms);
|
||||||
|
|
||||||
|
bool operator==(const Permissions &o) const
|
||||||
|
{
|
||||||
|
return this->permissions == o.permissions;
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // PERMISSIONS_H
|
#endif // PERMISSIONS_H
|
||||||
|
@ -37,6 +37,7 @@ SOFTWARE.
|
|||||||
#include "urlprovider.h"
|
#include "urlprovider.h"
|
||||||
#include "requestworker.h"
|
#include "requestworker.h"
|
||||||
#include "cache/fscache.h"
|
#include "cache/fscache.h"
|
||||||
|
#include "cache/nocache.h"
|
||||||
#include "sandbox/sandboxfactory.h"
|
#include "sandbox/sandboxfactory.h"
|
||||||
#include "cli.h"
|
#include "cli.h"
|
||||||
#include "cliconsole.h"
|
#include "cliconsole.h"
|
||||||
@ -68,9 +69,11 @@ static struct option long_options[] = {{"cli", no_argument, 0, 'c'}, {"version",
|
|||||||
|
|
||||||
std::unique_ptr<ICache> createCache(const ConfigVariableResolver &resolver)
|
std::unique_ptr<ICache> createCache(const ConfigVariableResolver &resolver)
|
||||||
{
|
{
|
||||||
|
|
||||||
std::string path = resolver.getConfig("cache_fs_dir");
|
std::string path = resolver.getConfig("cache_fs_dir");
|
||||||
|
if(path == "")
|
||||||
|
{
|
||||||
|
return std::make_unique<NoCache>(path);
|
||||||
|
}
|
||||||
return std::make_unique<FsCache>(path);
|
return std::make_unique<FsCache>(path);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -17,7 +17,7 @@ private:
|
|||||||
Parser parser;
|
Parser parser;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
RevisionRenderer(Template &templ, Database &db, UrlProvider &urlProvider) :dynamicContentFactory(templ, db, urlProvider)
|
RevisionRenderer(Template &templ, Database &db, UrlProvider &urlProvider, Session &session) :dynamicContentFactory(templ, db, urlProvider, session)
|
||||||
{
|
{
|
||||||
this->db = &db;
|
this->db = &db;
|
||||||
this->urlProvider = &urlProvider;
|
this->urlProvider = &urlProvider;
|
||||||
|
Loading…
Reference in New Issue
Block a user