Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Draft CLI tool #1

Draft
wants to merge 21 commits into
base: master
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions .gitmodules
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
[submodule "thirdparty/Jinja2Cpp"]
path = thirdparty/Jinja2Cpp
url = git@github.com:jinja2cpp/Jinja2Cpp.git
54 changes: 54 additions & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
cmake_minimum_required(VERSION 3.1)
project(jinja2cpp-cli CXX)

set(CMAKE_CXX_STANDARD 14)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
set(CMAKE_CXX_EXTENSIONS OFF)


set (CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} ${CMAKE_CURRENT_BINARY_DIR})

set (JINJA2CPP_DEPS_MODE conan-build CACHE STRING "" FORCE)
add_subdirectory (thirdparty/Jinja2Cpp ${CMAKE_CURRENT_BINARY_DIR}/thirdparty/jinja2cpp)

find_package(boost 1.71 COMPONENTS program_options filesystem REQUIRED)
find_package(jsonformoderncpp 3.7.0 REQUIRED)
find_package(yaml-cpp 0.6.0 REQUIRED)
#find_package(jinja2cpp REQUIRED)

# Generate Version file
execute_process(COMMAND ${GIT_EXECUTABLE} describe --tags --always OUTPUT_VARIABLE GIT_REPO_VERSION
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}/thirdparty/Jinja2Cpp)
configure_file("version.h.in" "version.h")

add_library(jinja2cpp-libcli
src/command_line.cpp
src/command_line_j2.cpp
src/command_line.h
src/param_resolver.cpp
src/param_resolver.h
src/yaml_reflector.h
)
add_library(jinja2cpp::cli ALIAS jinja2cpp-libcli)
target_include_directories(jinja2cpp-libcli PUBLIC ${CMAKE_CURRENT_BINARY_DIR})
target_link_libraries(jinja2cpp-libcli PUBLIC jinja2cpp
jsonformoderncpp::jsonformoderncpp
yaml-cpp::yaml-cpp
boost::boost
)

add_executable(${PROJECT_NAME} src/main.cpp)
target_link_libraries(${PROJECT_NAME} jinja2cpp::cli)
set_target_properties (${PROJECT_NAME} PROPERTIES
CXX_STANDARD 14
CXX_STANDARD_REQUIRED ON)

add_executable(j2cpp-cli src/main_j2.cpp)
target_link_libraries(j2cpp-cli jinja2cpp::cli)
set_target_properties (j2cpp-cli PROPERTIES
CXX_STANDARD 14
CXX_STANDARD_REQUIRED ON)

# Setup testing
enable_testing()
add_subdirectory(test)
28 changes: 28 additions & 0 deletions Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
FROM ubuntu:disco as builder

LABEL maintainer="Andrey Bronin <jonnib@yandex.ru>"

RUN apt-get update && \
apt-get install -y nano git build-essential cmake python3-pip && \
pip3 install conan

RUN conan user
RUN conan remote add bincrafters https://api.bintray.com/conan/bincrafters/public-conan
RUN conan remote add flexferrum https://api.bintray.com/conan/flexferrum/conan-packages
RUN conan remote add martin https://api.bintray.com/conan/martinmoene/nonstd-lite

COPY . /project
WORKDIR /project

RUN conan install . --build=missing
RUN cmake -DCMAKE_BUILD_TYPE=Release . && make

FROM ubuntu:disco
COPY --from=builder /project/bin/jinja2cpp-cli /jinja2cpp

# RUN apk update && \
# apk upgrade && \
# apk --update add libstdc++ \
# rm -rf /var/cache/apk/*

ENTRYPOINT [ "/jinja2cpp" ]
37 changes: 37 additions & 0 deletions Dockerfile.alpine
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
FROM alpine:latest as builder

LABEL maintainer="Andrey Bronin <jonnib@yandex.ru>"

RUN apk update && \
apk upgrade && \
apk --update add \
# alpine-sdk \
g++ \
build-base \
cmake \
libstdc++ \
git \
linux-headers \
py-pip && \
pip install conan && \
rm -rf /var/cache/apk/*

COPY . /project
WORKDIR /project
RUN conan user
RUN conan remote add bincrafters https://api.bintray.com/conan/bincrafters/public-conan
RUN conan remote add andreybronin https://api.bintray.com/conan/andreybronin/conan
RUN conan remote add martinmoene https://api.bintray.com/conan/martinmoene/nonstd-lite
RUN conan remote add flexferrum https://api.bintray.com/conan/flexferrum/conan-packages
RUN conan install . --build=missing
RUN cmake -DCMAKE_BUILD_TYPE=Release . && make

FROM alpine:latest
COPY --from=builder /project/bin/jinja2cpp-cli /jinja2cpp

RUN apk update && \
apk upgrade && \
apk --update add libstdc++ \
rm -rf /var/cache/apk/*

ENTRYPOINT [ "/jinja2cpp" ]
18 changes: 17 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
@@ -1 +1,17 @@
# tools-cli
# Jinja2cpp CLI tool

```
Usage: jinja2cpp [options] <input template> <input data>
Options:
-h [ --help ] Display this help message
-v [ --version ] Display the version number
--format Format of input variables: auto, ini, json, yaml, toml
--input-template arg Input template file path
--input-data arg Define template variable in the form of key=value
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Also '--templates-dir' option needed in order to properly setup TemplateEnv and templates inheritance/inclusion support.

```

### Docker

```
docker run --rm bronin/jinja2cpp -h
```
20 changes: 20 additions & 0 deletions conanfile.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
[requires]
boost/1.71.0
gtest/1.8.1
variant-lite/1.2.2
expected-lite/0.3.0
optional-lite/3.2.0
string-view-lite/1.3.0
fmt/5.3.0

yaml-cpp/0.6.3
jsonformoderncpp/3.7.0@vthiery/stable
tinytoml/0.4@bincrafters/stable

[options]
jinja2cpp:shared=False
gtest:shared=False
boost:shared=False

[generators]
cmake_find_package
100 changes: 100 additions & 0 deletions src/command_line.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,100 @@
#include "command_line.h"
#include "param_resolver.h"
#include <version.h>

#include <boost/program_options.hpp>

#include <iostream>
#include <memory>

namespace jinja2
{

CommandLine::CommandLine(std::unique_ptr<Template> tpl) : m_tpl(std::move(tpl)) { }

int CommandLine::Execute(int argc, char* argv[])
{
namespace po = boost::program_options;
po::options_description desc("Options");

desc.add_options()
("help,h", "Display this help message")
("version,v", "Display the version number")
("format", "Format of input variables: auto, ini, json, yaml, toml")
("input-template", po::value<std::string>(), "Input template file path")
("input-data", po::value<std::vector<std::string>>(),
"Define template variable in the form of key=value");

po::positional_options_description p;
p.add("input-template", 1);
p.add("input-data", -1);

try {
po::variables_map vm;
po::store(po::command_line_parser(argc, argv).options(desc).positional(p).allow_unregistered().run(), vm);
po::notify(vm);

if (vm.count("help")) {
std::cout << Help() << std::endl << desc << std::endl;
return EXIT_FAILURE;
}

if (vm.count("version")) {
std::cout << Version() << std::endl;
return EXIT_SUCCESS;
}

for (auto &v : vm["input-data"].as<std::vector<std::string> >())
{
if (vm.count("input-data")) {
std::cout << "Input data are: ";
std::cout << v << std::endl;
}
}


if (vm.count("input-template"))
{
const auto &filename = vm["input-template"].as<std::string>();
RenderTemplate(filename);
return EXIT_SUCCESS;
}

}
catch (std::exception const& e)
{
std::cerr << e.what() << std::endl;
}
return EXIT_FAILURE;
}

std::string CommandLine::Help()
{
return "Usage: jinja2cpp-cli [options] <input template> <input data>";
}

std::string CommandLine::Version()
{
return jinja2cppVersion;
}


void CommandLine::RenderTemplate(const std::string& fileName)
{
jinja2::Template tpl;
auto result = tpl.LoadFromFile(fileName);
if (!result.has_value()) {
std::cout << result.error() << std::endl;
}

std::cout << "Input template is: ";
std::cout << fileName << std::endl;


JsonParamResolver resolver;

ValuesMap vm = resolver.ParamsFromFile("sample.json");
tpl.Render(std::cout, vm);
}

} // namespace jinja2
53 changes: 53 additions & 0 deletions src/command_line.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
#pragma once

#include <jinja2cpp/template.h>

#include <string>

namespace jinja2 {

struct ICommands {
virtual ~ICommands() = default;

virtual std::string Help() = 0;
virtual std::string Version() = 0;
virtual void RenderTemplate(const std::string& fileName) = 0;
};

/**
* CommandLine is analog CLI of python jinja2-cli
*/
class CommandLine : protected ICommands {
public:
explicit CommandLine(std::unique_ptr<Template> tpl = std::make_unique<Template>());

int Execute(int argc, char **argv);

protected:
std::string Help() override ;
std::string Version() override;
void RenderTemplate(const std::string& fileName) override;

private:
std::unique_ptr<Template> m_tpl;
};

/**
* CommandLine is analog CLI of modern python j2cli (https://github.com/kolypto/j2cli)
*/
class CommandLineJ2 : protected ICommands {
public:
explicit CommandLineJ2(std::unique_ptr<Template> tpl = std::make_unique<Template>());

int Execute(int argc, char **argv);

protected:
std::string Help() override ;
std::string Version() override;
void RenderTemplate(const std::string& fileName) override;

private:
std::unique_ptr<Template> m_tpl;
};

} // namespace jinja2
31 changes: 31 additions & 0 deletions src/command_line_j2.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
#include "command_line.h"
#include <version.h>

namespace jinja2
{

CommandLineJ2::CommandLineJ2(std::unique_ptr<Template> tpl) : m_tpl(std::move(tpl)) { }

int CommandLineJ2::Execute(int argc, char* argv[])
{
// todo: implement me
return 0;
}

std::string CommandLineJ2::Help()
{
return "Usage: j2cpp-cli [options] <input template> <input data>";
}

std::string CommandLineJ2::Version()
{
return jinja2cppVersion;
}


void CommandLineJ2::RenderTemplate(const std::string& fileName)
{
// todo: implement me
}

} // namespace jinja2
6 changes: 6 additions & 0 deletions src/main.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
#include "command_line.h"

int main(int argc, char* argv[]) {
jinja2::CommandLine cli;
return cli.Execute(argc, argv);
}
6 changes: 6 additions & 0 deletions src/main_j2.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
#include "command_line.h"

int main(int argc, char* argv[]) {
jinja2::CommandLineJ2 cli;
return cli.Execute(argc, argv);
}
19 changes: 19 additions & 0 deletions src/param_resolver.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
#include "param_resolver.h"

// #include <jinja2cpp/template.h>
#include <jinja2cpp/binding/nlohmann_json.h>

using json = nlohmann::json;

namespace jinja2 {

const ValuesMap JsonParamResolver::ParamsFromFile(const std::string &filePath)
{
nlohmann::json values = {
{"message", "Hello World from Parser!"}
};
auto x = Reflect(std::move(values));
return {{"params", x}};
}

} // namespace jinja2
Loading