3) Developing with APyaX - Tutorial

The files for this tutorial are included in directory:

web/tutorials/tutorial1

This tutorial will cover the basic process of using APyaX to build web applications.

3.1) Adding Python functionality to a web page

This step adds python functionality into an XHTML web page. We could include the python script contents directly. However, we will reference an external Python script via its relative file name. Using external scripts with XHTML is preferred due to problems with embedded scripts which use characters that interfere with XML markup.

In the example below we will start by defining a simple external Python script to return some details of the python interpreter used in the server:



# script web/tutorials/tutorial1/get_python_info.py

import sys

def getPythonInfo(apyax,type):
    if type == 'version':
	    return sys.version
    elif type == 'platform':
	return sys.platform
    elif type == 'copyright':
	return sys.copyright
    elif type == 'executable':
	return sys.executable
    else:
	apyax.raiseError('Unrecognized request: '+type)

Source code for get_python_info.py


The first argument to the script passes an apyax environment object. Only python functions which name their first argument apyax are exposed by APyaX and can be invoked from web pages. The apyax environment object also provides services for session and database connection handling, but in this simple script, we invoke its raiseError method to handle the situation where a request is made for an unknown type of information (passed in the second argument).

Now we will create an XHTML web page:

web/tutorials/tutorial1/index.phtml

The Python script can be linked into this XHTML page using the <script> tag with the type set to "text/python".

<script type="text/python" src="get_python_info.py">
</script>

Now the getPythonInfo function can be called from JavaScript functions in the page.

For example, lets create a form which users can use to select the type of information required and submit to obtain the information from the server (via an APyaX call).


/* retrieve.js - utility javascript functions for invoking getPythonInfo
   and setting up callbacks to recieve the result */

function reveal(info) {
  document.getElementById('py_info').innerHTML = info;
}

function errorHandler(info) {
  document.getElementById('error_info').innerHTML = info;
}

function retrieveInfo(form) {
  reveal('');
  errorHandler('');
  info_key = form.info.options[form.info.selectedIndex].value; 
  getPythonInfo(new apyax(reveal,errorHandler),info_key);
  return false;
}

Source code for the JavaScript utility functions in retrieve.js




The retrieveInfo function writes empty strings to XHTML elements displaying output and error information (tagged with the ids 'py_info' and 'error_info') by calling functions reveal and errorHandler.

Then the retrieveInfo function obtains the selected option from the form and passes this to getPythonInfo as its second argument. The first argument passed to the function getPythonInfo specifies that either the JavaScript functions reveal and errorHandler should be called. If the python function getPythonInfo is successfully executed, the reveal function is invoked and passed the result. If instead, some error occurs, the errorHandler function is invoked with a string describing the error.

We will also add <div> tags to the page which is used by the reveal and errorHandler functions to display the information. For example:

<div id="py_info"></div>



The final page looks like:


<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>

<meta http-equiv="content-type" content="text/html;charset=utf-8" />
<title>APyaX Simple Tutorial</title>
<link rel="stylesheet" type="text/css" href="../../apyax.css"/>

<script type="text/python" src="get_python_info.py" />
<script type="text/JavaScript" src="retrieve.js" />

</head>
<body>
<h2>APyaX Simple Tutorial</h2>

<p>

<form onSubmit="return retrieveInfo(this);" name="testform" action="">
    <select name="info">
	    <option value="version">Python Version</option>
	    <option value="executable">Python Executable Path</option>
	    <option value="platform">Server Platform</option>
	</select>
    <input type="submit" value="Get Information"/>
</form>
</p>

<p>
Details:<div id="py_info"></div>
</p>

<p>
Error:<div id="error_info"></div>
</p>

</body>
</html>

HTML page index.phtml for tutorial example




3.2) Running the APyaX generator

Once the web page XHTML and python script(s) have been prepared, the APyaX generator should be run to modify the XHTML page to replace the Python scripts with JavaScript stubs:

python generate.py <in-file> <out-file>

[The generate.py script is a wrapper located in the web directory]

The APyaX examples name the input XHTML files with the .phtml suffix and the output files with the .html suffix.

For the example:

cd web/tutorials/tutorial1

python ../../generate.py index.phtml index.html

Alternatively, the script build.sh in this directory packages up the call to the APyaX generator for you.

The generator creates the file index.html which is identical to index.phtml, except that:

The generated file index_apgen.js contains JavaScript stub functions for those Python functions in the original script get_python_info.py that APyaX may expose (any functions having a first parameter named apyax). These stub functions marshal the arguments to be passed to the python script into a JavaScript array and invoke an apyax internal function apyax_dispatchRequest to remotely invoke the python function getPythonInfo on the server via (typically) an asynchronous XMLHttpRequest. apyax_dispatchRequest returns immediately, and later when the server returns a response to the request, the resulting value is passed back to the web page by invoking the callback functions defined in the apyax object passed as the first argument target.






function getPythonInfo(target,p1) {
   var parameters = new Array();
    parameters[0] = p1;
   return apyax_dispatchRequest('/apyax.py','tutorials/tutorial1/get_python_info.py','getPythonInfo',target,parameters);
}

Contents of generated file index_apgen.js




3.3) Running the APyaX wsgi dispatcher.

APyaX services can be integrated into web servers in various ways, but the easiest way of demonstrating APyaX is to use wsgi_dispatcher.py, a simple web server which hosts APyaX services (as well as serving files).

The unix script web/run.sh can be used to run a simple web server that incorporates the APyaX dispatcher for the examples (including this tutorial example).

After running the script run.sh, point your browser to:

http://localhost:8080/tutorials/tutorial1