shoelace-rails 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (81) hide show
  1. checksums.yaml +7 -0
  2. data/.github/workflows/main.yml +85 -0
  3. data/.gitignore +20 -0
  4. data/Appraisals +25 -0
  5. data/CHANGELOG.md +3 -0
  6. data/CODE_OF_CONDUCT.md +84 -0
  7. data/Gemfile +11 -0
  8. data/LICENSE.txt +21 -0
  9. data/README.md +178 -0
  10. data/Rakefile +27 -0
  11. data/app/helpers/shoelace/form_helper.rb +451 -0
  12. data/bin/console +15 -0
  13. data/bin/setup +8 -0
  14. data/dist/.keep +0 -0
  15. data/dist/types/.keep +0 -0
  16. data/gemfiles/rails_50.gemfile +12 -0
  17. data/gemfiles/rails_51.gemfile +11 -0
  18. data/gemfiles/rails_52.gemfile +11 -0
  19. data/gemfiles/rails_60.gemfile +11 -0
  20. data/gemfiles/rails_61.gemfile +11 -0
  21. data/gemfiles/rails_70.gemfile +11 -0
  22. data/gemfiles/rails_edge.gemfile +14 -0
  23. data/lib/shoelace/engine.rb +8 -0
  24. data/lib/shoelace/rails/version.rb +7 -0
  25. data/lib/shoelace/rails.rb +10 -0
  26. data/lib/shoelace/testing.rb +40 -0
  27. data/package.json +50 -0
  28. data/rollup.config.js +49 -0
  29. data/shoelace-rails.gemspec +35 -0
  30. data/src/index.ts +2 -0
  31. data/src/turbo/index.ts +6 -0
  32. data/src/turbo/polyfills/formdata-event.js +27 -0
  33. data/src/turbo/sl-turbo-form.ts +110 -0
  34. data/src/turbolinks/features/confirm.ts +42 -0
  35. data/src/turbolinks/features/disable.ts +94 -0
  36. data/src/turbolinks/features/remote.ts +107 -0
  37. data/src/turbolinks/index.ts +6 -0
  38. data/src/turbolinks/selectors.ts +38 -0
  39. data/src/turbolinks/start.ts +38 -0
  40. data/src/turbolinks/turbolinks.ts +78 -0
  41. data/src/turbolinks/utils/ajax.ts +146 -0
  42. data/src/turbolinks/utils/csp.ts +20 -0
  43. data/src/turbolinks/utils/csrf.ts +33 -0
  44. data/src/turbolinks/utils/dom.ts +40 -0
  45. data/src/turbolinks/utils/event.ts +57 -0
  46. data/src/turbolinks/utils/form.ts +58 -0
  47. data/test/dummy_app/Gemfile +19 -0
  48. data/test/dummy_app/Rakefile +6 -0
  49. data/test/dummy_app/app/controllers/hotwire_forms_controller.rb +46 -0
  50. data/test/dummy_app/app/controllers/turbolinks_forms_controller.rb +37 -0
  51. data/test/dummy_app/app/models/user.rb +16 -0
  52. data/test/dummy_app/app/packs/entrypoints/hotwire.js +1 -0
  53. data/test/dummy_app/app/packs/entrypoints/turbolinks.js +5 -0
  54. data/test/dummy_app/app/views/hotwire_forms/form.html.erb +45 -0
  55. data/test/dummy_app/app/views/hotwire_forms/show.html.erb +5 -0
  56. data/test/dummy_app/app/views/layouts/application.html.erb +39 -0
  57. data/test/dummy_app/app/views/turbolinks_forms/form.html.erb +44 -0
  58. data/test/dummy_app/app/views/turbolinks_forms/show.html.erb +5 -0
  59. data/test/dummy_app/bin/rails +5 -0
  60. data/test/dummy_app/bin/webpack +18 -0
  61. data/test/dummy_app/bin/yarn +18 -0
  62. data/test/dummy_app/config/application.rb +16 -0
  63. data/test/dummy_app/config/boot.rb +4 -0
  64. data/test/dummy_app/config/environment.rb +2 -0
  65. data/test/dummy_app/config/environments/development.rb +10 -0
  66. data/test/dummy_app/config/environments/test.rb +18 -0
  67. data/test/dummy_app/config/routes.rb +4 -0
  68. data/test/dummy_app/config/webpack/development.js +5 -0
  69. data/test/dummy_app/config/webpack/production.js +1 -0
  70. data/test/dummy_app/config/webpack/test.js +5 -0
  71. data/test/dummy_app/config/webpacker.yml +33 -0
  72. data/test/dummy_app/config.ru +6 -0
  73. data/test/dummy_app/package.json +24 -0
  74. data/test/dummy_app/test/system/hotwire_form_test.rb +65 -0
  75. data/test/dummy_app/test/system/turbolinks_form_test.rb +39 -0
  76. data/test/dummy_app/test/test_helper.rb +68 -0
  77. data/test/helpers/form_helper_test.rb +397 -0
  78. data/test/test_helper.rb +18 -0
  79. data/tsconfig.json +19 -0
  80. data/yarn.lock +249 -0
  81. metadata +196 -0
@@ -0,0 +1,397 @@
1
+ require 'test_helper'
2
+
3
+ require_relative '../../app/helpers/shoelace/form_helper'
4
+
5
+ class FormHelperTest < ActionView::TestCase
6
+ include Shoelace::FormHelper
7
+
8
+ test "#sl_text_field_tag with name and value" do
9
+ assert_dom_equal <<~HTML, sl_text_field_tag('name', 'Your name')
10
+ <sl-input type="text" name="name" id="name" value="Your name"></sl-input>
11
+ HTML
12
+ end
13
+
14
+ test "#sl_text_field_tag with class string" do
15
+ assert_dom_equal <<~HTML, sl_text_field_tag('name', 'Your name', class: "admin")
16
+ <sl-input type="text" name="name" id="name" value="Your name" class="admin"></sl-input>
17
+ HTML
18
+ end
19
+
20
+ test "#sl_text_field_tag with params" do
21
+ assert_raises ActionController::UnfilteredParameters do
22
+ sl_text_field_tag('name', 'Your name', **ActionController::Parameters.new(key: "value"))
23
+ end
24
+ end
25
+
26
+ test "#sl_text_field_tag with disabled: true" do
27
+ assert_dom_equal <<~HTML, sl_text_field_tag('name', 'Your name', disabled: true)
28
+ <sl-input type="text" name="name" id="name" value="Your name" disabled="disabled"></sl-input>
29
+ HTML
30
+ end
31
+
32
+ test "#sl_submit_tag" do
33
+ assert_dom_equal <<~HTML, sl_submit_tag("Save")
34
+ <sl-button type="submit" variant="primary" data-disable-with="Save">Save</sl-button>
35
+ HTML
36
+ end
37
+
38
+ test "#sl_submit_tag with onclick" do
39
+ assert_dom_equal <<~HTML, sl_submit_tag("Save", onclick: "alert('hello!')", data: { disable_with: "Saving..." })
40
+ <sl-button type="submit" variant="primary" onclick="alert(&#39;hello!&#39;)" data-disable-with="Saving...">Save</sl-button>
41
+ HTML
42
+ end
43
+
44
+ test "#sl_button_tag" do
45
+ assert_dom_equal(<<~HTML, sl_button_tag { "Submit" })
46
+ <sl-button>Submit</sl-button>
47
+ HTML
48
+ end
49
+
50
+ test "#sl_radio_button" do
51
+ assert_dom_equal(<<~HTML, sl_radio_button(:user, :name, 'userid-314', checked: true) { "Yuki Nishijima" })
52
+ <sl-radio value="userid-314" checked="checked" name="user[name]" id="user_name_userid-314">Yuki Nishijima</sl-radio>
53
+ HTML
54
+ end
55
+
56
+ test "#sl_form_tag" do
57
+ assert_dom_equal(<<~HTML, sl_form_tag("/posts") { })
58
+ <form data-remote="true" action="/posts" accept-charset="UTF-8" method="post">
59
+ <input name="utf8" type="hidden" value="&#x2713;" />
60
+ </sl-form>
61
+ HTML
62
+ end
63
+
64
+ test "#sl_form_with" do
65
+ assert_dom_equal(<<~HTML, sl_form_with(url: "/") {})
66
+ <form action="/" accept-charset="UTF-8" data-remote="true" method="post">
67
+ <input name="utf8" type="hidden" value="&#x2713;" />
68
+ </sl-form>
69
+ HTML
70
+ end
71
+
72
+ test "#sl_form_for" do
73
+ assert_dom_equal(<<~HTML, sl_form_for(User.new, url: "/") { })
74
+ <form class="new_user" id="new_user" action="/" accept-charset="UTF-8" method="post">
75
+ <input name="utf8" type="hidden" value="&#x2713;" />
76
+ </sl-form>
77
+ HTML
78
+ end
79
+
80
+ test "#sl_turbo_form_tag" do
81
+ assert_dom_equal(<<~HTML, sl_turbo_form_tag("/posts") { })
82
+ <form action="/posts" accept-charset="UTF-8" method="post">
83
+ <input name="utf8" type="hidden" value="&#x2713;" />
84
+ </form>
85
+ HTML
86
+ end
87
+
88
+ test "#sl_turbo_form_with" do
89
+ assert_dom_equal(<<~HTML, sl_turbo_form_with(url: "/") {})
90
+ <form action="/" accept-charset="UTF-8" data-remote="true" method="post">
91
+ <input name="utf8" type="hidden" value="&#x2713;" />
92
+ </form>
93
+ HTML
94
+ end
95
+
96
+ test "#sl_turbo_form_for" do
97
+ assert_dom_equal(<<~HTML, sl_turbo_form_for(User.new, url: "/") { })
98
+ <form class="new_user" id="new_user" action="/" accept-charset="UTF-8" method="post">
99
+ <input name="utf8" type="hidden" value="&#x2713;" />
100
+ </form>
101
+ HTML
102
+ end
103
+
104
+ test "#text_field" do
105
+ sl_form_for(User.new, url: "/") do |form|
106
+ assert_dom_equal <<~HTML, form.text_field(:name)
107
+ <sl-input label="Name" type="text" name="user[name]" id="user_name"></sl-input>
108
+ HTML
109
+ end
110
+ end
111
+
112
+ test "#text_field with a default value" do
113
+ sl_form_for(User.new(name: "Yuki"), url: "/") do |form|
114
+ assert_dom_equal <<~HTML, form.text_field(:name)
115
+ <sl-input label="Name" type="text" name="user[name]" id="user_name" value="Yuki"></sl-input>
116
+ HTML
117
+ end
118
+ end
119
+
120
+ test "#email_field" do
121
+ sl_form_for(User.new, url: "/") do |form|
122
+ assert_dom_equal <<~HTML, form.email_field(:name)
123
+ <sl-input label="Name" type="email" name="user[name]" id="user_name"></sl-input>
124
+ HTML
125
+ end
126
+ end
127
+
128
+ test "#number_field" do
129
+ sl_form_for(User.new, url: "/") do |form|
130
+ assert_dom_equal <<~HTML, form.number_field(:name)
131
+ <sl-input label="Name" type="number" name="user[name]" id="user_name"></sl-input>
132
+ HTML
133
+ end
134
+ end
135
+
136
+ test "#password_field" do
137
+ sl_form_for(User.new, url: "/") do |form|
138
+ assert_dom_equal <<~HTML, form.password_field(:name)
139
+ <sl-input label="Name" type="password" name="user[name]" id="user_name"></sl-input>
140
+ HTML
141
+ end
142
+ end
143
+
144
+ test "#search_field" do
145
+ sl_form_for(User.new, url: "/") do |form|
146
+ assert_dom_equal <<~HTML, form.search_field(:name)
147
+ <sl-input label="Name" type="search" name="user[name]" id="user_name"></sl-input>
148
+ HTML
149
+ end
150
+ end
151
+
152
+ test "#telephone_field" do
153
+ sl_form_for(User.new, url: "/") do |form|
154
+ assert_dom_equal <<~HTML, form.telephone_field(:name)
155
+ <sl-input label="Name" type="tel" name="user[name]" id="user_name"></sl-input>
156
+ HTML
157
+ end
158
+ end
159
+
160
+ test "#phone_field" do
161
+ sl_form_for(User.new, url: "/") do |form|
162
+ assert_dom_equal <<~HTML, form.phone_field(:name)
163
+ <sl-input label="Name" type="tel" name="user[name]" id="user_name"></sl-input>
164
+ HTML
165
+ end
166
+ end
167
+
168
+ test "#text_field with a block" do
169
+ sl_form_for(User.new(name: "Yuki"), url: "/") do |form|
170
+ assert_dom_equal <<~HTML, form.text_field(:name) { 'slot' }
171
+ <sl-input label="Name" type="text" name="user[name]" id="user_name" value="Yuki">slot</sl-input>
172
+ HTML
173
+ end
174
+ end
175
+
176
+ test "#url_field" do
177
+ sl_form_for(User.new, url: "/") do |form|
178
+ assert_dom_equal <<~HTML, form.url_field(:name)
179
+ <sl-input label="Name" type="url" name="user[name]" id="user_name"></sl-input>
180
+ HTML
181
+ end
182
+ end
183
+
184
+ test "#color_field" do
185
+ sl_form_for(User.new, url: "/") do |form|
186
+ assert_dom_equal <<~HTML, form.color_field(:name)
187
+ <sl-color-picker name="user[name]" id="user_name"></sl-color-picker>
188
+ HTML
189
+ end
190
+ end
191
+
192
+ test "#range_field" do
193
+ sl_form_for(User.new, url: "/") do |form|
194
+ assert_dom_equal <<~HTML, form.range_field(:name)
195
+ <sl-range name="user[name]" id="user_name"></sl-range>
196
+ HTML
197
+ end
198
+ end
199
+
200
+ test "#switch_field" do
201
+ sl_form_for(User.new, url: "/") do |form|
202
+ assert_dom_equal <<~HTML, form.switch_field(:name)
203
+ <sl-switch name="user[name]" id="user_name">Name</sl-switch>
204
+ HTML
205
+ end
206
+ end
207
+
208
+ test "#text_area" do
209
+ sl_form_for(User.new, url: "/") do |form|
210
+ assert_dom_equal <<~HTML, form.text_area(:name)
211
+ <sl-textarea resize="auto" name="user[name]" id="user_name"></sl-textarea>
212
+ HTML
213
+ end
214
+ end
215
+
216
+ test "#check_box" do
217
+ sl_form_for(User.new, url: "/") do |form|
218
+ assert_dom_equal <<~HTML, form.check_box(:name)
219
+ <sl-checkbox value="1" name="user[name]" id="user_name">Name</sl-checkbox>
220
+ HTML
221
+ end
222
+ end
223
+
224
+ test "#check_box with a block" do
225
+ sl_form_for(User.new, url: "/") do |form|
226
+ assert_dom_equal <<~HTML, form.check_box(:name) { "Maintainer Name" }
227
+ <sl-checkbox value="1" name="user[name]" id="user_name">Maintainer Name</sl-checkbox>
228
+ HTML
229
+ end
230
+ end
231
+
232
+ test "#select" do
233
+ users = {
234
+ "Yuki Nishijima" => 1,
235
+ "Matz" => 2,
236
+ "Koichi Sasada" => 3
237
+ }
238
+
239
+ sl_form_for(User.new, url: "/") do |form|
240
+ assert_dom_equal <<~HTML, form.select(:name, users)
241
+ <sl-select name="user[name]" id="user_name">
242
+ <sl-menu-item value="1">Yuki Nishijima</sl-menu-item>
243
+ <sl-menu-item value="2">Matz</sl-menu-item>
244
+ <sl-menu-item value="3">Koichi Sasada</sl-menu-item>
245
+ </sl-select>
246
+ HTML
247
+ end
248
+ end
249
+
250
+ test "#select with multiple" do
251
+ users = {
252
+ "Yuki Nishijima" => 1,
253
+ "Matz" => 2,
254
+ "Koichi Sasada" => 3
255
+ }
256
+
257
+ sl_form_for(User.new, url: "/") do |form|
258
+ assert_dom_equal <<~HTML, form.select(:name, users, {}, { multiple: true })
259
+ <sl-select name="user[name][]" id="user_name" multiple="multiple">
260
+ <sl-menu-item value="1">Yuki Nishijima</sl-menu-item>
261
+ <sl-menu-item value="2">Matz</sl-menu-item>
262
+ <sl-menu-item value="3">Koichi Sasada</sl-menu-item>
263
+ </sl-select>
264
+ HTML
265
+ end
266
+ end
267
+
268
+ test "#select with grouped options" do
269
+ users = {
270
+ "Main maintainers" => [
271
+ ["Matz", 2],
272
+ ["Koichi Sasada", 3]
273
+ ],
274
+ "Default gem maintainers" => [
275
+ ["Yuki Nishijima", 1],
276
+ ]
277
+ }
278
+
279
+ sl_form_for(User.new, url: "/") do |form|
280
+ assert_dom_equal <<~HTML, form.select(:name, users)
281
+ <sl-select name="user[name]" id="user_name">
282
+ <sl-menu-label>Main maintainers</sl-menu-label>
283
+ <sl-menu-item value="2">Matz</sl-menu-item>
284
+ <sl-menu-item value="3">Koichi Sasada</sl-menu-item>
285
+ <sl-divider></sl-divider>
286
+ <sl-menu-label>Default gem maintainers</sl-menu-label>
287
+ <sl-menu-item value="1">Yuki Nishijima</sl-menu-item>
288
+ </sl-select>
289
+ HTML
290
+ end
291
+ end
292
+
293
+ test "#select with grouped options with a default value" do
294
+ users = {
295
+ "Main maintainers" => [
296
+ ["Matz", 2],
297
+ ["Koichi Sasada", 3]
298
+ ],
299
+ "Default gem maintainers" => [
300
+ ["Yuki Nishijima", 1],
301
+ ]
302
+ }
303
+
304
+ sl_form_for(User.new(name: "2"), url: "/") do |form|
305
+ assert_dom_equal <<~HTML, form.select(:name, users)
306
+ <sl-select name="user[name]" id="user_name" value="2">
307
+ <sl-menu-label>Main maintainers</sl-menu-label>
308
+ <sl-menu-item value="2" checked="checked">Matz</sl-menu-item>
309
+ <sl-menu-item value="3">Koichi Sasada</sl-menu-item>
310
+ <sl-divider></sl-divider>
311
+ <sl-menu-label>Default gem maintainers</sl-menu-label>
312
+ <sl-menu-item value="1">Yuki Nishijima</sl-menu-item>
313
+ </sl-select>
314
+ HTML
315
+ end
316
+ end
317
+
318
+ test "#collection_select" do
319
+ users = {
320
+ 1 => "Yuki Nishijima",
321
+ 2 => "Matz",
322
+ 3 => "Koichi Sasada",
323
+ }
324
+
325
+ sl_form_for(User.new, url: "/") do |form|
326
+ assert_dom_equal <<~HTML, form.collection_select(:name, users, :first, :last)
327
+ <sl-select name="user[name]" id="user_name">
328
+ <sl-menu-item value="1">Yuki Nishijima</sl-menu-item>
329
+ <sl-menu-item value="2">Matz</sl-menu-item>
330
+ <sl-menu-item value="3">Koichi Sasada</sl-menu-item>
331
+ </sl-select>
332
+ HTML
333
+ end
334
+ end
335
+
336
+ test "#collection_select with a defalut value" do
337
+ users = {
338
+ 1 => "Yuki Nishijima",
339
+ 2 => "Matz",
340
+ 3 => "Koichi Sasada",
341
+ }
342
+
343
+ sl_form_for(User.new(name: "2"), url: "/") do |form|
344
+ assert_dom_equal <<~HTML, form.collection_select(:name, users, :first, :last)
345
+ <sl-select name="user[name]" id="user_name" value="2">
346
+ <sl-menu-item value="1">Yuki Nishijima</sl-menu-item>
347
+ <sl-menu-item value="2" checked="checked">Matz</sl-menu-item>
348
+ <sl-menu-item value="3">Koichi Sasada</sl-menu-item>
349
+ </sl-select>
350
+ HTML
351
+ end
352
+ end
353
+
354
+ test "#collection_radio_buttons" do
355
+ users = {
356
+ 1 => "Yuki Nishijima",
357
+ 2 => "Matz",
358
+ 3 => "Koichi Sasada",
359
+ }
360
+
361
+ sl_form_for(User.new, url: "/") do |form|
362
+ assert_dom_equal <<~HTML, form.collection_radio_buttons(:name, users, :first, :last)
363
+ <sl-radio-group label="Name">
364
+ <sl-radio name="user[name]" value="1" id="user_name_1">Yuki Nishijima</sl-radio>
365
+ <sl-radio name="user[name]" value="2" id="user_name_2">Matz</sl-radio>
366
+ <sl-radio name="user[name]" value="3" id="user_name_3">Koichi Sasada</sl-radio>
367
+ </sl-radio-group>
368
+ HTML
369
+ end
370
+ end
371
+
372
+ test "#collection_radio_buttons with a default value" do
373
+ users = {
374
+ 1 => "Yuki Nishijima",
375
+ 2 => "Matz",
376
+ 3 => "Koichi Sasada",
377
+ }
378
+
379
+ sl_form_for(User.new(name: 1), url: "/") do |form|
380
+ assert_dom_equal <<~HTML, form.collection_radio_buttons(:name, users, :first, :last)
381
+ <sl-radio-group label="Name">
382
+ <sl-radio name="user[name]" value="1" id="user_name_1" checked="checked">Yuki Nishijima</sl-radio>
383
+ <sl-radio name="user[name]" value="2" id="user_name_2">Matz</sl-radio>
384
+ <sl-radio name="user[name]" value="3" id="user_name_3">Koichi Sasada</sl-radio>
385
+ </sl-radio-group>
386
+ HTML
387
+ end
388
+ end
389
+
390
+ test "#submit" do
391
+ sl_form_for(User.new, url: "/") do |form|
392
+ assert_dom_equal <<~HTML, form.submit("Save")
393
+ <sl-button type="submit" variant="primary" data-disable-with="Save">Save</sl-button>
394
+ HTML
395
+ end
396
+ end
397
+ end
@@ -0,0 +1,18 @@
1
+ # frozen_string_literal: true
2
+
3
+ $LOAD_PATH.unshift File.expand_path("../lib", __dir__)
4
+ require "shoelace/rails"
5
+
6
+ require "minitest/autorun"
7
+ require "action_controller"
8
+ require "action_view"
9
+ require "action_view/testing/resolvers"
10
+ require "active_model"
11
+
12
+ ActionView::TestCase.include(Rails::Dom::Testing::Assertions)
13
+
14
+ class User
15
+ include ActiveModel::Model
16
+
17
+ attr_accessor :name
18
+ end
data/tsconfig.json ADDED
@@ -0,0 +1,19 @@
1
+ {
2
+ "compilerOptions": {
3
+ "declaration": true,
4
+ "outDir": "dist/types",
5
+ "esModuleInterop": true,
6
+ "lib": [ "dom", "dom.iterable", "esnext" ],
7
+ "module": "es2015",
8
+ "moduleResolution": "node",
9
+ "noUnusedLocals": true,
10
+ "rootDir": "src",
11
+ "strict": false,
12
+ "target": "es2017",
13
+ "noEmit": true,
14
+ "removeComments": true,
15
+ "allowSyntheticDefaultImports": true
16
+ },
17
+ "exclude": [ "dist", "src/tests/fixtures" ]
18
+ }
19
+
data/yarn.lock ADDED
@@ -0,0 +1,249 @@
1
+ # THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY.
2
+ # yarn lockfile v1
3
+
4
+
5
+ "@hotwired/turbo@^7.0.1":
6
+ version "7.0.1"
7
+ resolved "https://registry.yarnpkg.com/@hotwired/turbo/-/turbo-7.0.1.tgz#2a8c6ab2f24914d1d47f3a7a7779e2881e8c61a0"
8
+ integrity sha512-awqraytYXbHV2NT0WAOnDDDGJeHHnFtnztdXvRuIqgsStUtPKM8B9H7ISm77SwbHemEjxEOB8Ku4RfNbEEXsPQ==
9
+
10
+ "@lit/reactive-element@^1.0.0":
11
+ version "1.0.0"
12
+ resolved "https://registry.yarnpkg.com/@lit/reactive-element/-/reactive-element-1.0.0.tgz#7b6e6a85709cda0370c47e425ac2f3b553696a4b"
13
+ integrity sha512-Kpgenb8UNFsKCsFhggiVvUkCbcFQSd6N8hffYEEGjz27/4rw3cTSsmP9t3q1EHOAsdum60Wo64HvuZDFpEwexA==
14
+
15
+ "@popperjs/core@^2.7.0":
16
+ version "2.10.2"
17
+ resolved "https://registry.yarnpkg.com/@popperjs/core/-/core-2.10.2.tgz#0798c03351f0dea1a5a4cabddf26a55a7cbee590"
18
+ integrity sha512-IXf3XA7+XyN7CP9gGh/XB0UxVMlvARGEgGXLubFICsUMGz6Q+DU+i4gGlpOxTjKvXjkJDJC8YdqdKkDj9qZHEQ==
19
+
20
+ "@rollup/plugin-node-resolve@^13.0.4":
21
+ version "13.0.4"
22
+ resolved "https://registry.yarnpkg.com/@rollup/plugin-node-resolve/-/plugin-node-resolve-13.0.4.tgz#b10222f4145a019740acb7738402130d848660c0"
23
+ integrity sha512-eYq4TFy40O8hjeDs+sIxEH/jc9lyuI2k9DM557WN6rO5OpnC2qXMBNj4IKH1oHrnAazL49C5p0tgP0/VpqJ+/w==
24
+ dependencies:
25
+ "@rollup/pluginutils" "^3.1.0"
26
+ "@types/resolve" "1.17.1"
27
+ builtin-modules "^3.1.0"
28
+ deepmerge "^4.2.2"
29
+ is-module "^1.0.0"
30
+ resolve "^1.19.0"
31
+
32
+ "@rollup/plugin-typescript@^8.2.5":
33
+ version "8.2.5"
34
+ resolved "https://registry.yarnpkg.com/@rollup/plugin-typescript/-/plugin-typescript-8.2.5.tgz#e0319761b2b5105615e5a0c371ae05bc2984b7de"
35
+ integrity sha512-QL/LvDol/PAGB2O0S7/+q2HpSUNodpw7z6nGn9BfoVCPOZ0r4EALrojFU29Bkoi2Hr2jgTocTejJ5GGWZfOxbQ==
36
+ dependencies:
37
+ "@rollup/pluginutils" "^3.1.0"
38
+ resolve "^1.17.0"
39
+
40
+ "@rollup/pluginutils@^3.1.0":
41
+ version "3.1.0"
42
+ resolved "https://registry.yarnpkg.com/@rollup/pluginutils/-/pluginutils-3.1.0.tgz#706b4524ee6dc8b103b3c995533e5ad680c02b9b"
43
+ integrity sha512-GksZ6pr6TpIjHm8h9lSQ8pi8BE9VeubNT0OMJ3B5uZJ8pz73NPiqOtCog/x2/QzM1ENChPKxMDhiQuRHsqc+lg==
44
+ dependencies:
45
+ "@types/estree" "0.0.39"
46
+ estree-walker "^1.0.1"
47
+ picomatch "^2.2.2"
48
+
49
+ "@shoelace-style/animations@^1.1.0":
50
+ version "1.1.0"
51
+ resolved "https://registry.yarnpkg.com/@shoelace-style/animations/-/animations-1.1.0.tgz#17539abafd6dcbf2a79e089e1593175e9f7835b5"
52
+ integrity sha512-Be+cahtZyI2dPKRm8EZSx3YJQ+jLvEcn3xzRP7tM4tqBnvd/eW/64Xh0iOf0t2w5P8iJKfdBbpVNE9naCaOf2g==
53
+
54
+ "@shoelace-style/shoelace@^2.0.0-beta.52":
55
+ version "2.0.0-beta.52"
56
+ resolved "https://registry.yarnpkg.com/@shoelace-style/shoelace/-/shoelace-2.0.0-beta.52.tgz#a304f9991528946948f90002847e3d7e8f92217f"
57
+ integrity sha512-O4xXJ06EInHYUNQgtoin7bh2kRfGKK36ow+HFYqPluxQFkuCx1gIl26JIIUMiN7WYJLpL7w0KUGSqS6AmsSaQg==
58
+ dependencies:
59
+ "@popperjs/core" "^2.7.0"
60
+ "@shoelace-style/animations" "^1.1.0"
61
+ color "^3.1.3"
62
+ lit "^2.0.0"
63
+ lit-html "^2.0.0"
64
+ qr-creator "^1.0.0"
65
+
66
+ "@types/estree@0.0.39":
67
+ version "0.0.39"
68
+ resolved "https://registry.yarnpkg.com/@types/estree/-/estree-0.0.39.tgz#e177e699ee1b8c22d23174caaa7422644389509f"
69
+ integrity sha512-EYNwp3bU+98cpU4lAWYYL7Zz+2gryWH1qbdDTidVd6hkiR6weksdbMadyXKXNPEkQFhXM+hVO9ZygomHXp+AIw==
70
+
71
+ "@types/node@*":
72
+ version "16.7.1"
73
+ resolved "https://registry.yarnpkg.com/@types/node/-/node-16.7.1.tgz#c6b9198178da504dfca1fd0be9b2e1002f1586f0"
74
+ integrity sha512-ncRdc45SoYJ2H4eWU9ReDfp3vtFqDYhjOsKlFFUDEn8V1Bgr2RjYal8YT5byfadWIRluhPFU6JiDOl0H6Sl87A==
75
+
76
+ "@types/resolve@1.17.1":
77
+ version "1.17.1"
78
+ resolved "https://registry.yarnpkg.com/@types/resolve/-/resolve-1.17.1.tgz#3afd6ad8967c77e4376c598a82ddd58f46ec45d6"
79
+ integrity sha512-yy7HuzQhj0dhGpD8RLXSZWEkLsV9ibvxvi6EiJ3bkqLAO1RGo0WbkWQiwpRlSFymTJRz0d3k5LM3kkx8ArDbLw==
80
+ dependencies:
81
+ "@types/node" "*"
82
+
83
+ "@types/trusted-types@^2.0.2":
84
+ version "2.0.2"
85
+ resolved "https://registry.yarnpkg.com/@types/trusted-types/-/trusted-types-2.0.2.tgz#fc25ad9943bcac11cceb8168db4f275e0e72e756"
86
+ integrity sha512-F5DIZ36YVLE+PN+Zwws4kJogq47hNgX3Nx6WyDJ3kcplxyke3XIzB8uK5n/Lpm1HBsbGzd6nmGehL8cPekP+Tg==
87
+
88
+ builtin-modules@^3.1.0:
89
+ version "3.2.0"
90
+ resolved "https://registry.yarnpkg.com/builtin-modules/-/builtin-modules-3.2.0.tgz#45d5db99e7ee5e6bc4f362e008bf917ab5049887"
91
+ integrity sha512-lGzLKcioL90C7wMczpkY0n/oART3MbBa8R9OFGE1rJxoVI86u4WAGfEk8Wjv10eKSyTHVGkSo3bvBylCEtk7LA==
92
+
93
+ color-convert@^1.9.3:
94
+ version "1.9.3"
95
+ resolved "https://registry.yarnpkg.com/color-convert/-/color-convert-1.9.3.tgz#bb71850690e1f136567de629d2d5471deda4c1e8"
96
+ integrity sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==
97
+ dependencies:
98
+ color-name "1.1.3"
99
+
100
+ color-name@1.1.3:
101
+ version "1.1.3"
102
+ resolved "https://registry.yarnpkg.com/color-name/-/color-name-1.1.3.tgz#a7d0558bd89c42f795dd42328f740831ca53bc25"
103
+ integrity sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=
104
+
105
+ color-name@^1.0.0:
106
+ version "1.1.4"
107
+ resolved "https://registry.yarnpkg.com/color-name/-/color-name-1.1.4.tgz#c2a09a87acbde69543de6f63fa3995c826c536a2"
108
+ integrity sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==
109
+
110
+ color-string@^1.6.0:
111
+ version "1.6.0"
112
+ resolved "https://registry.yarnpkg.com/color-string/-/color-string-1.6.0.tgz#c3915f61fe267672cb7e1e064c9d692219f6c312"
113
+ integrity sha512-c/hGS+kRWJutUBEngKKmk4iH3sD59MBkoxVapS/0wgpCz2u7XsNloxknyvBhzwEs1IbV36D9PwqLPJ2DTu3vMA==
114
+ dependencies:
115
+ color-name "^1.0.0"
116
+ simple-swizzle "^0.2.2"
117
+
118
+ color@^3.1.3:
119
+ version "3.2.1"
120
+ resolved "https://registry.yarnpkg.com/color/-/color-3.2.1.tgz#3544dc198caf4490c3ecc9a790b54fe9ff45e164"
121
+ integrity sha512-aBl7dZI9ENN6fUGC7mWpMTPNHmWUSNan9tuWN6ahh5ZLNk9baLJOnSMlrQkHcrfFgz2/RigjUVAjdx36VcemKA==
122
+ dependencies:
123
+ color-convert "^1.9.3"
124
+ color-string "^1.6.0"
125
+
126
+ deepmerge@^4.2.2:
127
+ version "4.2.2"
128
+ resolved "https://registry.yarnpkg.com/deepmerge/-/deepmerge-4.2.2.tgz#44d2ea3679b8f4d4ffba33f03d865fc1e7bf4955"
129
+ integrity sha512-FJ3UgI4gIl+PHZm53knsuSFpE+nESMr7M4v9QcgB7S63Kj/6WqMiFQJpBBYz1Pt+66bZpP3Q7Lye0Oo9MPKEdg==
130
+
131
+ estree-walker@^1.0.1:
132
+ version "1.0.1"
133
+ resolved "https://registry.yarnpkg.com/estree-walker/-/estree-walker-1.0.1.tgz#31bc5d612c96b704106b477e6dd5d8aa138cb700"
134
+ integrity sha512-1fMXF3YP4pZZVozF8j/ZLfvnR8NSIljt56UhbZ5PeeDmmGHpgpdwQt7ITlGvYaQukCvuBRMLEiKiYC+oeIg4cg==
135
+
136
+ fsevents@~2.3.2:
137
+ version "2.3.2"
138
+ resolved "https://registry.yarnpkg.com/fsevents/-/fsevents-2.3.2.tgz#8a526f78b8fdf4623b709e0b975c52c24c02fd1a"
139
+ integrity sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==
140
+
141
+ function-bind@^1.1.1:
142
+ version "1.1.1"
143
+ resolved "https://registry.yarnpkg.com/function-bind/-/function-bind-1.1.1.tgz#a56899d3ea3c9bab874bb9773b7c5ede92f4895d"
144
+ integrity sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==
145
+
146
+ has@^1.0.3:
147
+ version "1.0.3"
148
+ resolved "https://registry.yarnpkg.com/has/-/has-1.0.3.tgz#722d7cbfc1f6aa8241f16dd814e011e1f41e8796"
149
+ integrity sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==
150
+ dependencies:
151
+ function-bind "^1.1.1"
152
+
153
+ is-arrayish@^0.3.1:
154
+ version "0.3.2"
155
+ resolved "https://registry.yarnpkg.com/is-arrayish/-/is-arrayish-0.3.2.tgz#4574a2ae56f7ab206896fb431eaeed066fdf8f03"
156
+ integrity sha512-eVRqCvVlZbuw3GrM63ovNSNAeA1K16kaR/LRY/92w0zxQ5/1YzwblUX652i4Xs9RwAGjW9d9y6X88t8OaAJfWQ==
157
+
158
+ is-core-module@^2.2.0:
159
+ version "2.6.0"
160
+ resolved "https://registry.yarnpkg.com/is-core-module/-/is-core-module-2.6.0.tgz#d7553b2526fe59b92ba3e40c8df757ec8a709e19"
161
+ integrity sha512-wShG8vs60jKfPWpF2KZRaAtvt3a20OAn7+IJ6hLPECpSABLcKtFKTTI4ZtH5QcBruBHlq+WsdHWyz0BCZW7svQ==
162
+ dependencies:
163
+ has "^1.0.3"
164
+
165
+ is-module@^1.0.0:
166
+ version "1.0.0"
167
+ resolved "https://registry.yarnpkg.com/is-module/-/is-module-1.0.0.tgz#3258fb69f78c14d5b815d664336b4cffb6441591"
168
+ integrity sha1-Mlj7afeMFNW4FdZkM2tM/7ZEFZE=
169
+
170
+ lit-element@^3.0.0:
171
+ version "3.0.0"
172
+ resolved "https://registry.yarnpkg.com/lit-element/-/lit-element-3.0.0.tgz#0e9e64ddbc3dd6a8da4d6fbfadbc070a54cf0597"
173
+ integrity sha512-oPqRhhBBhs+AlI62QLwtWQNU/bNK/h2L1jI3IDroqZubo6XVAkyNy2dW3CRfjij8mrNlY7wULOfyyKKOnfEePA==
174
+ dependencies:
175
+ "@lit/reactive-element" "^1.0.0"
176
+ lit-html "^2.0.0"
177
+
178
+ lit-html@^2.0.0:
179
+ version "2.0.0"
180
+ resolved "https://registry.yarnpkg.com/lit-html/-/lit-html-2.0.0.tgz#ba6779269c382e66d7403a96ed99516ccc3d658b"
181
+ integrity sha512-tJsCapCmc0vtLj6harqd6HfCxnlt/RSkgowtz4SC9dFE3nSL38Tb33I5HMDiyJsRjQZRTgpVsahrnDrR9wg27w==
182
+ dependencies:
183
+ "@types/trusted-types" "^2.0.2"
184
+
185
+ lit@^2.0.0:
186
+ version "2.0.0"
187
+ resolved "https://registry.yarnpkg.com/lit/-/lit-2.0.0.tgz#7710095dc518d9858dde579e9c76b9eed71e98ba"
188
+ integrity sha512-pqi5O/wVzQ9Bn4ERRoYQlt1EAUWyY5Wv888vzpoArbtChc+zfUv1XohRqSdtQZYCogl0eHKd+MQwymg2XJfECg==
189
+ dependencies:
190
+ "@lit/reactive-element" "^1.0.0"
191
+ lit-element "^3.0.0"
192
+ lit-html "^2.0.0"
193
+
194
+ path-parse@^1.0.6:
195
+ version "1.0.7"
196
+ resolved "https://registry.yarnpkg.com/path-parse/-/path-parse-1.0.7.tgz#fbc114b60ca42b30d9daf5858e4bd68bbedb6735"
197
+ integrity sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==
198
+
199
+ picomatch@^2.2.2:
200
+ version "2.3.0"
201
+ resolved "https://registry.yarnpkg.com/picomatch/-/picomatch-2.3.0.tgz#f1f061de8f6a4bf022892e2d128234fb98302972"
202
+ integrity sha512-lY1Q/PiJGC2zOv/z391WOTD+Z02bCgsFfvxoXXf6h7kv9o+WmsmzYqrAwY63sNgOxE4xEdq0WyUnXfKeBrSvYw==
203
+
204
+ prettier@^2.3.2:
205
+ version "2.3.2"
206
+ resolved "https://registry.yarnpkg.com/prettier/-/prettier-2.3.2.tgz#ef280a05ec253712e486233db5c6f23441e7342d"
207
+ integrity sha512-lnJzDfJ66zkMy58OL5/NY5zp70S7Nz6KqcKkXYzn2tMVrNxvbqaBpg7H3qHaLxCJ5lNMsGuM8+ohS7cZrthdLQ==
208
+
209
+ qr-creator@^1.0.0:
210
+ version "1.0.0"
211
+ resolved "https://registry.yarnpkg.com/qr-creator/-/qr-creator-1.0.0.tgz#f350a8f0b5be02bd1fc1ef133a038a06ef8bc5ef"
212
+ integrity sha512-C0cqfbS1P5hfqN4NhsYsUXePlk9BO+a45bAQ3xLYjBL3bOIFzoVEjs79Fado9u9BPBD3buHi3+vY+C8tHh4qMQ==
213
+
214
+ resolve@^1.17.0, resolve@^1.19.0:
215
+ version "1.20.0"
216
+ resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.20.0.tgz#629a013fb3f70755d6f0b7935cc1c2c5378b1975"
217
+ integrity sha512-wENBPt4ySzg4ybFQW2TT1zMQucPK95HSh/nq2CFTZVOGut2+pQvSsgtda4d26YrYcr067wjbmzOG8byDPBX63A==
218
+ dependencies:
219
+ is-core-module "^2.2.0"
220
+ path-parse "^1.0.6"
221
+
222
+ rollup@^2.56.2:
223
+ version "2.56.2"
224
+ resolved "https://registry.yarnpkg.com/rollup/-/rollup-2.56.2.tgz#a045ff3f6af53ee009b5f5016ca3da0329e5470f"
225
+ integrity sha512-s8H00ZsRi29M2/lGdm1u8DJpJ9ML8SUOpVVBd33XNeEeL3NVaTiUcSBHzBdF3eAyR0l7VSpsuoVUGrRHq7aPwQ==
226
+ optionalDependencies:
227
+ fsevents "~2.3.2"
228
+
229
+ simple-swizzle@^0.2.2:
230
+ version "0.2.2"
231
+ resolved "https://registry.yarnpkg.com/simple-swizzle/-/simple-swizzle-0.2.2.tgz#a4da6b635ffcccca33f70d17cb92592de95e557a"
232
+ integrity sha1-pNprY1/8zMoz9w0Xy5JZLeleVXo=
233
+ dependencies:
234
+ is-arrayish "^0.3.1"
235
+
236
+ tslib@^2.3.1:
237
+ version "2.3.1"
238
+ resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.3.1.tgz#e8a335add5ceae51aa261d32a490158ef042ef01"
239
+ integrity sha512-77EbyPPpMz+FRFRuAFlWMtmgUWGe9UOG2Z25NqCwiIjRhOf5iKGuzSe5P2w1laq+FkRy4p+PCuVkJSGkzTEKVw==
240
+
241
+ turbolinks@5.x:
242
+ version "5.2.0"
243
+ resolved "https://registry.yarnpkg.com/turbolinks/-/turbolinks-5.2.0.tgz#e6877a55ea5c1cb3bb225f0a4ae303d6d32ff77c"
244
+ integrity sha512-pMiez3tyBo6uRHFNNZoYMmrES/IaGgMhQQM+VFF36keryjb5ms0XkVpmKHkfW/4Vy96qiGW3K9bz0tF5sK9bBw==
245
+
246
+ typescript@^4.3.5:
247
+ version "4.3.5"
248
+ resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.3.5.tgz#4d1c37cc16e893973c45a06886b7113234f119f4"
249
+ integrity sha512-DqQgihaQ9cUrskJo9kIyW/+g0Vxsk8cDtZ52a3NGh0YNTfpUSArXSohyUGnvbPazEPLu398C0UxmKSOrPumUzA==