Next:
Text::Wigwam::Library::Assignment
Previous:
Text::Wigwam::Config
 [Table of Contents][Text::Wigwam Index]

Text::Wigwam::Globals



NAME

Text::Wigwam::Globals - a stacks management database

About

This module manages all globals data for Wigwam.

Description

The features provided by this module can be used by directive handlers to pass data and state information to other directive handlers within a common scope, such as with #if, #elsif, #else, #given, and #when. It also offers a means to affect process control, which is essential for coding directives such as #break, #continue, #return, and #exit. Child templates always inherit the globals object from their parent template, so it can can be useful as a means for sharing data among templates.

Declaring globals

Globals are declared by calling one of the following methods, where scope is the name of the scope with which to associate this global; TEMPLATE, BLOCK, GLOBAL, or LOCAL; name is an arbitrary ID by which the global is to be referenced; and default is the default value given to this global upon entering a new scope.

new_global( scope, name, default )
To set a generic (non-interrupt) global, use this method.
new_eflag( scope, name, default )
Use this method to declare an eflag interrupt that does not return a value, such as with #break, and #continue.
new_subst( scope, name, default )
Use this method to declare an eflag interrupt that returns a value, such as with #exit, and #return.
new_fatal( scope, name, default )
Use this method to declare a global if the interrupt is fatal.

Accessing globals

set_global( name, value )
Sets the value of the global, name to value and returns value.
get_global( name )
Returns the value of the global, name.
add_global( name1, name2, ... )
Adds one scope level to each specified global and sets their default value.
del_global( name1, name2, ... )
Deletes one scope level to each specified global and restores their previous value.
inc_scope( scope )
Push the default values into all stacks within the specified scope, thereby incrementing the scope of all of those globals.
dec_scope( scope )
Pop all stacks within the scope, thus restoring all of those globals to their previous values.
push_global( name, value )
Performs an add_global function on name, followed by a set_global function on name using value, and returns value.
eflag( )
Returns true if the engine was forced into passive mode by an eflag enabled global.
global_exists( name )
Returns the scope of the name global, or undef if it is not defined.
kill_global( name1, name2,... )
Removes a global, or a list of globals. (rarely needed)
snapshot
Returns a deep copy of the global object's data structure for debugging purposes.

Scopes

BLOCK scope

BLOCK scope is attributed on a per-argument basis in a directive's arguments prototype:

 use Text::Wigwam::Const qw( SCALAR ANY BLOCK );
 sub _proto_if   { [ SCALAR, ANY|BLOCK ] }
 sub _proto_elsif{ [ SCALAR, ANY|BLOCK ] }
 sub _proto_else { [ ANY|BLOCK ] }

Whenever a directive argument given the BLOCK attribute is invoked, a new scope is generated (a new default value is pushed onto the stacks) for all globals within the BLOCK scope.

As indicated in the preceding example, the directives #if, #elsif, and #else make use of the BLOCK scoped global, 'Do_else' to maintain state.

The BLOCK scoped global 'Do_else' is pre-declared in the module init routine, like so:

 sub init_lib {
    $_[0]->new_global( BLOCK => q/Do_else/ );
 }

TEMPLATE scope

TEMPLATE scope is like BLOCK scope in that all variables declared as such are updated as a whole. TEMPLATE scoped globals are refreshed each time an external template is processed.

TEMPLATE scope globals must be pre-declared by invoking the new_global method, using the format:

 $API->new_global( 'TEMPLATE', name, default );

As an example, the #stop directive, when invoked, uses the TEMPLATE scoped 'Stop' global to halt further processing of a template and return control over to its parent.

 sub _proto_stop { [ ] }
 sub _stop { $_[0]->set_global( Stop => 1 ); return }

 # module init routine follows:
 sub init_lib {
    $_[0]->new_eflag( TEMPLATE => q/Stop/ );
 }

LOCAL scope

Declaring LOCAL scoped globals can be done within a module init routine by calling the new_global method, using the format:

 $API->new_global( 'LOCAL', name, default );

However, LOCAL scoped globals need not be pre-declared unless a default value other than undef is desired.

LOCAL scope is effected by providing a list of global names in a second array reference within the directive's prototype. If a previously undeclared global appears in this list, then a stack will automatically vivified using a default value of undef.

 use Text::Wigwam::Const qw( STRING );
 sub _proto_given { [STRING, STRING], [qw/When Default/] }

In the preceding example, the engine will push a new default value onto the When and Default stacks before calling the directive handler. Once the directive handler has completed execution, the Wigwam engine restores those globals' original values by popping their stacks.

 sub _proto_bazz{ return( [ ], [ 'bazzvar' ] ); }

Assuming bazzvar was never pre declared using new_global, it would be vivified for you by the Wigwam engine, in essence like this:

 $API->new_global( 'LOCAL', 'bazzvar' );

GLOBAL scope

GLOBAL scope globals must be pre-declared by calling the new_global method, using the format:

 $API->new_global( 'GLOBAL', name, default );

The Wigwam engine never generates a new GLOBAL scope. Any global declared with GLOBAL scope will retain its value until altered by set_global or until all tokens in all templates are exhausted.

The GLOBAL scoped _DIE global is the only global inherently declared by Wigwam. It is declared thusly:

 $API->new_fatal( 'GLOBAL', '_DIE' );

Because it's declared with GLOBAL scope, all processing of the current template and parent templates (if any) will cease if its value becomes true.

The API sets the _DIE global's value to true upon invocation of the exception method.