Upload
alexandre-morgaut
View
2.720
Download
3
Embed Size (px)
DESCRIPTION
You may all know that JSON is a subset of JavaScript, but... Did you know that HTML5 implements NoSQL databases? Did you know that JavaScript was recommended for REST by Roy T. Fielding himself? Did you know that map & reduce are part of the native JavaScript API? Did you know that most NoSQL solutions integrate a JavaScript engine? CouchDB, MongoDB, WakandaDB, ArangoDB, OrientDB, Riak.... And when they don't, they have a shell client which does... The story of NoSQL and JavaScript goes beyond your expectations and open more opportunities than you might imagine... What better match could you find than a flexible and dynamic language for schemaless databases? Isn't, an event-driven language what you were waiting for to manage eventually consistency? When NoSQL doesn't come to JavaScript, JavaScript comes to NoSQL, and does it very well...
Citation preview
PresentationW3C AC member
Wakanda Community
Web Architect
JS Expert
REST Lover
NoSQL Fanboy@amorgaut
NoSQL FactsMostly Schemaless
Often with REST / JSON API
Many store JSON
Many embed a JavaScript engine
Map / Reduce
events
Many propose a JavaScript Shell
JavaScript FactsCreated in 1995
Running in Netscape Server in 1996, and then in IIS
Mostly Event-Driven
Recommended in the REST definition in 2000
Integrated in CouchDB in 2007
HTML5 Datastores appeared in 2009
SpiderMonkey3 JIT Compilers: TraceMonkey, JägerMonkey, IonMonkey
V8JIT Compiler : CrankShaft
webkit JavaScriptCore: JSCSquirrelFish Extreme: SFX aka Nitro
(JIT Compiler inside)
Trident: MSHTMLChakra
-> Classic JScript, Managed JScript, & JScript.NET
TamarinJIT Compiler : NanoJIT
-> ActionScript / “ECMAScript 4”
CarakanPreviously: Linear A, Linear B, Futhark
RhinoInterpreted or Compiled execution
CC++
C++Java
?
?C++
Nashorn?
JavaScript Engines
JavaScript & Databases
Netscape Enterprise Server
Microsoft: JScript, JScript.NET, ActiveX
Mozilla Rhino
JSDB
APE Project
W3C Web SQL
Netscape Enterprise Server
SQLTable()
DbPool
start/home.html
Shared Connections
pool = new DbPool("ORACLE", addr, user, pwd, "", 5, true);connection = pool.connection("A connection");
cursor = connection.cursor("select name from customer");
if ( cursor && (connection.majorErrorCode() == 0) ) { // Get the first row cursor.next(); // Display the values write("<B>Customer Name:</B> " + cursor.name + "<BR>"); //Close the cursor cursor.close();}
Note: Netscape Enterprise Server merged with Javagator to become iPlanet
MS JScript on the server
Active Server Page
runat=”server”
Windows Script Hosting
.NET
conn = Server.CreateObject("ADODB.Connection");
conn.Open(dsn, login, password);
reccordset = conn.Execute(sqlQuery);result = [];
while (!reccordset.EOF) {
result.push({ field1: reccordset("field1"), field2: reccordset("field2") }); rsAuthor2.MoveNext; }
conn.Close();conn = null;
Note: JScript is running on Microsoft IIS since 1997
MS JScript in the Browser
ActiveXObject
only IE
var connection = new ActiveXObject("ADODB.Connection"); connection.Open(dsn, login, password);var reccordset = new ActiveXObject("ADODB.Recordset"); reccordset.Open(sqlQuery, connection);reccordset.MoveFirst;
while(!reccordset.eof) { document.write(reccordset.fields(1)); reccordset.movenext;} reccordset.close;connection.close;
Mozilla Rhino
Java environment
Access to JDBC
ex: RingoJS
importPackage(java.sql);java.lang.Class.forName("org.sqlite.JDBC");
conn = DriverManager.getConnection("jdbc:sqlite:test.db");stat = conn.createStatement();resultSet = stat.executeQuery("select * from people;");
while (resultSet.next()){ print( resultSet.getString("name") + " - " + resultSet.getString("occupation") );}
resultSet.close();stat.close();conn.close();
https://developer.mozilla.org/en-US/docs/Rhino
JSDB
SpiderMonkey
Shell
JS Server
var db = new ODBC(dsn);var result = db.query("select * from mytable");
var searcher = new Index;for (var i=1; i <= result.count; i++){ searcher.add(result.get('NAME'));}
var i = searcher.find('Mr. Smith');var r = result.getRow(i + 1);
writeln('Data for Mr. Smith');writeln(r.toString());
db.close();
http://www.jsdb.org/
APE Project
Real Time Web
Comet
Web Sockets
MySQL
var sql = new Ape.MySQL(ip + ":3306", user, password, db);
Ape.registerCmd('foo', true, function(params, cmd) {
cmd.user.sendRaw( 'bar', { hello: 'world', echo: params.ping } ); sql.query( 'INSERT INTO table(log) VALUES("' + Ape.MySQL.escape(params.ping) + '")', function(res, errorNo) { Ape.log('Inserted ' + this.getInsertId()); } );});
http://www.ape-project.org/
Note: APE means “Ajax Push Engine”
W3C Web SQL
HTML5
Safari
Chrome
Opera
Sync / Async
db.transaction(function (tx) { tx.executeSql('CREATE TABLE IF NOT EXISTS foo (id unique, text)'); tx.executeSql('INSERT INTO foo (id, text) VALUES (1, "synergies")');});
http://html5doctor.com/introducing-web-sql-databases/
Note: standard paused because current implementations are only based on SQLite
var db = openDatabase('mydb', '1.0', 'my first db', 2 * 1024 * 1024);
result = x.executeSqlSync('SELECT * FROM foo');for (var i = 0, len = results.rows.length; i < len; i++) { alert(results.rows.item(i).text);}
tx.executeSql('SELECT * FROM foo', [], function (tx, results) { for (var i = 0, len = results.rows.length; i < len; i++) { alert(results.rows.item(i).text); }});
Key-Value: Web Storage, Riak
Document: CouchDB, MongoDB, IndexedDB
Object: JavaScriptDB, WakandaDB
Multi-Model: OrientDB & ArangoDB
Touching the DB Heart
Web Storage
W3C / WHATWG
HTML5
local
session
events
// set or get items by methodslocalStorage.setItem("storedItem", "value");var value = localStorage.getItem("storedItem");
http://www.w3.org/TR/webstorage/
// sync interface when data change, even from other windowwindow.addEventListener("storage", handle_storage, false);
// set or get items using the store as a maplocalStorage.storedItem = value;var value = localStorage.storedItem;
// accessible only for this sessionvar foo = sessionStorage.bar;sessionStorage.bar = foo;
Note: Firefox used to propose “globalStorage”, Wakanda implements “user.storage”
RiakBuckets
REST / JSON
Map / Reduce
Erlang alternative:
SpiderMonkey
// Map: compute the daily variance, key it by the monthfunction(value, keyData, arg){ var data = Riak.mapValuesJson(value)[0]; var month = value.key.split('-').slice(0,2).join('-'); var obj = {}; obj[month] = data.High - data.Low; return [ obj ];}
// Reduce: find the maximum variance per monthfunction(values, arg) { return [values.reduce(function(acc, item){ for (var month in item) { acc[month] = acc[month] ? Math.max(item[month], acc[month]) : item[month]; } return acc; })];}
{"inputs": "goog", "query": [ {"map": {"language": "javascript", "source": "function(value, keyData, arg){...}" }}, {"reduce": {"language": "javascript", "source": "function(values, arg){...}", "keep": true }} ]}
IndexedDBW3C / WHATWG
HTML5
Sync / Async
Indexes
Transactions
Cursors
request.onerror = function(event) { // Do something with request.errorCode!};request.onsuccess = function(event) { // Do something with request.result!};
http://www.w3.org/TR/IndexedDB/
var request = indexedDB.open("MyTestDatabase", 3);
request.onupgradeneeded = function(event) { // Update object stores and indices .... }
var objectStore = db.createObjectStore("customers", { keyPath: "ssn" });
objectStore.createIndex("name", "name", { unique: false });objectStore.add({ ssn: "444-44-4444", name: "Bill", age: 35});
var transaction = db.transaction(["customers"], IDBTransaction.READ_WRITE);
CouchDB
Views
JSON*
Map / Reduce
Erlang alternative:
Spidermonkey
function(doc) { if (doc.Type == "customer") { emit(doc.LastName, {FirstName: doc.FirstName, Addr: doc.Address}); emit(doc.FirstName, {LastName: doc.LastName, Addr: doc.Address}); }}
{ "total_rows":2, "offset":0, "rows": [ { "id":"64ACF01B05F53ACFEC48C062A5D01D89", "key":"Katz", "value":{"FirstName":"Damien", "Addr":"Charlotte NC"} }, { "id":"64ACF01B05F53ACFEC48C062A5D01D89", "key":"Damien", "value":{"LastName":"Katz", "Addr":"Charlotte NC"} }, ]}
http://wiki.apache.org/couchdb/HTTP_view_API
Note: CouchDB moved from XML to JSON & JS in 2007** http://jan.prima.de/~jan/plok/archives/89-CouchDb-updates.html
CouchBase
CouchDB alternative
using V8
adding memcache
meant to be more scalable
http://www.couchbase.com/
MongoDBSpidermonkey
BSON
Map / Reduce
REST / JSON
REST / JS
Shell
var map = function() { emit(this.author, {votes: this.votes});};
http://www.mongodb.org/display/DOCS/MapReduce
{ text: "lmao! great article!", author: 'kbanker', votes: 2}
// Add up all the votes for each key.var reduce = function(key, values) { var sum = 0; values.forEach(function(doc) { sum += doc.votes; }); return {votes: sum};};
var op = db.comments.mapReduce(map, reduce, {out: "mr_results"});
Persevere JavaScriptDB
Rhino
REST / JSON
JSON Schema
JSON Path
JSON Query
{"id":"generated.js","sources":[ { "name":"Data", "extends":"Object", "schema":{ "extends":{"$ref":"../Class/Object"}, hello : function() { console.log("hello hi"); }, "prototype":{ } } }]}
curl localhost:8080/Data/1
({"id":"1","test":12345})
Data.hello(); // INFO: hi there
var d = new Data();d.test = 12345;
http://www.sitepen.com/blog/2009/04/20/javascriptdb-perseveres-new-high-performance-storage-engine/
WakandaDBWebkit JavaScriptCore
REST / JSON
Data Classes
auto-updatable
accessors
events
methods
john = ds.Person.find("fistName eq John");
conferences = john.allConferences;
JohnJSConferences = conferences.filter("title eq :1", "*JavaScript*");
JSAttendeesJohnMet = JSConferences.allPeople;
http://wakanda.org/
ArangoDB
V8
events
filters
transactions
Shell
actions.defineHttp({ url : "world", context : "api", callback : function (req, res) { var collection = db._collection(req.parameter.collection); if (collection == null) { ... } else { ... } actions.resultOk(req, res, actions.HTTP_OK, result); }});
http://www.ape-project.org/
OrientDB
rhino
REST / JSON
transactions
hooks (events)
stored procedures
// create function getAllCustomerreturn db.query("select from V")
http://www.orientdb.org/
db.begin();try {" // some code" db.commit()} catch (e) {" db.rollback();"}
new com.orientechnologies.orient.core.record.impl.ODocument('Profile').field('name', 'Luca').save()
mongoose
mongodb-rhino
riak control
backbone-couchdb
dojox.data.couchDBRestStore
node-cassandra
WAF (Wakanda)
Ext.data.proxy.Wakanda
arango.client
voltdb-client-nodejs
redis-node-client
orientdb-api.js
Reaching the DB
Thank you!
@amorgaut
@wakandasoft
http://wakanda.org
@jseverywhere
http://jseverywhere.org
http://about.me/amorgaut http://w3.org/community/jseverywhere/
Client & Server JavaScript APIs
Let’s keep in touch...