Giovanni's logo
Dynamic MS WORD documents
this means Version 2
index
M
power search
blue line

1-About it 2-How to build a document template 3-How to write the user program

1-About it

Since May 2020 CGIDEV2 provides a command - UPDWORDX - for generating customized MS WORD documents starting from a template document.
This support is limited to MS Office 2007 documents, the ones with extension .docx. Documents with extension .doc are not supported.
Command CGIDEV2/UPDWORDX operates in a way like the one used in CGIDEV2 to create dynamic web pages from an external HTML template.
It loads into memory a given WORD template containing output variables, then it calls an exit (CGI-like) user program responsible for updating the output variables. On return from the user program, it calls the WrtHtmlToStmf() procedure to create a stream file containing the new customized WORD document.
The nice side of this command is that the user program is just required to perform as many UpdHtmlVar() calls as many output variables are to be filled in.
The uneasy side of the tool, however, is that setting output variables in the template WORD document is very critical and must be thoroughly checked out.

Command CGIDEV2/UPDWORDX looks as follow:

                         Update a MS WORD document (UPDDOCX)                    
                                                                                
 Type choices, press Enter.                                                     
                                                                                
 Input document stream file . . . INPSTMF  ____________________________________________
______                                                                          
 Output document stream file  . . OUTSTMF  ____________________________________________
______                                                                          
 User program . . . . . . . . . . USRPGM   __________    Name                          
   Library  . . . . . . . . . . .            *LIBL_____  Name, *LIBL, *CURLIB
Figure 1 - Command UPDDOCX
  • Input document stream file - (INPSTMF) - The IFS stream file of the template MS WORD document (see "How to build a document template" later in this page)
  • Output document stream file - (OUTSTMF) - The IFS stream file of the customized word document. If this file already exists, it is replaced.
  • User program - (USRPGM) - The user program performing the document update through a number calls to CGIDEV2 UpdHtmlVar() procedure.
    Example: UpdHtmlVar('custname':'John Doe')

2-How to build a document template

A 2007 MS WORD document (extension ".docx") is a set of 11 files distributed in 4 directories and zipped to make up the document. To unzip a MS WORD document we
  • copy the document to clipboard
  • paste into a folder
  • rename it by replacing extension docx with extension zip
  • unzip it.
The internal structure of the WORD document displays as follow:
document/_rels/.rels
document/docProps/app.xml
document/docProps/core.xml
document/words/_rels/document.xml.rels
document/words/theme/theme1.xml
document/words/document.xml
document/words/fontTable.xml
document/words/settings.xml
document/words/styles.xml
document/words/webSettings.xml
document/[Content_Types].xml

The file containing the document text strings is document/words/document.xml. This is the one that will contain the template words and the "output variables".
In this file, the text of the document is splitted in many little strings anclosed in XML <tag>'s.

Now, the "output variables" that we need to define in a document template are unique labels (to be mentioned in the RPG program), enclosed in specific start and end delimiters. Example: /%custname%/.
We absolutely need these "output variable" strings be uncoded as a whole, example
/%custname%/%/</w:t>
instead of being splitted into XML pieces such as
<w:t>/%</w:t> ... ... ... <w:t>custname%/</w:t> .
If that splitting takes place, then the RPG function UpdHtmlVar('custname':'John Doe') would not reach its target, which would then filled in with the string *Missing Data*.

To avoid unwanted splitting we proceed as follow:

  1. open a new WORD document
  2. Type in every other string, except the body of the document. If needed, assign font-family, font-size and color to these strings.
  3. Position the cursor in the point of the document where the body would start and assign font font-family, font-size and color for the next text
  4. Get out of this document and use NotePad to open a text file
  5. Type the document body as plain text, including the /%label%/'s representing the output variables
  6. Copy this document body to the clipboard
  7. Go back to the WORD document and paste the clipboard exactly where you left the cursor
  8. Don't do anything further, save the document while keeping fingers crossed.
That should work, but you've better to make sure before using it as a template. The following check will save you a lot of wasted time:
  1. Unzip that WORD document template (as described above)
  2. Open file document/words/document.xml using a XML browse tool (I.E. is good for that).
  3. Search for /%
  4. Check out in this way all the "output variables". If all of them are unsplitted, you are done.

The following is an example of a WORD document template (file /cgidev/word/sampleDoc.docx):

Figure 2 - Sample WORD document template

3-How to write the user program

That is really simple. Just code the UpdHtmlVar() instructions needed to fill in the document template "output variables".
The following is what was done with our sample program to customize the template in Figure 2:
  *=========================================================================          
  * Example of user program for command UPDDOCX                                       
  *                                                                                   
  * CRTBNDRPG PGM(CGIDEV2/UPDSAMPDOC) SRCFILE(CGIDEV2/QRPGLESRC)                      
  *           DFTACTGRP(*NO) ACTGRP(*CALLER) DBGVIEW(*SOURCE)                         
  *                                                                                   
  * Execution example:                                                                
  * UPDDOCX INPSTMF('/cgidev/word/sampleDoc.docx')                                    
  *         OUTSTMF('/tmp/sampleDocX.docx')                                           
  *         USRPGM(CGIDEV2/UPDSAMPDOC)                                                
  *                                                                                   
  *=========================================================================          
  /copy cgidev2/qrpglesrc,hspecs                                                      
  /copy cgidev2/qrpglesrc,hspecsbnd                                                   
  /copy cgidev2/qrpglesrc,prototypeb                                                  
  /copy cgidev2/qrpglesrc,usec                                                        
                                                                                      
  /free                                                                               
                                                                                   
     updhtmlvar('name':'John Doe');                                                   
     updhtmlvar('ordernumber':'CQK0964752');                                          
     updhtmlvar('numberdays':'37');                                                   
                                                                                    
     return;                                                                          
                                                                       
Figure 3 - Sample user program

By running command:

UPDDOCX INPSTMF('/cgidev/word/sampleDoc.docx')
            OUTSTMF('/tmp/sampleDocX.docx')
            USRPGM(CGIDEV2/UPDSAMPDOC)
Figure 3 - Sample UPDDOCX command

If you have a CGIDEV2 version dated at least May 1, 2020 you may run the above command for your own fun.
It provides the following MS FORM document (file /tmp/sampleDocX.docx)):
Figure 4 - Sample customized WORD document





References
  1. Draft of Scott Klement's WORD article