Server behavior techniques

 < Day Day Up > 

This section covers the common and advanced techniques that create and edit server behaviors. Most of the suggestions involve specific settings in the EDML files.

Finding server behaviors

Writing search patterns

In order to update or delete server behaviors, you must provide a way for Dreamweaver to find each instance in a document. This requires a quickSearch tag and at least one searchPattern tag, which is contained within the searchPatterns tag.

The quickSearch tag should be a string, not a regular expression, that indicates that the server behavior might exist on the page. It is not case-sensitive. It should be short and unique, and it should avoid spaces and other sections that can be changed by the user. The following example shows a participant that consists of the simple ASP JavaScript tag:

 <% if (Recordset1.EOF) Response.Redirect("some_url_here") %> 

In the following example, the quickSearch string checks for that tag:

 <quickSearch>Response.Redirect</quickSearch> 

For performance reasons, the quickSearch pattern is the beginning of the process of finding server behavior instances. If this string is found in the document and the participant identifies a server behavior (in the group file, partType="identifier" for this participant), the related server behavior files are loaded and the findServerBehaviors() function is called. If your participant has no reliable strings for which to search (or for debugging purposes), you can leave the quickSearch string empty, as shown in the following example:

 <quickSearch></quickSearch> 

In this example, the server behavior is always loaded and can search the document.

Next, the searchPattern tag searches the document more precisely than the quickSearch tag and extracts parameter values from the participant code. The search patterns specify where to search (the whereToSearch attribute) with a series of searchPattern tags that contain specific patterns. These patterns can use simple strings or regular expressions. The previous example code is an ASP directive, so the whereToSearch="directive" specification and a regular expression identifies the directive and extracts the parameters, as shown in the following example:

 <quickSearch>Response.Write</quickSearch> <searchPatterns whereToSearch="directive">   <searchPattern paramNames="rs,new__url">     /if\s*\((\w+)\.EOF\)\s*Response\.Redirect\("([^\r\n]*)"\)/i   </searchPattern> </searchPatterns> 

The search string is defined as a regular expression by starting and ending with a slash (/) and is followed by i, which means that it is not case-sensitive. Within the regular expression, special characters such as parentheses () and periods (.) are escaped by preceding them with a backslash (\). The two parameters rs and new__url are extracted from the string by using parenthetical subexpressions (the parameters must be enclosed in parentheses). In this example, they are indicated by (\w+) and ([^\r\n]*): These values correspond to the regular expression values that are normally returned by $1 and $2.

Optional search patterns

There might be cases where you want to identify a participant even if some parameters are not found. You might have a participant that stores some optional information such as a telephone number. For such an example, you could use the following ASP code:

 <% //address block   LNAME = "joe";   FNAME = "smith";   PHONE = "123-4567"; %> 

You could use the following search patterns:

 <quickSearch>address</quickSearch> <searchPatterns whereToSearch="directive">   <searchPattern paramNames="lname">/LNAME\s*=\s*"([^\r\n]*)"/i</searchPattern>   <searchPattern paramNames="fname">/FNAME\s*=\s*"([^\r\n]*)"/i</searchPattern> <searchPattern paramNames="phone">/PHONE\s*=\s*"([^\r\n]*)"/i</searchPattern> </searchPatterns> 

In the previous example, the telephone number must be specified. However, you can make the telephone number optional, by adding the isOptional attribute, as shown in the following example:

 <quickSearch>address</quickSearch> <searchPatterns whereToSearch="directive">   <searchPattern paramNames="lname">/LNAME\s*=\s*"([^\r\n]*)"/i</searchPattern>   <searchPattern paramNames="fname">/FNAME\s*=\s*"([^\r\n]*)"/i</searchPattern>   <searchPattern paramNames="phone" isOptional="true">/PHONE\s*=\s*"([^\r\n]*)"/i   </searchPattern> </searchPatterns> 

Now the participant is recognized, even if the telephone number is not found.

How participants are matched

If a server behavior has more than one participant, the participants must be identified in the user's document and matched. If the user applies multiple instances of the server behavior to a document, each group of participants must be matched accordingly. To ensure participants are matched correctly, you might need to change or add parameters and construct participants so they can be uniquely identified.

Matching requires some rules. Participants are matched when all parameters with the same name have the same value. Above and below the html tag, there can be only one instance of a participant with a given set of parameter values. Within the html.../html tags, participants are also matched by their position relative to the selection or to common nodes that are used for insertion.

Participants without parameters are automatically matched, as shown in the following example of a server behavior with group file:

 <group serverBehavior="test.htm">   <title>Test</title>   <groupParticipants>     <groupParticipant name="test_p1" partType="identifier" />     <groupParticipant name="test_p2" partType="identifier" />   </groupParticipants> </group> 

The following example inserts two simple participants above the html tag:

 <% //test_p1 %> <% //test_p2 %> <html> 

These participants are found and matched, and Test appears once in the Server Behaviors panel. If you add the server behavior again, nothing is added because the participants already exist.

If the participants have unique parameters, multiple instances can be inserted above the html tag. For example, by adding a name parameter to the participant, a user can enter a unique name in the Test Server Behavior dialog box. If the user enters name "aaa", the following participants are inserted:

 <% //test_p1 name="aaa" %> <% //test_p2 name="aaa" %> <html> 

If you add the server behavior again with a different name, such as "bbb", the document now looks like the following example:

 <% //test_p1 name="aaa" %> <% //test_p2 name="aaa" %> <% //test_p1 name="bbb" %> <% //test_p2 name="bbb" %> <html> 

There are two instances of Test listed in the Server Behaviors panel. If the user tries to add a third instance to the page and names it "aaa", nothing is added because it already exists.

Within the html tag, matching can also use position information. In the following example, there are two participants, one that is added before the selection and another that is added after the selection:

 <% if (expression) { //mySBName %>   Random HTML selection here <% } //end mySBName %> 

These two participants are without parameters, so they are grouped together. However, you can add another instance of this server behavior elsewhere in the HTML, as shown in the following example:

 <% if (expression) { //mySBName %>   Random HTML selection here <% } //end mySBName %>   More HTML here... <% if (expression) { //mySBName %>   Another HTML selection here <% } //end mySBName %> 

Now there are two identical instances of each participant, which is allowed within the HTML. They are matched by the order in which they occur in the document.

The following example shows a matching problem and how to avoid it. You can create a participant that computes the tax on some dynamic data and displays the result at the selection.

 <% total = Recordset1.Fields.Item("itemPrice").Value * 1.0825 %> <html> <body>   The total (with taxes) is $<%=total%> </body> </html> 

The two participants are matched because they have no common parameters. However, if you add a second instance of this server behavior, you should have the following code:

 <% total = Recordset1.Fields.Item("itemPrice").Value * 1.0825 %> <% total = Recordset1.Fields.Item("salePrice").Value * 1.0825 %> <html> <body>   The total  (with taxes) is $<%=total%>   Sale price (with taxes) is $<%=total%> </body> </html> 

This server behavior no longer works correctly because only one parameter is named total. To solve this problem, make sure that there is a parameter with a unique value and can be used to match the participants. In the following example, you could make the total variable name unique using the column name:

 <% itemPrice_total = Recordset1.Fields.Item("itemPrice").Value * 1.0825 %> <% salePrice_total = Recordset1.Fields.Item("salePrice").Value * 1.0825 %> <html> <body>   The total  (with taxes) is $<%=itemPrice_total%>   Sale price (with taxes) is $<%=salePrice_total%> </body> </html> 

The search patterns now uniquely identify and match the participants.

Search pattern resolution

Dreamweaver supports the following actions by using the participant searchPatterns functionality:

  • File transfer dependency

  • Updating the file paths for any file reference (such as those for include files)

When Dreamweaver creates server models, it builds lists of patterns by scanning all the participants for special paramNames attributes. To find URLs to check file dependency and to fix the pathname, Dreamweaver uses each searchPattern tag in which one of the paramNames attribute ends with _url. Multiple URLs can be specified in a single searchPattern tag.

For each translator searchPattern tag that has a paramNames attribute value that ends with _includeUrl, Dreamweaver uses that searchPattern tag to translate include file statements on the page. Dreamweaver uses a different suffix string to identify include file URLs because not all URL references are translated. Also, only a single URL can be translated as an include file.

In resolving a searchPatterns tag, Dreamweaver uses the following algorithm:

1.

Look for the whereToSearch attribute within the searchPatterns tag.

2.

If the attribute value starts with tag+, the remaining string is assumed to be the tag name (no spaces are allowed in the tag name).

3.

Look for the limitSearch attribute within the searchPattern tag.

4.

If the attribute value starts with attribute+, the remaining string is assumed to be the attribute name (no spaces are allowed in the attribute name).

If these four steps are successful, Dreamweaver assumes a tag/attribute combination. Otherwise, Dreamweaver starts looking for searchPattern tags with a paramName attribute that has a _url suffix and a regular expression that is defined. (For information about regular expressions, see the "Regular expressions" on page 338.)

The following example of a searchPatterns tag has no search pattern because it combines a tag (cfinclude) with an attribute (template) to isolate the URL for dependency file checking, path fixing, and so forth:

 <searchPatterns whereToSearch="tag+cfinclude">    <searchPattern paramNames="include_url" limitSearch="attribute+template" /> </searchPatterns> 

The tag/attribute combination (see the previous example) does not apply to translation because Dreamweaver always translates to straight text in the JavaScript layer. File dependency checking, path fixing, and so on occurs in the C layer. In the C layer, Dreamweaver internally splits the document into directives (straight text) and tags (parsed into an efficient tree structure).

Updating server behaviors

Replacement update

By default, participant EDML files do not have an <updatePatterns> tag, and instances of the participant are updated in the document by replacing them entirely. When a user edits an existing server behavior and clicks OK, any participant that contains a parameter whose value has changed is removed and reinserted with the new value in the same location.

If the user customizes participant code in the document, the participant might not be recognized if the search patterns look for the old code. Shorter search patterns can let the user customize the participant code in their document; however, updating the server behavior instance can cause the participant to be replaced, which loses the custom edits.

Precision update

In some cases, it can be desirable to let users customize the participant code after it is inserted in the document. This situation can be achieved by limiting the search patterns and providing update patterns in the EDML file. After you add the participant to the page, the server behavior updates only specific parts of it. The following example shows a simple participant with two parameters:

 <% if (Recordset1.EOF) Response.Redirect("some_url_here") %> 

This example might use the following search patterns:

 <quickSearch>Response.Write</quickSearch> <searchPatterns whereToSearch="directive">   <searchPattern paramNames="rs,new__url">     /if\s*\((\w+)\.EOF\)\s*Response\.Redirect\("([^\r\n]*)"\)/i   </searchPattern> </searchPatterns> 

The user might add another test to a particular instance of this code, as shown in the following example:

 <% if (Recordset1.EOF || x > 2) Response.Redirect("some_url_here") %> 

The search patterns fail because they are looking for a parenthesis after the EOF parameter. To make the search patterns more forgiving, you can shorten them by splitting them up, as shown in the following example:

 <quickSearch>Response.Write</quickSearch> <searchPatterns whereToSearch="directive">   <searchPattern paramNames="rs">/(\w+)\.EOF/</searchPattern>   <searchPattern paramNames="new__url">     /if\s*\([^\r\n]*\)\s*Response\.Redirect\("([^\r\n]*)"/i   </searchPattern> </searchPatterns> 

These shortened search patterns are flexible, so the user can add to the code. However, if the server behavior changes the URL, when the user clicks OK, the participant is replaced, and the customizations are lost. To update more precisely, add an updatePatterns tag that contains a pattern for updating each parameter:

 <updatePatterns>   <updatePattern paramNames="rs">/(\b)\w+(\.EOF)/</updatePattern>   <updatePattern paramNames="new__url">     /(Response\.Redirect\(")[^\r\n]*(")/i   </updatePattern> </updatePatterns> 

In update patterns, the parentheses are reversed and are placed around the text before and after the parameter. For search patterns, use the textBeforeParam(param)textAfterParam parameter. For update patterns, use the (textBeforeParam)param(textAfterParam) parameter. All the text between the two parenthetical subexpressions is replaced with the new value for the parameter.

Deleting server behaviors

Default deletion and dependency counts

The user can delete an instance that is selected in the Server Behaviors panel by clicking the Minus (-) button or pressing Delete. All the participants are removed except for the ones that are shared by other server behaviors. Specifically, if more than one server behavior has a participant pointer to the same node, the node is not deleted.

By default, participants are deleted by removing an entire tag. If the insert location is "wrapSelection", only the outer tag is removed. For attributes, the entire attribute declaration is removed. The following example shows an attribute participant on the ACTION attribute of a form tag:

 <form action="<% my_participant %>"> 

After deleting the attribute, only form remains.

Using delete flags to limit participant deletion

There might be cases where you want to limit the way that participants are deleted. This can be achieved by adding a delete tag to the EDML file. The following example shows a participant that is an href attribute of a link:

 <a href="<%=MY_URL%>">Link Text</a> 

When this attribute participant is deleted, the resulting tag is <a>Link Text</a>, which no longer appears as a link in Dreamweaver. It might be preferable to delete only the attribute value, which is done by adding the following tag to the participant EDML file:

 <delete deleteType="innerOnly"/> 

Another approach is to remove the entire tag when the attribute is deleted by typing <delete deleteType="tagOnly"/>. The resulting text is Link Text.

Avoiding conflicts with share-in-memory JavaScript files

If several HTML files reference a particular JavaScript file, Dreamweaver loads the JavaScript into a central location where the HTML files can share the same JavaScript source. These files contain the following line:

 //SHARE-IN-MEMORY=true 

If a JavaScript file has the SHARE-IN-MEMORY directive and an HTML file references it (by using the SCRIPT tag with the SRC attribute), Dreamweaver loads the JavaScript into a memory location where the code is implicitly included in all HTML files thereafter.

NOTE

Because JavaScript files that are loaded into this central location share memory, the files cannot duplicate any declarations. If a share-in-memory file defines a variable or function and any other JavaScript file defines the same variable or function, a name conflict occurs. When writing new JavaScript files, be aware of these files and their naming conventions.


     < Day Day Up > 


    Developing Extensions for Macromedia Dreamweaver 8
    Developing Extensions for Macromedia Dreamweaver 8
    ISBN: 0321395409
    EAN: 2147483647
    Year: 2005
    Pages: 282

    flylib.com © 2008-2017.
    If you may any questions please contact us: flylib@qtcs.net