@samitouri / QOS-React-2 / commits / a6b888b214

Escape component keys used in reactid

Andreas Svensson committed Dec 26, 2013 at 01:14 UTC a6b888b2142608fb415debe2a9c2a6be2f266ec6
3 files changed +32 -3
src/core/__tests__/ReactIdentity-test.js
+2 -1
@@ -137,7 +137,8 @@ describe('ReactIdentity', function() {
137 });
138
139 it('should not allow scripts in keys to execute', function() {
140 - var h4x0rKey = '"><script>window.YOUVEBEENH4X0RED=true;</script><div id="';
140 + var h4x0rKey =
141 + '"><script>window[\'YOUVEBEENH4X0RED\']=true;</script><div id="';
142
143 var attachedContainer = document.createElement('div');
144 document.body.appendChild(attachedContainer);
src/utils/__tests__/ReactChildren-test.js
+4 -1
@@ -288,7 +288,10 @@ describe('ReactChildren', function() {
288 var mappedForcedKeys = Object.keys(mappedChildrenForcedKeys);
289 expect(mappedForcedKeys).toEqual(expectedForcedKeys);
290
291 - var expectedRemappedForcedKeys = ['{{keyZero}}{giraffe}', '{{keyOne}}[0]'];
291 + var expectedRemappedForcedKeys = [
292 + '{{keyZero^C}{giraffe}',
293 + '{{keyOne^C}[0]'
294 + ];
295 var remappedChildrenForcedKeys =
296 ReactChildren.map(mappedChildrenForcedKeys, mapFn);
297 expect(
src/utils/traverseAllChildren.js
+26 -1
@@ -30,6 +30,18 @@ var invariant = require('invariant');
30 * });
31 */
32
33 +var userProvidedKeyEscaperLookup = {
34 + '^': '^X',
35 + '.': '^D',
36 + '}': '^C'
37 +};
38 +
39 +var userProvidedKeyEscapeRegex = /[.^}]/g;
40 +
41 +function userProvidedKeyEscaper(match) {
42 + return userProvidedKeyEscaperLookup[match];
43 +}
44 +
45 /**
46 * Generate a key string that identifies a component within a set.
47 *
@@ -46,6 +58,19 @@ function getComponentKey(component, index) {
58 return '[' + index + ']';
59 }
60
61 +/**
62 + * Escape a component key so that it is safe to use in a reactid.
63 + *
64 + * @param {*} key Component key to be escaped.
65 + * @return {string} An escaped string.
66 + */
67 +function escapeUserProvidedKey(text) {
68 + return ('' + text).replace(
69 + userProvidedKeyEscapeRegex,
70 + userProvidedKeyEscaper
71 + );
72 +}
73 +
74 /**
75 * Wrap a `key` value explicitly provided by the user to distinguish it from
76 * implicitly-generated keys generated by a component's index in its parent.
@@ -54,7 +79,7 @@ function getComponentKey(component, index) {
79 * @return {string}
80 */
81 function wrapUserProvidedKey(key) {
57 - return '{' + key + '}';
82 + return '{' + escapeUserProvidedKey(key) + '}';
83 }
84
85 /**