описал интерфейсную часть аутентификации, пока оставил без реализации
This commit is contained in:
parent
d9967b69e8
commit
82b433c447
@ -38,6 +38,8 @@ add_executable(terminal-web-server
|
|||||||
src/terminal_api_driver.cpp
|
src/terminal_api_driver.cpp
|
||||||
src/auth/resources.cpp
|
src/auth/resources.cpp
|
||||||
src/auth/resources.h
|
src/auth/resources.h
|
||||||
|
src/auth/jwt.cpp
|
||||||
|
src/auth/jwt.h
|
||||||
)
|
)
|
||||||
|
|
||||||
find_package(Boost 1.53.0 COMPONENTS system thread filesystem log log_setup REQUIRED)
|
find_package(Boost 1.53.0 COMPONENTS system thread filesystem log log_setup REQUIRED)
|
||||||
|
5
src/auth/jwt.cpp
Normal file
5
src/auth/jwt.cpp
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
//
|
||||||
|
// Created by vlad on 04.11.2024.
|
||||||
|
//
|
||||||
|
|
||||||
|
#include "jwt.h"
|
23
src/auth/jwt.h
Normal file
23
src/auth/jwt.h
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
#ifndef JWT_H
|
||||||
|
#define JWT_H
|
||||||
|
#include <string>
|
||||||
|
#include "resources.h"
|
||||||
|
|
||||||
|
namespace http::auth::jwt {
|
||||||
|
class Jwt {
|
||||||
|
public:
|
||||||
|
static Jwt fromCookies(const std::string& cookie);
|
||||||
|
static Jwt fromString(const std::string& cookie);
|
||||||
|
static Jwt fromUser(const std::string& User);
|
||||||
|
|
||||||
|
bool isValid();
|
||||||
|
|
||||||
|
std::string getUsername();
|
||||||
|
|
||||||
|
std::string asCookie();
|
||||||
|
|
||||||
|
~Jwt();
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif //JWT_H
|
@ -4,25 +4,74 @@
|
|||||||
|
|
||||||
namespace http::auth {
|
namespace http::auth {
|
||||||
/**
|
/**
|
||||||
* Класс пользовательских разрешений,
|
* Класс пользователя, содержит логин/хеш_пароля/настройки пользователя/права.
|
||||||
*/
|
* Хеш пароля представляется в виде строки
|
||||||
class UserPremision{};
|
*/
|
||||||
|
class User {
|
||||||
|
private:
|
||||||
|
uint32_t perms;
|
||||||
|
|
||||||
/**
|
public:
|
||||||
* Класс пользователя, содержит логин/хеш_пароля/настройки пользователя/права
|
const std::string username;
|
||||||
*/
|
std::string passwordHash;
|
||||||
class User{};
|
|
||||||
|
|
||||||
/**
|
User(const std::string& username, const std::string& passwordHash);
|
||||||
* Класс аутентификации. Управляет всеми сессиями, создает новые при логине, удаляет при логауте.
|
|
||||||
* @note Класс устанавливает заголовок 'Set-Cookie' в ответе, и этот заголовок должен дойти до пользователя!
|
|
||||||
*/
|
|
||||||
class AuthProvider {
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Проверить пароль на соответствие хешу
|
||||||
|
* @param pass
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
bool checkPassword(const std::string& pass);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Установка пароля
|
||||||
|
* @param pass строка с исходным паролем
|
||||||
|
*/
|
||||||
|
void setPassword(const std::string& pass);
|
||||||
|
|
||||||
|
|
||||||
|
static constexpr uint32_t SUPERUSER = 0x0001;
|
||||||
|
static constexpr uint32_t WATCH_STATISTICS = 0x0002; // мониторинг модема
|
||||||
|
static constexpr uint32_t RESET_PACKET_STATISTICS = 0x0004; // сброс статистики пакетов
|
||||||
|
static constexpr uint32_t WATCH_SETTINGS = 0x0008; // просмотр настроек , если недоступно, то вкладки с настройками не будет
|
||||||
|
static constexpr uint32_t EDIT_SETTINGS = 0x0010; // редактирование настроек, установка параметров модулятора/демодулятора/dma/cinc
|
||||||
|
static constexpr uint32_t UPDATE_FIRMWARE = 0x0020; // обновление прошивки
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Проверить, что у пользователя есть нужное право. Если это суперпользователь, то у него по умолчанию все права есть.
|
||||||
|
* @param p набор прав, из констант данного класса.
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
bool checkPremisions(uint32_t p);
|
||||||
|
|
||||||
|
void setPremisions(uint32_t p);
|
||||||
|
void resetPremisions(uint32_t p);
|
||||||
|
|
||||||
|
~User();
|
||||||
};
|
};
|
||||||
|
|
||||||
class NeedAuentificationResource: public resource::BasicResource {};
|
/**
|
||||||
|
* Класс аутентификации. Управляет всеми сессиями, создает новые при логине, удаляет при логауте.
|
||||||
|
* @note Класс устанавливает заголовок 'Set-Cookie' в ответе, и этот заголовок должен дойти до пользователя!
|
||||||
|
*/
|
||||||
|
class AuthProvider {
|
||||||
|
public:
|
||||||
|
AuthProvider();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Авторизовать пользователя.
|
||||||
|
*
|
||||||
|
* @param rep
|
||||||
|
* @return true, в случае успешной авторизации
|
||||||
|
*/
|
||||||
|
bool doAuth(const std::string& username, const std::string& password, server::Reply& rep);
|
||||||
|
|
||||||
|
~AuthProvider();
|
||||||
|
};
|
||||||
|
|
||||||
|
class NeedAuentificationResource : public resource::BasicResource {
|
||||||
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif //RESOURCES_H
|
#endif //RESOURCES_H
|
||||||
|
@ -13,7 +13,7 @@
|
|||||||
|
|
||||||
|
|
||||||
namespace http::server {
|
namespace http::server {
|
||||||
using request_handler = std::function<void(const Request &req, reply &rep)>;
|
using request_handler = std::function<void(const Request &req, Reply &rep)>;
|
||||||
|
|
||||||
class ConnectionManager;
|
class ConnectionManager;
|
||||||
/// Represents a single Connection from a client. Base class
|
/// Represents a single Connection from a client. Base class
|
||||||
@ -71,7 +71,7 @@ namespace http::server {
|
|||||||
RequestParser request_parser_;
|
RequestParser request_parser_;
|
||||||
|
|
||||||
/// The reply to be sent back to the client.
|
/// The reply to be sent back to the client.
|
||||||
reply reply_;
|
Reply reply_;
|
||||||
};
|
};
|
||||||
|
|
||||||
class SslConnection final : public ConnectionBase, public std::enable_shared_from_this<SslConnection> {
|
class SslConnection final : public ConnectionBase, public std::enable_shared_from_this<SslConnection> {
|
||||||
@ -113,7 +113,7 @@ namespace http::server {
|
|||||||
RequestParser request_parser_;
|
RequestParser request_parser_;
|
||||||
|
|
||||||
/// The reply to be sent back to the client.
|
/// The reply to be sent back to the client.
|
||||||
reply reply_;
|
Reply reply_;
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef std::shared_ptr<ConnectionBase> connection_ptr;
|
typedef std::shared_ptr<ConnectionBase> connection_ptr;
|
||||||
|
@ -68,7 +68,7 @@ namespace http::server {
|
|||||||
const char crlf[] = {'\r', '\n'};
|
const char crlf[] = {'\r', '\n'};
|
||||||
} // namespace misc_strings
|
} // namespace misc_strings
|
||||||
|
|
||||||
std::vector<boost::asio::const_buffer> reply::to_buffers() const {
|
std::vector<boost::asio::const_buffer> Reply::to_buffers() const {
|
||||||
std::vector<boost::asio::const_buffer> buffers;
|
std::vector<boost::asio::const_buffer> buffers;
|
||||||
buffers.push_back(status_strings::to_buffer(status));
|
buffers.push_back(status_strings::to_buffer(status));
|
||||||
for (const auto & h : headers) {
|
for (const auto & h : headers) {
|
||||||
@ -206,7 +206,7 @@ namespace http::server {
|
|||||||
}
|
}
|
||||||
} // namespace stock_replies
|
} // namespace stock_replies
|
||||||
|
|
||||||
void stockReply(status_type status, reply& rep) {
|
void stockReply(status_type status, Reply& rep) {
|
||||||
rep.status = status;
|
rep.status = status;
|
||||||
rep.headers.clear();
|
rep.headers.clear();
|
||||||
rep.headers.push_back({.name = "Content-Type", .value = toString(mime_types::text_html)});
|
rep.headers.push_back({.name = "Content-Type", .value = toString(mime_types::text_html)});
|
||||||
|
@ -28,7 +28,7 @@ namespace http::server {
|
|||||||
};
|
};
|
||||||
|
|
||||||
/// A reply to be sent to a client.
|
/// A reply to be sent to a client.
|
||||||
struct reply {
|
struct Reply {
|
||||||
status_type status;
|
status_type status;
|
||||||
|
|
||||||
/// The headers to be included in the reply.
|
/// The headers to be included in the reply.
|
||||||
@ -44,7 +44,7 @@ namespace http::server {
|
|||||||
};
|
};
|
||||||
|
|
||||||
/// Get a stock reply.
|
/// Get a stock reply.
|
||||||
void stockReply(status_type status, reply& rep);
|
void stockReply(status_type status, Reply& rep);
|
||||||
|
|
||||||
} // namespace http::Server
|
} // namespace http::Server
|
||||||
|
|
||||||
|
@ -30,7 +30,7 @@ http::resource::StaticFileResource::StaticFileResource(const std::string &path,
|
|||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
void http::resource::StaticFileResource::handle(const server::Request &req, server::reply &rep) {
|
void http::resource::StaticFileResource::handle(const server::Request &req, server::Reply &rep) {
|
||||||
if (req.method != "GET") {
|
if (req.method != "GET") {
|
||||||
stockReply(server::bad_request, rep);
|
stockReply(server::bad_request, rep);
|
||||||
return;
|
return;
|
||||||
@ -56,7 +56,7 @@ http::resource::GenericResource::GenericResource(const std::string &path, const
|
|||||||
this->path = path;
|
this->path = path;
|
||||||
}
|
}
|
||||||
|
|
||||||
void http::resource::GenericResource::handle(const server::Request &req, server::reply &rep) {
|
void http::resource::GenericResource::handle(const server::Request &req, server::Reply &rep) {
|
||||||
this->generator_(req, rep);
|
this->generator_(req, rep);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -14,7 +14,7 @@ namespace http::resource {
|
|||||||
public:
|
public:
|
||||||
std::string path;
|
std::string path;
|
||||||
|
|
||||||
virtual void handle(const server::Request &req, server::reply &rep) = 0;
|
virtual void handle(const server::Request &req, server::Reply &rep) = 0;
|
||||||
|
|
||||||
virtual ~BasicResource() = default;
|
virtual ~BasicResource() = default;
|
||||||
};
|
};
|
||||||
@ -34,12 +34,12 @@ namespace http::resource {
|
|||||||
public:
|
public:
|
||||||
StaticFileResource(const std::string& path, const std::string& filePath, server::mime_types::Mime type);
|
StaticFileResource(const std::string& path, const std::string& filePath, server::mime_types::Mime type);
|
||||||
|
|
||||||
void handle(const server::Request &req, server::reply &rep) override;
|
void handle(const server::Request &req, server::Reply &rep) override;
|
||||||
|
|
||||||
~StaticFileResource() override;
|
~StaticFileResource() override;
|
||||||
};
|
};
|
||||||
|
|
||||||
using respGenerator = std::function<void(const server::Request &req, server::reply &rep)>;
|
using respGenerator = std::function<void(const server::Request &req, server::Reply &rep)>;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Класс ресурса для POST-запросов
|
* Класс ресурса для POST-запросов
|
||||||
@ -51,7 +51,7 @@ namespace http::resource {
|
|||||||
public:
|
public:
|
||||||
GenericResource(const std::string& path, const respGenerator& generator);
|
GenericResource(const std::string& path, const respGenerator& generator);
|
||||||
|
|
||||||
void handle(const server::Request &req, server::reply &rep) override;
|
void handle(const server::Request &req, server::Reply &rep) override;
|
||||||
|
|
||||||
~GenericResource() override;
|
~GenericResource() override;
|
||||||
};
|
};
|
||||||
|
@ -111,7 +111,7 @@ namespace http::server {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
void Server::requestHandler(const Request &req, reply &rep) {
|
void Server::requestHandler(const Request &req, Reply &rep) {
|
||||||
// Request path must be absolute and not contain "..".
|
// Request path must be absolute and not contain "..".
|
||||||
if (req.url->path.empty() || req.url->path[0] != '/' || req.url->path.find("..") != std::string::npos) {
|
if (req.url->path.empty() || req.url->path[0] != '/' || req.url->path.find("..") != std::string::npos) {
|
||||||
stockReply(bad_request, rep);
|
stockReply(bad_request, rep);
|
||||||
|
@ -74,7 +74,7 @@ namespace http::server {
|
|||||||
ConnectionManager connection_manager_;
|
ConnectionManager connection_manager_;
|
||||||
|
|
||||||
/// Handle a request and produce a reply.
|
/// Handle a request and produce a reply.
|
||||||
void requestHandler(const Request &req, reply &rep);
|
void requestHandler(const Request &req, Reply &rep);
|
||||||
};
|
};
|
||||||
} // namespace http::Server
|
} // namespace http::Server
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user