to compile youpee you need the gcc compiler, freely available under linux. you can work under windows using gcc for windows : cygwin
creat a youpee folder and copy the youpee.tgz inside
> mkdir youpee
> cp youpee.tgz youpee
> cd youpee
> tar xvzf youpee.tgz

unpack and compile the pcre package:
> tar xvzf pcre-4.3.tar.gz
> cd pcre-4.3
> configure
> make

and run the make command in the youpee folder
> cd ..
> make
you will have a binary file for youpee

command line

Usage: youpee -F | [OPTION] [-f] 
          pre-process a file
            -?           this help
            -h           this help
            -v           return the version number
            -F           run as a script shell
            -r           display file dependencies on stderr
            -t template  template file
            -I include   include files before the processed file ( may be multiple )
            -P include   include files after the processed file ( may be multiple )
            -D "in out"  create a define  ( may be multiple )
            -o           destination file ( stdout is default )

youpee -o ouput -f input : process the file input and store the result in output

youpee -I include -f input : process the file include then the file input and write the result on stdout

youpee -P include -P include2 -f input : process the file input then the file include and inclued2 and write the result on stdout

youpee -D "toto \"titi is hungry\"" -f input : process the file input and replace each instance of toto by titi is hungry


You can set the first line of a file with :
#!_path_/youpee.exe -F
the file can be set as executable and all the lines beginning with #! will be ignored

environment variable

if PATH variables are not set, the default path is "." (the current directory)


<#NTARGET_ROOTFILENAME/> ( if the name ends with a number, increment it. it target is toto0, then NTARGET_ROOTFILENAME is toto1 )
<#ORG_SHORTFILENAME/>   ( filename without the path )
<#CUR_PATH/> ( the path of the current processed file )
<#LANG/> ( the value of the LANG environment variable )
<#YOUPEE/> ( Youhp3 v )
if the following strings are in the processed files, they will be replaced.

the ROOT variables does not contain the extension filename sample
the command is : youpee -t tmp_dir/ -o build/file.htm -f src/file.src

<#ORG_ROOTFILENAME/>        : src/file
<#TARGET_ROOTFILENAME/>     : build/file
<#TEMPLATE_ROOTFILENAME/>   : tmp_dir/template
<#ORG_SHORTFILENAME/>       : file.src
<#ORG_PATH/>                : src
<#ORG_FILENAME/>            : src/file.src
<#TARGET_FILENAME/>         : build/file.htm
<#TEMPLATE_FILENAME/>       : tmp_dir/
<#CUR_PATH/>                : tmp_dir while processing and src while processing file.src


youpee include a set of commands, simple commands can be placed whereever you want on a line and complex command which must be alone on the text line. you can place space before the complex command. so you can use indentation with the <#..> tag of youhp3.

you can use \ at the end of a line to continue a line on the next one

html character escapement

é è ê à ... are replaced automatically by &eacute; ... to disable this feature, place <#disable_htmlencode>, </#disable_htmlencode> around the section



<#define _DEF_ _"chaine de char"_ />
each following instance of _DEF_ will be replaced by _"chaine de char"_ 
the space is required after the value

<#undef  _DEF_ >
undefine _DEF_, so following instance of _DEF_ will not be replaced

builtin variables

you can define your own builtin variables inside a program
<#bindefine _org_ res >
then <#_org_> is replaced by res. in the youpee line process, the builtin variables are replaced before standard define.


<#include _filename_ [section] />
include the file named _filename_ 
we use the paths specified the environment variable INCLUDEPATH
and try to find first $LANG_filename_, so if you export did:
export INCLUDEPATH=.;..
export LANG=fr
youpee will try to include the first file it find in this list:
./fr_filename_  ,  ./_filename_  ,  ../fr_filename_  ,  ../_filename_

if the filename start with !, the ! is removed from the name and the

the content of that files is parsed again. mind that at the moment
infinite loop are not handled. so it is not recommended to include
in file f1 a file f2 which include f1.

you can split a file using the section tag
the optional parameter section let you specify that you only want the
section _filename_ to be included. the section is define as the lines between
<#section> and </#section>

so suppose that you the file f1 is :

this is the section S1


the following statement :
<#include f1 s1 />
will only include :
this is the section S1


<#includedefine _filename_ />

the filename must have the following organisation

@@ sec1
tag1 val1
t2 v2

@@ hello
t3 v1
t2 val2

this will define the following builtin defines
<#sec1.tag1/> when used will be replaced by val1
<#hello.t3/> when used will be replaced by v1


<#if FILEEXISTS _filename_ >
... instruction or html ('then' section)
... ( else section )
the follwing test are available : for the tests GT,LT,GE,LE, EQUAL, !EQUAL, if youpee detects that the arguments are both integer it does an integer comparisons instead of string compar.


<#script shell_interpreter >
script for the interpreter
create a file named .youpee.# which contains the script, then run shell_interpreter .youpee.#, and parse the output of the shell. the # is replace by a number. You can have 99 levels of script. for exemple :
<#script /bin/bash >
for i in $(ls *.on); do
echo "<#include $i section1 />"

we wrote a script in bash, and in result youpee will include the section
section1 from all the files with the on suffix


<#process> ... youpee code </#process> the youpee code is processed and the result is processed to. it something like an 'eval' in a script language. and it is equivalent to :
<#script "youpee.exe" "-f" "<#scriptname/>" >
... youpee code


<#call _prog_ param1 param2 ... />

call the _prog_ program with param1 ... in the command line
the result is parsed 
CODEPATH is used to find _prog_
LANG prefix is tryed


<#post _prog_ >
.. text ..

call _prog_ and send the text to its stdin
parsed its stdout
CODEPATH and LANG are used to find _prog_

macro / callmacro

<#macro toto >
.. text ..
.. you can use <#1/> <#2/> ...

define a text macro

<#callmacro toto un "deux trois" ... />
will use the text defined in the macro section
and replace <#1/> by un
<#2/> by 'deux trois' ...

the result is parsed

as a shortcut you can use : <#macro_name
( <#toto ... /> in the previous example )

loop with list

<#loop it in 1 two three .. >
print <#it/>

<#it/> takes the value in the list

loop with integer range

<#loop it between 3 10 2 >

<#it/> takes all the integer value between 3 and 10 ( included )
the value is incremented by 2 at each loop 
( this parameter is optional, default value = 1 )

loop with file

<#loop it infile _filename_ >

<#it/> takes all the lines in the file ( includepath is used to find it)

loop with field access in file

<#loop it incvs _filename_ >

same as infile but you can use <#it.n/>, where n is an integer, to get
the n th field. so if one line in the file is:
one 2 three four
and you use <#it.3/> , it will be replaced by three
so incvs can always be used even if you don't need to access specific field in the line. by the way, infile will save time processing and memory.

loop with section

<#loop it insection _filename_ >

the section file is like that :
@@ sectionName
tag1 value1
tag2 value2

@@ section2
a blank line is required a the end of the file you can use <#it/> <#it.tag1/> <#it.tag2/> ... in the loop


<#var _org_ >

<#_org_/> will be replace by this two lines section
var is exactly like a define but that you can easily write a multiline replacement string


<#list myList >
line 1
line 2

create the define : <#myList/>, <#myList.1/> which the first line, <#myList.2/> ...
and <#mylist.size/> which the number of line so you can write the following youpee code
to parse the lines

<#loop i between 1 <#myList.size >
line <#i/> is : <#myList.<#i/>/>
<#myList/> contains the whole text


<#tab mytab >
line 1
line 2

create the define : <#mytab/>, <#mytab.1/> which the first line, <#mytab.1.1/> is line ...
and <#mylist.size/> which the number of line so you can write
and <#mylist.1.size/> which the number of item for line 1

<#loop i between 1 <#mytab.size >
<#loop j between 1 <#mytab.<#i/>.size >


<#+ a b /> : replaced by the result of a+b
<#* a b /> : replaced by the result of a*b
<#- a b /> : replaced by the result of a-b
<#/ a b /> : replaced by the result of a/b

you can of course use multiple :
<#+ <#* 1 2 /> 3 /> : (1*2)+3 so 5

<#let i <#+ <#* 1 2 /> 3 /> /> : so <#i/> will be replaced by 5
the file smoketest/wc_c_test give a full example

regular expression

<#regexp _pattern_ _change_ />
each time the _pattern_ is found in a line it will be replaced by the

the _pattern_ is a perl regular expression 
(perl regular expression documentation)
the substring matching the pattern can be used in the _change_
using <#0/> for the whole math, <#1/> for the first substring ...

for example :
<#regexp "A(.*)Z" "--<#1/>--" />

will result in :

take care of <#0/> to avoid infinite loop during the process


<#break/> stops the current processed file or input
if you find a break in a file which is included in an other
one, that will stop the reading of the current file but not the calling
one. A break in a loop stops the loop. it's the same for a break
in a callmacro, call, post statement.


do nothing ...


<#error "...." />
log .... on stderr


abort the processing


escape the '<' and '>' in the section with
&lt; and &gt;


<#unicode "string" />
return the string with the ascii character : string
this is especially useful to encode your email address


<#filesize _filename_ b|k|M|G />
print the size of the file in b(ytes), k(ilobytes), M(egabytes) or G(igabytes)


<#date "_format_" />

_format_ is a string that supports the following option

o %a An abbreviation for the day of the week.
o %A The full name for the day of the week.
o %b An abbreviation for the month name.
o %B The full name of the month.
o  %c A string representing the complete date and time, in
the form
o %d The day of the month, formatted with two digits.
o %H The hour (on a 24-hour  clock),  formatted  with  two
o  %I  The  hour  (on a 12-hour clock), formatted with two
o %j The count of days in the year, formatted  with  three
digits (from ` 001' to ` 366').
o %m The month number, formatted with two digits.
o %M The minute, formatted with two digits.
o %p Either ` AM' or ` PM' as appropriate.
o %S The second, formatted with two digits.
o  %U  The  week number, formatted with two digits (from `
00' to ` 53'; week number 1 is taken as beginning with the
first Sunday in a year).  See also %W.
o %w A single digit representing the day of the week: Sun-
day is day 0.
o %W Another version of the week number: like `  %U',  but
counting  week  1  as beginning with the first Monday in a
o o %x A string representing the complete date, in a  for-
mat like
o  %X  A  string representing the full time of day (hours,
minutes, and seconds), in a format like
o %y The last two digits of the year.
o %Y The full year, formatted with four digits to  include
the century.
o  %Z  Defined  by  ANSI  C  as eliciting the time zone if
available; it is  not  available  in  this  implementation
(which accepts ` %Z' but generates no output for it).
o %% A single character, ` %'. 


<#image _filename_ _imageoption_ />

it will search _filename_ in IMAGEPATH and add the height
and the width

the result will be :

the jpg, gif and png files are supported

if the file is not found the result is the same w/o the
height and the width
sample: <#image tutu.gif border="0" class="img" />


each line is processed like that :
  1. make the builtin define change
  2. try to find the <# ... commands ( a command must be alone on the line )
    process the command, and process each resulting lines
  3. do the builtin macro, the defines and builtin defines until nothing changes