Creating user-defined functions



Before you create a UDF, determine where you want to define it, and whether you want to use CFML or CFScript to create it.

Determining where to create a user-defined function

You can define a function in the following places:

  • In a ColdFusion component. If you organize your functions in ColdFusion components, you use the functions as described in Using ColdFusion components.

  • On the page where it is called. You can even define it below the place on the page where it is called, but this poor coding practice can result in confusing code.

  • On a page that you include using a cfinclude tag. The cfinclude tag must be executed before the function gets called. For example, you can define all the functions for your application’s on a single page and place a cfinclude tag at the top of pages that use the functions.

  • On any page that places the function name in a scope common with the page on which you call the function. For more information on UDF scoping, see Specifying the scope of a function.

  • On the Application.cfc or Application.cfm page. For more information, see Designing and Optimizing a ColdFusion Application.

For recommendations on selecting where you define functions, see the sections Using Application.cfm and function include files and Specifying the scope of a function.

About creating functions using CFScript

You use the function statement to define the function in CFScript. CFScript function definitions have the following features and limitations:

  • The function definition syntax is familiar to anyone who uses JavaScript or most programming languages.

  • CFScript is efficient for writing business logic, such as expressions and conditional operations.

  • CFScript function definitions cannot include CFML tags.

The following is a CFScript definition for a function that returns a power of 2:

<cfscript> 
function twoPower(exponent) { 
    return 2^exponent;  
} 
</cfscript>

For more information on how to use CFScript to define a function, see Defining functions in CFScript.

Defining functions in CFScript

You define functions using CFScript in a similar manner defining JavaScript functions. You can define multiple functions in a single CFScript block.

Note: For more information on using CFScript, see Extending ColdFusion Pages with CFML Scripting.

CFScript function definition syntax

A CFScript function definition has the following syntax:

function functionName( [argName1[, argName2...]] ) 
    { 
        CFScript Statements 
    }

The following table describes the function variables:

Function variable

Description

functionName

The name of the function. You cannot use the name of a standard ColdFusion function or any name that starts with “cf”. You cannot use the same name for two different function definitions. Function names cannot include periods.

argName1...

Names of the arguments required by the function. The number of arguments passed into the function must equal or exceed the number of arguments in the parentheses at the start of the function definition. If the calling page omits any of the required arguments, ColdFusion generates a mismatched argument count error.

The body of the function definition must be in curly brackets, even if it is empty.

The following two statements are allowed only in function definitions:

Statement

Description

varvariableName = expression;

Creates and initializes a variable that is local to the function (function variable). This variable has meaning only inside the function and is not saved between calls to the function. It has precedence in the function body over any variables with the same name that exist in any other scopes. You never prefix a function variable with a scope identifier, and the name cannot include periods. The initial value of the variable is the result of evaluating the expression. The expression can be any valid ColdFusion expression, including a constant or even another UDF.

All var statements must be at the top of the function declaration, before any other statements. Initialize all variables when you declare them. You cannot use the same name for a function variable and an argument.

Each var statement can initialize only one variable.

Use the var statement to initialize all function-only variables, including loop counters and temporary variables.

returnexpression;

Evaluates expression (which can be a variable), returns its value to the page that called the function, and exits the function. You can return any ColdFusion variable type.

A simple CFScript example

The following example function adds the two arguments and returns the result:

<cfscript> 
function Sum(a,b) { 
    var sum = a + b; 
    return sum;  
}  
</cfscript>

In this example, a single line declares the function variable and uses an expression to set it to the value that it returns. This function can be simplified so that it does not use a function variable, as follows:

function MySum(a,b) {Return a + b;} 

Always use curly brackets around the function definition body, even if it is a single statement.

Note: ColdFusion does not COPY any of the function arguments into the local scope of a function. However, if an unscoped variable is called, it is searched first in argument scope and then local scope.

About creating functions by using tags

You use the cffunction tag to define a UDF in CFML. The cffunction tag syntax has the following features and limitations:

  • Developers who have a background in CFML or HTML, but no scripting or programming experience are more familiar with the syntax.

  • You can include any ColdFusion tag in your function definition. Therefore, you can create a function, for example, that accesses a database.

  • You can embed CFScript code inside the function definition.

  • The cffunction tag provides attributes that enable you to easily limit the execution of the tag to authorized users or specify how the function can be accessed.

The following code uses the cffunction tag to define the exponentiation function:

<cffunction name="twoPower" output=True> 
    <cfargument name="exponent"> 
    <cfreturn 2^exponent> 
</cffunction>

For more information on how to use the cffunction tag to define a function, see Defining functions by using the cffunction tag.

Defining functions by using the cffunction tag

The cffunction and cfargument tags let you define functions in CFML without using CFScript.

For information on ColdFusion components, see Building and Using ColdFusion Components. For more information on the cffunction tag, see the CFML Reference.

The cffunction tag function definition format

A cffunction tag function definition has the following format:

<cffunction name="functionName" [returnType="type" roles="roleList"  
        access="accessType" output="Boolean"]> 
    <cfargument name="argumentName" [Type="type" required="Boolean" 
        default="defaultValue">] 
    <!--- Function body code goes here. ---> 
    <cfreturn expression> 
</cffunction>

where brackets ([]) indicate optional arguments. You can have any number of cfargument tags.

The cffunction tag specifies the name you use when you call the function. You can optionally specify other function characteristics, as the following table describes:

Attribute

Description

name

The function name.

returnType

(Optional) The type of data that the function returns. The valid standard type names are: any, array, binary, Boolean, date, guid, numeric, query, string, struct, uuid, variableName, xml, and void. If you specify any other name, ColdFusion requires the argument to be a ColdFusion component with that name.

ColdFusion throws an error if you specify this attribute and the function tries to return data with a type that ColdFusion cannot automatically convert to the one you specified. For example, if the function returns the result of a numeric calculation, a returnType attribute of string or numeric is valid, but array is not.

roles

(Optional) A comma-delimited list of security roles that can run this method. If you omit this attribute, ColdFusion does not restrict user access to the function.

If you use this attribute, the function executes only if the current user is logged in using the cfloginuser tag and is a member of one or more of the roles specified in the attribute. Otherwise, ColdFusion throws an unauthorized access exception. For more information on user security, see Securing Applications.

output

(Optional) Determines how ColdFusion processes displayable output in the function body.

If you do not specify this option, ColdFusion treats the body of the function as normal CFML. As a result, text and the result of any cfoutput tags in the function definition body are displayed each time the function executes.

If you specify true or yes, the body of the function is processed as if it is in a cfoutput tag. ColdFusion displays variable values and expression results if you surround the variables and expressions with number signs (#).

If you specify false or no., the function is processed as if it is in a cfsilent tag. The function does not display any output. The code that calls the function is responsible for displaying any function results.

Use cfargument tags for required function arguments. All cfargument tags must precede any other CFML code in a cffunction tag body. Therefore, place the cfargument tags immediately following the cffunction opening tag. The cfargument tag takes the following attributes:

Attribute

Description

name

The argument name.

type

(Optional) The data type of the argument. The type of data that is passed to the function. The valid standard type names are any, array, binary, Boolean, date, guid, numeric, query, string, struct, uuid, and variableName. If you specify any other name, ColdFusion requires the argument to be a ColdFusion component with that name.

ColdFusion throws an error if you specify this attribute and the function is called with data of a type that ColdFusion cannot automatically convert to the one you specified. For example, if the argument type attribute is numeric, you cannot call the function with an array.

required

(Optional) A Boolean value that specifies whether the argument is required. If set to true and the argument is omitted from the function call, ColdFusion throws an error. The default value is false. The required attribute is not required if you specify a default attribute.

Because you do not identify arguments when you call a function, all cfargument tags that specify required arguments must precede any cfargument tags that specify optional arguments in the cffunction definition.

default

(Optional) The default value for an optional argument if no argument value is passed. If you specify this attribute, ColdFusion ignores the required attribute.

Note: The cfargument tag is not required for optional arguments. This feature is useful if a function can take an indeterminate number of arguments. If you do not use the cfargument tag for an optional argument, reference it by using its position in the Arguments scope array. For more information see Using the Arguments scope as an array.

Using a CFML tag in a user-defined function

The most important advantage of using the cffunction tag over defining a function in CFScript is that you can include CFML tags in the function. Thus, UDFs can encapsulate activities, such as database lookups, that require ColdFusion tags. Also, you can use the cfoutput tag to display output on the calling page with minimal coding.

Note: To improve performance, avoid using the cfparam tag in ColdFusion functions. Instead, use the cfset tag.

The following example function looks up and returns an employee department ID. It takes one argument, the employee ID, and looks up the corresponding department ID in the cfdocexamples Employee table:

<cffunction name="getDeptID" > 
    <cfargument name="empID" required="true" type="numeric"> 
    <cfset var cfdocexamples=""> 
    <cfquery dataSource="cfdocexamples" name="deptID"> 
        SELECT Dept_ID 
        FROM Employee 
        WHERE Emp_ID = #empID# 
    </cfquery> 
    <cfreturn deptID.Dept_ID> 
</cffunction>

Rules for function definitions

The following rules apply to functions that you define using CFScript or the cffunction tag:

  • The function name must be unique. It must be different from any existing variable, or UDF, except that you can use the ColdFusion advanced security function names.

  • You can have a user-defined function with the same name as a built-in function for a CFC but not for CFM.

  • You cannot use the following names to create user-defined functions:

    • writedump

    • writelog

    • location

    • throw

    • trace

  • The function name must not start with the letters cf in any form. (For example, CF_MyFunction, cfmyFunction, and cfxMyFunction are not valid UDF names.)

  • You cannot redefine or overload a function. If a function definition is active, ColdFusion generates an error if you define a second function with the same name.

  • You cannot nest function definitions; that is, you cannot define one function inside another function definition.

  • The function can be recursive, that is, the function definition body can call the function.

  • The function does not have to return a value.

You can use tags or CFScript to create a UDF. Each technique has advantages and disadvantages.