home Links Articles Books Past Meetings Photos SiteMap
The MDCFUG is sponsored by TeraTech. Visit us at www.TeraTech.com

Please send
comments/questions to

michael@
teratech.com

 

ColdFusion MX Coding Guidelines - Style: Naming, Comments & Layout

Release 3.0.2 (10/17/2003)

« Contents | Structure: Application, Component, Tag etc »

Style: Naming, Comments & Layout

This section provides guidelines on naming conventions (for files, tags, variables etc), comments and source code layout.

Naming

This section provides guidelines for naming various entities in your ColdFusion code.

General Naming Guidelines

All entities should be named for readability - names should be readable English words or phrases. The primary function or purpose of any entity should be obvious from its name. In general, "noun-verb" and "adjective-noun" phrases are the most natural choice, e.g.,:

course_list_output.cfm - invoked in a URL
sales_tax_calculate.cfm - a custom tag
productinformation.cfc - a ColdFusion component
userName - a variable, attribute, property etc

The singular noun is preferred. In general, files will be lower case with words optionally separated by underscores.

Abbreviations

Abbreviations and acronyms should be avoided. Only a few, widely understood acronyms or abbreviations may be used, such as ID, CGI and URL. Such abbreviations and acronyms will be uppercase, unless they are part of a filename that forms part of a URL, in which case they will be lowercase, e.g.,

userID - variable, attribute, property etc
set_user_id.cfm - invoked in a URL

File Naming

Suffixes:

  • HTML files end in .html;
  • CFML files end in .cfm;
  • Component files end in .cfc;
  • XML files end in .xml.

In general, follow our existing file naming conventions for files: all URL-accessible filenames shall be lowercase, with words optionally separated by underscores (determined by readability). Filenames must never contain spaces! Files whose names are not URL-accessible should also be lowercase for consistency but we allow more leeway in this situation.

Note: Application.cfm and OnRequestEnd.cfm are the only exceptions to the lowercase filename rule for URL-accessible files and must have exactly the case shown! The Mach II framework files are mixed case (and are not URL-accessible) - when referencing those files (as type names), you must use the same exact case as the filename.

ColdFusion Components

These are similar to Java classes but instead of following the traditional Java class naming conventions (MixedCase), we have historically kept component filenames lowercase because, prior to CFMX 6.1, mixed case component filenames were not uniformly supported. With CFMX 6.1, this practice can be relaxed and mixed case component names can be used if desired for components that are not URL-accessible.

The component name shall be lowercasewords, lowercase_words or MixedCaseWords; all method names, property names and instance names (variables referring to components) shall be mixedCaseInitLower. Components that are URL-accessible, e.g., that implement Web Services, shall be lowercasewords or lowercase_words. All references to component names in code shall match exactly the case of the implementation filename, i.e., references will be path.to.lowercasewords, path.to.lowercase_words or path.to.MixedCaseWords as appropriate.

If a ColdFusion component contains methods that are accessible as Web Services or via Flash Remoting (i.e., the cffunction tag specifies access="remote"), then the component should be stored under {cfmxroot}/wwwroot/{applicationname}/ (and have lowercase filenames). Otherwise, ColdFusion components should be stored under {cfmxroot}/extensions/components/{applicationname}/.

The directory structure should reflect the logical grouping of the major elements of each application. All the application-specific components should live in application-specific sub-directories. All the utility and common reusable components should live in appropriately named library sub-directories, e.g., WTG has both lib and util sub-directories for these common components (although those names are somewhat arbitrary).

Custom Tags

Custom tag names will be lowercase_words. Their implementation filename should be lowercase_words.cfm, stored somewhere within the {cfmxroot}/extensions/customtags/ hierarchy (so custom tags cannot be invoked directly via a URL). They should be invoked using a tag prefix (defined using cfimport before the first use of any custom tags in each file - cfimport tags should be grouped together near the top of the file) e.g., <pfx:lowercase_words ...> ... </pfx:lowercase_words>. The pfx will usually be the lowest-level directory containing the tags, e.g., mmlf for {cfmxroot}/extensions/customtags/mmlf/ - used like:

<cfimport taglib="/customtags/mmlf" prefix="mmlf" />
...
<mmlf:ssi virtual="/path/to/file.html" />

The expectation is that directories under the Custom Tag Paths will have unique names - the tag prefix must be unique within a page.

Note: The ssi tag currently complains if you invoke it with a closing / but I think that's a bug that should be fixed!

Note: CFX tags will not be used - instead write Java tag libraries and <cfimport ...> them (assuming you can't write the tag in CFML for some reason).

Type Names

The names used to reference ColdFusion types (e.g., in type= and returntype= attributes) shall be lowercase for built-in types (e.g., boolean, string). The names used to reference user-defined types (i.e., ColdFusion Components shall exactly match the case of the implementing filename, e.g., article, news_item, MachII.framework.Listener.

Built-in CFML Tags, Attributes & Operators

Built-in CFML tags shall be lowercase, just like our HTML tags. Attributes for CFML tags shall either be lowercase (mirroring XHTML-compliance) or mixed case, first letter lowercase (mixedCaseInitLower) - this is a stylistic choice but be consistent. Built-in operators shall be mixed case, first letter lowercase, e.g., mixedCaseInitLower.

Note: This means simple built-in operators will be lowercase, e.g., is, and, or, not.

Attributes, Fields, Functions, Methods, Parameters, Properties & Variables

All these entity names will be mixedCaseInitLower. To enhance readability, boolean attributes and variables should generally begin with "is" or "has", e.g., <cfif hasFlash> ... </cfif>.

Attribute Values

All attribute values to all tags - except cfset, cfif and cfreturn - will be quoted, usually with double quotes ("). Single quotes (') may be used if the attribute value already contains a double quote.

In cfset, the attribute name is always a variable name (possibly evaluated, e.g., arr[i]) and the apparent attribute value is really an expression. In cfif and cfreturn, the 'attribute' is really an expression. String values in expressions will be quoted (with " or ' as appropriate). Numeric values in expressions will not be quoted. Variable names in expressions will not be quoted, so that pound signs (#) are not needed, i.e., variableName instead of "#variableName#". The attribute name in cfset - the variable name - will not be quoted.

Do not use evaluated variable names like "caller.#resultVariable#" or "varname_#index#" - use caller[resultVariable] or variables["varname_" & index] instead.

The only acceptable boolean attribute values are true and false - which may be quoted or unquoted (in cfset, they should always be unquoted).

Examples:

<!--- string requires quotes: --->

<cfset x = "A string" />

<!--- other expressions require no quotes: --->
<cfset y = len(x) />
<cfif z gt y * 2 >

<!--- simple variable requires no quotes: --->
<cfset request.value = z />

<!--- evaluated variable requires no quotes: --->
<cfset caller[result] = z />

Scope Names

Scope name qualifiers should be used with all variables (except var scope variables inside functions), where there is any possibility of a collision with a name in another scope. Since ColdFusion looks 'up' the scope chain if it cannot find a name in the current scope, variables scope should be used for safety, to avoid accidentally picking up the wrong variable in an outer scope, e.g., a cookie. See Creating and using variables in scopes on LiveDocs for more information about scope lookup.

Inside components, variables scope refers to non-public instance data (and this scope refers to public instance data). If you want a local variable in a function, you should use var and then set the variable to 'declare' it (at the top of the function). Within a script function, you introduce local variables as follows:

function foo() {
    var localVar = 0;
    var anotherLocalVar = 0;
    ...
}

Within cffunction, you can use either of the following styles:

<!--- using tag syntax for the function body: --->
<cffunction name="bar">
    <cfset var localVar = 0 />
    <cfset var anotherLocalVar = 0 />
    ...
</cffunction>

<!--- using script syntax for the function body: --->
<cffunction name="bar">
    <cfscript>
        var localVar = 0;
        var anotherLocalVar = 0;
        ...
    </cfscript>
</cffunction>

Inside components, there are two special scopes: this and variables (in CFMX 6.0, variables scope was not available and you used instead the unnamed scope). When variables are qualified with this scope, they become public data members of the component instance and accessible to code outside the component. When variables are qualified with variables scope, or left unqualified - using the unnamed scope, they become non-public data members of the component instance (and, therefore, are not accessible outside the component). This is important since unqualified variables within functions will persist for the lifetime of the instance - which may not be what you intended.

Example:

<cfcomponent>
    <cffunction name="example">
        <cfset var localVar = "Just in this function" />
        <cfset variables.nonPublicVar = "Non-public data member" />

        <cfset anotherNonPublicVar = "Not recommended - use 'variables'" />
        <cfset this.publicVar = "Public data member" />
    </cffunction>
    <cffunction name="more">

        <cfset var localVar = "Different to example localVar" />
        <cfset var x = variables.nonPublicVar