insanity
This commit is contained in:
parent
adcb956fa2
commit
c81922fc97
|
|
@ -53,84 +53,3 @@ signals.trap 'EXIT':
|
|||
end`).toEvaluateTo(['EXIT', true])
|
||||
})
|
||||
})
|
||||
|
||||
describe('ribbit', () => {
|
||||
test('head tag', () => {
|
||||
expect(`
|
||||
head:
|
||||
title What up
|
||||
meta charSet=UTF-8
|
||||
meta name=viewport content='width=device-width, initial-scale=1, viewport-fit=cover'
|
||||
end`).toEvaluateTo(`head`, {
|
||||
head: () => 'head'
|
||||
})
|
||||
})
|
||||
|
||||
test('li', () => {
|
||||
expect(`
|
||||
list:
|
||||
li border-bottom='1px solid black' one
|
||||
li two
|
||||
li three
|
||||
end`).toEvaluateTo(`list`, {
|
||||
list: () => 'list'
|
||||
})
|
||||
})
|
||||
|
||||
test('inline expressions', () => {
|
||||
const buffer: string[] = []
|
||||
|
||||
const tagBlock = async (tagName: string, props = {}, fn: Function) => {
|
||||
const attrs = Object.entries(props).map(([key, value]) => `${key}="${value}"`)
|
||||
const space = attrs.length ? ' ' : ''
|
||||
|
||||
buffer.push(`<${tagName}${space}${attrs.join(' ')}>`)
|
||||
await fn()
|
||||
buffer.push(`</${tagName}>`)
|
||||
}
|
||||
|
||||
const tagCall = (tagName: string, atNamed: {}, ...args: any[]) => {
|
||||
const attrs = Object.entries(atNamed).map(([key, value]) => `${key}="${value}"`)
|
||||
const space = attrs.length ? ' ' : ''
|
||||
const children = args
|
||||
.reverse()
|
||||
.map(a => a === null ? buffer.pop() : a)
|
||||
.reverse().join(' ')
|
||||
.replaceAll(' !!ribbit-nospace!! ', '')
|
||||
|
||||
buffer.push(`<${tagName}${space}${attrs.join(' ')}>${children}</${tagName}>`)
|
||||
}
|
||||
|
||||
const tag = async (tagName: string, atNamed: {}, ...args: any[]) => {
|
||||
if (typeof args[0] === 'function')
|
||||
await tagBlock(tagName, atNamed, args[0])
|
||||
else
|
||||
tagCall(tagName, atNamed, ...args)
|
||||
}
|
||||
|
||||
expect(`
|
||||
ribbit:
|
||||
p class=container:
|
||||
h1 class=bright style='font-family: helvetica' Heya
|
||||
h2 man that is (b wild) (nospace) !
|
||||
p Double the fun.
|
||||
end
|
||||
end`).toEvaluateTo(
|
||||
`<p class="container">
|
||||
<h1 class="bright" style="font-family: helvetica">Heya</h1>
|
||||
<h2>man that is <b>wild</b>!</h2>
|
||||
<p>Double the fun.</p>
|
||||
</p>`, {
|
||||
ribbit: async (cb: Function) => {
|
||||
await cb()
|
||||
return buffer.join("\n")
|
||||
},
|
||||
p: (atNamed: {}, ...args: any[]) => tag('p', atNamed, ...args),
|
||||
h1: (atNamed: {}, ...args: any[]) => tag('h1', atNamed, ...args),
|
||||
h2: (atNamed: {}, ...args: any[]) => tag('h2', atNamed, ...args),
|
||||
b: (atNamed: {}, ...args: any[]) => tag('b', atNamed, ...args),
|
||||
nospace: () => '!!ribbit-nospace!!',
|
||||
join: (...args: string[]) => args.join(''),
|
||||
})
|
||||
})
|
||||
})
|
||||
113
src/compiler/tests/ribbit.test.ts
Normal file
113
src/compiler/tests/ribbit.test.ts
Normal file
|
|
@ -0,0 +1,113 @@
|
|||
import { expect, describe, test, beforeEach } from 'bun:test'
|
||||
import { type Value } from 'reefvm'
|
||||
|
||||
const buffer: string[] = []
|
||||
|
||||
const ribbitGlobals = {
|
||||
ribbit: async (cb: Function) => {
|
||||
await cb()
|
||||
return buffer.join("\n")
|
||||
},
|
||||
tag: (tagName: string, atDefaults = {}) => {
|
||||
return (atNamed = {}, ...args: any[]) => tag(tagName, Object.assign({}, atDefaults, atNamed), ...args)
|
||||
},
|
||||
head: (atNamed: {}, ...args: any[]) => tag('head', atNamed, ...args),
|
||||
title: (atNamed: {}, ...args: any[]) => tag('title', atNamed, ...args),
|
||||
meta: (atNamed: {}, ...args: any[]) => tag('meta', atNamed, ...args),
|
||||
p: (atNamed: {}, ...args: any[]) => tag('p', atNamed, ...args),
|
||||
h1: (atNamed: {}, ...args: any[]) => tag('h1', atNamed, ...args),
|
||||
h2: (atNamed: {}, ...args: any[]) => tag('h2', atNamed, ...args),
|
||||
b: (atNamed: {}, ...args: any[]) => tag('b', atNamed, ...args),
|
||||
ul: (atNamed: {}, ...args: any[]) => tag('ul', atNamed, ...args),
|
||||
li: (atNamed: {}, ...args: any[]) => tag('li', atNamed, ...args),
|
||||
nospace: () => NOSPACE_TOKEN,
|
||||
echo: (...args: any[]) => console.log(...args)
|
||||
}
|
||||
|
||||
function raw(fn: Function) { (fn as any).raw = true }
|
||||
|
||||
const tagBlock = async (tagName: string, props = {}, fn: Function) => {
|
||||
const attrs = Object.entries(props).map(([key, value]) => `${key}="${value}"`)
|
||||
const space = attrs.length ? ' ' : ''
|
||||
|
||||
buffer.push(`<${tagName}${space}${attrs.join(' ')}>`)
|
||||
await fn()
|
||||
buffer.push(`</${tagName}>`)
|
||||
}
|
||||
|
||||
const tagCall = (tagName: string, atNamed = {}, ...args: any[]) => {
|
||||
const attrs = Object.entries(atNamed).map(([key, value]) => `${key}="${value}"`)
|
||||
const space = attrs.length ? ' ' : ''
|
||||
const children = args
|
||||
.reverse()
|
||||
.map(a => a === null ? buffer.pop() : a)
|
||||
.reverse().join(' ')
|
||||
.replaceAll(` ${NOSPACE_TOKEN} `, '')
|
||||
|
||||
if (SELF_CLOSING.includes(tagName))
|
||||
buffer.push(`<${tagName}${space}${attrs.join(' ')} />`)
|
||||
else
|
||||
buffer.push(`<${tagName}${space}${attrs.join(' ')}>${children}</${tagName}>`)
|
||||
}
|
||||
|
||||
const tag = async (tagName: string, atNamed = {}, ...args: any[]) => {
|
||||
if (typeof args[0] === 'function')
|
||||
await tagBlock(tagName, atNamed, args[0])
|
||||
else
|
||||
tagCall(tagName, atNamed, ...args)
|
||||
}
|
||||
|
||||
const NOSPACE_TOKEN = '!!ribbit-nospace!!'
|
||||
const SELF_CLOSING = ["area", "base", "br", "col", "embed", "hr", "img", "input", "link", "meta", "param", "source", "track", "wbr"]
|
||||
|
||||
describe('ribbit', () => {
|
||||
beforeEach(() => buffer.length = 0)
|
||||
|
||||
test('head tag', () => {
|
||||
expect(`
|
||||
ribbit:
|
||||
head:
|
||||
title What up
|
||||
meta charset=UTF-8
|
||||
meta name=viewport content='width=device-width, initial-scale=1, viewport-fit=cover'
|
||||
end
|
||||
end
|
||||
`).toEvaluateTo(`<head>
|
||||
<title>What up</title>
|
||||
<meta charset="UTF-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1, viewport-fit=cover" />
|
||||
</head>`, ribbitGlobals)
|
||||
})
|
||||
|
||||
test('custom tags', () => {
|
||||
expect(`
|
||||
list = tag 'ul' class=list
|
||||
ribbit:
|
||||
list:
|
||||
li border-bottom='1px solid black' one
|
||||
li two
|
||||
li three
|
||||
end
|
||||
end`).toEvaluateTo(`<ul class="list">
|
||||
<li border-bottom="1px solid black">one</li>
|
||||
<li>two</li>
|
||||
<li>three</li>
|
||||
</ul>`, ribbitGlobals)
|
||||
})
|
||||
|
||||
test('inline expressions', () => {
|
||||
expect(`
|
||||
ribbit:
|
||||
p class=container:
|
||||
h1 class=bright style='font-family: helvetica' Heya
|
||||
h2 man that is (b wild) (nospace) !
|
||||
p Double the fun.
|
||||
end
|
||||
end`).toEvaluateTo(
|
||||
`<p class="container">
|
||||
<h1 class="bright" style="font-family: helvetica">Heya</h1>
|
||||
<h2>man that is <b>wild</b>!</h2>
|
||||
<p>Double the fun.</p>
|
||||
</p>`, ribbitGlobals)
|
||||
})
|
||||
})
|
||||
Loading…
Reference in New Issue
Block a user