5. Interchange Perl Objects
You can access all objects associated with the catalog and the user settings with opcode restrictions based on the standard Perl module Safe.pm. There are some unique things to know about programming with Interchange.
Under Safe, certain things cannot be used. For instance, the following can not be used when running Safe:
$variable = `cat file/contents`;
The backtick operator violates a number of the default Safe opcode restrictions. Also, direct file opens can not be used. For example:
open(SOMETHING, "something.txt") or die;
This will also cause a trap, and the code will fail to compile. However, equivalent Interchange routines can be used:
# This will work if your administrator doesn't have NoAbsolute set $users = $Tag->file('/home/you/list'); # This will always work, file names are based in the catalog directory $users = $Tag->file('userlist');
The following is a list of Interchange Perl standard objects are:
$CGI
-
This is a hash reference to %CGI::values, the value of user variables as submitted in the current page/form. To get the value of a variable submitted as
<INPUT TYPE=hidden NAME=foo VALUE=bar>
-
use
<% $Document->write("Value of foo is $CGI->{foo}"); %>
-
Remember, multiple settings of the same variable are separated by a NULL character. To get the array value, use $CGI_array.
$CGI_array
-
This is a hash reference to %CGI::values_array, arrays containing the value or values of user variables as submitted in the current page/form. To get the value of a variable submitted as
<INPUT TYPE=hidden NAME=foo VALUE='bar'> <INPUT TYPE=hidden NAME=foo VALUE='baz'>
-
use
<% = "The values of foo are", join (' and ', @{$CGI_array->{'foo'}}) %>
-
Remember, multiple settings of the same variable are separated by a NULL character. To get the array value, use $CGI_array.
$Carts
-
A reference to the shopping cart hash $Vend::Session->{carts}. The normal default cart is "main". A typical alias is $Items.
Shopping carts are an array of hash references. Here is an example of a session cart array containing a main and a layaway cart.
{ 'main' => [ { 'code' => '00-0011', 'mv_ib' => 'products', 'quantity' => 1, 'size' => undef, 'color' => undef }, { 'code' => '99-102', 'mv_ib' => 'products', 'quantity' => 2, 'size' => 'L', 'color' => 'BLUE' } ], 'layaway' => [ { 'code' => '00-341', 'mv_ib' => 'products', 'quantity' => 1, 'size' => undef, 'color' => undef } ] }
-
In this cart array, $Carts->{main}[1]{code} is equal to 99-102. Normally, it would be equivalent to $Items->[1]{code}.
$Config
-
A reference to the $Vend::Cfg array. This is normally used with a large amount of the Interchange source code, but for simple things use something like:
# Allow searching the User database this page only $Config->{NoSearch} =~ s/\buserdb\b//;
-
Changes are not persistent -- they are reset upon the next page access.
%Db
-
A hash of databases shared with the [mvasp tables="foo"] parameter to the tag call. Once the database is shared, it is open and can be accessed by any of its methods. This will not work with SQL unless AllowGlobal is set for the catalog.
To get a reference to a particular table, specify its hash element:
$ref = $Db{products};
-
The available methods are:
# access an element of the table $field = $ref->field($key, $column); # set an element of the table $ref->set_field($key, $column_name, $value); # atomic increment of an element of the table $ref->inc_field($key, $column_name, 1); # see if element of the table is numeric $is_numeric = $ref->numeric($column_name); # Quote for SQL query purposes $quoted = $ref->quote($value, $column_name); # Check configuration of the database $delimiter = $ref->config('DELIMITER'); # Find the names of the columns (not including the key) @columns = $ref->columns(); # Insert the key column name unshift @columns, $ref->config('KEY'); # See if a column is in the table $is_a_column = defined $ref->test_column($column_name); # See if a row is in the table $is_present = $ref->record_exists($key); # Create a subroutine to return a single column from the table $sub = $ref->field_accessor($column); for (@keys) { push @values, $sub->($key); } # Create a subroutine to set a single column in the database $sub = $ref->field_settor($column); for (@keys) { $sub->($key, $value); } # Create a subroutine to set a slice of the database $sub = $ref->row_settor(@columns); for (@keys) { $sub->($key, @values); } # Retrurn a complete array of the database (minus the key) @values = $ref->row($key); # Retrurn a complete hash of the database row (minus the key) $hashref = $ref->row_hash($key); # Delete a record/row from the table $ref->delete_record($key);
%Sql
-
A hash of SQL databases that you shared with the [mvasp tables="foo"] parameter to the tag call. It returns the DBI database handle, so operations like the following can be performed:
<% my $dbh = $Sql{products} or return HTML "Database not shared."; my $sth = $dbh->prepare('select * from products') or return HTML "Couldn't open database."; $sth->execute(); my @record; while(@record = $sth->fetchrow()) { foo(); } $sth = $dbh->prepare('select * from othertable') or return HTML "Couldn't open database."; $sth->execute(); while(@record = $sth->fetchrow()) { bar(); } %>
-
This will not work with unless AllowGlobal is set for your catalog.
$DbSearch
-
A search object that will search a database without using the text file. It is the same as Interchange's db searchtype. Options are specified in a hash and passed to the object. All multiple-field options should be passed as array references. Before using the $DbSearch object, it must be told which table to search. For example, to use the table foo, it must have been shared with [mvasp foo].
There are three search methods: array, hash, and list.
array Returns a reference to an array of arrays (best) hash Returns a reference to an array of hashes (slower) list Returns a reference to an array of tab-delimited lines
-
\Example:
$DbSearch->{table} = $Db{foo}; $search = { mv_searchspec => 'Mona Lisa', mv_search_field => [ 'title', 'artist', 'price' ], mv_return_fields => [ 'title' ] }; my $ary = $DbSearch->array($search); if(! scalar @$ary) { return HTML "No match.\n"; } for(@$ary) {
$Document
-
This is an object that has several routines associated with it.
HTML $foo; # Append $foo to the write buffer array $Document->write($foo); # object call to append $foo to the write # buffer array $Document->insert($foo); # Insert $foo to front of write buffer array $Document->header($foo, $opt); # Append $foo to page header $Document->send(); # Send write buffer array to output, done # automatically upon end of ASP, clears buffer # and invalidates $Document->header() $Document->hot(1); # Cause writes to send immediately $Document->hot(0); # Stop immediate send @ary = $Document->review(); # Place contents of write buffer in @ary $Document->replace(@ary) # Replace contents of write buffer with @ary $ary_ref = $Document->ref(); # Return ref to output buffer
$Document->write($foo)
-
Write $foo to the page in a buffered fashion. The buffer is an array containing the results of all previous $Document->write() operations. If $Document->hot(1) has been set, the output immediately goes to the user.
$Document->insert($foo)
-
Insert $foo to the page buffer. The following example will output "123"
$Document->write("23"); $Document->insert("1"); $Document->send();
-
while this example will output "231"
$Document->write("23"); $Document->write("1"); $Document->send();
-
will output "231".
$Document->header($foo, $opt)
-
Add the header line $foo to the HTTP header. This is used to change the page content type, cache options, or other attributes. The code below changes the content type (MIME type) to text/plain:
$Document->header("Content-type: text/plain");
-
There is an optional hash that can be sent with the only valid value being "replace." The code below scrubs all previous header lines:
$Document->header("Content-type: text/plain", { replace => 1 } );
-
Once output has been sent with $Document->send(), this can no longer be done.
$Document->hot($foo)
-
If the value of $foo is true (in a Perl sense), then all $Document->write() operations will be immediately sent until a $Document->hot(0) is executed.
$Document->send()
-
Causes the document write buffer to be sent to the browser and empties the buffer. Any further $Document->header() calls will be ignored. Can be used to implement non-parsed-header operation.
$Document->review()
-
Returns the value of the write buffer.
@ary = $Document->review();
$Document->replace(@new)
-
Completely replaces the write buffer with the arguments.
$Document->ref()
-
Returns a reference to the write buffer.
# Remove the first item in the write buffer my $ary_ref = $Document->ref(); shift @$ary_ref;
HTML
-
Writes a string (or list of strings) to the write buffer array. The call
HTML $foo, $bar;
-
is exactly equivalent to
$Document->write($foo, $bar);
-
Honors the $Document->hot() setting.
$Items
-
A reference to the current shopping cart. Unless an Interchange [cart ...] tag is used, it is normally the same as $Carts->{main}.
$Scratch
-
A reference to the scratch values ala [scratch foo].
<% $Scratch->{foo} = 'bar'; %>
-
is equivalent to:
[set foo]bar[/set]
$Session
-
A reference to the session values ala [data session username].
<% my $out = $Session->{browser}; $Document->write($out); %>
-
is equivalent to:
[data session browser]
-
Values can also be set. If the value of [data session source] needed to be changed, for example, set:
<% $Session->{source} = 'New_partner'; %>
$Tag
-
Using the $Tag object, any Interchange tag including user-defined tags can be accessed.
IMPORTANT NOTE: If the tag will access a database that has not been previously opened, the table name must be passed in the ASP call. For example:
-
HTML style:
<HTML MV="mvasp" MV.TABLES="products pricing">
-
or
Named parameters:
[mvasp tables="products pricing"]
-
or
Positional parameters:
[mvasp products pricing]
-
Any tag can be called.
<% my $user = $Session->{username}; my $name_from_db = $Tag->data('userdb', 'name', $user ); $Document->write($name_from_db); %>
-
is the same as:
[data table=userdb column=name key="[data session username]"]
-
If the tag has a dash (-) in it, use an underscore instead:
# WRONG!!! $Tag->shipping-desc('upsg'); # Right $Tag->shipping_desc('upsg');
-
There are two ways of specifying parameters. Either use the positional parameters as documented (for an authoritative look at the parameters, see the %Routine value in Vend::Parse), or specify it all with an option hash parameter names as in any named parameters as specified in an Interchange tag. The calls
$Tag->data('products', 'title', '00-0011');
-
and
my $opt = { table => 'products', column => 'title', key => '00-0011', }; $Tag->data( $opt );
-
are equivalent for the data tag.
If using the option hash method, and the tag has container text, either specify it in the hash parameter body or add it as the next argument. The two calls:
$Tag->item_list( { 'body' => "[item-code] [item-field title]", });
-
and
$Tag->item_list( { }, "[item-code] [item-field title]")
-
are equivalent.
Parameter names are ALWAYS lower case.
$Values
-
A reference to the user form values ala [value foo].
<% $Document->write($Values->{foo}); %>
-
is equivalent to:
[value foo]
&Log
-
Send a message to the error log (same as ::logError in GlobalSub or global UserTag).
<% Log("error log entry"); %>
-
It prepends the normal timestamp with user and page information. To supress that information, begin the message with a backslash (\).
<% Log("\\error log entry without timestamp"); Log('\another error log entry without timestamp'); Log("error log entry with timestamp"); %>