Skip to content

Commit 1130ad7

Browse files
authored
Merge pull request #744 from kethinov/1.1.0
1.1.0
2 parents 37bee1a + 1b73db1 commit 1130ad7

11 files changed

Lines changed: 260 additions & 133 deletions

CHANGELOG.md

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,13 @@
44

55
- Put your changes here...
66

7+
## 1.1.0
8+
9+
- Added `<escape>` tag.
10+
- Excluded `<pre>` tags from Teddy parsing. Add a `parse` attribute to prevent this behavior.
11+
- Fixed a bug that could cause infinite loops in variable parsing.
12+
- Updated dependencies.
13+
714
## 1.0.1
815

916
- Fixed a bug that caused client-side Teddy to try to fetch resources from the server inappropriately while parsing the template.

README.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -91,7 +91,7 @@ Display a variable by simply writing `{varName}` anywhere in the template. You c
9191

9292
All variable names are case-insensitive, both in `{varName}` form and when referenced in Teddy tags described below. This is to comply with the rules of HTML grammar which mandate that HTML tags and attributes be case insensitive.
9393

94-
HTML entities such as `<`, `>`, `&`, `'`, and `"` will be escaped by default as a safeguard against [cross-site scripting](https://en.wikipedia.org/wiki/Cross-site_scripting).
94+
HTML entities such as `<`, `>`, `&`, `'`, and `"` will be escaped by default as a safeguard against [cross-site scripting](https://en.wikipedia.org/wiki/Cross-site_scripting). If you want to deliberately escape some text or some HTML, then wrap it in an `<escape>` tag like this: `<escape><p>hello</p></escape>` which will output: `&lt;p&gt;hello&lt;/p&gt;`.
9595

9696
If you need to suppress this escaping in certain scenarios, write your variable like this: `{varName|s}`.
9797

@@ -393,7 +393,7 @@ You can also instruct the contents of a variable to not be parsed after that var
393393
<p>{this_var_will_be_parsed_but_its_contents_will_not_be|p}</p>
394394
```
395395

396-
Note: Teddy tags will also not be parsed if they appear inside of elements that interpret child text as plain text, e.g. `<style>`, `<script>`, `<textarea>`, etc.
396+
Note: Teddy tags will also not be parsed if they appear inside of elements that interpret child text as plain text, e.g. `<style>`, `<script>`, `<textarea>`, etc. Teddy will also not parse anything in a `<pre>` tag unless you add a `parse` attribute to the `<pre>` tag like `<pre parse>`.
397397

398398
Caching blocks
399399
---

cheerioPolyfill.js

Lines changed: 37 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,11 @@ export function load (html) {
3030
return getTeddyDOMInnerHTML(el)
3131
},
3232

33+
// e.g. dom(arg).toString() from teddy
34+
toString: function () {
35+
return getTeddyDOMOuterHTML(el)
36+
},
37+
3338
// e.g. dom(el).attr('teddydeferreddynamicinclude', 'true') from teddy
3439
attr: function (attr, val) {
3540
return el.setAttribute(attr, val)
@@ -68,6 +73,11 @@ export function load (html) {
6873
return getTeddyDOMInnerHTML(doc)
6974
}
7075

76+
// e.g. dom.toString() from teddy
77+
$.toString = function () {
78+
return getTeddyDOMOuterHTML(doc)
79+
}
80+
7181
return $
7282
}
7383

@@ -191,18 +201,17 @@ function parseTeddyDOMFromString (html) {
191201
return root
192202
}
193203

194-
// custom function to get inner HTML without escaping various things to prevent teddy from infinitely escaping them
204+
// custom functions to get inner/outer HTML without escaping various things to prevent teddy from infinitely escaping them
205+
const doublyEncodedEntities = {
206+
'&amp;amp;': '&amp;',
207+
'&amp;lt;': '&lt;',
208+
'&amp;gt;': '&gt;',
209+
'&amp;quot;': '&quot;',
210+
'&amp;#39;': '&#39;',
211+
'&amp;#x2F;': '&#x2F;'
212+
}
213+
const entityEntries = Object.entries(doublyEncodedEntities)
195214
function getTeddyDOMInnerHTML (node) {
196-
const doublyEncodedEntities = {
197-
'&amp;amp;': '&amp;',
198-
'&amp;lt;': '&lt;',
199-
'&amp;gt;': '&gt;',
200-
'&amp;quot;': '&quot;',
201-
'&amp;#39;': '&#39;',
202-
'&amp;#x2F;': '&#x2F;'
203-
}
204-
const entityEntries = Object.entries(doublyEncodedEntities)
205-
206215
// build html string
207216
let html = ''
208217
for (const child of node.childNodes) {
@@ -223,3 +232,20 @@ function getTeddyDOMInnerHTML (node) {
223232

224233
return html
225234
}
235+
function getTeddyDOMOuterHTML (node) {
236+
// start with the outerHTML of the node
237+
let outerHTML = ''
238+
239+
if (node.nodeType === window.Node.ELEMENT_NODE) {
240+
outerHTML = node.outerHTML
241+
} else if (node.nodeType === window.Node.TEXT_NODE) {
242+
outerHTML = node.textContent
243+
} else if (node.nodeType === window.Node.COMMENT_NODE) {
244+
outerHTML = `<!--${node.textContent}-->`
245+
}
246+
247+
// replace doubly encoded entities
248+
for (const [doublyEncoded, singleEncoded] of entityEntries) outerHTML = outerHTML.replace(new RegExp(doublyEncoded, 'g'), singleEncoded)
249+
250+
return outerHTML
251+
}

0 commit comments

Comments
 (0)