To avoid a confusion of rules for the different filters, it is useful to place each filter in a module. In the example used in Linking Chains of Streaming Filters , an xml2html
function can be placed in a module along with all of its markup rules:
module export string sink function xml2html value string sink destination as using output as destination do xml-parse scan #current-input output "%c" done element "para" output "<p>%c</p>%n"
With each filter in a module, you now have a set of plug and play filters that you can quickly assemble to solve a content engineering problem:
import "xml2fo.xmd" unprefixed import "xml2html.xmd" unprefixed import "tidy-xml.xmd" unprefixed import "compress-whitespace.xmd" unprefixed process using output as xml2html into file #args[1] & xml2fo into file #args[2] & file #args[3] output tidy-xml text2xml compress-whitespace #main-input
Many OmniMark users maintain large libraries of small OmniMark programs that perform common filtering, parsing, or transformation operations on their data. Now these programs can be transformed into plug and play filtering modules that can be quickly chained together to solve complex content engineering challenges.
One of the most useful applications of this new functionality is to perform initial cleanup of source data and to perform validation of generated output data. OmniMark programmers have long been able to use a context-translate style program to validate xml or sgml data generated by find rules. But it was not possible to use the same approach to validate markup data that was itself generated from markup by a markup parse. Now, with unlimited streaming, the results of any filter, parse, or transformation can be fed through a validator, which can validate both against a schema and against any business rules that may apply. The following is an example of a module that implements a MIF validator (for FrameMaker's MIF input format):
module require function handle-mif-error value string error define string sink function validate-mif as using output as #suppress submit #current-input export string sink function mif-validator value string sink destination as using output as destination & validate-mif output #current-input
Here, the exported function mif-validator splits its input into two streams, sending one directly to output, and the other to a second sink function validate-mif. The validate-mif function sends its output to #suppress, and submits its input to find rules that implement a MIF validator. Those find rules call the supplied function handle-mif-error if any errors are found in the MIF data. This module becomes a plug and play MIF validator that can be plugged easily into the output chain of any OmniMark program that generates MIF files. Here is how the validator would be plugged into a program:
define function handle-mif-error value string error as put #error error import "xml2mif.xmd" unprefixed import "mif-validator.xmd" unprefixed supply handle-mif-error import "xml2html.xmd" unprefixed import "tidy-xml.xmd" unprefixed import "compress-whitespace.xmd" unprefixed process using output as xml2html into file #args[1] & xml2mif mif-validator file #args[2] & file #args[3] output tidy-xml text2xml compress-whitespace #main-input