Skip to content
This repository

Test fixtures for issue #59 #60

Open
wants to merge 4 commits into from

3 participants

Dougal Campbell Federico Rampazzo Paolo Fragomeni
Dougal Campbell

Here are my tests for issue #59, "Another nested object problem"

Federico Rampazzo
framp commented July 26, 2012

Thanks for the fix!

After using plates for quite some time I got the same bug you described in issue #59
It's pretty easy to get caught by this one, still don't understand how I didn't manage to trigger it before!

The main problem here is that we're trying to parse HTML by using regular expressions (http://stackoverflow.com/questions/1732348/regex-match-open-tags-except-xhtml-self-contained-tags)

I'm not sure how much having a proper xml parser would impact speed, but using regex is quite bug prone in my book.

Hope this get merged up!

Dougal Campbell

Yeah, even though I came up with a patch that worked for me (never did get around to making an updated pull request, though), I wasn't 100% happy with it. It seems brittle, and I keep thinking there's some other edge-case lurking in there. Glad if it helped you, though.

Paolo Fragomeni

have you run this through benchmarkjs or something similar? this looks good and i'd like to pull it in, but I'd like to be sure it doesnt incur exponential overhead with the regexp creation and execution.

Dougal Campbell

No, I haven't benchmarked it, and I didn't think about the regex creation being looped. Also, I think I made additional changes on my fork after I made that pull request. I'll try to find time this weekend to give it another look and hopefully submit an updated pull request.

Thanks for taking a look!

The idea is really good, just needs some minor refinement ;) Thanks!!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
This page is out of date. Refresh to see the latest.
44  lib/plates.js
@@ -11,32 +11,64 @@ var Plates = (typeof process !== 'undefined' && typeof process.title !== 'undefi
11 11
 
12 12
   Merge.prototype = {
13 13
 
14  
-    nest: [],
  14
+    nest: [], 
  15
+    depth: 0, // iteration depth
15 16
 
16 17
     tag: new RegExp([
17 18
       '<',
18 19
       '(/?)', // 2 - is closing
19 20
       '([-:\\w]+)', // 3 - name
20 21
       '((?:[-\\w]+(?:', '=',
21  
-      '(?:\\w+|["|\'](?:.*)["|\']))?)*)', // 4 - attributes
  22
+      '(?:\\w+|["|\'](?:.*?)["|\']))?)*?)', // 4 - attributes
22 23
       '(/?)', // 5 - is self-closing
23 24
       '>'
24 25
     ].join('\\s*')),
25 26
 
26  
-    attr: /([\-\w]*)=(?:["\']([\-\.\w\s\/:;&#]*)["\'])/gi,
  27
+    attr: /([\-\w]*)=(?:["\']([\-\.\w\s\/:;&#]*?)["\'])/gi,
27 28
 
28 29
     hasClass: function(str, className) {
29 30
       return str.split(' ').indexOf(className) > -1;
30 31
     },
  32
+    
  33
+    balance: function(html, tagname) {
  34
+      var i = idx = skip = 0;
  35
+      matches = html.match(new RegExp(this.tag.source, 'g')); // globalize
  36
+      do {
  37
+        var components = this.tag.exec(matches[idx]);
  38
+        if ( components[2] === tagname) {
  39
+          if (components[4]) {
  40
+            continue;   // ignore isSelfClosing
  41
+          }
  42
+          if (components[1]) {
  43
+            --i;
  44
+            ++skip;     // isClosing
  45
+          } else {
  46
+            ++i;        // opening, matches segment-wrapping tagname
  47
+          }
  48
+        }
  49
+        ++idx;
  50
+      } while (i > 0);
31 51
 
32  
-    iterate: function(html, value, components, tagname, key) {
  52
+      // Now skip should tell us how many closing tags to look for
  53
+      var end = 0;
  54
+      for (var i = 0; i < skip; i++) {
  55
+        end = html.indexOf('</' + tagname, end) + tagname.length + 3;
  56
+      }
  57
+      
  58
+      return html.substr(0, end);
  59
+    },
33 60
 
  61
+    iterate: function(html, value, components, tagname, key) {
  62
+    
34 63
       var output  = '',
35  
-          segment = html.slice(
  64
+
  65
+/*          segment = html.slice(
36 66
             html.search(components.input),
37 67
             html.lastIndexOf(tagname) + tagname.length + 1
38 68
           ),
39  
-
  69
+*/
  70
+          segment = this.balance(html.substr(html.search(components.input)), tagname),
  71
+          
40 72
           data = {};
41 73
 
42 74
       // Is it an array?
14  test/api-test.js
@@ -215,6 +215,20 @@ vows.describe('merge data into markup').addBatch({
215 215
 
216 216
         return common.createTest('test-20', map);
217 217
       }()
  218
+    ),
  219
+
  220
+    '(21) Keep your place after handling nested objects': (
  221
+
  222
+      function() {
  223
+        return common.createTest('test-21');
  224
+      }()
  225
+    ),
  226
+
  227
+    '(22) Keep your place after handling nested objects, more varied html': (
  228
+
  229
+      function() {
  230
+        return common.createTest('test-22');
  231
+      }()
218 232
     )
219 233
 
220 234
   }
1  test/fixtures/test-21.html
... ...
@@ -0,0 +1 @@
  1
+<div id="entries"><div class="entry"><div class="created"></div><div class="user"><div class="name"></div><div class="city"></div><div class="state"></div></div><div class="custid"></div></div></div>
31  test/fixtures/test-21.json
... ...
@@ -0,0 +1,31 @@
  1
+{ 
  2
+  "entry": [
  3
+    {
  4
+      "custid": 10101,
  5
+      "created": "2001-01-01",
  6
+      "user": {
  7
+        "name": "John Q. User",
  8
+        "city": "Atlanta",
  9
+        "state": "GA"
  10
+      }
  11
+    },
  12
+    {
  13
+      "custid": 20202,
  14
+      "created": "2002-02-02",
  15
+      "user": {
  16
+        "name": "Jane Q. User",
  17
+        "city": "Mobile",
  18
+        "state": "AL"
  19
+      }
  20
+    },
  21
+    {
  22
+      "custid": 30303,
  23
+      "created": "2003-0303",
  24
+      "user": {
  25
+        "name": "Professor X",
  26
+        "city": "Menlo",
  27
+        "state": "CA"
  28
+      }
  29
+    }
  30
+  ]
  31
+}
1  test/fixtures/test-21.out
... ...
@@ -0,0 +1 @@
  1
+<div id="entries"><div class="entry"><div class="created">2001-01-01</div><div class="user"><div class="name">John Q. User</div><div class="city">Atlanta</div><div class="state">GA</div></div><div class="custid">10101</div></div><div class="entry"><div class="created">2002-02-02</div><div class="user"><div class="name">Jane Q. User</div><div class="city">Mobile</div><div class="state">AL</div></div><div class="custid">20202</div></div><div class="entry"><div class="created">2003-0303</div><div class="user"><div class="name">Professor X</div><div class="city">Menlo</div><div class="state">CA</div></div><div class="custid">30303</div></div></div>
1  test/fixtures/test-22.html
... ...
@@ -0,0 +1 @@
  1
+<ul id="entries"><li class="entry"><div class="created"></div><div class="user"><div class="name"></div><div class="city"></div><div class="state"></div></div><div class="custid"></div></li></ul>
31  test/fixtures/test-22.json
... ...
@@ -0,0 +1,31 @@
  1
+{ 
  2
+  "entry": [
  3
+    {
  4
+      "custid": 10101,
  5
+      "created": "2001-01-01",
  6
+      "user": {
  7
+        "name": "John Q. User",
  8
+        "city": "Atlanta",
  9
+        "state": "GA"
  10
+      }
  11
+    },
  12
+    {
  13
+      "custid": 20202,
  14
+      "created": "2002-02-02",
  15
+      "user": {
  16
+        "name": "Jane Q. User",
  17
+        "city": "Mobile",
  18
+        "state": "AL"
  19
+      }
  20
+    },
  21
+    {
  22
+      "custid": 30303,
  23
+      "created": "2003-0303",
  24
+      "user": {
  25
+        "name": "Professor X",
  26
+        "city": "Menlo",
  27
+        "state": "CA"
  28
+      }
  29
+    }
  30
+  ]
  31
+}
1  test/fixtures/test-22.out
... ...
@@ -0,0 +1 @@
  1
+<ul id="entries"><li class="entry"><div class="created">2001-01-01</div><div class="user"><div class="name">John Q. User</div><div class="city">Atlanta</div><div class="state">GA</div></div><div class="custid">10101</div></li><li class="entry"><div class="created">2002-02-02</div><div class="user"><div class="name">Jane Q. User</div><div class="city">Mobile</div><div class="state">AL</div></div><div class="custid">20202</div></li><li class="entry"><div class="created">2003-0303</div><div class="user"><div class="name">Professor X</div><div class="city">Menlo</div><div class="state">CA</div></div><div class="custid">30303</div></li></ul>
Commit_comment_tip

Tip: You can add notes to lines in a file. Hover to the left of a line to make a note

Something went wrong with that request. Please try again.