rails-jsdom 0.1.0
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 +7 -0
- data/CHANGELOG.md +13 -0
- data/LICENSE +21 -0
- data/README.md +351 -0
- data/lib/generators/rails_jsdom/install/install_generator.rb +108 -0
- data/lib/rails_jsdom/bridge.rb +80 -0
- data/lib/rails_jsdom/element.rb +186 -0
- data/lib/rails_jsdom/page.rb +33 -0
- data/lib/rails_jsdom/query.rb +76 -0
- data/lib/rails_jsdom/runner.js +3 -0
- data/lib/rails_jsdom/runtime.js +926 -0
- data/lib/rails_jsdom/test_case.rb +29 -0
- data/lib/rails_jsdom/test_helper.rb +767 -0
- data/lib/rails_jsdom/turbo_stream_deliveries.rb +25 -0
- data/lib/rails_jsdom/version.rb +4 -0
- data/lib/rails_jsdom.rb +83 -0
- metadata +158 -0
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
module RailsJsdom
|
|
2
|
+
class TurboStreamDeliveries # :nodoc:
|
|
3
|
+
def initialize
|
|
4
|
+
@delivered = {}
|
|
5
|
+
end
|
|
6
|
+
|
|
7
|
+
def undelivered_messages(session, streams)
|
|
8
|
+
previously_delivered = @delivered.fetch(session, {})
|
|
9
|
+
@delivered[session] = streams.to_h { |stream| [ stream, broadcasts(stream).size ] }
|
|
10
|
+
streams.flat_map { |stream| new_messages(stream, previously_delivered) }
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
private
|
|
14
|
+
|
|
15
|
+
def new_messages(stream, previously_delivered)
|
|
16
|
+
sent = broadcasts(stream)
|
|
17
|
+
unseen = sent.drop(previously_delivered.fetch(stream, sent.size))
|
|
18
|
+
unseen.map { |payload| ActiveSupport::JSON.decode(payload) }.grep(String)
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
def broadcasts(stream)
|
|
22
|
+
ActionCable.server.pubsub.broadcasts(stream)
|
|
23
|
+
end
|
|
24
|
+
end
|
|
25
|
+
end
|
data/lib/rails_jsdom.rb
ADDED
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
require "json"
|
|
2
|
+
require "open3"
|
|
3
|
+
require_relative "rails_jsdom/version"
|
|
4
|
+
|
|
5
|
+
# Browserless interaction tests for Rails apps built with Stimulus, Turbo and
|
|
6
|
+
# importmap.
|
|
7
|
+
#
|
|
8
|
+
# Write tests with RailsJsdom::TestCase. Its helpers are documented in
|
|
9
|
+
# RailsJsdom::TestHelper.
|
|
10
|
+
module RailsJsdom
|
|
11
|
+
# Raised when an action fails in the page: an element is not found or
|
|
12
|
+
# matches more than once, a JavaScript error or unexpected dialog occurs, or
|
|
13
|
+
# the Node process exits.
|
|
14
|
+
class Error < StandardError; end
|
|
15
|
+
|
|
16
|
+
# :stopdoc:
|
|
17
|
+
|
|
18
|
+
RUNNER = File.expand_path("rails_jsdom/runner.js", __dir__)
|
|
19
|
+
REMOTE = %r{\A[a-z][a-z0-9+.-]*://}i
|
|
20
|
+
HIDDEN_SELECTOR = "[hidden], template, script, style, noscript, dialog:not([open]), [style*='display: none'], [style*='display:none']".freeze
|
|
21
|
+
TIMER_HORIZON = 1000
|
|
22
|
+
|
|
23
|
+
class << self
|
|
24
|
+
def bridge
|
|
25
|
+
bridges[Process.pid] ||= Bridge.new(command: [ "node", RUNNER ], setup: setup, logger: Rails.logger)
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
def setup
|
|
29
|
+
{
|
|
30
|
+
command: "setup",
|
|
31
|
+
root: Rails.root.to_s,
|
|
32
|
+
controllers: Rails.root.join("app/javascript/controllers").to_s,
|
|
33
|
+
modules: modules,
|
|
34
|
+
stubs: remote_modules,
|
|
35
|
+
directories: directories,
|
|
36
|
+
horizon: TIMER_HORIZON,
|
|
37
|
+
hidden: HIDDEN_SELECTOR
|
|
38
|
+
}
|
|
39
|
+
end
|
|
40
|
+
|
|
41
|
+
def modules
|
|
42
|
+
packages.reject { |_name, path| path.match?(REMOTE) }.transform_values { |path| Rails.application.assets.load_path.find(path)&.path&.to_s }
|
|
43
|
+
end
|
|
44
|
+
|
|
45
|
+
def remote_modules
|
|
46
|
+
packages.select { |_name, path| path.match?(REMOTE) }.keys
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
def directories
|
|
50
|
+
Rails.application.importmap.directories.values.to_h { |directory| [ directory.under, Rails.root.join(directory.dir).to_s ] }
|
|
51
|
+
end
|
|
52
|
+
|
|
53
|
+
def keys(keys)
|
|
54
|
+
keys.map { |key| key.is_a?(Array) ? key_entry(key.last).merge(modifiers: key[0...-1].map(&:to_s)) : key_entry(key) }
|
|
55
|
+
end
|
|
56
|
+
|
|
57
|
+
def document(html)
|
|
58
|
+
"<!DOCTYPE html><html><head></head><body>#{html}</body></html>"
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
private
|
|
62
|
+
|
|
63
|
+
def key_entry(key)
|
|
64
|
+
key.is_a?(Symbol) ? { key: key.to_s } : { text: key.to_s }
|
|
65
|
+
end
|
|
66
|
+
|
|
67
|
+
def packages
|
|
68
|
+
Rails.application.importmap.packages.transform_values(&:path)
|
|
69
|
+
end
|
|
70
|
+
|
|
71
|
+
def bridges
|
|
72
|
+
@bridges ||= {}
|
|
73
|
+
end
|
|
74
|
+
end
|
|
75
|
+
end
|
|
76
|
+
|
|
77
|
+
require_relative "rails_jsdom/bridge"
|
|
78
|
+
require_relative "rails_jsdom/query"
|
|
79
|
+
require_relative "rails_jsdom/turbo_stream_deliveries"
|
|
80
|
+
require_relative "rails_jsdom/element"
|
|
81
|
+
require_relative "rails_jsdom/test_helper"
|
|
82
|
+
require_relative "rails_jsdom/page"
|
|
83
|
+
require_relative "rails_jsdom/test_case"
|
metadata
ADDED
|
@@ -0,0 +1,158 @@
|
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
|
2
|
+
name: rails-jsdom
|
|
3
|
+
version: !ruby/object:Gem::Version
|
|
4
|
+
version: 0.1.0
|
|
5
|
+
platform: ruby
|
|
6
|
+
authors:
|
|
7
|
+
- Jake Howerton
|
|
8
|
+
bindir: bin
|
|
9
|
+
cert_chain: []
|
|
10
|
+
date: 1980-01-02 00:00:00.000000000 Z
|
|
11
|
+
dependencies:
|
|
12
|
+
- !ruby/object:Gem::Dependency
|
|
13
|
+
name: actioncable
|
|
14
|
+
requirement: !ruby/object:Gem::Requirement
|
|
15
|
+
requirements:
|
|
16
|
+
- - ">="
|
|
17
|
+
- !ruby/object:Gem::Version
|
|
18
|
+
version: '7.1'
|
|
19
|
+
type: :runtime
|
|
20
|
+
prerelease: false
|
|
21
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
22
|
+
requirements:
|
|
23
|
+
- - ">="
|
|
24
|
+
- !ruby/object:Gem::Version
|
|
25
|
+
version: '7.1'
|
|
26
|
+
- !ruby/object:Gem::Dependency
|
|
27
|
+
name: actionpack
|
|
28
|
+
requirement: !ruby/object:Gem::Requirement
|
|
29
|
+
requirements:
|
|
30
|
+
- - ">="
|
|
31
|
+
- !ruby/object:Gem::Version
|
|
32
|
+
version: '7.1'
|
|
33
|
+
type: :runtime
|
|
34
|
+
prerelease: false
|
|
35
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
36
|
+
requirements:
|
|
37
|
+
- - ">="
|
|
38
|
+
- !ruby/object:Gem::Version
|
|
39
|
+
version: '7.1'
|
|
40
|
+
- !ruby/object:Gem::Dependency
|
|
41
|
+
name: importmap-rails
|
|
42
|
+
requirement: !ruby/object:Gem::Requirement
|
|
43
|
+
requirements:
|
|
44
|
+
- - ">="
|
|
45
|
+
- !ruby/object:Gem::Version
|
|
46
|
+
version: '2.0'
|
|
47
|
+
type: :runtime
|
|
48
|
+
prerelease: false
|
|
49
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
50
|
+
requirements:
|
|
51
|
+
- - ">="
|
|
52
|
+
- !ruby/object:Gem::Version
|
|
53
|
+
version: '2.0'
|
|
54
|
+
- !ruby/object:Gem::Dependency
|
|
55
|
+
name: nokogiri
|
|
56
|
+
requirement: !ruby/object:Gem::Requirement
|
|
57
|
+
requirements:
|
|
58
|
+
- - ">="
|
|
59
|
+
- !ruby/object:Gem::Version
|
|
60
|
+
version: '1.15'
|
|
61
|
+
type: :runtime
|
|
62
|
+
prerelease: false
|
|
63
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
64
|
+
requirements:
|
|
65
|
+
- - ">="
|
|
66
|
+
- !ruby/object:Gem::Version
|
|
67
|
+
version: '1.15'
|
|
68
|
+
- !ruby/object:Gem::Dependency
|
|
69
|
+
name: propshaft
|
|
70
|
+
requirement: !ruby/object:Gem::Requirement
|
|
71
|
+
requirements:
|
|
72
|
+
- - ">="
|
|
73
|
+
- !ruby/object:Gem::Version
|
|
74
|
+
version: '1.0'
|
|
75
|
+
type: :runtime
|
|
76
|
+
prerelease: false
|
|
77
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
78
|
+
requirements:
|
|
79
|
+
- - ">="
|
|
80
|
+
- !ruby/object:Gem::Version
|
|
81
|
+
version: '1.0'
|
|
82
|
+
- !ruby/object:Gem::Dependency
|
|
83
|
+
name: turbo-rails
|
|
84
|
+
requirement: !ruby/object:Gem::Requirement
|
|
85
|
+
requirements:
|
|
86
|
+
- - ">="
|
|
87
|
+
- !ruby/object:Gem::Version
|
|
88
|
+
version: '2.0'
|
|
89
|
+
type: :runtime
|
|
90
|
+
prerelease: false
|
|
91
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
92
|
+
requirements:
|
|
93
|
+
- - ">="
|
|
94
|
+
- !ruby/object:Gem::Version
|
|
95
|
+
version: '2.0'
|
|
96
|
+
description: rails-jsdom runs your real Rails pages, Stimulus controllers and Turbo
|
|
97
|
+
in a persistent Node + jsdom process, routing page fetches back into Rails in-process.
|
|
98
|
+
Interaction tests read like system tests without Capybara, a server or a browser.
|
|
99
|
+
email:
|
|
100
|
+
- jake.howerton@gmail.com
|
|
101
|
+
executables: []
|
|
102
|
+
extensions: []
|
|
103
|
+
extra_rdoc_files:
|
|
104
|
+
- CHANGELOG.md
|
|
105
|
+
- LICENSE
|
|
106
|
+
- README.md
|
|
107
|
+
files:
|
|
108
|
+
- CHANGELOG.md
|
|
109
|
+
- LICENSE
|
|
110
|
+
- README.md
|
|
111
|
+
- lib/generators/rails_jsdom/install/install_generator.rb
|
|
112
|
+
- lib/rails_jsdom.rb
|
|
113
|
+
- lib/rails_jsdom/bridge.rb
|
|
114
|
+
- lib/rails_jsdom/element.rb
|
|
115
|
+
- lib/rails_jsdom/page.rb
|
|
116
|
+
- lib/rails_jsdom/query.rb
|
|
117
|
+
- lib/rails_jsdom/runner.js
|
|
118
|
+
- lib/rails_jsdom/runtime.js
|
|
119
|
+
- lib/rails_jsdom/test_case.rb
|
|
120
|
+
- lib/rails_jsdom/test_helper.rb
|
|
121
|
+
- lib/rails_jsdom/turbo_stream_deliveries.rb
|
|
122
|
+
- lib/rails_jsdom/version.rb
|
|
123
|
+
homepage: https://github.com/jakehow/rails-jsdom
|
|
124
|
+
licenses:
|
|
125
|
+
- MIT
|
|
126
|
+
metadata:
|
|
127
|
+
homepage_uri: https://github.com/jakehow/rails-jsdom
|
|
128
|
+
source_code_uri: https://github.com/jakehow/rails-jsdom
|
|
129
|
+
documentation_uri: https://jakehow.github.io/rails-jsdom/
|
|
130
|
+
changelog_uri: https://github.com/jakehow/rails-jsdom/blob/main/CHANGELOG.md
|
|
131
|
+
bug_tracker_uri: https://github.com/jakehow/rails-jsdom/issues
|
|
132
|
+
rubygems_mfa_required: 'true'
|
|
133
|
+
post_install_message: 'rails-jsdom: set up interaction tests in your app with `bin/rails
|
|
134
|
+
generate rails_jsdom:install`.'
|
|
135
|
+
rdoc_options:
|
|
136
|
+
- "--main"
|
|
137
|
+
- README.md
|
|
138
|
+
- "--markup"
|
|
139
|
+
- markdown
|
|
140
|
+
- "--title"
|
|
141
|
+
- rails-jsdom
|
|
142
|
+
require_paths:
|
|
143
|
+
- lib
|
|
144
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
|
145
|
+
requirements:
|
|
146
|
+
- - ">="
|
|
147
|
+
- !ruby/object:Gem::Version
|
|
148
|
+
version: '3.3'
|
|
149
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
|
150
|
+
requirements:
|
|
151
|
+
- - ">="
|
|
152
|
+
- !ruby/object:Gem::Version
|
|
153
|
+
version: '0'
|
|
154
|
+
requirements: []
|
|
155
|
+
rubygems_version: 4.0.20
|
|
156
|
+
specification_version: 4
|
|
157
|
+
summary: Browserless Stimulus and Turbo interaction tests for Rails, on jsdom.
|
|
158
|
+
test_files: []
|