/** * Filename: mt-bia.js * * @projectDescription MooTools Bia Remoting Library * @author Matan Lurey * @version 0.1 Alpha * @namespace Bia * * Bia aids Ajax developers in applications with heavy remoting * and 'one-load' rich applications; such as editors and games. *//* * Includes... * =========== * Bia.io * .Cookie * .create(String id) * .set(String name, Object value) * .get(String name) * * #remove() * #update() * .SQLLiteConnection * .GoogleGears * .HTML5 * .FileSystem * .Remote * Bia.data * .SQL * .Database * .Table * #select() * #update() * #drop() * #deleteFrom() * #expiresIn * .Row * #columns * .create(String name) * * #createTable(String name) * #save(Object connection, Boolean clear) * #load(Object connection, Boolean clear) * #drop() * #autoSave [false] * #loadOnDemand [true] * Bia.net * .WebService * #establish * #request * .CrossDomain * #close * .encodeuri * .decodejson **//** * Interfaces */var Interface = new Class({ initialize: function() { this.required = $A(arguments); }, test: function(Cls) { this.required.each(function (item){ if (!Cls.prototype[x]) throw new Error('Class does not implement Interface.'+item); }); }});/** * Bia Application Extender Namespace */var Bia = {};/** * Data Management Functions for Bia */Bia.data = {sql :{}};/** * @constructor 'In-Memory' SQL Database in JavaScript * Isn't exactly sql, but parallels its features in a sort of huge hash object. * The cool thing is being able to load and save dynamically... * * [Loading] * ==> fromCookie (cookieName) You can read serialized json data from a cookie. * Not recommended for more than a handful of rows. * * ==> fromFile (fileName) IE with a trusted site can use an ActiveX File System Object * ==> fromGears (dbName) IE or Firefox users with Google Gears Installed and Allowed can * read and write directly to a SQLLite Database. * ==> fromHTML5 (dbName) Nightly builds of browsers with HTML5 SQL can read/write also. * * ==> fromRemote (url, dbName) Alternatively, you can read/write data to a PHP Web Service * * Rise or Fall uses a Bia SQL Database to cache all important data that will be displayed * multiple times, such as Players, Nations, Terrain, and Map Locations. Each table is * assigned an 'expiration' time of X minutes, which means X minutes after a row on the table * has been established it is requested again from the remote server. *//* * Examples: * * Players stores the players name, nation, and online status. It has an expiration of 15 * minutes, meaning every 15 minutes player information is recalled. This is to make sure * nation and online status stay up to date. * * If a user ever attempts to interact with an offline player, the server will force a * database update that it is offline, so no worries! * * Nation stores the nations name, colour, avatar, capital location, and more. This has * an expiration of -1, meaning it never expires. Its highly unlikely during one session * that a nation will change. * * Location stores the x, y, terrain and tile. This also has an expiration of -1. * * Unit stores information about any sort of unit active on the map. Since units can * be moved and such, this has an expiration of 5 minutes. However, server-side events * may override this quicker than this if necessary. *//* * NOTE: * * Using the caching feature of the remote database means that you receive data on demand * only, and never request data that is unlikely to have changed, so the response is instant! * * To use, set the Database#useMemoryCache to true. This should only be used with a remote database, * local databases don't need this functionality. */Bia.data.sql.Database = new Class({});/** * Input/Output Functions for Bia */Bia.io = {};/** * Cookie Object (Extends functionality of MooTools.Cookie) */Bia.io.Cookie = new Class({ initialize: function(name) { }, remove: function() { // Delete Cookie }, update: function(newData) { // JSON Encode Data and Save }, getData: function() { // JSON Decode Data and Return }});/** * Creats a Cookie (same as new Cookie()) */Bia.io.Cookie.create = function(name){ return new Cookie(name);};/** * SQL Lite Interface */Bia.io.SQLLiteConnection = new Interface('get', 'set', 'connect', 'close', 'remove', 'drop');/** * SQL Lite Connection for Google Gears */Bia.io.SQLLiteConnection.GoogleGears = new Class({ get: function(table, idOrQuery, cback) { // [Todo] }, set: function(cback) { // [Todo] }, remove: function(cback) { // [Todo] }, connect: function(cback) { // [Todo] }, close: function(cback) { // [Todo] }, drop: function(cback) { // [Todo] }});/** * SQL Lite Connection for HTML5 Proposed Standard */Bia.io.SQLLiteConnection.HTML5 = new Class({ get: function(table, idOrQuery, cback) { // [Todo] }, set: function(cback) { // [Todo] }, remove: function(cback) { // [Todo] }, connect: function(cback) { // [Todo] }, close: function(cback) { // [Todo] }, drop: function(cback) { // [Todo] }});/** * SQL Lite Connection for IE's FileSystem Object */Bia.io.SQLLiteConnection.FileSystem = new Class({ get: function(table, idOrQuery, cback) { // [Todo] }, set: function(cback) { // [Todo] }, remove: function(cback) { // [Todo] }, connect: function(cback) { // [Todo] }, close: function(cback) { // [Todo] }, drop: function(cback) { // [Todo] }});/** * @constructor * @alias Bia.io.SQLLiteconnection.Remote * SQL Lite Connection for a remote Web Service using Bia DB API */Bia.io.SQLLiteConnection.Remote = new Class({ /** * @alias Bia.io.SQLLiteConnection.Remote.prototype.get * @param {String} table * @param {Object} idOrQuery * @param {Function} cback * * Runs a 'SELECT FROM' statment on the server. In the case of * Rise or Fall, we check to make sure the table selected is * allowed (for example, you cant peak at your opponents gold amount) * and the columns of the table are filtered --- when selecting a player * you can see if they are online, but not where on the map they are looking @. * * @return {Object/Array[Object]} */ get: function(table, idOrQuery, cback) { this._transport.request({ action: 'get', table: table, where: idOrQueryOrNull }, function(data){ cback(data); }); }, /** * @alias Bia.io.SQLLiteConnection.Remote.prototype.set * @param {String} table * @param {Object} idOrQueryorNull * @param {Object} values * @param {Function} [cback] * * Runs either a 'INSERT INTO' or 'UPDATE' statement on the server. * Again, you must be authenticated server-side to do this. * * @return {Integer} Rows Affected */ set: function(table, idOrQueryOrNull, values, cback) { this._transport.request({ action: 'set', table: table, where: idOrQueryOrNull, values: values }, function(data){ if (cback) cback(data.rowsAffected); }); }, /** * @alias Bia.io.SQLLiteConnection.Remote.prototype.remove * @param {String} table * @param {Object} idOrQuery * @param {Function} [cback] * * Runs a 'Delete FROM' statement on the server. Your session authenticated user * must have privelages to do such a request. * * @return {Integer} Rows Affected */ remove: function(table, idOrQuery, cback) { this._transport.request({ action: 'remove', table: table, where: idOrQuery }, function(data){ if (cback) cback(data.rowsAffected); }); }, /** * @alias Bia.io.SQLLiteConnection.Remote.prototype.connect * @param {Function} cback Function to call when connection is successful * @param {CrossDomain} [cd] Optionally specify a cross-domain object to use * * Connects to a remote url via a Bia.net.WebService */ connect: function(url, cback, cd) { // Use a different domain object? var cd = this._window = (cd&&cd.container&&cd.container.contentWindow.Bia) ? cd.container.contentWindow : window; this._transport = cd.Bia.net.WebService(url); var handshake = { 'action': 'authenticate' }; this._transport.request(handshake, function(data){ return cback(data.accepted); }); }, close: function(cback) { this._transport.close(); }, /** * @alias Bia.io.SQLLiteConnection.Remote.prototype.drop * @param {String} table * @param {Function} cback * * Drop's a table. */ drop: function(table, cback) { this._transport.request({ action: 'drop', table: table, where: idOrQuery }, function(){ if (cback) cback(); }); }});/** * Namespace for Networking Functions for Bia */Bia.net = { encodeuri: function(data) { // [Todo] }, decodejson: Json.evaluate};/** * @constructor * @alias Bia.net.WebService * * Creates a remote web service url, which is an extended, automatic converting advanced * JSON Request. * * .request({names: ['mati', 'ray', 'alex'], stupid: true, colors: {blue: 0000FF}}); * => * &names[]=mati&names[]=ray&names=alex&stupid=1&colors[blue]=0000FF * * --- server returns... {data: {accepted: true, names: ['mati', 'ray', 'alex']}} * <= * data {Object} * .accepted {Boolean} = true * .names {Array} * [0] 'mati' * [1] 'ray' * [2] 'alex' */Bia.net.WebService = new Class({ initialize: function(url) { this.establish(url); }, establish: function(url) { this.url = url; return this; }, request: function(postData, cBack) { var X = new XHR().send(this.url, Bia.net.encodeuri(postData)); X.onSuccess = function() { cBack(Bia.net.decodejson(X.response.text)); }; }});/** * @constructor * @alias Bia.net.CrossDomain * * Creates an iFrame Proxy for Cross Domain Ajax. You must create a * cross-domain.htm that contains links to mootools and mt-bia, i.e.: * * <script type="text/javascript" src="to/moo/tools/mootools.js"></script> * <script type="text/javascript" src="to/moo/tools/mt-bia.js"></script> * * [Incompatible] !!! * Opera does not support accessing elements of another iFrame. It DOES * support cross-document messaging, but I'm not going to support that just yet - * to little of the population uses opera for it to be significant... However, * it WILL be supported in the future! */Bia.net.CrossDomain = new Class({ initialize: function(toCrossDomainDotHTM, rdyCBack) { this.container = new Element('iframe', { src: toCrossDomainDotHTM, styles: { width: 0, height: 0, position: 'absolute', left: -500000 } }).inject(document.body) // Support for Firefox and Safari this.container.onload = rdyCBack; // Support for IE this.container.onreadystatechange = function() { // [todo] }; }});