====== PHP ==
===== Server Setup ==
See [[:becki:linux:apache httpd]]
===== Variables ==
==== var Keyword ==
''var'' was the keyword for defining a member variable within a class. Since php5 it should never appear anywhere.
==== Variable parsing ==
For hashtables use this syntax:
echo "A banana is {$fruits['banana']}.";
==== predefined stuff ==
* %%__FILE__%%: The full path and filename of the file, see [[phpfn>language.constants.predefined]]
* ''%%$_SERVER['PHP_SELF']%%'': filename of the currently executing script, relative to the document root, see [[phpfn>reserved.variables]]
* HTTP POST variables: ''$_POST''
===== Arrays ==
[[phpfn>language.types.array|Arrays]] - [[phpfn>ref.array|Array Functions]]
==== Making of ==
$fruits = array (
"fruits" => array ("a"=>"orange", "b"=>"banana", "c"=>"apple"),
"numbers" => array (1, 2, 3, 4, 5, 6),
"holes" => array ("first", 5 => "second", "third")
);
==== Working with ==
foreach ($fruits as $fruit) {...} // traverse the array
foreach ($fruits as $key => $fruit) {...} // same if indices are needed
$length= count($fruits); // get number of items
print_r($fruits); // print content
==== Value in Stock? ==
Access to a nonexisting key generates a PHP notice. To prevent this, you can check //before// the access if the key exists or if the value is set. [[phpfn>function.array-key-exists|More]]
array_key_exists('key', $fruits)) // returns true if the key exists
isset($fruits['key']) // returns true if the key exists AND value != NULL
==== Copying, Passing and Returning ==
By default, arrays are copied //by value// (Unlike PHP objects and Java arrays and objects):
=== Assignment ==
$a=array(0);
$b= $a; /* Deep copy: Assignment by value */
$b[0]= 1;
assert($a[0] == 0);
$c= &$a; /* Shallow copy: Assignment by reference */
$c[0]= 2;
assert($a[0] == 2);
$a[0]= 3;
assert($c[0] == 3);
$d= $c; /* $c is not different from $a: Again assignment by value */
$d[0]= 4;
assert($a[0] == 3);
assert($c[0] == 3);
=== Passing to and returning from Functions ==
function f($v) { $v[0]= 1; }
function g(&$w) { $w[0]= 2; }
function h(&$x) { $x[0]= 3; return $x; }
$a= array(0);
f($a); /* pass-by-value */
assert($a[0] == 0);
f(&$a); /* Call-time pass-by-reference works, but is deprecated! */
assert($a[0] == 1);
g($a); /* pass-by-reference */
assert($a[0] == 2);
$b= h($a); /* return-by-reference seems to be default */
assert($a[0] == 3); /* (pass-by-reference just to make it verifiable) */
=== Passing Arrays to Arrays ==
$a= array(0);
$b= array('d'=> $a, 'e'=> &$a);
$a[0]= 1;
assert($b['d'][0] == 0);
assert($b['e'][0] == 1);
=== Passing Arrays to Objects ==
In order to really make an object work with a reference of an arry, you have to //pass// it //by reference// **and** to //assign// it to the member variable //by reference//:
class C {
public function f(&$v) { $this->v= $v; $this->v[0]= 1; }
public function g(&$w) { $this->w= &$w; $this->w[0]= 2; }
}
$o= new C();
$a= array(0);
$o->f($a);
assert($a[0] == 0);
$o->g($a);
assert($a[0] == 2);
===== Objects ==
==== Copying ==
Objects are copied by "something like a reference" [[phpfn>language.oop5.references|more]]. This means the reference operator is not necessary for ojects (anlike PHP arrays)
FIXME Add some code to prove this.
===== Logging ==
Use [[phpfn>function.error-log|error_log()]] for debug logging.
If the calling PHP script is run by the web server, the output usually goes to ''/var/log/httpd/error_log'' whereas if if the script is called from the command line, the output goes to ''stderr'' (tested).
===== Command Line Usage ==
==== Prerequisites ==
* see also php-docu: capter "Using Php from the command line"
* /usr/bin/php can be CLI- or CGI- Sapi; test it with "php -v"
* Only If CGI:
* Optin -qC is necessary in shebang; therefore use it BY DEFAULT! (-q suppresses header; -C keeps working dir)
* set register_argc_argv = On in /etc/apache/php.ini
==== Command Line Arguments ==
#!/usr/bin/php
$value) {
echo "$name: $value\n";
}
?>
Script saved as ''tester'' and called with ''tester bee fly'' prints:
argument count: 3
0: /home/becki/bin/tester
1: bee
2: fly
argv[0] = name of script
Dont't use $arc and $argv, because they are not available under all circumstances!
==== Standard In- and Output ==
This is only useful for PHP command line scripts, not for webserver scripts.
=== stdin ==
Read stdin line by line:
while (fgets(STDIN)) {/* do some thing */}
=== stdout ==
printf();
echo;
=== stderr ==
/* writing to stderr
Note that STDERR seems only to be available when script is called from command line */
fputs(STDERR, "Some msg!\n");
See also [[#logging]]
===== Handling own libraries ==
==== Requirements ==
- We want to intstall the lib somewhere under ''/usr/local/...'' to separate it from files of the Linux distribution
- We don't want to interfere with the C libraries in ''/usr/local/lib/''
- The lib shall be easy to inlcude without the need for an absolute pathname.
- We don't want to tweak the ''include_path'' in ''php.ini''
- Older code which uses the lib must not break when the API of the lib changes
==== Solution ==
Example with a self-written PHP library called ''mystuff'':
* Install the lib in ''/usr/local/lib/php/mystuff0''. This fulfills 1 and 2
* Make a symlink from a dir which is specified in the PHP ''include_path'' to the real lib, eg: ''/usr/lib/php/mystuff0 -> /usr/local/lib/php/mystuff0''. To find out what the ''include_path'' is, use ''phpinfo()''. This fulfills requirement #3 and #4
The number appendix specifies the API version of the lib. When the API of the lib changes, then the version number must be increased. This is the case when exported functions are removed, when their behavior changes or when the signature of the function changes. Note that adding more functions (or classes) to the lib do not break the API.
With every new API you have to install a new lib and keep the older ones:
/usr/lib/php/mystuff0 -> /usr/local/lib/php/mystuff0
/usr/lib/php/mystuff1 -> /usr/local/lib/php/mystuff1
/usr/lib/php/mystuff2 -> /usr/local/lib/php/mystuff2
It should be ovious that you should avoid to change the API too often!
Note that in C you need not to specify a version number. This is resolved by the linker which seems to automatically write a reference to the newest lib into the binary at compile time.
===== Draft: Pages and Actions ==
FIXME Pre- and Postactions are probably obsolete. See http://skiclub-mitwitz.de/lib/libPage/
See also: [[http://www.developer.com/lang/article.php/3836561|Build your own MVC Framework]]
==== Pre-Actions ==
- Every page //must// have exactly 1 unique pre-action (prefix) which is used for building the page eg a database query
- Pages can only be accessed by their pre-actions not directly by other pages. If the page has no dynamic content, the pre-action just calls the page constructor or sets the $page global variable.
- Although different pages may require to do the same things in it's pre-actions do not use the same action, but let those actions call the same helper function. Thus the target page becomes clear.
- FIXME pre-action can change page by calling other pre-action
==== Post-Actions ==
- Each link or form of a page //may// be bound to exactly 1 unique post-action (suffix) eg a database update
- Post-actions may be followed by pre-actions (chaining of actions)
- Actions are named after the page they are bound to. To the name of pre-actions 'p_' is prepended and to post-actons (suffixes) 's_' is prepended
- Use a parameter called eg 'target' for (the pre-actions of) pages wich can be called by differnt other pages and have to jump back to ther calling pages after they are left.
===== Authentication ==
FIXME This section is in progress
==== Possible information ressources ==
* [[http://books.google.de/books?id=WuxxvP7RZasC&pg=PA385&lpg=PA385&dq=%22form-based+Authentication%22+%22with+php%22&source=web&ots=CDagmwZVwv&sig=j80pzpe-cazIrGLPMwJTs7q7H-c&hl=de&sa=X&oi=book_result&resnum=1&ct=result |Google Buchsuche]]
* http://www.devshed.com/cp/bio/David-Web/
* Dokuwiki sourcode
* http://en.wikipedia.org/wiki/HTTP_cookie#Authentication
* http://pear.php.net/distributions/manual/pear_manual_en.html.gz#package.authentication.auth.intro
===== To do ==
* [[http://articles.sitepoint.com/article/php5-standard-library|Standard PHP Library SPL]]
* Check [[http://www.developer.com/lang/php/10-pear-packages-for-every-php-developers-toolbox.html|Auth, HTML_QuickForm2, Text_CAPTCHA, Validate]] of Pear
* Check http://www.devshed.com/cp/bio/Alejandro-Gervasio/
* Check out: [[http://www.developer.com/open/article.php/10930_3782831|Sending Email with PHP]] and [[http://www.wdvl.com/Authoring/PHP/E-mail/Jason_Gilmore01102010.html|Practical PHP: Sending E-mail]]
* Check active record pattern for database access