MocontiWebserver :: Sleep + NanoHTTPD  
--------    
Moconti is a Sleep Web Application Server capable of supporting 
multiple sites.


What it doesn't do (yet)
--------
This webserver does a lot but it doesn't do everything yet. Features
that are missing at this time include: HTTP authentication and file 
uploads.  

The API for this server doesn't include explicit cookie management 
either.  I'm not claiming this isn't a desirable feature.  Each session 
receives a cookie identifying it.  Ideally you persist long-term data 
server side based on this identifier.  Short term data (1 hour or so) 
will continue to exist in memory under normal load.  You shouldn't need 
to do anything with this.

To configure moconti:
--------
Create a moconti.sl script to hold your configuration information.

Moconti will execute this script on startup.  The moconti server API 
is accessible via the $server variable.

To add a site:

[$server addSite: "host.name", 
                  "/path-to/session.sl", 
                  "/path-to/rootDirectory", 
                  "/path-to/scriptWorkingDirectory"];

The last site added is considered the default site.

index.slp, index.html are the index files (searched for in that order)

The $server variable is accessible within sessions as well.  You can
use this configuration file as an opportunity to load "global" modules
that other sites can take advantage of.  

Modules can register statichooks against the $server variable.  A static 
hook is a high level URI hook that points to a file.  This allows modules 
to locate their resources in one place and share them amongst multiple
sites.  Include modules with Sleep's include() function. 

   Tip: this features helps you create reusable modules out of different
        features.  remember that include(...) sets the $__INCLUDE__ 
        variable.  Use this and getFileParent($__INCLUDE__) to locate
        resources specific to your module.  

To add a static hook:

[$server addStatic: "/scripts/phear.js", "module/phear/phear.js"]

Use the mime.types file to register file extensions with different
mime types.  This file is formatted as a Java properties file with the
extension as the key and the mime type as the value.  This file is loaded 
when the server starts.  An example mime.types snippet is below:

# mime type for .sl and .irc files (make them plain text)
sl=text/plain
irc=text/plain

To execute moconti:
--------
./run.sh

Where is my site:
--------
Moconti will run accepting connections on port 1048.

http://127.0.0.1:1048

Moconti is currently setup to use Apache as a proxy server.  I run
several websites from one Moconti instance with Apache directing
all connections from an IP to port 1048.

My configuration for this is:

<VirtualHost ip_address_here:80> 
   ProxyRequests Off

   <Proxy ip_address_here:80>
      Order deny,allow
      Allow from all
   </Proxy>

   ProxyPass / http://localhost:1048/
   ProxyPassReverse / http://localhost:1048/
</VirtualHost>

Session scripts:
--------
The session script is executed in its own environment when a new session is
created.  Sessions are bound to website host and a unique identifier.  
Sessions expire from memory after 1 hour.  Until that time a session will 
remain in memory with all state ready for use.  The cookie expires after
1 year of non-use.  To obtain the value of the cookie:

$sessionId = [$session getId]

The session script is responsible for registering any urls it wants to hook.
The Session object is available via the $session variable.

To kill the current session:
 
[$session kill];

To hook a site:

[$session addHook: "/path-to/[file.ext]", &closure];

When a url is requested, the session will execute the closure associated with the
url.  The following global variables are available:

%header - all of the key/value pairs passed to the server by the client
%parms - the POST or GET data submitted by the client
$method - the method used by the client to request the URL
$0 - the URI requested by the client

These values are global to save you the trouble of passing them to each call to
display().  See more on the template engine.

The default mime type of the data is text/html.  Any requested URL that does not 
have a hook will be served from the root directory associated with the site.

Session hooks may return a Sleep hash containing additional headers to return
to the user.  The mime type key is "Content-type" and the HTTP status key is
"status". 

Text written to STDOUT is collected and eventually sent to the client. i.e. to
send HTML to the client use:

println("<p>this is some text</p>");

Any of Sleep's other I/O functions will work as well.

You may modify/add headers with a session hook.  Simply return a hash of header
keys with their corresponding value.  For example, here is a redirection script:
 
# access as: http://127.0.0.1:1048/redirect?http://www.google.com

[$session addHook: "/redirect", 
{
   return %(status => '301 Moved Permanently', Location => %header["QUERY_STRING"]);
}];

Scripts can share data between sessions.  The mechanism requires some initiative
on your part but it is faily flexible.  Here is the pattern:

global('%data');

acquire([$session getSiteLock]);
if ([$session getSharedData] is $null)
{
   [$session setSharedData: %data];
}
else
{
   %data = [session getSharedData];
}
release([$session getSiteLock]);

Please note that until the next Sleep release, reads on hashes are not thread
safe.  This is because Sleep hashes update their internal structure when a miss 
occurs. 

Template Engine:
--------
Moconti features a template engine.  A template file is a file with embedded 
Sleep code.  The following tags are supported:

  <% expression %>
    evaluates the specified expression and prints the result in place.

  <?sleep code ?> 
    evaluates the specified sleep code; any writes to stdout will show up in
    place

Anything not enclosed with tags is printed out.  Templates are cached making them
extremely fast.  Feel free to decompose your pages into Sleep scripts that call
display() multiple times.  Templates can call display() as well.  Moconti does its
best to reload templates as they change.

To display a template:

display("/path/to/template.slp", arg1, arg2);

Arguments to &display beyond the path are passed to the template as $1, 
$2, etc.. You may also pass named arguments to a template.

   Tip: think of .slp files as a template engine and display as your 
        means to access them.  You can call display anywhere you like to 
        add to the output of a page (even from within .slp files)

.slp files within the root directory or one of its children are executed 
as Sleep templates.  

Templates use the current working directory specified in the moconti.sl file.

The variables %header, %parms, $method, and $0 are available to a .slp file.
	
Contact:
-------
Raphael Mudge (rsmudge@gmail.com)

This code is released under the LGPL

(NanoHTTPD used here with permission from developer)
