My first mission was to try and work around the fact that URLs for HTTP-IN are transient to say the least, whilst avoiding the use of an external server to act as Dynamic DNS.
Working on the same basis as the older LSL based Servers, I have made the assumption that the UUID of the server remains constant even when the URL changes, and therefor, have used eMail to establish the initial handshake. The server polls for incoming requests every minuet but the requester only poles IF it has not established a valid URL. Once established, all subsequent communication may be event driven with llHTTPRequest and llHTTPResponse acting as the transport layer.
The Server Portion:
CODE
// Very Keynes
// October 2008
//
// InterObject HTTP Server Beta
//
// System Variables
//
string MyAdr;
string MyUrl;
string xPath;
string Query;
//
default
{
// If any event has occured that releases the URL we need to request a new one
changed(integer c){
if (c & (CHANGED_REGION | CHANGED_REGION_RESTART | CHANGED_TELEPORT))llRequestURL();}
//
// Initialise the server
//
state_entry(){
llSetTimerEvent(60.0);// Start Polling for URL requests Via eMail
// Inform Owner of my eMail Address to place into all Requester Objects
llOwnerSay(MyAdr = (string)llGetKey()+"@lsl.aditi.lindenlab.com");
if("" == MyUrl)llRequestURL();// if we don't have a valid URL Request one
}
touch_start(integer total_number)
{
llOwnerSay(MyAdr);
llOwnerSay(MyUrl);
}
//
// The Server Portion - Process HTTP Requests
//
http_request(key id, string method, string body)
{
//Parse the request Header
xPath = llGetHTTPHeader(id, "x-path-info");
Query = llGetHTTPHeader(id, "x-query-string");
// Process Our own URL Request
if (method == URL_REQUEST_GRANTED)
llOwnerSay(MyUrl = body);
else if (method == URL_REQUEST_DENIED)
llOwnerSay("Something went wrong, no url. " + body);
//
// Process Incomming HTTP Requests
//
else if (method == "DELETE")
{
// perform DELETE requests here
llHTTPResponse(id, 200, "Delete Requested -" +
" x-path-info " + xPath +
" x-query-string " + Query
);
}
else if (method == "GET")
{
// perform GET Requests here
llHTTPResponse(id, 200, "Get Requested -" +
" x-path-info " + xPath +
" x-query-string " + Query
);
}
else if (method == "POST")
{
// perform POST requests here
llHTTPResponse(id, 200, "Post Requested" +
" x-path-info " + xPath +
" x-query-string " + Query
);
}
else if (method == "PUT")
{
// perform PUT Requests here
llHTTPResponse(id, 200, "Put Requested" +
" x-path-info " + xPath +
" x-query-string " + Query
);
}
else
{
// Respond with an Error if Requested Method is not Supported
llHTTPResponse(id, 405, "Method unsupported");
}
}
//
// Process incomming eMail Requests
//
timer(){llGetNextEmail("", "");}
email(string time, string address, string subject, string body, integer remaining)
{
if(MyUrl != "")llEmail(address, MyUrl, ""); // Send Current URL if valid
else llEmail(address, "Error, no url.", ""); // else Send Error Message
if(remaining)llGetNextEmail("", ""); // request next in queue
}
}
and the Requester Portion:
CODE
// Very Keynes
// October 2008
//
// InterObject HTTP Requestor Beta
//
// Server / DNS Fixed Address - eMail
//
string address = "3d6304ab-6ea9-dc27-e230-e1082e3e28d0@lsl.aditi.lindenlab.com";
//
// System Variables
//
string ServerURL; //Current Server / DNS URL
//
default
{
// if we don't have a valid ServerURL then request a new Server URL
state_entry(){if("" == ServerURL)state URLRequest;}
//
// Normal Processing follows
//
touch_start(integer total_number)
{
// test code to demonstate system
llHTTPRequest(ServerURL,[HTTP_METHOD,"DELETE"],"");
llHTTPRequest(ServerURL,[HTTP_METHOD,"GET"],"");
llHTTPRequest(ServerURL,[HTTP_METHOD,"POST"],"");
llHTTPRequest(ServerURL,[HTTP_METHOD,"PUT"],"");
}
http_response(key request_id, integer status, list metadata, string body)
{
if(404 == status)state URLRequest;
llSay(0, body); // Say the results of the request
}
}
state URLRequest
{
state_entry()
{
llOwnerSay("Requesting URL");
llEmail(address,"URL Request","");
llSetTimerEvent(30.0);
}
timer(){llGetNextEmail("", "");}
email(string time, string address, string subject, string body, integer remaining)
{
ServerURL = subject;
llSetTimerEvent(0.0);
llOwnerSay("Ready");
state default;
}
}
Create the Server First then copy the eMail Address it reports and paste it into the address line of the Requester code.
Compile the requester code.
The requester will say that it is "Requesting URL", it may take a minute or 2 to establish and will return "Ready".
Once the Requester is ready touch it and it should say the results of the 3 HTTP Requests that it makes.
The requester, in theory, should work in the main grid against a server in The Beta Grid, but for some reason today the beta grid is not sending outbound emails. It all works fine within the beta grid though.
Hope it gives others a place to start playing with what I feel is a much needed functionality.

