How to Write a Change Management System (CMS) Export Plug-In


A CMS export plug-in externalizes the information about changes made to a design and emits it in a format that can be consumed by a corresponding import plug-in. An export plug-in

The sections that follow provide a general guide for writing an export plug-in.

For an overview of the CMS system, refer to Change Management System (CMS) in the Programmers Guide.

How Database Changes Are Exported by Applications

An application exports information about tracked design changes through CMS using the public oaChangeMgr class and an export plug-in. All interactions between CMS and the plug-in are managed by the oaChangeMgr singleton public class.

The exported changes can then be imported by a different application with the appropriate import plug-in.

Refer to Exporting Changes in the Change Management System (CMS) document for an overview of the sequence of interactions between the end user, the application, the oaChangeMgr instance, and the tracking plug-in.

Creating a CMS Export Plug-In

Before starting this project, you might want to read How to Write a Plug-In, which is a more generic document describing the general concept of plug-ins and how they work.

In order to create an CMS export plug-in, you need to:

OpenAccess provides infrastructure support for implementing a CMS plug-in. The functions in oaCommon.h provide basic plug-in support such as the ability to get the globally unique identifier (Guid) and manage the plug-in lifetime. Functions in oaCM.h provide support for all CMS objects.

Note that a sample export plug-in is provided at <install_dir>/oa/examples/cms/src/export.

To create a basic export plug-in:

  1. Create a factory for your export plug-in and construct a static member of it:

    const oa::oaString myExportPlugIn::plugInName("myExportPlugIn");
    oaCommon::Factory<myExportPlugIn> myTrackingPlugIn::factory(myExportPlugIn::getPlugInName());


  2. Define the entry point function getClassObject(). Use:

    extern "C" long
    getClassObject(const char *classID,
                   const Guid &interfaceID,
                   void       **ptr);


  3. Implement the entry point function as:

    long
    getClassObject(const char           *classID,
                   const oaCommon::Guid &interfaceID,
                   void                 **ptr)
    {
         return oaCommon::FactoryBase::getClassObject(classID, interfaceID, ptr);
    }


  4. Define a new class inherited from IExport, and implement the required functions. For example:

    class myCMExport : public oaCommon::PlugInBase <oaPlugIn::IExport> {
    public:
       
                                                   myCMExport();
        virtual void                                   init();
       
        virtual void                                   getProtocols(oa::oaCMProtocolArray &out) const;
        virtual void                                   setProtocol(const oa::oaCMProtocol &in);
       
        virtual void                                   exportFull(oa::oaChangeSetBase *changeSet);
        virtual void                                   exportIncr(oa::oaChangeSetBase *changeSet);
       
        virtual void                                   discardChangeSet(oa::oaChangeSetBase *in);

        static oaCommon::IFactory                      *getFactory();
        static const oa::oaString                      &getPlugInName();

    private:
         oaCMProtocolArray                             m_protocols;
         oaCMProtocol                                  m_protocol;
         static const oa::oaString                     plugInName;
         static oaCommon::Factory <oaCMExportSample>   factory;
    };


    Refer to Sample Interface Implementations for details about these interfaces and how they might be implemented.

  5. Optionally implement an ICompatibility::validate function to verify whether or not the version of OpenAccess is compatible with the plug-in. The validate() function should check the OpenAccess API version and either throw an exception with a description of the requirements or simply return false. REVIEWERS: Need to describe how an app might check if an interface has an ICompatibility component and if so, how to use it.
    virtual bool                validate()
  6. Write the plug-in registration file myExportPlugIn.plg. Use:
        <?xml version="1.0" encoding="utf-8" ?>      
    <plugIn lib="myExportPlugIn"/>
    Note: The registration file can be installed in $(OA_HOME)/data/plugins when the plug-in shared library is installed. Alternatively, the OA_PLUGIN_PATH environment variable can be used to reference a .plg file outside of $(OA_HOME)/data/plugins. Refer to Writing the Plug-In Registration File in How to Write a Plug-In for more information.

Sample Interface Implementations

The following are sample implementations of the interface functions shown in Step 4 above.

init( )

This function initializes the plug-in and establishes the protocol. It could be implemented as:

void
myCMExport::init()
{
    oaCMAttrArray   fixed;
    oaCMAttrArray   mod;

    fixed.append(oaCMAttr("Format", "File"));
    mod.append(oaCMAttr("FileName"));

    m_protocols.append(oaCMProtocol("myExport", "myCMExport", fixed, mod));
}

getProtocols( )

This function returns the protocol array for the plug-in and could be implemented as:
void
myCMExport::getProtocols(oa::oaCMProtocolArray &out) const
{
out = m_protocols;
}

setProtocol( )

This function sets the protocols of this plug-in and could be implemented as:

void
myCMExport::setProtocol(const oa::oaCMProtocol &in)
{
    if (!m_protocols.validate(in)) {
        throw oaError(oacCMInvalidPlugInProtocol);
    }

    m_protocol = in;
}
 

exportFull( ) and ExportInc( )

void
myCMExport::exportFull(oa::oaChangeSetBase *changeSet)
{
    changeSet->setExported();
}

void
myCMExport::exportIncr(oa::oaChangeSetBase *changeSet)
{
    if (!changeSet->isActive()) {
        changeSet->setExported();
    }
}

discardChangeSet( )

void
myCMExport::discardChangeSet(oa::oaChangeSetBase *in)
{
}

getFactory( )

This function returns the factory interface for this plug-in and could be implemented as:

inline oaPlugIn::IFactory*
myCMExport::getFactory()
{
    return &factory;
}

getPlugInName( )

This function returns the string name of the plug-in and could be implemented as:

inline const oa::oaString&
myCMExport::getPlugInName()
{
    return plugInName;
}

Return to top of page

Return to Programmers Guide topics


Copyright © 2001-2010 Cadence Design Systems, Inc.
All rights reserved.