Simple String Template

Version 1.1

/Home /Professional /Papers /STemplate

Contents

Introduction

Simple String Template (STemplate) is a concept originally designed for creating sets of static HTML pages with a lot of boilerplate but which will work for any text document type. It also works well for a simple CGI program. This is similar to a very simple form of the StringTemplate program.

http://www.stringtemplate.org

The explanations of purpose and design from the StringTemplate website apply in a general sense to the STemplate concept. The StringTemplate program is much too complicated for my purposes and incorporates logic processing into the template file which I believe violates its own intended purpose and certainly does not fit in with my design purposes.

The purpose of the STemplate concept is to separate the form and design of a document from the code which generates data to be included in the document. In the simplest sense, the STemplate concept uses an organized hierarchical string substitution on a "fill-in-the-blank" type of document to fill in parts of the document template form to create the final document. The template document can be edited completely separate of any need for program changes.

The document designer and the programmer only need to agree on the element names of data to be inserted. In a general sense, the document designer creates a beginning skeleton template which the programmer analyzes to create program code. It is certainly possible the designer and programmer are the same person. Long after the program is finished, the document template can be modified to adjust the form of the output.

Release Notes

VS2010 project:

STemplateA.zip

Version 1.1.0.0 released 2013-03-18:

Allow the template to come from a string. Added the methods Begin and End.

Cleaned up resources and flushed improperly terminated sections.

Version 1.0.0.0 released 2013-03-11:

STemplate Class

I wrote this concept into several C# programs before I decided I needed to write a general solution. The class does not assume any name delimiters whatsoever and assumes you know what you are doing. It will figure out whatever it can or simply do nothing. The class is very flexible in how you choose to use it.

The minimal class requirements or assumptions are that the element-names and section-names cannot be confused with each other or the rest of the document. The beginning and ending names of a section must be identical. Identically named sections cannot be nested.

Since the entire template and final output is kept in memory, the order in which you do some operations is not important. You can decide your own rules and procedures for using the class.

The class uses only a default constructor. The class has no properties. The list of methods:

// default constructor
S_Template template = new S_Template ();

// a template file to begin processing
template.Read (filename);

// a template string to begin processing
template.Begin (str);

// Replace all occurences of element-name
template.Replace ("element-name", str);

// start or repeat a new section
template.SectionBegin ("section-name");

// finishes current section and any repeats
template.SectionEnd ();

// optionally discards unused section
template.SectionRemove ("section-name");

// Return the finished template and discard resources
str = template.End ();

// Write the finished template and discard resources
template.Write (filename);

A more detailed description of the class methods is covered in the description of the analyzer program and in the source code.

STemplate Analyzer Program

The STemplateA program analyzes a template file for errors and outputs the skeleton C# code needed to fill in the template using the STemplate class. The class itself makes no restrictions for element-names and section-names. The analyzer program has the following requirements for identifying elements and sections.

A template data element is enclosed with braces ({element-name}). The case is sensitive and is only numbers and letters with a maximum of 32 characters.

A repeating or optional section is enclosed with double braces with a beginning ({{section}}) and ending ({{section}}). Ideally, each section name must be unique and should not be duplicated. Ideally, Section names must not match element names.

The only error checking currently supplied is noting unclosed sections.

This is a completely empty example skeleton:

{element1}
{{section}}
{element2}
{{section}}

Example output from the STemplateA program for the previous skeleton file:

using STemplate;

//
// Template analysis for STemplateAt.txt
// Sample code skeleton
//
S_Template template = new S_Template ();

//
// starts a new copy and can be repeated after Write
// repeating a Read or Begin without a Write or End
// loses all changes
//
template.Read ("STemplateAt.txt");

//
// Replace a main element
//
template.Replace ("{element1}", str);

//
// starts a new section and can be repeated
//
template.SectionBegin ("{{section}}");

//
// Replace a section specific element
//
template.Replace ("{element2}", str);

//
// finishes current section and any repeats
//
template.SectionEnd ();

//
// optional discards section completely when used
// instead of SectionBegin
//
template.SectionRemove ("{{section}}");

//
// writes result file erases all data
//
template.Write ("STemplateAt.txt.new");

Example template used by the STemplateA program to create analysis output:

using STemplate;

//
// Template analysis for {template_analyze_file}
// Sample code skeleton
//
S_Template template = new S_Template ();

//
// starts a new copy and can be repeated after Write
// repeating a Read or Begin without a Write or End
// loses all changes
//
template.Read ("{template_analyze_file}");
{{template_analyze_main_replace}}
//
// Replace a main element
//
template.Replace ("{template_analyze_text1}", str);
{{template_analyze_main_replace}}{{template_analyze_section}}
//
// starts a new section and can be repeated
//
template.SectionBegin ("{template_analyze_section_name}");
{{template_analyze_section_replace}}
//
// Replace a section specific element
//
template.Replace ("{template_analyze_text2}", str);
{{template_analyze_section_replace}}
//
// finishes current section and any repeats
//
template.SectionEnd ();

//
// optional discards section completely when used
// instead of SectionBegin
//
template.SectionRemove ("{template_analyze_section_name}");
{{template_analyze_section}}

//
// writes result file erases all data
//
template.Write ("{template_analyze_file}.new");

Please note that the analysis program uses the '_' character in names, which is supported by the class but not by the analysis program itself. Therefore, the analysis program cannot be used to analyze its own template file. This is also not possible because of the conflict between names matching in the analysis program template file and the names in the file being analyzed.

The {, }, {{, and }} delimiters can be easily changed in the analysis program code. Maybe a future version will make them arguments. The STemplate class already adapts automatically to any delimiter. Only the STemplateA analysis program would need to be changed.


Revised 2013-03-18