How do the Mogenerator parameters work, which can I send via Xcode? [closed] - documentation

Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 5 years ago.
Improve this question
The help for Mogenerator is very minimal. What do all the parameters do?

Parameters that work both via the command line utility and Xcode:
--base-class: The name af the base class which the "private class" (e.g. _MyObject.h) will inherit from. This will also add an import in the form of #import "MyManagedObject.h" to the same .h file. Tip: if the class you want to inherit from is located in a library, the default import statement won't work. As a workaround, you could have an extra level of inheritance for each project you create and have that class inherit from the library on (e.g. set the base class to MyProjectManagedObject which you create manually and inherit from MyLibManagedObject).
--template-path: The path to where the 4 .motemplate files are located. When this is not provided, it will look at all the "app support directories" (e.g. "/Library/Application Support/mogenerator/").
--template-group: A subdirectory name underneath the template-path directory to use.
--template-var arc=true: Required for the generated files to compile while using ARC.
--output-dir: The output directory for all generated files.
--machine-dir: The directory where the _<class>.h and _<class>.m will be output to. If --output-dir is also defined, this parameter takes precedence.
--human-dir: The directory where the <class>.h and <class>.m will be output to. If --output-dir is also defined, this parameter takes precedence.
--includem: the full path to a file that will include all the #import for all the .h files that are created. This file does not need to exist (i.e. it will be created for you if it doesn't). This file, will not be included in the project automatically for you. You must include it manually by dragging it into the Groups & Files list of your project.
Using relative paths in Xcode for any of the above arguments won't work since the working directory is set to one of the root directories of the system (e.g. Applications, Developer, Library, or System). (I haven't had enough time to figure out which one of these it is exactly.)
Parameters that cannot be used in Xcode:
--model: The path to the .xcdatamodel file, cannot be set in Xcode.
--list-source-files
--orphaned
--versioned
--help
Running and sending parameters to xmod via Xcode:
(Update: I haven't tried this on Xcode 4, only Xcode 3. For Xcode 4, you can add mogenerator as a build phase instead of following the following steps.)
Go to the info page of the .xcdatamodel file.
Choose the Comments tab.
Add xmod to the comments field, on its own line.
Every time you save the model, it will regenerate the machine files for you.
To send parameters, they must be on their own line(s):
This works:
xmod
--base-class CLASS
--template-path PATH
And even this works:
xmod
--base-class CLASS --template-path PATH
But, this won't work:
xmod --base-class CLASS --template-path PATH
Note: You must close the Info window for the settings to take effect.

As of XCode 4, the Info window is no longer available, so don't be concerned if you can't set it up as answered above.
Use John Blanco's guide to set up a scripting target which allows you to pass command-line arguments directly to mogenerator. Note that you might have to tweak the paths in his example slightly... toss a pwd in the script and check the paths against the script's working directory if it doesn't run for you right away.
For a list of available command-line arguments, run mogenerator --help in the Terminal. AFAICT, all of them work from the scripting step.
See this answer for another way to invoke mogenerator via a "pre-action" if you want to automatically rebuild your machine files with every build. There's also a good tip on putting a mogenerator script into your VCS.

Here is the output from --help as of version 1.27
mogenerator: Usage [OPTIONS] <argument> [...]
-m, --model MODEL Path to model
-C, --configuration CONFIG Only consider entities included in the named configuration
--base-class CLASS Custom base class
--base-class-import TEXT Imports base class as #import TEXT
--base-class-force CLASS Same as --base-class except will force all entities to have the specified base class. Even if a super entity exists
--includem FILE Generate aggregate include file for .m files for both human and machine generated source files
--includeh FILE Generate aggregate include file for .h files for human generated source files only
--template-path PATH Path to templates (absolute or relative to model path)
--template-group NAME Name of template group
--template-var KEY=VALUE A key-value pair to pass to the template file. There can be many of these.
-O, --output-dir DIR Output directory
-M, --machine-dir DIR Output directory for machine files
-H, --human-dir DIR Output directory for human files
--list-source-files Only list model-related source files
--orphaned Only list files whose entities no longer exist
--version Display version and exit
-h, --help Display this help and exit
Implements generation gap codegen pattern for Core Data.
Inspired by eogenerator.

Also, maybe will be helpful.
For determining which params can be used for
--template-var KEY=VALUE
open *.motemplate file, and find string like "TemplateVar." after point you will see parameter name and will able to understand what it do.
This params has built-in template
--template-var arc=true
--template-var frc=true
--template-var modules=true

Related

Include from upper layer of files

I've got main project structure in 1 folder, and units tests closed in another folder(2 different meson instances). In unit tests i need to include one file from main project(element to be tested). I dont want to specify relative path as i want to be portable between other programmers.
How can i instruct meson to first go back from current folder and then look through application files if there is file i'm looking for? I want to make it that way so any change in code can be tested right away without any copying or modifications.
C:\Users\User1\Project\application
C:\Users\User1\Project\unittests
I need to be able to see files from application while beeing currently on unittests
Declare project dependency at top level meson.build like
project_dep = declare_dependency(include_directories: inc_dir, sources: srcs, dependencies:[...])
Make sure that your main is not in the sources. In test level meson.build
include project_dep like this:
unit_tests_exec = executable('UnitTests', gtest_srcs,
dependencies :[gtest_dep, gmock_dep, project_dep])
You can check how I organized project using meson for Tdd session here:
https://github.com/elvisoric/tdd_session

Code generator generating its own CMake files and targets

Let's assume I have a script that generates a set of source files forming a target I want to link against in a CMakeLists.txt. If the file names are known to the latter then the usual add_custom_target() and add_custom_command() commands will make it possible to use the generated files as target sources.
Let's assume, though, that only the generator script knows the file names and locations. How can a target library be generated so that the parent CMakeLists.txt can link against it without its knowing the actual file names?
Note that the dependency topic isn't in this question's scope as the script knows itself when to regenerate or not. It's not the finest use of CMake, but it's sufficient in this use case.
Idea #1
The script also generates a generated.cmake file included by the parent one using include(generated.cmake). Problem: CMake doesn't find generated.cmake as it isn't existing at configuration time.
Idea #2
Similar to idea #1, but the script is called with the execute_process() so that generated.cmake is present at configuration time. Problem: The script is not called anymore at subsequent builds, thus ignoring possible changes to its input.
Idea #3
The script passes back a list of targets and files that is somehow considered by the parent CMakeLists.txt. So far I couldn't find a way to do so.
The solution I came with is eventually a mixture of all three ideas.
Solution to idea #1's problem
execute_process() actually ensures that generated_targets.cmake is present at configure time.
Solution to idea #2's and #3's problems
As stated in this answer to "Add dependency to the CMake-generated build-system itself", the CMAKE_CONFIGURE_DEPENDS directory property can be edited to add files whose touching re-triggers the configure step.
The key success factor is that this property can be set after the initial execute_process() call so that the script can identify and list its input dependencies (in an output file) that are then added to CMAKE_CONFIGURE_DEPENDS, hence also solving the input dependency problem.
Resulting pseudo code
# The script generates:
# - <output_dir>/cmake/input_files
# - <output_dir>/cmake/generated_targets.cmake
execute_process(
COMMAND myScript
--output-dir ${CMAKE_CURRENT_BINARY_DIR}/generated
)
# Mark the input files as configure step dependencies so that the execute_process
# commands are retriggered on input file change.
file(STRINGS ${CMAKE_CURRENT_BINARY_DIR}/generated/cmake/input_files _input_files)
set_property(
DIRECTORY APPEND PROPERTY CMAKE_CONFIGURE_DEPENDS
${_input_files}
)
# Add the generated CMake targets.
include(${CMAKE_CURRENT_BINARY_DIR}/generated/cmake/generated_targets.cmake)

Can we make Spoon's output follow the same directory path as the original?

For now, Spoon's directory structure of output will follow the package path written in *.java file. In fact, there are many other files even *.java files, whose real file paths are different from package paths.
So, my Spoon's output folder was disordered.
In short the answer for this question is: no.
Spoon uses standard Java organization to process output files, meaning: each Java file is output in its package hierarchy as it should be done for source files (see: https://docs.oracle.com/javase/tutorial/java/package/managingfiles.html).
However if your problem is related to file created because of inner classes: you could solve it using the following option:
[--output-type ]
States how to print the processed source code:
nooutput|classes|compilationunits (default: classes)
with value "compilationunits".
Finally if it's really an issue for you, don't hesitate to propose a new feature through a pull request on the Github repository!

Refer to higher directory in #import statement Objective C

I am using Mogenerator to automatically create subclasses for my Entities in Core Data.
I had acted upon a recommendation I read to store the files in subdirectories within my project (since I will have many). Used the following arguments when running the script:
cd Project
mogenerator --template-var arc=true -m Project.xcdatamodeld/Project.xcdatamodel/ - M CoreData/Machine/ -H CoreData/Human/
I added these to my project as a folder reference, as the script may add files to match my model and I don't want to have to add them to my project manually.
The directory structure for both the created files are like this:
Project/CoreData/Human/Entity.h
Project/CoreData/Machine/_Entity.h
I need to import "_Entity.h" inside of "Entity.h". The problem is, it's not in the same or lower directory and I don't know how to do a relative reference to a higher directory. I'm forced to use an absolute directory all the way from /Users.. which works, but it includes my username etc. so I'd rather not.
Question: How can I import _Entity.h from Entity.h using relative reference?
Bonus question: Is it possible to have mogenerator automatically use the proper reference? I mean, I'm clearly telling it where to put both files and it's doing it, but still only puts the following in Entity.h:
#import "_Entity.h"
...and I get an error.
Thanks in advance,
Pat
".." (without the quotes) represents the directory that's "one level higher". Use this to go to "CoreData", then to "Machine".
Try this:
#import "../Machine/_Entity.h"
I'm not sure if it'll work, but it's worth a try!

.h generated from .h.in?

There are struct definitions in the .h file that my library creates after I build it.. but I cannot find these in the corresponding .h.in. Can somebody tell me how all this works and where it gets the extra info from?
To be specific: I am building pth, the userspace threading library. It has pth_p.h.in, which doesn't contain the struct definition I am looking for, yet when I build the library, a pth_p.h appears and it has the definition I need.
In fact, I have searched every single file in the library before it is built and cannot find where it is generating the struct definition.
Pth uses GNU Autoconf, Automake, and Libtool. By running ./configure you'll be running a shell script which eventually runs m4 to detect the presence of a whole bunch of different system attributes and make changes to a number of files.
It looks like it boils down to ./configure generating Makefile from Makefile.in and then running something via make that triggers the shtool subcommand scpp:
pth_p.h: $(S)pth_p.h.in
$(SHTOOL) scpp -o pth_p.h -t $(S)pth_p.h.in -Dcpp -Cintern -M '==#==' $(HSRCS)
Obscure link, but here's an shtool-scpp manpage, which describes it as:
This command is an additional ANSI C
source file pre-processor for sharing
cpp(1) code segments, internal
variables and internal functions. The
intention for this comes from writing
libraries in ANSI C. Here a common
shared internal header file is usually
used for sharing information between
the library source files.
The operation is to parse special
constructs in files, generate a few
things out of these constructs and
insert them at position mark in tfile
by writing the output to ofile.
Additionally the files are never
touched or modified. Instead the
constructs are removed later by the
cpp(1) phase of the build process. The
only prerequisite is that every file
has a ``"#include ""ofile"""'' at the
top.
.h.in is probably processed within a configure (generated from configure.ac) script, look out for
AC_CONFIG_FILES([thatfile.h])
It replaces variables of the form #VAR# in the .in file with their values.
Edit: Just noticed if I'm right you should retag your question