10.1.1.248 - - [14/Mar/2002:13:31:37 -0500] "GET /php-cookbook/colors.html  
HTTP/1.1" 200 460 "-" "Mozilla/4.0 (compatible; MSIE 5.5; Windows NT 5.0)" 
In the first line, 
10.1.1.162
is the IP address that the request came from. Depending on the 
server configuration, this could be a hostname instead. When the 
$matches
array is assigned 
to the list of separate variables, the hostname is stored in 
$remote_host
. The next hyphen 
(-) means that the remote host didn't supply a username via identd,
[1]
so 
$logname
is set to 
-
 
[1]
identd, defined in RFC 1413, is supposed to be a good way to identify users 
remotely. However, it's not very secure or reliable. A good explanation of why 
is at http://www.clock.org/~fair/opinion/identd.html
The string 
david
is a username provided by the browser using HTTP Basic Authentication and 
is put in 
$user
. The date and time of the request, stored in 
$time
, is in brackets. This date 
and time format isn't understood by 
strtotime( )
, so if you wanted to do calculations based 
on request date and time, you have to do some further processing to extract each piece of the 
formatted time string. Next, in quotes, is the first line of the request. This is composed of the 
method (GET, POST, HEAD, etc.) which is stored in 
$method
; the requested URI, which is 
stored in 
$request
, and the protocol, which is stored in 
$protocol
. For GET requests, the 
query string is part of the URI. For POST requests, the request body that contains the 
variables isn't logged.  
After the request comes the request status, stored in 
$status
. Status 
200
means the request 
was successful. After the status is the size in bytes of the response, stored in 
$bytes
. The 
last two elements of the line, each in quotes, are the referring page if any, stored in 
$referer
[2]
and the user agent string identifying the browser that made the request, stored 
in 
$user_agent
.  
[2]
The correct way to spell this word is "referrer." However, since the original 
HTTP specification (RFC 1945) misspelled it as "referer," the three-R spelling is 
frequently used in context. 
Once the log file line has been parsed into distinct variables, you can do the needed 
calculations. In this case, just keep a counter in the 
$requests
array of how many times 
each URI is requested. After looping through all lines in the file, print out a sorted, formatted 
list of requests and counts.  
Calculating statistics this way from web server access logs is easy, but it's not very flexible. 
The program needs to be modified for different kinds of reports, restricted date ranges, report 
formatting, and many other features. A better solution for comprehensive web site statistics is 
to use a program such as analog, available for free at http://www.analog.cx
. It has many 
types of reports and configuration options that should satisfy just about every need you may 
have.  
Pdf create fillable form - C# PDF Field Edit Library: insert, delete, update pdf form field in C#.net, ASP.NET, MVC, Ajax, WPF
Online C# Tutorial to Insert, Delete and Update Fields in PDF Document
convert word document to editable pdf form; create a pdf form online
Pdf create fillable form - VB.NET PDF Field Edit library: insert, delete, update pdf form field in vb.net, ASP.NET, MVC, Ajax, WPF
How to Insert, Delete and Update Fields in PDF Document with VB.NET Demo Code
best program to create pdf forms; add photo to pdf form
11.14.4 See Also 
Documentation on 
preg_match( )
at http://www.php.net/preg-match
; information about 
common log file formats is available at http://httpd.apache.org/docs/logs.html
Recipe 11.15 Program: Finding Stale Links 
The stale-links.php program in Example 11-5
produces a list of links in a page and their 
status. It tells you if the links are okay, if they've been moved somewhere else, or if they're 
bad. Run the program by passing it a URL to scan for links:  
stale-links.php http://www.oreilly.com/ 
http://www.oreilly.com/index.html: OK 
http://www.oreillynet.com: OK 
http://conferences.oreilly.com: OK 
http://international.oreilly.com: OK 
http://safari.oreilly.com: MOVED: mainhom.asp?home 
... 
The stale-links.php program uses the cURL extension to retrieve web pages. First, it retrieves 
the URL specified on the command line. Once a page has been retrieved, the program uses 
the 
pc_link_extractor( )
function from Recipe 11.9
to get a list of links in the page. 
Then, after prepending a base URL to each link if necessary, the link is retrieved. Because we 
need just the headers of these responses, we use the HEAD method instead of GET by setting 
the 
CURLOPT_NOBODY
option. Setting 
CURLOPT_HEADER
tells 
curl_exec( )
to include the 
response headers in the string it returns. Based on the response code, the status of the link is 
printed, along with its new location if it's been moved.  
Example 11-5. stale-links.php  
function_exists('curl_exec') or die('CURL extension required'); 
function pc_link_extractor($s) { 
$a = array(); 
if (preg_match_all('/<A\s+.*?HREF=[\"\']?([^\"\' 
>]*)[\"\']?[^>]*>(.*?)<\/A>/i', 
$s,$matches,PREG_SET_ORDER)) { 
foreach($matches as $match) { 
array_push($a,array($match[1],$match[2])); 
return $a; 
$url = $_SERVER['argv'][1]; 
// retrieve URL 
$c = curl_init($url); 
curl_setopt($c, CURLOPT_RETURNTRANSFER, 1); 
curl_setopt($c, CURLOPT_FOLLOWLOCATION,1); 
$page = curl_exec($c); 
$info = curl_getinfo($c); 
curl_close($c); 
VB.NET Create PDF from PowerPoint Library to convert pptx, ppt to
Convert multiple pages PowerPoint to fillable and editable PDF documents. Easy to create searchable and scanned PDF files from PowerPoint.
create a pdf form; chrome save pdf form
VB.NET Create PDF from Word Library to convert docx, doc to PDF in
Edit Bookmark. Metadata: Edit, Delete Metadata. Form Process. Create PDF files from both DOC and DOCX formats. Convert multiple pages Word to fillable and editable
pdf add signature field; create pdf form
// compute base url from url 
// this doesn't pay attention to a <base> tag in the page 
$url_parts = parse_url($info['url']); 
if ('' == $url_parts['path']) { $url_parts['path'] = '/'; } 
$base_path = preg_replace('<^(.*/)([^/]*)$>','\\1',$url_parts['path']); 
$base_url = sprintf('%s://%s%s%s', 
$url_parts['scheme'], 
($url_parts['username'] || $url_parts['password']) ? 
"$url_parts[username]:$url_parts[password]@" : '', 
$url_parts['host'], 
$url_parts['path']); 
// keep track of the links we visit so we don't visit each more than once 
$seen_links = array(); 
if ($page) { 
$links = pc_link_extractor($page); 
foreach ($links as $link) { 
// resolve relative links 
if (! (preg_match('{^(http|https|mailto):}',$link[0]))) { 
$link[0] = $base_url.$link[0]; 
// skip this link if we've seen it already 
if ($seen_links[$link[0]]) { 
continue; 
 
// mark this link as seen 
$seen_links[$link[0]] = true; 
// print the link we're visiting 
print $link[0].': '; 
flush(); 
// visit the link 
$c = curl_init($link[0]); 
curl_setopt($c, CURLOPT_RETURNTRANSFER, 1); 
curl_setopt($c, CURLOPT_NOBODY, 1); 
curl_setopt($c, CURLOPT_HEADER, 1); 
$link_headers = curl_exec($c); 
$curl_info = curl_getinfo($c); 
curl_close($c); 
switch (intval($curl_info['http_code']/100)) { 
case 2: 
// 2xx response codes mean the page is OK 
$status = 'OK'; 
break; 
case 3: 
// 3xx response codes mean redirection 
$status = 'MOVED'; 
if (preg_match('/^Location: (.*)$/m',$link_headers,$matches)) { 
$location = trim($matches[1]); 
$status .= ": $location"; 
break; 
default: 
// other response codes mean errors 
$status = "ERROR: $curl_info[http_code]"; 
VB.NET Create PDF from Excel Library to convert xlsx, xls to PDF
Link: Edit URL. Bookmark: Edit Bookmark. Metadata: Edit, Delete Metadata. Form Process. Create fillable and editable PDF documents from Excel in Visual
add form fields to pdf online; change font in pdf fillable form
C# Create PDF from Excel Library to convert xlsx, xls to PDF in C#
Create fillable and editable PDF documents from Excel in both .NET WinForms and ASP.NET. Create searchable and scanned PDF files from Excel.
cannot edit pdf form; adding form fields to pdf files
break; 
print "$status\n"; 
Recipe 11.16 Program: Finding Fresh Links 
Example 11-6
fresh-links.php, is a modification of the program in Recipe 11.15
that produces 
a list of links and their last modified time. If the server on which a URL lives doesn't provide a 
last modified time, the program reports the URL's last modified time as the time the URL was 
requested. If the program can't retrieve the URL successfully, it prints out the status code it 
got when it tried to retrieve the URL. Run the program by passing it a URL to scan for links:  
fresh-links.php http://www.oreilly.com 
http://www.oreilly.com/index.html: Fri Aug 16 16:48:34 2002 
http://www.oreillynet.com: Mon Aug 19 10:18:54 2002 
http://conferences.oreilly.com: Fri Aug 16 19:41:46 2002 
http://international.oreilly.com: Fri Mar 29 18:06:32 2002 
http://safari.oreilly.com: 302 
http://www.oreilly.com/catalog/search.html: Tue Apr  2 19:05:57 2002 
http://www.oreilly.com/oreilly/press/: 302 
... 
This output is from a run of the program at about 10:20 A.M. EDT on August 19, 2002. The 
link to http://www.oreillynet.com
is very fresh, but the others are of varying ages. The link to 
http://www.oreilly.com/oreilly/press/
doesn't have a last modified time next to it; it has 
instead, an HTTP status code (302). This means it's been moved elsewhere, as reported by 
the output of stale-links.php in Recipe 11.15
.  
The program to find fresh links is conceptually almost identical to the program to find stale 
links. It uses the same 
pc_link_extractor( )
function from Recipe 11.10
; however, it 
uses the 
HTTP_Request
class instead of cURL to retrieve URLs. The code to get the base URL 
specified on the command line is inside a loop so that it can follow any redirects that are 
returned.  
Once a page has been retrieved, the program uses the 
pc_link_extractor( )
function to 
get a list of links in the page. Then, after prepending a base URL to each link if necessary, 
sendRequest( )
is called on each link found in the original page. Since we need just the 
headers of these responses, we use the HEAD method instead of GET. Instead of printing out 
a new location for moved links, however, it prints out a formatted version of the 
Last-
Modified
header if it's available.  
Example 11-6. fresh-links.php  
require 'HTTP/Request.php'; 
function pc_link_extractor($s) { 
$a = array(); 
C# Create PDF from PowerPoint Library to convert pptx, ppt to PDF
Convert multiple pages PowerPoint to fillable and editable PDF documents. Easy to create searchable and scanned PDF files from PowerPoint.
create a pdf form from excel; add fillable fields to pdf online
C# Create PDF from Word Library to convert docx, doc to PDF in C#.
Convert multiple pages Word to fillable and editable PDF documents in both .NET WinForms and ASP.NET. Easy to create searchable and scanned PDF files from
add text field to pdf; create a pdf form that can be filled out
if (preg_match_all('/<A\s+.*?HREF=[\"\']?([^\"\' 
>]*)[\"\']?[^>]*>(.*?)<\/A>/i', 
$s,$matches,PREG_SET_ORDER)) { 
foreach($matches as $match) { 
array_push($a,array($match[1],$match[2])); 
return $a; 
$url = $_SERVER['argv'][1]; 
// retrieve URLs in a loop to follow redirects  
$done = 0; 
while (! $done) { 
$req = new HTTP_Request($url); 
$req->sendRequest(); 
if ($response_code = $req->getResponseCode()) { 
if ((intval($response_code/100) == 3) && 
($location = $req->getResponseHeader('Location'))) { 
$url = $location; 
} else { 
$done = 1; 
} else { 
return false; 
// compute base url from url 
// this doesn't pay attention to a <base> tag in the page  
$base_url = preg_replace('{^(.*/)([^/]*)$}','\\1',$req->_url->getURL()); 
// keep track of the links we visit so we don't visit each more than once 
$seen_links = array(); 
if ($body = $req->getResponseBody()) { 
$links = pc_link_extractor($body); 
foreach ($links as $link) { 
// skip https URLs 
if (preg_match('{^https://}',$link[0])) { 
continue; 
// resolve relative links 
if (! (preg_match('{^(http|mailto):}',$link[0]))) { 
$link[0] = $base_url.$link[0]; 
// skip this link if we've seen it already 
if ($seen_links[$link[0]]) { 
continue; 
 
// mark this link as seen 
$seen_links[$link[0]] = true; 
// print the link we're visiting 
print $link[0].': '; 
flush(); 
// visit the link 
C# Create PDF Library SDK to convert PDF from other file formats
Create fillable PDF document with fields. Load PDF from existing documents and image in SQL server. Load PDF from stream programmatically.
adding form fields to pdf; chrome pdf save form data
VB.NET Create PDF Library SDK to convert PDF from other file
Create fillable PDF document with fields in Visual Basic .NET application. Load PDF from existing documents and image in SQL server.
android edit pdf forms; create pdf forms
$req2 = new HTTP_Request($link[0], 
array('method' => 
HTTP_REQUEST_METHOD_HEAD)); 
$now = time(); 
$req2->sendRequest(); 
$response_code = $req2->getResponseCode(); 
// if the retrieval is successful 
if ($response_code == 200) { 
// get the Last-Modified header 
if ($lm = $req2->getResponseHeader('Last-Modified')) { 
$lm_utc = strtotime($lm); 
} else { 
// or set Last-Modified to now 
$lm_utc = $now; 
print strftime('%c',$lm_utc); 
} else { 
// otherwise, print the response code 
print $response_code; 
print "\n"; 
VB.NET Create PDF from OpenOffice to convert odt, odp files to PDF
Create PDF document from OpenOffice Text Document with embedded Export PDF document from OpenOffice Presentation. ODT, ODS, ODP forms into fillable PDF formats.
best pdf form creator; pdf form maker
C# Create PDF from OpenOffice to convert odt, odp files to PDF in
Create PDF document from OpenOffice Presentation in both .NET WinForms and ASP.NET NET control to change ODT, ODS, ODP forms to fillable PDF formats in Visual
change font on pdf form; add image field to pdf form
Chapter 12. XML 
Section 12.1.  Introduction
Recipe 12.2.  Generating XML Manually
Recipe 12.3.  Generating XML with the DOM
Recipe 12.4.  Parsing XML with the DOM
Recipe 12.5.  Parsing XML with SAX
Recipe 12.6.  Transforming XML with XSLT
Recipe 12.7.  Sending XML-RPC Requests
Recipe 12.8.  Receiving XML-RPC Requests
Recipe 12.9.  Sending SOAP Requests
Recipe 12.10.  Receiving SOAP Requests
Recipe 12.11.  Exchanging Data with WDDX
Recipe 12.12.  Reading RSS Feeds
12.1 Introduction 
Recently, XML has gained popularity as a data-exchange and message-passing format. As web 
services become more widespread, XML plays an even more important role in a developer's 
life. With the help of a few extensions, PHP lets you read and write XML for every occasion.  
XML provides developers with a structured way to mark up data with tags arranged in a tree-
like hierarchy. One perspective on XML is to treat it as CSV on steroids. You can use XML to 
store records broken into a series of fields. But, instead of merely separating each field with a 
comma, you can include a field name, type, and attributes alongside the data.  
Another view of XML is as a document representation language. For instance, the PHP 
Cookbook was written using XML. The book is divided into chapters; each chapter into recipes; 
and each recipe into Problem, Solution, and Discussion sections. Within any individual section, 
we further subdivide the text into paragraphs, tables, figures, and examples. An article on a 
web page can similarly be divided into the page title and headline, the authors of the piece, 
the story itself, and any sidebars, related links, and additional content.  
XML text looks similar to HTML. Both use tags bracketed by 
<
and 
>
for marking up text. But 
XML is both stricter and looser than HTML. It's stricter because all container tags must be 
properly closed. No opening elements are allowed without a corresponding closing tag. It's 
looser because you're not forced to use a set list of tags, such as 
<a>
<img>
, and 
<h1>
Instead, you have the freedom to choose a series of tag names that best describe your data.  
Other key differences between XML and HTML are case-sensitivity, attribute quoting, and 
whitespace. In HTML, 
<B>
and 
<b>
are the same bold tag; in XML, they're two different tags. 
In HTML, you can often omit quotation marks around attributes; XML, however, requires 
them. So, you must always write:  
<element attribute="value"> 
Additionally, HTML parsers generally ignore whitespace, so a run of 20 consecutive spaces is 
treated the same as one space. XML parsers preserve whitespace, unless explicitly instructed 
otherwise. Because all elements must be closed, empty elements must end with 
/>
. For 
instance in HTML, the line break is 
<br>
, while in XML, it's written as 
<br />
.
[1]
[1]
This is why 
nl2br( )
outputs 
<br />
; its output is XML-compatible. 
There is another restriction on XML documents. Since XML documents can be parsed into a 
tree of elements, the outermost element is known as the root element . Just as a tree has only 
one trunk, an XML document must have exactly one root element. In the previous book 
example, this means chapters must be bundled inside a book tag. If you want to place 
multiple books inside a document, you need to package them inside a bookcase or another 
container. This limitation applies only to the document root. Again, just like trees can have 
multiple branches off of the trunk, it's legal to store multiple books inside a bookcase.  
This chapter doesn't aim to teach you XML; for an introduction to XML, see Learning XML, by 
Erik T. Ray. A solid nuts-and-bolts guide to all aspects of XML is XML in a Nutshell, by Elliotte 
Rusty Harold and W. Scott Means. Both books are published by O'Reilly & Associates.  
Now that we've covered the rules, here's an example: if you are a librarian and want to 
convert your card catalog to XML, start with this basic set of XML tags:  
<book> 
<title>PHP Cookbook</title> 
<author>Sklar, David and Trachtenberg, Adam</author> 
<subject>PHP</subject> 
</book> 
From there, you can add new elements or modify existing ones. For example, 
<author>
can 
be divided into first and last name, or you can allow for multiple records so two authors aren't 
placed in one field.  
The first three recipes in this chapter cover writing and reading XML. Recipe 12.2
shows how 
to write XML without additional tools. To use the DOM XML extension to write XML in a 
standardized fashion, see Recipe 12.3
. Reading XML using DOM is the topic of Recipe 12.4
.  
But XML isn't an end by itself. Once you've gathered all your XML, the real question is "What 
do you do with it?" With an event-based parser, as described in Recipe 12.5
, you can make 
element tags trigger actions, such as storing data into easily manipulated structures or 
reformatting the text.  
With XSLT, you can take a XSL stylesheet and turn XML into viewable output. By separating 
content from presentation, you can make one stylesheet for web browsers, another for PDAs, 
and a third for cell phones, all without changing the content itself. This is the subject of Recipe 
12.6
.  
You can use a protocol such as XML-RPC or SOAP to exchange XML messages between 
yourself and a server, or to act as a server yourself. You can thus put your card catalog on the 
Internet and allow other programmers to query the catalog and retrieve book records in a 
format that's easy for them to parse and display in their applications. Another use would be to 
set up an RSS feed that gets updated whenever the library gets a new book in stock. XML-RPC 
clients and servers are the subjects of Recipe 12.7
and Recipe 12.8
, respectively. Recipe 12.9
and Recipe 12.10
cover SOAP clients and servers. WDDX, a data exchange format that 
originated with the ColdFusion language, is the topic of Recipe 12.11
. Reading RSS feeds, a 
popular XML-based headline syndication format, is covered in Recipe 12.12
.  
As with many bleeding-edge technologies, some of PHP's XML tools are not feature-complete 
and bug-free. However, XML is an area of active development in the PHP community; new 
features are added and bugs are fixed on a regular basis. As a result, many XML functions 
documented here are still experimental. Sometimes, all that means is that the function is 99% 
complete, but there may be a few small bugs lying around. Other times, it means that the 
name or the behavior of the function could be completely changed. If a function is in a highly 
unstable state, we mention it in the recipe.  
We've documented the functions as they're currently planned to work in PHP 4.3. Because 
XML is such an important area, it made no sense to omit these recipes from the book. Also, 
we wanted to make sure that the latest functions are used in our examples. This can, 
however, lead to small problems if the function names and prototypes change. If you find that 
a recipe isn't working as you'd expect it to, please check the online PHP manual or the errata 
section of the catalog page for the PHP Cookbook, http://www.oreilly.com/catalog/phpckbk
Recipe 12.2 Generating XML Manually 
12.2.1 Problem 
You want to generate XML. For instance, you want to provide an XML version of your data for 
another program to parse.  
12.2.2 Solution 
Loop through your data and print it out surrounded by the correct XML tags:  
header('Content-Type: text/xml'); 
print '<?xml version="1.0"?>' . "\n"; 
print "<shows>\n"; 
$shows = array(array('name'     => 'Simpsons', 
'channel'  => 'FOX',  
'start'    => '8:00 PM', 
'duration' => '30'), 
array('name'     => 'Law & Order',  
'channel'  => 'NBC', 
'start'    => '8:00 PM', 
'duration' => '60')); 
foreach ($shows as $show) { 
print "    <show>\n"; 
foreach($show as $tag => $data) { 
print "        <$tag>" . htmlspecialchars($data) . "</$tag>\n"; 
print "    </show>\n"; 
print "</shows>\n";   
12.2.3 Discussion 
Printing out XML manually mostly involves lots of 
foreach
loops as you iterate through 
arrays. However, there are a few tricky details. First, you need to call 
header( )
to set the 
correct 
Content-Type
header for the document. Since you're sending XML instead of HTML, 
it should be 
text/xml
 
Documents you may be interested
Documents you may be interested