diff --git a/app/riot/package.json b/app/riot/package.json index ee27bb80b245..8c597edec94a 100644 --- a/app/riot/package.json +++ b/app/riot/package.json @@ -53,10 +53,11 @@ "ts-dedent": "^2.0.0" }, "devDependencies": { - "@babel/plugin-transform-modules-commonjs": "^7.12.1", - "@babel/preset-env": "^7.12.1", - "@babel/preset-flow": "^7.12.1", - "@babel/preset-react": "^7.12.1" + "@types/riot": "^3.6.2", + "riot": "^3.13.2", + "riot-compiler": "^3.6.0", + "riot-hot-reload": "^1.0.0", + "riot-tag-loader": "^2.1.0" }, "peerDependencies": { "@babel/core": "*", diff --git a/app/riot/src/client/index.js b/app/riot/src/client/index.ts similarity index 100% rename from app/riot/src/client/index.js rename to app/riot/src/client/index.ts diff --git a/app/riot/src/client/preview/__snapshots__/render-riot.test.js.snap b/app/riot/src/client/preview/__snapshots__/render-riot.test.ts.snap similarity index 100% rename from app/riot/src/client/preview/__snapshots__/render-riot.test.js.snap rename to app/riot/src/client/preview/__snapshots__/render-riot.test.ts.snap diff --git a/app/riot/src/client/preview/compileStageFunctions.js b/app/riot/src/client/preview/compileStageFunctions.ts similarity index 68% rename from app/riot/src/client/preview/compileStageFunctions.js rename to app/riot/src/client/preview/compileStageFunctions.ts index 8c80595f1853..924ceb9354e5 100644 --- a/app/riot/src/client/preview/compileStageFunctions.js +++ b/app/riot/src/client/preview/compileStageFunctions.ts @@ -2,22 +2,22 @@ import compiler from 'riot-compiler'; export const alreadyCompiledMarker = "var riot = require('riot')"; -export function asCompiledCode(text) { +export function asCompiledCode(text: string) { return compiler .compile(text, {}) .replace('var riot = require("riot")', '') .replace('riot.tag2(', 'tag2('); } -export function compileNow(tag2, text) { +export function compileNow(tag2: unknown, text: string) { // eslint-disable-next-line no-eval return tag2 && eval(asCompiledCode(text)); } -export function getRidOfRiotNoise(compiled) { +export function getRidOfRiotNoise(compiled: string) { return compiled.replace(/riot\.tag2/g, 'tag2').replace(alreadyCompiledMarker, ''); } -export function setConstructor(compiledSourceCode, constructor) { +export function setConstructor(compiledSourceCode: string, constructor: any) { return compiledSourceCode.replace(/function\(opts\)\s*{\s*}(?=\);$)/, constructor.toString()); } diff --git a/app/riot/src/client/preview/globals.js b/app/riot/src/client/preview/globals.ts similarity index 100% rename from app/riot/src/client/preview/globals.js rename to app/riot/src/client/preview/globals.ts diff --git a/app/riot/src/client/preview/index.js b/app/riot/src/client/preview/index.ts similarity index 78% rename from app/riot/src/client/preview/index.js rename to app/riot/src/client/preview/index.ts index 4ecddb28577b..97a034aac70b 100644 --- a/app/riot/src/client/preview/index.js +++ b/app/riot/src/client/preview/index.ts @@ -17,8 +17,9 @@ export const { } = clientApi; const framework = 'riot'; -export const storiesOf = (...args) => clientApi.storiesOf(...args).addParameters({ framework }); -export const configure = (...args) => coreConfigure(framework, ...args); +export const storiesOf = (...args: any) => + clientApi.storiesOf(...args).addParameters({ framework }); +export const configure = (...args: any) => coreConfigure(framework, ...args); const mount = vendorMount.bind(riot, '#root'); const compileNow = unboundCompileNow.bind(null, tag2); diff --git a/app/riot/src/client/preview/render-riot.test.js b/app/riot/src/client/preview/render-riot.test.js deleted file mode 100644 index 7478535be143..000000000000 --- a/app/riot/src/client/preview/render-riot.test.js +++ /dev/null @@ -1,130 +0,0 @@ -import { document } from 'global'; -import { unregister, tag2, mount } from 'riot'; -import compiler from 'riot-compiler'; -import { render } from './rendering'; -import { asCompiledCode } from './compileStageFunctions'; - -const rootElement = document.createElement('div'); -rootElement.id = 'root'; -document.body = document.createElement('body'); -document.body.appendChild(rootElement); - -const context = { - unregister, - compiler, - tag2, - mount, -}; - -beforeEach(() => { - unregister('#root'); - rootElement.dataset.is = 'root'; -}); - -describe('render a riot element', () => { - it('should not work with nothing', () => { - expect(render(null, context)).toBe(false); - - expect(rootElement.innerHTML).toEqual(''); - }); - - it('can work with some text', () => { - expect(render({ tags: ['

some tests

'] }, context)).toBe(true); - - expect(rootElement.innerHTML).toEqual('

some tests

'); - }); - - it('can work with raw code', () => { - expect(render("riot.tag2('root', '
raw code
', '', '', () => {})", context)).toBe( - true - ); - - expect(rootElement.innerHTML).toEqual('
raw code
'); - }); - - it('can work with compiled code', () => { - expect(render([{}], context)).toBe(true); - // does only work in true mode, and not in jest mode - }); - - it('will be possible to compile a template before rendering it', () => { - const compiledTemplate = asCompiledCode(''); - - expect(compiledTemplate).toEqual( - "tag2('template', '
raw code
', '', '', function(opts) {\n});" - ); - }); - - it('works with a json consisting in a tagName and opts', () => { - tag2('hello', '

Hello { opts.suffix }

', '', '', () => {}); - - expect(render({ tagName: 'hello', opts: { suffix: 'World' } }, context)).toBe(true); - - expect(rootElement.innerHTML).toEqual('

Hello World

'); - }); - - it('can nest several tags', () => { - expect( - render( - { - tags: [ - '
Inside tag1:
', - '
Inside tag2:
', - '
Inside tag3:
', - '
Inside tag4:
', - '
Inside tag5:
', - ], - template: '
Content
', - }, - context - ) - ).toBe(true); - - expect(rootElement.innerHTML).toMatchSnapshot(); - }); - - it('can template some vars', () => { - expect( - render( - { - tags: [ - { - content: - "
simple test ({opts.test || 'without parameter'}). Oh, by the way ({opts.riotValue || '... well, nothing'})
", - boundAs: 'mustBeUniquePlease', - }, - ], - template: - '', - }, - context - ) - ).toBe(true); - - expect(rootElement.innerHTML).toMatchSnapshot(); - }); - - it('can accept a constructor', () => { - expect( - render( - { - tags: [ - { - content: - "
HACKED : {opts.hacked} ; simple test ({opts.test || 'without parameter'}). Oh, by the way ({opts.riotValue || '... well, nothing'})
", - boundAs: 'mustBeUniquePlease', - }, - ], - template: - '', - tagConstructor: function tagConstructor() { - this.hacked = true; - }, - }, - context - ) - ).toBe(true); - - expect(rootElement.innerHTML).toMatchSnapshot(); - }); -}); diff --git a/app/riot/src/client/preview/render-riot.test.ts b/app/riot/src/client/preview/render-riot.test.ts new file mode 100644 index 000000000000..8c249fc090bd --- /dev/null +++ b/app/riot/src/client/preview/render-riot.test.ts @@ -0,0 +1,111 @@ +import { document } from 'global'; +import { unregister, tag2 } from 'riot'; +import { render } from './rendering'; +import { asCompiledCode } from './compileStageFunctions'; + +const rootElement = document.createElement('div'); +rootElement.id = 'root'; +document.body = document.createElement('body'); +document.body.appendChild(rootElement); + +beforeEach(() => { + unregister('#root'); + rootElement.dataset.is = 'root'; +}); + +describe('render a riot element', () => { + it('should not work with nothing', () => { + expect(render(null)).toBe(false); + + expect(rootElement.innerHTML).toEqual(''); + }); + + it('can work with some text', () => { + expect(render({ tags: ['

some tests

'] })).toBe(true); + + expect(rootElement.innerHTML).toEqual('

some tests

'); + }); + + it('can work with raw code', () => { + expect(render("riot.tag2('root', '
raw code
', '', '', () => {})")).toBe(true); + + expect(rootElement.innerHTML).toEqual('
raw code
'); + }); + + it('can work with compiled code', () => { + expect(render([{}])).toBe(true); + // does only work in true mode, and not in jest mode + }); + + it('will be possible to compile a template before rendering it', () => { + const compiledTemplate = asCompiledCode(''); + + expect(compiledTemplate).toEqual( + "tag2('template', '
raw code
', '', '', function(opts) {\n});" + ); + }); + + it('works with a json consisting in a tagName and opts', () => { + tag2('hello', '

Hello { opts.suffix }

', '', '', () => {}); + + expect(render({ tagName: 'hello', opts: { suffix: 'World' } })).toBe(true); + + expect(rootElement.innerHTML).toEqual('

Hello World

'); + }); + + it('can nest several tags', () => { + expect( + render({ + tags: [ + '
Inside tag1:
', + '
Inside tag2:
', + '
Inside tag3:
', + '
Inside tag4:
', + '
Inside tag5:
', + ], + template: '
Content
', + }) + ).toBe(true); + + expect(rootElement.innerHTML).toMatchSnapshot(); + }); + + it('can template some vars', () => { + expect( + render({ + tags: [ + { + content: + "
simple test ({opts.test || 'without parameter'}). Oh, by the way ({opts.riotValue || '... well, nothing'})
", + boundAs: 'mustBeUniquePlease', + }, + ], + template: + '', + }) + ).toBe(true); + + expect(rootElement.innerHTML).toMatchSnapshot(); + }); + + it('can accept a constructor', () => { + expect( + render({ + tags: [ + { + content: + "
HACKED : {opts.hacked} ; simple test ({opts.test || 'without parameter'}). Oh, by the way ({opts.riotValue || '... well, nothing'})
", + boundAs: 'mustBeUniquePlease', + }, + ], + template: + '', + tagConstructor: function tagConstructor() { + this.hacked = true; + }, + }) + ).toBe(true); + + expect(rootElement.innerHTML).toMatchSnapshot(); + }); +}); diff --git a/app/riot/src/client/preview/render.js b/app/riot/src/client/preview/render.ts similarity index 84% rename from app/riot/src/client/preview/render.js rename to app/riot/src/client/preview/render.ts index f17ee2596383..c5338a4f2358 100644 --- a/app/riot/src/client/preview/render.js +++ b/app/riot/src/client/preview/render.ts @@ -9,6 +9,12 @@ export default function renderMain({ name, showMain = () => {}, showError = () => {}, +}: { + storyFn: Function; + kind: string; + name: string; + showMain: () => any; + showError: (input: { title: string; description: string }) => void; }) { showMain(); unregister('#root'); diff --git a/app/riot/src/client/preview/rendering/compiledButUnmounted.js b/app/riot/src/client/preview/rendering/compiledButUnmounted.ts similarity index 56% rename from app/riot/src/client/preview/rendering/compiledButUnmounted.js rename to app/riot/src/client/preview/rendering/compiledButUnmounted.ts index 5a8d92e47be5..47d8f3ee3bc4 100644 --- a/app/riot/src/client/preview/rendering/compiledButUnmounted.js +++ b/app/riot/src/client/preview/rendering/compiledButUnmounted.ts @@ -1,5 +1,5 @@ import { mount } from 'riot'; -export default function renderCompiledButUnmounted(component) { +export default function renderCompiledButUnmounted(component: any) { mount('root', component.tagName, component.opts || {}); } diff --git a/app/riot/src/client/preview/rendering/index.js b/app/riot/src/client/preview/rendering/index.ts similarity index 93% rename from app/riot/src/client/preview/rendering/index.js rename to app/riot/src/client/preview/rendering/index.ts index 752053ba02e5..67bf624371ae 100644 --- a/app/riot/src/client/preview/rendering/index.js +++ b/app/riot/src/client/preview/rendering/index.ts @@ -2,7 +2,7 @@ import renderCompiledButUnmounted from './compiledButUnmounted'; import renderStringified from './stringified'; import renderRaw from './raw'; -export function render(component) { +export function render(component: any) { if (typeof component === 'string') { renderRaw(component); return true; diff --git a/app/riot/src/client/preview/rendering/raw.js b/app/riot/src/client/preview/rendering/raw.ts similarity index 88% rename from app/riot/src/client/preview/rendering/raw.js rename to app/riot/src/client/preview/rendering/raw.ts index f706cd8876ba..8ed2fdebf320 100644 --- a/app/riot/src/client/preview/rendering/raw.js +++ b/app/riot/src/client/preview/rendering/raw.ts @@ -2,7 +2,7 @@ import { mount, tag2 as tag } from 'riot'; import compiler from 'riot-compiler'; import { alreadyCompiledMarker, getRidOfRiotNoise } from '../compileStageFunctions'; -export default function renderRaw(sourceCode) { +export default function renderRaw(sourceCode: string) { const tag2 = tag; // eslint-disable-next-line no-eval eval( diff --git a/app/riot/src/client/preview/rendering/stringified.js b/app/riot/src/client/preview/rendering/stringified.ts similarity index 93% rename from app/riot/src/client/preview/rendering/stringified.js rename to app/riot/src/client/preview/rendering/stringified.ts index 4a7a732b34a9..fcde052b227b 100644 --- a/app/riot/src/client/preview/rendering/stringified.js +++ b/app/riot/src/client/preview/rendering/stringified.ts @@ -4,7 +4,7 @@ import compiler from 'riot-compiler'; import { document } from 'global'; import { alreadyCompiledMarker, getRidOfRiotNoise, setConstructor } from '../compileStageFunctions'; -function guessRootName(stringified) { +function guessRootName(stringified: string) { const whiteSpaceLocation = stringified.indexOf(' ', stringified.indexOf('<') + 1); const firstWhitespace = whiteSpaceLocation === -1 ? stringified.length : whiteSpaceLocation; const supposedName = stringified.trim().match(/^<[^ >]+\/>$/) @@ -17,7 +17,7 @@ function guessRootName(stringified) { return matchingBuiltInTag === 'HTMLUnknownElement' ? supposedName : 'root'; } -function compileText(code, rootName) { +function compileText(code: string, rootName: string) { const sourceCodeEndOfHtml = (Math.min(code.indexOf('`, tagConstructor, +}: { + tags: any[]; + template: string; + tagConstructor: any; }) { const tag2 = tag; tags.forEach((input) => { diff --git a/app/riot/src/server/build.js b/app/riot/src/server/build.ts similarity index 100% rename from app/riot/src/server/build.js rename to app/riot/src/server/build.ts diff --git a/app/riot/src/server/framework-preset-riot.js b/app/riot/src/server/framework-preset-riot.ts similarity index 83% rename from app/riot/src/server/framework-preset-riot.js rename to app/riot/src/server/framework-preset-riot.ts index 820e02e015d2..9c12474030e8 100644 --- a/app/riot/src/server/framework-preset-riot.js +++ b/app/riot/src/server/framework-preset-riot.ts @@ -1,4 +1,6 @@ -export function webpack(config) { +import { Configuration } from 'webpack'; + +export function webpack(config: Configuration) { return { ...config, module: { diff --git a/app/riot/src/server/index.js b/app/riot/src/server/index.ts similarity index 100% rename from app/riot/src/server/index.js rename to app/riot/src/server/index.ts diff --git a/app/riot/src/server/options.js b/app/riot/src/server/options.ts similarity index 100% rename from app/riot/src/server/options.js rename to app/riot/src/server/options.ts diff --git a/app/riot/src/typings.d.ts b/app/riot/src/typings.d.ts new file mode 100644 index 000000000000..d811ce7d4116 --- /dev/null +++ b/app/riot/src/typings.d.ts @@ -0,0 +1,8 @@ +declare module '@storybook/core/*'; +declare module 'global'; +declare module 'riot-compiler'; +declare module 'riot' { + const tag2: Function; + const mount: Function; + const unregister: Function; +} diff --git a/app/riot/tsconfig.json b/app/riot/tsconfig.json new file mode 100644 index 000000000000..f6ba3c7e250f --- /dev/null +++ b/app/riot/tsconfig.json @@ -0,0 +1,7 @@ +{ + "extends": "../../tsconfig.json", + "compilerOptions": { + "rootDir": "./src", + "types": ["jest", "webpack-env"] + } +} diff --git a/yarn.lock b/yarn.lock index 4088e971f55f..096b8b8f6ab2 100644 --- a/yarn.lock +++ b/yarn.lock @@ -5252,6 +5252,11 @@ "@types/glob" "*" "@types/node" "*" +"@types/riot@^3.6.2": + version "3.6.2" + resolved "https://registry.yarnpkg.com/@types/riot/-/riot-3.6.2.tgz#d3e0f384ffb1d718f5fd89b8a14e7d60c7f6940c" + integrity sha512-e/q9dwOgGXeouq1ipQMxwuukYf8lMZbhzbuvFqX4XhdQHyf6Dn4pOxwZGkXSCJ+HZ8c79fgAzpACO92MqbTi2g== + "@types/selenium-webdriver@^3.0.0": version "3.0.17" resolved "https://registry.yarnpkg.com/@types/selenium-webdriver/-/selenium-webdriver-3.0.17.tgz#50bea0c3c2acc31c959c5b1e747798b3b3d06d4b" @@ -28967,7 +28972,7 @@ riot-cli@^4.0.2: riot-compiler "^3.5.1" rollup "^0.57.1" -riot-compiler@^3.5.1, riot-compiler@^3.5.2: +riot-compiler@^3.5.1, riot-compiler@^3.5.2, riot-compiler@^3.6.0: version "3.6.0" resolved "https://registry.yarnpkg.com/riot-compiler/-/riot-compiler-3.6.0.tgz#f65428cf25b940098e35ea9c8357ca91cae10280" integrity sha512-P2MVj0T9ox0EFPTSSHJIAaBe6/fCnKln76BtPK6ezAlBW2+qKCDzzvkj3gwFvGEG1dYUHa2jQ/O6+FZNNe8CYw== @@ -29008,7 +29013,7 @@ riot-tmpl@^3.0.8: dependencies: eslint-config-riot "^1.0.0" -riot@^3.13.0, riot@^3.3.1: +riot@^3.13.0, riot@^3.13.2, riot@^3.3.1: version "3.13.2" resolved "https://registry.yarnpkg.com/riot/-/riot-3.13.2.tgz#3f5fb86b0d2b864bdcc959b7f86e2f4c2f696726" integrity sha512-L4WFJEhbTA0deDoZ1XxoVw7Tf96+xYc06aQ+4QM+IkYClD6mZ7E/9zN3Rd48uYMBvHQfHtbPvR0KEiu3pJyI2A==