Tải bản đầy đủ (.pdf) (72 trang)

Tài liệu Exploring XSLT Processing Options Within PHP docx

Bạn đang xem bản rút gọn của tài liệu. Xem và tải ngay bản đầy đủ của tài liệu tại đây (2.07 MB, 72 trang )

Blazing Site Performance
Using Objects and Sessions
MARCH 2003
www.phparch.com
VOLUME II - ISSUE 3
Exploring XSLT ProcessingExploring XSLT Processing
Options Within PHPOptions Within PHP
Turn XML into HTML with
various proven methods
Plus:
Tips&Tricks, Book Reviews, Product Reviews
and much more..
Web-Free PHP: Web-Free PHP:
Using PHP's CLI InterpreterUsing PHP's CLI Interpreter
Creating an RSS Client With PHP
Beauty and Brains:
Using Flash's ActionScript, XML and
PHP for Easy Multi-tier Solutions
FreeTrade:
A PHP-Based E-Commerce Solution
The Magazine For PHP Professionals
php|architect
As PHP’s importance grows on the IT
scene—something that is happening every
day—it’s clear that its true capabilities go
well beyond what it’s being used for
today. The PHP platform itself has a lot of
potential as a general-purpose language,
and not just a scripting tool; just its basic
extensions, even discounting repositories
like PEAR and PECL, provide a high-


quality array of functionality that most of
its commercial competitors can’t afford
without expensive external components.
At php|a, we’ve always felt that our mis-
sion is not limited to try our best to pro-
vide the PHP community with a publica-
tion of the highest possible quality. We
think that our role is also that of reinvest-
ing in the community that we serve in a
way that leads to tangible results.
To that end, this month we’re launching
the php|architect Grant Program, a new
initiative that will see us award two
$1,000 (US) grants to PHP-related proj-
ects at the end of June.
Participating to the program is easy. We
invite all the leaders of PHP projects to
register with our website at
and submit
their applications for a grant. Our goal is
to provide a financial incentive to those
projects that, in our opinion, have the
opportunity to revolutionize PHP and its
position in the IT world.
In order to be eligible for the Grant
Program, a project must be strictly related
to PHP, but not necessarily written in PHP.
For example, a new PHP extension written
in C, or a new program in any language
that lends itself to using PHP in new and

interesting ways would also be acceptable.
The only other important restriction is that
the project must be released under either
the LGPL, the GPL or the PHP/Zend
license. Thus, commercial products are
not eligible.
Submit Your Project Today!
Visit http://www
.phparch.com/grant
for more information
Introducing
the php|architect Grant
Program
3
IINNDDEEXX
Departments
php|architect
Features
12 Shell Scripting with PHP (PHP CLI)
by Jayesh Jain
19 FreeTrade, e-commerce for
developers
by Vladan Zirojevic
32 Blazing Site Performance Using
Objects and Sessions
by Peter Moulding
41 Writing an RSS Aggregator With
PHP
by Marco Tabini
49 Exploring XSLT Processing Options

Within PHP
by Stuart Herbert
58 The Story of theBouncing Ball and
XML
by Sam Smith
5 EDITORIAL RANTS
7 NEW STUFF
8 REVIEW
TUTOS
29 REVIEW
phpLens
67 TIPS & TRICKS
by John Holmes
70 BOOK REVIEWS
PHP Professional Projects
Professional PHP Web Services
72 exit(0);
Let Me Throw The First Stone
TABLE OF CONTENT
March 2003 · PHP Architect · www.phparch.com
Technologies Ltd.
Visit
www.zend.com
for evaluation version and ROI calculator
Zend Performance Suite
Reliable Performance Management for PHP
Serve More.
With Less.
The designers of PHP offer you the full spectrum of PHP solutionsThe designers of PHP offer you the full spectrum of PHP solutions
5

EEDDIITTOORRIIAALL RRAANNTTSS
php|architect
Volume II - Issue 3
March, 2003
Publisher
Marco Tabini
Editor-in-Chief
Brian K. Jones
brian@phpar
ch.com
Editorial Team
Arbi Arzoumani
Brian Jones
Peter James
Marco Tabini
Graphics & Layout
Arbi Arzoumani
Administration
Emanuela Corso
Authors
Stuart Herbert, Jayesh Jain, Peter Moulding,
Dave Palmer, Sam Smith, Marco Tabini,
Vladan
Zirojevic
php|architect (ISSN 1705-1142) is published twelve times a year by Marco
Tabini & Associates, Inc., P.O. Box. 3342, Markham, ON L3R 6G6,
Canada.
Although all possible care has been placed in assuring the accuracy of the
contents of this magazine, including all associated source code, listings
and figures, the publisher assumes no responsibilities with regards of use

of the information contained herein or in all associated material.
Contact Information:
General mailbox:
Editorial:
Subscriptions:
Sales & advertising:
Technical support:
Copyright © 2002-2003 Marco Tabini & Associates,
Inc. — All Rights Reserved
Awwww Yeah....
These were the first words I uttered after accept-
ing an invitation to take the reins as editor-in-chief
for php|architect magazine. About 3 weeks later,
Marco, our fearless publisher, reminded me that I
still had to write the ‘Editor’s Rants’ aritcle. This is
essentially what you see at the beginning of seem-
ingly every magazine ever published. ‘Letter from
the Editor’, ‘From the Editor’s Desk’. Whatever
you want to call it – it’s all the same – and as far
as I can tell, it’s all pretty meaningless.
Over the past few weeks I’ve read no fewer than
30 of these articles, trying to get a clue as to this
article’s purpose in life. I read magazines covering
every conceivable topic, formal and informal,
from the politically perfect to the underground,
grass-roots publications and found that these edi-
torial columns all seem to accomplish a single
goal: to make the editor look like the most preten-
tious, micro-managing, self-important species
ever to roam the earth. Did these people lack

attention as children or something? The more I
read, the more I came under the suspicion that
the species I had been recruited to emulate might
be... well... not my cup of tea. I also couldn’t help
but ask myself out loud on several occasions, ‘who
reads these things?’
But alas, this is not meant to be an editorial on
editorials (or a ‘metatorial’ if you will). If I’m
forced to partake in this charade, then I will
endeavor to make it something useful. It so hap-
pens that, being my first month at the helm, I
have plenty to share with whoever is reading this,
specifically with regard to my vision for php|a over
the coming months. I do welcome comments on
all of this, by the way: brian@phpar
ch.com
I’ll break my thoughts down into sections cover-
ing our current status, the near future, and the
longer haul.
Where We Are
From rather humble beginnings, I think php|a has
accomplished much with regard to the vision of
its creator – Marco Tabini. This vision was two-
fold, so I’ll cover them seperately.
First, php|architect has become known as a rep-
utable resource for well written, well edited docu-
mentation covering all aspects of PHP develop-
ment. While I will not bore you with the laborious
details of how challenging it can be to combine
EDITORIAL

March 2003 · PHP Architect · www.phparch.com
March 2003 · PHP Architect · www.phparch.com
6
EDITORIAL
editorial precision with technical savvy, I will say
that this process and this accomplishment both
fall under the heading of ‘non-trivial’ tasks.
Certainly a very large thank you is in order for
each of the many authors who collaborate with
our editorial staff each month. Working together,
we have been able to overcome challenges rang-
ing from differences in opinion to differences in
time zone, culture, and even language. Their time,
patience, and hard work is very much appreciated.
Second, php|architect continues to make great
strides in establishing itself as a voice for the PHP
developer community, as well as an advocate for
the deployment, evolution, and progress of the
PHP platform. We haven’t sought to glorify the
state of PHP, nor to shun its more proprietary
peers. Instead, we try to maintain a realistic focus
on the use of PHP in production environments.
We also take a decidedly optimistic view of the
future of PHP, which at times finds itself at odds
with what some of the larger names in communi-
ty might have in mind. Nevertheless, we feel that
the opinions of our authors, the editors, and the
community are an important part in shaping any
project which lists ‘open development’ as a goal.
The Months Ahead

The months ahead will continue to build upon
the foundation laid in the first months of our exis-
tence. The main goals in the immediate future
focus largely on quality and efficiency – in other
words, bringing you even better quality content
whithout breaking our necks or collapsing from
exhaustion in the process. To that end, there have
already been improvements, tweaks and hacks put
in place.
First, we’ve convinced a one-time volunteer edi-
tor, Peter James, to come on staff as a full-fledged
editor. Peter has proven himself to be a tireless
worker and a great collaborator. He has already
done wonderful work here, and he will undoubt-
edly leave an indelible mark upon the pages of
php|architect over the coming months.
Second, as further proof of our commitment to
the community at large, we are very proud to
announce this month the launch of a grant pro-
gram to aid fledgling (or not-so-fledgling) projects
to continue to progress and bring PHP into the
places where no man has gone before – or at least
the road less traveled. See this months pages and
the php|architect website for more details.
The Longer Term
Looking out and attempting to predict our
future at such an early stage, while fun, is proba-
bly also an exercise in futility. All that can be said
for sure is that there are plans of great size and
great number. More huge ideas are born every

day. Surprisingly, only some of the ideas belong to
us ‘staffers’. The rest come from you!
So far, most of the changes and adjustments
we’ve made, and some which we’re working on,
have come directly from our readers. We’re all
constantly monitoring emails, looking in the
php|architect forums, and even monitoring the
PHP mailing lists in search of yet another unful-
filled need that we might be able to lend a hand
to. Please keep these requests coming! There is
hardly a greater compliment that can be paid to a
publication than constructive feedback.
In Conclusion
So now that I’ve firmly planted the image in
your head of an SUV-driving, tie-wearing, clean-
shaven, pretty boy editor sitting in his overstuffed
couch with a $4.00 cup of coffee and a laptop, let
me assure you that while I take the publication
and my work seriously, I don’t take myself all that
seriously at all. The reality is that I have hardly a
clue how I got here. I can only be thankful for
Marco’s obvious and complete insanity in choos-
ing me for this post.
I am grateful both to Marco for this opportunity,
those authors with whom I’ve had (and continue
to have) the distinct honor of collaborating, and
the many readers who have offered their feedback
and encouragement.
Until next month...
NNEEWW SSTTUUFFFF

NEW STUFF
PHP 4.3.1 Released
The PHP Group has announced the release of
version 4.3.1 of the PHP interpreter. The new
release addresses a bug in the CGI version of the
interpreter that invalidates the effectiveness of the
—enable-force-cgi-redirect compile-time switch.
This, in turn, makes PHP-CGI susceptible to out-
side hacking attacks that could result in the execu-
tion of arbitrary PHP code.
For more information, visit
/>ADODB 3.20 Available
A new version of ADODB, the popular and effi-
cient database abstraction library, has been
released by its maintainer, PHPEverywhere blog
author John Lim.
ADODB 3.20 supports several new features,
including abstracted capabilities for creating
tables and indexes, although this functionality is
still considered in its alpha stage.
According to its website, available at
/>, ADODB is twice
as fast as PEAR-DB and 10% faster than PHP-Lib
Nova: A P2P Client In PHP
The Nova Project has released Nova, a peer-to-
peer application compatible with the popular
GNUtella file-sharing network. Nova is written
entirely in PHP using the PHP-GTK extension, and
provides an excellent example of how PHP can be
used to develop application outside the Web

space.
Nova, which is based on the GnucDNA library,
currently supports only basic functionality and is
only compatible with Windows. You can find more
information at the project’s homepage
(https://sour
ceforge.net/projects/novap2p/).
Zend Releases Studio 2.6
PHP powerhouse Zend Technologies has release
version 2.6 of their Zend Studio IDE. The new
application includes several bug fixes, as well as
new features, such as CVS
integration, advanced
project management
capabilities and improved
performance on all plat-
forms.
The Zend Studio 2.6 is
priced starting at $195
(US). More information is
available from the Zend
website at
http://www
.zend.com.
Introducing the php|architect
Affiliate Program
Earlier this month, we proudly announced the
introduction of our new affiliate program, which
pays a commission for each purchase made
through our website by visitors referred from on of

our partners.
Participation in the program is free, and open to
all websites, without any minimum requirements.
You can find more information on the php|a web-
site at https://www
.phparch.com/afflogin.php.
PHP Conference in Montréal
PHP Québec will hold their first PHP conference
in the city of Montréal on March 20 and 21.
Speakers at the event include a who’s who of the
PHP community, including Zeev Suraski, Andrei
Zmeivski and Rasmus Lerdorf. php|architect will
also be there and our own Marco Tabini will give
a presentation on PHP-based business and our
experience in the world of electronic publishing.
For more information, you can visit the confer-
ence’s web site at
/>.
March 2003 · PHP Architect · www.phparch.com
7
php|a
RREEVVIIEEWW
REVIEWS
March 2003 · PHP Architect · www.phparch.com
A
few days before writing this review (which, at the
time, was another review), I had something of an
epiphany. I was on the phone with a client, boast-
ing about how organized I am, when Arbi walked by
my office and laughed a typical “I know better” at

me. My ego was bruised, so I wrote down a list of
ways that I am organized on a piece of paper. I’d
gladly show you that piece of paper if I hadn’t, er,
temporarily misplaced it.
As the saying goes, if you can’t blame anyone but
yourself, blame the process. After all, a person can
only do so much on his own. I set out to find a
decent groupware application that would allow me
to get more organized and, at the same time, better
manage the office’s internal processes (formatting
Arbi’s hard drive would have been a bonus, but I
couldn’t find any applications capable of the perfect
union between a calendar and that).
After a bit of searching, I came across TUTOS,
which stands for The Ultimate Team Organization
Software. Created by German developer Gero
Kohnert as an internal application for his previous
employer, TUTOS has evolved into a complex group-
ware application that is used by the likes of Siemens.
Best of all, it’s written entirely in PHP.
Reviewed For You
TUTOS
T
he
U
ltimate
T
eam
O
rganization

S
oftware
By Marco Tabini
The Cost:
Free (released under the GPL)
Requirements:
Apache
You wil need one of these Databases
PostgreSQL Database
MySQL Database (MySQL-3.23.21-1.i386.rpm)
Oracle Database
Borland Interbase 5
PHP 4 (minimum php4.1)
Download Page:
/>Home Page:

Developer Background:
“I started a first TUTOS like system for my former compa-
ny back in 1997 or so. They still use it alot to have an
overview of all their customers , software installations and
different products and to support the internal Quality
Managment (ISO9600). After leaving this company I start-
ed TUTOS, an enhanced system based on the same
thoughts with a lot more features. On TUTOS I'm working
now for more than a year and after making a first installa-
tion in my department at my current employer I think it is
time to release it to the public, giving something back to
the Open Source Community.”
8
REVIEWS

March 2003 · PHP Architect · www.phparch.com
9
TUTOS
Groupware, Anyone?
TUTOS is a complete groupware application in every
sense. It includes a calendar, a contact management
system, a bug tracking system, a product/project repos-
itory, mail capabilities, a time tracking system, an
invoicing system, and much more. The system is also
multilingual, supporting about fifteen languages right
out of the proverbial box.
For companies whose groups work in different parts
of the world, TUTOS includes the ability to specify time-
zone information for each user profile, so that every-
thing remains properly synchronized and meaningful
to all users.
Finally, the system includes a “watchlist” mechanism
that makes it possible to remain up-to-date, via e-mail,
on changes to systems such as the bug tracking data-
base or the calendar schedule. Even for a small work-
group, this “active notification” approach is a very
important feature, particularly when the members of a
team do not all work in the same office.
User Interface
and Security Features
The system implements a very fine-grained permission
system, thus ensuring that the administrators have
every way to control access to each function. In addi-
tion, a TUTOS administrator has prompt access to all of
the security settings, including his/her own.

TUTOS features a colourful and easy-to-use interface
that is sure to please both lovers and haters of GUIs. As
Figure 1
REVIEWS
March 2003 · PHP Architect · www.phparch.com
10
TUTOS
you can see in Figure 1, only a minimal amount of
information is kept on the left-side frame menu, leaving
as much real estate as possible available for the system’s
actual functionality.
Documentation, Interoperability
and Limitations
It’s interesting to notice that the ultimate goal of the
TUTOS project is to create a portable groupware sys-
tem whose interface can be written for a number of dif-
ferent platforms. As such, the development team has
put a large amount of work into the design of the
underlying data structures themselves. Naturally, that’s
good news because, in addition to the PHP interface,
other interfaces are likely to be developed. In fact, a
KDE/Gnome version is currently in the works.
From a portability perspective, TUTOS’ PHP interface
doesn’t use any proprietary components that are tied
to a particular architecture, and it supports several dif-
ferent database systems, including MySQL, PostgreSQL
and Oracle.
In my opinion, the system could use a bit more work
as far as interoperability is concerned. In particular, I
think that attention should be paid to integration with

outside services like LDAP and/or Microsoft Exchange.
This could help make TUTOS a more appealing solution
for larger organizations.
Since the entire system is based on PHP, however, it
should be relatively simple to expand its functionality to
include whatever elements one needs. The code is
quite clean and well documented, so it forms a good
foundation on which to build a more complex and spe-
cialized application.
TUTOS includes a good deal of documentation. For
the developer, the TUTOS website provides a detailed
analysis of all the data structures and logical organiza-
tion of the system, as well as an API reference and an
installation guide. As for the end user, they get a com-
plete contextual help system, shown in Figure 2, that
includes an accurate description of what each individ-
ual screen does.
Conclusion
Now that I have TUTOS running on my computer, I
can say with confidence that I feel more organized. As
with all groupware systems, the trick to getting TUTOS
into an organization is to stimulate user acceptance.
After all, your average user is normally not keen on try-
ing new things, and prefers instead to stick with the
application that he or she has learned to use well.
TUTOS represents an excellent groupware solution
that is easy to learn and offers a wide array of function-
ality. It is organized in a logical fashion, provides lots of
documentation, and its PHP codebase makes it easily
extensible.

php|a
Figure 2
TUTOS doesn't use any
proprietary components that
are tied to a particular
architecture.

12
FFEEAATTUURREESS
Introduction
With the introduction of version 4.2, PHP started sup-
porting a new SAPI (Server Application Programming
Interface) called CLI (Command Line Interface). This
facility was introduced to help developers create small
shell applications with PHP that have no dependencies
on a web server.
In version 4.2.0, the CLI SAPI was experimental, and
had to be explicitly enabled using the —enable-cli
option when running ./configure. However, with
PHP 4.3.0, the CLI SAPI has been deemed stable and is
therefore enabled by default. It can be explicitly dis-
abled by specifying the —disable-cli option to
./configure.
Though it was technically always possible to create
independent shell-style scripts with PHP using a stand-
alone CGI interpreter, there are a few things that make
the new CLI SAPI an especially attractive and unique
tool:
- Unlike the CGI SAPI, no headers are written to
the output. Though the CGI SAPI provides a

way to suppress HTTP headers, there’s no equiv-
alent switch to enable them in the CLI SAPI.
- The CLI starts up in quiet mode by default,
though the -q switch is kept for compatibility so
that you can use older CGI scripts.
- The CLI does not change the working directory
to that of the script. (-C switch kept for compati-
bility)
- Three words: Plain text errors! (no HTML format-
ting).
In this article, we’ll discuss how to use PHP’s CLI fea-
ture to exploit the power of PHP from the command
line. We’ll assume that you have a fair understanding
of PHP and that PHP is installed and working properly
on your computer. Most of the examples in this tutori-
al were tested on a Windows platform (w2k, to be pre-
cise), but should work unaltered on a Linux box.
Shell SScripting wwith
PHP ((PHP CCLI)
By Jayesh Jain
PHP 4.3.0's new CLI SAPI improves greatly on the foundation laid by its CGI ancestor.
Take it for a spin – no web server required!
PHP Version: 4.3 and Above
O/S: Any
Additional Software: N/A
REQUIREMENTS
FEATURES
March 2003 · PHP Architect · www.phparch.com
FEATURES
March 2003 · PHP Architect · www.phparch.com

13
Shell Scripting with PHP (PHP CLI)
What is a PHP Shell Script?
The term ‘PHP shell script’ can cause some confusion
for those who are used to traditional UNIX-style shell
scripts. The reason for the confusion is that PHP, strict-
ly speaking, does not provide a traditional interactive
environment for command execution. Another source
of confusion is the fact that the name of the SAPI – ‘CLI’
is also an acronym used to refer to a UNIX shell, which
by definition is an interactive command execution envi-
ronment! Let’s clarify this right now by simply stating
that the PHP CLI is an interface to a PHP interpreter that
can be accessed via the command line - not an interac-
tive shell. In reality, ‘PHP shell scripts’ are just PHP
scripts that can be run from a command line or a cron
job (which will be discussed later in the article) in the
same fashion as a shell or PERL script.
A normal shell script consists of two main parts: the
very first line, which indicates the interpreter that
should be parsing the script, and the code to be exe-
cuted by the interpreter. Normally, the interpreter that
is specified is a UNIX shell, or some other interpreter,
like PERL. However, since the creation of a PHP inter-
preter which can be executed directly from a shell
(without the help of a web server), we can specify PHP
as the interpreter for our script, and then fill the file
with PHP code. For all you Windows users, PHP shell
scripts are just like batch (.bat) files in MS-DOS, but
with the power of the PHP programming language.

Finding Your PHP CLI
Output on my Windows machine of the php.exe in the
‘cli’ folder was:
PHP 4.3.0 (cli) (built: Dec 27 2002
05:34:00)
Copyright (c) 1997-2002 The PHP Group
Zend Engine v1.3.0, Copyright (c) 1998-
2002 Zend Technologies
Output on my machine of php.exe in the php root
folder was:
PHP 4.3.0 (cgi-fcgi), Copyright (c)
1997-2002 The PHP Group
Zend Engine v1.3.0, Copyright (c) 1998-
2002 Zend Technologies
This would indicate that the ‘php.exe’ file on my
machine in the php root folder is actually the old CGI.
For the reasons mentioned earlier comparing the CGI
and CLI interpreters, and because the title of this article
says ‘CLI’ in it and not ‘CGI’, I’ll be refraining from
using the CGI in the examples going forward. I just
wanted to point out a possible point of confusion
here... so on we go!
Getting Started
Let’s start with a small script (the most familiar one)
which simply prints the words “Hello World” to the
screen. Using your favorite text editor, create a text file
called “world.php” in your PHP folder and enter the fol-
lowing text.
Save the file, ensure that you have the PHP CLI exe-
cutable in your path, and run the following command

> php world.php
Surprised to see the output, ‘Hello World’ in the com-
mand prompt instead of the web browser? Welcome
to the other dimension of PHP!
Note: If you are using PHP version 4.2 (or the CGI
Version) you may have noticed that the following head-
er is also in the output:
X-Powered-By: PHP/4.2.3
Content-type: text/html
The PHP CGI version does that by default, which can
serve as an indicator that you’re using the CGI (in addi-
tion to cluing you in on the PHP version you’re run-
ning).
To suppress the HTTP headers and follow along with
the remaining examples, run the PHP CGI with the ‘-q’
command line flag.
> php -q world.php
Using the ‘-r’ option, you can also pass the PHP code
to be executed to the PHP CLI directly from the com-
mand line. For example:
> php -r ‘echo “Hello World\n”;’
Will output ‘Hello World’, the same exact message as
our earlier example. This is fine for small bits of code
you only want to execute once. Only as the code gets
larger will you need the power of a script.
You can redirect the output from any script to a file
by running:
> php world.php > outputfile
Linux and UNIX users can also redirect the script out-
put to another command by using the | (pipe opera-

tor). For example:
<?php
echo "Hello World\n";
?>
FEATURES
March 2003 · PHP Architect · www.phparch.com
14
Shell Scripting with PHP (PHP CLI)
> php world.php | wc -w
Will return the word count of the output (in this case,
it will output the number ‘2’).
Conversely, you can also send output from some
application or command to the php interpreter by
using the pipe operator, for example:
> someapp | php
This might be useful if ‘someapp’ outputs PHP code
which can be immediately executed by the interpreter
instead of adding the overhead of first writing to a file
and then calling the interpreter separately – which will
then also be subject to the added overhead of opening
and reading a file from disk.
Getting Interactive
PHP has always made it very easy to interact and trade
data with a user via the traditional browser interface.
Let’s have a look at how PHP’s ‘stream’ functions and
associated constants can extend this ease to the com-
mand line interface. There are three streams available
in PHP CLI. If you’re familiar with the corresponding
standard UNIX device names, you’ll be right at home
here, as these streams emulate the same functionality.

stdin (‘php://stdin’)
stdout (‘php://stdout’)
stderr (‘php://stderr’)
The following example will display “Hello World” in
the output window using the output stream.
This time, we’ll demonstrate how to use an input
stream. It will accept an input from the user, wait for
the user to press the Enter key and then display the
entered text.
The following example shows you how to output text
to an error stream.
<?
$stdin = fopen('php://stdin', 'r');
echo "Please Enter your Name: ";
$mystr = fgets($stdin,100);
echo "Your Name Is :\n";
echo $mystr;
fclose($stdin);
?>
<?
$stdout = fopen('php://stdout', 'w');
fwrite($stdout,"Hello World");
fclose($stdout);
?>
Figure 1
Why Do You Need A
PHP Shell Script?
- Shell scripts can take input from,
and send output to a user via
STDIN/STDOUT, a regular text file,

or even another command. In other
words, they’re very flexible.
- Shell scripts are a ‘quick and dirty’
way to create your own command-
line tools and applications.
- If you already use PHP for web
development, why learn another
language to write shell scripts?
- Shell scripts are commonly used to
automate day-to-day administration
tasks.
FEATURES
March 2003 · PHP Architect · www.phparch.com
15
Shell Scripting with PHP (PHP CLI)
To make accessing and moving data around in a shell
environment simpler, PHP has added the following
constants. Again, for UNIX users, these names should
look familiar. In UNIX, these typically map to the key-
board (STDIN) and the screen (STDOUT and STDERR)
by default.
Using Arguments in Scripts
Anyone who has experience writing shell or PERL
scripts would probably consider the PHP CLI complete-
ly useless if the scripts weren’t able to handle argu-
ments passed to it from the command line. The CLI
handles this with the use of the $argv and $argc vari-
ables.
All of the arguments passed to your script are stored
in a zero based global array variable $argv. Another

global variable, $argc, holds the number of argu-
ments passed to the script (everyone coming from a
C/C++ background, should be familiar with this prac-
tice). Here is the code, which displays the total num-
ber of arguments passed as well as the arguments:
<?
echo "Total argument passed are: $argc\n";

for( $i = 0 ; $i <= $argc –1 ; $i++)
{
echo "Argument $i : $argv[$i] \n";
}
?>
<?
$stderr = fopen('php://stderr', 'w');
fwrite($stderr,"There was an Error");
fclose($stderr);
?>
Figure 2
Constant Details
STDIN
An already opened stream to stdin. You don’t
have to open it with:
STDOUT
An already opened stream to stdout. You don’t
have to open it with:
STDERR
An already opened stream to stderr. You don’t
have to open it with:
Here is an example of how to use a stream with constants:

For users of version 4.2, you’ll need to add these addition-
al lines to the top of your script in order for the above
example to work:
define('STDIN',fopen("php://stdin","r"));
define('STDOUT',fopen("php://stdout","w")
define('STDERR',fopen("php://stderr","w")
<?
fwrite(STDOUT,"Hello World \n");
?>
$stderr = fopen('php://stderr', 'w');
$stdout = fopen('php://stdout', 'w');
$stdin = fopen('php://stdin', 'r');
FEATURES
March 2003 · PHP Architect · www.phparch.com
16
Shell Scripting with PHP (PHP CLI)
Assuming this is stored in a file argument.php you
could test this script by running:
> php argument.php arg1 arg2
Refer to Figure 2 for
sample output
Important : You can use $argc and $argv in the man-
ner described above only if you have both the
regis-
ter_globals
and
register_argc_argv
settings in
php.ini
set to ‘on’. As of PHP version 4.3,

regis-
ter_globals
is set to ‘off’ by default. You should do
your best to write your scripts so that they do not require
register_globals to be on, to avoid possible security issues
in your incoming form variables. You can still use
$argv
and
$argc
if
register_globals
is set to ‘off’. Just
use the following code:
Using External commands
in Scripts
In order to run any external command from the script,
we will have to use the php function
shell_exec
.
Shell_exec
will execute a command via the shell and
return complete output as a string.
For Linux/UNIX Users
As we’ve discussed, the PHP executable runs independ-
ently of the web server. An added benefit of using this
interface for your scripting is that it makes your scripts
more portable than using, say, ‘/bin/bash’. Using
‘#!/usr/bin/php’ at the top of your script will allow
you to invoke the PHP interpreter on a Linux machine,
and on Windows, this line will be skipped over to get to

the PHP code below. Now you can write in your famil-
iar Linux environment, and still deploy to Windows.
Tip: Don’t forget that Linux won’t let you do any-
thing until the script has its ‘execute’ bit set. Assuming
your script is called ‘testscript.php’, you can just ‘cd’ to
the directory where the script lives and type:
> chmod +x testscript.php
Once you have set the executable attribute, you can
execute the file like this:
> ./testscript.php
Also, don’t forget to add the PHP tags in the script
file, otherwise PHP will not interpret it properly. If
you’re stuck with the CGI version and want to suppress
the HTTP headers, use #!/usr/bin/php -q.
Similarly, you can also use any other PHP arguments.
Scheduling PHP Scripts
PHP scripts can be scheduled to run automatically with
the help of ‘cron’. Cron is the name of the standard
execution scheduling mechanism that enables UNIX
users to execute commands or scripts automatically at
some regular interval. A common use for it is to back-
up all of the file on the server, do some database
cleanup, or send emails to administrators about the
state of the system. Try typing ‘man cron’ or ‘man
crontab’ on your Linux system to learn more about
how to get your PHP scripts to run at regular intervals.
This can be an extremely valuable tool to developers
who need to do major data crunching without the user
in the browser being adversely affected. For example,
while it’s possible to have a user click a button which

triggers the collection of live network data coming
from remote LDAP, SNMP or other sources, grabbing
and manipulating this code to make it suitable for pres-
entation can really take some time. Why not poll these
sources in a cron job at regular intervals, store every-
thing to a database in a more friendly format, and have
the front end simply grab from the database in a more
‘bite size’ format. The possibilities are endless!
For Windows Users:
Configuring Windows to Execute
PHP Scripts
To run PHP scripts on your Windows machine, you’ll
need to associate the PHP files with the PHP interpreter.
To do this, open Windows Explorer, click on the tools
menu and select ‘folder options’. Click on the ‘File
Types’ tab and select the ‘New’ button. Type ‘.php’ in
as the file extension, and click OK.
<?
$command = "ls - al";
echo shell_exec($command);
?>
$argc = $_SERVER['argc'];
$argv = $_SERVER['argv'];
...using
PHP's CLI
interface makes your
scripts more portable
than using, say,
'
/bin/bash

'.
FEATURES
March 2003 · PHP Architect · www.phparch.com
17
Shell Scripting with PHP (PHP CLI)
Refer to Figure 3
Select the PHP entry in the ‘Registered File Types’ list
box, click the ‘Advanced’ button, click ‘new’ and type
‘Run’ in the Action box. In the ‘Application Used to
Perform Actions’ box, type C:\PHP\PHP.exe “%1”
%* (change the PHP path if it’s different on your
machine. Note that ‘%*’ is used to send any command
line arguments). Click ‘OK’, ‘OK’ again and then the
‘Close’ button. Your Windows machine is now config-
ured to run PHP Scripts. Just double click on any PHP
file in Windows Explorer to run it.
Refer to Figure 4
You can also register files with extension ‘.php3’ or
‘.php4’ in the same fashion mentioned above.
More Information
There are certain php.ini directives, which are over-
ridden by the CLI SAPI because they do not make sense
in shell environments:
a) html_errors = FALSE
As the output of the PHP CLI does not go to a brows-
er, there is no need to echo HTML tags hence this direc-
tive defaults to FALSE.
Figure 3
FEATURES
March 2003 · PHP Architect · www.phparch.com

18
Shell Scripting with PHP (PHP CLI)
b) implicit_flush = TRUE
All the output coming from output commands need
to be shown instantly and should not be cached. As a
result, this directive is defaulted to TRUE.
c) max_execution_time = 0 (unlimited)
Because the PHP runs in the shell environment and
often does tasks which take a longer time, the
max_execution_time is defaulted to unlimited.
d) register_argc_argv = TRUE
This setting is TRUE so that you can always have
access to the number of arguments passed to the script
($argc) and array of the actual arguments ($argv) in
the CLI SAPI.
Extensions
Now that you know all about the PHP CLI, use the fol-
lowing code examples , or make up some of your own,
to test the power of PHP and the CLI.
Sending Email in Scripts
The syntax used to send email is shown below. You can
skip the header part, as it is an optional parameter.
Using the MySQL Database in Your Scripts
You can connect to MySQL database exactly the same
way as you do in your normal php scripts except you
should not use HTML tags as the output is not sent to
the browser.
Here is a simple example, which connects to a
MySQL database and lists the username field for all
records in the user table.

Conclusion
In this article we have tried to show you the power of
the PHP CLI interface. I am sure you are now convinced
of PHP’s flexibility, and urge you to expand upon the
concepts discussed here. Certainly, this is an area that
will likely receive much attention as PHP evolves into a
more complete and mature language. Enjoy!
<?
mysql_connect("localhost","root","test");
mysql_select_db("mydatabase");
$query = "select username from user";
$searchresult = mysql_query($query);
while ($line = mysql_fetch_array
($searchresult))
{
print " $line[0] \n";
}
?>
<?
$username = "Jayesh Jain";
$useremail = "";
$message = "This is a message from
Administrator";
$subject = "System Message";
$headers = "MIME-Version: 1.0\r\n";
$headers .= "Content-type: text/html;
charset=iso-8859-1\r\n";
$headers .= "From: Administrator
<>\r\n";
$headers .= "To: Administrator

<>\r\n";
$headers .= "Reply-To: >\r\n";
$headers .= "X-Priority: 1\r\n";
$headers .= "X-MSMail-Priority: High\r\n";
$headers .= "X-Mailer: PHP on
someserver.com";
mail($useremail, $subject, $message,
$headers)
?>

About The Author ?>
Jayesh Jain is working as a consultant in Auckland, New Zealand. He
has several years of n-Tier development experience and is currently work-
ing with PHP to develop interactive client solutions. He has a passion for
Web development and in the spare time he likes to write articles. Contact
him at:
Click HERE To Discuss This Article
/>Figure 4
19
FFEEAATTUURREESS
E
-commerce applications are one of the most com-
mon requests web developers receive today. An e-
commerce solution should provide two different types
of functionality. Site visitors should see a fully-featured
online shop, while business owners should have an
easy-to-use back end administration system.
There are many open source e-commerce solutions
with many good features, and I have tried almost all of
them. Specific to PHP there are a few cool scripts

which will help you accomplish everything needed to
set up an online store and to maintain it easily.
Applications like osCommerce (om
-
merce.com), FishCart (),
and phpShop () are just
a few examples.
How can you select a package to use as your e-com-
merce ‘solution of choice’? It’s not easy. You must ask
yourself what you are looking for and identify the prob-
lems which need solving. In my case I was looking for
a solution which met the following requirements:
•open source
•well written
• fully-featured
•not in an early beta version
•supported by the community
•very configurable
FreeTrade, ee-ccommerce
for ddevelopers
By Vladan Zirojevic
A package aimed at the developer, FreeTrade offers a cost-effective yet robust framework for creating your next online
superstore. This article will show the power and flexibility of FreeTrade, and follow up with a short Q&A with
FreeTrade creator and author of 'Core PHP Programming', Leon Atkinson.
PHP Version: PHP 4.1.x, MySQL
O/S: Any
Additional Software: N/A
REQUIREMENTS
FreeTrade on the Web
The Cost:

Free (released under a BSD-style license
Home Page:
/>Download Page:
chever
.com/freetrade/downloads/freetrade3.tar.gz
Mailing list archive:
/>Demo store:
/>March 2003 · PHP Architect · www.phparch.com
FEATURES
FEATURES
March 2003 · PHP Architect · www.phparch.com
20
FreeTrade, e-commerce for developers
These requirements are not too strict, but some of
them do exclude a number of the solutions out there.
After searching, configuring, testing, customizing, and
a good many sleepless nights, I believe that I have
found a good, although not well-known, solution for a
developer.
FreeTrade is a fully-featured and highly configurable
PHP script for creating and maintaing e-commerce Web
applications. FreeTrade is not a very well-known script,
and there are a few reasons for this. For example, it
does not have its own domain name, the demo store is
very poorly designed , and FreeTrade uses a different
(and, at first glance, strange) development model
called FreeEnergy.
FreeEnergy
FreeEnergy is not a new concept in PHP develop-
ment, but it is also not a widely used one. I am sure

that you use the include() function in your PHP
scripts frequently. Some of the more common uses are
for headers, footers, and function libraries. We had this
functionality before PHP, too, with Server-Side Includes.
This include() functionality is the core of the
FreeEnergy concept.
FreeEnergy uses the idea of ‘modules’. These mod-
ules are a set of directories, generally kept outside of
the web directory tree for security reasons. Almost all
FreeEnergy code is kept in these modules. Module files
are PHP scripts that are included when needed. Some
standard modules are layout, navigation, action, utility
and screen. These directories contain code specific to
their function, and will be examined in greater detail in
a moment.
A FreeEnergy application has only one PHP script
inside the web directory, named index.php. This is
the controlling code for the application, and it loads
modules when needed. It is a small script, and we will
discuss it in the upcoming example.
As an example of how the FreeEnergy concept works,
we’ll create the layout of an e-commerce site. Design
and content are elements of every page in a site. While
the design can be almost the same for groups of pages,
the content will be different on every page. Since mix-
ing design and content is never a good idea, we should
try to keep them separate.
Usually we have a few design schemes for a site. For
example, we could have different schemes for the
home page, department and product pages, news

pages, and pop-up pages. The FreeEnergy concept
calls each scheme a layout. You may have as many lay-
outs for a site as you need, and these are housed in the
layout module directory.
Each layout consists of one or more components. For
example, one layout might have a header, content, and
a footer as components. Another layout might have a
header, a left-side navigation bar, content, and a foot-
er. These components can be laid out in the layout file
using HTML tables, div tags, or any other means. Note
that none of the components of a layout are hardcod-
ed. They are just included into it with a simple
include(). Each component is saved in a separate
file. The code making up each of the navigation, head-
er and footer components is kept in the navigation
module directory.
The content component (or screen) is kept in a file in
the screen module directory. A screen may be pure
HTML or PHP, but the screen file never performs any
action past showing page content. Listing 1 lists the
code for an example screen showing a user login page.
This example login screen script would reside in the
login file in the modules/screen directory. Module
files have no file extension (like .php) because they are
to be included, not executed. I will stay focused on this
example and explain a few things.
FreeEnergy has a general module, called utility, which
contains common functions and libraries. Some of
these files are included in every FreeEnergy page. In
Listing 1 we used functions such as StartForm(),

startTable(), and printLink(), which are func-
tions from the utility module.
FreeEnergy doesn’t force you to use these functions
(you may use print(“<table>”) instead of
startTable()), but using them ensures that you can
control all site elements from single functions. This
means that the StartForm() function controls all site
forms. This is great because we can automatically add
as many hidden variables to all of the forms as we need.
Site changes are very easy with this approach!
Let’s look at the definition of the StartForm() func-
tion and compare it with the function call in our exam-
ple screen in Listing 1.
The $screen parameter defines which screen will be
loaded when the form is submitted. $method specifies
whether the GET or POST form method is to be used.
$action names the action to be executed before the
next screen is shown. $secure defines whether we
will use HTTP or HTTPS for this form. These function
parameters are the most important. For our purposes,
the remaining parameters may be ignored.
The action is a file in the modules/action directo-
function StartForm($screen,
$method=’get’,
$action=’’,
$secure=FALSE,
$extra=’’,
$windowName=’’,
$encodingType=’’,
$formName=’’,

$onReset=’’,
$onSubmit=’’,
$class=FALSE);
FEATURES
March 2003 · PHP Architect · www.phparch.com
21
FreeTrade, e-commerce for developers
ry which will be included and executed before the tar-
get screen is loaded. Actions never print text. They
only take action and return a result to the
$ActionResults array. Some actions are very simple
(ie. add a news item to a site), but some are very com-
plex and require several steps (ie. submit order). Each
step of an action must completed successfully for the
action to be successful.
In our example, the target screen is ‘contents’ (which
will show the shopping cart contents), and the action
script is ‘LOGIN_USER’. When the form is submitted it
will load and execute the action script. If the action
completes successfully, it will then transfer the user to a
page showing the contents of his shopping cart.
Now that we know how FreeEnergy works, let’s take
a look at how FreeTrade builds on it.
FreeTrade Organization
FreeTrade, a child of the FreeEnergy concept, follows
the same code organization we just described. The
directory structure is as follows:
·htdocs/
index.php
·modules/

action/
configuration/
database/
help/
language/
layout/
navigation/
screen/
utility/
We already know the purpose of the general
FreeEnergy modules like layout, navigation, screen and
action. Let’s examine the new FreeTrade-specific mod-
ules.
The configuration module contains scripts for specify-
ing application parameters. The well-commented
modules/configuration/global file defines all
important global constants. I will discuss this file in
detail later.
1 <?php
2
3 /*
4 ** File: login
5 ** Description: form for logging in
6 */
7
8 /*
9 ** Login Form
10 */
11
12 print(StartForm("contents", 'post', 'LOGIN_USER', TRUE, '', '', '', 'loginForm'));

13
14 startTable();
15
16 printEditRow(localize('Name'), "inputLogin", "", 32, 255);
17 printEditRow(localize('Password'), "inputPassword", "", 32, 255, "password");
18 printSubmit(localize('Login'));
19
20 endTable();
21
22 endForm();
23
24 /*
25 ** Link for users who haven't registered yet.
26 */
27 print(localize("If you don't have an account, please") . " ");
28 printLink(localize('create an account'), "create_account",
29 0, FALSE, TRUE);
30 print(".");
31
32 /*
33 ** Put the cursor in the correct place.
34 */
35 if ($Browser_JavaScriptOK)
36 {
37 print("<script language=\"Javascript\">\n");
38 print("\tdocument.forms.loginForm.inputLogin.focus();\n");
39 print("</script>\n");
40 }
41
42 ?>

Listing 1
FEATURES
March 2003 · PHP Architect · www.phparch.com
22
FreeTrade, e-commerce for developers
The modules/configuration/screenInfo
script describes every page (page=screen) of the site.
The default screen definition is as follows:
‘SI_LAYOUT’ defines the layout to use for this screen.
‘SI_PERMISSION’ is an array of user permissions
needed to view the page. For instance, to limit page
access to the administrator, we would use:
All screen definitons are stored in an array called
$ScreenInfo. Screen definitions don’t usually speci-
fy all of the parameters. Any parameters that are omit-
ted will be filled in from $ScreenDefaults.
An example of an administrative section for adding a
new product into the store database is as follows:
This page will have a default description, default key-
words, and default navigation (‘with_side_nav’). An
example of a screen with a different layout is as follows:
In this help screen we defined a different layout, but
omitted permissions. This means that the default per-
missions will be used (everybody will be able to open
the page).
The database module is a kind of abstraction layer for
MySQL and PostgreSQL databases. Which of them to
use is up to you. The database type is set in the mod-
ules/configuration/global file, and the data-
base module contains function libraries for database

operations.
The help module is a set of screens to create context-
sensitive help.
The language module is used for localization.
FreeTrade may be totally localized and translated to any
language. By default, it supports English, Italian,
German, French and Spanish.
Now let’s see how to install and configure the script.
Configuration and Installation
FreeTrade is easy to configure, but there are a few
things which may cause problems. FreeTrade requires
at least PHP 4.2.
Take a look again at the FreeTrade directory structure.
The modules directory is parallel to htdocs. This
implies that modules has to be outside the web direc-
tory. If your host doesn’t allow such a configuration, it
can be a security problem. You can place the modules
directory within htdocs, but the module files don’t
have .php extensions. This means that they may not
be parsed by PHP and everyone will be able to see your
configuration parameters. Although you can protect
this directory, the only secure configuration is to place
modules outside of the Web directory.
After you install the code, you will need to make a
database for FreeTrade. In the FreeTrade distribution
package, you will find an install directory with SQL
files for both MySQL and PostgreSQL. Load the desired
database type’s build.sql into a new database. You
may also load sampledb.sql into the database to
populate it with sample data for testing.

The last installation step is to modify the
modules/configuration/global file. You will
probably need to change only database-related param-
eters, but I will explain some other interesting parame-
ters, too.
The first section of this file defines the debug status
and the behaviour of error logging. You can set the
‘DEBUG’ constant to ‘TRUE’ for site-wide debugging,
but don’t forget to turn it off once the site is live. Also,
make sure that the error log directory you select in
‘LOG_DESTINATION’ exists and is writable by the web
process.
The next section of this file is for configuring global
network behaviour.
Setting ‘USE_FLAT_URLS’ to ‘TRUE’ will turn on flat
URLs (which will be decoded in index.php). Flat URLs
use a sneaky technique to pass data in like a querys-
tring. A flat URL looks like this:
/>tment/Green/item/Jacket.html
A normal URL would look like this:
/>m&department=2&item=3
Notice that the script being used here is actually just
Many search engines
will not index dynamic-looking sites like the second
URL. By passing in data using the method shown in the
first (flat) URL, you can encourage search engines to
spider the site.
The network behavior section of the global file also
“help”=>array (‘SI_TITLE’=>”Help”,
‘SI_LAYOUT’=>”plain”

)

“add_item”=>array (
‘SI_TITLE’=>”Add item to Catalog”,
‘SI_PERMISSION’ =>array(‘Administrate’))
‘SI_PERMISSION’=> array(‘Administrate’)
$ScreenDefaults = array(
‘SI_TITLE’=>’Page title...’,
‘SI_DESCRIPTION’=>’Desctiption ...’,
‘SI_KEYWORDS’=>’Keywords...’,
‘SI_LAYOUT’=>’with_side_nav’,
‘SI_BODY’=>’style=”background: white;”’,
‘SI_PERMISSION’=>FALSE);
FEATURES
March 2003 · PHP Architect · www.phparch.com
23
FreeTrade, e-commerce for developers
allows you to specify the use of department names,
instead of their IDs, in links (set ‘USE_NAMED_DEPART-
MENTS’ to ‘TRUE’). The same is available for items (set
‘USE_NAMED_ITEMS’ to ‘TRUE’). Stores with these
options turned on will also be better listed on search
engines.
The ‘DEFAULT_SCREEN’ constant defines the screen
to be loaded if no screen has been requested. By
default, it is the welcome screen (home page).
‘SEND_EMAIL’ specifies whether or not the system will
send order confirmation emails. The ‘USE_SSL’ con-
stant should be set to ‘TRUE’ if you want sensitive areas
of the system to only be viewed using an SSL connec-

tion (ie. checkout process). This constant affects the
ScreenURL() and StartForm() functions.
FreeTrade doesn’t force users to have cookies turned
on. Session variables will be tracked anyway, but if you
want to use cookies, set the ‘USE_COOKIES’ constant
to ‘TRUE’.
The next section of the global configuration file is
dedicated to the store catalog. Set ‘ITEMS_IN_MUL-
TIPLE_DEPARTMENTS’ to ‘TRUE’ if you want some
items to be shown in more than one department (very
useful). The ‘ALLOW_DUPLICATE_DEPT_NAMES’ con-
stant allows two departments to have the same name
in the same parent department. I suggest that you turn
this option off, especially if you have
‘USE_FLAT_URLS’ turned on.
FreeTrade users, by default, can buy items whether
they are registered or not. If you want to force users to
be registered before checkout, set
‘SHOPPER_MUST_REGISTER’ to ‘TRUE’.
FreeTrade supports coupons and gift certificates as
well. If you want to allow them on your site, you
should set the ‘USE_COUPONS’ and ‘USE_GIFTCER-
TIFICATES’ constants to ‘TRUE’. By default, coupons
are turned off and gift certificates are turned on.
The most important parameters in this file are related
to the database. Indeed, it will be ‘challenging’ at best
to run an online store without a successful connection
to a database! You can use MySQL (set the ‘DATABASE’
constant to ‘mysql’) or PostgreSQL (set the ‘DATA-
BASE’ constant to ‘pgsql’). You will need to set

‘DATABASE_HOST’, ‘DATABASE_USER’,
‘DATABASE_PASSWORD’, and ‘DATABASE_NAME’ to
match your server settings.
You may try the new FreeTrade caching option by
turning the ‘USE_CACHE’ constant on. This option will
force FreeTrade to cache the results of database queries.
This feature is still in the testing phase, so don’t use it
on live stores.
Now you can play with your FreeTrade application.
The default administrator login is a username of
‘admin’ and a password of ‘admin’. To test FreeTrade,
you may use the FreeTrade Test Specifications that are
located in the doc directory of your distribution pack-
age. It covers all of the store functions.
Troubleshooting
If the script fails to run properly and your configura-
tion parameters are correct, there may be two possible
causes.
FreeTrade requires magic_quotes_gpc to be off.
If magic quotes are on, FreeTrade will not function as
expected. Throughout the site’s form handling code
FreeTrade uses addslashes() when inserting or
updating the database. It does not do anything special
when setting the value of form variables, which may
cause some headaches. You can only change the value
of this setting in the system-wide php.ini file or in a
.htaccess file in the site’s directory.
Some installations may experience problems with file
paths. FreeTrade automatically tries to find the right file
paths in index.php in order to provide the capability

to change hosts painlessly. If it fails, you can set it up
manually. I’ve never had problems with these paths on
Unix/Apache, but I have experienced it a few times on
Windows.
Setting it up manually means hardcoding the file
paths in index.php. The constants you may have to
hardcode are ‘SERVER_NAME’ (the name of the server,
like ‘www.phparch.com’), ‘SCRIPT_NAME’ (the name
of the store script, which is ‘index.php’ by default),
‘APPLICATION_ROOT’ (the path on the Web server’s
filesystem where the modules directory is located, like
‘/www/’ or ‘/usr/local/apache/’), and ‘EXTER-
NAL_PATH’ (the path from the root of the Web site to
the index script, such as ‘/’ or ‘/store/’).
FreeTrade Workflow
Many first-time users have problems with under-
standing how things work in FreeTrade, so I will explain
the FreeTrade execution process in detail.
When a page is requested, the index script first veri-
fies that the PHP version is acceptable and that the con-
figuration is correct. If everything is in order, it locates
the modules directory. Next we include the global
configuration file from the configuration module, as well
as standard libraries from the utility and database mod-
ules.
Now that everything is ready for initialization, so we
include the initialization script from the utility
module. This script will get the database initialization
code and the caching code (if caching is turned on),
and blank out the global variable $ActionResults.

The initialization script handles cases where no
session ID or department ID was provided, and sets
them to defaults. Finally, this script detects the user’s
browser, CSS support, Javascript settings, and anything
else avaiable in the ‘HTTP_USER_AGENT’ variable.
At this point, if everything is OK, we have finished
preprocessing. Now we get into the more interesing
part: executing actions. As stated previously, the
FEATURES
March 2003 · PHP Architect · www.phparch.com
24
FreeTrade, e-commerce for developers
ACTION form variable, from the script which requested
the page, names a file in the modules/action direc-
tory to be included. This script contains the action to
take on submission of the form. For index.php, the
action is like a black box. We include the requested
action and receive the results (or error message) from it
in $ActionResults.
The action usually has several steps, and all of them
must be successfully completed. FreeTrade uses an
interesting technique to process these steps. Instead of
using nested if’s and ending up with highly nested
and hard-to-read code, it uses a nice feature of PHP4’s
include() statement.
In PHP4 a file that has
been included can prema-
turely exit and return a value
with a return() state-
ment, like a function (this is

valid for PHP4+ only; PHP3
doesn’t function like this).
As actions are included files,
we may use return() if
any of the steps of an action
fails. With this funcionality, we can organize the action
as a set of steps in if blocks. If any of them fails, the
others will be skipped. This improves readability and
decreases the size of our code.
Once an action has finished executing, we include
the modules/configuration/ScreenInfo file and
try to find the requested screen definition. If the screen
is not found (or one has not been requested), we show
the default welcome screen to the user. The default
screen is defined in the
modules/configuration/global file, as men-
tioned earlier (the ‘DEFAULT_SCREEN’ constant). The
welcome screen is located in modules/screen, just
like any other site screen. If we did find the screen def-
inition, we read the layout and any other definitions for
the requested screen.
Now we have the action results, the layout, and the
screen content. We just need to print it out and we’re
done. That’s all - the index.php script is over!
The workflow I’ve described is a general one. Each
page is processed this way, whether it be user login or
registration, adding an item to the shopping cart, or
ordering.
Real Life Tips
FreeTrade has two sections. One section is for shop-

pers and one is for administrators. When logged in as
an administrator, you will have an additional menu
option (Admin Menu) in the left side navigation. This is
a link to a set of protected pages for store administra-
tion. There you will find options for managing invoic-
es, departments, products, gifts, coupons, taxes, and so
on.
There are a few things which may confuse you if you
are new. Some of them are related to FreeTrade, while
some are related to e-commerce programming in gen-
eral. I will try to clear things up and save you some
time.
First, let me explain the FreeTrade nomenclature and
how an online store basically works. FreeTrade calls
your online shop a store. A store may have many dif-
ferent departments and subdepartments. For exam-
ple, you might have two departments - one called
‘Books’, and another called ‘Music’. Each department
can contain subdepartments and products. By default,
there is a department called Root. All store depart-
ments are its subdepart-
ments. You can place prod-
ucts in the Root department,
too.
A product is called an item
in FreeTrade. A store user (a
shopper) can add any item
to their own shopping cart.
FreeTrade uses the term bas-
ket when talking about the

shopping cart. When a shopper is finished adding all of
the items he plans to buy to his basket, he goes to the
checkout page. On the checkout page, he is asked for
his shipping and billing details. Finally, we save his
order and eventually process his payment in real-time.
Some other important terms are attributes and vari-
ations. I will try to explain them using an example. If
you are planning to sell shirts in your store, then a shirt
is an item. This item can be different colors and differ-
ent sizes. Color and size are referred to as attributes,
and you are free to specify as many attributes as you
need. In our example, the shirt’s color variations may
be red, blue, white and black. Size variations may be S,
M, L, and XL. Every variation may have an extra price
attached to it (an XL shirt may cost an extra $2). You
are free to specify as many variations you need. You
can manage attributes and variations in the Attributes
and Variations administration menu.
Now that we know what attributes and variations are,
let’s go back to items again. If we want to sell our
example item (a shirt with different colors and sizes),
we must be able to give the selection of these attributes
to the shopper. For some less powerful e-commerce
scripts, the only way to offer a selection of attributes is
to define a different item for each variation of each
attribute. This means that we would create an item for
a green and size S shirt, and another item for red and
size XL shirt, and so on. We would need items for all
combinations of sizes and colors. After that, just imag-
ine how to change the price of that shirt! You would

have to edit all items and change the price for every
one of them. Obviously this is not a good approach.
Let’s introduce a new, well known term in e-commerce:
a SKU.
FreeTrade is a fully-featured
and highly configurable PHP
script for creating and main-
taining e-commerce Web appli-
cations.
FEATURES
March 2003 · PHP Architect · www.phparch.com
25
FreeTrade, e-commerce for developers
SKU stands for Stock Keeping Unit and is an ID asso-
ciated with a product for inventory purposes. Each SKU
in FreeTrade has external SKU information to help con-
nect a store’s offline business with its online business.
FreeTrade uses this number to identify an individual
product. A SKU is a subitem and it has its own name,
price, weight, inventory stock, and any number of
attributes and variations. An item has none of this. It
has only a name, a description and images. All addi-
tional information for an item is stored in its SKUs.
Each item has zero, one, or more SKUs. FreeTrade
allows you to make items with no SKUs, but such items
make no sense. As I said, you can select as many attrib-
utes and variations as you like for a SKU. In our shirt
example, we can select all available colors and sizes for
our shirt. If there is more than one variation of any
attribute (for example, there are 4 colors), the shopper

will see a selection box with all available colors for this
item and he will be able to select the color he likes. For
each attribute with more than one variation, FreeTrade
will show a separate selection box. In our example, the
shopper will see two selection boxes. One selection
box will be for color selection and the other will be for
size selection.
You will probably have only one SKU per item, but
sometimes it is good to have more than one SKU. For
example, you may sell movies. You might have one
SKU for the VHS version and another for the DVD ver-
sion of the same item. Note that in this movie exam-
ple you don’t actually need to make two SKUs, since
you could define an attribute ‘Edition’ with two varia-
tions: ‘VHS’ and ‘DVD’. If, however, you need totally
different pricing for both of these editions, you will
have to define two SKUs.
A SKU can have two prices; List Price and Sale Price.
The Sale Price is the price the item sells for, and it’s the
only price used for calculating order totals. If both
prices are defined, a user will see both prices. You may
leave List Price blank if you wish to show only sale
prices.
You can use the List Price to recalculate the prices for
a whole department. If you implement a sale
(Administrate Sales option), you can set the Sale Price to
the List Price minus a defined discount.
FreeTrade supports cross-selling. For example, if you
are selling mobile phones, cross-selling allows you to
offer headphones, hands-free kits, and cases for a

phone model on that phone’s detail page. This can
definitely increase sales. If you want to cross-sell (show
similar items and/or accessories on the item page), you
have to define a relationship (Administrate Item-to-Item
Relationships option). Once a relationship has been
defined, you’ll need to specify all of the items in the
relationship (Administrate Departments and Items).
In order to actually show related items to the shop-
per, you’ll need to edit the modules/screen/item
file. On line 240, you will find:
‘Cross-Sell’ and ‘Accessory’ are default relationships.
To show any other relationship, you will need to add a
line for each new relationship you’ve created. The
showRelationship() function is defined in the
same file, so you are able to modify it to show related
items in the way you would like. The default way to
show related items is just a bulleted list of linked item’s
names.
Items may have up to 3 images: Thumbnail, Graphic
and LargeGraphic. The Thumbnail image is used in
the department listing. The Graphic image is used on
an item’s detail page. The LargeGraphic image is used
in a pop-up window opened by clicking the Graphic
image on the item detail page. None of these images
are required, so you can have items without having
images. FreeTrade does not support image uploads in
this version, which may be a problem for store owners
if they are not familiar with FTP. Of course, the beauty
of open source is that you can always just add the
upload option. This would require changes in a few of

the scripts for item administration.
The checkout process takes a little getting used to at
first, but I believe that this will be improved in future
versions. As soon as the user steps into the checkout
procedure, all of his shopping cart content is moved
(cart becomes empty!) to a temporary invoice. This
may be a problem if a user decides to exit from the
checkout procedure to buy something else. Although
no data will be lost, the shopping cart will show only
items added after he exited from the checkout. The
checkout process will collect all of the items and the
user will still be able to order all selected items, but it
can be really confusing. A user expects all items to
remain in his shopping cart until the checkout process
finishes. Aside from this, the checkout procedure is
quite smooth.
A shopper with items in his basket can step into the
checkout page either from the basket content page or
from the menu. FreeTrade shows the complete content
of his basket, along with a form for the shopper’s
address. If the shopper is already registered and logged
in, his address will be auto-filled. Form submission will
transfer him to a billing page where he enters his billing
information. FreeTrade will check the credit card infor-
mation that a shopper enters here before transferring
him to the last step: the confirmation page. This verifi-
cation is handled by the
modules/utility/validateCard script. Note
that this verfication only checks that the credit card
number is valid; no charges occur. If the card is

showRelationship($Item, ‘Cross-Sell’,
“Similar Items:”);
showRelationship($Item, ‘Accessory’,
“Accessories:”);

×