Writing your own synopsis script
Prev | Chapter 3. Scripting And Extending Synopsis | Next

## Writing your own synopsis script

The synopsis framework provides a function `process` that lets you declare and expose processors as commands so they can be used per command line:

    #
    # Copyright (C) 2006 Stefan Seefeld
    # All rights reserved.
    # Licensed to the public under the terms of the GNU LGPL (>= 2),
    # see the file COPYING for details.
    #

    from Synopsis.process import process
    from Synopsis.Processor import Processor, Parameter, Composite
    from Synopsis.Parsers import Cxx
    from Synopsis.Parsers import Python
    from Synopsis.Processors import Linker
    from Synopsis.Processors import Comments
    from Synopsis.Formatters import HTML
    from Synopsis.Formatters import Dot
    from Synopsis.Formatters import Dump

    class Joker(Processor):

        parameter = Parameter(':-)', 'a friendly parameter')

        def process(self, ir, **keywords):
            # override default parameter values
            self.set_parameters(keywords)
            # merge in IR from 'input' parameter if given
            self.ir = self.merge_input(ir)

            print 'this processor is harmless...', self.parameter

            # write to output (if given) and return IR
            return self.output_and_return_ir()

    cxx = Cxx.Parser(base_path='../src')

    ss = Comments.Translator(filter = Comments.SSFilter(),
                             processor = Comments.Grouper())
    ssd_prev = Comments.Translator(filter = Comments.SSDFilter(),
                                   processor = Composite(Comments.Previous(),
                                                         Comments.Grouper()))
    javadoc = Comments.Translator(markup='javadoc',
                                  filter = Comments.JavaFilter(),
                                  processor = Comments.Grouper())
    rst = Comments.Translator(markup='rst',
                              filter = Comments.SSDFilter(),
                              processor = Comments.Grouper())

    process(cxx_ss = Composite(cxx, ss),
            cxx_ssd_prev = Composite(cxx, ssd_prev),
            cxx_javadoc = Composite(cxx, javadoc),
            cxx_rst = Composite(cxx, rst),
            link = Linker(),
            html = HTML.Formatter(),
            dot = Dot.Formatter(),
            joker = Joker(parameter = '(-;'))

With such a script `synopsis.py` it is possible to call

    python synopsis.py cxx_ssd --output=Bezier.syn Bezier.h

to do the same as in Chapter 2, Using the synopsis tool, but with much more flexibility. Let's have a closer look at how this script works:

### Importing all desired processors

As every conventional python script, the first thing to do is to pull in all the definitions that are used later on, in our case the definition of the `process` function, together with a number of predefined processors.

### Composing new processors

As outlined in the section called “Composing A Pipeline”, processors can be composed into pipelines, which are themselfs new (composite) processors. Synopsis provides a Composite type for convenient pipeline construction. Its constructor takes a list of processors that the process method will iterate over.

### Defining New Processors

New processors can be defined by deriving from Processor or any of its subclasses. As outlined in the section called “The Processor class”, it has only to respect the semantics of the `process` method.

### Exposing The Commands

With all these new processrs defined, they need to be made accessible to be called per command line. That is done with the `process` function. It sets up a dictionary of named processors, with which the script can be invoked as

    python synopsis.py joker

which will invoke the joker's `process` method with any argument that was provided passed as a named value (keyword).

Prev | Up | Next
Composing A Pipeline | Home | Chapter 4. Processor Design