From 1696e6a88dfad9b1236b9b7c870940ca9d0b82a8 Mon Sep 17 00:00:00 2001 From: Gulliver Date: Thu, 10 Nov 2022 01:31:47 +0100 Subject: [PATCH] initial checkin --- .gitignore | 191 ++++++++++++++++++++++++++++++++++++------------- CMakeLists.txt | 51 +++++++++++++ README.md | 8 ++- src/main.cpp | 72 +++++++++++++++++++ src/model.cpp | 130 +++++++++++++++++++++++++++++++++ src/model.hpp | 111 ++++++++++++++++++++++++++++ 6 files changed, 511 insertions(+), 52 deletions(-) create mode 100644 CMakeLists.txt create mode 100644 src/main.cpp create mode 100644 src/model.cpp create mode 100644 src/model.hpp diff --git a/.gitignore b/.gitignore index 2bb29bc..c7f3b7d 100644 --- a/.gitignore +++ b/.gitignore @@ -1,54 +1,3 @@ -# ---> Emacs -# -*- mode: gitignore; -*- -*~ -\#*\# -/.emacs.desktop -/.emacs.desktop.lock -*.elc -auto-save-list -tramp -.\#* - -# Org-mode -.org-id-locations -*_archive - -# flymake-mode -*_flymake.* - -# eshell files -/eshell/history -/eshell/lastdir - -# elpa packages -/elpa/ - -# reftex files -*.rel - -# AUCTeX auto folder -/auto/ - -# cask packages -.cask/ -dist/ - -# Flycheck -flycheck_*.el - -# server auth directory -/server/ - -# projectiles files -.projectile - -# directory configuration -.dir-locals.el - -# network security -/network-security.data - - # ---> C++ # Prerequisites *.d @@ -83,6 +32,146 @@ flycheck_*.el *.out *.app +# ---> Python +# Byte-compiled / optimized / DLL files +__pycache__/ +*.py[cod] +*$py.class + +# C extensions +*.so + +# Distribution / packaging +.Python +build/ +develop-eggs/ +dist/ +downloads/ +eggs/ +.eggs/ +lib/ +lib64/ +parts/ +sdist/ +var/ +wheels/ +share/python-wheels/ +*.egg-info/ +.installed.cfg +*.egg +MANIFEST + +# PyInstaller +# Usually these files are written by a python script from a template +# before PyInstaller builds the exe, so as to inject date/other infos into it. +*.manifest +*.spec + +# Installer logs +pip-log.txt +pip-delete-this-directory.txt + +# Unit test / coverage reports +htmlcov/ +.tox/ +.nox/ +.coverage +.coverage.* +.cache +nosetests.xml +coverage.xml +*.cover +*.py,cover +.hypothesis/ +.pytest_cache/ +cover/ + +# Translations +*.mo +*.pot + +# Django stuff: +*.log +local_settings.py +db.sqlite3 +db.sqlite3-journal + +# Flask stuff: +instance/ +.webassets-cache + +# Scrapy stuff: +.scrapy + +# Sphinx documentation +docs/_build/ + +# PyBuilder +.pybuilder/ +target/ + +# Jupyter Notebook +.ipynb_checkpoints + +# IPython +profile_default/ +ipython_config.py + +# pyenv +# For a library or package, you might want to ignore these files since the code is +# intended to run in multiple environments; otherwise, check them in: +# .python-version + +# pipenv +# According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control. +# However, in case of collaboration, if having platform-specific dependencies or dependencies +# having no cross-platform support, pipenv may install dependencies that don't work, or not +# install all needed dependencies. +#Pipfile.lock + +# PEP 582; used by e.g. github.com/David-OConnor/pyflow +__pypackages__/ + +# Celery stuff +celerybeat-schedule +celerybeat.pid + +# SageMath parsed files +*.sage.py + +# Environments +.env +.venv +env/ +venv/ +ENV/ +env.bak/ +venv.bak/ + +# Spyder project settings +.spyderproject +.spyproject + +# Rope project settings +.ropeproject + +# mkdocs documentation +/site + +# mypy +.mypy_cache/ +.dmypy.json +dmypy.json + +# Pyre type checker +.pyre/ + +# pytype static type analyzer +.pytype/ + +# Cython debug symbols +cython_debug/ + # ---> CMake CMakeLists.txt.user CMakeCache.txt diff --git a/CMakeLists.txt b/CMakeLists.txt new file mode 100644 index 0000000..126cf29 --- /dev/null +++ b/CMakeLists.txt @@ -0,0 +1,51 @@ +cmake_minimum_required(VERSION 3.1.3) + +enable_language(C) +enable_language(CXX) +set(CMAKE_CXX_STANDARD 17) + +if(POLICY CMP0077) + cmake_policy(SET CMP0077 NEW) +endif() + +if (MSVC) + add_compile_options(/W4 /WX) +else() + add_compile_options(-Wall -Wextra -pedantic) +endif() + +project(oc-mint VERSION 0.0.1 LANGUAGES CXX) + +include(FetchContent) +# +# crow project Configuration variables +# +set(CROW_BUILD_EXAMPLES Off) +set(CROW_BUILD_TOOLS Off) +set(CROW_BUILD_TESTS Off) +set(CROW_BUILD_DOCS Off) + +# add crow project to the build +FetchContent_Declare(crow + GIT_REPOSITORY https://github.com/CrowCpp/Crow.git + GIT_TAG v1.0+5 + ) + +if(NOT crow_POPULATED) + FetchContent_Populate(crow) + add_subdirectory(${crow_SOURCE_DIR} ${crow_BINARY_DIR}) +endif(NOT crow_POPULATED) + +# add tartan lamas expected library +FetchContent_Declare(expected + GIT_REPOSITORY https://github.com/TartanLlama/expected.git + GIT_TAG master + ) +if(NOT expected_POPULATED) + FetchContent_Populate(expected) +endif(NOT expected_POPULATED) + +set(API_SOURCES src/main.cpp src/model.cpp src/model.hpp) +add_executable(oc-mint ${API_SOURCES}) +target_link_libraries(oc-mint PRIVATE Crow::Crow INTERFACE tl::expected::expected) +target_include_directories(oc-mint PRIVATE ${expected_SOURCE_DIR}/include) diff --git a/README.md b/README.md index 2383e34..e2e9eec 100644 --- a/README.md +++ b/README.md @@ -1,2 +1,8 @@ -# oc-mint +# oc mint sample + + +# Protocol Questions + +What is signed as cdd - only the content of the cdd item with curly braces +or also the key? diff --git a/src/main.cpp b/src/main.cpp new file mode 100644 index 0000000..3bdd5ad --- /dev/null +++ b/src/main.cpp @@ -0,0 +1,72 @@ +#include "crow/http_response.h" +#include "crow/json.h" +#include + +#include "crow.h" + +#include "model.hpp" + + +int main() +{ + crow::SimpleApp app; + std::shared_ptr model = Model::getModel("simple"); + + CROW_ROUTE(app, "/cddc")//.methods(crow::HTTPMethod::GET) + ([&model](const crow::request& req){ + auto json = crow::json::load(req.body); + if (!json) { + return crow::response(crow::status::BAD_REQUEST, + "json parse error"); + } else { + auto req_cddc = RequestCDDC::from_json(json); + if (!req_cddc) + return crow::response(crow::status::BAD_REQUEST, + "json decode error "); + else { + ResponseCDDC res; + // TBD use serial from req + res.cddc = model->getCDDC(); + res.message_reference = req_cddc->message_reference; + res.status_code = 200; + return crow::response(res.to_json()); + } + } + }); + + CROW_ROUTE(app, "/cddc/serial").methods(crow::HTTPMethod::GET) + ([](){ + return crow::response(crow::status::NOT_IMPLEMENTED); + }); + + CROW_ROUTE(app, "/mkcs").methods(crow::HTTPMethod::GET) + ([](){ + return crow::response(crow::status::NOT_IMPLEMENTED); + }); + + CROW_ROUTE(app, "/mint").methods(crow::HTTPMethod::GET) + ([](){ + return crow::response(crow::status::NOT_IMPLEMENTED); + }); + + + CROW_ROUTE(app, "/renew").methods(crow::HTTPMethod::GET) + ([](){ + return crow::response(crow::status::NOT_IMPLEMENTED); + }); + + CROW_ROUTE(app, "/resume").methods(crow::HTTPMethod::GET) + ([](){ + return crow::response(crow::status::NOT_IMPLEMENTED); + }); + + CROW_ROUTE(app, "/redeem").methods(crow::HTTPMethod::GET) + ([](){ + return crow::response(crow::status::NOT_IMPLEMENTED); + }); + + + + + app.port(18080).run(); +} diff --git a/src/model.cpp b/src/model.cpp new file mode 100644 index 0000000..228b4be --- /dev/null +++ b/src/model.cpp @@ -0,0 +1,130 @@ +#include "model.hpp" +#include "crow/json.h" + +#define TO_JSON(name) r[#name]=name +#define TO_JSON_JSON(name) r[#name]=name.to_json() +#define SEQ_TO_JSON(name) r[#name]=list_to_json(name) + +template +crow::json::wvalue list_to_json(const std::vector& array) { + crow::json::wvalue::list l; + for(auto item:array) + l.push_back(item.to_json()); + return crow::json::wvalue(l); +} + +crow::json::wvalue list_to_json(const std::vector& array) { + crow::json::wvalue::list l; + for(auto item:array) + l.push_back(item); + return crow::json::wvalue(l); +} + + +crow::json::wvalue PublicKey::to_json() const { + crow::json::wvalue r; + TO_JSON(modulus); + TO_JSON(public_exponent); + r["type"]="rsa public key"; + return r; +} + +crow::json::wvalue WeightedUrl::to_json() const +{ + crow::json::wvalue::list l; + crow::json::wvalue w(weight); + + l.push_back(w); + l.push_back(url); + return l; +} + +crow::json::wvalue CDD::to_json() const { + + crow::json::wvalue r; + TO_JSON(additional_info); + TO_JSON(cdd_expiry_date); + TO_JSON(cdd_location); + TO_JSON(cdd_serial); + TO_JSON(cdd_signing_date); + TO_JSON(currency_divisor); + TO_JSON( currency_name); + SEQ_TO_JSON(denominations); + TO_JSON(id); + SEQ_TO_JSON(info_service); + TO_JSON(issuer_cipher_suite); + TO_JSON_JSON(issuer_public_master_key); + SEQ_TO_JSON(mint_service); + TO_JSON(protocol_version); + SEQ_TO_JSON(redeem_service); + SEQ_TO_JSON(renew_service); + + r["type"]= "cdd"; + return r; +} + +crow::json::wvalue CDDC::to_json() const{ + crow::json::wvalue r; + TO_JSON_JSON(cdd); + TO_JSON(signature); + r["type"]= "cdd certificate"; + return r; +} + +crow::json::wvalue MintKey::to_json() const { + crow::json::wvalue r; + + TO_JSON(cdd_serial); + TO_JSON(coins_expiry_date); + TO_JSON(denomination); + TO_JSON(id); + TO_JSON(issuer_id); + TO_JSON_JSON(public_mint_key); + + TO_JSON(sign_coins_not_after); + TO_JSON(sign_coins_not_before); + + r["type"]= "mint key"; + return r; +} + + +crow::json::wvalue MintKeyCert::to_json() const { + crow::json::wvalue r; + TO_JSON_JSON(mint_key); + TO_JSON(signature); + r["type"]= "mint key certificate"; + return r; +} + + +crow::json::wvalue ResponseCDDC::to_json() const +{ + crow::json::wvalue r; + TO_JSON_JSON(cddc); + TO_JSON(message_reference); + TO_JSON(status_code); + TO_JSON(status_description); + + r["type"]= "response cddc"; + return r; +} + +/** blafasel */ +class DefaultModel : public Model { +public: + + DefaultModel() {} + const CDDC& getCDDC() override {return m_cddc; }; + void mint() override {}; + +private: + CDDC m_cddc; +}; + +std::unique_ptr Model::getModel(const std::string& backend_name) +{ +//:wq +//if (backend_name=="default") + return std::make_unique(); +} diff --git a/src/model.hpp b/src/model.hpp new file mode 100644 index 0000000..0e3ecc7 --- /dev/null +++ b/src/model.hpp @@ -0,0 +1,111 @@ +#ifndef MODEL_HPP +#define MODEL_HPP + +#include +#include +#include + +#include "crow/json.h" + +#include "tl/expected.hpp" + +struct PublicKey { + std::string modulus; //: "daaa63ddda38c189b8c49020c8276adbe0a695685a...", + std::string public_exponent;//: 65537, + + crow::json::wvalue to_json() const; +}; + +struct WeightedUrl { + uint32_t weight; + std::string url; + + crow::json::wvalue to_json() const; +}; + + +/** currency description document */ +struct CDD { + + std::string additional_info; + time_t cdd_expiry_date;//: 2023-07-22T15:45:53.164685 + std::string cdd_location;//: https://opencent.org, + size_t cdd_serial;//: 1, + time_t cdd_signing_date;//: 2022-07-22T15:45:53.164685, + size_t currency_divisor;//: 100, + std::string currency_name;//: OpenCent, + std::vector denominations;//: [1, 2, 5], + std::string id;//: 23ed956e629ba35f0002eaf833ea436aea7db5c2, + std::vector info_service; + /* eCipherSuite*/ std::string issuer_cipher_suite;//: RSA-SHA256-PSS-CHAUM82, + PublicKey issuer_public_master_key;//: { + // modulus: daaa63ddda38c189b8c49020c8276adbe0a695685a..., + // public_exponent: 65537, + // type: rsa public key + //}, + std::vector mint_service; + std::string protocol_version; //: https://opencoin.org/1.0, + std::vector redeem_service; + std::vector renew_service; + + crow::json::wvalue to_json() const; +}; + +struct CDDC { + CDD cdd; + std::string signature; + + crow::json::wvalue to_json() const; +}; + +struct MintKey { + unsigned int cdd_serial; + std::string coins_expiry_date; //": "2023-10-30T15:45:53.164685", + unsigned int denomination; //": 1, + std::string id; // "1ceb977bb531c65f133ab8b0d60862b17369d96", + std::string issuer_id; //": "23ed956e629ba35f0002eaf833ea436aea7db5c2", + PublicKey public_mint_key; + + std::string sign_coins_not_after; + std::string sign_coins_not_before; + // "type": "mint key" + crow::json::wvalue to_json() const; +}; + +struct MintKeyCert { + MintKey mint_key; + std::string signature; + + crow::json::wvalue to_json() const; +}; + +struct RequestCDDC { + unsigned int cdd_serial;/// The version of the CDD. (Int) + unsigned int message_reference; /// Client internal message reference. + /// (Integer) + static std::optional from_json(const crow::json::rvalue & json); +}; + +struct ResponseCDDC { + CDDC cddc; + unsigned int message_reference; + unsigned int status_code; + std::string status_description; + + crow::json::wvalue to_json() const; +}; + + +class Model { +public: + virtual ~Model(){}; + + virtual const CDDC& getCDDC() = 0; + virtual void mint() = 0; + + static std::unique_ptr getModel(const std::string& backend_name); +private: +}; + +#endif // #ifndef MODEL_HPP +