PhoenixGenerator  2.0.0
Set of tools to generate code
wrapper_generator.cpp File Reference
+ Include dependency graph for wrapper_generator.cpp:

Go to the source code of this file.

Functions

ProjectConfig project_createWrapperConfig (const ProjectConfig &projectConfig)
 Create the config of the wrapper. More...
 
bool project_wrapper_generator (const ProjectConfig &projectConfig, const PPath &configFile)
 Generate a full python wrapper project with PhoenixDataStream and PhoenixTypeStream. More...
 
bool project_wrapper_generator_pyprojectToml (const PPath &fileName, const ProjectConfig &projectConfig, const PString &baseImplInclude, const std::vector< PClassConfig > &vecClassConfig, const PVecPath &vecInclude)
 Create the readme of the project directory. More...
 
bool project_wrapper_generator_readme (const PPath &fileName, const ProjectConfig &projectConfig)
 Create the readme of the project directory. More...
 
bool project_wrapper_generator_setuppy (const PPath &fileName, const ProjectConfig &projectConfig, const PString &baseImplInclude, const std::vector< PClassConfig > &vecClassConfig, const PVecPath &vecInclude)
 Create the readme of the project directory. More...
 
void updateVecClassConfig (std::vector< PClassConfig > &vecClassConfig)
 Update the vector of class configuration. More...
 

Function Documentation

◆ project_createWrapperConfig()

ProjectConfig project_createWrapperConfig ( const ProjectConfig projectConfig)

Create the config of the wrapper.

Parameters
projectConfig: main configuration
Returns
wrapper configuration

Definition at line 16 of file wrapper_generator.cpp.

16  {
17  ProjectConfig wrapper(projectConfig);
18  wrapper.name = "Py"+projectConfig.name;
19  wrapper.url = wrapper.url.replace(projectConfig.name, wrapper.name);
20 
21  return wrapper;
22 }
PString replace(const PString &pattern, const PString &replaceStr) const
Replace a PString into an other PString.
Definition: PString.cpp:204
Configuration of the project.
PString name
Name of the project.

References ProjectConfig::name, PString::replace(), and ProjectConfig::url.

Referenced by project_wrapper_generator().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ project_wrapper_generator()

bool project_wrapper_generator ( const ProjectConfig projectConfig,
const PPath configFile 
)

Generate a full python wrapper project with PhoenixDataStream and PhoenixTypeStream.

Parameters
projectConfig: description of the full project
configFile: configuration file of the
Returns
true on success, false otherwise

Definition at line 178 of file wrapper_generator.cpp.

178  {
179  ProjectConfig wrapperConfig(project_createWrapperConfig(projectConfig));
180  PVecPath vecInclude;
181  std::vector<PClassConfig> vecClassConfig;
182  if(!parserClassConfig(vecClassConfig, vecInclude, configFile)){
183  std::cerr << "project_wrapper_generator : can't load file '" << configFile << "'" << std::endl;
184  return false;
185  }
186  //TODO : pass through vecClassConfig and replace PPath and PString by std::string to ensure PhoenixDataStream will work well on them for the wrapper
187  updateVecClassConfig(vecClassConfig);
188 
189  //Then, let's create the hierarchy
190  PPath mainProjectDir(wrapperConfig.name);
191  if(!mainProjectDir.createDirectory()){
192  std::cerr << "project_wrapper_generator : cannot create main directory of project '"<<mainProjectDir<<"'" << std::endl;
193  return false;
194  }
195  //And module dir
196  PPath mainProjectModule(mainProjectDir / PPath(wrapperConfig.name.toLower()));
197  if(!mainProjectModule.createDirectory()){
198  std::cerr << "project_generator : cannot create module directory of project '"<<mainProjectModule<<"'" << std::endl;
199  return false;
200  }
201  //The readme
202  PPath readmeFile(mainProjectDir / PPath("README.md"));
203  if(!project_wrapper_generator_readme(readmeFile, projectConfig)){return false;}
204 
205  PString baseImplInclude = configFile.getFileName().eraseExtension();
206  //The readme
207  PPath setupFile(mainProjectDir / PPath("setup.py"));
208  if(!project_wrapper_generator_setuppy(setupFile, projectConfig, baseImplInclude, vecClassConfig, vecInclude)){return false;}
209 
210  PPath pyprojectFile(mainProjectDir / PPath("pyproject.toml"));
211  if(!project_wrapper_generator_pyprojectToml(pyprojectFile, projectConfig, baseImplInclude, vecClassConfig, vecInclude)){return false;}
212  //The unit tests
213  if(!project_wrapper_moduleGeneratorTest(mainProjectDir, projectConfig, "py"+projectConfig.name.toLower(), vecClassConfig, vecInclude)){return false;}
214  //The full module
215  return project_wrapper_moduleGenerator(mainProjectModule, projectConfig, baseImplInclude, vecClassConfig, vecInclude);
216 }
std::vector< PPath > PVecPath
Definition: PPath.h:75
Path of a directory or a file.
Definition: PPath.h:17
PPath & eraseExtension()
Erase the extension of the PPath.
Definition: PPath.cpp:292
PPath getFileName() const
Get the name of the file, from last char to /.
Definition: PPath.cpp:172
Extends the std::string.
Definition: PString.h:16
PString toLower() const
Convert PString in lower case.
Definition: PString.cpp:598
bool parserClassConfig(std::vector< PClassConfig > &listClassConfig, PVecPath &listInclude, const PPath &fileName)
Parser list class config.
bool project_wrapper_generator_setuppy(const PPath &fileName, const ProjectConfig &projectConfig, const PString &baseImplInclude, const std::vector< PClassConfig > &vecClassConfig, const PVecPath &vecInclude)
Create the readme of the project directory.
bool project_wrapper_generator_readme(const PPath &fileName, const ProjectConfig &projectConfig)
Create the readme of the project directory.
bool project_wrapper_generator_pyprojectToml(const PPath &fileName, const ProjectConfig &projectConfig, const PString &baseImplInclude, const std::vector< PClassConfig > &vecClassConfig, const PVecPath &vecInclude)
Create the readme of the project directory.
ProjectConfig project_createWrapperConfig(const ProjectConfig &projectConfig)
Create the config of the wrapper.
void updateVecClassConfig(std::vector< PClassConfig > &vecClassConfig)
Update the vector of class configuration.
bool project_wrapper_moduleGenerator(const PPath &modulePath, const ProjectConfig &projectConfig, const PString &baseImplInclude, const std::vector< PClassConfig > &vecClassConfig, const PVecPath &vecInclude)
Create the wrapper module.
bool project_wrapper_moduleGeneratorTest(const PPath &projectPath, const ProjectConfig &projectConfig, const PString &moduleName, const std::vector< PClassConfig > &vecClassConfig, const PVecPath &vecInclude)
Generate the unit tests of the project.

References PPath::createDirectory(), PPath::eraseExtension(), PPath::getFileName(), ProjectConfig::name, parserClassConfig(), project_createWrapperConfig(), project_wrapper_generator_pyprojectToml(), project_wrapper_generator_readme(), project_wrapper_generator_setuppy(), project_wrapper_moduleGenerator(), project_wrapper_moduleGeneratorTest(), PString::toLower(), and updateVecClassConfig().

Referenced by project_generator().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ project_wrapper_generator_pyprojectToml()

bool project_wrapper_generator_pyprojectToml ( const PPath fileName,
const ProjectConfig projectConfig,
const PString baseImplInclude,
const std::vector< PClassConfig > &  vecClassConfig,
const PVecPath vecInclude 
)

Create the readme of the project directory.

Parameters
fileName: name of the file to be created
projectConfig: config of the project
baseImplInclude: basic include of the module implementation
vecClassConfig: vector of class confoguration
vecInclude: vector of includes
Returns
true on success, false otherwise

Definition at line 102 of file wrapper_generator.cpp.

102  {
103  PString body;
104  body += "\n";
105  body += getCMakeListsHeader();
106  body += "[project]\n";
107  body += "name = \"py"+projectConfig.name.toLower()+"\"\n";
108  body += "version = \""+projectConfig.version+"\"\n";
109  body += "description = \""+projectConfig.description.replace("\n", " ")+"\"\n";
110  body += "readme = \"README.md\"\n";
111  body += "license = \"CeCILL-C\"\n";
112  body += "dependencies = [\n";
113  body += "\t\"numpy\"\n";
114  body += "]\n";
115  body += "\n";
116  body += "[build-system]\n";
117  body += "requires = [\n";
118  body += "\t\"numpy\",\n";
119  body += "\t\"setuptools >= 74.1\",\n";
120  body += "\t\"cython\"\n";
121  body += "]\n";
122  body += "build-backend = \"setuptools.build_meta\"\n";
123  body += "\n";
124 // body += "[tool.setuptools]\n";
125 // body += "ext-modules = [\n";
126 // body += "\t{\n";
127 // body += "\t\tname = \""+projectConfig.name.toLower()+"\",\n";
128 // body += "\t\tsources = [\n";
129 // body += "\t\t\t\""+projectConfig.name.toLower()+"/"+baseImplInclude+"_wrapper.cpp\",\n";
130 // body += "\t\t\t\""+projectConfig.name.toLower()+"/"+projectConfig.name+"_module.cpp\"\n";
131 // body += "\t\t],\n";
132 // body += "\t\textra_compile_args = [\"-O3\", \"-Werror\", \"-g\"]\n";
133 // body += "\t}\n";
134 // body += "\n";
135 // body += "]\n";
136  body += "\n";
137  return fileName.saveFileContent(body);
138 }
bool saveFileContent(const PString &content) const
Save a PString in a file.
Definition: PPath.cpp:395
PString getCMakeListsHeader()
Get the CMakeLists.txt header.
PString description
Description of the project.
PString version
Project version.

References ProjectConfig::description, getCMakeListsHeader(), ProjectConfig::name, PString::replace(), PPath::saveFileContent(), PString::toLower(), and ProjectConfig::version.

Referenced by project_wrapper_generator().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ project_wrapper_generator_readme()

bool project_wrapper_generator_readme ( const PPath fileName,
const ProjectConfig projectConfig 
)

Create the readme of the project directory.

Parameters
fileName: name of the file to be created
projectConfig: config of the project
Returns
true on success, false otherwise

Definition at line 29 of file wrapper_generator.cpp.

29  {
30  PString body;
31  body += "![PLIBS_9 logo](doc/logo.png)\n\n";
32 
33  body += "# Remarks\n\n";
34  body += "This project was generated automatically by [phoenix_filegenerator](https://gitlab.in2p3.fr/CTA-LAPP/PHOENIX_LIBS2/PhoenixFileGenerator)\n";
35  body += "using [phoenix_generator](https://gitlab.in2p3.fr/CTA-LAPP/PHOENIX_LIBS2/PhoenixGenerator) library\n\n";
36 
37  body += "# Code\n\n";
38  body += "Version : " + projectConfig.version + "\n\n";
39  body += projectConfig.url + "\n\n";
40  body += "# Description\n\n";
41  body += "Python wrapper version.\n";
42  body += projectConfig.description + "\n\n";
43 
44  return fileName.saveFileContent(body);
45 }
PString url
Project url.

References ProjectConfig::description, PPath::saveFileContent(), ProjectConfig::url, and ProjectConfig::version.

Referenced by project_wrapper_generator().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ project_wrapper_generator_setuppy()

bool project_wrapper_generator_setuppy ( const PPath fileName,
const ProjectConfig projectConfig,
const PString baseImplInclude,
const std::vector< PClassConfig > &  vecClassConfig,
const PVecPath vecInclude 
)

Create the readme of the project directory.

Parameters
fileName: name of the file to be created
projectConfig: config of the project
baseImplInclude: basic include of the module implementation
vecClassConfig: vector of class confoguration
vecInclude: vector of includes
Returns
true on success, false otherwise

Definition at line 55 of file wrapper_generator.cpp.

55  {
56  PString body, moduleName = "py" + projectConfig.name.toLower();
57  body += "\n";
58  body += getCMakeListsHeader();
59  body += "from setuptools import setup\n";
60  body += "from setuptools import Extension\n";
61  body += "import sys\n";
62  body += "import numpy as np\n";
63  body += "import subprocess\n";
64  body += "\n";
65  body += "dataStreamIncludeDir = subprocess.run(['phoenixdatastream-config', '--include'], capture_output = True, text = True).stdout.strip(\"\\n\")\n";
66  body += "dataStreamLibDir = subprocess.run(['phoenixdatastream-config', '--lib'], capture_output = True, text = True).stdout.strip(\"\\n\")\n";
67  body += "\n";
68  body += "ext_modules = [\n";
69  body += "\tExtension(\""+moduleName+"\", sources=([\n";
70  body += "\t\t\""+moduleName+"/"+baseImplInclude+"_wrapper.cpp\",\n";
71  body += "\t\t\""+moduleName+"/"+projectConfig.name.toLower()+"_module.cpp\"\n";
72  body += "\t]),\n";
73  body += "\textra_compile_args = [\"-O3\", \"-Werror\", \"-g\"],\n";
74 
75  body += "\tinclude_dirs = [np.get_include(), dataStreamIncludeDir, \"./\", \""+moduleName+"/\"],\n";
76  body += "\tlibraries=[\"phoenix_data_stream\"],\n";
77  body += "\tlibrary_dirs=[dataStreamLibDir],\n";
78  body += "\t)\n";
79  body += "]\n\n";
80 
81  body += "try:\n";
82  body += "\tsetup(\n";
83  body += "\t\tname=\""+moduleName+"\",\n";
84  body += "\t\tversion=\""+projectConfig.version+"\",\n";
85  body += "\t\text_modules=ext_modules,\n";
86  body += "\t)\n";
87  body += "except Exception as e:\n";
88  body += "\tprint(str(e))\n";
89  body += "\tsys.exit(-1)\n";
90  body += "\n";
91  return fileName.saveFileContent(body);
92 }

References getCMakeListsHeader(), ProjectConfig::name, PPath::saveFileContent(), PString::toLower(), and ProjectConfig::version.

Referenced by project_wrapper_generator().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ updateVecClassConfig()

void updateVecClassConfig ( std::vector< PClassConfig > &  vecClassConfig)

Update the vector of class configuration.

Parameters
[out]vecClassConfig: vector of class configuration to be updated

Definition at line 143 of file wrapper_generator.cpp.

143  {
144  std::map<std::string, std::string> mapEnum;
145  for(std::vector<PClassConfig>::iterator it(vecClassConfig.begin()); it != vecClassConfig.end(); ++it){
146  if(it->getIsEnum()){
147  mapEnum[it->getName() + "::" + it->getName()] = it->getName();
148  size_t i(0lu);
149  std::vector<PClassAttribute> & vecAttr = it->getListAttribute();
150  for(std::vector<PClassAttribute>::iterator itAttr(vecAttr.begin()); itAttr != vecAttr.end(); ++itAttr){
151  if(itAttr->getDefaultValue() == ""){
152  itAttr->setDefaultValue(PString::toString(i));
153  }
154  ++i;
155  }
156  }
157  }
158  for(std::vector<PClassConfig>::iterator itClass(vecClassConfig.begin()); itClass != vecClassConfig.end(); ++itClass){
159  std::vector<PClassAttribute> & vecAttr = itClass->getListAttribute();
160  for(std::vector<PClassAttribute>::iterator itAttr(vecAttr.begin()); itAttr != vecAttr.end(); ++itAttr){
161  std::map<std::string, std::string>::iterator it(mapEnum.find(itAttr->getType()));
162  if(it != mapEnum.end()){
163  itAttr->setType(it->second);
164  itAttr->setIsEnum(true);
165  }
166  if(itAttr->getType() == "PPath" || itAttr->getType() == "PString"){
167  itAttr->setType("std::string");
168  }
169  }
170  }
171 }
static PString toString(const T &value)
Convert a value to a PString.
Definition: PString_impl.h:18

References PString::toString().

Referenced by project_wrapper_generator().

+ Here is the call graph for this function:
+ Here is the caller graph for this function: