Node.js ABC’s - F is for Functions

JavaScript, and thus Node.js, is at it's heart a functional programming language.  Functions are fully typed objects that can be modified, extended, and used as data objects. 

A function is a block of code designed to perform a specific task and is much the same as a procedure or subroutine in other programming languages.  Node.js takes advantage quite extensively of this capability allowing the developer to define code once and reuse it many times.

Function Syntax

A JavaScript function is defined with the "function" keyword, followed by a name, followed by parentheses.  A function name has the same rules as variables in that they can contain letters, digits, underscores, and dollar signs.  The code to be executed in the function is placed inside curly braces after the function declaration.

function name(param1, param2, ...) {
  code to be executed
}

As I mentioned above, functions can be used as data objects in code and other function calls.  When passing a function in as a parameter, one could do something like this

function passInFunc(f) {
  f("in myfunc");
}
function myfunc(param) {
  console.log(param);
}
passInFunc(myfunc);

When control hits the "passInFunc" function, the name of the "myfunc" function is not relevant.  this is where "Anonymous functions" come into play.  Anonymous functions are commonly used as callback parameters when using the Event Emitter pattern described in my article on Node.js Events.

An anonymous function can be declared either as a standalone variable

function passInFunc(f) {
   f("in myfunc");
}
var f = function(param) {
  console.log(param);
}
passInFunc(f);

or more concisely as

function passInFunc(f) {
  console.log("in myfunc");
}
passInFunc(function(param) {
  console.log(param);
});

It is this later format that you see used extensively in the Event Emitter pattern.  Anonymous functions have the drawback in that when exceptions are thrown, the debugger does not have a name context for the call stack which makes life a bit more difficult when debugging.

Function Parameters

To declare parameters, you simply list them in the parentheses separated by commas.  Since JavaScript is a loosely typed language, there is no checking of these parameters at runtime.  If a function is declared with two parameters, but the caller does not include them, the values of the parameters within the function will be set to undefined.  Within the scope of the function, parameters have local scope to the function, meaning that their values are not accessible from a global scope or from other functions.

function func(param1, param2, param3) {}
func("one");  // param2, and param3 are undefined
func("one", "two"); // param3 is undefined
func("one", "two", "three"); // all parameters are defined

Function Return Values

Functions can include return statements.  When a return statement is reached, the function will stop executing and control will be returned to the code after the statement that invoked the function call. To return a status back to the caller, the return statement can take an optional value parameter which the caller can use to make logic decisions.

function add(a, b) {
  return a+b;
}
var sum = add(1,2)  // the sum variable will contain the value 3.

Function Invocation

To cause the function to execute, you must include the () operator after the function name.  Referencing just the function name refers to the function object. 

function myfunc(param) { }
# f contains the myfunc object
var f = myfunc;

# f contains the return value from the myfunc 
var f = myfunc(param);

Function Scope

When a function is called, a new variable scope is created.  Variables declared in the calling scope are available to the function, but variables declared within the new function scope are not available when the function completes it's processing and returns.

var best_language = "JavaScript";
function print_best() {
  console.log(best_language);
  best_language = "c++";
  console.log(best_language);
}
print_best();
console.log(best_language);

The above code will print the following to the console

JavaScript
c++
JavaScript

Combining scope with anonymous functions can yield some interesting ways to do work with private variables that disappear when the anonymous function exits.

Updated Jun 06, 2023
Version 2.0

Was this article helpful?

3 Comments

  • Johnny_Schmidt_'s avatar
    Johnny_Schmidt_
    Historic F5 Account
    The statement "but variables declared within the new function scope are not available when the function completes it's processing and returns." is not 100% true when you consider closures :)
  • So, I created a function (getDG(id) that then calls an icontrol method, with the attached callback. When I use the function, the return value is not set, because the callback hasn't been completed. Any way to solve this problem?