aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAlexander Sulfrian <alexander@sulfrian.net>2011-01-29 14:00:40 +0100
committerAlexander Sulfrian <alexander@sulfrian.net>2011-01-29 14:00:40 +0100
commitd857e652d28ab6988b60d3d72e3b4432d0125eaf (patch)
tree5ad69e6d738102bcd7fdd19034ea5efed8c36b84
parenta9a2daeebf8ef351b3efe74549026ce7619873ff (diff)
parentdb5acf7cda7855bb22660f993cc0c25dd27bf631 (diff)
downloadosm-xapi-d857e652d28ab6988b60d3d72e3b4432d0125eaf.tar.gz
osm-xapi-d857e652d28ab6988b60d3d72e3b4432d0125eaf.tar.xz
osm-xapi-d857e652d28ab6988b60d3d72e3b4432d0125eaf.zip
Merge remote branch 'upstream/master'
Conflicts: src/nodejs/main.js
-rw-r--r--src/nodejs/alternative/xapi-peg-grammar.peg48
-rw-r--r--src/nodejs/alternative/xapi-peg-parser.js151
-rw-r--r--src/nodejs/main.js240
-rw-r--r--src/nodejs/parse.js155
-rw-r--r--src/nodejs/tests/pathparsing.js8
-rw-r--r--src/nodejs/tests/urlToResObj.js63
-rw-r--r--src/nodejs/xmlGenerator.js29
7 files changed, 524 insertions, 170 deletions
diff --git a/src/nodejs/alternative/xapi-peg-grammar.peg b/src/nodejs/alternative/xapi-peg-grammar.peg
new file mode 100644
index 0000000..d9f5547
--- /dev/null
+++ b/src/nodejs/alternative/xapi-peg-grammar.peg
@@ -0,0 +1,48 @@
+Expr ← Path Type XPath?
+Path ← "/"
+Type ← WildCard / "node" / "way" / "relation"
+XPath ← Bbox (Tag Child?)? / Bbox Child Tag? / Tag (Bbox Child?)? / Tag Child Bbox? / Child (Tag Bbox?)? / Child Bbox Tag?
+Bbox ← LeftBracket BboxPredicate RightBracket
+Tag ← LeftBracket TagPredicate RightBracket
+Child ← LeftBracket ChildPredicate RightBracket
+
+BboxPredicate ← [bB] [bB] [oO] [xX] Equals Left Komma Bottom Komma Right Komma Top
+Left ← Coordinate
+Bottom ← Coordinate
+Right ← Coordinate
+Top ← Coordinate
+Coordinate ← Sign? Double / Sign? Integer
+
+TagPredicate ← Keys Equals Vals
+
+Keys ← Key (Pipe Key)*
+Key ← Chars
+Vals ← WildCard / Val
+Val ← Chars Pipe Keys / Chars
+
+Chars ← Char (Char)*
+SpecialChar ← Escape Special
+Special ← Equals / LeftBracket / RightBracket / LeftParent / RightParent / Pipe / Backslash
+Space ← [ U+0020 ]
+Equals ← [ U+003D ]
+Escape ← [ U+005C ]
+LeftBracket ← [ U+005B ]
+RightBracket ← [ U+005D ]
+LeftParent ← [ U+0028 ]
+RightParent ← [ U+0029 ]
+Backslash ← [ U+005C ]
+Pipe ← [ U+007C ]
+Char ← SpecialChar / [U+0021-U+0027] / [U+002B-U+003C] / [U+003E-U+005A] / [U+005C] / [U+005E-U+007B] / [U+007D-U+FFFF]
+
+ChildPredicate ← "nd" / "not(nd)" / "tag" / "not(tag)" / "not(tag)" / "way" / "not(way)" / "node" / "not(node)" / "relation" / "not(relation)"
+
+Integer ← "0" / Sign? [1-9] [0-9]*
+Double ← Integer "." [0-9]*
+Sign ← "+" / "-"
+Empty ← ""
+
+Dot ← "."
+Komma ← ","
+WildCard ← "*"
+CR ← [U+0013]
+LF ← [U+000A] \ No newline at end of file
diff --git a/src/nodejs/alternative/xapi-peg-parser.js b/src/nodejs/alternative/xapi-peg-parser.js
new file mode 100644
index 0000000..45345c5
--- /dev/null
+++ b/src/nodejs/alternative/xapi-peg-parser.js
@@ -0,0 +1,151 @@
+function parseToXML(string){
+ var res = Expr(string);
+ return (res[0] ? f(res[1],0,string) : 'parse error')
+ function f(n,p,s){
+ var ret,i,l
+ if (n[0] == -1)
+ return string.substring(p,p+n[1])
+ ret = '<' + Expr.names[n[0]] + ' raw="' + string.substring(p,p+n[1]) + '">';
+ for(i=0 , l=n[2].length ; i<l ; i++)
+ {
+ ret += '\n' + f(n[2][i],p,s)
+ p += n[2][i][1]
+ }
+ ret += '\n' + '<\\' + Expr.names[n[0]]+'>'
+ return ret.replace(/\n/g,'\n ')
+ }
+}
+
+function Expr(str){
+ var tbl=[],pos=0,l=str.length+1;while(l--)tbl.push([]);l=str.length;
+ function Expr(a){var x,p=pos,c;if(x=tbl[p][0]){pos=x[1];a.push([p,0]);return 1}if(x==false){return 0}c=[];return fin(c,p,0,_Expr(c),a)}
+ function Path(a){var x,p=pos,c;if(x=tbl[p][1]){pos=x[1];a.push([p,1]);return 1}if(x==false){return 0}c=[];return fin(c,p,1,_Path(c),a)}
+ function Type(a){var x,p=pos,c;if(x=tbl[p][2]){pos=x[1];a.push([p,2]);return 1}if(x==false){return 0}c=[];return fin(c,p,2,_Type(c),a)}
+ function XPath(a){var x,p=pos,c;if(x=tbl[p][3]){pos=x[1];a.push([p,3]);return 1}if(x==false){return 0}c=[];return fin(c,p,3,_XPath(c),a)}
+ function Bbox(a){var x,p=pos,c;if(x=tbl[p][4]){pos=x[1];a.push([p,4]);return 1}if(x==false){return 0}c=[];return fin(c,p,4,_Bbox(c),a)}
+ function Tag(a){var x,p=pos,c;if(x=tbl[p][5]){pos=x[1];a.push([p,5]);return 1}if(x==false){return 0}c=[];return fin(c,p,5,_Tag(c),a)}
+ function Child(a){var x,p=pos,c;if(x=tbl[p][6]){pos=x[1];a.push([p,6]);return 1}if(x==false){return 0}c=[];return fin(c,p,6,_Child(c),a)}
+ function BboxPredicate(a){var x,p=pos,c;if(x=tbl[p][7]){pos=x[1];a.push([p,7]);return 1}if(x==false){return 0}c=[];return fin(c,p,7,_BboxPredicate(c),a)}
+ function Left(a){var x,p=pos,c;if(x=tbl[p][8]){pos=x[1];a.push([p,8]);return 1}if(x==false){return 0}c=[];return fin(c,p,8,_Left(c),a)}
+ function Bottom(a){var x,p=pos,c;if(x=tbl[p][9]){pos=x[1];a.push([p,9]);return 1}if(x==false){return 0}c=[];return fin(c,p,9,_Bottom(c),a)}
+ function Right(a){var x,p=pos,c;if(x=tbl[p][10]){pos=x[1];a.push([p,10]);return 1}if(x==false){return 0}c=[];return fin(c,p,10,_Right(c),a)}
+ function Top(a){var x,p=pos,c;if(x=tbl[p][11]){pos=x[1];a.push([p,11]);return 1}if(x==false){return 0}c=[];return fin(c,p,11,_Top(c),a)}
+ function Coordinate(a){var x,p=pos,c;if(x=tbl[p][12]){pos=x[1];a.push([p,12]);return 1}if(x==false){return 0}c=[];return fin(c,p,12,_Coordinate(c),a)}
+ function TagPredicate(a){var x,p=pos,c;if(x=tbl[p][13]){pos=x[1];a.push([p,13]);return 1}if(x==false){return 0}c=[];return fin(c,p,13,_TagPredicate(c),a)}
+ function Keys(a){var x,p=pos,c;if(x=tbl[p][14]){pos=x[1];a.push([p,14]);return 1}if(x==false){return 0}c=[];return fin(c,p,14,_Keys(c),a)}
+ function Key(a){var x,p=pos,c;if(x=tbl[p][15]){pos=x[1];a.push([p,15]);return 1}if(x==false){return 0}c=[];return fin(c,p,15,_Key(c),a)}
+ function Vals(a){var x,p=pos,c;if(x=tbl[p][16]){pos=x[1];a.push([p,16]);return 1}if(x==false){return 0}c=[];return fin(c,p,16,_Vals(c),a)}
+ function Val(a){var x,p=pos,c;if(x=tbl[p][17]){pos=x[1];a.push([p,17]);return 1}if(x==false){return 0}c=[];return fin(c,p,17,_Val(c),a)}
+ function Chars(a){var x,p=pos,c;if(x=tbl[p][18]){pos=x[1];a.push([p,18]);return 1}if(x==false){return 0}c=[];return fin(c,p,18,_Chars(c),a)}
+ function SpecialChar(a){var x,p=pos,c;if(x=tbl[p][19]){pos=x[1];a.push([p,19]);return 1}if(x==false){return 0}c=[];return fin(c,p,19,_SpecialChar(c),a)}
+ function Special(a){var x,p=pos,c;if(x=tbl[p][20]){pos=x[1];a.push([p,20]);return 1}if(x==false){return 0}c=[];return fin(c,p,20,_Special(c),a)}
+ function Space(a){var x,p=pos,c;if(x=tbl[p][21]){pos=x[1];a.push([p,21]);return 1}if(x==false){return 0}c=[];return fin(c,p,21,_Space(c),a)}
+ function Equals(a){var x,p=pos,c;if(x=tbl[p][22]){pos=x[1];a.push([p,22]);return 1}if(x==false){return 0}c=[];return fin(c,p,22,_Equals(c),a)}
+ function Escape(a){var x,p=pos,c;if(x=tbl[p][23]){pos=x[1];a.push([p,23]);return 1}if(x==false){return 0}c=[];return fin(c,p,23,_Escape(c),a)}
+ function LeftBracket(a){var x,p=pos,c;if(x=tbl[p][24]){pos=x[1];a.push([p,24]);return 1}if(x==false){return 0}c=[];return fin(c,p,24,_LeftBracket(c),a)}
+ function RightBracket(a){var x,p=pos,c;if(x=tbl[p][25]){pos=x[1];a.push([p,25]);return 1}if(x==false){return 0}c=[];return fin(c,p,25,_RightBracket(c),a)}
+ function LeftParent(a){var x,p=pos,c;if(x=tbl[p][26]){pos=x[1];a.push([p,26]);return 1}if(x==false){return 0}c=[];return fin(c,p,26,_LeftParent(c),a)}
+ function RightParent(a){var x,p=pos,c;if(x=tbl[p][27]){pos=x[1];a.push([p,27]);return 1}if(x==false){return 0}c=[];return fin(c,p,27,_RightParent(c),a)}
+ function Backslash(a){var x,p=pos,c;if(x=tbl[p][28]){pos=x[1];a.push([p,28]);return 1}if(x==false){return 0}c=[];return fin(c,p,28,_Backslash(c),a)}
+ function Pipe(a){var x,p=pos,c;if(x=tbl[p][29]){pos=x[1];a.push([p,29]);return 1}if(x==false){return 0}c=[];return fin(c,p,29,_Pipe(c),a)}
+ function Char(a){var x,p=pos,c;if(x=tbl[p][30]){pos=x[1];a.push([p,30]);return 1}if(x==false){return 0}c=[];return fin(c,p,30,_Char(c),a)}
+ function ChildPredicate(a){var x,p=pos,c;if(x=tbl[p][31]){pos=x[1];a.push([p,31]);return 1}if(x==false){return 0}c=[];return fin(c,p,31,_ChildPredicate(c),a)}
+ function Integer(a){var x,p=pos,c;if(x=tbl[p][32]){pos=x[1];a.push([p,32]);return 1}if(x==false){return 0}c=[];return fin(c,p,32,_Integer(c),a)}
+ function Double(a){var x,p=pos,c;if(x=tbl[p][33]){pos=x[1];a.push([p,33]);return 1}if(x==false){return 0}c=[];return fin(c,p,33,_Double(c),a)}
+ function Sign(a){var x,p=pos,c;if(x=tbl[p][34]){pos=x[1];a.push([p,34]);return 1}if(x==false){return 0}c=[];return fin(c,p,34,_Sign(c),a)}
+ function Empty(a){var x,p=pos,c;if(x=tbl[p][35]){pos=x[1];a.push([p,35]);return 1}if(x==false){return 0}c=[];return fin(c,p,35,_Empty(c),a)}
+ function Dot(a){var x,p=pos,c;if(x=tbl[p][36]){pos=x[1];a.push([p,36]);return 1}if(x==false){return 0}c=[];return fin(c,p,36,_Dot(c),a)}
+ function Komma(a){var x,p=pos,c;if(x=tbl[p][37]){pos=x[1];a.push([p,37]);return 1}if(x==false){return 0}c=[];return fin(c,p,37,_Komma(c),a)}
+ function WildCard(a){var x,p=pos,c;if(x=tbl[p][38]){pos=x[1];a.push([p,38]);return 1}if(x==false){return 0}c=[];return fin(c,p,38,_WildCard(c),a)}
+ function CR(a){var x,p=pos,c;if(x=tbl[p][39]){pos=x[1];a.push([p,39]);return 1}if(x==false){return 0}c=[];return fin(c,p,39,_CR(c),a)}
+ function LF(a){var x,p=pos,c;if(x=tbl[p][40]){pos=x[1];a.push([p,40]);return 1}if(x==false){return 0}c=[];return fin(c,p,40,_LF(c),a)}
+ var _Expr=q(Path,Type,r(0,1,XPath))
+ var _Path=sl_0
+ var _Type=o(WildCard,sl_1,sl_2,sl_3)
+ var _XPath=o(q(Bbox,r(0,1,q(Tag,r(0,1,Child)))),q(Bbox,Child,r(0,1,Tag)),q(Tag,r(0,1,q(Bbox,r(0,1,Child)))),q(Tag,Child,r(0,1,Bbox)),q(Child,r(0,1,q(Tag,r(0,1,Bbox)))),q(Child,Bbox,r(0,1,Tag)))
+ var _Bbox=q(LeftBracket,BboxPredicate,RightBracket)
+ var _Tag=q(LeftBracket,TagPredicate,RightBracket)
+ var _Child=q(LeftBracket,ChildPredicate,RightBracket)
+ var _BboxPredicate=q(cs_0,cs_0,cs_1,cs_2,Equals,Left,Komma,Bottom,Komma,Right,Komma,Top)
+ var _Left=Coordinate
+ var _Bottom=Coordinate
+ var _Right=Coordinate
+ var _Top=Coordinate
+ var _Coordinate=o(q(r(0,1,Sign),Double),q(r(0,1,Sign),Integer))
+ var _TagPredicate=q(Keys,Equals,Vals)
+ var _Keys=q(Key,r(0,0,q(Pipe,Key)))
+ var _Key=Chars
+ var _Vals=o(WildCard,Val)
+ var _Val=o(q(Chars,Pipe,Keys),Chars)
+ var _Chars=q(Char,r(0,0,Char))
+ var _SpecialChar=q(Escape,Special)
+ var _Special=o(Equals,LeftBracket,RightBracket,LeftParent,RightParent,Pipe,Backslash)
+ var _Space=cs_3
+ var _Equals=cs_4
+ var _Escape=cs_5
+ var _LeftBracket=cs_6
+ var _RightBracket=cs_7
+ var _LeftParent=cs_8
+ var _RightParent=cs_9
+ var _Backslash=cs_5
+ var _Pipe=cs_10
+ var _Char=o(SpecialChar,cs_11,cs_12,cs_13,cs_5,cs_14,cs_15)
+ var _ChildPredicate=o(sl_4,sl_5,sl_6,sl_7,sl_7,sl_2,sl_8,sl_1,sl_9,sl_3,sl_10)
+ var _Integer=o(sl_11,q(r(0,1,Sign),cs_16,r(0,0,cs_17)))
+ var _Double=q(Integer,sl_12,r(0,0,cs_17))
+ var _Sign=o(sl_13,sl_14)
+ var _Empty=e
+ var _Dot=sl_12
+ var _Komma=sl_15
+ var _WildCard=sl_16
+ var _CR=cs_18
+ var _LF=cs_19
+ function cs_0(){var c,x;if(pos==l)return false;c=g(pos);x=c<67?c<66?0:1:c<98?0:c<99?1:0;if(x){pos++;return true}return false}
+ function cs_1(){var c,x;if(pos==l)return false;c=g(pos);x=c<80?c<79?0:1:c<111?0:c<112?1:0;if(x){pos++;return true}return false}
+ function cs_2(){var c,x;if(pos==l)return false;c=g(pos);x=c<89?c<88?0:1:c<120?0:c<121?1:0;if(x){pos++;return true}return false}
+ function cs_3(){var c,x;if(pos==l)return false;c=g(pos);x=c<32?0:c<33?1:0;if(x){pos++;return true}return false}
+ function cs_4(){var c,x;if(pos==l)return false;c=g(pos);x=c<61?0:c<62?1:0;if(x){pos++;return true}return false}
+ function cs_5(){var c,x;if(pos==l)return false;c=g(pos);x=c<92?0:c<93?1:0;if(x){pos++;return true}return false}
+ function cs_6(){var c,x;if(pos==l)return false;c=g(pos);x=c<91?0:c<92?1:0;if(x){pos++;return true}return false}
+ function cs_7(){var c,x;if(pos==l)return false;c=g(pos);x=c<93?0:c<94?1:0;if(x){pos++;return true}return false}
+ function cs_8(){var c,x;if(pos==l)return false;c=g(pos);x=c<40?0:c<41?1:0;if(x){pos++;return true}return false}
+ function cs_9(){var c,x;if(pos==l)return false;c=g(pos);x=c<41?0:c<42?1:0;if(x){pos++;return true}return false}
+ function cs_10(){var c,x;if(pos==l)return false;c=g(pos);x=c<124?0:c<125?1:0;if(x){pos++;return true}return false}
+ function cs_11(){var c,x;if(pos==l)return false;c=g(pos);x=c<33?0:c<40?1:0;if(x){pos++;return true}return false}
+ function cs_12(){var c,x;if(pos==l)return false;c=g(pos);x=c<43?0:c<61?1:0;if(x){pos++;return true}return false}
+ function cs_13(){var c,x;if(pos==l)return false;c=g(pos);x=c<62?0:c<91?1:0;if(x){pos++;return true}return false}
+ function cs_14(){var c,x;if(pos==l)return false;c=g(pos);x=c<94?0:c<124?1:0;if(x){pos++;return true}return false}
+ function cs_15(){var c,x;if(pos==l)return false;c=g(pos);x=c<125?0:c<65536?1:0;if(x){pos++;return true}return false}
+ function cs_16(){var c,x;if(pos==l)return false;c=g(pos);x=c<49?0:c<58?1:0;if(x){pos++;return true}return false}
+ function cs_17(){var c,x;if(pos==l)return false;c=g(pos);x=c<48?0:c<58?1:0;if(x){pos++;return true}return false}
+ function cs_18(){var c,x;if(pos==l)return false;c=g(pos);x=c<19?0:c<20?1:0;if(x){pos++;return true}return false}
+ function cs_19(){var c,x;if(pos==l)return false;c=g(pos);x=c<10?0:c<11?1:0;if(x){pos++;return true}return false}
+ function sl_0(){var p=pos;if(str.charCodeAt(p)==47){pos+=1;return true}return false}
+ function sl_1(){var p=pos;if(str.charCodeAt(p++)==110&&str.charCodeAt(p++)==111&&str.charCodeAt(p++)==100&&str.charCodeAt(p)==101){pos+=4;return true}return false}
+ function sl_2(){var p=pos;if(str.charCodeAt(p++)==119&&str.charCodeAt(p++)==97&&str.charCodeAt(p)==121){pos+=3;return true}return false}
+ function sl_3(){var p=pos;if(str.charCodeAt(p++)==114&&str.charCodeAt(p++)==101&&str.charCodeAt(p++)==108&&str.charCodeAt(p++)==97&&str.charCodeAt(p++)==116&&str.charCodeAt(p++)==105&&str.charCodeAt(p++)==111&&str.charCodeAt(p)==110){pos+=8;return true}return false}
+ function sl_4(){var p=pos;if(str.charCodeAt(p++)==110&&str.charCodeAt(p)==100){pos+=2;return true}return false}
+ function sl_5(){var p=pos;if(str.charCodeAt(p++)==110&&str.charCodeAt(p++)==111&&str.charCodeAt(p++)==116&&str.charCodeAt(p++)==40&&str.charCodeAt(p++)==110&&str.charCodeAt(p++)==100&&str.charCodeAt(p)==41){pos+=7;return true}return false}
+ function sl_6(){var p=pos;if(str.charCodeAt(p++)==116&&str.charCodeAt(p++)==97&&str.charCodeAt(p)==103){pos+=3;return true}return false}
+ function sl_7(){var p=pos;if(str.charCodeAt(p++)==110&&str.charCodeAt(p++)==111&&str.charCodeAt(p++)==116&&str.charCodeAt(p++)==40&&str.charCodeAt(p++)==116&&str.charCodeAt(p++)==97&&str.charCodeAt(p++)==103&&str.charCodeAt(p)==41){pos+=8;return true}return false}
+ function sl_8(){var p=pos;if(str.charCodeAt(p++)==110&&str.charCodeAt(p++)==111&&str.charCodeAt(p++)==116&&str.charCodeAt(p++)==40&&str.charCodeAt(p++)==119&&str.charCodeAt(p++)==97&&str.charCodeAt(p++)==121&&str.charCodeAt(p)==41){pos+=8;return true}return false}
+ function sl_9(){var x=str.slice(pos,pos+9);if(x=="not(node)"){pos+=9;return true}return false}
+ function sl_10(){var x=str.slice(pos,pos+13);if(x=="not(relation)"){pos+=13;return true}return false}
+ function sl_11(){var p=pos;if(str.charCodeAt(p)==48){pos+=1;return true}return false}
+ function sl_12(){var p=pos;if(str.charCodeAt(p)==46){pos+=1;return true}return false}
+ function sl_13(){var p=pos;if(str.charCodeAt(p)==43){pos+=1;return true}return false}
+ function sl_14(){var p=pos;if(str.charCodeAt(p)==45){pos+=1;return true}return false}
+ function sl_15(){var p=pos;if(str.charCodeAt(p)==44){pos+=1;return true}return false}
+ function sl_16(){var p=pos;if(str.charCodeAt(p)==42){pos+=1;return true}return false}
+ function fin(c,p,x,r,a){if(r)a.push([p,x]);tbl[p][x]=r?[true,pos,c]:false;return r}
+ function e(){return true}
+ function o(){var args=arguments;return function(c){var i,l;for(i=0,l=args.length;i<l;i++)if(args[i](c))return true;return false}}
+ function q(){var args=arguments;return function(c){var i,l,cp=pos,cl=c.length;for(i=0,l=args.length;i<l;i++)if(!args[i](c)){pos=cp;t(c,cl);return false}return true}}
+ function r(m,n,f){return function(c){var i=0,cp=pos,cl=c.length;while(i<m){i++;if(!f(c)){pos=cp;t(c,cl);return false}}cl=c.length;while(i++<n||n==0)if(!f(c))return true;return true}}
+ function n(f){return function(){var p=pos,x=f([]);pos=p;return !x}}
+ function p(f){return function(){var p=pos,x=f([]);pos=p;return x}}
+ function t(a,n){if(a.length>n)a.splice(n)}
+ function g(p){return str.charCodeAt(p)}
+ function b(p,n){var x=tbl[p][n],c=[],a=[n,x[1]-p,c],y=x[2],i=0,l=y.length,z;for(;i<l;i++){z=y[i];if(z[0]>p)c.push([-1,z[0]-p]);c.push(b(z[0],z[1]));p=tbl[z[0]][z[1]][1]}if(p<x[1]&&c.count)c.push([-1,x[1]-p]);return a}
+ return Expr([])&&pos==l?[true,b(0,0)]:[false,pos,tbl]}
+Expr.names=['Expr','Path','Type','XPath','Bbox','Tag','Child','BboxPredicate','Left','Bottom','Right','Top','Coordinate','TagPredicate','Keys','Key','Vals','Val','Chars','SpecialChar','Special','Space','Equals','Escape','LeftBracket','RightBracket','LeftParent','RightParent','Backslash','Pipe','Char','ChildPredicate','Integer','Double','Sign','Empty','Dot','Komma','WildCard','CR','LF']; \ No newline at end of file
diff --git a/src/nodejs/main.js b/src/nodejs/main.js
index a7ff07b..80bd051 100644
--- a/src/nodejs/main.js
+++ b/src/nodejs/main.js
@@ -7,6 +7,7 @@ var opts = require('opts');
var osmRes = require('./response');
var log4js = require('log4js')();
var log = log4js.getLogger('global');
+var parser = require('./parse');
var config;
// #################### MAY be put to different module later
@@ -65,11 +66,11 @@ function rowToWay(row){
'changeset' : row.changeset_id
};
if(row.tags != '{}') {
- node.tags = [];
+ way.tags = [];
// FIXME: something doesnt work at all
temp = row.tags.replace("{","").replace("}","").split(",");
for(var x=0;x<temp.length;x=x+2){
- node.tags.push({
+ way.tags.push({
'k' : temp[x],
'v' : temp[x+1]
});
@@ -80,120 +81,107 @@ function rowToWay(row){
// #################### MAY be put to different module later
+var options = [
+ { short : 'c',
+ long : 'config',
+ description : 'Select configuration file',
+ value : true
+ }
+];
-// #################### my little clutch replacments
-
-
-var urlToXpathObj = function urlToXpathObj(url){
-
- // FIXME: more validaiton
- // filter stars in keys
- // filter no enough arguments
+//
+// {
+// object = node/way/relation/* ,
+// bbox = { left : 1.0 , right : 1.0 , top : 1.0, bottom : 1.0 }
+// tag = { key : [ ], value [ ] }
+// }
+
+
+function buildMainQuery(reqJso){
+
+ var id = 1;
+ var replacements = Array();
+
+ var selectMap = {
+ 'node' : 'id,user_id,tstamp,version,changeset_id,hstore_to_array(tags) as tags, ' +
+ 'X(geom) as lat, Y(geom) as lon',
+ 'way' : 'id,tstamp,version,changeset_id,nodes,user_id,hstore_to_array(tags) as tags ',
+ 'relation' : '' //FIXME: plz
+ }
+
+ // FIXME: help me i am not side effect free
+ function buildTagsQuery(map){
+
+ tagQueries = new Array();
+
+ for(tagkey in map){
+ tagQueries.push("tags @> hstore($" + id++ + ",$" + id++ + ")");
+ replacements.push(tagkey);
+ replacements.push(map[tagkey]);
+ }
- var parseKeyList = function(string){
- result = /(.+)(:?\|(.+))/.exec(string);
- result.shift();
- return result;
+ return tagQueries.join(" OR \n");
}
- var parseBboxList = function(string){
-
- result = /(.+)(:?,(.+)){3}/.exec(string);
-
- if(result.length != 4){
- throw "error";
+ // FIXME: help me i am not side effect free
+ function buildBbox(object,bbox){
+
+ var colName = {
+ node : 'geom',
+ way : 'linestring',
+ relation : '' // FIXME: whats my name
}
- result.shift();
+ bboxQueryStr = colName[object] + ' && st_setsrid(st_makebox2d( ' +
+ ' st_setsrid(st_makepoint($' + id++ + ', $' + id++ + '), 4326), ' +
+ ' st_setsrid(st_makepoint($' + id++ + ', $' + id++ + '), 4326) ' +
+ ' ), 4326) ';
+
+ for( direction in bbox ) {
+ replacements.push(bbox[direction]);
+ }
- return {
- 'left' : result[0],
- 'bottom' : result[1],
- 'right' : result[2],
- 'top' : result[3]
- };
+ return bboxQueryStr;
}
- var xp = {};
-
- result = /\/(*|node|way|relation)(:?\[(.*)=(.*)\])*/.exec(url);
-
- xp.object=result[1];
-
- for(i=2;i<=result.length();i++){
- if(result[i]==="bbox"){
- xp.bbox = parseBboxValues(result[i+1]);
- } else {
- xp.tag ={};
- xp.tag.keys = parseKeyList(result[i]);
- xp.tag.values = parseKeyList(result[i+1]);
+ function explodeTags(keys,values){
+ var map = {};
+ for(key in keys) {
+ for(value in values) {
+ map[keys[key]]=values[value]; // FIXME: das ist scheiße
+ }
}
- i++;
+ return map;
}
-}
-
-
-
-
-
-
-
-// ################## end my little clutch replacments
-
-
-
+
+ query = "SELECT " + selectMap[reqJso.object] + " FROM " + reqJso.object + "s";
+
+ whereClauses = Array();
+ if(reqJso.bbox != undefined){
+ whereClauses.push(buildBbox(reqJso.object,reqJso.bbox));
+ }
+
+ // FIXME: rename tag to tags key to keys value to values
+ if(reqJso.tag != undefined){
+ tags = explodeTags(reqJso.tag.key,reqJso.tag.value);
+ whereClauses.push(buildTagsQuery(tags));
+ }
+ if(whereClauses.length > 0) {
+ query += ' WHERE (' + whereClauses.join(' AND ') + ')';
+ }
-var options = [
- { short : 'c',
- long : 'config',
- description : 'Select configuration file',
- value : true
- }
-];
+ query += ';'
-function createWayBboxQuery(key, value, left, bottom, right, top) {
return {
- text: 'SELECT id,tstamp,version,changeset_id,nodes,user_id,hstore_to_array(tags) as tags ' +
- 'FROM ways ' +
- 'WHERE ( ' +
- ' tags @> hstore($1, $2) AND ' +
- ' linestring && st_setsrid(st_makebox2d( ' +
- ' st_setsrid(st_makepoint($3, $4), 4326), ' +
- ' st_setsrid(st_makepoint($5, $6), 4326) ' +
- ' ), 4326) ' +
- ')',
- values: [key, value, left, bottom, right, top],
- name: 'way bbox query'
- };
+ text:query,
+ values:replacements,
+ name: query
+ };
}
-function createNodeBboxQuery(key, value, left, bottom, right, top) {
- return {
- text: 'SELECT id,user_id,tstamp,version,changeset_id,hstore_to_array(tags) as tags, X(geom) as lat, Y(geom) as lon ' +
- 'FROM nodes ' +
- 'WHERE ( ' +
- ' tags @> hstore($1, $2) AND ' +
- ' geom && st_setsrid(st_makebox2d( ' +
- ' st_setsrid(st_makepoint($3, $4), 4326), ' +
- ' st_setsrid(st_makepoint($5, $6), 4326) ' +
- ' ), 4326) ' +
- ')',
- values: [key, value, left, bottom, right, top],
- name: 'node bbox query'
- };
-}
-function createNodesForWayQuery(nodes) {
- return {
- text: 'SELECT id,tstamp,version,changeset_id,hstore_to_array(tags) as tags, X(geom) as lat, Y(geom) as lon ' +
- 'FROM nodes ' +
- 'WHERE (id = ANY($1))',
- values: [nodes],
- name: 'nodes for way'
- };
-}
function dbConnect(res, callback) {
pg.connect(config.connectionString, function(err, client) {
@@ -251,7 +239,7 @@ function wayBboxHandler(req, res, key, value, left, bottom, right, top) {
dbConnect(res, function(client) {
var count = 0;
var success = false;
- //console.log(createWayBboxQuery(key, value, left, bottom, right, top));
+ console.log(createWayBboxQuery(key, value, left, bottom, right, top));
var query = client.query(createWayBboxQuery(key, value, left, bottom, right, top));
query.on('error', function(err) {
@@ -284,26 +272,46 @@ function wayBboxHandler(req, res, key, value, left, bottom, right, top) {
});
}
-function relationWorldHandler(req, res, key, value) {
- res.writeHead(200, {'Content-Type': 'text/plain'});
- res.end(' key:' +key +' value:'+value+'!\n');
-}
-function relationBboxHandler(req, res, key, value, left, bottom, right, top) {
+function myFunction(req,res){
-}
+ res.writeHead(200);
+
+ var reqObj = parser.urlToXpathObj(req.url);
+
+ var queryDict = buildMainQuery(reqObj);
+
+ var resXml = osmRes.mkXmlRes(res);
+
-myRoutes = clutch.route404([
- //['GET /api/(\\w+)(\\[bbox=(\\d,\\d,\\d,\\d)\\])*\\[(\\w+)=(\\w+)\\]$', helloSomeone],
- ['GET /api/node\\[(\\w+)=(\\w+)\\]$',nodeWorldHandler],
- //['GET /api/node\\[(\\w+)=(\\w+)\\]\\[bbox=(\\d+(\\.\\d+)?),(\\d+),(\\d+),(\\d+)\\]$',nodeBboxHandler],
- ['GET /api/node\\[(\\w+)=(\\w+)\\]\\[bbox=(\\d+(?:\\.\\d+)?),(\\d+(?:\\.\\d+)?),(\\d+(?:\\.\\d+)?),(\\d+(?:\\.\\d+)?)\\]$',nodeBboxHandler],
- //['GET /api/node\\[(\\w+)=(\\w+)\\]\\[bbox=(\\d+\\.\\d+),(\\d+),(\\d+),(\\d+)\\]$',nodeBboxHandler],
- ['GET /api/way\\[(\\w+)=(\\w+)\\]$',wayWorldHandler],
- ['GET /api/way\\[(\\w+)=(\\w+)\\]\\[bbox=(\\d+(?:\\.\\d+)?),(\\d+(?:\\.\\d+)?),(\\d+(?:\\.\\d+)?),(\\d+(?:\\.\\d+)?)\\]$',wayBboxHandler],
- ['GET /api/relation\\[(\\w+)=(\\w+)\\]$',relationWorldHandler]
- //['GET /api/relation\\[(\\w+)=(\\w+)\\](\\[bbox=(\\d),(\\d),(\\d),(\\d)\\])$',relationBboxHandler],
-]);
+ console.log(JSON.stringify(queryDict));
+ console.log("??????????????????????????????");
+ console.log(JSON.stringify(reqObj));
+ dbConnect(resXml, function(client) {
+ var success = false;
+ var query = client.query(queryDict);
+
+ query.on('error', function(err) {
+ res.endWith500();
+ });
+
+ query.on('end', function() {
+ console.log(" EEEND ");
+ res.atEnd();
+ });
+
+ query.on('row', function(row) {
+ //console.log(JSON.stringify(row));
+ if(reqObj.object == "node") {
+ var pojo = rowToNode(row);
+ res.putNode(pojo);
+ }
+ else if(reqObj.object == "way") {
+ var pojo = rowToWay(row);
+ res.putWay(pojo);}
+ });
+ });
+}
function getConfig(configPath, callback) {
if( configPath[0] != '/'){
@@ -323,7 +331,7 @@ function init(newConfig) {
log.setLevel(config.logLevel);
log.info("server starting...");
log.info("loaded config from " + configPath);
- http.createServer(myRoutes).listen(config.port, config.host);
+ http.createServer(myFunction).listen(config.port, config.host);
log.info("Started server at " + config.host + ":" + config.port );
}
diff --git a/src/nodejs/parse.js b/src/nodejs/parse.js
index 0338954..321823b 100644
--- a/src/nodejs/parse.js
+++ b/src/nodejs/parse.js
@@ -1,48 +1,131 @@
-exports.urlToXpathObj = function urlToXpathObj(url){
- // FIXMEresult.shift(): more validaiton
- // filter stars in keys
- // filter no enough arguments
- var parseKeyList = function(string){
- result = /(.+)(:?\|(.+))/.exec(string);
- result.shift();
- return result;
- }
+var parser = function(){
- var parseBboxList = function(string){
+ var offset =0;
+ var expr ="";
- result = /(.+)(:?,(.+)){3}/.exec(string);
+ var keys = [];
+ var values = [];
+ var bbox= {};
+ var object = "";
- if(result.length != 4){
- throw "error";
- }
+ var check = function(char){
+ if (expr.charAt(offset) != char) {
+ throw "Unexpected char " + expr[offset] + " at " + offset + " expected: " + char;
+ }
+ offset ++;
+ }
+
+ var parsePredicate = function(){
+ check('[');
+ parseInnerPredicate();
+ check(']');
+ }
- result.shift();
+ var parseInnerPredicate = function(){
+ tmpKeys=[];
+ parseKeyValue(tmpKeys,'=');
+ check('=');
+ if(tmpKeys.length==1 && tmpKeys[0] == "bbox"){
+ parseBboxValues();
+ } else {
+ keys = tmpKeys;
+ parseKeyValue(values,']');
+ }
+ }
- return {
- 'left' : result[0],
- 'bottom' : result[1],
- 'right' : result[2],
- 'top' : result[3]
- }
- }
-
- var xp = {};
+ var parseBboxValues = function(){
+ bbox.left = parseBboxFloat();
+ check(',');
+ bbox.bottom = parseBboxFloat();
+ check(',');
+ bbox.right = parseBboxFloat();
+ check(',');
+ bbox.top = parseBboxFloat();
+ }
- result = /\/(*|node|way|relation)(:?\[(.*)=(.*)\])*/.exec(url);
+ var parseBboxFloat = function(){
+ var floatStr = "";
+ while(expr[offset]!=',' && expr[offset]!=']' && offset < expr.length){
+ floatStr += expr[offset];
+ offset ++;
+ }
+ return parseFloat(floatStr);
+ }
- xp.object=result[1];
+ var parseKeyValue = function(list,delim){
+ var word = "";
+ while(expr[offset]!=delim && offset < expr.length){
+ if(expr[offset]=='|'){
+ list.push(word);
+ word="";
+ offset ++;
+ continue;
+ }
+ // jump escaped chars
+ if(expr[offset]=='\\'){
+ word += expr[offset];
+ offset ++;
+ }
+ word += expr[offset];
+ offset ++;
+ }
+ list.push(word);
- for(i=2;i<=result.length;i++){
- if(result[i]==="bbox"){
- xp.bbox = parseBboxValues(result[i+1]);
- } else {
- xp.tag ={};
- xp.tag.keys = parseKeyList(result[i]);
- xp.tag.values = parseKeyList(result[i+1]);
- }
- i++;
- }
+ }
+
+ this.parse = function(exprLocal){
+ expr = exprLocal;
+ offset = 0;
+ object = "";
+
+
+
+ check('/');
+
+ for(;expr[offset]!='[' && offset<expr.length;offset++){
+ if(expr[offset] == '/' && offset == expr.length-1){
+ offset ++;
+ break;
+ }
+ object += expr[offset];
+ }
+
+ if (object != "*" && object != "way" && object != "node" && object != "relation"){
+ throw "invalid identifier: " + object;
+ }
+
+
+ for(var i=0; i<3 && offset < expr.length;i++) {
+ parsePredicate();
+ }
+ if (offset < expr.length){
+
+ throw "string longer than excepected";
+ }
+
+ var result = {
+ object : object
+ };
+
+ if(bbox.left != undefined){
+ result.bbox = bbox;
+ }
+
+ if(keys.length > 0){
+
+ result.tag = {
+ key : keys,
+ value : values
+ }
+ }
+ return result;
+ }
}
+
+exports.urlToXpathObj = function urlToXpathObj(url){
+ var parse = new parser();
+ return parse.parse(url);
+}
diff --git a/src/nodejs/tests/pathparsing.js b/src/nodejs/tests/pathparsing.js
index e1a20f5..ebd5baf 100644
--- a/src/nodejs/tests/pathparsing.js
+++ b/src/nodejs/tests/pathparsing.js
@@ -54,7 +54,7 @@ module.exports =
test.ok(true);
var simpleRelationStringTrail = "/relation/";
var expected = { object: "relation" };
- assert.deepEqual(toTest(simpleRelationStringTrail), expectedi);
+ assert.deepEqual(toTest(simpleRelationStringTrail), expected);
test.finish();
}
@@ -78,20 +78,20 @@ module.exports =
, 'tag with two values': function(test) {
test.ok(true);
var nodeWithTwoValues = "/node[tag=foo|bar]";
- var expected = { object: "node", tag: { key:["key"], value:["foo", "bar"]}};
+ var expected = { object: "node", tag: { key:["tag"], value:["foo", "bar"]}};
assert.deepEqual(toTest(nodeWithTwoValues), expected);
test.finish();
}
, 'tag with two keys': function(test) {
test.ok(true);
- var nodeWithTwoKeys = "/node[foo,bar=value]";
+ var nodeWithTwoKeys = "/node[foo|bar=value]";
var expected = { object: "node", tag: { key:["foo", "bar"], value:["value"]}};
assert.deepEqual(toTest(nodeWithTwoKeys), expected);
test.finish();
}
, 'tags with cross product': function(test) {
test.ok(true);
- var tagCrossProduct = "/node[key1,key2=value1,value2]";
+ var tagCrossProduct = "/node[key1|key2=value1|value2]";
var expected = { object: "node", tag: {key:["key1", "key2"], value:["value1", "value2"]}};
assert.deepEqual(toTest(tagCrossProduct), expected);
test.finish();
diff --git a/src/nodejs/tests/urlToResObj.js b/src/nodejs/tests/urlToResObj.js
new file mode 100644
index 0000000..b45edfd
--- /dev/null
+++ b/src/nodejs/tests/urlToResObj.js
@@ -0,0 +1,63 @@
+var assert = require('assert');
+var test = require('../parse.js');
+
+
+//TODO function does not exist yet
+var toTest = test.urlToXpathObj;
+
+
+// test all simple objects { node, way, relation }
+
+var simpleNodeString = "/node";
+var expected = { object: "node" };
+assert.deepEqual(toTest(simpleNodeString), expected);
+
+var simpleNodeStringTrail = "/node/";
+var expected = { object: "node" };
+assert.deepEqual(toTest(simpleNodeStringTrail), expected);
+
+var simpleWayString = "/way";
+var expected = { object: "way" };
+assert.deepEqual(toTest(simpleWayString), expected);
+
+var simpleWayStringTrail = "/way/";
+var expected = { object: "way" };
+assert.deepEqual(toTest(simpleWayStringTrail), expected);
+
+var simpleRelationString = "/relation";
+var expected = { object: "relation" };
+assert.deepEqual(toTest(simpleRelationString), expected);
+
+var simpleRelationStringTrail = "/relation/";
+var expected = { object: "relation" };
+assert.deepEqual(toTest(simpleRelationStringTrail), expected);
+
+// TODO invalid object eg not (node, way, relation)
+
+var nodeWithBbox = "/node[bbox=0,51.5,0.25,51.75]";
+var expected = { object: "node", bbox: {left:0, bottom:51.5, right:0.25, top:51.75} };
+assert.deepEqual(toTest(nodeWithBbox), expected);
+
+var nodeWithSimpleTag = "/node[key=value]";
+var expected = { object: "node", tag: { key:["key"], value:["value"]}};
+assert.deepEqual(toTest(nodeWithSimpleTag), expected);
+
+var nodeWithTwoValues = "/node[tag=foo|bar]";
+var expected = { object: "node", tag: { key:["key"], value:["foo", "bar"]}};
+assert.deepEqual(toTest(nodeWithTwoValues), expected);
+
+var nodeWithTwoKeys = "/node[foo,bar=value]";
+var expected = { object: "node", tag: { key:["foo", "bar"], value:["value"]}};
+assert.deepEqual(toTest(nodeWithTwoKeys), expected);
+
+var tagCrossProduct = "/node[key1,key2=value1,value2]";
+var expected = { object: "node", tag: {key:["key1", "key2"], value:["value1", "value2"]}};
+assert.deepEqual(toTest(tagCrossProduct), expected);
+
+var nodeBboxTag = "/node[bbox=0,0,0,0][key=value]";
+var nodeTagBbox = "/node[bbox=0,0,0,0][key=value]";
+var expected = { object: "node", bbox: {left:0,bottom:0,right:0,top:0}, tag: {key:["key"], value:["value"]}};
+assert.deepEqual(toTest(nodeBboxTag), expected);
+assert.deepEqual(toTest(nodeTagBbox), expected);
+
+
diff --git a/src/nodejs/xmlGenerator.js b/src/nodejs/xmlGenerator.js
index a477457..6ba0191 100644
--- a/src/nodejs/xmlGenerator.js
+++ b/src/nodejs/xmlGenerator.js
@@ -30,23 +30,24 @@ exports.createNode = function (node) {
// FIXME: make this shit working
exports.createWay = function (row) {
- var way = builder.begin('way')
+ var xmlWay = builder.begin('way')
.att('id', row.id)
- .att('timestamp', toISO8601(row.tstamp))
+ .att('timestamp', row.timestamp)
.att('version', row.version)
- .att('changeset', row.changeset_id);
- if(row.tags != '{}') {
- temp = row.tags.replace("{","").replace("}","").split(",");
- for(var x=0;x<temp.length;x=x+2){
- way.ele('tag')
- .att('k',escape(temp[x]))
- .att('v',escape(temp[x+1]));
- }
- }
- temp = row.nodes.replace("{","").replace("}","").split(",");
- for(var i=0;i<temp.length;i++) {
- way.ele('nd').att('ref',temp[i]);
+ .att('changeset', row.changeset);
+
+ if(row.tags) {
+ row.tags.forEach(function(tuple){
+ xmlWay.ele('tag')
+ .att('k',escape(tuple.key))
+ .att('v',escape(tuple.value));
+ });
}
+
+ //temp = row.nodes.replace("{","").replace("}","").split(",");
+ //for(var i=0;i<temp.length;i++) {
+ // way.ele('nd').att('ref',temp[i]);
+ //}
return builder.toString({pretty:'true'});
};