This section gives some examples of the use of RES-Reach variable replacement. Examples of private and public variables are given in section 4.6.
Example 1: Form Input Variables
This example shows how form variables can be used to respond to user requests.
The template file includes code for processing each type of user request. File variables are used to include only the required HTML and RES-Reach code.
<IF VARIABLE="{PROCESS}" OPERATOR="EQ" COMPARISON="DELETE">
{@MALL/delfldr.inc}
</IF>
<IF VARIABLE="{PROCESS}" OPERATOR="EQ" COMPARISON="NEW">
{@MALL/newfldr.inc}
</IF>
This part of the template file defines the form which presents the allowable actions to the end-user. Note the use of profile variables to avoid hard-coding URLs for the ACTION attributes of FORMs.
<DATA SQL="SELECT COUNT (*) AS NumberOfFolders FROM Folder WHERE [UserId] = '{[User.UserId]}' ;", DATABASE="{DB}/mall.mdb", CONNECT="", MODE="READONLY">
<RECORD>
<TABLE BORDER=0 CELLPADDING=5 WIDTH=100%>
<TR>
<![ Do not show the Delete button when there is only one folder left. ]>
<IF VARIABLE="{[NumberOfFolders]}" OPERATOR="NE" COMPARISON="0">
<![ If more than one folder exists, allow deleting. ]>
<IF VARIABLE="{[NumberOfFolders]}" OPERATOR="NE" COMPARISON="1">
<TD>
<![ Show the Delete button ! ]>
<FORM ACTION={Call_NBT}>
<INPUT TYPE=HIDDEN NAME="PROCESS" Value="DELETE">
<INPUT TYPE=HIDDEN NAME="NBT" Value="MALL/foldlist">
<INPUT TYPE="submit" VALUE={@MALL/foldlt18.eng}>
</FORM>
</TD>
</IF>
</IF>
<![ "New" folder function is always available. ]>
<TD>
<![ Create New receipt folder ]>
<FORM ACTION={Call_NBT}>
<INPUT TYPE=Hidden NAME="PROCESS" Value="NEW">
<INPUT TYPE=Hidden NAME="NBT" Value="MALL/foldlist">
<INPUT TYPE="submit" VALUE={@MALL/foldlt17.eng}>
</FORM>
</TD>
</TR>
</TABLE>
</RECORD>
</DATA> <![ End of Number of Folders query. ]>
Example 2: Current Query
This example shows how the "TotalRows" current query variable can be used to determine when a default message should be displayed. See section 4.4 for more information on the DATA tag.
<DATA SQL="Select * from [Tables] WHERE Table_Name ='{TABLE_NAME}';", DATABASE="{DB}/mall.mdb", CONNECT="", MODE="READONLY">
<RECORD>
{@MALL/showtbl.inc}
</RECORD>
<IF VARIABLE="{TotalRows}" OPERATOR="EQ" COMPARISON="0">
<!-- No Table Found -->
<H3><B>{@mall/tbldt11.eng}</B></H3>
</IF>
</DATA>
See also Example 3.
Example 3: Current Record
This example shows the use of current record variables in nested DATA and RECORD queries (see sections 4.4 and 4.5 for more information on these RES-Reach tags). The first DATA statement fetches an order using a "{[User.CartNumber]}" variable from an enclosing query (shown in Example 5 below); the alias "GetOrd" is established for it. This alias is used in the second nested query to find the items associated with it.
A use of the "RecNo" variable is shown as a mechanism for inserting HTML TABLE start tags only if there are items to display and only just before the first item. The current query variable "TotalRows" is used to determine when to place the TABLE end tag.
Finally, note that file variable references such as "{@MALL/currct33.eng}" are evaluated once for each RECORD iteration. If the file itself contains variables referencing the results of the query, then the displayed text will vary for each iteration.
<![ Get all the purchase orders in the shopping cart. ]>
<DATA SQL="SELECT PONumber, Vendor_Code, OrderStatus FROM PurchaseOrder WHERE CartNumber = {[User.CartNumber]} ;", DATABASE="{DB}/mall.mdb" CONNECT="" MODE="READONLY", ALIAS="GetOrd">
<RECORD>
<IF VARIABLE="{RecNo}" OPERATOR="EQ" COMPARISON="1">
<![ Show the general instructions for this page. ]>
{@MALL/currct38.eng}
<P>
<![ Insert the TABLE tag. ]>
<CENTER><TABLE BORDER=0 CELLPADDING=2 CELLSPACING=2 WIDTH=100%>
</IF>
<![ Show each item on the order. ]>
<DATA SQL="SELECT DISTINCTROW * , (ExpiryDate \< Now()) AS EXPIRED FROM CartItem WHERE PONumber = {[GetOrd.PONumber]};", DATABASE="{DB}/mall.mdb" CONNECT="" MODE="READONLY", ALIAS="OrdItem">
<RECORD>
<IF VARIABLE="{RecNo}" OPERATOR="EQ" COMPARISON="1">
<![ This is the first item on a new order, show the
merchant name, with links if possible. ]>
<TR>
<TD WIDTH=100% VALIGN=TOP COLSPAN=4>
{@MALL/crtvend.inc}
</TD>
</TR>
</IF>
<![ Show the item details. ]>
<TR>
<TD WIDTH=100% VALIGN=TOP COLSPAN=4>
<I>{[OrdItem.Vendor_ItemDescription]}</I>
<NOBR> <WBR>
({[OrdItem.Quantity]} {[OrdItem.UnitOfIssue]} {@MALL/currct33.eng}
${[OrdItem.ItemPrice]}
<![ Expiry message ]>
<IF VARIABLE="{[EXPIRED]}" OPERATOR="EQ" COMPARISON="-1">
<FONT COLOR=RED> <I> {@MALL/currct21.eng} </I> </FONT>
</IF>
)
</NOBR>
</TD>
</TR>
</RECORD>
</DATA> <![ End of display of a single item. ]>
</RECORD> <![ End fetch purchase orders. ]>
<IF VARIABLE="{TotalRows}" OPERATOR="NE" COMPARISON="0">
</TABLE></CENTER>
</IF>
<IF VARIABLE="{TotalRows}" OPERATOR="EQ" COMPARISON="0">
<![ Shopping Cart is Empty ]>
<H3 ALIGN=CENTER>{@MALL/currct24.eng} </H3>
</IF>
</DATA> <![ End get order query. ]>
See also Examples 5 and 7. Example 7, in particular, shows an interesting use of the "RecNo" variable.
Example 4: Run-time Errors
This example shows a sample error processing template attached to a DATA query. A combination of run-time errors, program variables and HTTP environment variables are used to report the nature of the problem. A profile variable "DEBUG" is used to determine how detailed the error message should be.
<IF VARIABLE="{DEBUG}" OPERATOR="NE" COMPARISON="1">
<FONT SIZE=6 COLOR=RED>Ooops!</FONT>
<BR><FONT SIZE=4 COLOR=BLACK>Try to reload once</FONT>
<BR>
<BR><FONT SIZE=1>{DATE} {TIME} <BR>{SERVER_NAME} {SCRIPT_NAME} {NBT} <BR>{HTTP_REFERER}</FONT><BR>
</IF>
<IF VARIABLE="{DEBUG}" OPERATOR="EQ" COMPARISON="1"> <H1>Error {ErrNo}</H1>
Meaning: <I>{ErrString}</I><p>
</IF>
Example 5: HTTP Environment Variables
This example shows the use of cookies and IP addresses as a means of recognizing visitors.
<IF VARIABLE=";USERID=" OPERATOR="SS" COMPARISON=";{HTTP_COOKIE}">
<DATA SQL="Select TOP 1 *, Format$( Now()+1, 'ddd, dd-mmm-yyyy')+' 04:00:00 GMT' AS Todays_Date FROM [User] WHERE ( UserID = Mid('{HTTP_COOKIE}', 8 )) OR ([Remote_ADDR] = '{Remote_ADDR}' AND [Remote_HOST] = '{Remote_HOST}') ;", DATABASE="{DB}/bazar.mdb", CONNECT="", MODE="READONLY", ALIAS="User" ERROR="loginerr.nbt">
</IF>
<IF VARIABLE=";USERID=" OPERATOR="NS" COMPARISON=";{HTTP_COOKIE}">
<DATA SQL="Select TOP 1 *, Format$( Now()+1, 'ddd, dd-mmm-yyyy')+' 04:00:00 GMT' AS Todays_Date FROM [User] WHERE ([Remote_ADDR] = '{Remote_ADDR}' AND [Remote_HOST] = '{Remote_HOST}') ;", DATABASE="{DB}/bazar.mdb", CONNECT="", MODE="READONLY", ALIAS="User" ERROR="loginerr.nbt">
</IF>
<RECORD>
<![ If the user does not have a cookie yet, then set one. ]>
<IF VARIABLE="{[User.UserId]}" OPERATOR="NS" COMPARISON="{HTTP_COOKIE}">
<META HTTP-EQUIV="Set-Cookie" CONTENT="USERID={[User.UserId]}; expires={[Todays_Date]};path=/cgi-bin;">
</IF>
</RECORD>
</DATA>
See also Example 6.
Example 6: Program Functions
This example shows the use of the "Date" program variable to provide a default date for a form. It also shows the use of HTTP environment variables to compose a return URL. Other default values are assigned using form variables passed to the template.
<FORM ACTION="{Call_NBT}">
<INPUT TYPE=HIDDEN NAME="NBT" Value="mall/currcart">
<INPUT TYPE=hidden NAME="VendorCode" Value="{VendorCode}">
<INPUT TYPE=hidden NAME="PriceURL" Value="http://{server_name}:{server_port}/{script_name}">
<INPUT TYPE=hidden NAME="PriceNBT" Value="{NBT}">
<TABLE BORDER=0>
<TR><TD>{@mall/NOCAT04.eng} </TD><TD><INPUT TYPE=Text SIZE=12 NAME="ItemID" Value=""></TD></TR>
<TR><TD>{@mall/NOCAT05.eng} </TD><TD><INPUT TYPE=Text SIZE=25 NAME="ItemDesc" Value=""></TD></TR>
<TR><TD>{@mall/NOCAT06.eng}</TD><TD><INPUT TYPE=date SIZE=12 NAME="ExpiryDate" Value="{DATE}"></TD></TR>
<TR><TD>{@mall/NOCAT08.eng} </TD><TD>$<INPUT TYPE=text SIZE=15 NAME="Price" Value=""></TD></TR>
<TR><TD>{@mall/NOCAT09.eng} </TD><TD><INPUT TYPE=Text SIZE=12 NAME="Units" Size=5 Value=""></TD></TR>
<TR><TD>{@mall/NOCAT10.eng}</TD><TD><INPUT TYPE=Text SIZE=5 NAME="Quantity" Size=5 Value="1"></TD></TR>
</TABLE>
<INPUT TYPE=submit Value="{@mall/NOCAT11.eng} ">
</FORM>
See also Example 4 for another example of the use of the Date and Time program variables. Example 9 shows how to use the program variable Unknown for error checking and handling.
Example 7: Profile Settings
This example assumes that a two profile variables have been defined in NETBASE.INI:
CHECKED:-0=
CHECKED:-1=CHECKED
These variables are used, in conjunction with a DATA query and some CGI form variables passed to this template, to determine which shipping rate checkbox should be selected by default.
Note also the trick used to dynamically define form variables for a series of database records. These can later be used to save the contents of the form back to the database.
<DATA SQL="Select * , Measure = {SelectedMeasure} AS HIT from ShipTable_Calc WHERE Rates_Number ={RATES_NUMBER} ;", DATABASE="{DB}/mall.mdb", CONNECT="", MODE="READONLY">
<RECORD>
<TD Align=CENTER><INPUT TYPE=Checkbox {CHECKED:-{[HIT]}} NAME="Code" VALUE={RECNO}></TD>
<TD Align=CENTER><INPUT TYPE=Text SIZE=10 MAXLENGTH=10 NAME="{RECNO}_Measure" VALUE="{[Measure]}"></TD>
<TD Align=CENTER><INPUT TYPE=Text SIZE=10 MAXLENGTH=10 NAME="{RECNO}_Fee" VALUE="{[Fee]}"></TD>
</TR>
</RECORD>
</DATA>
Example 4 shows the use of a "DEBUG" profile variable in error detection. See also Examples 1 and 6 for an example the use of "CALL_NBT" and "GET_NBT" profile settings. Most of the examples in this section also illustrate the use of a "DB" profile variable to specify the location of database files.
Example 8: Files (1)
This example shows how multiple languages can be supported easily using RES-Reach's recursive variable replacement. The "{[User.LANG]}" variable refers to a database field (retrieved by the DATA tag shown in Example 5) specific to the current user which stores their preferred language of interaction. RES-Reach will include the contents of a text file (e.g. a file named "currct01.eng") containing a string in the preferred language as the title of the document sent to the Browser.
<HEAD>
<![ Choose an appropriate title for this page, given the
contents of the form variable "PROCESS".]>
<IF VARIABLE="{PROCESS}" OPERATOR="EQ" COMPARISON="MENU">
<TITLE>{@MALL/currct01.{[User.LANG]}}</TITLE>
</IF>
<IF VARIABLE="{PROCESS}" OPERATOR="NE" COMPARISON="MENU">
<TITLE>{@MALL/currct76.{[User.LANG]}}</TITLE>
</IF>
</HEAD>
Example 9: Files (2)
This example shows how to increase the understandability and maintainability of large RES-Reach templates using file variables. (Example 1 also shows this feature.) The contents of a "UserAction" form variable are used to determine the action requested by the user. Each of the actions shown below involve large blocks of HTML and RES-Reach tags. By localizing the code for the various operations in different files, it has been pseudo-modularized. The overall flow and functions of the main template file are clear and if changes need to be made to one of the operations, it is easily located.
Note also the error checking here. If "{UserAction}" is unknown, we automatically trigger an error handling include file.
Warning: RECORD start and end tags must be in the same file.
<IF VARIABLE="{UserAction}" OPERATOR="EQ" COMPARISON="NEW">
{@MALL/OPS/crtnew.inc}
</IF>
<IF VARIABLE="{UserAction}" OPERATOR="EQ" COMPARISON="COPY">
{@MALL/OPS/crtcopy.inc}
</IF>
<IF VARIABLE="{UserAction}" OPERATOR="EQ" COMPARISON="DELETE">
{@MALL/OPS/crtdel.inc}
</IF>
<IF VARIABLE="{UserAction}" OPERATOR="EQ" COMPARISON="{Unknown}">
{@MALL/OPS/crterr.inc}
</IF>
Example 10: Using Group Names
This example shows the use of group names to disambiguate variable references. Suppose there is a form which allows a user to buy a set of sheets.
<FORM ACTION={Call_NBT}>
<INPUT TYPE=HIDDEN NAME="Name" Value="Sheet Set">
<INPUT TYPE=HIDDEN NAME="Size" Value="Queen">
<INPUT TYPE=HIDDEN NAME="ThreadCount" Value="250">
<INPUT TYPE=HIDDEN NAME="NBT" Value="MALL/currcart">
<INPUT TYPE="submit" VALUE=Buy>
</FORM>
A RES-Reach NBT file could contain the following code to process the form when the "Buy" button is clicked.
<IF VARIABLE="{UserAction}" OPERATOR="EQ" COMPARISON="Buy"> There are currently {_SYS.ThreadCount} shoppers buying our products right now! <P><DATA SQL="INSERT INTO ProductsPurchased (ProductId, VendorCode, Attribute_1, Attribute_2) VALUES ('{Name}', 'TOTAL', '{Size}', '{_FRM.ThreadCount}');", DATABASE="{DB}/mall.mdb", CONNECT="", MODE="SHARED">
{TotalRows} (or {_DAT.TotalRows}) {_FRM.ThreadCount} thread count bed sheets purchased.<P> </DATA> </IF>
Example 11:
This example shows how file variables without variable expansion can be used to send an image to a browser.
<IF VARIABLE=";{HTTP_COOKIE};" OPERATOR="NS" COMPARISON=";{Unknown};;"> Content-type: image/jpeg {@@cookie.jpg} </IF><IF VARIABLE=";{HTTP_COOKIE};" OPERATOR="SS" COMPARISON=";{Unknown};;"> Content-type: image/gif {@@cake.gif} </IF>