-
Notifications
You must be signed in to change notification settings - Fork 743
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
* add svelte lexer * remove trailing newline * remove unneeded comment Co-authored-by: Tan Le <[email protected]> * remove excessive newlines Co-authored-by: Tan Le <[email protected]> * formatting * Add guessing specs for Svelte lexer * Ensure HTML is loaded as part of Svelte lexer * Add Svelte to the list of supported languages --------- Co-authored-by: Brodie Davis <[email protected]> Co-authored-by: Tan Le <[email protected]>
- Loading branch information
1 parent
17b3aef
commit b584ea1
Showing
5 changed files
with
217 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,29 @@ | ||
<!-- This file is made up from several examples on https://svelte.dev/examples and is not expected to function. --> | ||
<script lang="ts"> | ||
import Image from './Image.svelte'; | ||
|
||
let src: string = '/tutorial/image.gif'; | ||
let count: number = 1; | ||
$: doubled = count * 2; // the `$:` is special in svelte | ||
</script> | ||
|
||
<Image {src} bind:alt="{name.capitalize()} dancing" user={name.toUpperCase(false, 42, {key: 'value'})} | ||
tooltip="I'm helping" false text=asdf on:message={handleMessage} /> | ||
|
||
{#await loadSrc(src)} | ||
loading... | ||
{:then data} | ||
{#each cats as { name }, i} | ||
<li>{name}</li> | ||
{/each} | ||
|
||
<!-- Keyed Each Block --> | ||
{#each cats as cat (cat.id)} | ||
<li>{cat.name}</li> | ||
{/each} | ||
{:catch err} | ||
{@debug err} | ||
{#await solveErr(err, {x: 'asdf'}) then reason}{@html reason}{/await} | ||
{/await} | ||
|
||
<style>p {font-family: 'Comic Sans MS', cursive;}</style> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,91 @@ | ||
# -*- coding: utf-8 -*- # | ||
# frozen_string_literal: true | ||
|
||
module Rouge | ||
module Lexers | ||
load_lexer 'html.rb' | ||
|
||
class Svelte < HTML | ||
desc 'Svelte single-file components (https://svelte.dev/)' | ||
tag 'svelte' | ||
filenames '*.svelte' | ||
mimetypes 'text/x-svelte', 'application/x-svelte' | ||
|
||
def initialize(*) | ||
super | ||
# todo add support for typescript script blocks | ||
@js = Javascript.new(options) | ||
end | ||
|
||
# Shorthand syntax for passing attributes - ex, `{src}` instead of `src={src}` | ||
prepend :tag do | ||
rule %r/(\{)\s*([a-zA-Z0-9_]+)\s*(})/m do | ||
groups Str::Interpol, Name::Variable, Str::Interpol | ||
pop! | ||
end | ||
end | ||
|
||
prepend :attr do | ||
# Duplicate template_start mixin here with a pop! | ||
# Because otherwise we'll never exit the attr state | ||
rule %r/\{/ do | ||
token Str::Interpol | ||
pop! | ||
push :template | ||
end | ||
end | ||
|
||
# handle templates within attribute single/double quotes | ||
prepend :dq do | ||
mixin :template_start | ||
end | ||
|
||
prepend :sq do | ||
mixin :template_start | ||
end | ||
|
||
prepend :root do | ||
# detect curly braces within HTML text (outside of tags/attributes) | ||
rule %r/([^<&{]*)(\{)(\s*)/ do | ||
groups Text, Str::Interpol, Text | ||
push :template | ||
end | ||
end | ||
|
||
state :template_start do | ||
# open template | ||
rule %r/\s*\{\s*/, Str::Interpol, :template | ||
end | ||
|
||
state :template do | ||
# template end | ||
rule %r/}/, Str::Interpol, :pop! | ||
|
||
# Allow JS lexer to handle matched curly braces within template | ||
rule(/(?<=^|[^\\])\{.*?(?<=^|[^\\])\}/) do | ||
delegate @js | ||
end | ||
|
||
# keywords | ||
rule %r/@(debug|html)\b/, Keyword | ||
rule %r/(#await)(.*)(then|catch)(\s+)(\w+)/ do |m| | ||
token Keyword, m[1] | ||
delegate @js, m[2] | ||
token Keyword, m[3] | ||
token Text, m[4] | ||
delegate @js, m[5] | ||
end | ||
rule %r/([#\/])(await|each|if|key)\b/, Keyword | ||
rule %r/(:else)(\s+)(if)?\b/ do | ||
groups Keyword, Text, Keyword | ||
end | ||
rule %r/:?(catch|then)\b/, Keyword | ||
|
||
# allow JS parser to handle anything that's not a curly brace | ||
rule %r/[^{}]+/ do | ||
delegate @js | ||
end | ||
end | ||
end | ||
end | ||
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,18 @@ | ||
# frozen_string_literal: true | ||
|
||
describe Rouge::Lexers::Svelte do | ||
let(:subject) { Rouge::Lexers::Svelte.new } | ||
|
||
describe 'guessing' do | ||
include Support::Guessing | ||
|
||
it 'guesses by filename' do | ||
assert_guess :filename => 'foo.svelte' | ||
end | ||
|
||
it 'guesses by mimetype' do | ||
assert_guess :mimetype => 'text/x-svelte' | ||
assert_guess :mimetype => 'application/x-svelte' | ||
end | ||
end | ||
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,78 @@ | ||
<!-- This file is made up from several examples on https://svelte.dev/examples and is not expected to function. --> | ||
<script> | ||
let name = 'rick'; | ||
let cats = [ | ||
{ name: 'Keyboard Cat' }, | ||
{ name: 'Maru' }, | ||
{ name: 'Henri The Existential Cat' } | ||
]; | ||
|
||
function doStuff() { | ||
console.log('standard javascript is cool'); | ||
return false; | ||
}; | ||
</script> | ||
|
||
<script lang="ts"> | ||
import Nested from './Nested.svelte'; | ||
|
||
let src = '/tutorial/image.gif'; | ||
let count: number = 1; | ||
|
||
// the `$:` is special in svelte | ||
$: doubled = count * 2; | ||
|
||
async function doMoreStuff(): boolean { | ||
console.log('but typescript has more stuff!'); | ||
return false; | ||
}; | ||
</script> | ||
|
||
<h1 false tooltip="welcome" text=hi>Page Title</h1> | ||
|
||
<img alt="{name} dancing" {src} /> | ||
<Nested user={name.toUpperCase(false, 42, {key: 'value'})} tooltip="I'm helping" false text=asdf on:message={handleMessage} /> | ||
|
||
<input bind:value={name} placeholder="enter your name" /> | ||
<h1>Hey {name}, check out our { cats.length } cats! Hello {name}!</h1> | ||
|
||
Hey { name}, check out our { cats.length } cats! | ||
|
||
{#if x > 10} | ||
<p>{x} is greater than 10</p> | ||
{:else if 5 > x} | ||
<p>{x} is less than 5</p> | ||
{:else} | ||
<p>{x} is between 5 and 10</p> | ||
{/if} | ||
|
||
<ul> | ||
{#each cats as { name }, i} | ||
<li>{name}</li> | ||
{/each} | ||
|
||
<!-- Keyed Each Block --> | ||
{#each cats as cat (cat.id)} | ||
<li>{cat.name}</li> | ||
{/each} | ||
</ul> | ||
|
||
{#await promise} | ||
loading... | ||
{:then data} | ||
{@html data} | ||
{:catch err} | ||
{@debug err} | ||
{/await} | ||
|
||
{#await Fn('asdf', 42, {x: 'asdf'}) then data} | ||
loading... | ||
{/await} | ||
|
||
<style> | ||
p { | ||
color: purple; | ||
font-family: 'Comic Sans MS', cursive; | ||
font-size: 2em; | ||
} | ||
</style> |