mirror of
https://github.com/amark/gun.git
synced 2025-03-30 15:08:33 +00:00
key fix
This commit is contained in:
parent
21875b3d81
commit
02c3425829
35
gun.js
35
gun.js
@ -17,8 +17,8 @@
|
||||
Gun.is.value = function(v){ // null, binary, number (!Infinity), text, or a rel.
|
||||
if(v === null){ return true } // deletes
|
||||
if(v === Infinity){ return false } // we want this to be, but JSON does not support it, sad face.
|
||||
if(Gun.bi.is(v)
|
||||
|| Gun.num.is(v)
|
||||
if(Gun.bi.is(v)
|
||||
|| Gun.num.is(v)
|
||||
|| Gun.text.is(v)){
|
||||
return true; // simple values
|
||||
}
|
||||
@ -105,7 +105,7 @@
|
||||
function HAM(machineState, incomingState, currentState, incomingValue, currentValue){ // TODO: Lester's comments on roll backs could be vulnerable to divergence, investigate!
|
||||
if(machineState < incomingState){
|
||||
// the incoming value is outside the boundary of the machine's state, it must be reprocessed in another state.
|
||||
return {amnesiaQuarantine: true};
|
||||
return {amnesiaQuarantine: true};
|
||||
}
|
||||
if(incomingState < currentState){
|
||||
// the incoming value is within the boundary of the machine's state, but not within the range.
|
||||
@ -239,6 +239,7 @@
|
||||
var gun = this.chain();
|
||||
gun.shot('done');
|
||||
gun.shot.done(function(){
|
||||
opt = opt || {};
|
||||
cb = cb || function(){};
|
||||
cb.soul = (key||{})[Gun._.soul];
|
||||
if(cb.soul){
|
||||
@ -247,7 +248,7 @@
|
||||
gun._.key = key;
|
||||
cb.node = gun.__.keys[key];
|
||||
}
|
||||
if(cb.node){ // set this to the current node, too!
|
||||
if(!opt.force && cb.node){ // set this to the current node, too!
|
||||
Gun.log.call(gun, "load via gun"); // remember to do all the same stack stuff here also!
|
||||
gun._.node = cb.node;
|
||||
if(Gun.fns.is(cb)){ cb.call(gun, null, Gun.obj.copy(gun._.node)) } // frozen copy
|
||||
@ -284,11 +285,11 @@
|
||||
cb = cb || function(){};
|
||||
if(Gun.obj.is(key)){ // if key is an object then we get the soul directly from it because the node might not exist in cache.
|
||||
Gun.obj.map(key, function(soul, field){ return key = field, cb.soul = soul });
|
||||
cb.node = gun.__.keys[key] = gun.__.graph[cb.soul]; // if it is cached, then it is important to reference it.
|
||||
} else { // else the node does exist in cache and we will get the soul from it instead, plus link the key.
|
||||
cb.node = gun.__.keys[key] = gun._.node;
|
||||
}
|
||||
if(Gun.fns.is(gun.__.opt.hooks.key)){
|
||||
console.log("UGLY UGLY UGLY UGLY", key, cb.soul, cb.node);
|
||||
gun.__.opt.hooks.key(key, cb.soul || (cb.node||{_:{}})._[Gun._.soul], function(err, data){
|
||||
//Gun.log.call(gun, "key made", key);
|
||||
if(err){ return cb(err) }
|
||||
@ -300,16 +301,16 @@
|
||||
});
|
||||
if(!gun.back){ gun.shot('then').fire() }
|
||||
return gun;
|
||||
}
|
||||
}
|
||||
/*
|
||||
how many different ways can we get something?
|
||||
Find via a singular path
|
||||
Find via a singular path
|
||||
.path('blah').get(blah);
|
||||
Find via multiple paths with the callback getting called many times
|
||||
.path('foo', 'bar').get(foorOrBar);
|
||||
Find via multiple paths with the callback getting called once with matching arguments
|
||||
.path('foo', 'bar').get(foo, bar)
|
||||
Find via multiple paths with the result aggregated into an object of pre-given fields
|
||||
Find via multiple paths with the result aggregated into an object of pre-given fields
|
||||
.path('foo', 'bar').get({foo: foo, bar: bar}) || .path({a: 'foo', b: 'bar'}).get({a: foo, b: bar})
|
||||
Find via multiple paths where the fields and values must match
|
||||
.path({foo: val, bar: val}).get({})
|
||||
@ -515,7 +516,7 @@
|
||||
Util.obj.del = function(o, k){
|
||||
if(!o){ return }
|
||||
o[k] = null;
|
||||
delete o[k];
|
||||
delete o[k];
|
||||
return true;
|
||||
}
|
||||
Util.obj.ify = function(o){
|
||||
@ -609,7 +610,7 @@
|
||||
return me;
|
||||
}
|
||||
return Chain;
|
||||
}());
|
||||
}());
|
||||
return Flow;
|
||||
}());Gun.shot.chain.chain.fire=Gun.shot.chain.chain.pipe;
|
||||
;Gun.on=(function(){
|
||||
@ -772,7 +773,7 @@
|
||||
if(field !== Gun._.soul){
|
||||
context.err = err;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
if(unique[soul]){ return }
|
||||
unique[soul] = 1;
|
||||
map(val);
|
||||
@ -873,7 +874,7 @@
|
||||
}
|
||||
Gun.obj.map(gun.__.opt.peers, function(peer, url){
|
||||
request(url, meta, function(err, reply){
|
||||
console.log("gun key done", soul, err, reply);
|
||||
//console.log("gun key done", soul, err, reply);
|
||||
if(err || !reply){
|
||||
Gun.log.call(gun, err = err || "Error: Key failed to be made on " + url);
|
||||
// tab.key(key, soul, cb); // naive implementation of retry TODO: BUG: need backoff and anti-infinite-loop!
|
||||
@ -888,11 +889,11 @@
|
||||
cb = cb || function(){};
|
||||
// TODO: batch and throttle later.
|
||||
//tab.store.set(cb.id = 'send/' + Gun.text.random(), nodes);
|
||||
console.log("gun set start");
|
||||
//console.log("gun set start");
|
||||
Gun.obj.map(gun.__.opt.peers, function(peer, url){
|
||||
request(url, nodes, function respond(err, reply, id){
|
||||
console.log("gun set done", err, reply, id);
|
||||
|
||||
//console.log("gun set done", err, reply, id);
|
||||
|
||||
return;
|
||||
var body = reply && reply.body;
|
||||
respond.id = respond.id || cb.id;
|
||||
@ -1018,7 +1019,7 @@
|
||||
js.parentNode.removeChild(js);
|
||||
window[cb.id] = null; // TODO! BUG: This needs to handle chunking!
|
||||
try{delete window[cb.id];
|
||||
}catch(e){}
|
||||
}catch(e){}
|
||||
}
|
||||
js.async = true;
|
||||
document.getElementsByTagName('head')[0].appendChild(js);
|
||||
@ -1082,4 +1083,4 @@
|
||||
}
|
||||
return r;
|
||||
}());
|
||||
}({}));
|
||||
}({}));
|
||||
|
32
lib/wsp.js
32
lib/wsp.js
@ -107,6 +107,7 @@
|
||||
key = {};
|
||||
key[Gun._.soul] = req.url.query[Gun._.soul];
|
||||
}
|
||||
console.log("transport.loading key ->", key, gun.__.graph, gun.__.keys);
|
||||
gun.load(key, function(err, node){
|
||||
//tran.sub.scribe(req.tab, node._[Gun._.soul]);
|
||||
cb({headers: reply.headers, body: (err? (err.err? err : {err: err || "Unknown error."}) : node || null)});
|
||||
@ -119,30 +120,37 @@
|
||||
if(!req.body){ return cb({headers: reply.headers, body: {err: "No body"}}) }
|
||||
if(tran.post.key(req, cb)){ return }
|
||||
// saving
|
||||
Gun.obj.map(req.body, function(node, soul){
|
||||
Gun.obj.map(req.body, function(node, soul){ // iterate over every node
|
||||
if(soul != Gun.is.soul.on(node)){ return this.end("No soul!") }
|
||||
gun.load(node._, this.add(soul));
|
||||
gun.load(node._, this.add(soul)); // and begin loading it in case it is not cached.
|
||||
}, Gun.fns.sum(function(err){
|
||||
if(err){ return cb({headers: reply.headers, body: {err: err}}) }
|
||||
gun.union(req.body, function(err, context){
|
||||
if(err || context.err || !context.nodes){ return cb({headers: reply.headers, body: {err: err || context.err || "Union failed." }}) }
|
||||
if(err){ return reply.err = err }
|
||||
reply.loaded = true;
|
||||
}));
|
||||
// could there be a timing error somewhere in here?
|
||||
setImmediate(function(){ // do not do it right away because gun.load above is async, this should be cleaner.
|
||||
var context = gun.union(req.body, function check(err, ctx){ // check if the body is valid, and get it into cache immediately.
|
||||
context = ctx || context;
|
||||
if(err || reply.err || context.err || !context.nodes){ return cb({headers: reply.headers, body: {err: err || reply.err || context.err || "Union failed." }}) }
|
||||
if(!Gun.fns.is(gun.__.opt.hooks.set)){ return cb({headers: reply.headers, body: {err: "Persistence not supported." }}) }
|
||||
if(!reply.loaded){ return setTimeout(check, 2) } // only persist if all nodes have been loaded into cache.
|
||||
gun.__.opt.hooks.set(context.nodes, function(err, data){ // since we've already manually done the union, we can now directly call the persistence layer.
|
||||
if(err){ return cb({headers: reply.headers, body: {err: err || "Persistence failed." }}) }
|
||||
cb({headers: reply.headers, body: {ok: "Persisted."}});
|
||||
});
|
||||
});
|
||||
}));
|
||||
});
|
||||
gun.server.on('network').emit(req);
|
||||
}
|
||||
tran.post.key = function(req, cb){ // key hook!
|
||||
if(!req || !req.url || !req.url.key || !Gun.obj.has(req.body, Gun._.soul)){ return }
|
||||
var index = {};
|
||||
index[req.url.key] = req.body[Gun._.soul];
|
||||
console.log("NASTY INDEX", index);
|
||||
gun.key(index, function(err, reply){
|
||||
if(err){ return cb({headers: {'Content-Type': tran.json}, body: {err: err}}) }
|
||||
cb({headers: {'Content-Type': tran.json}, body: reply});
|
||||
var load = {}, index = {}, soul;
|
||||
soul = load[Gun._.soul] = index[req.url.key] = req.body[Gun._.soul];
|
||||
gun.load(load, function(e,r){
|
||||
gun.key(index, function(err, reply){
|
||||
if(err){ return cb({headers: {'Content-Type': tran.json}, body: {err: err}}) }
|
||||
cb({headers: {'Content-Type': tran.json}, body: reply});
|
||||
});
|
||||
});
|
||||
return true;
|
||||
}
|
||||
|
1348
web/img/devices.svg
1348
web/img/devices.svg
File diff suppressed because it is too large
Load Diff
Before Width: | Height: | Size: 12 KiB After Width: | Height: | Size: 69 KiB |
47
web/img/stand.svg
Normal file
47
web/img/stand.svg
Normal file
@ -0,0 +1,47 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
version="1.1"
|
||||
width="104.80719"
|
||||
height="52.775127"
|
||||
id="svg7584">
|
||||
<defs
|
||||
id="defs7586" />
|
||||
<metadata
|
||||
id="metadata7589">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title></dc:title>
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g
|
||||
transform="translate(-304.73926,-448.83176)"
|
||||
id="layer1">
|
||||
<g
|
||||
transform="translate(176.16559,-378.81147)"
|
||||
id="g7567">
|
||||
<path
|
||||
d="m 151.79064,827.64323 58.37326,0 6.88337,46.98126 -72.14001,0 z"
|
||||
id="rect3979"
|
||||
style="fill:#868686;fill-opacity:1" />
|
||||
<rect
|
||||
width="104.80719"
|
||||
height="7.1926503"
|
||||
x="128.57367"
|
||||
y="873.22571"
|
||||
id="rect3982"
|
||||
style="fill:#868686;fill-opacity:1" />
|
||||
</g>
|
||||
</g>
|
||||
</svg>
|
After Width: | Height: | Size: 1.2 KiB |
@ -27,7 +27,7 @@
|
||||
font-family: 'Oxygen', Candara, Calibri, Segoe, "Segoe UI", Optima, Arial, sans-serif;
|
||||
}
|
||||
pre {
|
||||
background-color: black;
|
||||
background-color: black;
|
||||
border: 1px dashed white;
|
||||
color: white;
|
||||
line-height: 1.5em;
|
||||
@ -64,7 +64,26 @@
|
||||
width: 30%;
|
||||
padding: 2em;
|
||||
}
|
||||
.svg {
|
||||
background: white url('./img/devices.svg') no-repeat 50% 50%;
|
||||
height: 40em;
|
||||
}
|
||||
</style>
|
||||
<div class="html" style="width: 100%; height: 40em; margin:0;padding:0;">
|
||||
|
||||
<div class="desktop" style="height: 10em; width: 17em; position: absolute; top: 40%; left: 20%;">
|
||||
<div class="monitor" style="height: 100%; width: 100%; background: #222; padding: .75em; margin-left: -.75em; border-radius: 1em;">
|
||||
<div class="monitor" style="height: 100%; width: 100%; background: #999;">
|
||||
</div>
|
||||
</div>
|
||||
<center><img src="./img/stand.svg" style="margin-top: 1px;"></img></center>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
<div class="svg">
|
||||
AWESOME SAUCE COLOR SYNCING
|
||||
</div>
|
||||
|
||||
<div class="center">
|
||||
<h1 class="lean">Easiest . Database . Ever</h1>
|
||||
<h2 class="lean">Scale without pain, because it is decentralized.</h2>
|
||||
@ -90,7 +109,7 @@ gun.set({hello: 'world'}).key('<span class="random">my/first/data</span>');</pre
|
||||
</div>
|
||||
-->
|
||||
</div>
|
||||
|
||||
|
||||
<div id="step2" class="step">
|
||||
Let's test to see if the data got saved.
|
||||
<ol>
|
||||
@ -101,7 +120,7 @@ gun.set({hello: 'world'}).key('<span class="random">my/first/data</span>');</pre
|
||||
<textarea style="width: 100%; height: 100px;">// Your data will log here!</textarea>
|
||||
The next level will be unlocked when you complete the realtime sync between tabs.
|
||||
</div>
|
||||
|
||||
|
||||
<div id="step3" class="step">
|
||||
<pre>var gun = Gun('http://localhost:8888/gun');
|
||||
gun.load('<span class="random">my/first/data</span>', function(err, data){
|
||||
@ -112,7 +131,7 @@ gun.load('<span class="random">my/first/data</span>', function(err, data){
|
||||
</button></a> Does the key match from the previous tab?
|
||||
<textarea style="width: 100%; height: 100px;">// Your data will log here!</textarea>
|
||||
</div>
|
||||
|
||||
|
||||
<div id="step4" class="step">
|
||||
Now let's listen to realtime updates, and change the value on the 'hello' field.
|
||||
<pre>gun.load('<span class="random">my/first/data</span>')
|
||||
@ -124,10 +143,10 @@ gun.load('<span class="random">my/first/data</span>', function(err, data){
|
||||
</button></a>
|
||||
<textarea style="width: 100%; height: 100px;">// Your data will log here!</textarea>
|
||||
</div>
|
||||
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
|
||||
|
||||
<div class="grid">
|
||||
<div class="learn unit center">
|
||||
<h1 class="lean">Did you know?</h1>
|
||||
@ -176,7 +195,7 @@ gun.load('<span class="random">my/first/data</span>', function(err, data){
|
||||
demo.step1 = function(){
|
||||
demo.step0();
|
||||
gun.set({hello: 'world'}).key(demo.random);
|
||||
|
||||
|
||||
// and also do this, so we can unlock!
|
||||
gun.load(demo.random)
|
||||
.on(function(updates){
|
||||
@ -207,4 +226,4 @@ gun.load('<span class="random">my/first/data</span>', function(err, data){
|
||||
</script>
|
||||
<a href="https://github.com/amark/gun"><img style="position: absolute; top: 0; right: 0; border: 0;" src="https://camo.githubusercontent.com/38ef81f8aca64bb9a64448d0d70f1308ef5341ab/68747470733a2f2f73332e616d617a6f6e6177732e636f6d2f6769746875622f726962626f6e732f666f726b6d655f72696768745f6461726b626c75655f3132313632312e706e67" alt="Fork me on GitHub" data-canonical-src="https://s3.amazonaws.com/github/ribbons/forkme_right_darkblue_121621.png"></a>
|
||||
</body>
|
||||
</html>
|
||||
</html>
|
||||
|
Loading…
x
Reference in New Issue
Block a user