From 4cb8effccdf8493cd93b61bb7ad590b90f06f6d7 Mon Sep 17 00:00:00 2001 From: Rich Harris Date: Sun, 18 Mar 2018 19:33:09 -0400 Subject: [PATCH 1/2] failing test for #1254 --- test/runtime/index.js | 23 ++++++++++------- .../deconflict-elements-indexes/_config.js | 25 +++++++++++++++++++ .../deconflict-elements-indexes/main.html | 24 ++++++++++++++++++ 3 files changed, 63 insertions(+), 9 deletions(-) create mode 100644 test/runtime/samples/deconflict-elements-indexes/_config.js create mode 100644 test/runtime/samples/deconflict-elements-indexes/main.html diff --git a/test/runtime/index.js b/test/runtime/index.js index aaafaff21b2c..a9b95898c458 100644 --- a/test/runtime/index.js +++ b/test/runtime/index.js @@ -14,9 +14,11 @@ import { spaces } from "../helpers.js"; +let svelte$; let svelte; let compileOptions = null; +let compile = null; function getName(filename) { const base = path.basename(filename).replace(".html", ""); @@ -25,7 +27,8 @@ function getName(filename) { describe("runtime", () => { before(() => { - svelte = loadSvelte(true); + svelte$ = loadSvelte(true); + svelte = loadSvelte(false); require.extensions[".html"] = function(module, filename) { const options = Object.assign( @@ -33,7 +36,7 @@ describe("runtime", () => { compileOptions ); - const { code } = svelte.compile(fs.readFileSync(filename, "utf-8"), options); + const { code } = compile(fs.readFileSync(filename, "utf-8"), options); return module._compile(code, filename); }; @@ -58,6 +61,8 @@ describe("runtime", () => { throw new Error('skipping test, already failed'); } + compile = (config.preserveIdentifiers ? svelte : svelte$).compile; + const cwd = path.resolve(`test/runtime/samples/${dir}`); global.document.title = ''; @@ -75,7 +80,7 @@ describe("runtime", () => { `test/runtime/samples/${dir}/main.html`, "utf-8" ); - const { code } = svelte.compile(source, compileOptions); + const { code } = compile(source, compileOptions); const startIndex = code.indexOf("function create_main_fragment"); // may change! if (startIndex === -1) throw new Error("missing create_main_fragment"); const endIndex = code.lastIndexOf("export default"); @@ -95,7 +100,7 @@ describe("runtime", () => { if (err.frame) { console.error(chalk.red(err.frame)); // eslint-disable-line no-console } - showOutput(cwd, { shared, format: 'cjs', store: !!compileOptions.store }, svelte); // eslint-disable-line no-console + showOutput(cwd, { shared, format: 'cjs', store: !!compileOptions.store }, svelte$); // eslint-disable-line no-console throw err; } } @@ -140,7 +145,7 @@ describe("runtime", () => { try { SvelteComponent = require(`./samples/${dir}/main.html`); } catch (err) { - showOutput(cwd, { shared, format: 'cjs', hydratable: hydrate, store: !!compileOptions.store }, svelte); // eslint-disable-line no-console + showOutput(cwd, { shared, format: 'cjs', hydratable: hydrate, store: !!compileOptions.store }, svelte$); // eslint-disable-line no-console throw err; } @@ -198,12 +203,12 @@ describe("runtime", () => { config.error(assert, err); } else { failed.add(dir); - showOutput(cwd, { shared, format: 'cjs', hydratable: hydrate, store: !!compileOptions.store }, svelte); // eslint-disable-line no-console + showOutput(cwd, { shared, format: 'cjs', hydratable: hydrate, store: !!compileOptions.store }, svelte$); // eslint-disable-line no-console throw err; } }) .then(() => { - if (config.show) showOutput(cwd, { shared, format: 'cjs', hydratable: hydrate, store: !!compileOptions.store }, svelte); + if (config.show) showOutput(cwd, { shared, format: 'cjs', hydratable: hydrate, store: !!compileOptions.store }, svelte$); }); }); } @@ -216,7 +221,7 @@ describe("runtime", () => { }); it("fails if options.target is missing in dev mode", () => { - const { code } = svelte.compile(`
`, { + const { code } = svelte$.compile(`
`, { format: "iife", name: "SvelteComponent", dev: true @@ -232,7 +237,7 @@ describe("runtime", () => { }); it("fails if options.hydrate is true but the component is non-hydratable", () => { - const { code } = svelte.compile(`
`, { + const { code } = svelte$.compile(`
`, { format: "iife", name: "SvelteComponent", dev: true diff --git a/test/runtime/samples/deconflict-elements-indexes/_config.js b/test/runtime/samples/deconflict-elements-indexes/_config.js new file mode 100644 index 000000000000..1e98e4295ba8 --- /dev/null +++ b/test/runtime/samples/deconflict-elements-indexes/_config.js @@ -0,0 +1,25 @@ +export default { + solo: true, + show: true, + + html: ` +
+ one +
+ `, + + preserveIdentifiers: true, + + test(assert, component, target) { + const { tagList } = component.get(); + tagList.push('two'); + component.set({ tagList }); + + assert.htmlEqual(target.innerHTML, ` +
+ one + two +
+ `); + } +}; \ No newline at end of file diff --git a/test/runtime/samples/deconflict-elements-indexes/main.html b/test/runtime/samples/deconflict-elements-indexes/main.html new file mode 100644 index 000000000000..75a257747f77 --- /dev/null +++ b/test/runtime/samples/deconflict-elements-indexes/main.html @@ -0,0 +1,24 @@ +
+ {{#each tagList as tag, i}} + + {{tag}} + + {{/each}} +
+ + \ No newline at end of file From 4b5d465a97931fef1b8621782d664254c4181a3d Mon Sep 17 00:00:00 2001 From: Rich Harris Date: Sun, 18 Mar 2018 19:48:16 -0400 Subject: [PATCH 2/2] prevent name collisions with each block index - fixes #1254 --- src/generators/nodes/EachBlock.ts | 4 +++- test/helpers.js | 4 ++-- test/runtime/index.js | 10 +++++----- .../samples/deconflict-elements-indexes/_config.js | 3 --- 4 files changed, 10 insertions(+), 11 deletions(-) diff --git a/src/generators/nodes/EachBlock.ts b/src/generators/nodes/EachBlock.ts index ba9ffc11a927..fa658c25370d 100644 --- a/src/generators/nodes/EachBlock.ts +++ b/src/generators/nodes/EachBlock.ts @@ -54,9 +54,11 @@ export default class EachBlock extends Node { this.block.contextTypes.set(this.context, 'each'); this.block.indexNames.set(this.context, indexName); this.block.listNames.set(this.context, listName); + if (this.index) { + this.block.getUniqueName(this.index); // this prevents name collisions (#1254) this.block.indexes.set(this.index, this.context); - this.block.changeableIndexes.set(this.index, this.key) + this.block.changeableIndexes.set(this.index, this.key); // TODO is this right? } const context = this.block.getUniqueName(this.context); diff --git a/test/helpers.js b/test/helpers.js index 4a65b995b7ac..82b9cd979874 100644 --- a/test/helpers.js +++ b/test/helpers.js @@ -174,7 +174,7 @@ function capitalise(str) { return str[0].toUpperCase() + str.slice(1); } -export function showOutput(cwd, options = {}, s = svelte) { +export function showOutput(cwd, options = {}, compile = svelte.compile) { glob.sync('**/*.html', { cwd }).forEach(file => { if (file[0] === '_') return; @@ -183,7 +183,7 @@ export function showOutput(cwd, options = {}, s = svelte) { .replace(/^\d/, '_$&') .replace(/[^a-zA-Z0-9_$]/g, ''); - const { code } = s.compile( + const { code } = compile( fs.readFileSync(`${cwd}/${file}`, 'utf-8'), Object.assign(options, { filename: file, diff --git a/test/runtime/index.js b/test/runtime/index.js index a9b95898c458..8dfa1d50fd6b 100644 --- a/test/runtime/index.js +++ b/test/runtime/index.js @@ -27,8 +27,8 @@ function getName(filename) { describe("runtime", () => { before(() => { - svelte$ = loadSvelte(true); svelte = loadSvelte(false); + svelte$ = loadSvelte(true); require.extensions[".html"] = function(module, filename) { const options = Object.assign( @@ -100,7 +100,7 @@ describe("runtime", () => { if (err.frame) { console.error(chalk.red(err.frame)); // eslint-disable-line no-console } - showOutput(cwd, { shared, format: 'cjs', store: !!compileOptions.store }, svelte$); // eslint-disable-line no-console + showOutput(cwd, { shared, format: 'cjs', store: !!compileOptions.store }, compile); // eslint-disable-line no-console throw err; } } @@ -145,7 +145,7 @@ describe("runtime", () => { try { SvelteComponent = require(`./samples/${dir}/main.html`); } catch (err) { - showOutput(cwd, { shared, format: 'cjs', hydratable: hydrate, store: !!compileOptions.store }, svelte$); // eslint-disable-line no-console + showOutput(cwd, { shared, format: 'cjs', hydratable: hydrate, store: !!compileOptions.store }, compile); // eslint-disable-line no-console throw err; } @@ -203,12 +203,12 @@ describe("runtime", () => { config.error(assert, err); } else { failed.add(dir); - showOutput(cwd, { shared, format: 'cjs', hydratable: hydrate, store: !!compileOptions.store }, svelte$); // eslint-disable-line no-console + showOutput(cwd, { shared, format: 'cjs', hydratable: hydrate, store: !!compileOptions.store }, compile); // eslint-disable-line no-console throw err; } }) .then(() => { - if (config.show) showOutput(cwd, { shared, format: 'cjs', hydratable: hydrate, store: !!compileOptions.store }, svelte$); + if (config.show) showOutput(cwd, { shared, format: 'cjs', hydratable: hydrate, store: !!compileOptions.store }, compile); }); }); } diff --git a/test/runtime/samples/deconflict-elements-indexes/_config.js b/test/runtime/samples/deconflict-elements-indexes/_config.js index 1e98e4295ba8..7e3a91a30658 100644 --- a/test/runtime/samples/deconflict-elements-indexes/_config.js +++ b/test/runtime/samples/deconflict-elements-indexes/_config.js @@ -1,7 +1,4 @@ export default { - solo: true, - show: true, - html: `
one