proscenium 0.5.1-x86_64-darwin → 0.7.0-x86_64-darwin
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/README.md +128 -92
- data/bin/proscenium +0 -0
- data/bin/proscenium.h +109 -0
- data/config/routes.rb +0 -3
- data/lib/proscenium/css_module/class_names_resolver.rb +66 -0
- data/lib/proscenium/css_module/resolver.rb +76 -0
- data/lib/proscenium/css_module.rb +18 -39
- data/lib/proscenium/esbuild/golib.rb +97 -0
- data/lib/proscenium/esbuild.rb +32 -0
- data/lib/proscenium/helper.rb +0 -23
- data/lib/proscenium/log_subscriber.rb +26 -0
- data/lib/proscenium/middleware/base.rb +28 -36
- data/lib/proscenium/middleware/esbuild.rb +18 -44
- data/lib/proscenium/middleware/url.rb +1 -6
- data/lib/proscenium/middleware.rb +12 -16
- data/lib/proscenium/phlex/component_concerns.rb +27 -0
- data/lib/proscenium/phlex/page.rb +62 -0
- data/lib/proscenium/phlex/react_component.rb +52 -8
- data/lib/proscenium/phlex/resolve_css_modules.rb +67 -0
- data/lib/proscenium/phlex.rb +34 -33
- data/lib/proscenium/railtie.rb +41 -67
- data/lib/proscenium/side_load/ensure_loaded.rb +25 -0
- data/lib/proscenium/side_load/helper.rb +25 -0
- data/lib/proscenium/side_load/monkey.rb +48 -0
- data/lib/proscenium/side_load.rb +58 -52
- data/lib/proscenium/version.rb +1 -1
- data/lib/proscenium/view_component/react_component.rb +14 -0
- data/lib/proscenium/view_component.rb +28 -18
- data/lib/proscenium.rb +79 -2
- metadata +35 -72
- data/app/channels/proscenium/connection.rb +0 -13
- data/app/channels/proscenium/reload_channel.rb +0 -9
- data/bin/esbuild +0 -0
- data/bin/lightningcss +0 -0
- data/lib/proscenium/compiler.js +0 -84
- data/lib/proscenium/compilers/esbuild/argument_error.js +0 -24
- data/lib/proscenium/compilers/esbuild/compile_error.js +0 -148
- data/lib/proscenium/compilers/esbuild/css/postcss.js +0 -67
- data/lib/proscenium/compilers/esbuild/css_plugin.js +0 -172
- data/lib/proscenium/compilers/esbuild/env_plugin.js +0 -46
- data/lib/proscenium/compilers/esbuild/http_bundle_plugin.js +0 -53
- data/lib/proscenium/compilers/esbuild/import_map.js +0 -59
- data/lib/proscenium/compilers/esbuild/resolve_plugin.js +0 -205
- data/lib/proscenium/compilers/esbuild/setup_plugin.js +0 -45
- data/lib/proscenium/compilers/esbuild/solidjs_plugin.js +0 -24
- data/lib/proscenium/compilers/esbuild.bench.js +0 -14
- data/lib/proscenium/compilers/esbuild.js +0 -179
- data/lib/proscenium/link_to_helper.rb +0 -40
- data/lib/proscenium/middleware/lightningcss.rb +0 -64
- data/lib/proscenium/middleware/outside_root.rb +0 -26
- data/lib/proscenium/middleware/runtime.rb +0 -22
- data/lib/proscenium/middleware/static.rb +0 -14
- data/lib/proscenium/phlex/component.rb +0 -9
- data/lib/proscenium/precompile.rb +0 -31
- data/lib/proscenium/runtime/auto_reload.js +0 -40
- data/lib/proscenium/runtime/react_shim/index.js +0 -1
- data/lib/proscenium/runtime/react_shim/package.json +0 -5
- data/lib/proscenium/utils.js +0 -8
- data/lib/tasks/assets.rake +0 -19
data/lib/proscenium.rb
CHANGED
@@ -12,8 +12,85 @@ module Proscenium
|
|
12
12
|
autoload :ViewComponent
|
13
13
|
autoload :Phlex
|
14
14
|
autoload :Helper
|
15
|
-
autoload :
|
16
|
-
|
15
|
+
autoload :Esbuild
|
16
|
+
|
17
|
+
def self.reset_current_side_loaded
|
18
|
+
Current.reset
|
19
|
+
Current.loaded = SideLoad::EXTENSIONS.to_h { |e| [e, Set.new] }
|
20
|
+
end
|
21
|
+
|
22
|
+
class PathResolutionFailed < StandardError
|
23
|
+
def initialize(path)
|
24
|
+
@path = path
|
25
|
+
super
|
26
|
+
end
|
27
|
+
|
28
|
+
def message
|
29
|
+
"Path #{@path.inspect} cannot be resolved"
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
module Utils
|
34
|
+
module_function
|
35
|
+
|
36
|
+
# @param value [#to_s] The value to create the digest from. This will usually be a `Pathname`.
|
37
|
+
# @return [String] string digest of the given value.
|
38
|
+
def digest(value)
|
39
|
+
Digest::SHA1.hexdigest(value.to_s)[..7]
|
40
|
+
end
|
41
|
+
|
42
|
+
# Resolve the given `path` to a URL path.
|
43
|
+
#
|
44
|
+
# @param path [String] Can be URL path, file system path, or bare specifier (ie. NPM package).
|
45
|
+
# @return [String] URL path.
|
46
|
+
def resolve_path(path) # rubocop:disable Metrics/AbcSize
|
47
|
+
raise ArgumentError, 'path must be a string' unless path.is_a?(String)
|
48
|
+
|
49
|
+
if path.starts_with?('./', '../')
|
50
|
+
raise ArgumentError, 'path must be an absolute file system or URL path'
|
51
|
+
end
|
52
|
+
|
53
|
+
matched_gem = Proscenium.config.side_load_gems.find do |_, opts|
|
54
|
+
path.starts_with?("#{opts[:root]}/")
|
55
|
+
end
|
56
|
+
|
57
|
+
if matched_gem
|
58
|
+
sroot = "#{matched_gem[1][:root]}/"
|
59
|
+
relpath = path.delete_prefix(sroot)
|
60
|
+
|
61
|
+
if matched_gem[1][:package_name]
|
62
|
+
return Esbuild::Golib.resolve("#{matched_gem[1][:package_name]}/#{relpath}")
|
63
|
+
end
|
64
|
+
|
65
|
+
# TODO: manually resolve the path without esbuild
|
66
|
+
raise PathResolutionFailed, path
|
67
|
+
end
|
68
|
+
|
69
|
+
return path.delete_prefix(Rails.root.to_s) if path.starts_with?("#{Rails.root}/")
|
70
|
+
|
71
|
+
Esbuild::Golib.resolve(path)
|
72
|
+
end
|
73
|
+
|
74
|
+
# Resolves CSS class `names` to CSS module names. Each name will be converted to a CSS module
|
75
|
+
# name, consisting of the camelCased name (lower case first character), and suffixed with the
|
76
|
+
# given `digest`.
|
77
|
+
#
|
78
|
+
# @param names [String, Array]
|
79
|
+
# @param digest: [String]
|
80
|
+
# @returns [Array] of class names generated from the given CSS module `names` and `digest`.
|
81
|
+
def css_modularise_class_names(*names, digest: nil)
|
82
|
+
names.flatten.compact.map { |name| css_modularise_class_name name, digest: digest }
|
83
|
+
end
|
84
|
+
|
85
|
+
def css_modularise_class_name(name, digest: nil)
|
86
|
+
sname = name.to_s
|
87
|
+
if sname.starts_with?('_')
|
88
|
+
"_#{sname[1..].camelize(:lower)}#{digest}"
|
89
|
+
else
|
90
|
+
"#{sname.camelize(:lower)}#{digest}"
|
91
|
+
end
|
92
|
+
end
|
93
|
+
end
|
17
94
|
end
|
18
95
|
|
19
96
|
require 'proscenium/railtie'
|
metadata
CHANGED
@@ -1,17 +1,17 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: proscenium
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.7.0
|
5
5
|
platform: x86_64-darwin
|
6
6
|
authors:
|
7
7
|
- Joel Moss
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2023-05-31 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
|
-
name:
|
14
|
+
name: activesupport
|
15
15
|
requirement: !ruby/object:Gem::Requirement
|
16
16
|
requirements:
|
17
17
|
- - ">="
|
@@ -31,81 +31,75 @@ dependencies:
|
|
31
31
|
- !ruby/object:Gem::Version
|
32
32
|
version: '8.0'
|
33
33
|
- !ruby/object:Gem::Dependency
|
34
|
-
name:
|
34
|
+
name: ffi
|
35
35
|
requirement: !ruby/object:Gem::Requirement
|
36
36
|
requirements:
|
37
|
-
- - "
|
38
|
-
- !ruby/object:Gem::Version
|
39
|
-
version: 6.1.0
|
40
|
-
- - "<"
|
37
|
+
- - "~>"
|
41
38
|
- !ruby/object:Gem::Version
|
42
|
-
version:
|
39
|
+
version: 1.15.5
|
43
40
|
type: :runtime
|
44
41
|
prerelease: false
|
45
42
|
version_requirements: !ruby/object:Gem::Requirement
|
46
43
|
requirements:
|
47
|
-
- - "
|
48
|
-
- !ruby/object:Gem::Version
|
49
|
-
version: 6.1.0
|
50
|
-
- - "<"
|
44
|
+
- - "~>"
|
51
45
|
- !ruby/object:Gem::Version
|
52
|
-
version:
|
46
|
+
version: 1.15.5
|
53
47
|
- !ruby/object:Gem::Dependency
|
54
|
-
name:
|
48
|
+
name: nokogiri
|
55
49
|
requirement: !ruby/object:Gem::Requirement
|
56
50
|
requirements:
|
57
51
|
- - "~>"
|
58
52
|
- !ruby/object:Gem::Version
|
59
|
-
version: '
|
53
|
+
version: '1.13'
|
60
54
|
type: :runtime
|
61
55
|
prerelease: false
|
62
56
|
version_requirements: !ruby/object:Gem::Requirement
|
63
57
|
requirements:
|
64
58
|
- - "~>"
|
65
59
|
- !ruby/object:Gem::Version
|
66
|
-
version: '
|
60
|
+
version: '1.13'
|
67
61
|
- !ruby/object:Gem::Dependency
|
68
|
-
name:
|
62
|
+
name: oj
|
69
63
|
requirement: !ruby/object:Gem::Requirement
|
70
64
|
requirements:
|
71
65
|
- - "~>"
|
72
66
|
- !ruby/object:Gem::Version
|
73
|
-
version: '
|
67
|
+
version: '3.13'
|
74
68
|
type: :runtime
|
75
69
|
prerelease: false
|
76
70
|
version_requirements: !ruby/object:Gem::Requirement
|
77
71
|
requirements:
|
78
72
|
- - "~>"
|
79
73
|
- !ruby/object:Gem::Version
|
80
|
-
version: '
|
74
|
+
version: '3.13'
|
81
75
|
- !ruby/object:Gem::Dependency
|
82
|
-
name:
|
76
|
+
name: phlex
|
83
77
|
requirement: !ruby/object:Gem::Requirement
|
84
78
|
requirements:
|
85
79
|
- - "~>"
|
86
80
|
- !ruby/object:Gem::Version
|
87
|
-
version:
|
81
|
+
version: 1.8.1
|
88
82
|
type: :runtime
|
89
83
|
prerelease: false
|
90
84
|
version_requirements: !ruby/object:Gem::Requirement
|
91
85
|
requirements:
|
92
86
|
- - "~>"
|
93
87
|
- !ruby/object:Gem::Version
|
94
|
-
version:
|
88
|
+
version: 1.8.1
|
95
89
|
- !ruby/object:Gem::Dependency
|
96
|
-
name: phlex
|
90
|
+
name: phlex-rails
|
97
91
|
requirement: !ruby/object:Gem::Requirement
|
98
92
|
requirements:
|
99
93
|
- - "~>"
|
100
94
|
- !ruby/object:Gem::Version
|
101
|
-
version: 0.
|
95
|
+
version: 1.0.0
|
102
96
|
type: :runtime
|
103
97
|
prerelease: false
|
104
98
|
version_requirements: !ruby/object:Gem::Requirement
|
105
99
|
requirements:
|
106
100
|
- - "~>"
|
107
101
|
- !ruby/object:Gem::Version
|
108
|
-
version: 0.
|
102
|
+
version: 1.0.0
|
109
103
|
- !ruby/object:Gem::Dependency
|
110
104
|
name: railties
|
111
105
|
requirement: !ruby/object:Gem::Requirement
|
@@ -126,78 +120,47 @@ dependencies:
|
|
126
120
|
- - "<"
|
127
121
|
- !ruby/object:Gem::Version
|
128
122
|
version: '8.0'
|
129
|
-
- !ruby/object:Gem::Dependency
|
130
|
-
name: view_component
|
131
|
-
requirement: !ruby/object:Gem::Requirement
|
132
|
-
requirements:
|
133
|
-
- - "~>"
|
134
|
-
- !ruby/object:Gem::Version
|
135
|
-
version: 2.74.1
|
136
|
-
type: :runtime
|
137
|
-
prerelease: false
|
138
|
-
version_requirements: !ruby/object:Gem::Requirement
|
139
|
-
requirements:
|
140
|
-
- - "~>"
|
141
|
-
- !ruby/object:Gem::Version
|
142
|
-
version: 2.74.1
|
143
123
|
description:
|
144
124
|
email:
|
145
125
|
- joel@developwithstyle.com
|
146
126
|
executables:
|
147
|
-
-
|
148
|
-
- lightningcss
|
127
|
+
- proscenium
|
149
128
|
extensions: []
|
150
129
|
extra_rdoc_files: []
|
151
130
|
files:
|
152
131
|
- CODE_OF_CONDUCT.md
|
153
132
|
- LICENSE.txt
|
154
133
|
- README.md
|
155
|
-
-
|
156
|
-
-
|
157
|
-
- bin/esbuild
|
158
|
-
- bin/lightningcss
|
134
|
+
- bin/proscenium
|
135
|
+
- bin/proscenium.h
|
159
136
|
- config/routes.rb
|
160
137
|
- lib/proscenium.rb
|
161
|
-
- lib/proscenium/compiler.js
|
162
|
-
- lib/proscenium/compilers/esbuild.bench.js
|
163
|
-
- lib/proscenium/compilers/esbuild.js
|
164
|
-
- lib/proscenium/compilers/esbuild/argument_error.js
|
165
|
-
- lib/proscenium/compilers/esbuild/compile_error.js
|
166
|
-
- lib/proscenium/compilers/esbuild/css/postcss.js
|
167
|
-
- lib/proscenium/compilers/esbuild/css_plugin.js
|
168
|
-
- lib/proscenium/compilers/esbuild/env_plugin.js
|
169
|
-
- lib/proscenium/compilers/esbuild/http_bundle_plugin.js
|
170
|
-
- lib/proscenium/compilers/esbuild/import_map.js
|
171
|
-
- lib/proscenium/compilers/esbuild/resolve_plugin.js
|
172
|
-
- lib/proscenium/compilers/esbuild/setup_plugin.js
|
173
|
-
- lib/proscenium/compilers/esbuild/solidjs_plugin.js
|
174
138
|
- lib/proscenium/css_module.rb
|
139
|
+
- lib/proscenium/css_module/class_names_resolver.rb
|
140
|
+
- lib/proscenium/css_module/resolver.rb
|
175
141
|
- lib/proscenium/current.rb
|
142
|
+
- lib/proscenium/esbuild.rb
|
143
|
+
- lib/proscenium/esbuild/golib.rb
|
176
144
|
- lib/proscenium/helper.rb
|
177
|
-
- lib/proscenium/
|
145
|
+
- lib/proscenium/log_subscriber.rb
|
178
146
|
- lib/proscenium/middleware.rb
|
179
147
|
- lib/proscenium/middleware/base.rb
|
180
148
|
- lib/proscenium/middleware/esbuild.rb
|
181
|
-
- lib/proscenium/middleware/lightningcss.rb
|
182
|
-
- lib/proscenium/middleware/outside_root.rb
|
183
|
-
- lib/proscenium/middleware/runtime.rb
|
184
|
-
- lib/proscenium/middleware/static.rb
|
185
149
|
- lib/proscenium/middleware/url.rb
|
186
150
|
- lib/proscenium/phlex.rb
|
187
|
-
- lib/proscenium/phlex/
|
151
|
+
- lib/proscenium/phlex/component_concerns.rb
|
152
|
+
- lib/proscenium/phlex/page.rb
|
188
153
|
- lib/proscenium/phlex/react_component.rb
|
189
|
-
- lib/proscenium/
|
154
|
+
- lib/proscenium/phlex/resolve_css_modules.rb
|
190
155
|
- lib/proscenium/railtie.rb
|
191
|
-
- lib/proscenium/runtime/auto_reload.js
|
192
|
-
- lib/proscenium/runtime/react_shim/index.js
|
193
|
-
- lib/proscenium/runtime/react_shim/package.json
|
194
156
|
- lib/proscenium/side_load.rb
|
195
|
-
- lib/proscenium/
|
157
|
+
- lib/proscenium/side_load/ensure_loaded.rb
|
158
|
+
- lib/proscenium/side_load/helper.rb
|
159
|
+
- lib/proscenium/side_load/monkey.rb
|
196
160
|
- lib/proscenium/version.rb
|
197
161
|
- lib/proscenium/view_component.rb
|
198
162
|
- lib/proscenium/view_component/react_component.rb
|
199
163
|
- lib/proscenium/view_component/tag_builder.rb
|
200
|
-
- lib/tasks/assets.rake
|
201
164
|
homepage: https://github.com/joelmoss/proscenium
|
202
165
|
licenses:
|
203
166
|
- MIT
|
@@ -221,7 +184,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
221
184
|
- !ruby/object:Gem::Version
|
222
185
|
version: '0'
|
223
186
|
requirements: []
|
224
|
-
rubygems_version: 3.
|
187
|
+
rubygems_version: 3.4.13
|
225
188
|
signing_key:
|
226
189
|
specification_version: 4
|
227
190
|
summary: The engine powering your Rails frontend
|
@@ -1,13 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
module Proscenium
|
4
|
-
class Connection < ActionCable::Connection::Base
|
5
|
-
identified_by :uid
|
6
|
-
|
7
|
-
def connect
|
8
|
-
self.uid = request.params[:uid]
|
9
|
-
logger.add_tags(uid)
|
10
|
-
logger.info 'connected to Proscenium'
|
11
|
-
end
|
12
|
-
end
|
13
|
-
end
|
data/bin/esbuild
DELETED
Binary file
|
data/bin/lightningcss
DELETED
Binary file
|
data/lib/proscenium/compiler.js
DELETED
@@ -1,84 +0,0 @@
|
|
1
|
-
// Recursively Scans the /app path for any JS/JSX/CSS files, and compiles each one, while also
|
2
|
-
// building a manifest (JSON) of all files that are built. The manifest contains a simple mapping of
|
3
|
-
// source file => compiled file. The compiled files are appended with the content digest, for
|
4
|
-
// caching.
|
5
|
-
|
6
|
-
import { writeAll } from 'std/streams/mod.ts'
|
7
|
-
import { MuxAsyncIterator } from 'std/async/mod.ts'
|
8
|
-
import { expandGlob, ensureDir } from 'std/fs/mod.ts'
|
9
|
-
import { extname, relative, join, dirname, parse } from 'std/path/mod.ts'
|
10
|
-
|
11
|
-
import build from './cli.js'
|
12
|
-
|
13
|
-
const extnameToBuilderMap = {
|
14
|
-
'.js': 'javascript'
|
15
|
-
}
|
16
|
-
|
17
|
-
async function main(args = []) {
|
18
|
-
const [root, ...paths] = args
|
19
|
-
const outDir = join(root, 'public', 'assets')
|
20
|
-
const manifest = {}
|
21
|
-
const promises = []
|
22
|
-
const mux = new MuxAsyncIterator()
|
23
|
-
|
24
|
-
paths.forEach(path => {
|
25
|
-
mux.add(expandGlob(`${path}/**/*.{css,js,jsx}`, { root }))
|
26
|
-
})
|
27
|
-
|
28
|
-
for await (const file of mux) {
|
29
|
-
const builder = extnameToBuilderMap[extname(file.path)]
|
30
|
-
|
31
|
-
if (!builder) {
|
32
|
-
console.error('--! Failed to compile %o (unknown builder)', relative(root, file.path))
|
33
|
-
continue
|
34
|
-
}
|
35
|
-
|
36
|
-
promises.push(
|
37
|
-
compile({ ...file, root, outDir }).then(({ inPath, outPath }) => {
|
38
|
-
manifest[inPath] = outPath
|
39
|
-
})
|
40
|
-
)
|
41
|
-
}
|
42
|
-
|
43
|
-
await Promise.allSettled(promises)
|
44
|
-
|
45
|
-
return new TextEncoder().encode(JSON.stringify(manifest))
|
46
|
-
}
|
47
|
-
|
48
|
-
function compile({ root, path, outDir }) {
|
49
|
-
const entrypoint = relative(root, path)
|
50
|
-
const { dir, name, ext } = parse(entrypoint)
|
51
|
-
const builder = extnameToBuilderMap[ext]
|
52
|
-
|
53
|
-
console.log('--- Compiling %o with %s builder...', entrypoint, builder)
|
54
|
-
|
55
|
-
return build([root, entrypoint, builder])
|
56
|
-
.then(src => {
|
57
|
-
console.log(2)
|
58
|
-
return digest(src)
|
59
|
-
})
|
60
|
-
.then(({ hash, source }) => {
|
61
|
-
const path = join(outDir, dir, `${name}-${hash}${ext}`)
|
62
|
-
|
63
|
-
return ensureDir(dirname(path))
|
64
|
-
.then(() => Deno.writeTextFile(path, new TextDecoder().decode(source)))
|
65
|
-
.then(() => ({ inPath: entrypoint, outPath: relative(outDir, path) }))
|
66
|
-
})
|
67
|
-
}
|
68
|
-
|
69
|
-
async function digest(source) {
|
70
|
-
const view = new DataView(await crypto.subtle.digest('SHA-1', source))
|
71
|
-
|
72
|
-
let hash = ''
|
73
|
-
for (let index = 0; index < view.byteLength; index += 4) {
|
74
|
-
hash += view.getUint32(index).toString(16).padStart(8, '0')
|
75
|
-
}
|
76
|
-
|
77
|
-
return { hash, source }
|
78
|
-
}
|
79
|
-
|
80
|
-
export default main
|
81
|
-
|
82
|
-
if (import.meta.main) {
|
83
|
-
await writeAll(Deno.stdout, await main(Deno.args))
|
84
|
-
}
|
@@ -1,24 +0,0 @@
|
|
1
|
-
export default class ArgumentError extends Error {
|
2
|
-
static MESSAGES = {
|
3
|
-
rootRequired: 'Current working directory is required as --root.',
|
4
|
-
lightningcssBinRequired:
|
5
|
-
'Path to the lightningcss CLI binary is required as --lightningcss-bin.',
|
6
|
-
pathsRequired: 'One or more file paths or globs are required.',
|
7
|
-
|
8
|
-
rootUnknown: ({ root }) => `A valid working directory is required - received ${root}`
|
9
|
-
}
|
10
|
-
|
11
|
-
constructor(reason, options) {
|
12
|
-
let message = ArgumentError.MESSAGES[reason]
|
13
|
-
if (typeof message === 'function') {
|
14
|
-
message = message(options)
|
15
|
-
}
|
16
|
-
|
17
|
-
message = `${reason}: ${message}`
|
18
|
-
|
19
|
-
super(message, options)
|
20
|
-
|
21
|
-
this.reason = reason
|
22
|
-
this.message = message
|
23
|
-
}
|
24
|
-
}
|
@@ -1,148 +0,0 @@
|
|
1
|
-
export default function () {
|
2
|
-
if (Deno.env.get('RAILS_ENV') === 'development') {
|
3
|
-
return function (detail) {
|
4
|
-
const template = `
|
5
|
-
<style>
|
6
|
-
:host {
|
7
|
-
position: fixed;
|
8
|
-
z-index: 99999;
|
9
|
-
top: 0;
|
10
|
-
left: 0;
|
11
|
-
width: 100%;
|
12
|
-
height: 100%;
|
13
|
-
overflow-y: scroll;
|
14
|
-
margin: 0;
|
15
|
-
background: rgba(0, 0, 0, 0.66);
|
16
|
-
display: flex;
|
17
|
-
align-items: center;
|
18
|
-
--monospace: 'SFMono-Regular', Consolas,
|
19
|
-
'Liberation Mono', Menlo, Courier, monospace;
|
20
|
-
--red: #ff5555;
|
21
|
-
--yellow: #e2aa53;
|
22
|
-
--purple: #cfa4ff;
|
23
|
-
--cyan: #2dd9da;
|
24
|
-
--dim: #c9c9c9;
|
25
|
-
}
|
26
|
-
|
27
|
-
.window {
|
28
|
-
font-family: var(--monospace);
|
29
|
-
line-height: 1.5;
|
30
|
-
width: 800px;
|
31
|
-
height: 66vh;
|
32
|
-
color: #d8d8d8;
|
33
|
-
margin: 30px auto;
|
34
|
-
padding: 25px 40px;
|
35
|
-
position: relative;
|
36
|
-
background: #181818;
|
37
|
-
border-radius: 6px 6px 8px 8px;
|
38
|
-
box-shadow: 0 19px 38px rgba(0,0,0,0.30), 0 15px 12px rgba(0,0,0,0.22);
|
39
|
-
overflow: hidden;
|
40
|
-
border-top: 8px solid var(--red);
|
41
|
-
}
|
42
|
-
|
43
|
-
pre {
|
44
|
-
font-family: var(--monospace);
|
45
|
-
font-size: 16px;
|
46
|
-
margin: 0 0 1em 0;
|
47
|
-
overflow-x: scroll;
|
48
|
-
scrollbar-width: none;
|
49
|
-
}
|
50
|
-
|
51
|
-
pre::-webkit-scrollbar {
|
52
|
-
display: none;
|
53
|
-
}
|
54
|
-
|
55
|
-
.title, .message {
|
56
|
-
line-height: 1.3;
|
57
|
-
font-weight: 600;
|
58
|
-
white-space: pre-wrap;
|
59
|
-
}
|
60
|
-
|
61
|
-
.message-body {
|
62
|
-
color: var(--red);
|
63
|
-
}
|
64
|
-
|
65
|
-
.file {
|
66
|
-
color: var(--cyan);
|
67
|
-
margin-bottom: 0;
|
68
|
-
white-space: pre-wrap;
|
69
|
-
word-break: break-all;
|
70
|
-
}
|
71
|
-
|
72
|
-
.code {
|
73
|
-
background: black;
|
74
|
-
border-left: 3px solid gray;
|
75
|
-
padding: 10px 0 0 20px;
|
76
|
-
}
|
77
|
-
.lineText {
|
78
|
-
display: block;
|
79
|
-
white-space: pre-wrap;
|
80
|
-
}
|
81
|
-
.lineCursor {
|
82
|
-
white-space: pre;
|
83
|
-
color: blueviolet;
|
84
|
-
display: block;
|
85
|
-
}
|
86
|
-
</style>
|
87
|
-
<div class="window">
|
88
|
-
<pre class="title">COMPILE ERROR!</pre>
|
89
|
-
<pre class="message"><span class="message-body"></span> in <span class="file"></span></pre>
|
90
|
-
<pre class="code"><span class="lineText"></span><span class="lineCursor"></span></pre>
|
91
|
-
</div>
|
92
|
-
`
|
93
|
-
|
94
|
-
class ErrorOverlay extends HTMLElement {
|
95
|
-
constructor(err) {
|
96
|
-
super()
|
97
|
-
|
98
|
-
this.root = this.attachShadow({ mode: 'open' })
|
99
|
-
this.root.innerHTML = template
|
100
|
-
this.root.querySelector('.message-body').textContent = err.text.trim()
|
101
|
-
if (err.location) {
|
102
|
-
const location = [err.location.file]
|
103
|
-
err.location.line && location.push(err.location.line)
|
104
|
-
err.location.column && location.push(err.location.column)
|
105
|
-
this.root.querySelector('.file').textContent = `/${location.join(':')}`
|
106
|
-
|
107
|
-
if (err.location.lineText) {
|
108
|
-
this.root.querySelector('.lineText').textContent = err.location.lineText
|
109
|
-
this.root.querySelector('.lineCursor').textContent =
|
110
|
-
''.padStart(err.location.column - 1, ' ') + '^'
|
111
|
-
} else {
|
112
|
-
this.root.querySelector('.code').remove()
|
113
|
-
}
|
114
|
-
|
115
|
-
console.error('%s at %O', err.text, location)
|
116
|
-
} else {
|
117
|
-
console.error(err.text)
|
118
|
-
}
|
119
|
-
|
120
|
-
this.root.querySelector('.window').addEventListener('click', e => {
|
121
|
-
e.stopPropagation()
|
122
|
-
})
|
123
|
-
|
124
|
-
this.addEventListener('click', () => {
|
125
|
-
this.close()
|
126
|
-
})
|
127
|
-
}
|
128
|
-
|
129
|
-
close() {
|
130
|
-
this.parentNode?.removeChild(this)
|
131
|
-
}
|
132
|
-
}
|
133
|
-
|
134
|
-
const overlayId = 'proscenium-error-overlay'
|
135
|
-
if (customElements && !customElements.get(overlayId)) {
|
136
|
-
customElements.define(overlayId, ErrorOverlay)
|
137
|
-
}
|
138
|
-
|
139
|
-
document.body.appendChild(new ErrorOverlay(detail))
|
140
|
-
}
|
141
|
-
} else {
|
142
|
-
return function (detail) {
|
143
|
-
const location = `/${detail.location.file}:${detail.location.line}:${detail.location.column}`
|
144
|
-
console.error('%s at %O', detail.text, location)
|
145
|
-
throw `${detail.text} at ${location}`
|
146
|
-
}
|
147
|
-
}
|
148
|
-
}
|
@@ -1,67 +0,0 @@
|
|
1
|
-
import { expandGlob } from 'std/fs/mod.ts'
|
2
|
-
import postcss from 'postcss'
|
3
|
-
|
4
|
-
export default async (root, path) => {
|
5
|
-
let tmpFile
|
6
|
-
let contents
|
7
|
-
|
8
|
-
const mixinFiles = []
|
9
|
-
for await (const file of expandGlob('lib/**/*.mixin.css', { root, globstar: true })) {
|
10
|
-
mixinFiles.push(file.path)
|
11
|
-
}
|
12
|
-
|
13
|
-
// Only process mixins with PostCSS if there are any 'lib/**/*.mixin.css' files.
|
14
|
-
if (mixinFiles.length > 0) {
|
15
|
-
tmpFile = await Deno.makeTempFile()
|
16
|
-
contents = await Deno.readTextFile(path)
|
17
|
-
|
18
|
-
const result = await postcss([mixinsPlugin({ mixinFiles })]).process(contents, { from: path })
|
19
|
-
contents = result.css
|
20
|
-
}
|
21
|
-
|
22
|
-
return [tmpFile, contents]
|
23
|
-
}
|
24
|
-
|
25
|
-
const mixinsPlugin = (opts = {}) => {
|
26
|
-
return {
|
27
|
-
postcssPlugin: 'mixins',
|
28
|
-
|
29
|
-
prepare() {
|
30
|
-
const mixins = {}
|
31
|
-
|
32
|
-
return {
|
33
|
-
async Once(_, helpers) {
|
34
|
-
for (const path of opts.mixinFiles) {
|
35
|
-
const content = await Deno.readTextFile(path)
|
36
|
-
const root = helpers.parse(content, { from: path })
|
37
|
-
|
38
|
-
root.walkAtRules('define-mixin', atrule => {
|
39
|
-
mixins[atrule.params] = atrule
|
40
|
-
})
|
41
|
-
}
|
42
|
-
},
|
43
|
-
|
44
|
-
AtRule: {
|
45
|
-
mixin: (rule, helpers) => {
|
46
|
-
const mixin = mixins[rule.params]
|
47
|
-
|
48
|
-
if (!mixin) {
|
49
|
-
throw rule.error(`Undefined mixin '${rule.params}'`)
|
50
|
-
}
|
51
|
-
|
52
|
-
const proxy = new helpers.Root()
|
53
|
-
for (let i = 0; i < mixin.nodes.length; i++) {
|
54
|
-
const node = mixin.nodes[i].clone()
|
55
|
-
delete node.raws.before
|
56
|
-
proxy.append(node)
|
57
|
-
}
|
58
|
-
|
59
|
-
rule.parent.insertBefore(rule, proxy)
|
60
|
-
|
61
|
-
if (rule.parent) rule.remove()
|
62
|
-
}
|
63
|
-
}
|
64
|
-
}
|
65
|
-
}
|
66
|
-
}
|
67
|
-
}
|