... You could have the following code in your {{hello.shtml}} file:
{code} <html> <head> <title>shtml custom tag example</title> </head> <body> <!--#HELLO--> </body> </html> {code}
When the browser displays this code, each occurrence of the {{HELLO}} tag calls the function.
The general steps for defining a customized server-parsed tag are:
* [#Defining the Functions that Implement the Tag]. You must define the tag execution function. You must also define other functions that are called on tag loading and unloading, and on page loading and unloading.
* [#Writing an Initialization Function]. Write an initialization function that registers the tag using the {{shtml_add_tag}} function.
* [#Loading the New Tag into the Server].
h3. Defining the Functions that Implement the Tag
Define the functions that implement the tags in C, using NSAPI. Include the header {{shtml_public.h}}, which is in the directory _install-dir_{{/include/shtml}}. Link against the SHTML shared library in the _install_-dir_/{{lib}} directory. On Windows, the SHTML shared library is named {{sshtml.dll}}. On UNIX platforms, the library is named {{libShtml.so}} or {{libShtml.sl}}.
{{ShtmlTagExecuteFunc}} is the tag handler which gets called with the NSAPI {{pblock}}, {{Session}}, and {{Request}} variables. In addition, this handler also gets passed the {{TagUserData}} created from the result of executing the tag loading and page loading functions, if any such functions are defined for that tag.
The signature for the tag execution function is: {code} typedef int (*ShtmlTagExecuteFunc) (pblock*, Session*, Request*, TagUserData, TagUserData); {code}
|
... * {{REQ_PROCEED}} — the execution was successful * {{REQ_NOACTION}} — nothing happened * {{REQ_ABORTED}} — an error occurred * {{REQ_EXIT}} — the connection was lost
The other functions you must define for your tag are:
* {{ShtmlTagInstanceLoad}} — Called when a page containing the tag is parsed. This function is not called if the page is retrieved from the browser's cache. It serves as a constructor, the result of which is cached and is passed into {{ShtmlTagExecuteFunc}} whenever the execution function is called. * {{ShtmlTagInstanceUnload}} — A destructor for cleaning up whatever was created in the {{ShtmlTagInstanceLoad}} function. This function gets passed the result that was originally returned from the {{ShtmlTagInstanceLoad}} function. * {{ShtmlTagPageLoadFunc}} — Called when a page containing the tag is executed, regardless of whether the page is still in the browser's cache. This function provides a way to make information persistent between occurrences of the same tag on the same page. * {{ShtmlTagPageUnLoadFn}} — Called after a page containing the tag has executed. This function provides a way to clean up any allocations done in a {{ShtmlTagPageLoadFunc}} and hence gets passed the result returned from the {{ShtmlTagPageLoadFunc}}.
The signature for these functions are:
{code} #define TagUserData void* typedef TagUserData (*ShtmlTagInstanceLoad) (const char* tag, pblock*, const char*, size_t); typedef void (*ShtmlTagInstanceUnload)(TagUserData); typedef int (*ShtmlTagExecuteFunc) (pblock*, Session*, Request*, TagUserData, TagUserData); typedef TagUserData (*ShtmlTagPageLoadFunc) (block* pb, Session*, Request*); typedef void (*ShtmlTagPageUnLoadFunc)(TagUserData); {code}
The following code example implements the {{HELLO}} tag: {code} /* * mytag.c: NSAPI functions to implement #HELLO SSI calls */ #include "nsapi.h" #include "shtml/shtml_public.h" /* FUNCTION : mytag_con * * DESCRIPTION: ShtmlTagInstanceLoad function */ #ifdef __cplusplus extern "C" #endif TagUserData mytag_con(const char* tag, pblock* pb, const char* c1, size_t t1) { return NULL; } /* FUNCTION : mytag_des * * DESCRIPTION: ShtmlTagInstanceUnload */ #ifdef __cplusplus extern "C" #endif void mytag_des(TagUserData v1) { } /* FUNCTION : mytag_load * DESCRIPTION: ShtmlTagPageLoadFunc */ #ifdef __cplusplus extern "C" #endif TagUserData mytag_load(pblock *pb, Session *sn, Request *rq) { return NULL; } /* FUNCTION : mytag_unload * * DESCRIPTION: ShtmlTagPageUnloadFunc */ # #ifdef __cplusplus extern "C" #endif void mytag_unload(TagUserData v2) { } /* FUNCTION : mytag * DESCRIPTION: ShtmlTagExecuteFunc */ #ifdef __cplusplus extern "C" #endif int mytag(pblock* pb, Session* sn, Request* rq, TagUserData t1, TagUserData t2) { char* buf; int length; char* client; buf = (char *) MALLOC(100*sizeof(char)); length = util_sprintf(buf, "<h1>Hello World! </h1>", client); if (net_write(sn->csd, buf, length) == IO_ERROR) { FREE(buf); return REQ_ABORTED; } FREE(buf); return REQ_PROCEED; } /* FUNCTION : mytag_init * DESCRIPTION: initialization function, calls shtml_add_tag() to * load new tag */ # #ifdef __cplusplus extern "C" #endif int mytag_init(pblock* pb, Session* sn, Request* rq) { int retVal = 0; // NOTE: ALL arguments are required in the shtml_add_tag() function retVal = shtml_add_tag("HELLO", mytag_con, mytag_des, mytag, mytag_load, mytag_unload); return retVal; } /* end mytag.c */ {code}
h3. Writing an Initialization Function
In the initialization function for the shared library that defines the new tag, register the tag using the function {{shtml_add_tag}}. The signature is:
{code} NSAPI_PUBLIC int shtml_add_tag ( const char* tag, ShtmlTagInstanceLoad ctor, ShtmlTagInstanceUnload dtor, ShtmlTagExecuteFunc execFn, ShtmlTagPageLoadFunc pageLoadFn, ShtmlTagPageUnLoadFunc pageUnLoadFn); {code}
Any of these arguments can return NULL except for the {{tag}} and {{execFn}}.
h3. Loading the New Tag into the Server
After creating the shared library that defines the new tag, you load the library into the Web Server. Add the following directives to the configuration file {{magnus.conf}}:
* An {{Init}} directive whose {{fn}} parameter is {{load-modules}} and whose {{shlib}} parameter is the shared library to load. For example, if you compiled your tag into the shared object _install-dir_{{/hello.so}}, the {{Init}} directive would be: {code} Init funcs="mytag,mytag_init" shlib="_install-dir_/hello.so" fn="load-modules" {code}
* An {{Init}} directive whose {{fn}} parameter is the initialization function in the shared library that uses {{shtml_add_tag}} to register the tag. For example: {code} Init fn="mytag_init" {code}
|