αα αααα»αα’αααααααααααα»αααΉααα·ααΆαα’αααΈααααααααααα»ααααααΎαααααΌ (cookiecutter) αα·ααααα αααα·ααααΆααααααΆααααΆααααααααααΆ REST API αα αααα»α C++ αααααααΎ docker/docker-compose αα·ααααααα·ααΈααααααααααααα αα conan α
αααα»αα’αα‘α»αααα hackathon αααααΆαα ααααααα»αααΆαα
αΌααα½αααΆα’αααα’αα·αααααααααααα·ααΈααΆαααααα αααα½αααΆαααΎαα‘αΎαα’αααΈα’αααΈαααααααΌαααααΎααΎααααΈαααααααααΆααααααΈααααΌαααααΆααα α’αααΈαβαααβααΆαβαααααβαα αΌαβααβαααβαααβααα ααΊβαααααβαααβαααα»α αα·αβαααα»α
ααΌα αααα ααΎαααααΌαααααααα»αααΉαααΆααα·α αα ααααΆααααααααααΆαααααααααΆαααααα»αααααα αααααΆααΆααα·α αα α ααααααΊααααΌαααααΎαααΆααα·ααααααααααααααααΆααΆαα»α α αΎααααααααΆαα αααα»αααΌαααααΆααα·ααααααα α αΎααααααΆααααΈααΆααααααααααα½αααα αα·αααααααΆααααΆαααααΎα±αααααα»ααααα»αααΆαααΆα’αααα’αα·αααααα C++ αααααααααΆααααααααααααααΎα’αααααααΆαα αααααΎαα ααα»αααααααΊααΆααΆααΉαααΆααααααΏα ααα·αααΆαααΆααααα αααΎα α αΎαααΆααΌαα ααααα·αα·α ααααααΉαααΈαααΆαααΆαα½αααΉααααααααααΎαααΉαααΈαααααααααααααααααΆααααααααα»αα ααααααα»αααΆαααααΎαααΆ αααα»ααα·ααααααααΎααΏααααααααα αααα»α C++ α αΎαα’αΆα α αααΆαααα 20+ ααααααααα αααααΎααααΈααααααα α ααααα αα·αααααΆαααααααΆααααααααααααααΆααααΆαααΆααααα½αα αα·ααΆαβα²ααβα αβαα αααα»αβααΆαβα αΉαα αααα αΎαααΆα’αααΈαααααΎαααΆααααααα α α·ααα α αΎαααΆααααα ααααααααααΆαααααααααααααΆαααα αααα»α Pythonα
α₯α‘αΌαααα αααα»αα’αα‘α»ααααααααααααα½αα―αα±αααα
ααΆα
ααααα‘αα αααα»αααΆααααααα
α
α·ααααααα·ααΈαααααααααΆαααααα
αααα»α C++ α ααΏαααααΌααααααααΌαααααΎααΊαααααα
α
α·αααααΎαααααΆααααααααααααα αααααΎααααααααα»αααΆαααααΆααα
α»α
conanfile.txt
[ααΆαααΆα]
poco/1.9.3
libpq/11.5
α αΎαααΆαα½αααΉαααΆααααααααΆααΆαααα "conan install ." ααα‘αΎααααααΆαααα αΆαααΆα αα ααΆαααααααΆαα· ααΆααα αΆαααΆα αααΎααααΈααααΎααΆαααααΆααααααΌααααααα
CMakeLists.txt
include(build/conanbuildinfo.cmake)
conan_basic_setup()
target_link_libraries(<target_name> ${CONAN_LIBS})
αααααΆααααΈααααα αααα»αα αΆααααααΎαααααααααααααΆαααααΎααααΈααααΎααΆαααΆαα½α PostgreSQL αααααααΆααΆαααααααα½αααααααα»αααΆααααα·ααααααα·α αα½α αααα»αααΆαααααΎααΆαααΆαα½α α αΎαααΆααααΆααααΆαααα Python ααααααΎαααααΎα’ααααααααααΆαα½ααααααα α αΎαααΎα’αααααΉαααΈα’αααΈααααααα»αααΆαααααα? ααΆαααα·ααα αααα»α POCO! ααα»αααα conan αα·αααΉαααΆααΆαααα·ααα αααα»α POCO α αΎααα·αααΉαααΈαααααααααΎαααΆαα ααΆαα―αααΆαααααααα ααΆααααααααα α½ααααααα αααα»αααααΆαα (αααα»αααΆαααααααα½α α αΎαα’αααΈααα α»αααααα ααΆααα’ααααααααΎα POCO)α αααααΆααααααΆα’αααααΉαααααΌαααααΎααααααΆααααα½αααααααααα
α αΎααααααΆαααααααααΎααααααααα»αααΆαααααΆαααα
ααΎαααααΆαααααααα·αααΌαααααα·αα
ααα αΆααααααΆααααΊααααΌααααααααααΌααααΆαααααααα’αΆα
ααααΎαααΆαααααΎα
ααΎαααααΌαααααα½ααααα TemplateServerApp ααααααΎαααΈ Poco::Util::ServerApplication α αΎαααα·ααααα·ααΈααΆαααααααααΆααα
TemplateServerApp
#pragma once
#include <string>
#include <vector>
#include <Poco/Util/ServerApplication.h>
class TemplateServerApp : public Poco::Util::ServerApplication
{
protected:
int main(const std::vector<std::string> &);
};
int TemplateServerApp::main(const vector<string> &)
{
HTTPServerParams* pParams = new HTTPServerParams;
pParams->setMaxQueued(100);
pParams->setMaxThreads(16);
HTTPServer s(new TemplateRequestHandlerFactory, ServerSocket(8000), pParams);
s.start();
cerr << "Server started" << endl;
waitForTerminationRequest(); // wait for CTRL-C or kill
cerr << "Shutting down..." << endl;
s.stop();
return Application::EXIT_OK;
}
αα αααα»ααα·ααΈααΆαααααααααΆααααΎαααααΌαααααααααΆαααΆαααααα: α αααα ααα½ααααααααα‘αΆααα·αααα ααα½αα α αΎαααααΆαααααα»α α’αααααααΌααααααααΆααα’ααααααααααΆααααααΆααααααΎα αΌαα αααααααΌαααΆαααααΎαααααΆααααααΎααααα ααα
TemplateRequestHandlerFactory
class TemplateRequestHandlerFactory : public HTTPRequestHandlerFactory
{
public:
virtual HTTPRequestHandler* createRequestHandler(const HTTPServerRequest & request)
{
return new TemplateServerAppHandler;
}
};
αααα»αααααΈαααααααα»α ααΆααααΆαααααααααΎαα§ααααααααααααΆαααΌα ααααΆααΆααααα - TemplateServerAppHandler α αααααΊααΆαααααααααααΎαα’αΆα ααΆαααααααα·ααααΆα’αΆααΈαααααααααααΎαα
TemplateServerAppHandler
class TemplateServerAppHandler : public HTTPRequestHandler
{
public:
void handleRequest(HTTPServerRequest &req, HTTPServerResponse &resp)
{
URI uri(req.getURI());
string method = req.getMethod();
cerr << "URI: " << uri.toString() << endl;
cerr << "Method: " << req.getMethod() << endl;
StringTokenizer tokenizer(uri.getPath(), "/", StringTokenizer::TOK_TRIM);
HTMLForm form(req,req.stream());
if(!method.compare("POST"))
{
cerr << "POST" << endl;
}
else if(!method.compare("PUT"))
{
cerr << "PUT" << endl;
}
else if(!method.compare("DELETE"))
{
cerr << "DELETE" << endl;
}
resp.setStatus(HTTPResponse::HTTP_OK);
resp.setContentType("application/json");
ostream& out = resp.send();
out << "{"hello":"heh"}" << endl;
out.flush();
}
};
αααα»αααααΆααααααΎαααααΌααααΆααααΎααααΈααααΎααΆαααΆαα½α PostgreSQL α ααΎααααΈα’αα»αααα SQL ααΆααααααΌα ααΆααΆααααααΎαααΆααΆαααΆααα·ααΈααΆααααααα½αα ααααα·ααααα·SQL(). αααααΆαααααα½αααααααα»αααααααΆα α¬ααΆαααΆααααα·αααααα α’αααααΉαααααΌαααα½αααΆαααΆααααααΆααααΆαααα GetConnection() α αΎαααααΎ libpg APIα (αααα ααβααΆβαααβαααααβαααα»αβααΉαβααβα’αα»αααα·αααβααα)α
ααΌαααααΆααα·αααααα
#pragma once
#include <memory>
#include <mutex>
#include <libpq-fe.h>
class Database
{
public:
Database();
std::shared_ptr<PGconn> GetConnection() const;
bool ExecuteSQL(const std::string& sql);
private:
void establish_connection();
void LoadEnvVariables();
std::string m_dbhost;
int m_dbport;
std::string m_dbname;
std::string m_dbuser;
std::string m_dbpass;
std::shared_ptr<PGconn> m_connection;
};
αααΆαααΆααααααααΆααα’αααααααΆααααααΆαααα ααΌαααααΆααα·ααααααααααΌαααΆαααα ααααΈααα·ααααΆα ααΌα ααααα’αααααααααΌααααααΎα αα·αααααααα ααΆααααααααα―αααΆα .env αααααα
.NS
DATABASE_NAME=template
DATABASE_USER=user
DATABASE_PASSWORD=password
DATABASE_HOST=postgres
DATABASE_PORT=5432
α’αααα’αΆα
ααΎαααΌαααΆααα’αααα
α αΎαα₯α‘αΌαααααααααααααΆααααΆαα α»ααααααααααΆαααααα dockerfile αα·α docker-compose.yml α αα·ααΆαα±ααααααααα ααΆααΆαα αααΆααααααΆαα αααΎα α αΎααα·αααααΉααααααααΆααααααα»αααΆαααααααααα αααααααΆα αΆαααΆα ααααα»αααΆααααΆααααααΆαααα‘αΎααα·αααΆααααα ααα»αααααααααΆααααααα αΆαααα conan α ααΆα§ααΆα ααα ααΎααααΈα±αα conan ααΆααα ααα‘αΎα αα·ααααααΎαααΆαα’αΆαααααα αΆαααΆα α ααΆαα·ααααααααααΆαααααααΆααααΆαααα»αααΆαααΆααα "conan install ." ααΆααααααΌαααααααΆαααααΆαααΆαααααα -s compiler.libcxx=libstdc++11 ααΎαα·αααΌα αααααα α’αααααααα»αααΉαααΆαααα½αααα α»αααΆα αααΎααα ααααΆααααΆαααααΆαααααααα·ααΈααααα’αααα αααα»αααΆαααΆααααΆααααΆαα½αααΉαααα α»ααααα’ααααααααααΆα αααΎααααα α αΎααααα»ααααααΉαααΆα’ααααααααααΉααα½αααα»ααααααααααααααααααΆααααα αΆααααααα»ααααααααα·α α
αααααΆαααα αααααΆααααΈααααα docker-compose.yml ααΆαααααΌααααΆααααααα·ααααααα»α αααα»αααΆαααααααααΆαααΆαααα
αααα»ααααααΉαααΆααααΌαααααΉααα½αα’αααα
αΆααααααΎαααααΌααα
ααΎααααΌαααααΆααααααα½ααααααα»αααΆαα’αα·αααααααααααα·ααΈ REST API ααΆααΆααΆααα’ααα
αΆααα αα·αααΆαααΆααα ααα»ααααααΆααΆααΆαααα
ααααΌαα
αααααααΌα
ααΆ C ++ ααΆααΎαα
ααΌα
ααααΆαααααααα αααα»αααΌααααααα’αα»ααΆαααα±ααα’αΆααα
ααΈααα
ααααα: www.habr.com