How to Move from C++ to OSM |
| Technical Article |
AbstractThis article explains to you how to move from C++ to OSM language to manage your catalog features. |
This migration is strongly recommended for several reasons
Catalogs are defined by writing a file containing OSM statements (the OSM file) and translated into CATfct catalogs with the CATfctEditorAssistant tool. The reverse is also possible: a CATfct can also be translated back to OSM.
Creation of new catalogs is not addressed in this article because it is not a migration case, see the appropriate article [2]
[Top]
If you decide to use OSM language to define your StartUp, you can delete your source creating or updating them. There are useless.
First, obtain the OSM version of the CATfct with CATfctEditorAssistant:
$ CATfctEditorAssistant -generate-osm -client-id myid myCatalog.CATfct myCatalog.osm
Notes:
CATGraphicPath
environment variable)Next, edit the newly created OSM file (myCatalog.osm) to include the changes. For further information on OSM, please refer to the Modeling Feature StartUps article [1].
$ your_favorite_editor myCatalog.osm
Finally, upgrade the CATfct with the OSM file (myCatalog.osm):
$ CATfctEditorAssistant -upgrade-catalog -client-id myid myCatalog.CATfct myCatalog.osm
Notes:
This process is similar to the edit-compile cycle that you are probably very familiar with, except that you are not starting from scratch but from the OSM that corresponds to an existing CATfct. The three steps are illustrated in Fig. 2 below:
![]() |
[Top]
In this section you will find explanation about the reasons of the requirement and how to realize them:
These catalogs can be migrated because this will allow extensions to be located at run-time without the need to open the catalog (See the AccessCatalog/AddExtension Pattern section). The OSM does not require any modification:
$ CATfctEditorAssistant -generate-osm -client-id myid myCatalog.CATfct myCatalog.osm $ CATfctEditorAssistant -upgrade-catalog -client-id myid myCatalog.CATfct myCatalog.osm
You should also add the following lines to the extension CATRsc file, which will trigger the creation of the applicative container:
ExtensionFeature.ContType="CATFeatCont"; ExtensionFeature.ContSuperType="CATFeatCont";
As a consequence, applicative containers for extensions need not be created explicitly (See the AccessCatalog/AddExtension Pattern section).
StartUps that are derivable used to be declared with CATCreatePublicSpecsInFile
which then writes this information in CATSpecs files. This information
must now be specified in OSM by adding the #inheritability(caa)
facet on the corresponding StartUps.
For example, this is how the StartUp CAAOsmAdd is made derivable:
...
feature CAAOsmAdd #startup #inheritability(caa) {
...
The migration steps for a catalog containing derivable StartUps:
$ CATfctEditorAssistant -generate-osm -client-id myid myCatalog.CATfct myCatalog.osm $ .... # edit myCatalog.osm to add #inheritability(caa) on derivable StartUps $ CATfctEditorAssistant -upgrade-catalog -client-id myid myCatalog.CATfct myCatalog.osm
You are strongly invited to upgrade any catalog in order to increase the instantiation's time. If your Startup's catalog is updated, its instantation will be faster as described in the About CATOsmSUHandler section. The OSM does not require any modification.
$ CATfctEditorAssistant -generate-osm -client-id myid myCatalog.CATfct myCatalog.osm $ CATfctEditorAssistant -upgrade-catalog -client-id myid myCatalog.CATfct myCatalog.osm
[Top]
In this section, we will explain how to migrate the run-time code that used
APIs from Table 1. It must be converted to use a new class:
CATOsmSUHandler. This new APIs will make the code simpler,
sometimes replacing up to three calls with just a single one.
| Header File | API | Purpose |
|---|---|---|
CATCatalogFactoryServices.h |
AccessCatalog |
Loads a catalog |
CATICatalog.h |
RetrieveSU |
Retrieves a StartUp |
We will now illustrate how some of the most frequent patterns of usage can be converted:
[Top]
The previous way of retrieving a StartUp was to first open a catalog
with AccessCatalog to get a CATICatalog handle on it, and then
using this handle to retrieve the StartUp with RetrieveSU:
...
HRESULT rc;
CATBaseUnknown *piContainter = NULL;
...
CATUnicodeString catalogName("CAAOsmCatalogSU.CATfct");
CATUnicodeString clientId("CAAOsmClientId");
CATICatalog *piStartUpCatalog = NULL;
rc = ::AccessCatalog(&catalogName, &clientId, piContainer, &piStartUpCatalog);
...
CATBaseUnknown *pNovelSU = NULL;
CATUnicodeString novelSUType("CAAOsmNovel");
rc = piStartUpCatalog->RetrieveSU(&pNovelSU, &novelSUType, "CATISpecObject");
...
CATISpecObject *piNovelSU = (CATISpectObject *) pNovelSU;
...
This is now done by constructing a CATOsmSUHandler object
with three parameters: the StartUp name, the client ID and the catalog name and
then calling its RetrieveSU method :
...
HRESULT rc;
CATUnicodeString catalogName("CAAOsmCatalogSU.CATfct");
CATUnicodeString clientId("CAAOsmClientId");
CATUnicodeString novelSUType("CAAOsmNovel");
CATOsmSUHandler novelSUHandler(novelSUType, clientId, catalogName);
CATISpecObject_var spNovelSU = NULL_var;
rc = novelSUHandler.RetrieveSU(spNovelSU);
...
As you can see the new code is simpler: one call instead of two.
You must note that the StartUp is now returned as a smart
pointer
to its CATISpecObject interface (previously it was a pointer to
CATBaseUnknown that had to be cast into a CATISpecObject).
Due to the fact that it is now a smart pointer, a Release is not
required (it will be Release'd once its scope ends). This also
means that
an AddRef is necessary if the smart pointer continues to be used
outside of its scope (like when returning it to a caller function for example).
[Top]
This pattern is similar to the one above, with the additional step of instantiating the StartUp retrieved:
...
HRESULT rc;
CATBaseUnknown *piContainter = NULL;
...
CATUnicodeString catalogName("CAAOsmCatalogSU.CATfct");
CATUnicodeString clientId("CAAOsmClientId");
CATICatalog *piStartUpCatalog = NULL;
rc = ::AccessCatalog(&catalogName, &clientId, piContainer, &piStartUpCatalog);
...
CATBaseUnknown *pNovelSU = NULL;
CATUnicodeString novelSUType("CAAOsmNovel");
rc = piStartUpCatalog->RetrieveSU(&pNovelSU, &novelSUType, "CATISpecObject");
...
CATISpecObject *piNovelSU = (CATISpectObject *) pNovelSU;
...
CATISpecObject *piNovelInst1 = piNovelSU->Instanciate(CATUnicodeString("CAAOsmNovel1"),
piContainer);
...
The replacement is still done with CATOsmSUHandler but with its
Instanciate method. If the handle on the StartUp is not required, the
call to RetrieveSU can be skipped.
...
HRESULT rc;
CATBaseUnknown *piContainter = NULL;
...
CATUnicodeString catalogName("CAAOsmCatalogSU.CATfct");
CATUnicodeString clientId("CAAOsmClientId");
CATUnicodeString novelSUType("CAAOsmNovel");
CATOsmSUHandler novelSUHandler(novelSUType, clientId, catalogName);
CATISpecObject_var spNovelInst = NULL_var;
rc = novelSUHandler.Instanciate(spNovelInst, piContainer, CATUnicodeString("CAAOsmNovel1"));
...
Since the instance is returned as a smart pointer to its CATISpecObject,
the same life-cycle rule applies as with the StartUp retrieved via
RetrieveSU.
The last argument of the CATOsmSUHandler class, the name of the catalog of the feature to instantiate, can be useless if the catalog has been upgrated since V5R18SP2. If the catalog has been migrated, that you refer or not the catalog name, the instantiation will be faster.
... HRESULT rc; CATBaseUnknown *piContainter = NULL; ...CATUnicodeString catalogName("CAAOsmCatalogSU.CATfct");// this line is useless CATUnicodeString clientId("CAAOsmClientId"); CATUnicodeString novelSUType("CAAOsmNovel"); CATOsmSUHandler novelSUHandler(novelSUType, clientId, catalogName); ...
[Top]
A catalog containing Feature Extensions is opened via AccessCatalog with an applicative container. Another
feature can then add one of these extensions by calling the AddExtension
method of its CATIOsmExtendable interface. Added extensions
are created in the applicative container.
...
HRESULT rc;
CATIOsmExtendable *piExtendable = NULL;
...
//
// Applicative container creation
//
CATBaseUnknown *piContainter = NULL;
...
CATUnicodeString catalogName("CAAOsmExt2Catalog.CATfct");
CATUnicodeString clientId("CAAOsmClientId1");
CATICatalog *piExtensionsCatalog = NULL;
rc = ::AccessCatalog(&catalogName, &clientId, piContainer, &piExtensionsCatalog);
...
rc = piExtentable->AddExtension("CAAOsmChildrensNovel");
...
With OSM, it is no longer necessary to open the extensions
catalog. As the catalog have been migrated the Feature Modeler will be able to locate the extension by its name.
Both the AccessCatalog call and the applicative container creation
code are discarded:
...
HRESULT rc;
CATIOsmExtendable *piExtendable = NULL;
...
rc = piExtentable->AddExtension("CAAOsmChildrensNovel");
...
Please note that the container creation code is suppressed because the following lines are added in the CATRsc file of the Feature Extension:
ExtensionFeature.ContType="CATFeatCont"; ExtensionFeature.ContSuperType="CATFeatCont";
In summary, the AddExtension method of
CATIOsmExtendable no longer requires the catalog to be opened, provided it
has been migrated. The container creation code can also
be removed if the container type and supertype are defined in
the CATRsc file.
[Top]
For your reference, Table 2 lists all the APIs that are useless as the result in the introduction of OSM:
| Header File | API | Purpose | Usage Patterns |
|---|---|---|---|
CATCatalogFactoryServices.h |
AccessCatalog |
Loads a catalog | AccessCatalog/RetrieveSU AccessCatalog/RetrieveSU/Instanciate AccessCatalog/AddExtension |
CreateCatalog |
Creates a catalog | ||
SaveCatalog |
Saves a catalog | ||
UpgradeCatalog |
Loads a catalog to be updated | ||
CATICatalog.h |
CreateSUInCatalog |
Creates a StartUp | |
OpenPrereqCatalog |
Opens a catalog | ||
RetrieveSU |
Retrieves a StartUp | AccessCatalog/RetrieveSU | |
SetClientId |
Assigns a client ID | ||
CATIOsmExtensionFactory.h |
CreateExtension |
Creates an Extension StartUp | |
CATOsmSUFactory.h |
CATOsmSUFactory |
Creates a StartUp | |
CATPublicSpecsDef.h |
|||
CATPublicSpecsFileServices.h |
CATCreatePublicSpecsInFile |
Declare public and derivable StartUps | |
CATAddPublicAttributeToFile |
Declare public attributes |
[Top]
This article shows how OSM impacts your existing catalogs and run-time code:
AccessCatalog/RetrieveSU/Instanciate
pattern should be converted to the new and simpler
CATOsmSUHandler/RetrieveSU and/or CATOsmSUHandler/Instantiate.[Top]
| [1] | Modeling Feature StartUps |
| [2] | Managing StartUp Catalogs |
[Top]
| Version: 1 [Oct 2009] | Document created |
[Top]