")
+ expect(find('div.foo')).to have_content('lorem-bar')
end
end
end
@@ -581,7 +581,14 @@ class Foo
end
end
end
- expect(page.body).to include('
')
+ expect(
+ JSON.parse(
+ find(
+ 'div[data-react-class="Hyperstack.Internal.Component.TopLevelRailsComponent"]',
+ visible: false
+ )['data-react-props']
+ ).with_indifferent_access
+ ).to include render_params: {}, component_name: 'Foo', controller: 'HyperSpecTest'
end
end
diff --git a/ruby/hyper-component/spec/client_features/dsl_spec.rb b/ruby/hyper-component/spec/client_features/dsl_spec.rb
index 5903205aa..590a38d34 100644
--- a/ruby/hyper-component/spec/client_features/dsl_spec.rb
+++ b/ruby/hyper-component/spec/client_features/dsl_spec.rb
@@ -101,11 +101,15 @@ class Foo
class Foo
include Hyperstack::Component
render do
- DIV { "hello".br }
+ DIV(class: :foo) { "hello".br }
end
end
end
- expect(page.body[-285..-233]).to match(/(
hello<(br|br\/|br \/)><\/span><\/div>/)
+ expect(
+ find(
+ 'div[data-react-class="Hyperstack.Internal.Component.TopLevelRailsComponent"] div.foo span'
+ )['innerHTML']
+ ).to eq 'hello '
end
it "has a .td short hand String method" do
diff --git a/ruby/hyper-component/spec/client_features/param_declaration_spec.rb b/ruby/hyper-component/spec/client_features/param_declaration_spec.rb
index 2df289b69..40befc90b 100644
--- a/ruby/hyper-component/spec/client_features/param_declaration_spec.rb
+++ b/ruby/hyper-component/spec/client_features/param_declaration_spec.rb
@@ -7,11 +7,11 @@ class Foo < Hyperloop::Component
collect_other_params_as :foo
render do
- DIV { @Foo[:bar] }
+ DIV(class: :foo) { @Foo[:bar] }
end
end
end
- expect(page.body[-35..-19]).to include("
biz
")
+ expect(find('div.foo')).to have_content 'biz'
end
it 'can override PropsWrapper.instance_var_name' do
@@ -28,11 +28,11 @@ class Foo < Hyperloop::Component
collect_other_params_as :foo
render do
- DIV { @foo[:bar] }
+ DIV(class: :foo) { @foo[:bar] }
end
end
end
- expect(page.body[-35..-19]).to include("
biz
")
+ expect(find('div.foo')).to have_content 'biz'
end
it 'defines collect_other_params_as method on params proxy' do
@@ -66,11 +66,11 @@ class Foo < Hyperloop::Component
param :foo
render do
- DIV { @Foo }
+ DIV(class: :foo) { @Foo }
end
end
end
- expect(page.body[-35..-19]).to include("
bar
")
+ expect(find('div.foo')).to have_content 'bar'
end
it "can give a param an accessor alias" do
@@ -79,11 +79,11 @@ class Foo < Hyperloop::Component
param :foo, alias: :bar
render do
- DIV { @bar }
+ DIV(class: :foo) { @bar }
end
end
end
- expect(page.body[-35..-19]).to include("
bar
")
+ expect(find('div.foo')).to have_content 'bar'
end
it "can create and access an optional params" do
diff --git a/ruby/hyper-component/spec/deprecated_features/param_declaration_legacy_spec.rb b/ruby/hyper-component/spec/deprecated_features/param_declaration_legacy_spec.rb
index b80ca8392..a7156e80b 100644
--- a/ruby/hyper-component/spec/deprecated_features/param_declaration_legacy_spec.rb
+++ b/ruby/hyper-component/spec/deprecated_features/param_declaration_legacy_spec.rb
@@ -102,7 +102,7 @@ class Foo
end
end
end
-
+
it 'defines collect_other_params_as method on params proxy' do
mount 'Foo', bar: 'biz' do
class Foo < Hyperloop::Component
@@ -110,11 +110,11 @@ class Foo < Hyperloop::Component
collect_other_params_as :foo
render do
- DIV { params.foo[:bar] }
+ DIV(class: :foo) { params.foo[:bar] }
end
end
end
- expect(page.body[-35..-19]).to include("
biz
")
+ expect(find('div.foo')).to have_content 'biz'
end
it 'defines collect_other_params_as method on params proxy' do
@@ -151,11 +151,11 @@ class Foo < Hyperloop::Component
param :foo
render do
- DIV { params.foo }
+ DIV(class: :foo) { params.foo }
end
end
end
- expect(page.body[-35..-19]).to include("
bar
")
+ expect(find('div.foo')).to have_content 'bar'
end
it "can create and access an optional params" do
diff --git a/ruby/hyper-component/spec/spec_helper.rb b/ruby/hyper-component/spec/spec_helper.rb
index 8ba43b259..c90ce845a 100644
--- a/ruby/hyper-component/spec/spec_helper.rb
+++ b/ruby/hyper-component/spec/spec_helper.rb
@@ -52,6 +52,8 @@ class JavaScriptError < StandardError; end
raise JavaScriptError, errors.join("\n\n") if errors.present?
end
end
+
+ HyperSpec::ComponentTestHelpers.alias_method :on_client, :before_mount
end
# Stubbing the React calls so we can test outside of Opal
diff --git a/ruby/hyper-i18n/spec/spec_helper.rb b/ruby/hyper-i18n/spec/spec_helper.rb
index 9b512f7fa..9927231b8 100644
--- a/ruby/hyper-i18n/spec/spec_helper.rb
+++ b/ruby/hyper-i18n/spec/spec_helper.rb
@@ -14,4 +14,7 @@
config.before(:all) do
`rm -rf spec/test_app/tmp/cache/`
end
+
+ # Use legacy hyper-spec on_client behavior
+ HyperSpec::ComponentTestHelpers.alias_method :on_client, :before_mount
end
diff --git a/ruby/hyper-model/spec/spec_helper.rb b/ruby/hyper-model/spec/spec_helper.rb
index 11fd2acd5..378895490 100644
--- a/ruby/hyper-model/spec/spec_helper.rb
+++ b/ruby/hyper-model/spec/spec_helper.rb
@@ -25,7 +25,7 @@ def self.log_import(s)
end
end
end
-
+
config.color = true
config.fail_fast = ENV['FAIL_FAST'] || false
config.fixture_path = File.join(File.expand_path(File.dirname(__FILE__)), "fixtures")
@@ -318,6 +318,8 @@ class JavaScriptError < StandardError; end
# Capybara::Selenium::Driver.new(app, :browser => :chrome, :desired_capabilities => caps)
# end
+ # Use legacy hyper-spec on_client behavior
+ HyperSpec::ComponentTestHelpers.alias_method :on_client, :before_mount
end
FactoryBot.define do
diff --git a/ruby/hyper-operation/spec/spec_helper.rb b/ruby/hyper-operation/spec/spec_helper.rb
index 3fe0c454c..e2260d48d 100644
--- a/ruby/hyper-operation/spec/spec_helper.rb
+++ b/ruby/hyper-operation/spec/spec_helper.rb
@@ -131,6 +131,9 @@ def self.on_server?
# #.reject { |e| e =~ /Unexpected response code: 200/ }
# raise JavaScriptError, errors.join("\n\n") if errors.present?
# end
+
+ # Use legacy hyper-spec on_client behavior
+ HyperSpec::ComponentTestHelpers.alias_method :on_client, :before_mount
end
module HyperSpec
diff --git a/ruby/hyper-store/spec/hyper-store/reset_context_spec.rb b/ruby/hyper-store/spec/hyper-store/reset_context_spec.rb
index 76cd93b84..8161d2dd0 100644
--- a/ruby/hyper-store/spec/hyper-store/reset_context_spec.rb
+++ b/ruby/hyper-store/spec/hyper-store/reset_context_spec.rb
@@ -3,7 +3,7 @@
describe "resetting contexts" do
it "does not reset any predefined boot receivers", js: true do
- on_client do
+ before_mount do
class Store
include Hyperstack::Legacy::Store
class << self
diff --git a/upgrade-from-opal-0.11-rails-5.md b/upgrade-from-opal-0.11-rails-5.md
index c0e008124..5a7e86400 100644
--- a/upgrade-from-opal-0.11-rails-5.md
+++ b/upgrade-from-opal-0.11-rails-5.md
@@ -259,3 +259,26 @@ ActiveRecord::Base. But in order for it to work the "page" was being passed so
a page.evaluate_ruby, but the whole method was backwards. It should be a capybara helper method that takes a active record model. This is fixed.
---
+
+### Hyperspec changes behavior of on_client
+
+New hyperspec aliases evaluate_ruby as on_client for readability, the old on_client is now called before_mount.
+
+You can either update calls to on_client to be before_mount, or
+
+You can get legacy behavior by executing this line in the spec_helper:
+```ruby
+HyperSpec::ComponentTestHelpers.alias_method :on_client, :before_mount
+```
+
+---
+
+### HyperSpec todos
+
+TODO: Hyperspec is dependent on HyperComponent for mounting components, and initializing the system.
+
+However we want to make sure you can use HyperSpec without HyperComponent
+
+TODO: Investigate why we need before_mount...
+
+---
From 504a2b52920dd32983b7719e6c38daec81490df2 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 16 Jan 2021 10:56:12 -0500
Subject: [PATCH 053/307] removed add_locals method
---
.../spec/batch1/column_types/column_type_spec.rb | 2 +-
ruby/hyper-model/spec/spec_helper.rb | 12 ++++++++++--
ruby/hyper-operation/spec/spec_helper.rb | 13 +++++++++++--
upgrade-from-opal-0.11-rails-5.md | 4 +++-
4 files changed, 25 insertions(+), 6 deletions(-)
diff --git a/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb b/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb
index b98181124..cb7e344a5 100644
--- a/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb
+++ b/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb
@@ -184,7 +184,7 @@ class DefaultTest < ActiveRecord::Base
it 'loads and converts the value' do # randomly generates an error, but the exactual spec passed... perhaps move it up or down? (tried moving down one step)
t = Timex.parse('1/2/2003')
- r = TypeTest.create(
+ TypeTest.create(
boolean: true,
date: t.time,
datetime: t.time,
diff --git a/ruby/hyper-model/spec/spec_helper.rb b/ruby/hyper-model/spec/spec_helper.rb
index 378895490..3ea6ca7d0 100644
--- a/ruby/hyper-model/spec/spec_helper.rb
+++ b/ruby/hyper-model/spec/spec_helper.rb
@@ -317,9 +317,17 @@ class JavaScriptError < StandardError; end
# caps = Selenium::WebDriver::Remote::Capabilities.chrome("chromeOptions" => {"args" => [ "--window-size=200,200" ]})
# Capybara::Selenium::Driver.new(app, :browser => :chrome, :desired_capabilities => caps)
# end
+end
- # Use legacy hyper-spec on_client behavior
- HyperSpec::ComponentTestHelpers.alias_method :on_client, :before_mount
+module HyperSpec
+ module ComponentTestHelpers
+ # Use legacy hyper-spec on_client behavior
+ # turn off add_locals
+ alias_method :on_client, :before_mount
+ def add_locals(in_str, block)
+ in_str
+ end
+ end
end
FactoryBot.define do
diff --git a/ruby/hyper-operation/spec/spec_helper.rb b/ruby/hyper-operation/spec/spec_helper.rb
index e2260d48d..6b49cae30 100644
--- a/ruby/hyper-operation/spec/spec_helper.rb
+++ b/ruby/hyper-operation/spec/spec_helper.rb
@@ -131,11 +131,20 @@ def self.on_server?
# #.reject { |e| e =~ /Unexpected response code: 200/ }
# raise JavaScriptError, errors.join("\n\n") if errors.present?
# end
+end
- # Use legacy hyper-spec on_client behavior
- HyperSpec::ComponentTestHelpers.alias_method :on_client, :before_mount
+module HyperSpec
+ module ComponentTestHelpers
+ # Use legacy hyper-spec on_client behavior
+ # turn off add_locals
+ alias_method :on_client, :before_mount
+ def add_locals(in_str, block)
+ in_str
+ end
+ end
end
+
module HyperSpec
module ComponentTestHelpers
alias old_expect_promise expect_promise
diff --git a/upgrade-from-opal-0.11-rails-5.md b/upgrade-from-opal-0.11-rails-5.md
index 5a7e86400..5258f2338 100644
--- a/upgrade-from-opal-0.11-rails-5.md
+++ b/upgrade-from-opal-0.11-rails-5.md
@@ -270,7 +270,6 @@ You can get legacy behavior by executing this line in the spec_helper:
```ruby
HyperSpec::ComponentTestHelpers.alias_method :on_client, :before_mount
```
-
---
### HyperSpec todos
@@ -281,4 +280,7 @@ However we want to make sure you can use HyperSpec without HyperComponent
TODO: Investigate why we need before_mount...
+TODO: add_locals method only works on simple cases. For now make it experimental (i.e. make the method called
+ experimental_add_locals, which you can alias, or include a module that switches on the behavior.)
+
---
From a1ea8be623fca6217e03dd18744d4c3c5ff9730e Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 16 Jan 2021 16:46:23 -0500
Subject: [PATCH 054/307] few more fixes to the new hyper-spec
---
ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb | 5 +++--
1 file changed, 3 insertions(+), 2 deletions(-)
diff --git a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
index 0ec700a6e..26a985c17 100644
--- a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
@@ -271,7 +271,8 @@ def evaluate_ruby(p1 = nil, p2 = nil, p3 = nil, &block)
str = "#{name} = #{value.to_opal_expression}\n#{str}"
end
str = add_opal_block(str, block) if block
- js = opal_compile(str).delete("\n").gsub('(Opal);', '(Opal)')
+ js = opal_compile(str).gsub("// Prepare super implicit arguments\n", '')
+ .delete("\n").gsub('(Opal);', '(Opal)')
# workaround for firefox 58 and geckodriver 0.19.1, because firefox is unable to find .$to_json:
# JSON.parse(evaluate_script("(function(){var a=Opal.Array.$new(); a[0]=#{js}; return a.$to_json();})();"), opts).first
JSON.parse(evaluate_script("[#{js}].$to_json()"), opts).first
@@ -533,7 +534,7 @@ def add_class(class_name, style)
end
def attributes_on_client(model)
- evaluate_ruby("#{model.class.name}.find(#{model.id}).attributes", symbolize_names: true)
+ evaluate_ruby("#{model.class.name}.find(#{model.id}).attributes").symbolize_keys
end
From de69d8f0201aad36aa541f470ba1fc5b4917d8d1 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 16 Jan 2021 21:19:03 -0500
Subject: [PATCH 055/307] rewrote hyper-spec add_locals method
---
ruby/hyper-model/lib/hyper-model.rb | 1 +
ruby/hyper-model/spec/spec_helper.rb | 12 +--
ruby/hyper-operation/spec/spec_helper.rb | 13 +--
.../lib/hyper-spec/component_test_helpers.rb | 90 ++++++++++++-------
.../lib/sources/top_level_rails_component.rb | 7 ++
.../spec/test_app/app/views/components.rb | 1 +
6 files changed, 73 insertions(+), 51 deletions(-)
diff --git a/ruby/hyper-model/lib/hyper-model.rb b/ruby/hyper-model/lib/hyper-model.rb
index 93b5e51d0..767ec320c 100644
--- a/ruby/hyper-model/lib/hyper-model.rb
+++ b/ruby/hyper-model/lib/hyper-model.rb
@@ -59,6 +59,7 @@
require "reactive_record/active_record/public_columns_hash"
require "reactive_record/serializers"
require "reactive_record/pry"
+ require "hyper_spec/component_test_helpers"
require_relative 'active_record_base'
require 'hyper_model/version'
diff --git a/ruby/hyper-model/spec/spec_helper.rb b/ruby/hyper-model/spec/spec_helper.rb
index 3ea6ca7d0..378895490 100644
--- a/ruby/hyper-model/spec/spec_helper.rb
+++ b/ruby/hyper-model/spec/spec_helper.rb
@@ -317,17 +317,9 @@ class JavaScriptError < StandardError; end
# caps = Selenium::WebDriver::Remote::Capabilities.chrome("chromeOptions" => {"args" => [ "--window-size=200,200" ]})
# Capybara::Selenium::Driver.new(app, :browser => :chrome, :desired_capabilities => caps)
# end
-end
-module HyperSpec
- module ComponentTestHelpers
- # Use legacy hyper-spec on_client behavior
- # turn off add_locals
- alias_method :on_client, :before_mount
- def add_locals(in_str, block)
- in_str
- end
- end
+ # Use legacy hyper-spec on_client behavior
+ HyperSpec::ComponentTestHelpers.alias_method :on_client, :before_mount
end
FactoryBot.define do
diff --git a/ruby/hyper-operation/spec/spec_helper.rb b/ruby/hyper-operation/spec/spec_helper.rb
index 6b49cae30..e2260d48d 100644
--- a/ruby/hyper-operation/spec/spec_helper.rb
+++ b/ruby/hyper-operation/spec/spec_helper.rb
@@ -131,20 +131,11 @@ def self.on_server?
# #.reject { |e| e =~ /Unexpected response code: 200/ }
# raise JavaScriptError, errors.join("\n\n") if errors.present?
# end
-end
-module HyperSpec
- module ComponentTestHelpers
- # Use legacy hyper-spec on_client behavior
- # turn off add_locals
- alias_method :on_client, :before_mount
- def add_locals(in_str, block)
- in_str
- end
- end
+ # Use legacy hyper-spec on_client behavior
+ HyperSpec::ComponentTestHelpers.alias_method :on_client, :before_mount
end
-
module HyperSpec
module ComponentTestHelpers
alias old_expect_promise expect_promise
diff --git a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
index 26a985c17..83e7cb563 100644
--- a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
@@ -33,24 +33,48 @@ def lines_for(file_name, name = nil)
end
class Object
- def to_opal_expression
- to_json
- rescue Exception
- to_s
+ def opal_serialize
+ nil
end
end
-class Time
- def to_opal_expression
- "Time.parse('#{inspect}')"
+class Hash
+ def opal_serialize
+ "{#{collect { |k, v| "#{k.opal_serialize} => #{v.opal_serialize}"}.join(', ')}}"
+ end
+end
+
+class Array
+ def opal_serialize
+ "[#{collect { |v| v.opal_serialize }.join(', ')}]"
end
end
-class NilClass
+[FalseClass, Float, Integer, NilClass, String, Symbol, TrueClass].each do |klass|
+ klass.send(:define_method, :opal_serialize) do
+ inspect
+ end
+end
+
+if Gem::Version.new(RUBY_VERSION) < Gem::Version.new('2.4.0')
+ [Bignum, Fixnum].each do |klass|
+ klass.send(:define_method, :opal_serialize) do
+ inspect
+ end
+ end
+end
+
+class Time
def to_opal_expression
- self.inspect
+ "Time.parse('#{inspect}')"
end
end
+#
+# class NilClass
+# def to_opal_expression
+# self.inspect
+# end
+# end
module HyperSpec
@@ -246,6 +270,11 @@ def isomorphic(&block)
before_mount(&block)
end
+ def set_local_var(name, object)
+ serialized = object.opal_serialize
+ "#{name} = #{serialized}" if serialized
+ end
+
def evaluate_ruby(p1 = nil, p2 = nil, p3 = nil, &block)
insure_page_loaded
# TODO: better error message here...either you give us a block
@@ -268,7 +297,8 @@ def evaluate_ruby(p1 = nil, p2 = nil, p3 = nil, &block)
end
args.each do |name, value|
- str = "#{name} = #{value.to_opal_expression}\n#{str}"
+ str = "#{set_local_var(name, value)}\n#{str}"
+ # str = "#{name} = #{value.to_opal_expression}\n#{str}"
end
str = add_opal_block(str, block) if block
js = opal_compile(str).gsub("// Prepare super implicit arguments\n", '')
@@ -319,19 +349,21 @@ def add_locals(in_str, block)
memoized = b.eval('__memoized').instance_variable_get(:@memoized)
in_str = memoized.inject(in_str) do |str, pair|
- "#{str}\n#{pair.first} = #{pair.last.to_opal_expression}"
+ str = "#{str}\n#{set_local_var(pair.first, pair.last)}"
+ # "#{str}\n#{pair.first} = #{pair.last.to_opal_expression}"
end if memoized
in_str = b.local_variables.inject(in_str) do |str, var|
next str if PRIVATE_VARIABLES.include? var
-
- "#{str}\n#{var} = #{b.local_variable_get(var).to_opal_expression}"
+ str = "#{str}\n#{set_local_var(var, b.local_variable_get(var))}"
+ # "#{str}\n#{var} = #{b.local_variable_get(var).to_opal_expression}"
end
in_str = b.eval('instance_variables').inject(in_str) do |str, var|
next str if PRIVATE_VARIABLES.include? var
- "#{str}\n#{var} = #{b.eval("instance_variable_get('#{var}')").to_opal_expression}"
+ str = "#{str}\n#{set_local_var(var, b.eval("instance_variable_get('#{var}')"))}"
+ # "#{str}\n#{var} = #{b.eval("instance_variable_get('#{var}')").to_opal_expression}"
end
in_str
end
@@ -442,6 +474,14 @@ def mount(component_name = nil, params = nil, opts = {}, &block)
opts = client_options opts
test_url = build_test_url_for(opts.delete(:controller))
if block || @_hyperspec_private_client_code || component_name.nil?
+ if defined? ::Hyperstack::Component
+ test_dummy = <<-code
+ class Hyperstack::Internal::Component::TestDummy
+ include Hyperstack::Component
+ render {}
+ end
+ code
+ end
block_with_helpers = <<-code
module ComponentHelpers
def self.js_eval(s)
@@ -472,25 +512,19 @@ def self.add_class(class_name, styles={})
}
end
end
- class Hyperstack::Internal::Component::TestDummy
- include Hyperstack::Component
- render {}
- end
+ #{test_dummy}
#{@_hyperspec_private_client_code}
#{Unparser.unparse(Parser::CurrentRuby.parse(block.source).children.last) if block}
code
opts[:code] = opal_compile(block_with_helpers)
end
@_hyperspec_private_client_code = nil
- # TODO: TestDummy is here to initialize the Hyper stack, but it also means you can't use
- # hyper-spec without hyper-component. Figure out a better way to do this, or configure it.
- # perhaps just some config setting to include certain code on init if needed?
- component_name ||= 'Hyperstack::Internal::Component::TestDummy'
+ component_name ||= 'Hyperstack::Internal::Component::TestDummy' if defined? ::Hyperstack::Component
value = [component_name, params, @_hyperspec_private_html_block, opts]
ComponentTestHelpers.cache_write(test_url, value)
@_hyperspec_private_html_block = nil
test_code_key = "hyper_spec_prerender_test_code.js"
- if defined? ::Hyperstack::Component # was ::React in old hyperloop version
+ if defined? ::Hyperstack::Component
@@original_server_render_files ||= ::Rails.configuration.react.server_renderer_options[:files]
if opts[:render_on] == :both || opts[:render_on] == :server_only
unless opts[:code].blank?
@@ -533,11 +567,6 @@ def add_class(class_name, style)
@_hyperspec_private_client_code = "#{@_hyperspec_private_client_code}ComponentHelpers.add_class('#{class_name}', #{style})\n"
end
- def attributes_on_client(model)
- evaluate_ruby("#{model.class.name}.find(#{model.id}).attributes").symbolize_keys
- end
-
-
def open_in_chrome
if false && ['linux', 'freebsd'].include?(`uname`.downcase)
`google-chrome http://#{page.server.host}:#{page.server.port}#{page.current_path}`
@@ -689,8 +718,9 @@ def initialize(target, args)
@target = target
@args_str = args.collect do |name, value|
- "#{name} = #{value.to_opal_expression}"
- end.join("\n")
+ set_local_var(name, value)
+ # "#{name} = #{value.to_opal_expression}"
+ end.compact.join("\n")
end
end
diff --git a/ruby/hyper-spec/lib/sources/top_level_rails_component.rb b/ruby/hyper-spec/lib/sources/top_level_rails_component.rb
index ae655c080..d7f2451b1 100644
--- a/ruby/hyper-spec/lib/sources/top_level_rails_component.rb
+++ b/ruby/hyper-spec/lib/sources/top_level_rails_component.rb
@@ -1,3 +1,10 @@
+class Time
+ def self._load(*args)
+ debugger
+ nil
+ end
+end
+
module Hyperstack
module Internal
module Component
diff --git a/ruby/hyper-spec/spec/test_app/app/views/components.rb b/ruby/hyper-spec/spec/test_app/app/views/components.rb
index d81c614ca..b205e4276 100644
--- a/ruby/hyper-spec/spec/test_app/app/views/components.rb
+++ b/ruby/hyper-spec/spec/test_app/app/views/components.rb
@@ -3,6 +3,7 @@
require 'hyper-component'
require 'hyper-state'
require 'time'
+require 'opal/full'
if Hyperstack::Component::IsomorphicHelpers.on_opal_client?
require 'browser'
require 'browser/delay'
From 2c4de175047030a198673658fb3456c513b0241b Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 16 Jan 2021 21:44:46 -0500
Subject: [PATCH 056/307] regressions fixed
---
ruby/hyper-model/lib/hyper-model.rb | 1 -
ruby/hyper-spec/lib/sources/top_level_rails_component.rb | 7 -------
ruby/hyper-spec/spec/test_app/app/views/components.rb | 1 -
3 files changed, 9 deletions(-)
diff --git a/ruby/hyper-model/lib/hyper-model.rb b/ruby/hyper-model/lib/hyper-model.rb
index 767ec320c..93b5e51d0 100644
--- a/ruby/hyper-model/lib/hyper-model.rb
+++ b/ruby/hyper-model/lib/hyper-model.rb
@@ -59,7 +59,6 @@
require "reactive_record/active_record/public_columns_hash"
require "reactive_record/serializers"
require "reactive_record/pry"
- require "hyper_spec/component_test_helpers"
require_relative 'active_record_base'
require 'hyper_model/version'
diff --git a/ruby/hyper-spec/lib/sources/top_level_rails_component.rb b/ruby/hyper-spec/lib/sources/top_level_rails_component.rb
index d7f2451b1..ae655c080 100644
--- a/ruby/hyper-spec/lib/sources/top_level_rails_component.rb
+++ b/ruby/hyper-spec/lib/sources/top_level_rails_component.rb
@@ -1,10 +1,3 @@
-class Time
- def self._load(*args)
- debugger
- nil
- end
-end
-
module Hyperstack
module Internal
module Component
diff --git a/ruby/hyper-spec/spec/test_app/app/views/components.rb b/ruby/hyper-spec/spec/test_app/app/views/components.rb
index b205e4276..d81c614ca 100644
--- a/ruby/hyper-spec/spec/test_app/app/views/components.rb
+++ b/ruby/hyper-spec/spec/test_app/app/views/components.rb
@@ -3,7 +3,6 @@
require 'hyper-component'
require 'hyper-state'
require 'time'
-require 'opal/full'
if Hyperstack::Component::IsomorphicHelpers.on_opal_client?
require 'browser'
require 'browser/delay'
From 4fb868d46b3f8e691d2fe1e567c5d9417a55c95f Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 16 Jan 2021 22:15:32 -0500
Subject: [PATCH 057/307] moved attributes_on_client to hyper-model
---
ruby/hyper-model/lib/hyper_spec/component_test_helpers.rb | 7 +++++++
1 file changed, 7 insertions(+)
create mode 100644 ruby/hyper-model/lib/hyper_spec/component_test_helpers.rb
diff --git a/ruby/hyper-model/lib/hyper_spec/component_test_helpers.rb b/ruby/hyper-model/lib/hyper_spec/component_test_helpers.rb
new file mode 100644
index 000000000..7164f69d9
--- /dev/null
+++ b/ruby/hyper-model/lib/hyper_spec/component_test_helpers.rb
@@ -0,0 +1,7 @@
+module HyperSpec
+ module ComponentTestHelpers
+ def attributes_on_client(model)
+ evaluate_ruby("#{model.class.name}.find(#{model.id}).attributes").symbolize_keys
+ end
+ end
+end
From 46f0bb887e551b7f8d58315e4390233f479eb572 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 16 Jan 2021 22:38:55 -0500
Subject: [PATCH 058/307] moved attributes_on_client back to hyper-spec
---
ruby/hyper-model/lib/hyper_spec/component_test_helpers.rb | 7 -------
ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb | 4 ++++
2 files changed, 4 insertions(+), 7 deletions(-)
delete mode 100644 ruby/hyper-model/lib/hyper_spec/component_test_helpers.rb
diff --git a/ruby/hyper-model/lib/hyper_spec/component_test_helpers.rb b/ruby/hyper-model/lib/hyper_spec/component_test_helpers.rb
deleted file mode 100644
index 7164f69d9..000000000
--- a/ruby/hyper-model/lib/hyper_spec/component_test_helpers.rb
+++ /dev/null
@@ -1,7 +0,0 @@
-module HyperSpec
- module ComponentTestHelpers
- def attributes_on_client(model)
- evaluate_ruby("#{model.class.name}.find(#{model.id}).attributes").symbolize_keys
- end
- end
-end
diff --git a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
index 83e7cb563..d429cebb4 100644
--- a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
@@ -647,6 +647,10 @@ def size_window(width = nil, height = nil)
rescue StandardError
true
end
+
+ def attributes_on_client(model)
+ evaluate_ruby("#{model.class.name}.find(#{model.id}).attributes").symbolize_keys
+ end
end
RSpec.configure do |config|
From 419191b2825839c2e49854159f507d33873e8b76 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 16 Jan 2021 22:40:57 -0500
Subject: [PATCH 059/307] run all specs
---
.travis.yml | 98 ++++++++++++++++++++++++++---------------------------
1 file changed, 49 insertions(+), 49 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 98fe5a4f4..9927bc5af 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -83,57 +83,57 @@ jobs:
- <<: *_test_gem
env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
- # - <<: *_test_gem
- # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- #
+ - <<: *_test_gem
+ env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
+ - <<: *_test_gem
+ env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+
- <<: *_test_gem
env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
- # - <<: *_test_gem
- # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
+ - <<: *_test_gem
+ env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- <<: *_deploy_gem
env: COMPONENT=hyper-i18n
From 52755b7609d0b5288935c2b8f2383c406ed3c0b5 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 17 Jan 2021 15:04:35 -0500
Subject: [PATCH 060/307] fixed intermittent failure
---
.../spec/batch1/column_types/column_type_spec.rb | 6 ++++--
ruby/rails-hyperstack/.gitignore | 5 +++++
2 files changed, 9 insertions(+), 2 deletions(-)
diff --git a/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb b/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb
index cb7e344a5..c6ad92680 100644
--- a/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb
+++ b/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb
@@ -149,8 +149,10 @@ class DefaultTest < ActiveRecord::Base
TypeTest.serialize :string
TypeTest.serialize :text
end
- [:string, :text].each do |attr|
- expect_evaluate_ruby("TypeTest.find(1).#{attr}.class").to eq('NilClass')
+ %i[string text].each_with_index do |attr, i|
+ # find a different record for each iteration to prevent finding a model
+ # which is loaded
+ expect { TypeTest.find(i + 1)[attr].class }.on_client_to eq('NilClass')
end
end
diff --git a/ruby/rails-hyperstack/.gitignore b/ruby/rails-hyperstack/.gitignore
index 9abccdc3d..71aa55cc3 100644
--- a/ruby/rails-hyperstack/.gitignore
+++ b/ruby/rails-hyperstack/.gitignore
@@ -50,3 +50,8 @@ bower.json
# ignore Gemfile.locks https://yehudakatz.com/2010/12/16/clarifying-the-roles-of-the-gemspec-and-gemfile/
/spec/test_app/Gemfile.lock
/Gemfile.lock
+
+node_modules
+package.json
+spec/test_app
+yarn.lock
From 3dd24b97c2ef48a4ca0f43eb73a4a828fa6d6cc5 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 17 Jan 2021 17:52:16 -0500
Subject: [PATCH 061/307] better handling of unserialized vars in hyper-spec
---
.../lib/hyper-spec/component_test_helpers.rb | 29 +++++++++----------
ruby/hyper-spec/spec/hyper_spec.rb | 21 ++++++++++++++
2 files changed, 34 insertions(+), 16 deletions(-)
diff --git a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
index d429cebb4..c61fd4a4a 100644
--- a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
@@ -69,17 +69,10 @@ def to_opal_expression
"Time.parse('#{inspect}')"
end
end
-#
-# class NilClass
-# def to_opal_expression
-# self.inspect
-# end
-# end
module HyperSpec
# add a before eval hook to pry so we can capture the source
-
if defined? Pry
class << self
attr_accessor :current_pry_code_block
@@ -272,7 +265,14 @@ def isomorphic(&block)
def set_local_var(name, object)
serialized = object.opal_serialize
- "#{name} = #{serialized}" if serialized
+ if serialized
+ "#{name} = #{serialized}"
+ else
+ "self.class.define_method(:#{name}) "\
+ "{ raise 'Attempt to access the variable #{name} "\
+ 'that was defined in the spec, but its value could not be serialized '\
+ "so it is undefined on the client.' }"
+ end
end
def evaluate_ruby(p1 = nil, p2 = nil, p3 = nil, &block)
@@ -349,21 +349,19 @@ def add_locals(in_str, block)
memoized = b.eval('__memoized').instance_variable_get(:@memoized)
in_str = memoized.inject(in_str) do |str, pair|
- str = "#{str}\n#{set_local_var(pair.first, pair.last)}"
- # "#{str}\n#{pair.first} = #{pair.last.to_opal_expression}"
+ "#{str}\n#{set_local_var(pair.first, pair.last)}"
end if memoized
in_str = b.local_variables.inject(in_str) do |str, var|
next str if PRIVATE_VARIABLES.include? var
- str = "#{str}\n#{set_local_var(var, b.local_variable_get(var))}"
- # "#{str}\n#{var} = #{b.local_variable_get(var).to_opal_expression}"
+
+ "#{str}\n#{set_local_var(var, b.local_variable_get(var))}"
end
in_str = b.eval('instance_variables').inject(in_str) do |str, var|
next str if PRIVATE_VARIABLES.include? var
- str = "#{str}\n#{set_local_var(var, b.eval("instance_variable_get('#{var}')"))}"
- # "#{str}\n#{var} = #{b.eval("instance_variable_get('#{var}')").to_opal_expression}"
+ "#{str}\n#{set_local_var(var, b.eval("instance_variable_get('#{var}')"))}"
end
in_str
end
@@ -723,8 +721,7 @@ def initialize(target, args)
@target = target
@args_str = args.collect do |name, value|
set_local_var(name, value)
- # "#{name} = #{value.to_opal_expression}"
- end.compact.join("\n")
+ end.join("\n")
end
end
diff --git a/ruby/hyper-spec/spec/hyper_spec.rb b/ruby/hyper-spec/spec/hyper_spec.rb
index 148836f84..5e4f54145 100644
--- a/ruby/hyper-spec/spec/hyper_spec.rb
+++ b/ruby/hyper-spec/spec/hyper_spec.rb
@@ -269,6 +269,27 @@ class StyledDiv
expect { another_string.gsub(/\W/, '') }.on_client_to eq another_string.gsub(/\W/, '')
end
+ it 'will deal with unserailized local vars, instance vars and memoized values correctly' do
+ foo_bar = page
+ expect do
+ evaluate_ruby { foo_bar }
+ end.to raise_error(Exception, /foo_bar/)
+ end
+
+ it 'will ignore unserailized local vars, instance vars and memoized values if not accessed' do
+ foo_bar = page
+ good_value = 12
+ expect { good_value * 2 }.on_client_to eq good_value * 2
+ end
+
+ it 'will allow unserailized local vars, instance vars and memoized values can be redefined on the client' do
+ foo_bar = page
+ expect do
+ foo_bar = 12
+ foo_bar * 2
+ end.on_client_to eq 24
+ end
+
it 'aliases evaluate_ruby as on_client and c?' do
expect(on_client { 12 % 5 }).to eq(2)
expect(c? { 12 % 5 }).to eq(2)
From 99f1543ed0dcebd229ba533d520bd3c80ce49ad8 Mon Sep 17 00:00:00 2001
From: catmando
Date: Wed, 20 Jan 2021 18:19:42 -0500
Subject: [PATCH 062/307] removed hard dependency on pry from hyper-spec
---
ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb | 7 +++++--
ruby/hyper-spec/spec/hyper_spec.rb | 3 +--
2 files changed, 6 insertions(+), 4 deletions(-)
diff --git a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
index c61fd4a4a..5e2e43985 100644
--- a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
@@ -3,7 +3,11 @@
require 'unparser'
require 'hyper-spec/unparser_patch' # not present in original version of refactored hyperspec
require 'method_source'
-require 'pry'
+begin
+ require 'pry'
+rescue LoadError
+ nil
+end
require_relative '../../lib/hyper-spec/time_cop.rb'
require 'filecache'
@@ -298,7 +302,6 @@ def evaluate_ruby(p1 = nil, p2 = nil, p3 = nil, &block)
args.each do |name, value|
str = "#{set_local_var(name, value)}\n#{str}"
- # str = "#{name} = #{value.to_opal_expression}\n#{str}"
end
str = add_opal_block(str, block) if block
js = opal_compile(str).gsub("// Prepare super implicit arguments\n", '')
diff --git a/ruby/hyper-spec/spec/hyper_spec.rb b/ruby/hyper-spec/spec/hyper_spec.rb
index 5e4f54145..4361dba41 100644
--- a/ruby/hyper-spec/spec/hyper_spec.rb
+++ b/ruby/hyper-spec/spec/hyper_spec.rb
@@ -284,7 +284,7 @@ class StyledDiv
it 'will allow unserailized local vars, instance vars and memoized values can be redefined on the client' do
foo_bar = page
- expect do
+ expect do
foo_bar = 12
foo_bar * 2
end.on_client_to eq 24
@@ -298,7 +298,6 @@ class StyledDiv
it 'allows local variables on the client to be set using the with method' do
expect { with_var * 2 }.with(with_var: 4).on_client_to eq(8)
end
-
end
end
From 4f2078e2c395121705536b2364075261b8bdb361 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 24 Jan 2021 12:00:03 -0500
Subject: [PATCH 063/307] initial refactor
---
.../lib/hyper-spec/component_test_helpers.rb | 219 ++++++++++--------
1 file changed, 124 insertions(+), 95 deletions(-)
diff --git a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
index 5e2e43985..0f6aed99d 100644
--- a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
@@ -86,6 +86,101 @@ class << self
end
end
+ module ControllerHelpers
+ TOP_LEVEL_COMPONENT_PATCH =
+ Opal.compile(File.read(File.expand_path('../../sources/top_level_rails_component.rb', __FILE__)))
+ TIME_COP_CLIENT_PATCH =
+ Opal.compile(File.read(File.expand_path('../../hyper-spec/time_cop.rb', __FILE__))) +
+ "\n#{File.read(File.expand_path('../../sources/lolex.js', __FILE__))}"
+
+ def initialize!
+ head(:no_content) && return if params[:id] == 'ping'
+ route_root = self.class.name.gsub(/Controller$/, '').underscore
+ key = "/#{route_root}/#{params[:id]}"
+ test_params = ComponentTestHelpers.cache_read(key)
+ @component_name = test_params[0]
+ @component_params = test_params[1]
+ @html_block = test_params[2]
+ @render_params = test_params[3]
+ @render_on = @render_params.delete(:render_on) || :client_only
+ @_mock_time = @render_params.delete(:mock_time)
+ @style_sheet = @render_params.delete(:style_sheet)
+ @javascript = @render_params.delete(:javascript)
+ @code = @render_params.delete(:code)
+
+ @page = "\n"
+ end
+
+ def mount_component!
+ @page = '<%= react_component @component_name, @component_params, '\
+ "{ prerender: #{@render_on != :client_only} } %>\n#{@page}"
+ end
+
+ def client_code!
+ if @component_name
+ @page = "\n#{@page}"
+ end
+ @page = "\n#{@page}" if @code
+ end
+
+ def time_cop_patch!
+ @page = "\n#{@page}"
+ end
+
+ def application!
+ @page = "<%= javascript_include_tag '#{@javascript || 'application'}' %>\n#{@page}"
+ end
+
+ def style_sheet!
+ @page = "<%= stylesheet_link_tag '#{@style_sheet || 'application'}' %>\n#{@page}"
+ end
+
+ def go_function!
+ @page = "\n#{@page}"
+ end
+
+ def client_title!
+ title = view_context.escape_javascript(ComponentTestHelpers.current_example.description)
+ title = "#{title}...continued." if ComponentTestHelpers.description_displayed
+
+ @page = "\n#{@page}"
+
+ ComponentTestHelpers.description_displayed = true
+ end
+
+ def html_block!
+ @page = "\n#{@html_block}\n#{@page}"
+ end
+
+ def deliver!
+ @render_params[:inline] = @page
+ response.headers['Cache-Control'] = 'max-age=120'
+ response.headers['X-Tracking-ID'] = '123456'
+ render @render_params
+ end
+
+ def server_only?
+ @render_on == :server_only
+ end
+
+ def test
+ initialize!
+ # TODO: reverse the the layout in the above methods so they can run in
+ # the right order
+ mount_component! if @component_name
+ client_code! unless server_only?
+ time_cop_patch! if !server_only? || Lolex.initialized?
+ application! if (!server_only? && !@render_params[:layout]) || @javascript
+ style_sheet! if !@render_params[:layout] || @style_sheet
+ go_function!
+ client_title! if ComponentTestHelpers.current_example
+ html_block!
+ deliver!
+ end
+ end
+
module ComponentTestHelpers
def self.opal_compile(s)
Opal.compile(s)
@@ -98,13 +193,6 @@ def opal_compile(s)
ComponentTestHelpers.opal_compile(s)
end
- TOP_LEVEL_COMPONENT_PATCH =
- Opal.compile(File.read(File.expand_path('../../sources/top_level_rails_component.rb', __FILE__)))
- TIME_COP_CLIENT_PATCH =
- Opal.compile(File.read(File.expand_path('../../hyper-spec/time_cop.rb', __FILE__))) +
- "\n#{File.read(File.expand_path('../../sources/lolex.js', __FILE__))}"
-
-
class << self
attr_accessor :current_example
attr_accessor :description_displayed
@@ -160,102 +248,43 @@ def cache_delete(key)
# to ActionController::Base
def new_controller
- if defined? ApplicationController
- Class.new ApplicationController
- else
- Class.new ::ActionController::Base
- end
- end
+ return ::HyperSpecTestController if defined?(::HyperSpecTestController)
- def build_test_url_for(controller, ping = nil)
- unless controller
- unless defined?(::HyperSpecTestController)
- Object.const_set('HyperSpecTestController', new_controller)
- end
+ controller = if defined? ApplicationController
+ Class.new ApplicationController
+ elsif defined? ::ActionController::Base
+ Class.new ::ActionController::Base
+ end
- controller = ::HyperSpecTestController
- end
-
- route_root = controller.name.gsub(/Controller$/, '').underscore
+ raise raise 'No HyperSpecTestController class found' unless controller
- unless controller.method_defined?(:test)
- controller.class_eval do
- define_method(:test) do
- head(:no_content) && return if params[:id] == 'ping'
- route_root = self.class.name.gsub(/Controller$/, '').underscore
- key = "/#{route_root}/#{params[:id]}"
- test_params = ComponentTestHelpers.cache_read(key)
- @component_name = test_params[0]
- @component_params = test_params[1]
- html_block = test_params[2]
- render_params = test_params[3]
- render_on = render_params.delete(:render_on) || :client_only
- _mock_time = render_params.delete(:mock_time)
- style_sheet = render_params.delete(:style_sheet)
- javascript = render_params.delete(:javascript)
- code = render_params.delete(:code)
- #page = "#{html_block}\n\n"
- page = "
\n#{page}"
- unless render_on == :server_only
- page = "\n#{page}" if @component_name
- page = "\n#{page}" if code
- end
-
- if render_on != :server_only || Lolex.initialized?
- page = "\n#{page}"
- end
-
- if (render_on != :server_only && !render_params[:layout]) || javascript
- page = "<%= javascript_include_tag '#{javascript || 'application'}' %>\n#{page}"
- end
+ Object.const_set('HyperSpecTestController', controller)
+ end
- if !render_params[:layout] || style_sheet
- page = "<%= stylesheet_link_tag '#{style_sheet || 'application'}' %>\n#{page}"
- end
- page = "\n#{page}"
+ def add_rails_route(route_root)
+ routes = ::Rails.application.routes
+ routes.disable_clear_and_finalize = true
+ routes.clear!
+ routes.draw { get "/#{route_root}/:id", to: "#{route_root}#test" }
+ ::Rails.application.routes_reloader.paths.each { |path| load(path) }
+ routes.finalize!
+ ActiveSupport.on_load(:action_controller) { routes.finalize! }
+ ensure
+ routes.disable_clear_and_finalize = false
+ end
- if ComponentTestHelpers.current_example
+ def build_test_url_for(controller = nil, ping = nil)
+ controller ||= new_controller
+ route_root = controller.name.gsub(/Controller$/, '').underscore
- title = view_context.escape_javascript(ComponentTestHelpers.current_example.description)
- title = "#{title}...continued." if ComponentTestHelpers.description_displayed
+ unless controller.method_defined?(:test)
+ controller.include ControllerHelpers
+ add_rails_route(route_root)
+ end
- page = "\n#{page}"
+ id = ping ? 'ping' : ComponentTestHelpers.test_id
- ComponentTestHelpers.description_displayed = true
- end
- page = "\n#{html_block}\n#{page}"
- render_params[:inline] = page
- response.headers['Cache-Control'] = 'max-age=120'
- response.headers['X-Tracking-ID'] = '123456'
- render render_params
- end
- end
-
- begin
- routes = ::Rails.application.routes
- routes.disable_clear_and_finalize = true
- routes.clear!
- routes.draw do
- get "/#{route_root}/:id", to: "#{route_root}#test"
- end
- ::Rails.application.routes_reloader.paths.each { |path| load(path) }
- routes.finalize!
- ActiveSupport.on_load(:action_controller) { routes.finalize! }
- ensure
- routes.disable_clear_and_finalize = false
- end
- end
- if ping
- "/#{route_root}/ping"
- else
- "/#{route_root}/#{ComponentTestHelpers.test_id}"
- end
+ "/#{route_root}/#{id}"
end
def insert_html(str)
From d1a00ead5a939eda9e4e5e34ffa2809bb8b77337 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 24 Jan 2021 15:43:40 -0500
Subject: [PATCH 064/307] more refactors
---
ruby/hyper-spec/hyper-spec.gemspec | 1 +
ruby/hyper-spec/lib/hyper-spec.rb | 99 +++---
.../lib/hyper-spec/component_test_helpers.rb | 296 +-----------------
.../lib/hyper-spec/controller_helpers.rb | 121 +++++++
.../hyper-spec/lib/hyper-spec/expectations.rb | 76 +++++
ruby/hyper-spec/lib/hyper-spec/patches.rb | 68 ++++
.../lib/hyper-spec/unparser_patch.rb | 10 -
7 files changed, 340 insertions(+), 331 deletions(-)
create mode 100644 ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
create mode 100644 ruby/hyper-spec/lib/hyper-spec/expectations.rb
create mode 100644 ruby/hyper-spec/lib/hyper-spec/patches.rb
delete mode 100644 ruby/hyper-spec/lib/hyper-spec/unparser_patch.rb
diff --git a/ruby/hyper-spec/hyper-spec.gemspec b/ruby/hyper-spec/hyper-spec.gemspec
index d1af270f0..2018b1fc2 100644
--- a/ruby/hyper-spec/hyper-spec.gemspec
+++ b/ruby/hyper-spec/hyper-spec.gemspec
@@ -24,6 +24,7 @@ Gem::Specification.new do |spec| # rubocop:disable Metrics/BlockLength
spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
spec.require_paths = ['lib']
+ spec.add_dependency 'actionview'
spec.add_dependency 'capybara'
spec.add_dependency 'chromedriver-helper', '1.2.0'
spec.add_dependency 'filecache'
diff --git a/ruby/hyper-spec/lib/hyper-spec.rb b/ruby/hyper-spec/lib/hyper-spec.rb
index 1f2c76353..9f7ed1ea0 100644
--- a/ruby/hyper-spec/lib/hyper-spec.rb
+++ b/ruby/hyper-spec/lib/hyper-spec.rb
@@ -1,13 +1,46 @@
-require 'capybara/rspec'
+# hyper-spec
+require 'action_view'
require 'opal'
-require 'selenium-webdriver'
+require 'unparser'
+require 'method_source'
+require 'hyper-spec/time_cop.rb'
+require 'filecache'
+require 'capybara/rspec'
require 'hyper-spec/component_test_helpers'
+require 'hyper-spec/controller_helpers'
+require 'hyper-spec/patches'
require 'hyper-spec/version'
require 'hyper-spec/wait_for_ajax'
+require 'hyper-spec/expectations'
+require 'parser/current'
require 'selenium/web_driver/firefox/profile'
+require 'selenium-webdriver'
+
+begin
+ require 'pry'
+rescue LoadError
+ nil
+end
+
+Parser::Builders::Default.emit_procarg0 = true
+
+# not available in parser 2.3
+if Parser::Builders::Default.respond_to? :emit_arg_inside_procarg0
+ Parser::Builders::Default.emit_arg_inside_procarg0 = true
+end
module HyperSpec
+ if defined? Pry
+ # add a before eval hook to pry so we can capture the source
+ class << self
+ attr_accessor :current_pry_code_block
+ Pry.hooks.add_hook(:before_eval, 'hyper_spec_code_capture') do |code|
+ HyperSpec.current_pry_code_block = code
+ end
+ end
+ end
+
def self.reset_between_examples=(value)
RSpec.configuration.reset_between_examples = value
end
@@ -21,7 +54,8 @@ def self.reset_sessions!
end
end
-# TODO: figure out why we need this patch - its because we are on an old version of Selenium Webdriver, but why?
+# TODO: figure out why we need this patch - its because we are on an old version
+# of Selenium Webdriver, but why?
require 'selenium-webdriver'
module Selenium
@@ -33,7 +67,7 @@ module Bridge
COMMANDS.freeze
def log(type)
- data = execute :get_log, {}, {type: type.to_s}
+ data = execute :get_log, {}, type: type.to_s
Array(data).map do |l|
begin
@@ -48,10 +82,9 @@ def log(type)
end
end
-
module Capybara
class << self
- alias_method :old_reset_sessions!, :reset_sessions!
+ alias old_reset_sessions! reset_sessions!
def reset_sessions!
old_reset_sessions! if HyperSpec.reset_between_examples?
end
@@ -80,19 +113,22 @@ def reset_sessions!
config.add_setting :debugger_width, default: nil
-
config.before(:each) do
- Hyperstack.class_eval do
- def self.on_server?
- true
+ if defined?(Hyperstack)
+ Hyperstack.class_eval do
+ def self.on_server?
+ true
+ end
end
- end if defined?(Hyperstack)
+ end
# for compatibility with HyperMesh
- HyperMesh.class_eval do
- def self.on_server?
- true
+ if defined?(HyperMesh)
+ HyperMesh.class_eval do
+ def self.on_server?
+ true
+ end
end
- end if defined?(HyperMesh)
+ end
end
config.before(:each, js: true) do
@@ -112,6 +148,11 @@ def self.on_server?
# Capybara config
RSpec.configure do |config|
+ config.before(:each) do |example|
+ HyperSpec::ComponentTestHelpers.current_example = example
+ HyperSpec::ComponentTestHelpers.description_displayed = false
+ end
+
config.add_setting :wait_for_initialization_time
config.wait_for_initialization_time = 3
@@ -121,28 +162,15 @@ def self.on_server?
options = {}
options.merge!(
w3c: false,
- args: %w[auto-open-devtools-for-tabs]) #,
- #prefs: { 'devtools.open_docked' => false, "devtools.currentDockState" => "undocked", devtools: {currentDockState: :undocked} }
- #) unless ENV['NO_DEBUGGER']
- # this does not seem to work properly. Don't document this feature yet.
- # options['mobileEmulation'] = { 'deviceName' => ENV['DEVICE'].tr('-', ' ') } if ENV['DEVICE']
+ args: %w[auto-open-devtools-for-tabs]
+ )
options['mobileEmulation'] = { 'deviceName' => ENV['DEVICE'].tr('-', ' ') } if ENV['DEVICE']
- capabilities = Selenium::WebDriver::Remote::Capabilities.chrome(chromeOptions: options, 'goog:loggingPrefs' => {browser: 'ALL'})
+ capabilities = Selenium::WebDriver::Remote::Capabilities.chrome(
+ chromeOptions: options, 'goog:loggingPrefs' => { browser: 'ALL' }
+ )
Capybara::Selenium::Driver.new(app, browser: :chrome, desired_capabilities: capabilities)
end
- # Capybara.register_driver :chrome do |app|
- # options = {}
- # options.merge!(
- # args: %w[auto-open-devtools-for-tabs],
- # prefs: { 'devtools.open_docked' => false, "devtools.currentDockState" => "undocked", devtools: {currentDockState: :undocked} }
- # ) unless ENV['NO_DEBUGGER']
- # # this does not seem to work properly. Don't document this feature yet.
- # options['mobileEmulation'] = { 'deviceName' => ENV['DEVICE'].tr('-', ' ') } if ENV['DEVICE']
- # capabilities = Selenium::WebDriver::Remote::Capabilities.chrome(chromeOptions: options)
- # Capybara::Selenium::Driver.new(app, browser: :chrome, desired_capabilities: capabilities)
- # end
-
Capybara.register_driver :firefox do |app|
Capybara::Selenium::Driver.new(app, browser: :firefox)
end
@@ -152,7 +180,9 @@ def self.on_server?
options.add_argument('--headless')
options.add_argument('--no-sandbox')
options.add_argument('--disable-dev-shm-usage')
- Capybara::Selenium::Driver.new(app, browser: :chrome, :driver_path => "/usr/lib/chromium-browser/chromedriver", options: options)
+ Capybara::Selenium::Driver.new(
+ app, browser: :chrome, driver_path: '/usr/lib/chromium-browser/chromedriver', options: options
+ )
end
Capybara.register_driver :firefox_headless do |app|
@@ -184,5 +214,4 @@ def self.on_server?
when 'travis' then :chrome_headless_docker_travis
else :selenium_chrome_headless
end
-
end
diff --git a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
index 0f6aed99d..855a9035b 100644
--- a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
@@ -1,194 +1,15 @@
# see component_test_helpers_spec.rb for examples
-require 'parser/current'
-require 'unparser'
-require 'hyper-spec/unparser_patch' # not present in original version of refactored hyperspec
-require 'method_source'
-begin
- require 'pry'
-rescue LoadError
- nil
-end
-require_relative '../../lib/hyper-spec/time_cop.rb'
-require 'filecache'
-
-Parser::Builders::Default.emit_procarg0 = true # not present in original version of refactored hyperspec
-if Parser::Builders::Default.respond_to? :emit_arg_inside_procarg0
- Parser::Builders::Default.emit_arg_inside_procarg0 = true # not available in parser 2.3
-end
-
-module MethodSource
- class << self
- alias original_lines_for_before_hyper_spec lines_for
- alias original_source_helper_before_hyper_spec source_helper
-
- def source_helper(source_location, name=nil)
- source_location[1] = 1 if source_location[0] == '(pry)'
- original_source_helper_before_hyper_spec source_location, name
- end
-
- def lines_for(file_name, name = nil)
- if file_name == '(pry)'
- HyperSpec.current_pry_code_block
- else
- original_lines_for_before_hyper_spec file_name, name
- end
- end
- end
-end
-
-class Object
- def opal_serialize
- nil
- end
-end
-
-class Hash
- def opal_serialize
- "{#{collect { |k, v| "#{k.opal_serialize} => #{v.opal_serialize}"}.join(', ')}}"
- end
-end
-
-class Array
- def opal_serialize
- "[#{collect { |v| v.opal_serialize }.join(', ')}]"
- end
-end
-
-[FalseClass, Float, Integer, NilClass, String, Symbol, TrueClass].each do |klass|
- klass.send(:define_method, :opal_serialize) do
- inspect
- end
-end
-
-if Gem::Version.new(RUBY_VERSION) < Gem::Version.new('2.4.0')
- [Bignum, Fixnum].each do |klass|
- klass.send(:define_method, :opal_serialize) do
- inspect
- end
- end
-end
-
-class Time
- def to_opal_expression
- "Time.parse('#{inspect}')"
- end
-end
-
module HyperSpec
-
- # add a before eval hook to pry so we can capture the source
- if defined? Pry
- class << self
- attr_accessor :current_pry_code_block
- Pry.hooks.add_hook(:before_eval, "hyper_spec_code_capture") do |code|
- HyperSpec.current_pry_code_block = code
- end
- end
- end
-
- module ControllerHelpers
- TOP_LEVEL_COMPONENT_PATCH =
- Opal.compile(File.read(File.expand_path('../../sources/top_level_rails_component.rb', __FILE__)))
- TIME_COP_CLIENT_PATCH =
- Opal.compile(File.read(File.expand_path('../../hyper-spec/time_cop.rb', __FILE__))) +
- "\n#{File.read(File.expand_path('../../sources/lolex.js', __FILE__))}"
-
- def initialize!
- head(:no_content) && return if params[:id] == 'ping'
- route_root = self.class.name.gsub(/Controller$/, '').underscore
- key = "/#{route_root}/#{params[:id]}"
- test_params = ComponentTestHelpers.cache_read(key)
- @component_name = test_params[0]
- @component_params = test_params[1]
- @html_block = test_params[2]
- @render_params = test_params[3]
- @render_on = @render_params.delete(:render_on) || :client_only
- @_mock_time = @render_params.delete(:mock_time)
- @style_sheet = @render_params.delete(:style_sheet)
- @javascript = @render_params.delete(:javascript)
- @code = @render_params.delete(:code)
-
- @page = "\n"
- end
-
- def mount_component!
- @page = '<%= react_component @component_name, @component_params, '\
- "{ prerender: #{@render_on != :client_only} } %>\n#{@page}"
- end
-
- def client_code!
- if @component_name
- @page = "\n#{@page}"
- end
- @page = "\n#{@page}" if @code
- end
-
- def time_cop_patch!
- @page = "\n#{@page}"
- end
-
- def application!
- @page = "<%= javascript_include_tag '#{@javascript || 'application'}' %>\n#{@page}"
- end
-
- def style_sheet!
- @page = "<%= stylesheet_link_tag '#{@style_sheet || 'application'}' %>\n#{@page}"
- end
-
- def go_function!
- @page = "\n#{@page}"
- end
-
- def client_title!
- title = view_context.escape_javascript(ComponentTestHelpers.current_example.description)
- title = "#{title}...continued." if ComponentTestHelpers.description_displayed
-
- @page = "\n#{@page}"
-
- ComponentTestHelpers.description_displayed = true
- end
-
- def html_block!
- @page = "\n#{@html_block}\n#{@page}"
- end
-
- def deliver!
- @render_params[:inline] = @page
- response.headers['Cache-Control'] = 'max-age=120'
- response.headers['X-Tracking-ID'] = '123456'
- render @render_params
- end
-
- def server_only?
- @render_on == :server_only
- end
-
- def test
- initialize!
- # TODO: reverse the the layout in the above methods so they can run in
- # the right order
- mount_component! if @component_name
- client_code! unless server_only?
- time_cop_patch! if !server_only? || Lolex.initialized?
- application! if (!server_only? && !@render_params[:layout]) || @javascript
- style_sheet! if !@render_params[:layout] || @style_sheet
- go_function!
- client_title! if ComponentTestHelpers.current_example
- html_block!
- deliver!
- end
- end
-
module ComponentTestHelpers
- def self.opal_compile(s)
- Opal.compile(s)
+ def self.opal_compile(str)
+ Opal.compile(str)
rescue Exception => e
- puts "puts could not compile: \n\n#{s}\n\n"
+ puts "puts could not compile: \n\n#{str}\n\n"
raise e
end
+ extend ActionView::Helpers::JavaScriptHelper
+
def opal_compile(s)
ComponentTestHelpers.opal_compile(s)
end
@@ -206,34 +27,21 @@ def display_example_description
""
end
- RAILS_CACHE = false
def file_cache
@file_cache ||= FileCache.new("cache", "/tmp/hyper-spec-caches", 30, 3)
end
def cache_read(key)
- if RAILS_CACHE
- ::Rails.cache.read(key)
- else
- file_cache.get(key)
- end
+ file_cache.get(key)
end
def cache_write(key, value)
- if RAILS_CACHE
- ::Rails.cache.write(key, value)
- else
- file_cache.set(key, value)
- end
+ file_cache.set(key, value)
end
def cache_delete(key)
- if RAILS_CACHE
- ::Rails.cache.write(key, value)
- else
- file_cache.delete(key)
- end
+ file_cache.delete(key)
rescue StandardError
nil
end
@@ -275,16 +83,15 @@ def add_rails_route(route_root)
def build_test_url_for(controller = nil, ping = nil)
controller ||= new_controller
- route_root = controller.name.gsub(/Controller$/, '').underscore
unless controller.method_defined?(:test)
controller.include ControllerHelpers
- add_rails_route(route_root)
+ add_rails_route(controller.route_root)
end
id = ping ? 'ping' : ComponentTestHelpers.test_id
- "/#{route_root}/#{id}"
+ "/#{controller.route_root}/#{id}"
end
def insert_html(str)
@@ -682,87 +489,4 @@ def attributes_on_client(model)
evaluate_ruby("#{model.class.name}.find(#{model.id}).attributes").symbolize_keys
end
end
-
- RSpec.configure do |config|
- config.before(:each) do |example|
- ComponentTestHelpers.current_example = example
- ComponentTestHelpers.description_displayed = false
- end
- end
-end
-
-module RSpec
- module Expectations
- class ExpectationTarget
- end
-
- module HyperSpecInstanceMethods
-
- def self.included(base)
- base.include HyperSpec::ComponentTestHelpers
- end
-
- def to_on_client(matcher, message = nil, &block)
- evaluate_client('ruby').to(matcher, message, &block)
- end
-
- alias on_client_to to_on_client
-
- def to_on_client_not(matcher, message = nil, &block)
- evaluate_client('ruby').not_to(matcher, message, &block)
- end
-
- alias on_client_to_not to_on_client_not
- alias on_client_not_to to_on_client_not
- alias to_not_on_client to_on_client_not
- alias not_to_on_client to_on_client_not
-
- def to_then(matcher, message = nil, &block)
- evaluate_client('promise').to(matcher, message, &block)
- end
-
- alias then_to to_then
-
- def to_then_not(matcher, message = nil, &block)
- evaluate_client('promise').not_to(matcher, message, &block)
- end
-
- alias then_to_not to_then_not
- alias then_not_to to_then_not
- alias to_not_then to_then_not
- alias not_to_then to_then_not
-
- private
-
- def evaluate_client(method)
- source = add_opal_block(@args_str, @target)
- value = @target.binding.eval("evaluate_#{method}(#{source.inspect}, {}, {})")
- ExpectationTarget.for(value, nil)
- end
- end
-
- class OnClientWithArgsTarget
- include HyperSpecInstanceMethods
-
- def initialize(target, args)
- unless args.is_a? Hash
- raise ExpectationNotMetError,
- "You must pass a hash of local var, value pairs to the 'with' modifier"
- end
-
- @target = target
- @args_str = args.collect do |name, value|
- set_local_var(name, value)
- end.join("\n")
- end
- end
-
- class BlockExpectationTarget < ExpectationTarget
- include HyperSpecInstanceMethods
-
- def with(args)
- OnClientWithArgsTarget.new(@target, args)
- end
- end
- end
end
diff --git a/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
new file mode 100644
index 000000000..32d736f6d
--- /dev/null
+++ b/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
@@ -0,0 +1,121 @@
+module HyperSpec
+ module ControllerHelpers
+ TOP_LEVEL_COMPONENT_PATCH =
+ Opal.compile(File.read(File.expand_path('../../sources/top_level_rails_component.rb', __FILE__)))
+ TIME_COP_CLIENT_PATCH =
+ Opal.compile(File.read(File.expand_path('../../hyper-spec/time_cop.rb', __FILE__))) +
+ "\n#{File.read(File.expand_path('../../sources/lolex.js', __FILE__))}"
+
+ def self.included(base)
+ def base.route_root
+ # Implement underscore without using rails underscore, so we don't have a
+ # dependency on ActiveSupport
+ name.gsub(/Controller$/, '')
+ .gsub(/::/, '/')
+ .gsub(/([A-Z]+)([A-Z][a-z])/, '\1_\2')
+ .gsub(/([a-z\d])([A-Z])/, '\1_\2')
+ .tr('-', '_')
+ .downcase
+ end
+ end
+
+ def initialize!
+ return ping! if params[:id] == 'ping'
+
+ key = "/#{self.class.route_root}/#{params[:id]}"
+ test_params = ComponentTestHelpers.cache_read(key)
+
+ @component_name = test_params[0]
+ @component_params = test_params[1]
+ @html_block = test_params[2]
+ @render_params = test_params[3]
+ @render_on = @render_params.delete(:render_on) || :client_only
+ @_mock_time = @render_params.delete(:mock_time)
+ @style_sheet = @render_params.delete(:style_sheet)
+ @javascript = @render_params.delete(:javascript)
+ @code = @render_params.delete(:code)
+
+ @page = "\n"
+ end
+
+ def ping!
+ head(:no_content)
+ nil
+ end
+
+ def mount_component!
+ @page = '<%= react_component @component_name, @component_params, '\
+ "{ prerender: #{@render_on != :client_only} } %>\n#{@page}"
+ end
+
+ def client_code!
+ if @component_name
+ @page = "\n#{@page}"
+ end
+ @page = "\n#{@page}" if @code
+ end
+
+ def time_cop_patch!
+ @page = "\n#{@page}"
+ end
+
+ def application!
+ @page = "<%= javascript_include_tag '#{@javascript || 'application'}' %>\n#{@page}"
+ end
+
+ def style_sheet!
+ @page = "<%= stylesheet_link_tag '#{@style_sheet || 'application'}' %>\n#{@page}"
+ end
+
+ def go_function!
+ @page = "\n#{@page}"
+ end
+
+ def escape_javascript(str)
+ ComponentTestHelpers.escape_javascript(str)
+ end
+
+ def client_title!
+ title =
+ ComponentTestHelpers.escape_javascript(ComponentTestHelpers.current_example.description)
+ title = "#{title}...continued." if ComponentTestHelpers.description_displayed
+
+ @page = "\n#{@page}"
+
+ ComponentTestHelpers.description_displayed = true
+ end
+
+ def html_block!
+ @page = "\n#{@html_block}\n#{@page}"
+ end
+
+ def deliver!
+ @render_params[:inline] = @page
+ response.headers['Cache-Control'] = 'max-age=120'
+ response.headers['X-Tracking-ID'] = '123456'
+ render @render_params
+ end
+
+ def server_only?
+ @render_on == :server_only
+ end
+
+ def test
+ return unless initialize!
+
+ # TODO: reverse the the layout in the above methods so they can run in
+ # the right order
+ mount_component! if @component_name
+ client_code! unless server_only?
+ time_cop_patch! if !server_only? || Lolex.initialized?
+ application! if (!server_only? && !@render_params[:layout]) || @javascript
+ style_sheet! if !@render_params[:layout] || @style_sheet
+ go_function!
+ client_title! if ComponentTestHelpers.current_example
+ html_block!
+ deliver!
+ end
+ end
+end
diff --git a/ruby/hyper-spec/lib/hyper-spec/expectations.rb b/ruby/hyper-spec/lib/hyper-spec/expectations.rb
new file mode 100644
index 000000000..ba4c33227
--- /dev/null
+++ b/ruby/hyper-spec/lib/hyper-spec/expectations.rb
@@ -0,0 +1,76 @@
+# don't put this in directory lib/rspec/ as that will cause stack overflow with rails/rspec loads
+module RSpec
+ module Expectations
+ class ExpectationTarget
+ end
+
+ module HyperSpecInstanceMethods
+
+ def self.included(base)
+ base.include HyperSpec::ComponentTestHelpers
+ end
+
+ def to_on_client(matcher, message = nil, &block)
+ evaluate_client('ruby').to(matcher, message, &block)
+ end
+
+ alias on_client_to to_on_client
+
+ def to_on_client_not(matcher, message = nil, &block)
+ evaluate_client('ruby').not_to(matcher, message, &block)
+ end
+
+ alias on_client_to_not to_on_client_not
+ alias on_client_not_to to_on_client_not
+ alias to_not_on_client to_on_client_not
+ alias not_to_on_client to_on_client_not
+
+ def to_then(matcher, message = nil, &block)
+ evaluate_client('promise').to(matcher, message, &block)
+ end
+
+ alias then_to to_then
+
+ def to_then_not(matcher, message = nil, &block)
+ evaluate_client('promise').not_to(matcher, message, &block)
+ end
+
+ alias then_to_not to_then_not
+ alias then_not_to to_then_not
+ alias to_not_then to_then_not
+ alias not_to_then to_then_not
+
+ private
+
+ def evaluate_client(method)
+ source = add_opal_block(@args_str, @target)
+ value = @target.binding.eval("evaluate_#{method}(#{source.inspect}, {}, {})")
+ ExpectationTarget.for(value, nil)
+ end
+ end
+
+ class OnClientWithArgsTarget
+ include HyperSpecInstanceMethods
+
+ def initialize(target, args)
+ unless args.is_a? Hash
+ raise ExpectationNotMetError,
+ "You must pass a hash of local var, value pairs to the 'with' modifier"
+ end
+
+ @target = target
+ @args_str = args.collect do |name, value|
+ set_local_var(name, value)
+ end.join("\n")
+ end
+ end
+
+ class BlockExpectationTarget < ExpectationTarget
+ include HyperSpecInstanceMethods
+
+ def with(args)
+ OnClientWithArgsTarget.new(@target, args)
+ end
+ end
+ end
+end
diff --git a/ruby/hyper-spec/lib/hyper-spec/patches.rb b/ruby/hyper-spec/lib/hyper-spec/patches.rb
new file mode 100644
index 000000000..e88cc5111
--- /dev/null
+++ b/ruby/hyper-spec/lib/hyper-spec/patches.rb
@@ -0,0 +1,68 @@
+module Unparser
+ class Emitter
+ # Emitter for send
+ class Send < self
+ def local_variable_clash?
+ selector =~ /^[A-Z]/ || local_variable_scope.local_variable_defined_for_node?(node, selector)
+ end
+ end
+ end
+end
+
+module MethodSource
+ class << self
+ alias original_lines_for_before_hyper_spec lines_for
+ alias original_source_helper_before_hyper_spec source_helper
+
+ def source_helper(source_location, name=nil)
+ source_location[1] = 1 if source_location[0] == '(pry)'
+ original_source_helper_before_hyper_spec source_location, name
+ end
+
+ def lines_for(file_name, name = nil)
+ if file_name == '(pry)'
+ HyperSpec.current_pry_code_block
+ else
+ original_lines_for_before_hyper_spec file_name, name
+ end
+ end
+ end
+end
+
+class Object
+ def opal_serialize
+ nil
+ end
+end
+
+class Hash
+ def opal_serialize
+ "{#{collect { |k, v| "#{k.opal_serialize} => #{v.opal_serialize}"}.join(', ')}}"
+ end
+end
+
+class Array
+ def opal_serialize
+ "[#{collect { |v| v.opal_serialize }.join(', ')}]"
+ end
+end
+
+[FalseClass, Float, Integer, NilClass, String, Symbol, TrueClass].each do |klass|
+ klass.send(:define_method, :opal_serialize) do
+ inspect
+ end
+end
+
+if Gem::Version.new(RUBY_VERSION) < Gem::Version.new('2.4.0')
+ [Bignum, Fixnum].each do |klass|
+ klass.send(:define_method, :opal_serialize) do
+ inspect
+ end
+ end
+end
+
+class Time
+ def to_opal_expression
+ "Time.parse('#{inspect}')"
+ end
+end
diff --git a/ruby/hyper-spec/lib/hyper-spec/unparser_patch.rb b/ruby/hyper-spec/lib/hyper-spec/unparser_patch.rb
deleted file mode 100644
index dc0a720b8..000000000
--- a/ruby/hyper-spec/lib/hyper-spec/unparser_patch.rb
+++ /dev/null
@@ -1,10 +0,0 @@
-module Unparser
- class Emitter
- # Emitter for send
- class Send < self
- def local_variable_clash?
- selector =~ /^[A-Z]/ || local_variable_scope.local_variable_defined_for_node?(node, selector)
- end
- end
- end
-end
From ac01576828996f234ed40dd9a746bb63071bf81a Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 24 Jan 2021 15:51:22 -0500
Subject: [PATCH 065/307] cleanup
---
ruby/hyper-spec/lib/hyper-spec/expectations.rb | 1 -
1 file changed, 1 deletion(-)
diff --git a/ruby/hyper-spec/lib/hyper-spec/expectations.rb b/ruby/hyper-spec/lib/hyper-spec/expectations.rb
index ba4c33227..e6a2898fd 100644
--- a/ruby/hyper-spec/lib/hyper-spec/expectations.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/expectations.rb
@@ -5,7 +5,6 @@ class ExpectationTarget
end
module HyperSpecInstanceMethods
-
def self.included(base)
base.include HyperSpec::ComponentTestHelpers
end
From 631bf62c15ae82f7d4c58b8c0c3b3ea9bbec0bbe Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 24 Jan 2021 18:17:19 -0500
Subject: [PATCH 066/307] more cleanup
---
.../lib/hyper-spec/component_test_helpers.rb | 15 ++++++++-------
.../lib/hyper-spec/controller_helpers.rb | 15 +++------------
2 files changed, 11 insertions(+), 19 deletions(-)
diff --git a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
index 855a9035b..18be6e402 100644
--- a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
@@ -8,10 +8,8 @@ def self.opal_compile(str)
raise e
end
- extend ActionView::Helpers::JavaScriptHelper
-
- def opal_compile(s)
- ComponentTestHelpers.opal_compile(s)
+ def opal_compile(str)
+ ComponentTestHelpers.opal_compile(str)
end
class << self
@@ -23,9 +21,12 @@ def test_id
@_hyperspec_private_test_id += 1
end
- def display_example_description
- ""
+ include ActionView::Helpers::JavaScriptHelper
+
+ def current_example_description!
+ title = "#{title}...continued." if description_displayed
+ self.description_displayed = true
+ "#{escape_javascript(current_example.description)}#{title}"
end
def file_cache
diff --git a/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
index 32d736f6d..ee82f6abf 100644
--- a/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
@@ -72,19 +72,10 @@ def go_function!
"{window.hyper_spec_waiting_for_go = false}\n#{@page}"
end
- def escape_javascript(str)
- ComponentTestHelpers.escape_javascript(str)
- end
-
- def client_title!
- title =
- ComponentTestHelpers.escape_javascript(ComponentTestHelpers.current_example.description)
- title = "#{title}...continued." if ComponentTestHelpers.description_displayed
-
+ def example_title!
+ title = ComponentTestHelpers.current_example_description!
@page = "\n#{@page}"
-
- ComponentTestHelpers.description_displayed = true
end
def html_block!
@@ -113,7 +104,7 @@ def test
application! if (!server_only? && !@render_params[:layout]) || @javascript
style_sheet! if !@render_params[:layout] || @style_sheet
go_function!
- client_title! if ComponentTestHelpers.current_example
+ example_title! if ComponentTestHelpers.current_example
html_block!
deliver!
end
From a2472b2b50e542ec97f01a618aca32400c310bdd Mon Sep 17 00:00:00 2001
From: catmando
Date: Wed, 27 Jan 2021 14:02:38 -0500
Subject: [PATCH 067/307] refactored with rack and rails helpers
---
ruby/hyper-spec/lib/hyper-spec.rb | 1 +
.../lib/hyper-spec/component_test_helpers.rb | 61 ++++------
.../lib/hyper-spec/controller_helpers.rb | 115 ++++++++++++------
ruby/hyper-spec/lib/hyper-spec/rack.rb | 57 +++++++++
.../hyper-spec/rails_controller_helpers.rb | 48 ++++++++
ruby/hyper-spec/spec/hyper_spec.rb | 2 +-
6 files changed, 209 insertions(+), 75 deletions(-)
create mode 100644 ruby/hyper-spec/lib/hyper-spec/rack.rb
create mode 100644 ruby/hyper-spec/lib/hyper-spec/rails_controller_helpers.rb
diff --git a/ruby/hyper-spec/lib/hyper-spec.rb b/ruby/hyper-spec/lib/hyper-spec.rb
index 9f7ed1ea0..652a8e68a 100644
--- a/ruby/hyper-spec/lib/hyper-spec.rb
+++ b/ruby/hyper-spec/lib/hyper-spec.rb
@@ -10,6 +10,7 @@
require 'hyper-spec/component_test_helpers'
require 'hyper-spec/controller_helpers'
require 'hyper-spec/patches'
+require 'hyper-spec/rails_controller_helpers'
require 'hyper-spec/version'
require 'hyper-spec/wait_for_ajax'
require 'hyper-spec/expectations'
diff --git a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
index 18be6e402..5e63e3b88 100644
--- a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
@@ -48,51 +48,38 @@ def cache_delete(key)
end
end
- # TODO: verify this works in all cases...
- # at one time it was ApplicationController
- # then it changed to ::ActionController::Base (going to rails 5?)
- # but HyperModel has specs that depend on it being ApplicationController
- # We could use the controller param in those cases, but it seems reasonable
- # that by default we would use ApplicationController if it exists and fallback
- # to ActionController::Base
-
- def new_controller
- return ::HyperSpecTestController if defined?(::HyperSpecTestController)
-
- controller = if defined? ApplicationController
- Class.new ApplicationController
- elsif defined? ::ActionController::Base
- Class.new ::ActionController::Base
- end
+ # By default we assume we are operating in a Rails environment and will
+ # hook in using a rails controller. To override this define the
+ # HyperSpecController class in your spec helper. See the rack.rb file
+ # for an example of how to do this.
- raise raise 'No HyperSpecTestController class found' unless controller
+ def hyper_spec_test_controller
+ return ::HyperSpecTestController if defined?(::HyperSpecTestController)
- Object.const_set('HyperSpecTestController', controller)
+ base = if defined? ApplicationController
+ Class.new ApplicationController
+ elsif defined? ::ActionController::Base
+ Class.new ::ActionController::Base
+ else
+ raise "Unless using Rails you must define the HyperSpecTestController\n"\
+ 'For rack apps try requiring hyper-spec/rack.'
+ end
+ Object.const_set('HyperSpecTestController', base)
end
- def add_rails_route(route_root)
- routes = ::Rails.application.routes
- routes.disable_clear_and_finalize = true
- routes.clear!
- routes.draw { get "/#{route_root}/:id", to: "#{route_root}#test" }
- ::Rails.application.routes_reloader.paths.each { |path| load(path) }
- routes.finalize!
- ActiveSupport.on_load(:action_controller) { routes.finalize! }
- ensure
- routes.disable_clear_and_finalize = false
+ # First insure we have a controller, then make sure it responds to the test method
+ # if not, then add the rails specific controller methods. The RailsControllerHelpers
+ # module will automatically add a top level route back to the controller.
+
+ def route_root_for(controller)
+ controller ||= hyper_spec_test_controller
+ controller.include RailsControllerHelpers unless controller.method_defined?(:test)
+ controller.route_root
end
def build_test_url_for(controller = nil, ping = nil)
- controller ||= new_controller
-
- unless controller.method_defined?(:test)
- controller.include ControllerHelpers
- add_rails_route(controller.route_root)
- end
-
id = ping ? 'ping' : ComponentTestHelpers.test_id
-
- "/#{controller.route_root}/#{id}"
+ "/#{route_root_for(controller)}/#{id}"
end
def insert_html(str)
diff --git a/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
index ee82f6abf..c6acb6401 100644
--- a/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
@@ -1,10 +1,49 @@
+require 'pry'
module HyperSpec
+ # Defines a series of methods that will build a test page
+ # This module is typically included into the HyperSpecTestController class.
module ControllerHelpers
- TOP_LEVEL_COMPONENT_PATCH =
- Opal.compile(File.read(File.expand_path('../../sources/top_level_rails_component.rb', __FILE__)))
- TIME_COP_CLIENT_PATCH =
- Opal.compile(File.read(File.expand_path('../../hyper-spec/time_cop.rb', __FILE__))) +
- "\n#{File.read(File.expand_path('../../sources/lolex.js', __FILE__))}"
+
+ # These methods are dependent on the stack being used. See the
+ # RailsControllerHelpers module and rack.rb for two implementations.
+ # Each method should append the appropriate data to the @page variable
+
+ # return an empty 204 status
+ # either by setting headers or returning and appropriate response for rack.
+ def ping!
+ raise 'must implement'
+ end
+
+ # return a script or style_sheet tag pointing to the application js code.
+ # typically you be pointing to a path on the server or using
+ # sprockets to deliver the file.
+
+ def application!(_file_)
+ raise 'must implement'
+ end
+
+ def style_sheet!(_file_)
+ raise 'must implement'
+ end
+
+ # deliver the page. The @page variable will contain the html ready to go,
+ # any additional options that are passed through from the spec will be
+ # in the @render_params variable. For example layout: 'my special layout'
+
+ def deliver!
+ raise 'must implement'
+ end
+
+ # generate a react_render top level block. This will only be called if
+ # you use the mount directive in your specs, so it is optional.
+
+ def mount_component!
+ raise 'mount_component not implemented in HyperSpecTestController'
+ end
+
+ # by default the route back to the controller will be the controller name, less the
+ # word Controller, and underscored. If you want some other name redefine this
+ # method in the HyperSpecController class.
def self.included(base)
def base.route_root
@@ -19,8 +58,21 @@ def base.route_root
end
end
+ # The remainder of the methods should work for most implementations.
+
+ # helper method checking the render_on parameter
+
+ def server_only?
+ @render_on == :server_only
+ end
+
+ # The controllers behavior is kept as an array of values in the ComponentTestHelpers cache
+ # under a unique id for each test run. Grab the parameters and move them to instance vars
+
+ # If this is just a ping! Then we can just exit with nil.
+
def initialize!
- return ping! if params[:id] == 'ping'
+ return if params[:id] == 'ping'
key = "/#{self.class.route_root}/#{params[:id]}"
test_params = ComponentTestHelpers.cache_read(key)
@@ -38,16 +90,22 @@ def initialize!
@page = "\n"
end
- def ping!
- head(:no_content)
- nil
- end
+ # add any html code generated by the insert_html directive
- def mount_component!
- @page = '<%= react_component @component_name, @component_params, '\
- "{ prerender: #{@render_on != :client_only} } %>\n#{@page}"
+ def html_block!
+ @page = "\n#{@html_block}\n#{@page}"
end
+ # patch behavior of the HyperComponent TopLevelRailsComponent class
+ # so that things like events are passed back to the test harness
+ TOP_LEVEL_COMPONENT_PATCH =
+ Opal.compile(File.read(File.expand_path('../../sources/top_level_rails_component.rb', __FILE__)))
+
+ # patch time cop and lolex so they stay in sync across the client and server
+ TIME_COP_CLIENT_PATCH =
+ Opal.compile(File.read(File.expand_path('../../hyper-spec/time_cop.rb', __FILE__))) +
+ "\n#{File.read(File.expand_path('../../sources/lolex.js', __FILE__))}"
+
def client_code!
if @component_name
@page = "\n#{@page}"
@@ -59,50 +117,33 @@ def time_cop_patch!
@page = "\n#{@page}"
end
- def application!
- @page = "<%= javascript_include_tag '#{@javascript || 'application'}' %>\n#{@page}"
- end
-
- def style_sheet!
- @page = "<%= stylesheet_link_tag '#{@style_sheet || 'application'}' %>\n#{@page}"
- end
+ # Add the go_function to the client console. This is used to stop a hyper-spec pause directive.
def go_function!
@page = "\n#{@page}"
end
+ # First lines displayed on the console will be the name of the spec
+
def example_title!
title = ComponentTestHelpers.current_example_description!
@page = "\n#{@page}"
end
- def html_block!
- @page = "\n#{@html_block}\n#{@page}"
- end
-
- def deliver!
- @render_params[:inline] = @page
- response.headers['Cache-Control'] = 'max-age=120'
- response.headers['X-Tracking-ID'] = '123456'
- render @render_params
- end
-
- def server_only?
- @render_on == :server_only
- end
+ # generate each piece of the page, and then deliver it
def test
- return unless initialize!
+ return ping! unless initialize!
# TODO: reverse the the layout in the above methods so they can run in
# the right order
mount_component! if @component_name
client_code! unless server_only?
time_cop_patch! if !server_only? || Lolex.initialized?
- application! if (!server_only? && !@render_params[:layout]) || @javascript
- style_sheet! if !@render_params[:layout] || @style_sheet
+ application!(@javascript || 'application') if (!server_only? && !@render_params[:layout]) || @javascript
+ style_sheet!(@style_sheet || 'application') if !@render_params[:layout] || @style_sheet
go_function!
example_title! if ComponentTestHelpers.current_example
html_block!
diff --git a/ruby/hyper-spec/lib/hyper-spec/rack.rb b/ruby/hyper-spec/lib/hyper-spec/rack.rb
new file mode 100644
index 000000000..9d18f3139
--- /dev/null
+++ b/ruby/hyper-spec/lib/hyper-spec/rack.rb
@@ -0,0 +1,57 @@
+require 'hyper-spec'
+
+class HyperSpecTestController < SimpleDelegator
+ include HyperSpec::ControllerHelpers
+
+ class << self
+ attr_reader :sprocket_server
+ attr_reader :asset_path
+
+ def wrap(app:, append_path: 'app', asset_path: '/assets')
+ @sprocket_server = Opal::Sprockets::Server.new do |s|
+ s.append_path append_path
+ end
+
+ @asset_path = asset_path
+
+ ::Rack::Builder.app(app) do
+ map "/#{HyperSpecTestController.route_root}" do
+ use HyperSpecTestController
+ end
+ end
+ end
+ end
+
+ def sprocket_server
+ self.class.sprocket_server
+ end
+
+ def asset_path
+ self.class.asset_path
+ end
+
+ def ping!
+ [204, {}, []]
+ end
+
+ def application!(file)
+ @page = Opal::Sprockets.javascript_include_tag(
+ file,
+ debug: true,
+ sprockets: sprocket_server.sprockets,
+ prefix: asset_path
+ ) + "\n#{@page}"
+ end
+
+ def style_sheet!(_file_); end
+
+ def deliver!
+ [200, { 'Content-Type' => 'text/html' }, [@page]]
+ end
+
+ def call(env)
+ __setobj__(Rack::Request.new(env))
+ params[:id] = path.split('/').last
+ test
+ end
+end
diff --git a/ruby/hyper-spec/lib/hyper-spec/rails_controller_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/rails_controller_helpers.rb
new file mode 100644
index 000000000..9e0c4e870
--- /dev/null
+++ b/ruby/hyper-spec/lib/hyper-spec/rails_controller_helpers.rb
@@ -0,0 +1,48 @@
+module HyperSpec
+ module RailsControllerHelpers
+ def self.included(base)
+ base.include ControllerHelpers
+ base.include Helpers
+ routes = ::Rails.application.routes
+ routes.disable_clear_and_finalize = true
+ routes.clear!
+ routes.draw { get "/#{base.route_root}/:id", to: "#{base.route_root}#test" }
+ ::Rails.application.routes_reloader.paths.each { |path| load(path) }
+ routes.finalize!
+ ActiveSupport.on_load(:action_controller) { routes.finalize! }
+ ensure
+ routes.disable_clear_and_finalize = false
+ end
+
+ module Helpers
+ def ping!
+ head(:no_content)
+ nil
+ end
+
+ def mount_component!
+ @page = '<%= react_component @component_name, @component_params, '\
+ "{ prerender: #{@render_on != :client_only} } %>\n#{@page}"
+ end
+
+ def application!(file)
+ @page = "<%= javascript_include_tag '#{file}' %>\n#{@page}"
+ end
+
+ def style_sheet!(file)
+ @page = "<%= stylesheet_link_tag '#{file}' %>\n#{@page}"
+ end
+
+ def deliver!
+ @render_params[:inline] = @page
+ response.headers['Cache-Control'] = 'max-age=120'
+ response.headers['X-Tracking-ID'] = '123456'
+ render @render_params
+ end
+
+ def server_only?
+ @render_on == :server_only
+ end
+ end
+ end
+end
diff --git a/ruby/hyper-spec/spec/hyper_spec.rb b/ruby/hyper-spec/spec/hyper_spec.rb
index 4361dba41..68c7d2e03 100644
--- a/ruby/hyper-spec/spec/hyper_spec.rb
+++ b/ruby/hyper-spec/spec/hyper_spec.rb
@@ -227,7 +227,7 @@ class StyledDiv
end
end
- context "new style rspec expressions" do
+ context "new style rspec expressions", no_reset: true do
before(:each) do
@str = 'hello'
From 5c3d3454b14c2df953159d9a61518fa362614d0a Mon Sep 17 00:00:00 2001
From: catmando
Date: Wed, 27 Jan 2021 21:18:17 -0500
Subject: [PATCH 068/307] easy to run rackup refactor complete
---
ruby/hyper-i18n/hyper-i18n.gemspec | 1 +
ruby/hyper-spec/hyper-spec.gemspec | 3 +-
.../lib/hyper-spec/controller_helpers.rb | 65 +++++++++++--------
ruby/hyper-spec/lib/hyper-spec/rack.rb | 14 +++-
.../hyper-spec/rails_controller_helpers.rb | 8 +--
.../hyperstack-config.gemspec | 1 +
6 files changed, 58 insertions(+), 34 deletions(-)
diff --git a/ruby/hyper-i18n/hyper-i18n.gemspec b/ruby/hyper-i18n/hyper-i18n.gemspec
index 790778bfd..d7a7e8051 100644
--- a/ruby/hyper-i18n/hyper-i18n.gemspec
+++ b/ruby/hyper-i18n/hyper-i18n.gemspec
@@ -31,6 +31,7 @@ Gem::Specification.new do |spec|
spec.add_development_dependency 'puma'
spec.add_development_dependency 'rake', '~> 10.0'
spec.add_development_dependency 'rspec'
+ spec.add_development_dependency 'rspec-rails'
spec.add_development_dependency 'rubocop', '~> 0.51.0'
spec.add_development_dependency 'sqlite3', '~> 1.4.2' # see https://github.com/rails/rails/issues/35153
end
diff --git a/ruby/hyper-spec/hyper-spec.gemspec b/ruby/hyper-spec/hyper-spec.gemspec
index 2018b1fc2..911b673fc 100644
--- a/ruby/hyper-spec/hyper-spec.gemspec
+++ b/ruby/hyper-spec/hyper-spec.gemspec
@@ -33,7 +33,7 @@ Gem::Specification.new do |spec| # rubocop:disable Metrics/BlockLength
spec.add_dependency 'mini_racer', '~> 0.2.6'
spec.add_dependency 'opal', ENV['OPAL_VERSION'] || '>= 0.11.0', '< 2.0'
spec.add_dependency 'parser', '>= 2.3.3.1' # on rails-6 this is now >= 2.3
- spec.add_dependency 'rspec-rails'
+ spec.add_dependency 'rspec'
spec.add_dependency 'selenium-webdriver'
spec.add_dependency 'timecop', '~> 0.8.1'
spec.add_dependency 'uglifier'
@@ -50,6 +50,7 @@ Gem::Specification.new do |spec| # rubocop:disable Metrics/BlockLength
spec.add_development_dependency 'rails', ENV['RAILS_VERSION'] || '>= 5.0.0', '< 7.0'
spec.add_development_dependency 'rake'
spec.add_development_dependency 'react-rails', '>= 2.3.0', '< 2.5.0'
+ spec.add_development_dependency 'rspec-rails'
spec.add_development_dependency 'rspec-collection_matchers'
spec.add_development_dependency 'rspec-expectations'
spec.add_development_dependency 'rspec-its'
diff --git a/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
index c6acb6401..e2d864716 100644
--- a/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
@@ -1,9 +1,7 @@
-require 'pry'
module HyperSpec
# Defines a series of methods that will build a test page
# This module is typically included into the HyperSpecTestController class.
module ControllerHelpers
-
# These methods are dependent on the stack being used. See the
# RailsControllerHelpers module and rack.rb for two implementations.
# Each method should append the appropriate data to the @page variable
@@ -14,11 +12,16 @@ def ping!
raise 'must implement'
end
- # return a script or style_sheet tag pointing to the application js code.
+ def json!
+ # this can be a no-op but if json included by the application,
+ # hyper-spec will fail, with an error complaining about to_json
+ end
+
+ # return a script or style_sheet tag pointing to some asset.
# typically you be pointing to a path on the server or using
# sprockets to deliver the file.
- def application!(_file_)
+ def require!(_file_)
raise 'must implement'
end
@@ -62,8 +65,8 @@ def base.route_root
# helper method checking the render_on parameter
- def server_only?
- @render_on == :server_only
+ def on_client?
+ @render_on != :server_only
end
# The controllers behavior is kept as an array of values in the ComponentTestHelpers cache
@@ -87,66 +90,74 @@ def initialize!
@javascript = @render_params.delete(:javascript)
@code = @render_params.delete(:code)
- @page = "\n"
+ @page = ['']
end
# add any html code generated by the insert_html directive
def html_block!
- @page = "\n#{@html_block}\n#{@page}"
+ @page << @html_block
end
# patch behavior of the HyperComponent TopLevelRailsComponent class
# so that things like events are passed back to the test harness
TOP_LEVEL_COMPONENT_PATCH =
- Opal.compile(File.read(File.expand_path('../../sources/top_level_rails_component.rb', __FILE__)))
+ Opal.compile(File.read(File.expand_path('../sources/top_level_rails_component.rb', __dir__)))
# patch time cop and lolex so they stay in sync across the client and server
TIME_COP_CLIENT_PATCH =
- Opal.compile(File.read(File.expand_path('../../hyper-spec/time_cop.rb', __FILE__))) +
- "\n#{File.read(File.expand_path('../../sources/lolex.js', __FILE__))}"
+ Opal.compile(File.read(File.expand_path('../hyper-spec/time_cop.rb', __dir__))) +
+ "\n#{File.read(File.expand_path('../sources/lolex.js', __dir__))}"
def client_code!
if @component_name
- @page = "\n#{@page}"
+ @page << ""
end
- @page = "\n#{@page}" if @code
+ @page << "" if @code
end
def time_cop_patch!
- @page = "\n#{@page}"
+ @page << ""
end
# Add the go_function to the client console. This is used to stop a hyper-spec pause directive.
def go_function!
- @page = "\n#{@page}"
+ @page << "'
end
# First lines displayed on the console will be the name of the spec
def example_title!
title = ComponentTestHelpers.current_example_description!
- @page = "\n#{@page}"
+ @page << ""
end
# generate each piece of the page, and then deliver it
+ def style_sheet_file
+ @style_sheet || (!@render_params[:layout] && 'application')
+ end
+
+ def application_file
+ @javascript || (on_client? && !@render_params[:layout] && 'application')
+ end
+
def test
return ping! unless initialize!
- # TODO: reverse the the layout in the above methods so they can run in
- # the right order
- mount_component! if @component_name
- client_code! unless server_only?
- time_cop_patch! if !server_only? || Lolex.initialized?
- application!(@javascript || 'application') if (!server_only? && !@render_params[:layout]) || @javascript
- style_sheet!(@style_sheet || 'application') if !@render_params[:layout] || @style_sheet
- go_function!
- example_title! if ComponentTestHelpers.current_example
html_block!
+ example_title! if ComponentTestHelpers.current_example
+ go_function! if on_client?
+ style_sheet!(style_sheet_file) if style_sheet_file
+ application!(application_file) if application_file
+ json! # MUST BE AFTER application_file which
+ time_cop_patch! if on_client? || Lolex.initialized?
+ client_code! if on_client?
+ mount_component! if @component_name
+ @page = @page.join("\n") + "\n\n"
deliver!
end
end
diff --git a/ruby/hyper-spec/lib/hyper-spec/rack.rb b/ruby/hyper-spec/lib/hyper-spec/rack.rb
index 9d18f3139..14fed7e37 100644
--- a/ruby/hyper-spec/lib/hyper-spec/rack.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/rack.rb
@@ -35,14 +35,24 @@ def ping!
end
def application!(file)
- @page = Opal::Sprockets.javascript_include_tag(
+ @page << Opal::Sprockets.javascript_include_tag(
file,
debug: true,
sprockets: sprocket_server.sprockets,
prefix: asset_path
- ) + "\n#{@page}"
+ )
end
+ def json!
+ @page << Opal::Sprockets.javascript_include_tag(
+ 'json',
+ debug: true,
+ sprockets: sprocket_server.sprockets,
+ prefix: asset_path
+ )
+ end
+
+
def style_sheet!(_file_); end
def deliver!
diff --git a/ruby/hyper-spec/lib/hyper-spec/rails_controller_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/rails_controller_helpers.rb
index 9e0c4e870..af953f5c0 100644
--- a/ruby/hyper-spec/lib/hyper-spec/rails_controller_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/rails_controller_helpers.rb
@@ -21,16 +21,16 @@ def ping!
end
def mount_component!
- @page = '<%= react_component @component_name, @component_params, '\
- "{ prerender: #{@render_on != :client_only} } %>\n#{@page}"
+ @page << '<%= react_component @component_name, @component_params, '\
+ "{ prerender: #{@render_on != :client_only} } %>"
end
def application!(file)
- @page = "<%= javascript_include_tag '#{file}' %>\n#{@page}"
+ @page << "<%= javascript_include_tag '#{file}' %>"
end
def style_sheet!(file)
- @page = "<%= stylesheet_link_tag '#{file}' %>\n#{@page}"
+ @page << "<%= stylesheet_link_tag '#{file}' %>"
end
def deliver!
diff --git a/ruby/hyperstack-config/hyperstack-config.gemspec b/ruby/hyperstack-config/hyperstack-config.gemspec
index 8ad3af09e..40b9621b8 100644
--- a/ruby/hyperstack-config/hyperstack-config.gemspec
+++ b/ruby/hyperstack-config/hyperstack-config.gemspec
@@ -36,6 +36,7 @@ Gem::Specification.new do |spec|
spec.add_development_dependency 'rails', ENV['RAILS_VERSION'] || '>= 5.0.0', '< 7.0'
spec.add_development_dependency 'rake'
spec.add_development_dependency 'rspec', '~> 3.7.0'
+ spec.add_development_dependency 'rspec-rails'
spec.add_development_dependency 'rubocop', '~> 0.51.0'
spec.add_development_dependency 'sqlite3', '~> 1.4.2' # see https://github.com/rails/rails/issues/35153
spec.add_development_dependency 'timecop', '~> 0.8.1'
From 74a7f81176b826514ad3ebe88172963da7773156 Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 29 Jan 2021 09:28:29 -0500
Subject: [PATCH 069/307] better no_reset handling, added to_js method
---
.travis.yml | 2 +-
ruby/hyper-spec/lib/hyper-spec.rb | 3 ++
.../lib/hyper-spec/component_test_helpers.rb | 30 ++++++++++++++++++-
3 files changed, 33 insertions(+), 2 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 9927bc5af..9bee9afb7 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -25,7 +25,7 @@ _test_gem: &_test_gem
# must remove this zombie for new yarn to work
- sudo rm -f /usr/local/bin/yarn
- nvm install 10
- - rvm install 2.5.1
+ - rvm install 2.6.3 # was 2.5.1
- gem install bundler
- ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
before_script:
diff --git a/ruby/hyper-spec/lib/hyper-spec.rb b/ruby/hyper-spec/lib/hyper-spec.rb
index 652a8e68a..b6aa1c414 100644
--- a/ruby/hyper-spec/lib/hyper-spec.rb
+++ b/ruby/hyper-spec/lib/hyper-spec.rb
@@ -97,6 +97,9 @@ def reset_sessions!
config.before(:all, no_reset: true) do
HyperSpec.reset_between_examples = false
end
+ config.before(:all, no_reset: false) do
+ HyperSpec.reset_between_examples = true
+ end
config.after(:all) do
HyperSpec.reset_sessions! unless HyperSpec.reset_between_examples?
end
diff --git a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
index 5e63e3b88..25576ce06 100644
--- a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
@@ -137,10 +137,38 @@ def evaluate_ruby(p1 = nil, p2 = nil, p3 = nil, &block)
alias c? evaluate_ruby
- # TODO: add a compile_ruby method. refactor evaluate_ruby and expect_evaluate ruby to use common methods
+ # TODO: add a to_js method. refactor evaluate_ruby and expect_evaluate ruby to use common methods
# that process the params, and produce a ruby code string, and a resulting JS string
# compile_ruby can be useful in seeing what code opal produces...
+ def to_js(p1 = nil, p2 = nil, p3 = nil, &block)
+ insure_page_loaded
+ # TODO: better error message here...either you give us a block
+ # or first argument must be a hash or a string.
+ if p1.is_a? Hash
+ str = ''
+ p3 = p2
+ p2 = p1
+ else
+ str = p1
+ end
+ if p3
+ opts = p2
+ args = p3
+ elsif p2
+ opts = {}
+ args = p2
+ else
+ opts = args = {}
+ end
+
+ args.each do |name, value|
+ str = "#{set_local_var(name, value)}\n#{str}"
+ end
+ str = add_opal_block(str, block) if block
+ opal_compile(str)
+ end
+
def expect_evaluate_ruby(p1 = nil, p2 = nil, p3 = nil, &block)
insure_page_loaded
if p1.is_a? Hash
From 3e3b62b1ac0cc21e95428e352ce094e5365beaf6 Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 29 Jan 2021 09:49:49 -0500
Subject: [PATCH 070/307] travis unique errors working around
---
ruby/hyper-spec/lib/hyper-spec.rb | 11 +++++++++++
1 file changed, 11 insertions(+)
diff --git a/ruby/hyper-spec/lib/hyper-spec.rb b/ruby/hyper-spec/lib/hyper-spec.rb
index b6aa1c414..d22ab308b 100644
--- a/ruby/hyper-spec/lib/hyper-spec.rb
+++ b/ruby/hyper-spec/lib/hyper-spec.rb
@@ -24,6 +24,17 @@
nil
end
+module Capybara
+ module Selenium
+ module DeprecationSuppressor
+ def deprecate(*args, &block)
+ puts "!!!!!!!!!!!!DEPRECATION MESSAGE: #{args}"
+ super unless @suppress_for_capybara
+ end
+ end
+ end
+end
+
Parser::Builders::Default.emit_procarg0 = true
# not available in parser 2.3
From 8ffd0c74b50eddf83315704176357bc12776c105 Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 29 Jan 2021 09:58:29 -0500
Subject: [PATCH 071/307] travis unique errors working around round 2
---
ruby/hyper-spec/lib/hyper-spec.rb | 18 ++++++++++++------
1 file changed, 12 insertions(+), 6 deletions(-)
diff --git a/ruby/hyper-spec/lib/hyper-spec.rb b/ruby/hyper-spec/lib/hyper-spec.rb
index d22ab308b..d8ab0277a 100644
--- a/ruby/hyper-spec/lib/hyper-spec.rb
+++ b/ruby/hyper-spec/lib/hyper-spec.rb
@@ -24,12 +24,18 @@
nil
end
-module Capybara
- module Selenium
- module DeprecationSuppressor
- def deprecate(*args, &block)
- puts "!!!!!!!!!!!!DEPRECATION MESSAGE: #{args}"
- super unless @suppress_for_capybara
+module Selenium
+ module WebDriver
+ class Logger
+ def deprecate(old, new = nil, **)
+ message = +"[DEPRECATION] #{old} is deprecated"
+ message << if new
+ ". Use #{new} instead."
+ else
+ ' and will be removed in the next releases.'
+ end
+
+ warn message
end
end
end
From a1b2080370f2bbfd45d87a07516b204abff3ebc6 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 2 Feb 2021 12:57:15 -0500
Subject: [PATCH 072/307] removed hard dependencies on libv8 and mini_racer
---
ruby/hyper-component/hyper-component.gemspec | 4 ++--
.../spec/client_features/dsl_spec.rb | 6 +++---
.../spec/client_features/element_spec.rb | 2 +-
.../spec/client_features/server_spec.rb | 2 +-
.../spec/client_features/state_spec.rb | 2 +-
.../isomorphic/isomorphic_helpers_spec.rb | 6 +++---
.../isomorphic/rails/component_mount_spec.rb | 2 +-
.../contextual_renderer_spec.rb | 2 +-
ruby/hyper-component/spec/spec_helper.rb | 12 +++++++++++
ruby/hyper-i18n/hyper-i18n.gemspec | 1 +
ruby/hyper-i18n/spec/hyper_i18n_spec.rb | 2 +-
ruby/hyper-i18n/spec/spec_helper.rb | 12 +++++++++++
ruby/hyper-model/hyper-model.gemspec | 1 +
.../spec/batch3/aaa_edge_cases_spec.rb | 4 ++--
ruby/hyper-model/spec/spec_helper.rb | 21 +++++++++++++++++++
.../config/initializers/synchromesh.rb | 20 ------------------
.../spec/hyper-router/basic_dsl_spec.rb | 2 +-
ruby/hyper-router/spec/spec_helper.rb | 11 ++++++++++
.../config/initializers/hyperstack.rb | 3 ---
ruby/hyper-spec/hyper-spec.gemspec | 2 +-
ruby/hyper-spec/spec/hyper_spec.rb | 2 +-
ruby/hyper-spec/spec/spec_helper.rb | 11 ++++++++++
ruby/hyper-state/hyper-state.gemspec | 2 +-
ruby/hyper-store/hyper-store.gemspec | 2 +-
.../hyperstack-config.gemspec | 2 +-
ruby/rails-hyperstack/lib/rails-hyperstack.rb | 2 +-
.../rails-hyperstack/rails-hyperstack.gemspec | 4 ++--
27 files changed, 94 insertions(+), 48 deletions(-)
delete mode 100644 ruby/hyper-model/spec/test_app/config/initializers/synchromesh.rb
delete mode 100644 ruby/hyper-router/spec/test_app/config/initializers/hyperstack.rb
diff --git a/ruby/hyper-component/hyper-component.gemspec b/ruby/hyper-component/hyper-component.gemspec
index 49296406d..fd1a06bc5 100644
--- a/ruby/hyper-component/hyper-component.gemspec
+++ b/ruby/hyper-component/hyper-component.gemspec
@@ -23,12 +23,12 @@ Gem::Specification.new do |spec|
spec.add_dependency 'hyper-state', Hyperstack::Component::VERSION
spec.add_dependency 'hyperstack-config', Hyperstack::Component::VERSION
- spec.add_dependency 'libv8', '~> 7.3.492.27.1'
- spec.add_dependency 'mini_racer', '~> 0.2.6'
+ # spec.add_dependency 'libv8', '~> 7.3.492.27.1'
spec.add_dependency 'opal-activesupport', '~> 0.3.1'
spec.add_dependency 'react-rails', '>= 2.4.0', '< 2.5.0'
spec.add_development_dependency 'bundler'
+ spec.add_development_dependency 'mini_racer', '~> 0.2.6'
spec.add_development_dependency 'chromedriver-helper'
spec.add_development_dependency 'hyper-spec', Hyperstack::Component::VERSION
spec.add_development_dependency 'jquery-rails'
diff --git a/ruby/hyper-component/spec/client_features/dsl_spec.rb b/ruby/hyper-component/spec/client_features/dsl_spec.rb
index 590a38d34..16c996d21 100644
--- a/ruby/hyper-component/spec/client_features/dsl_spec.rb
+++ b/ruby/hyper-component/spec/client_features/dsl_spec.rb
@@ -55,7 +55,7 @@ class Foo
expect(page.body[-60..-19]).to include('
hello
')
end
- it "in prerender will pass converted props through event handlers" do
+ it "in prerender will pass converted props through event handlers", :prerendering_on do
client_option render_on: :both
mount 'Foo' do
class Foo
@@ -94,7 +94,7 @@ class Foo
expect(page.body[-70..-19]).to include('
hellogoodby
')
end
- it "in prerendering has a .br short hand String method" do
+ it "in prerendering has a .br short hand String method", :prerendering_on do
client_option render_on: :server_only
client_option raise_on_js_errors: :off
mount 'Foo' do
@@ -186,7 +186,7 @@ class Comp; end
.to match(/Comp does not appear to be a react component./)
end
- it 'raises a method missing error' do
+ it 'raises a method missing error', :prerendering_on do
client_option render_on: :both
client_option raise_on_js_errors: :off
expect_evaluate_ruby do
diff --git a/ruby/hyper-component/spec/client_features/element_spec.rb b/ruby/hyper-component/spec/client_features/element_spec.rb
index b4390dc28..1ba9c8eac 100644
--- a/ruby/hyper-component/spec/client_features/element_spec.rb
+++ b/ruby/hyper-component/spec/client_features/element_spec.rb
@@ -18,7 +18,7 @@
end
describe "Event Subscription" do
- it "keeps the original params, and ignores false, nil, and blank event names" do
+ it "keeps the original params, and ignores false, nil, and blank event names", :prerendering_on do
client_option render_on: :both
mount 'Foo' do
class Foo
diff --git a/ruby/hyper-component/spec/client_features/server_spec.rb b/ruby/hyper-component/spec/client_features/server_spec.rb
index 6ff1774f8..d57c05b2f 100644
--- a/ruby/hyper-component/spec/client_features/server_spec.rb
+++ b/ruby/hyper-component/spec/client_features/server_spec.rb
@@ -1,6 +1,6 @@
require "spec_helper"
-describe 'React::Server', js: true do
+describe 'React::Server', :js, :prerendering_on do
describe "render_to_string" do
it "should render a React.Element to string" do
diff --git a/ruby/hyper-component/spec/client_features/state_spec.rb b/ruby/hyper-component/spec/client_features/state_spec.rb
index 3c0a6db35..e3dacde8f 100644
--- a/ruby/hyper-component/spec/client_features/state_spec.rb
+++ b/ruby/hyper-component/spec/client_features/state_spec.rb
@@ -16,7 +16,7 @@ class << self
end.to eq('bar')
end
- it 'ignores state updates during rendering' do
+ it 'ignores state updates during rendering', :prerendering_on do
client_option render_on: :both
evaluate_ruby do
class StateTest < Hyperloop::Component
diff --git a/ruby/hyper-component/spec/isomorphic/isomorphic_helpers_spec.rb b/ruby/hyper-component/spec/isomorphic/isomorphic_helpers_spec.rb
index 35eb380e9..f12b0bf3a 100644
--- a/ruby/hyper-component/spec/isomorphic/isomorphic_helpers_spec.rb
+++ b/ruby/hyper-component/spec/isomorphic/isomorphic_helpers_spec.rb
@@ -132,7 +132,7 @@ def self.valediction
end
]}
- it 'raises an error when react cannot be loaded' do
+ it 'raises an error when react cannot be loaded', :prerendering_on do
context = described_class.new('unique-id', v8_context, controller, name)
context.instance_variable_set(:@ctx, test_context)
expect {
@@ -140,7 +140,7 @@ def self.valediction
}.to raise_error(/No Hyperstack components found/)
end
- it 'executes method with args inside opal rubyracer context' do
+ it 'executes method with args inside opal rubyracer context', :prerendering_on do
ctx = react_context
context = described_class.new('unique-id', ctx, controller, name)
context.eval(opal_code)
@@ -148,7 +148,7 @@ def self.valediction
expect(result).to eq('Hello, world!')
end
- it 'executes the method inside opal rubyracer context' do
+ it 'executes the method inside opal rubyracer context', :prerendering_on do
ctx = react_context
context = described_class.new('unique-id', ctx, controller, name)
context.eval(opal_code)
diff --git a/ruby/hyper-component/spec/isomorphic/rails/component_mount_spec.rb b/ruby/hyper-component/spec/isomorphic/rails/component_mount_spec.rb
index 42470e37f..44b89a824 100644
--- a/ruby/hyper-component/spec/isomorphic/rails/component_mount_spec.rb
+++ b/ruby/hyper-component/spec/isomorphic/rails/component_mount_spec.rb
@@ -13,7 +13,7 @@
expect(html).to match(/<\/div>/)
end
- it 'accepts a pre-render option' do
+ it 'accepts a pre-render option', :prerendering_on do
html = helper.react_component('Components::HelloWorld', {}, prerender: true)
expect(html).to match(/Hello, World!<\/span><\/div>/)
end
diff --git a/ruby/hyper-component/spec/isomorphic/server_rendering/contextual_renderer_spec.rb b/ruby/hyper-component/spec/isomorphic/server_rendering/contextual_renderer_spec.rb
index 9d11a2133..91d2e689c 100644
--- a/ruby/hyper-component/spec/isomorphic/server_rendering/contextual_renderer_spec.rb
+++ b/ruby/hyper-component/spec/isomorphic/server_rendering/contextual_renderer_spec.rb
@@ -5,7 +5,7 @@
let(:init) { Proc.new {} }
let(:options) { { context_initializer: init } }
- describe '#render' do
+ describe '#render', :prerendering_on do
it 'pre-renders HTML' do
result = renderer.render('Components.Todo',
{ todo: 'finish reactive-ruby' },
diff --git a/ruby/hyper-component/spec/spec_helper.rb b/ruby/hyper-component/spec/spec_helper.rb
index c90ce845a..711eacab6 100644
--- a/ruby/hyper-component/spec/spec_helper.rb
+++ b/ruby/hyper-component/spec/spec_helper.rb
@@ -15,6 +15,7 @@
require 'opal-browser'
require 'timecop'
+
RSpec.configure do |config|
config.color = true
config.fail_fast = ENV['FAIL_FAST'] || false
@@ -32,6 +33,17 @@
Rails.cache.clear
end
+ config.before :suite do
+ MiniRacer_Backup = MiniRacer
+ Object.send(:remove_const, :MiniRacer)
+ end
+
+ config.around(:each, :prerendering_on) do |example|
+ MiniRacer = MiniRacer_Backup
+ example.run
+ Object.send(:remove_const, :MiniRacer)
+ end
+
config.filter_run_including focus: true
config.filter_run_excluding opal: true
config.run_all_when_everything_filtered = true
diff --git a/ruby/hyper-i18n/hyper-i18n.gemspec b/ruby/hyper-i18n/hyper-i18n.gemspec
index 790778bfd..ad8298cf3 100644
--- a/ruby/hyper-i18n/hyper-i18n.gemspec
+++ b/ruby/hyper-i18n/hyper-i18n.gemspec
@@ -26,6 +26,7 @@ Gem::Specification.new do |spec|
spec.add_development_dependency 'chromedriver-helper'
spec.add_development_dependency 'hyper-model', Hyperstack::I18n::VERSION
spec.add_development_dependency 'hyper-spec', Hyperstack::I18n::VERSION
+ spec.add_development_dependency 'mini_racer'
spec.add_development_dependency 'opal-rails', '>= 0.9.4', '< 2.0.0'
spec.add_development_dependency 'pry'
spec.add_development_dependency 'puma'
diff --git a/ruby/hyper-i18n/spec/hyper_i18n_spec.rb b/ruby/hyper-i18n/spec/hyper_i18n_spec.rb
index c74e7e4fe..6a85d00c4 100644
--- a/ruby/hyper-i18n/spec/hyper_i18n_spec.rb
+++ b/ruby/hyper-i18n/spec/hyper_i18n_spec.rb
@@ -22,7 +22,7 @@ class TestComponent
end
end
[['component rendering', :client_only], ['prerendering', :server_only]].each do |mode, flag|
- it "will translate during #{mode}" do
+ it "will translate during #{mode}", prerendering_on: flag == :server_only do
mount 'Components::TestComponent', {}, render_on: flag
expect(find('#tp1')).to have_content('I am a key')
expect(find('#tp2')).to have_content('Hello world')
diff --git a/ruby/hyper-i18n/spec/spec_helper.rb b/ruby/hyper-i18n/spec/spec_helper.rb
index 9927231b8..cb505b28b 100644
--- a/ruby/hyper-i18n/spec/spec_helper.rb
+++ b/ruby/hyper-i18n/spec/spec_helper.rb
@@ -9,6 +9,18 @@
require 'hyper-i18n'
RSpec.configure do |config|
+
+ config.before :suite do
+ MiniRacer_Backup = MiniRacer
+ Object.send(:remove_const, :MiniRacer)
+ end
+
+ config.around(:each, :prerendering_on) do |example|
+ MiniRacer = MiniRacer_Backup
+ example.run
+ Object.send(:remove_const, :MiniRacer)
+ end
+
config.color = true
config.formatter = :documentation
config.before(:all) do
diff --git a/ruby/hyper-model/hyper-model.gemspec b/ruby/hyper-model/hyper-model.gemspec
index 7329a92e4..99c76614b 100644
--- a/ruby/hyper-model/hyper-model.gemspec
+++ b/ruby/hyper-model/hyper-model.gemspec
@@ -33,6 +33,7 @@ Gem::Specification.new do |spec|
spec.add_development_dependency 'database_cleaner'
spec.add_development_dependency 'factory_bot_rails'
spec.add_development_dependency 'hyper-spec', HyperModel::VERSION
+ spec.add_development_dependency 'mini_racer'
spec.add_development_dependency 'mysql2'
spec.add_development_dependency 'opal-rails', '>= 0.9.4', '< 2.0'
spec.add_development_dependency 'pry-rescue'
diff --git a/ruby/hyper-model/spec/batch3/aaa_edge_cases_spec.rb b/ruby/hyper-model/spec/batch3/aaa_edge_cases_spec.rb
index e23381c5e..768adce75 100644
--- a/ruby/hyper-model/spec/batch3/aaa_edge_cases_spec.rb
+++ b/ruby/hyper-model/spec/batch3/aaa_edge_cases_spec.rb
@@ -45,7 +45,7 @@
end
- it "prerenders a belongs to relationship" do
+ it "prerenders a belongs to relationship", :prerendering_on do
# must be first otherwise check for ajax fails because of race condition
# with previous test
user_item = User.create(name: 'Fred')
@@ -86,7 +86,7 @@ class PrerenderTest < HyperComponent
end.to eq(1)
end
- it "fetches data during prerendering" do
+ it "fetches data during prerendering", :prerendering_on do
5.times do |i|
FactoryBot.create(:todo, title: "Todo #{i}")
end
diff --git a/ruby/hyper-model/spec/spec_helper.rb b/ruby/hyper-model/spec/spec_helper.rb
index 378895490..fe04f7b01 100644
--- a/ruby/hyper-model/spec/spec_helper.rb
+++ b/ruby/hyper-model/spec/spec_helper.rb
@@ -26,6 +26,27 @@ def self.log_import(s)
end
end
+ config.before :suite do
+ # grab the prerendered .js file, for debugging purposes
+ class MiniRacer::Context
+ alias original_eval eval
+ def eval(str, options = nil)
+ original_eval str, options
+ rescue Exception => e
+ File.write('react_prerendering_src.js', str) rescue nil
+ raise e
+ end
+ end
+ MiniRacer_Backup = MiniRacer
+ Object.send(:remove_const, :MiniRacer)
+ end
+
+ config.around(:each, :prerendering_on) do |example|
+ MiniRacer = MiniRacer_Backup
+ example.run
+ Object.send(:remove_const, :MiniRacer)
+ end
+
config.color = true
config.fail_fast = ENV['FAIL_FAST'] || false
config.fixture_path = File.join(File.expand_path(File.dirname(__FILE__)), "fixtures")
diff --git a/ruby/hyper-model/spec/test_app/config/initializers/synchromesh.rb b/ruby/hyper-model/spec/test_app/config/initializers/synchromesh.rb
deleted file mode 100644
index 8d6858222..000000000
--- a/ruby/hyper-model/spec/test_app/config/initializers/synchromesh.rb
+++ /dev/null
@@ -1,20 +0,0 @@
-# require 'pusher'
-# Pusher.app_id = "MY_TEST_ID"
-# Pusher.key = "MY_TEST_KEY"
-# Pusher.secret = "MY_TEST_SECRET"
-# require 'pusher-fake'
-#
-# HyperMesh.configuration do |config|
-# config.transport = :pusher
-# config.channel_prefix = "synchromesh"
-# config.opts = {app_id: Pusher.app_id, key: Pusher.key, secret: Pusher.secret}.merge(PusherFake.configuration.web_options)
-# end
-class MiniRacer::Context
- alias original_eval eval
- def eval(str, options=nil)
- original_eval str, options
- rescue Exception => e
- File.write('react_prerendering_src.js', str) rescue nil
- raise e
- end
-end
diff --git a/ruby/hyper-router/spec/hyper-router/basic_dsl_spec.rb b/ruby/hyper-router/spec/hyper-router/basic_dsl_spec.rb
index b40a81785..b3635b056 100644
--- a/ruby/hyper-router/spec/hyper-router/basic_dsl_spec.rb
+++ b/ruby/hyper-router/spec/hyper-router/basic_dsl_spec.rb
@@ -20,7 +20,7 @@
end
[:server_only, :client_only].each do |render_on|
- it "a routers render method can return a string (#{render_on})" do
+ it "a routers render method can return a string (#{render_on})", prerendering_on: render_on == :server_only do
client_option render_on: render_on
mount 'SimpleStringRouter'
expect(page).to have_content('a simple string')
diff --git a/ruby/hyper-router/spec/spec_helper.rb b/ruby/hyper-router/spec/spec_helper.rb
index 6fbe79626..b600a261c 100644
--- a/ruby/hyper-router/spec/spec_helper.rb
+++ b/ruby/hyper-router/spec/spec_helper.rb
@@ -16,6 +16,17 @@
RSpec.configure do |config|
+ config.before :suite do
+ MiniRacer_Backup = MiniRacer
+ Object.send(:remove_const, :MiniRacer)
+ end
+
+ config.around(:each, :prerendering_on) do |example|
+ MiniRacer = MiniRacer_Backup
+ example.run
+ Object.send(:remove_const, :MiniRacer)
+ end
+
config.after :each do
Rails.cache.clear
end
diff --git a/ruby/hyper-router/spec/test_app/config/initializers/hyperstack.rb b/ruby/hyper-router/spec/test_app/config/initializers/hyperstack.rb
deleted file mode 100644
index a70c483de..000000000
--- a/ruby/hyper-router/spec/test_app/config/initializers/hyperstack.rb
+++ /dev/null
@@ -1,3 +0,0 @@
-Hyperstack.configuration do |config|
- config.prerendering = :on
-end
diff --git a/ruby/hyper-spec/hyper-spec.gemspec b/ruby/hyper-spec/hyper-spec.gemspec
index d1af270f0..573f36e6d 100644
--- a/ruby/hyper-spec/hyper-spec.gemspec
+++ b/ruby/hyper-spec/hyper-spec.gemspec
@@ -29,7 +29,6 @@ Gem::Specification.new do |spec| # rubocop:disable Metrics/BlockLength
spec.add_dependency 'filecache'
spec.add_dependency 'libv8', '~> 7.3.492.27.1'
spec.add_dependency 'method_source'
- spec.add_dependency 'mini_racer', '~> 0.2.6'
spec.add_dependency 'opal', ENV['OPAL_VERSION'] || '>= 0.11.0', '< 2.0'
spec.add_dependency 'parser', '>= 2.3.3.1' # on rails-6 this is now >= 2.3
spec.add_dependency 'rspec-rails'
@@ -41,6 +40,7 @@ Gem::Specification.new do |spec| # rubocop:disable Metrics/BlockLength
spec.add_development_dependency 'bundler'
spec.add_development_dependency 'hyper-component', HyperSpec::VERSION
+ spec.add_development_dependency 'mini_racer'
spec.add_development_dependency 'opal-browser', '~> 0.2.0'
spec.add_development_dependency 'opal-rails', '>= 0.9.4'
spec.add_development_dependency 'pry-rescue'
diff --git a/ruby/hyper-spec/spec/hyper_spec.rb b/ruby/hyper-spec/spec/hyper_spec.rb
index 4361dba41..1e4dfbc9b 100644
--- a/ruby/hyper-spec/spec/hyper_spec.rb
+++ b/ruby/hyper-spec/spec/hyper_spec.rb
@@ -22,7 +22,7 @@ class ShowOff
context "the client_option method" do
- it "can render server side only" do
+ it "can render server side only", :prerendering_on do
client_option render_on: :server_only
mount 'SayHello', name: 'George'
expect(page).to have_content('Hello there George')
diff --git a/ruby/hyper-spec/spec/spec_helper.rb b/ruby/hyper-spec/spec/spec_helper.rb
index aceee18f8..413bbed44 100644
--- a/ruby/hyper-spec/spec/spec_helper.rb
+++ b/ruby/hyper-spec/spec/spec_helper.rb
@@ -44,4 +44,15 @@ def adjusted(width, height)
# config.after :each do
# Rails.cache.clear
# end
+
+ config.before :suite do
+ MiniRacer_Backup = MiniRacer
+ Object.send(:remove_const, :MiniRacer)
+ end
+
+ config.around(:each, :prerendering_on) do |example|
+ MiniRacer = MiniRacer_Backup
+ example.run
+ Object.send(:remove_const, :MiniRacer)
+ end
end
diff --git a/ruby/hyper-state/hyper-state.gemspec b/ruby/hyper-state/hyper-state.gemspec
index 3e13f9121..9ed133d8a 100644
--- a/ruby/hyper-state/hyper-state.gemspec
+++ b/ruby/hyper-state/hyper-state.gemspec
@@ -28,7 +28,7 @@ Gem::Specification.new do |spec|
spec.add_development_dependency 'hyper-component', Hyperstack::State::VERSION
spec.add_development_dependency 'hyper-spec', Hyperstack::State::VERSION
spec.add_development_dependency 'listen'
- spec.add_development_dependency 'mini_racer', '~> 0.2.4'
+ # spec.add_development_dependency 'mini_racer', '~> 0.2.4'
spec.add_development_dependency 'opal-browser', '~> 0.2.0'
spec.add_development_dependency 'opal-rails', '>= 0.9.4', '< 2.0'
spec.add_development_dependency 'pry-rescue'
diff --git a/ruby/hyper-store/hyper-store.gemspec b/ruby/hyper-store/hyper-store.gemspec
index 77a472c9d..ea3191680 100644
--- a/ruby/hyper-store/hyper-store.gemspec
+++ b/ruby/hyper-store/hyper-store.gemspec
@@ -29,7 +29,7 @@ Gem::Specification.new do |spec|
spec.add_development_dependency 'hyper-component', Hyperstack::Legacy::Store::VERSION
spec.add_development_dependency 'hyper-spec', Hyperstack::Legacy::Store::VERSION
spec.add_development_dependency 'listen'
- spec.add_development_dependency 'mini_racer', '~> 0.2.6'
+ # spec.add_development_dependency 'mini_racer', '~> 0.2.6'
spec.add_development_dependency 'opal-browser', '~> 0.2.0'
spec.add_development_dependency 'opal-rails', '>= 0.9.4', '< 2.0'
spec.add_development_dependency 'pry-rescue'
diff --git a/ruby/hyperstack-config/hyperstack-config.gemspec b/ruby/hyperstack-config/hyperstack-config.gemspec
index 8ad3af09e..4c79330c1 100644
--- a/ruby/hyperstack-config/hyperstack-config.gemspec
+++ b/ruby/hyperstack-config/hyperstack-config.gemspec
@@ -21,7 +21,7 @@ Gem::Specification.new do |spec|
spec.require_paths = ['lib']
spec.add_dependency 'listen', '~> 3.0' # for hot loader
- spec.add_dependency 'mini_racer', '~> 0.2.6'
+ # spec.add_dependency 'mini_racer', '~> 0.2.6'
spec.add_dependency 'opal', ENV['OPAL_VERSION'] || '>= 0.11.0', '< 2.0'
spec.add_dependency 'opal-browser', '~> 0.2.0'
spec.add_dependency 'uglifier'
diff --git a/ruby/rails-hyperstack/lib/rails-hyperstack.rb b/ruby/rails-hyperstack/lib/rails-hyperstack.rb
index 1a356de67..8fa1f90d0 100644
--- a/ruby/rails-hyperstack/lib/rails-hyperstack.rb
+++ b/ruby/rails-hyperstack/lib/rails-hyperstack.rb
@@ -21,11 +21,11 @@
require 'opal-rails'
require 'hyper-model'
require 'hyper-router'
+ require 'mini_racer'
rescue LoadError
end
require 'react-rails'
require 'opal-browser'
-require 'mini_racer'
require 'hyperstack/version'
class RailsHyperstack < Rails::Railtie
diff --git a/ruby/rails-hyperstack/rails-hyperstack.gemspec b/ruby/rails-hyperstack/rails-hyperstack.gemspec
index 5eaf26b30..469153b20 100644
--- a/ruby/rails-hyperstack/rails-hyperstack.gemspec
+++ b/ruby/rails-hyperstack/rails-hyperstack.gemspec
@@ -61,8 +61,8 @@ You can control how much of the stack gets installed as well:
spec.add_dependency 'opal-browser', '~> 0.2.0'
spec.add_dependency 'react-rails', '>= 2.4.0', '< 2.5.0'
- spec.add_dependency 'mini_racer', '~> 0.2.6'
- spec.add_dependency 'libv8', '~> 7.3.492.27.1'
+ # spec.add_dependency 'mini_racer', '~> 0.2.6'
+ # spec.add_dependency 'libv8', '~> 7.3.492.27.1'
spec.add_dependency 'rails', ENV['RAILS_VERSION'] || '>= 5.0.0', '< 7.0'
spec.add_development_dependency 'bundler'
From 234d14858047d4764203aa1d67c9c769a4f54e28 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 2 Feb 2021 15:56:53 -0500
Subject: [PATCH 073/307] added error message if MiniRacer is missing
---
ruby/hyper-component/hyper-component.gemspec | 2 +-
.../component/rails/server_rendering/contextual_renderer.rb | 4 ++++
2 files changed, 5 insertions(+), 1 deletion(-)
diff --git a/ruby/hyper-component/hyper-component.gemspec b/ruby/hyper-component/hyper-component.gemspec
index fd1a06bc5..4fd919aed 100644
--- a/ruby/hyper-component/hyper-component.gemspec
+++ b/ruby/hyper-component/hyper-component.gemspec
@@ -28,12 +28,12 @@ Gem::Specification.new do |spec|
spec.add_dependency 'react-rails', '>= 2.4.0', '< 2.5.0'
spec.add_development_dependency 'bundler'
- spec.add_development_dependency 'mini_racer', '~> 0.2.6'
spec.add_development_dependency 'chromedriver-helper'
spec.add_development_dependency 'hyper-spec', Hyperstack::Component::VERSION
spec.add_development_dependency 'jquery-rails'
spec.add_development_dependency 'listen'
spec.add_development_dependency 'mime-types'
+ spec.add_development_dependency 'mini_racer'
spec.add_development_dependency 'nokogiri'
spec.add_development_dependency 'opal-jquery'
spec.add_development_dependency 'opal-rails', '>= 0.9.4', '< 2.0'
diff --git a/ruby/hyper-component/lib/hyperstack/internal/component/rails/server_rendering/contextual_renderer.rb b/ruby/hyper-component/lib/hyperstack/internal/component/rails/server_rendering/contextual_renderer.rb
index 0c415e347..b9159e596 100644
--- a/ruby/hyper-component/lib/hyperstack/internal/component/rails/server_rendering/contextual_renderer.rb
+++ b/ruby/hyper-component/lib/hyperstack/internal/component/rails/server_rendering/contextual_renderer.rb
@@ -13,6 +13,10 @@ def self.context_instance_for(context)
class ContextualRenderer < React::ServerRendering::BundleRenderer
def initialize(options = {})
+ unless v8_runtime?
+ raise "Hyperstack prerendering only works with MiniRacer. Add 'mini_racer' to your Gemfile"
+ end
+
super({ files: ['hyperstack-prerender-loader.js'] }.merge(options))
ComponentLoader.new(v8_context).load
end
From 1aebde62684e3076464b8785689b20be79ff09ef Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 2 Feb 2021 16:14:02 -0500
Subject: [PATCH 074/307] removed deprecated driver_path option
---
ruby/hyper-spec/lib/hyper-spec.rb | 22 ++--------------------
1 file changed, 2 insertions(+), 20 deletions(-)
diff --git a/ruby/hyper-spec/lib/hyper-spec.rb b/ruby/hyper-spec/lib/hyper-spec.rb
index d8ab0277a..8375bfa73 100644
--- a/ruby/hyper-spec/lib/hyper-spec.rb
+++ b/ruby/hyper-spec/lib/hyper-spec.rb
@@ -24,23 +24,6 @@
nil
end
-module Selenium
- module WebDriver
- class Logger
- def deprecate(old, new = nil, **)
- message = +"[DEPRECATION] #{old} is deprecated"
- message << if new
- ". Use #{new} instead."
- else
- ' and will be removed in the next releases.'
- end
-
- warn message
- end
- end
- end
-end
-
Parser::Builders::Default.emit_procarg0 = true
# not available in parser 2.3
@@ -201,9 +184,8 @@ def self.on_server?
options.add_argument('--headless')
options.add_argument('--no-sandbox')
options.add_argument('--disable-dev-shm-usage')
- Capybara::Selenium::Driver.new(
- app, browser: :chrome, driver_path: '/usr/lib/chromium-browser/chromedriver', options: options
- )
+ Selenium::WebDriver::Chrome::Service.driver_path = '/usr/lib/chromium-browser/chromedriver'
+ Capybara::Selenium::Driver.new(app, browser: :chrome, options: options)
end
Capybara.register_driver :firefox_headless do |app|
From 883e0b71c02ed3d7dff5cd240e8933e95b2071e4 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 2 Feb 2021 16:43:14 -0500
Subject: [PATCH 075/307] include rspec/rails in rails-hyperstack dev gem set
as its no longer in hyper-spec
---
ruby/rails-hyperstack/rails-hyperstack.gemspec | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/ruby/rails-hyperstack/rails-hyperstack.gemspec b/ruby/rails-hyperstack/rails-hyperstack.gemspec
index 5eaf26b30..091860fb3 100644
--- a/ruby/rails-hyperstack/rails-hyperstack.gemspec
+++ b/ruby/rails-hyperstack/rails-hyperstack.gemspec
@@ -71,7 +71,7 @@ You can control how much of the stack gets installed as well:
spec.add_development_dependency 'pry'
spec.add_development_dependency 'puma'
spec.add_development_dependency 'bootsnap'
- spec.add_development_dependency 'rspec'
+ spec.add_development_dependency 'rspec-rails'
spec.add_development_dependency 'rubocop', '~> 0.51.0'
spec.add_development_dependency 'sqlite3', '~> 1.4' # was 1.3.6 -- see https://github.com/rails/rails/issues/35153
spec.add_development_dependency 'sass-rails', '~> 5.0'
From 0bf8d3bb3116964a2fd4c1a18a9cf99f58cf4b3e Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 2 Feb 2021 16:47:11 -0500
Subject: [PATCH 076/307] refactored and improved hyperspec
---
.travis.yml | 2 +-
ruby/hyper-i18n/hyper-i18n.gemspec | 1 +
ruby/hyper-spec/hyper-spec.gemspec | 4 +-
ruby/hyper-spec/lib/hyper-spec.rb | 102 +++--
.../lib/hyper-spec/component_test_helpers.rb | 371 ++++--------------
.../lib/hyper-spec/controller_helpers.rb | 164 ++++++++
.../hyper-spec/lib/hyper-spec/expectations.rb | 75 ++++
ruby/hyper-spec/lib/hyper-spec/patches.rb | 68 ++++
ruby/hyper-spec/lib/hyper-spec/rack.rb | 67 ++++
.../hyper-spec/rails_controller_helpers.rb | 48 +++
.../lib/hyper-spec/unparser_patch.rb | 10 -
ruby/hyper-spec/spec/hyper_spec.rb | 2 +-
.../hyperstack-config.gemspec | 1 +
.../rails-hyperstack/rails-hyperstack.gemspec | 2 +-
14 files changed, 567 insertions(+), 350 deletions(-)
create mode 100644 ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
create mode 100644 ruby/hyper-spec/lib/hyper-spec/expectations.rb
create mode 100644 ruby/hyper-spec/lib/hyper-spec/patches.rb
create mode 100644 ruby/hyper-spec/lib/hyper-spec/rack.rb
create mode 100644 ruby/hyper-spec/lib/hyper-spec/rails_controller_helpers.rb
delete mode 100644 ruby/hyper-spec/lib/hyper-spec/unparser_patch.rb
diff --git a/.travis.yml b/.travis.yml
index 9927bc5af..9bee9afb7 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -25,7 +25,7 @@ _test_gem: &_test_gem
# must remove this zombie for new yarn to work
- sudo rm -f /usr/local/bin/yarn
- nvm install 10
- - rvm install 2.5.1
+ - rvm install 2.6.3 # was 2.5.1
- gem install bundler
- ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
before_script:
diff --git a/ruby/hyper-i18n/hyper-i18n.gemspec b/ruby/hyper-i18n/hyper-i18n.gemspec
index ad8298cf3..b7d62e9bd 100644
--- a/ruby/hyper-i18n/hyper-i18n.gemspec
+++ b/ruby/hyper-i18n/hyper-i18n.gemspec
@@ -32,6 +32,7 @@ Gem::Specification.new do |spec|
spec.add_development_dependency 'puma'
spec.add_development_dependency 'rake', '~> 10.0'
spec.add_development_dependency 'rspec'
+ spec.add_development_dependency 'rspec-rails'
spec.add_development_dependency 'rubocop', '~> 0.51.0'
spec.add_development_dependency 'sqlite3', '~> 1.4.2' # see https://github.com/rails/rails/issues/35153
end
diff --git a/ruby/hyper-spec/hyper-spec.gemspec b/ruby/hyper-spec/hyper-spec.gemspec
index 573f36e6d..b86e9fce3 100644
--- a/ruby/hyper-spec/hyper-spec.gemspec
+++ b/ruby/hyper-spec/hyper-spec.gemspec
@@ -24,6 +24,7 @@ Gem::Specification.new do |spec| # rubocop:disable Metrics/BlockLength
spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
spec.require_paths = ['lib']
+ spec.add_dependency 'actionview'
spec.add_dependency 'capybara'
spec.add_dependency 'chromedriver-helper', '1.2.0'
spec.add_dependency 'filecache'
@@ -31,7 +32,7 @@ Gem::Specification.new do |spec| # rubocop:disable Metrics/BlockLength
spec.add_dependency 'method_source'
spec.add_dependency 'opal', ENV['OPAL_VERSION'] || '>= 0.11.0', '< 2.0'
spec.add_dependency 'parser', '>= 2.3.3.1' # on rails-6 this is now >= 2.3
- spec.add_dependency 'rspec-rails'
+ spec.add_dependency 'rspec'
spec.add_dependency 'selenium-webdriver'
spec.add_dependency 'timecop', '~> 0.8.1'
spec.add_dependency 'uglifier'
@@ -49,6 +50,7 @@ Gem::Specification.new do |spec| # rubocop:disable Metrics/BlockLength
spec.add_development_dependency 'rails', ENV['RAILS_VERSION'] || '>= 5.0.0', '< 7.0'
spec.add_development_dependency 'rake'
spec.add_development_dependency 'react-rails', '>= 2.3.0', '< 2.5.0'
+ spec.add_development_dependency 'rspec-rails'
spec.add_development_dependency 'rspec-collection_matchers'
spec.add_development_dependency 'rspec-expectations'
spec.add_development_dependency 'rspec-its'
diff --git a/ruby/hyper-spec/lib/hyper-spec.rb b/ruby/hyper-spec/lib/hyper-spec.rb
index 1f2c76353..8375bfa73 100644
--- a/ruby/hyper-spec/lib/hyper-spec.rb
+++ b/ruby/hyper-spec/lib/hyper-spec.rb
@@ -1,13 +1,47 @@
-require 'capybara/rspec'
+# hyper-spec
+require 'action_view'
require 'opal'
-require 'selenium-webdriver'
+require 'unparser'
+require 'method_source'
+require 'hyper-spec/time_cop.rb'
+require 'filecache'
+require 'capybara/rspec'
require 'hyper-spec/component_test_helpers'
+require 'hyper-spec/controller_helpers'
+require 'hyper-spec/patches'
+require 'hyper-spec/rails_controller_helpers'
require 'hyper-spec/version'
require 'hyper-spec/wait_for_ajax'
+require 'hyper-spec/expectations'
+require 'parser/current'
require 'selenium/web_driver/firefox/profile'
+require 'selenium-webdriver'
+
+begin
+ require 'pry'
+rescue LoadError
+ nil
+end
+
+Parser::Builders::Default.emit_procarg0 = true
+
+# not available in parser 2.3
+if Parser::Builders::Default.respond_to? :emit_arg_inside_procarg0
+ Parser::Builders::Default.emit_arg_inside_procarg0 = true
+end
module HyperSpec
+ if defined? Pry
+ # add a before eval hook to pry so we can capture the source
+ class << self
+ attr_accessor :current_pry_code_block
+ Pry.hooks.add_hook(:before_eval, 'hyper_spec_code_capture') do |code|
+ HyperSpec.current_pry_code_block = code
+ end
+ end
+ end
+
def self.reset_between_examples=(value)
RSpec.configuration.reset_between_examples = value
end
@@ -21,7 +55,8 @@ def self.reset_sessions!
end
end
-# TODO: figure out why we need this patch - its because we are on an old version of Selenium Webdriver, but why?
+# TODO: figure out why we need this patch - its because we are on an old version
+# of Selenium Webdriver, but why?
require 'selenium-webdriver'
module Selenium
@@ -33,7 +68,7 @@ module Bridge
COMMANDS.freeze
def log(type)
- data = execute :get_log, {}, {type: type.to_s}
+ data = execute :get_log, {}, type: type.to_s
Array(data).map do |l|
begin
@@ -48,10 +83,9 @@ def log(type)
end
end
-
module Capybara
class << self
- alias_method :old_reset_sessions!, :reset_sessions!
+ alias old_reset_sessions! reset_sessions!
def reset_sessions!
old_reset_sessions! if HyperSpec.reset_between_examples?
end
@@ -63,6 +97,9 @@ def reset_sessions!
config.before(:all, no_reset: true) do
HyperSpec.reset_between_examples = false
end
+ config.before(:all, no_reset: false) do
+ HyperSpec.reset_between_examples = true
+ end
config.after(:all) do
HyperSpec.reset_sessions! unless HyperSpec.reset_between_examples?
end
@@ -80,19 +117,22 @@ def reset_sessions!
config.add_setting :debugger_width, default: nil
-
config.before(:each) do
- Hyperstack.class_eval do
- def self.on_server?
- true
+ if defined?(Hyperstack)
+ Hyperstack.class_eval do
+ def self.on_server?
+ true
+ end
end
- end if defined?(Hyperstack)
+ end
# for compatibility with HyperMesh
- HyperMesh.class_eval do
- def self.on_server?
- true
+ if defined?(HyperMesh)
+ HyperMesh.class_eval do
+ def self.on_server?
+ true
+ end
end
- end if defined?(HyperMesh)
+ end
end
config.before(:each, js: true) do
@@ -112,6 +152,11 @@ def self.on_server?
# Capybara config
RSpec.configure do |config|
+ config.before(:each) do |example|
+ HyperSpec::ComponentTestHelpers.current_example = example
+ HyperSpec::ComponentTestHelpers.description_displayed = false
+ end
+
config.add_setting :wait_for_initialization_time
config.wait_for_initialization_time = 3
@@ -121,28 +166,15 @@ def self.on_server?
options = {}
options.merge!(
w3c: false,
- args: %w[auto-open-devtools-for-tabs]) #,
- #prefs: { 'devtools.open_docked' => false, "devtools.currentDockState" => "undocked", devtools: {currentDockState: :undocked} }
- #) unless ENV['NO_DEBUGGER']
- # this does not seem to work properly. Don't document this feature yet.
- # options['mobileEmulation'] = { 'deviceName' => ENV['DEVICE'].tr('-', ' ') } if ENV['DEVICE']
+ args: %w[auto-open-devtools-for-tabs]
+ )
options['mobileEmulation'] = { 'deviceName' => ENV['DEVICE'].tr('-', ' ') } if ENV['DEVICE']
- capabilities = Selenium::WebDriver::Remote::Capabilities.chrome(chromeOptions: options, 'goog:loggingPrefs' => {browser: 'ALL'})
+ capabilities = Selenium::WebDriver::Remote::Capabilities.chrome(
+ chromeOptions: options, 'goog:loggingPrefs' => { browser: 'ALL' }
+ )
Capybara::Selenium::Driver.new(app, browser: :chrome, desired_capabilities: capabilities)
end
- # Capybara.register_driver :chrome do |app|
- # options = {}
- # options.merge!(
- # args: %w[auto-open-devtools-for-tabs],
- # prefs: { 'devtools.open_docked' => false, "devtools.currentDockState" => "undocked", devtools: {currentDockState: :undocked} }
- # ) unless ENV['NO_DEBUGGER']
- # # this does not seem to work properly. Don't document this feature yet.
- # options['mobileEmulation'] = { 'deviceName' => ENV['DEVICE'].tr('-', ' ') } if ENV['DEVICE']
- # capabilities = Selenium::WebDriver::Remote::Capabilities.chrome(chromeOptions: options)
- # Capybara::Selenium::Driver.new(app, browser: :chrome, desired_capabilities: capabilities)
- # end
-
Capybara.register_driver :firefox do |app|
Capybara::Selenium::Driver.new(app, browser: :firefox)
end
@@ -152,7 +184,8 @@ def self.on_server?
options.add_argument('--headless')
options.add_argument('--no-sandbox')
options.add_argument('--disable-dev-shm-usage')
- Capybara::Selenium::Driver.new(app, browser: :chrome, :driver_path => "/usr/lib/chromium-browser/chromedriver", options: options)
+ Selenium::WebDriver::Chrome::Service.driver_path = '/usr/lib/chromium-browser/chromedriver'
+ Capybara::Selenium::Driver.new(app, browser: :chrome, options: options)
end
Capybara.register_driver :firefox_headless do |app|
@@ -184,5 +217,4 @@ def self.on_server?
when 'travis' then :chrome_headless_docker_travis
else :selenium_chrome_headless
end
-
end
diff --git a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
index 5e2e43985..25576ce06 100644
--- a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
@@ -1,110 +1,17 @@
# see component_test_helpers_spec.rb for examples
-require 'parser/current'
-require 'unparser'
-require 'hyper-spec/unparser_patch' # not present in original version of refactored hyperspec
-require 'method_source'
-begin
- require 'pry'
-rescue LoadError
- nil
-end
-require_relative '../../lib/hyper-spec/time_cop.rb'
-require 'filecache'
-
-Parser::Builders::Default.emit_procarg0 = true # not present in original version of refactored hyperspec
-if Parser::Builders::Default.respond_to? :emit_arg_inside_procarg0
- Parser::Builders::Default.emit_arg_inside_procarg0 = true # not available in parser 2.3
-end
-
-module MethodSource
- class << self
- alias original_lines_for_before_hyper_spec lines_for
- alias original_source_helper_before_hyper_spec source_helper
-
- def source_helper(source_location, name=nil)
- source_location[1] = 1 if source_location[0] == '(pry)'
- original_source_helper_before_hyper_spec source_location, name
- end
-
- def lines_for(file_name, name = nil)
- if file_name == '(pry)'
- HyperSpec.current_pry_code_block
- else
- original_lines_for_before_hyper_spec file_name, name
- end
- end
- end
-end
-
-class Object
- def opal_serialize
- nil
- end
-end
-
-class Hash
- def opal_serialize
- "{#{collect { |k, v| "#{k.opal_serialize} => #{v.opal_serialize}"}.join(', ')}}"
- end
-end
-
-class Array
- def opal_serialize
- "[#{collect { |v| v.opal_serialize }.join(', ')}]"
- end
-end
-
-[FalseClass, Float, Integer, NilClass, String, Symbol, TrueClass].each do |klass|
- klass.send(:define_method, :opal_serialize) do
- inspect
- end
-end
-
-if Gem::Version.new(RUBY_VERSION) < Gem::Version.new('2.4.0')
- [Bignum, Fixnum].each do |klass|
- klass.send(:define_method, :opal_serialize) do
- inspect
- end
- end
-end
-
-class Time
- def to_opal_expression
- "Time.parse('#{inspect}')"
- end
-end
-
module HyperSpec
-
- # add a before eval hook to pry so we can capture the source
- if defined? Pry
- class << self
- attr_accessor :current_pry_code_block
- Pry.hooks.add_hook(:before_eval, "hyper_spec_code_capture") do |code|
- HyperSpec.current_pry_code_block = code
- end
- end
- end
-
module ComponentTestHelpers
- def self.opal_compile(s)
- Opal.compile(s)
+ def self.opal_compile(str)
+ Opal.compile(str)
rescue Exception => e
- puts "puts could not compile: \n\n#{s}\n\n"
+ puts "puts could not compile: \n\n#{str}\n\n"
raise e
end
- def opal_compile(s)
- ComponentTestHelpers.opal_compile(s)
+ def opal_compile(str)
+ ComponentTestHelpers.opal_compile(str)
end
- TOP_LEVEL_COMPONENT_PATCH =
- Opal.compile(File.read(File.expand_path('../../sources/top_level_rails_component.rb', __FILE__)))
- TIME_COP_CLIENT_PATCH =
- Opal.compile(File.read(File.expand_path('../../hyper-spec/time_cop.rb', __FILE__))) +
- "\n#{File.read(File.expand_path('../../sources/lolex.js', __FILE__))}"
-
-
class << self
attr_accessor :current_example
attr_accessor :description_displayed
@@ -114,148 +21,65 @@ def test_id
@_hyperspec_private_test_id += 1
end
- def display_example_description
- ""
+ include ActionView::Helpers::JavaScriptHelper
+
+ def current_example_description!
+ title = "#{title}...continued." if description_displayed
+ self.description_displayed = true
+ "#{escape_javascript(current_example.description)}#{title}"
end
- RAILS_CACHE = false
def file_cache
@file_cache ||= FileCache.new("cache", "/tmp/hyper-spec-caches", 30, 3)
end
def cache_read(key)
- if RAILS_CACHE
- ::Rails.cache.read(key)
- else
- file_cache.get(key)
- end
+ file_cache.get(key)
end
def cache_write(key, value)
- if RAILS_CACHE
- ::Rails.cache.write(key, value)
- else
- file_cache.set(key, value)
- end
+ file_cache.set(key, value)
end
def cache_delete(key)
- if RAILS_CACHE
- ::Rails.cache.write(key, value)
- else
- file_cache.delete(key)
- end
+ file_cache.delete(key)
rescue StandardError
nil
end
end
- # TODO: verify this works in all cases...
- # at one time it was ApplicationController
- # then it changed to ::ActionController::Base (going to rails 5?)
- # but HyperModel has specs that depend on it being ApplicationController
- # We could use the controller param in those cases, but it seems reasonable
- # that by default we would use ApplicationController if it exists and fallback
- # to ActionController::Base
-
- def new_controller
- if defined? ApplicationController
- Class.new ApplicationController
- else
- Class.new ::ActionController::Base
- end
- end
+ # By default we assume we are operating in a Rails environment and will
+ # hook in using a rails controller. To override this define the
+ # HyperSpecController class in your spec helper. See the rack.rb file
+ # for an example of how to do this.
- def build_test_url_for(controller, ping = nil)
- unless controller
- unless defined?(::HyperSpecTestController)
- Object.const_set('HyperSpecTestController', new_controller)
- end
+ def hyper_spec_test_controller
+ return ::HyperSpecTestController if defined?(::HyperSpecTestController)
- controller = ::HyperSpecTestController
- end
-
- route_root = controller.name.gsub(/Controller$/, '').underscore
-
- unless controller.method_defined?(:test)
- controller.class_eval do
- define_method(:test) do
- head(:no_content) && return if params[:id] == 'ping'
- route_root = self.class.name.gsub(/Controller$/, '').underscore
- key = "/#{route_root}/#{params[:id]}"
- test_params = ComponentTestHelpers.cache_read(key)
- @component_name = test_params[0]
- @component_params = test_params[1]
- html_block = test_params[2]
- render_params = test_params[3]
- render_on = render_params.delete(:render_on) || :client_only
- _mock_time = render_params.delete(:mock_time)
- style_sheet = render_params.delete(:style_sheet)
- javascript = render_params.delete(:javascript)
- code = render_params.delete(:code)
- #page = "#{html_block}\n\n"
- page = "\n"
-
- page = '<%= react_component @component_name, @component_params, '\
- "{ prerender: #{render_on != :client_only} } %>\n#{page}" if @component_name
- #page = "\n#{page}"
- unless render_on == :server_only
- page = "\n#{page}" if @component_name
- page = "\n#{page}" if code
- end
-
- if render_on != :server_only || Lolex.initialized?
- page = "\n#{page}"
- end
-
- if (render_on != :server_only && !render_params[:layout]) || javascript
- page = "<%= javascript_include_tag '#{javascript || 'application'}' %>\n#{page}"
- end
-
- if !render_params[:layout] || style_sheet
- page = "<%= stylesheet_link_tag '#{style_sheet || 'application'}' %>\n#{page}"
- end
- page = "\n#{page}"
-
- if ComponentTestHelpers.current_example
-
- title = view_context.escape_javascript(ComponentTestHelpers.current_example.description)
- title = "#{title}...continued." if ComponentTestHelpers.description_displayed
+ base = if defined? ApplicationController
+ Class.new ApplicationController
+ elsif defined? ::ActionController::Base
+ Class.new ::ActionController::Base
+ else
+ raise "Unless using Rails you must define the HyperSpecTestController\n"\
+ 'For rack apps try requiring hyper-spec/rack.'
+ end
+ Object.const_set('HyperSpecTestController', base)
+ end
- page = "\n#{page}"
+ # First insure we have a controller, then make sure it responds to the test method
+ # if not, then add the rails specific controller methods. The RailsControllerHelpers
+ # module will automatically add a top level route back to the controller.
- ComponentTestHelpers.description_displayed = true
- end
- page = "\n#{html_block}\n#{page}"
- render_params[:inline] = page
- response.headers['Cache-Control'] = 'max-age=120'
- response.headers['X-Tracking-ID'] = '123456'
- render render_params
- end
- end
+ def route_root_for(controller)
+ controller ||= hyper_spec_test_controller
+ controller.include RailsControllerHelpers unless controller.method_defined?(:test)
+ controller.route_root
+ end
- begin
- routes = ::Rails.application.routes
- routes.disable_clear_and_finalize = true
- routes.clear!
- routes.draw do
- get "/#{route_root}/:id", to: "#{route_root}#test"
- end
- ::Rails.application.routes_reloader.paths.each { |path| load(path) }
- routes.finalize!
- ActiveSupport.on_load(:action_controller) { routes.finalize! }
- ensure
- routes.disable_clear_and_finalize = false
- end
- end
- if ping
- "/#{route_root}/ping"
- else
- "/#{route_root}/#{ComponentTestHelpers.test_id}"
- end
+ def build_test_url_for(controller = nil, ping = nil)
+ id = ping ? 'ping' : ComponentTestHelpers.test_id
+ "/#{route_root_for(controller)}/#{id}"
end
def insert_html(str)
@@ -313,10 +137,38 @@ def evaluate_ruby(p1 = nil, p2 = nil, p3 = nil, &block)
alias c? evaluate_ruby
- # TODO: add a compile_ruby method. refactor evaluate_ruby and expect_evaluate ruby to use common methods
+ # TODO: add a to_js method. refactor evaluate_ruby and expect_evaluate ruby to use common methods
# that process the params, and produce a ruby code string, and a resulting JS string
# compile_ruby can be useful in seeing what code opal produces...
+ def to_js(p1 = nil, p2 = nil, p3 = nil, &block)
+ insure_page_loaded
+ # TODO: better error message here...either you give us a block
+ # or first argument must be a hash or a string.
+ if p1.is_a? Hash
+ str = ''
+ p3 = p2
+ p2 = p1
+ else
+ str = p1
+ end
+ if p3
+ opts = p2
+ args = p3
+ elsif p2
+ opts = {}
+ args = p2
+ else
+ opts = args = {}
+ end
+
+ args.each do |name, value|
+ str = "#{set_local_var(name, value)}\n#{str}"
+ end
+ str = add_opal_block(str, block) if block
+ opal_compile(str)
+ end
+
def expect_evaluate_ruby(p1 = nil, p2 = nil, p3 = nil, &block)
insure_page_loaded
if p1.is_a? Hash
@@ -653,87 +505,4 @@ def attributes_on_client(model)
evaluate_ruby("#{model.class.name}.find(#{model.id}).attributes").symbolize_keys
end
end
-
- RSpec.configure do |config|
- config.before(:each) do |example|
- ComponentTestHelpers.current_example = example
- ComponentTestHelpers.description_displayed = false
- end
- end
-end
-
-module RSpec
- module Expectations
- class ExpectationTarget
- end
-
- module HyperSpecInstanceMethods
-
- def self.included(base)
- base.include HyperSpec::ComponentTestHelpers
- end
-
- def to_on_client(matcher, message = nil, &block)
- evaluate_client('ruby').to(matcher, message, &block)
- end
-
- alias on_client_to to_on_client
-
- def to_on_client_not(matcher, message = nil, &block)
- evaluate_client('ruby').not_to(matcher, message, &block)
- end
-
- alias on_client_to_not to_on_client_not
- alias on_client_not_to to_on_client_not
- alias to_not_on_client to_on_client_not
- alias not_to_on_client to_on_client_not
-
- def to_then(matcher, message = nil, &block)
- evaluate_client('promise').to(matcher, message, &block)
- end
-
- alias then_to to_then
-
- def to_then_not(matcher, message = nil, &block)
- evaluate_client('promise').not_to(matcher, message, &block)
- end
-
- alias then_to_not to_then_not
- alias then_not_to to_then_not
- alias to_not_then to_then_not
- alias not_to_then to_then_not
-
- private
-
- def evaluate_client(method)
- source = add_opal_block(@args_str, @target)
- value = @target.binding.eval("evaluate_#{method}(#{source.inspect}, {}, {})")
- ExpectationTarget.for(value, nil)
- end
- end
-
- class OnClientWithArgsTarget
- include HyperSpecInstanceMethods
-
- def initialize(target, args)
- unless args.is_a? Hash
- raise ExpectationNotMetError,
- "You must pass a hash of local var, value pairs to the 'with' modifier"
- end
-
- @target = target
- @args_str = args.collect do |name, value|
- set_local_var(name, value)
- end.join("\n")
- end
- end
-
- class BlockExpectationTarget < ExpectationTarget
- include HyperSpecInstanceMethods
-
- def with(args)
- OnClientWithArgsTarget.new(@target, args)
- end
- end
- end
end
diff --git a/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
new file mode 100644
index 000000000..e2d864716
--- /dev/null
+++ b/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
@@ -0,0 +1,164 @@
+module HyperSpec
+ # Defines a series of methods that will build a test page
+ # This module is typically included into the HyperSpecTestController class.
+ module ControllerHelpers
+ # These methods are dependent on the stack being used. See the
+ # RailsControllerHelpers module and rack.rb for two implementations.
+ # Each method should append the appropriate data to the @page variable
+
+ # return an empty 204 status
+ # either by setting headers or returning and appropriate response for rack.
+ def ping!
+ raise 'must implement'
+ end
+
+ def json!
+ # this can be a no-op but if json included by the application,
+ # hyper-spec will fail, with an error complaining about to_json
+ end
+
+ # return a script or style_sheet tag pointing to some asset.
+ # typically you be pointing to a path on the server or using
+ # sprockets to deliver the file.
+
+ def require!(_file_)
+ raise 'must implement'
+ end
+
+ def style_sheet!(_file_)
+ raise 'must implement'
+ end
+
+ # deliver the page. The @page variable will contain the html ready to go,
+ # any additional options that are passed through from the spec will be
+ # in the @render_params variable. For example layout: 'my special layout'
+
+ def deliver!
+ raise 'must implement'
+ end
+
+ # generate a react_render top level block. This will only be called if
+ # you use the mount directive in your specs, so it is optional.
+
+ def mount_component!
+ raise 'mount_component not implemented in HyperSpecTestController'
+ end
+
+ # by default the route back to the controller will be the controller name, less the
+ # word Controller, and underscored. If you want some other name redefine this
+ # method in the HyperSpecController class.
+
+ def self.included(base)
+ def base.route_root
+ # Implement underscore without using rails underscore, so we don't have a
+ # dependency on ActiveSupport
+ name.gsub(/Controller$/, '')
+ .gsub(/::/, '/')
+ .gsub(/([A-Z]+)([A-Z][a-z])/, '\1_\2')
+ .gsub(/([a-z\d])([A-Z])/, '\1_\2')
+ .tr('-', '_')
+ .downcase
+ end
+ end
+
+ # The remainder of the methods should work for most implementations.
+
+ # helper method checking the render_on parameter
+
+ def on_client?
+ @render_on != :server_only
+ end
+
+ # The controllers behavior is kept as an array of values in the ComponentTestHelpers cache
+ # under a unique id for each test run. Grab the parameters and move them to instance vars
+
+ # If this is just a ping! Then we can just exit with nil.
+
+ def initialize!
+ return if params[:id] == 'ping'
+
+ key = "/#{self.class.route_root}/#{params[:id]}"
+ test_params = ComponentTestHelpers.cache_read(key)
+
+ @component_name = test_params[0]
+ @component_params = test_params[1]
+ @html_block = test_params[2]
+ @render_params = test_params[3]
+ @render_on = @render_params.delete(:render_on) || :client_only
+ @_mock_time = @render_params.delete(:mock_time)
+ @style_sheet = @render_params.delete(:style_sheet)
+ @javascript = @render_params.delete(:javascript)
+ @code = @render_params.delete(:code)
+
+ @page = ['']
+ end
+
+ # add any html code generated by the insert_html directive
+
+ def html_block!
+ @page << @html_block
+ end
+
+ # patch behavior of the HyperComponent TopLevelRailsComponent class
+ # so that things like events are passed back to the test harness
+ TOP_LEVEL_COMPONENT_PATCH =
+ Opal.compile(File.read(File.expand_path('../sources/top_level_rails_component.rb', __dir__)))
+
+ # patch time cop and lolex so they stay in sync across the client and server
+ TIME_COP_CLIENT_PATCH =
+ Opal.compile(File.read(File.expand_path('../hyper-spec/time_cop.rb', __dir__))) +
+ "\n#{File.read(File.expand_path('../sources/lolex.js', __dir__))}"
+
+ def client_code!
+ if @component_name
+ @page << ""
+ end
+ @page << "" if @code
+ end
+
+ def time_cop_patch!
+ @page << ""
+ end
+
+ # Add the go_function to the client console. This is used to stop a hyper-spec pause directive.
+
+ def go_function!
+ @page << "'
+ end
+
+ # First lines displayed on the console will be the name of the spec
+
+ def example_title!
+ title = ComponentTestHelpers.current_example_description!
+ @page << ""
+ end
+
+ # generate each piece of the page, and then deliver it
+
+ def style_sheet_file
+ @style_sheet || (!@render_params[:layout] && 'application')
+ end
+
+ def application_file
+ @javascript || (on_client? && !@render_params[:layout] && 'application')
+ end
+
+ def test
+ return ping! unless initialize!
+
+ html_block!
+ example_title! if ComponentTestHelpers.current_example
+ go_function! if on_client?
+ style_sheet!(style_sheet_file) if style_sheet_file
+ application!(application_file) if application_file
+ json! # MUST BE AFTER application_file which
+ time_cop_patch! if on_client? || Lolex.initialized?
+ client_code! if on_client?
+ mount_component! if @component_name
+ @page = @page.join("\n") + "\n\n"
+ deliver!
+ end
+ end
+end
diff --git a/ruby/hyper-spec/lib/hyper-spec/expectations.rb b/ruby/hyper-spec/lib/hyper-spec/expectations.rb
new file mode 100644
index 000000000..e6a2898fd
--- /dev/null
+++ b/ruby/hyper-spec/lib/hyper-spec/expectations.rb
@@ -0,0 +1,75 @@
+# don't put this in directory lib/rspec/ as that will cause stack overflow with rails/rspec loads
+module RSpec
+ module Expectations
+ class ExpectationTarget
+ end
+
+ module HyperSpecInstanceMethods
+ def self.included(base)
+ base.include HyperSpec::ComponentTestHelpers
+ end
+
+ def to_on_client(matcher, message = nil, &block)
+ evaluate_client('ruby').to(matcher, message, &block)
+ end
+
+ alias on_client_to to_on_client
+
+ def to_on_client_not(matcher, message = nil, &block)
+ evaluate_client('ruby').not_to(matcher, message, &block)
+ end
+
+ alias on_client_to_not to_on_client_not
+ alias on_client_not_to to_on_client_not
+ alias to_not_on_client to_on_client_not
+ alias not_to_on_client to_on_client_not
+
+ def to_then(matcher, message = nil, &block)
+ evaluate_client('promise').to(matcher, message, &block)
+ end
+
+ alias then_to to_then
+
+ def to_then_not(matcher, message = nil, &block)
+ evaluate_client('promise').not_to(matcher, message, &block)
+ end
+
+ alias then_to_not to_then_not
+ alias then_not_to to_then_not
+ alias to_not_then to_then_not
+ alias not_to_then to_then_not
+
+ private
+
+ def evaluate_client(method)
+ source = add_opal_block(@args_str, @target)
+ value = @target.binding.eval("evaluate_#{method}(#{source.inspect}, {}, {})")
+ ExpectationTarget.for(value, nil)
+ end
+ end
+
+ class OnClientWithArgsTarget
+ include HyperSpecInstanceMethods
+
+ def initialize(target, args)
+ unless args.is_a? Hash
+ raise ExpectationNotMetError,
+ "You must pass a hash of local var, value pairs to the 'with' modifier"
+ end
+
+ @target = target
+ @args_str = args.collect do |name, value|
+ set_local_var(name, value)
+ end.join("\n")
+ end
+ end
+
+ class BlockExpectationTarget < ExpectationTarget
+ include HyperSpecInstanceMethods
+
+ def with(args)
+ OnClientWithArgsTarget.new(@target, args)
+ end
+ end
+ end
+end
diff --git a/ruby/hyper-spec/lib/hyper-spec/patches.rb b/ruby/hyper-spec/lib/hyper-spec/patches.rb
new file mode 100644
index 000000000..e88cc5111
--- /dev/null
+++ b/ruby/hyper-spec/lib/hyper-spec/patches.rb
@@ -0,0 +1,68 @@
+module Unparser
+ class Emitter
+ # Emitter for send
+ class Send < self
+ def local_variable_clash?
+ selector =~ /^[A-Z]/ || local_variable_scope.local_variable_defined_for_node?(node, selector)
+ end
+ end
+ end
+end
+
+module MethodSource
+ class << self
+ alias original_lines_for_before_hyper_spec lines_for
+ alias original_source_helper_before_hyper_spec source_helper
+
+ def source_helper(source_location, name=nil)
+ source_location[1] = 1 if source_location[0] == '(pry)'
+ original_source_helper_before_hyper_spec source_location, name
+ end
+
+ def lines_for(file_name, name = nil)
+ if file_name == '(pry)'
+ HyperSpec.current_pry_code_block
+ else
+ original_lines_for_before_hyper_spec file_name, name
+ end
+ end
+ end
+end
+
+class Object
+ def opal_serialize
+ nil
+ end
+end
+
+class Hash
+ def opal_serialize
+ "{#{collect { |k, v| "#{k.opal_serialize} => #{v.opal_serialize}"}.join(', ')}}"
+ end
+end
+
+class Array
+ def opal_serialize
+ "[#{collect { |v| v.opal_serialize }.join(', ')}]"
+ end
+end
+
+[FalseClass, Float, Integer, NilClass, String, Symbol, TrueClass].each do |klass|
+ klass.send(:define_method, :opal_serialize) do
+ inspect
+ end
+end
+
+if Gem::Version.new(RUBY_VERSION) < Gem::Version.new('2.4.0')
+ [Bignum, Fixnum].each do |klass|
+ klass.send(:define_method, :opal_serialize) do
+ inspect
+ end
+ end
+end
+
+class Time
+ def to_opal_expression
+ "Time.parse('#{inspect}')"
+ end
+end
diff --git a/ruby/hyper-spec/lib/hyper-spec/rack.rb b/ruby/hyper-spec/lib/hyper-spec/rack.rb
new file mode 100644
index 000000000..14fed7e37
--- /dev/null
+++ b/ruby/hyper-spec/lib/hyper-spec/rack.rb
@@ -0,0 +1,67 @@
+require 'hyper-spec'
+
+class HyperSpecTestController < SimpleDelegator
+ include HyperSpec::ControllerHelpers
+
+ class << self
+ attr_reader :sprocket_server
+ attr_reader :asset_path
+
+ def wrap(app:, append_path: 'app', asset_path: '/assets')
+ @sprocket_server = Opal::Sprockets::Server.new do |s|
+ s.append_path append_path
+ end
+
+ @asset_path = asset_path
+
+ ::Rack::Builder.app(app) do
+ map "/#{HyperSpecTestController.route_root}" do
+ use HyperSpecTestController
+ end
+ end
+ end
+ end
+
+ def sprocket_server
+ self.class.sprocket_server
+ end
+
+ def asset_path
+ self.class.asset_path
+ end
+
+ def ping!
+ [204, {}, []]
+ end
+
+ def application!(file)
+ @page << Opal::Sprockets.javascript_include_tag(
+ file,
+ debug: true,
+ sprockets: sprocket_server.sprockets,
+ prefix: asset_path
+ )
+ end
+
+ def json!
+ @page << Opal::Sprockets.javascript_include_tag(
+ 'json',
+ debug: true,
+ sprockets: sprocket_server.sprockets,
+ prefix: asset_path
+ )
+ end
+
+
+ def style_sheet!(_file_); end
+
+ def deliver!
+ [200, { 'Content-Type' => 'text/html' }, [@page]]
+ end
+
+ def call(env)
+ __setobj__(Rack::Request.new(env))
+ params[:id] = path.split('/').last
+ test
+ end
+end
diff --git a/ruby/hyper-spec/lib/hyper-spec/rails_controller_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/rails_controller_helpers.rb
new file mode 100644
index 000000000..af953f5c0
--- /dev/null
+++ b/ruby/hyper-spec/lib/hyper-spec/rails_controller_helpers.rb
@@ -0,0 +1,48 @@
+module HyperSpec
+ module RailsControllerHelpers
+ def self.included(base)
+ base.include ControllerHelpers
+ base.include Helpers
+ routes = ::Rails.application.routes
+ routes.disable_clear_and_finalize = true
+ routes.clear!
+ routes.draw { get "/#{base.route_root}/:id", to: "#{base.route_root}#test" }
+ ::Rails.application.routes_reloader.paths.each { |path| load(path) }
+ routes.finalize!
+ ActiveSupport.on_load(:action_controller) { routes.finalize! }
+ ensure
+ routes.disable_clear_and_finalize = false
+ end
+
+ module Helpers
+ def ping!
+ head(:no_content)
+ nil
+ end
+
+ def mount_component!
+ @page << '<%= react_component @component_name, @component_params, '\
+ "{ prerender: #{@render_on != :client_only} } %>"
+ end
+
+ def application!(file)
+ @page << "<%= javascript_include_tag '#{file}' %>"
+ end
+
+ def style_sheet!(file)
+ @page << "<%= stylesheet_link_tag '#{file}' %>"
+ end
+
+ def deliver!
+ @render_params[:inline] = @page
+ response.headers['Cache-Control'] = 'max-age=120'
+ response.headers['X-Tracking-ID'] = '123456'
+ render @render_params
+ end
+
+ def server_only?
+ @render_on == :server_only
+ end
+ end
+ end
+end
diff --git a/ruby/hyper-spec/lib/hyper-spec/unparser_patch.rb b/ruby/hyper-spec/lib/hyper-spec/unparser_patch.rb
deleted file mode 100644
index dc0a720b8..000000000
--- a/ruby/hyper-spec/lib/hyper-spec/unparser_patch.rb
+++ /dev/null
@@ -1,10 +0,0 @@
-module Unparser
- class Emitter
- # Emitter for send
- class Send < self
- def local_variable_clash?
- selector =~ /^[A-Z]/ || local_variable_scope.local_variable_defined_for_node?(node, selector)
- end
- end
- end
-end
diff --git a/ruby/hyper-spec/spec/hyper_spec.rb b/ruby/hyper-spec/spec/hyper_spec.rb
index 1e4dfbc9b..97f10c545 100644
--- a/ruby/hyper-spec/spec/hyper_spec.rb
+++ b/ruby/hyper-spec/spec/hyper_spec.rb
@@ -227,7 +227,7 @@ class StyledDiv
end
end
- context "new style rspec expressions" do
+ context "new style rspec expressions", no_reset: true do
before(:each) do
@str = 'hello'
diff --git a/ruby/hyperstack-config/hyperstack-config.gemspec b/ruby/hyperstack-config/hyperstack-config.gemspec
index 4c79330c1..55f0e6a08 100644
--- a/ruby/hyperstack-config/hyperstack-config.gemspec
+++ b/ruby/hyperstack-config/hyperstack-config.gemspec
@@ -36,6 +36,7 @@ Gem::Specification.new do |spec|
spec.add_development_dependency 'rails', ENV['RAILS_VERSION'] || '>= 5.0.0', '< 7.0'
spec.add_development_dependency 'rake'
spec.add_development_dependency 'rspec', '~> 3.7.0'
+ spec.add_development_dependency 'rspec-rails'
spec.add_development_dependency 'rubocop', '~> 0.51.0'
spec.add_development_dependency 'sqlite3', '~> 1.4.2' # see https://github.com/rails/rails/issues/35153
spec.add_development_dependency 'timecop', '~> 0.8.1'
diff --git a/ruby/rails-hyperstack/rails-hyperstack.gemspec b/ruby/rails-hyperstack/rails-hyperstack.gemspec
index 469153b20..b38872ea9 100644
--- a/ruby/rails-hyperstack/rails-hyperstack.gemspec
+++ b/ruby/rails-hyperstack/rails-hyperstack.gemspec
@@ -71,7 +71,7 @@ You can control how much of the stack gets installed as well:
spec.add_development_dependency 'pry'
spec.add_development_dependency 'puma'
spec.add_development_dependency 'bootsnap'
- spec.add_development_dependency 'rspec'
+ spec.add_development_dependency 'rspec-rails'
spec.add_development_dependency 'rubocop', '~> 0.51.0'
spec.add_development_dependency 'sqlite3', '~> 1.4' # was 1.3.6 -- see https://github.com/rails/rails/issues/35153
spec.add_development_dependency 'sass-rails', '~> 5.0'
From 1a8dcbfae17679e52bd7413644fb653ea8943730 Mon Sep 17 00:00:00 2001
From: catmando
Date: Wed, 3 Feb 2021 15:11:44 -0500
Subject: [PATCH 077/307] refactored and removed special promise methods
---
.../lib/hyper-spec/component_test_helpers.rb | 137 ++++++------------
.../hyper-spec/lib/hyper-spec/expectations.rb | 33 ++---
ruby/hyper-spec/lib/hyper-spec/time_cop.rb | 2 +
ruby/hyper-spec/spec/hyper_spec.rb | 5 +-
4 files changed, 60 insertions(+), 117 deletions(-)
diff --git a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
index 25576ce06..0c2ae2353 100644
--- a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
@@ -1,7 +1,8 @@
# see component_test_helpers_spec.rb for examples
module HyperSpec
module ComponentTestHelpers
- def self.opal_compile(str)
+ def self.opal_compile(str, _opts = nil)
+ # _opts allows second dummy param to be passed from to_js
Opal.compile(str)
rescue Exception => e
puts "puts could not compile: \n\n#{str}\n\n"
@@ -103,36 +104,21 @@ def set_local_var(name, object)
end
end
- def evaluate_ruby(p1 = nil, p2 = nil, p3 = nil, &block)
+ def evaluate_ruby(*args, &block)
insure_page_loaded
- # TODO: better error message here...either you give us a block
- # or first argument must be a hash or a string.
- if p1.is_a? Hash
- str = ''
- p3 = p2
- p2 = p1
- else
- str = p1
- end
- if p3
- opts = p2
- args = p3
- elsif p2
- opts = {}
- args = p2
- else
- opts = args = {}
- end
-
- args.each do |name, value|
- str = "#{set_local_var(name, value)}\n#{str}"
- end
- str = add_opal_block(str, block) if block
+ str, opts = process_params(*args, &block)
+ str = add_promise_wrapper(str)
js = opal_compile(str).gsub("// Prepare super implicit arguments\n", '')
.delete("\n").gsub('(Opal);', '(Opal)')
- # workaround for firefox 58 and geckodriver 0.19.1, because firefox is unable to find .$to_json:
- # JSON.parse(evaluate_script("(function(){var a=Opal.Array.$new(); a[0]=#{js}; return a.$to_json();})();"), opts).first
- JSON.parse(evaluate_script("[#{js}].$to_json()"), opts).first
+ page.execute_script("window.hyper_spec_promise_result = false; #{js}")
+ Timeout.timeout(Capybara.default_max_wait_time) do
+ loop do
+ break if page.evaluate_script('!!window.hyper_spec_promise_result')
+
+ sleep 0.25
+ end
+ end
+ JSON.parse(page.evaluate_script("window.hyper_spec_promise_result.$to_json()"), opts).first
end
alias c? evaluate_ruby
@@ -141,56 +127,22 @@ def evaluate_ruby(p1 = nil, p2 = nil, p3 = nil, &block)
# that process the params, and produce a ruby code string, and a resulting JS string
# compile_ruby can be useful in seeing what code opal produces...
- def to_js(p1 = nil, p2 = nil, p3 = nil, &block)
- insure_page_loaded
- # TODO: better error message here...either you give us a block
- # or first argument must be a hash or a string.
- if p1.is_a? Hash
- str = ''
- p3 = p2
- p2 = p1
- else
- str = p1
- end
- if p3
- opts = p2
- args = p3
- elsif p2
- opts = {}
- args = p2
- else
- opts = args = {}
- end
-
- args.each do |name, value|
- str = "#{set_local_var(name, value)}\n#{str}"
- end
- str = add_opal_block(str, block) if block
- opal_compile(str)
+ def to_js(*args, &block)
+ opal_compile *process_params(*args, &block)
end
- def expect_evaluate_ruby(p1 = nil, p2 = nil, p3 = nil, &block)
- insure_page_loaded
- if p1.is_a? Hash
- str = ''
- p3 = p2
- p2 = p1
- else
- str = p1
- end
- if p3
- opts = p2
- args = p3
- elsif p2
- opts = {}
- args = p2
- else
- opts = args = {}
- end
- args.each do |name, value|
+ def process_params(*args, &block)
+ args = ['', *args] if args[0].is_a? Hash
+ args = [args[0], {}, args[1] || {}] if args.length < 3
+ str, opts, vars = args
+ vars.each do |name, value|
str = "#{name} = #{value.inspect}\n#{str}"
end
- expect(evaluate_ruby(add_opal_block(str, block), opts, {}))
+ [add_opal_block(str, block), opts]
+ end
+
+ def expect_evaluate_ruby(*args, &block)
+ expect(evaluate_ruby(*args, &block))
end
PRIVATE_VARIABLES = %i[
@@ -199,6 +151,21 @@ def expect_evaluate_ruby(p1 = nil, p2 = nil, p3 = nil, &block)
b __ _ _ex_ pry_instance _out_ _in_ _dir_ _file_
]
+ def add_promise_wrapper(str)
+<
Date: Wed, 3 Feb 2021 15:54:46 -0500
Subject: [PATCH 078/307] Only look for Promise if Promise is loaded
---
ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
index 0c2ae2353..55ac9f1b1 100644
--- a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
@@ -154,7 +154,7 @@ def expect_evaluate_ruby(*args, &block)
def add_promise_wrapper(str)
<
Date: Thu, 4 Feb 2021 10:59:43 -0500
Subject: [PATCH 079/307] more refactoring, cleanup and documentation
---
ruby/hyper-spec/lib/hyper-spec.rb | 26 +-
.../lib/hyper-spec/component_test_helpers.rb | 457 ------------------
.../lib/hyper-spec/controller_helpers.rb | 20 +-
.../hyper-spec/lib/hyper-spec/expectations.rb | 2 +-
ruby/hyper-spec/lib/hyper-spec/helpers.rb | 242 ++++++++++
.../hyper-spec/internal/client_execution.rb | 133 +++++
.../hyper-spec/internal/component_mount.rb | 122 +++++
.../lib/hyper-spec/internal/controller.rb | 70 +++
.../lib/hyper-spec/{ => internal}/patches.rb | 24 +-
.../internal/rails_controller_helpers.rb | 50 ++
.../lib/hyper-spec/{ => internal}/time_cop.rb | 6 +-
.../lib/hyper-spec/internal/window_sizing.rb | 23 +
.../hyper-spec/rails_controller_helpers.rb | 48 --
ruby/hyper-spec/spec/hyper_spec.rb | 8 +-
14 files changed, 696 insertions(+), 535 deletions(-)
delete mode 100644 ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
create mode 100644 ruby/hyper-spec/lib/hyper-spec/helpers.rb
create mode 100644 ruby/hyper-spec/lib/hyper-spec/internal/client_execution.rb
create mode 100644 ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb
create mode 100644 ruby/hyper-spec/lib/hyper-spec/internal/controller.rb
rename ruby/hyper-spec/lib/hyper-spec/{ => internal}/patches.rb (61%)
create mode 100644 ruby/hyper-spec/lib/hyper-spec/internal/rails_controller_helpers.rb
rename ruby/hyper-spec/lib/hyper-spec/{ => internal}/time_cop.rb (96%)
create mode 100644 ruby/hyper-spec/lib/hyper-spec/internal/window_sizing.rb
delete mode 100644 ruby/hyper-spec/lib/hyper-spec/rails_controller_helpers.rb
diff --git a/ruby/hyper-spec/lib/hyper-spec.rb b/ruby/hyper-spec/lib/hyper-spec.rb
index 8375bfa73..720054a1c 100644
--- a/ruby/hyper-spec/lib/hyper-spec.rb
+++ b/ruby/hyper-spec/lib/hyper-spec.rb
@@ -3,21 +3,31 @@
require 'opal'
require 'unparser'
require 'method_source'
-require 'hyper-spec/time_cop.rb'
require 'filecache'
require 'capybara/rspec'
-require 'hyper-spec/component_test_helpers'
+require 'hyper-spec/internal/client_execution'
+require 'hyper-spec/internal/component_mount'
+require 'hyper-spec/internal/controller'
+require 'hyper-spec/internal/patches'
+require 'hyper-spec/internal/rails_controller_helpers'
+require 'hyper-spec/internal/time_cop.rb'
+require 'hyper-spec/internal/window_sizing'
+
require 'hyper-spec/controller_helpers'
-require 'hyper-spec/patches'
-require 'hyper-spec/rails_controller_helpers'
-require 'hyper-spec/version'
+
require 'hyper-spec/wait_for_ajax'
+
+require 'hyper-spec/helpers'
require 'hyper-spec/expectations'
+
require 'parser/current'
require 'selenium/web_driver/firefox/profile'
require 'selenium-webdriver'
+require 'hyper-spec/version'
+
+
begin
require 'pry'
rescue LoadError
@@ -109,7 +119,7 @@ def reset_sessions!
end
RSpec.configure do |config|
- config.include HyperSpec::ComponentTestHelpers
+ config.include HyperSpec::Helpers
config.include HyperSpec::WaitForAjax
config.include Capybara::DSL
@@ -153,8 +163,8 @@ def self.on_server?
# Capybara config
RSpec.configure do |config|
config.before(:each) do |example|
- HyperSpec::ComponentTestHelpers.current_example = example
- HyperSpec::ComponentTestHelpers.description_displayed = false
+ HyperSpec::Internal::Controller.current_example = example
+ HyperSpec::Internal::Controller.description_displayed = false
end
config.add_setting :wait_for_initialization_time
diff --git a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
deleted file mode 100644
index 55ac9f1b1..000000000
--- a/ruby/hyper-spec/lib/hyper-spec/component_test_helpers.rb
+++ /dev/null
@@ -1,457 +0,0 @@
-# see component_test_helpers_spec.rb for examples
-module HyperSpec
- module ComponentTestHelpers
- def self.opal_compile(str, _opts = nil)
- # _opts allows second dummy param to be passed from to_js
- Opal.compile(str)
- rescue Exception => e
- puts "puts could not compile: \n\n#{str}\n\n"
- raise e
- end
-
- def opal_compile(str)
- ComponentTestHelpers.opal_compile(str)
- end
-
- class << self
- attr_accessor :current_example
- attr_accessor :description_displayed
-
- def test_id
- @_hyperspec_private_test_id ||= 0
- @_hyperspec_private_test_id += 1
- end
-
- include ActionView::Helpers::JavaScriptHelper
-
- def current_example_description!
- title = "#{title}...continued." if description_displayed
- self.description_displayed = true
- "#{escape_javascript(current_example.description)}#{title}"
- end
-
- def file_cache
- @file_cache ||= FileCache.new("cache", "/tmp/hyper-spec-caches", 30, 3)
- end
-
- def cache_read(key)
- file_cache.get(key)
- end
-
- def cache_write(key, value)
- file_cache.set(key, value)
- end
-
- def cache_delete(key)
- file_cache.delete(key)
- rescue StandardError
- nil
- end
- end
-
- # By default we assume we are operating in a Rails environment and will
- # hook in using a rails controller. To override this define the
- # HyperSpecController class in your spec helper. See the rack.rb file
- # for an example of how to do this.
-
- def hyper_spec_test_controller
- return ::HyperSpecTestController if defined?(::HyperSpecTestController)
-
- base = if defined? ApplicationController
- Class.new ApplicationController
- elsif defined? ::ActionController::Base
- Class.new ::ActionController::Base
- else
- raise "Unless using Rails you must define the HyperSpecTestController\n"\
- 'For rack apps try requiring hyper-spec/rack.'
- end
- Object.const_set('HyperSpecTestController', base)
- end
-
- # First insure we have a controller, then make sure it responds to the test method
- # if not, then add the rails specific controller methods. The RailsControllerHelpers
- # module will automatically add a top level route back to the controller.
-
- def route_root_for(controller)
- controller ||= hyper_spec_test_controller
- controller.include RailsControllerHelpers unless controller.method_defined?(:test)
- controller.route_root
- end
-
- def build_test_url_for(controller = nil, ping = nil)
- id = ping ? 'ping' : ComponentTestHelpers.test_id
- "/#{route_root_for(controller)}/#{id}"
- end
-
- def insert_html(str)
- @_hyperspec_private_html_block = "#{@_hyperspec_private_html_block}\n#{str}"
- end
-
- def isomorphic(&block)
- yield
- before_mount(&block)
- end
-
- def set_local_var(name, object)
- serialized = object.opal_serialize
- if serialized
- "#{name} = #{serialized}"
- else
- "self.class.define_method(:#{name}) "\
- "{ raise 'Attempt to access the variable #{name} "\
- 'that was defined in the spec, but its value could not be serialized '\
- "so it is undefined on the client.' }"
- end
- end
-
- def evaluate_ruby(*args, &block)
- insure_page_loaded
- str, opts = process_params(*args, &block)
- str = add_promise_wrapper(str)
- js = opal_compile(str).gsub("// Prepare super implicit arguments\n", '')
- .delete("\n").gsub('(Opal);', '(Opal)')
- page.execute_script("window.hyper_spec_promise_result = false; #{js}")
- Timeout.timeout(Capybara.default_max_wait_time) do
- loop do
- break if page.evaluate_script('!!window.hyper_spec_promise_result')
-
- sleep 0.25
- end
- end
- JSON.parse(page.evaluate_script("window.hyper_spec_promise_result.$to_json()"), opts).first
- end
-
- alias c? evaluate_ruby
-
- # TODO: add a to_js method. refactor evaluate_ruby and expect_evaluate ruby to use common methods
- # that process the params, and produce a ruby code string, and a resulting JS string
- # compile_ruby can be useful in seeing what code opal produces...
-
- def to_js(*args, &block)
- opal_compile *process_params(*args, &block)
- end
-
- def process_params(*args, &block)
- args = ['', *args] if args[0].is_a? Hash
- args = [args[0], {}, args[1] || {}] if args.length < 3
- str, opts, vars = args
- vars.each do |name, value|
- str = "#{name} = #{value.inspect}\n#{str}"
- end
- [add_opal_block(str, block), opts]
- end
-
- def expect_evaluate_ruby(*args, &block)
- expect(evaluate_ruby(*args, &block))
- end
-
- PRIVATE_VARIABLES = %i[
- @__inspect_output @__memoized @example @_hyperspec_private_client_code @_hyperspec_private_html_block @fixture_cache
- @fixture_connections @connection_subscriber @loaded_fixtures @_hyperspec_private_client_options
- b __ _ _ex_ pry_instance _out_ _in_ _dir_ _file_
- ]
-
- def add_promise_wrapper(str)
-< 2 || stable_count_h > 2
- prev_size = curr_size
- end while (Capybara::Helpers.monotonic_time - start_time) < Capybara.current_session.config.default_max_wait_time
- raise Capybara::WindowError, "Window size not stable within #{Capybara.current_session.config.default_max_wait_time} seconds."
- end
-
- def size_window(width = nil, height = nil)
- # return if @window_cannot_be_resized
- # original_width = evaluate_script('window.innerWidth')
- # original_height = evaluate_script('window.innerHeight')
- width, height = [height, width] if width == :portrait
- width, height = width if width.is_a? Array
- portrait = true if height == :portrait
-
- case width
- when :small
- width, height = [480, 320]
- when :mobile
- width, height = [640, 480]
- when :tablet
- width, height = [960, 640]
- when :large
- width, height = [1920, 6000]
- when :default, nil
- width, height = [1024, 768]
- end
-
- width, height = [height, width] if portrait
-
- unless RSpec.configuration.debugger_width
- Capybara.current_session.current_window.resize_to(1000, 500)
- sleep RSpec.configuration.wait_for_initialization_time
- wait_for_size(1000, 500)
- inner_width = evaluate_script('window.innerWidth')
- RSpec.configuration.debugger_width = 1000 - inner_width
- end
- Capybara.current_session.current_window
- .resize_to(width + RSpec.configuration.debugger_width, height)
- wait_for_size(width + RSpec.configuration.debugger_width, height)
- rescue StandardError
- true
- end
-
- def attributes_on_client(model)
- evaluate_ruby("#{model.class.name}.find(#{model.id}).attributes").symbolize_keys
- end
- end
-end
diff --git a/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
index e2d864716..b2a6a0b4d 100644
--- a/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
@@ -4,16 +4,16 @@ module HyperSpec
module ControllerHelpers
# These methods are dependent on the stack being used. See the
# RailsControllerHelpers module and rack.rb for two implementations.
- # Each method should append the appropriate data to the @page variable
+ # Each method should append the appropriate code to the @page array
- # return an empty 204 status
- # either by setting headers or returning and appropriate response for rack.
+ # return an empty 204 status either by setting headers or
+ # returning and appropriate response for rack.
def ping!
raise 'must implement'
end
def json!
- # this can be a no-op but if json included by the application,
+ # this can be a no-op but if json is not included by the application,
# hyper-spec will fail, with an error complaining about to_json
end
@@ -69,7 +69,7 @@ def on_client?
@render_on != :server_only
end
- # The controllers behavior is kept as an array of values in the ComponentTestHelpers cache
+ # The controllers behavior is kept as an array of values in the Controller cache
# under a unique id for each test run. Grab the parameters and move them to instance vars
# If this is just a ping! Then we can just exit with nil.
@@ -78,7 +78,7 @@ def initialize!
return if params[:id] == 'ping'
key = "/#{self.class.route_root}/#{params[:id]}"
- test_params = ComponentTestHelpers.cache_read(key)
+ test_params = Internal::Controller.cache_read(key)
@component_name = test_params[0]
@component_params = test_params[1]
@@ -106,7 +106,7 @@ def html_block!
# patch time cop and lolex so they stay in sync across the client and server
TIME_COP_CLIENT_PATCH =
- Opal.compile(File.read(File.expand_path('../hyper-spec/time_cop.rb', __dir__))) +
+ Opal.compile(File.read(File.expand_path('../hyper-spec/internal/time_cop.rb', __dir__))) +
"\n#{File.read(File.expand_path('../sources/lolex.js', __dir__))}"
def client_code!
@@ -130,7 +130,7 @@ def go_function!
# First lines displayed on the console will be the name of the spec
def example_title!
- title = ComponentTestHelpers.current_example_description!
+ title = Internal::Controller.current_example_description!
@page << ""
end
@@ -149,11 +149,11 @@ def test
return ping! unless initialize!
html_block!
- example_title! if ComponentTestHelpers.current_example
+ example_title! if Internal::Controller.current_example
go_function! if on_client?
style_sheet!(style_sheet_file) if style_sheet_file
application!(application_file) if application_file
- json! # MUST BE AFTER application_file which
+ json!
time_cop_patch! if on_client? || Lolex.initialized?
client_code! if on_client?
mount_component! if @component_name
diff --git a/ruby/hyper-spec/lib/hyper-spec/expectations.rb b/ruby/hyper-spec/lib/hyper-spec/expectations.rb
index 30dfc3d37..4b2a033c6 100644
--- a/ruby/hyper-spec/lib/hyper-spec/expectations.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/expectations.rb
@@ -4,7 +4,7 @@ module Expectations
class ExpectationTarget; end
module HyperSpecInstanceMethods
def self.included(base)
- base.include HyperSpec::ComponentTestHelpers
+ base.include HyperSpec::Helpers
end
def to_on_client(matcher, message = nil, &block)
diff --git a/ruby/hyper-spec/lib/hyper-spec/helpers.rb b/ruby/hyper-spec/lib/hyper-spec/helpers.rb
new file mode 100644
index 000000000..0570bc9a2
--- /dev/null
+++ b/ruby/hyper-spec/lib/hyper-spec/helpers.rb
@@ -0,0 +1,242 @@
+module HyperSpec
+ module Helpers
+ include Internal::ClientExecution
+ include Internal::Controller
+ include Internal::ComponentMount
+ include Internal::WindowSizing
+
+ ##
+ # Mount a component on a page, with a full execution environment
+ # i.e. `mount('MyComponent')` will mount MyComponent on the page.
+
+ # The params argument is a hash of parameters to be passed to the
+ # component.
+ # i.e. `mount('MyComponent', title: 'hello')`
+
+ # The options parameters can set things like:
+ # + controller: the controller class, defaults to HyperSpecTestController
+ # + no_wait: do not wait for any JS to finish executing before proceeding with the spec
+ # + render_on: :client_only (default), :client_and_server, or :server_only
+ # + style_sheet: style sheet file defaults to 'application'
+ # + javascript: javascript file defaults to 'application'
+ # + layout: if provided will use the specified layout otherwise no layout is used
+ # Note that if specifying options the params will have to inclosed in their
+ # own hash.
+ # i.e. `mount('MyComponent', { title: 'hello' }, render_on: :server_only)`
+ # The options can be specified globally using the client_options method (see below.)
+
+ # You may provide a block to mount. This block will be executed on the client
+ # before mounting the component. This is useful for setting up test
+ # components or modifying a components behavior.
+ # i.e.
+ # ```ruby
+ # mount('MyComponent', title: 'hello') do
+ # # this line will be printed on the client console
+ # puts "I'm about to mount my component!"
+ # end
+ # ```
+ def mount(component_name = nil, params = nil, opts = {}, &block)
+ unless params
+ params = opts
+ opts = {}
+ end
+ internal_mount(component_name, params, client_options(opts), &block)
+ end
+
+ ##
+ # The following methods retrieve callback and event responses from
+ # the mounted components. The history methods contain the array of all
+ # responses, while last_... returns the last response.
+ # i.e. event_history_for(:save) would return any save events
+ # that the component has raised.
+
+ %i[
+ callback_history_for last_callback_for clear_callback_history_for
+ event_history_for last_event_for clear_event_history_for
+ ].each do |method|
+ define_method(method) do |event_name|
+ evaluate_ruby(
+ "Hyperstack::Internal::Component::TopLevelRailsComponent.#{method}('#{event_name}')"
+ )
+ end
+ end
+
+ ##
+ # Define a code block to be prefixed to the mount code.
+ # Useful in before(:each) blocks.
+
+ # In legacy code this was called `on_client`. To get the legacy
+ # behavior alias on_client before_mount
+ # but be aware that on_client is now by default the method
+ # for executing a block of code on the client which was called
+ # evaluate_ruby
+
+ def before_mount(&block)
+ @_hyperspec_private_client_code =
+ "#{@_hyperspec_private_client_code}"\
+ "#{Unparser.unparse Parser::CurrentRuby.parse(block.source).children.last}\n"
+ end
+
+ # Execute the block both on the client and on the server. Useful
+ # for mocking isomorphic classes such as ActiveRecord models.
+
+ def isomorphic(&block)
+ yield
+ before_mount(&block)
+ end
+
+ # Allows options to the mount method to be specified globally
+
+ def client_option(opts = {})
+ @_hyperspec_private_client_options ||= {}
+ @_hyperspec_private_client_options.merge! opts
+ end
+
+ alias client_options client_option
+
+ ##
+ # shorthand for mount with no params (which will effectively reload the page.)
+ # also aliased as reload_page
+ def load_page
+ mount
+ end
+
+ alias reload_page load_page
+
+ ##
+ # evaluate a block (or string) on the client
+ # on_client(, , &block)
+ #
+ # normal use is to pass a block that will be compiled to the client
+ # but if the ruby code can be supplied as a string in the first arg.
+
+ # opts are passed on to JSON.parse when retrieving the result
+ # from the client.
+
+ # vars is a hash of name: value pairs. Each name will be initialized
+ # as a local variable on the client.
+
+ # example: on_client(x: 12) { x * x } => 144
+
+ # in legacy code on_client was called before_mount
+ # to get legacy on_client behavior you can alias
+ # on_client before_mount
+
+ alias on_client internal_evaluate_ruby
+
+ # same signature as on_client, but just returns the compiled
+ # js code. Useful for debugging suspected issues with the
+ # Opal compiler, etc.
+
+ def to_js(*args, &block)
+ opal_compile(*process_params(*args, &block))
+ end
+
+ # legacy methods for backwards compatibility
+ # these may be removed in a future version
+
+ def expect_evaluate_ruby(*args, &block)
+ expect(evaluate_ruby(*args, &block))
+ end
+
+ alias evaluate_ruby internal_evaluate_ruby
+ alias evaluate_promise evaluate_ruby
+ alias expect_promise expect_evaluate_ruby
+
+ def run_on_client(&block)
+ script = opal_compile(Unparser.unparse(Parser::CurrentRuby.parse(block.source).children.last))
+ page.execute_script(script)
+ end
+
+ def insert_html(str)
+ @_hyperspec_private_html_block = "#{@_hyperspec_private_html_block}\n#{str}"
+ end
+
+ def ppr(str)
+ js = Opal.hyperspec_compile(str)
+ execute_script("console.log(#{js})")
+ end
+
+ def debugger
+ `debugger`
+ nil
+ end
+
+ def add_class(class_name, style)
+ @_hyperspec_private_client_code =
+ "#{@_hyperspec_private_client_code}ComponentHelpers.add_class('#{class_name}', #{style})\n"
+ end
+
+ def attributes_on_client(model)
+ evaluate_ruby("#{model.class.name}.find(#{model.id}).attributes").symbolize_keys
+ end
+
+ ### --- Debugging Helpers ----
+
+ def pause(message = nil)
+ if message
+ puts message
+ page.evaluate_ruby "puts #{message.inspect}.to_s + ' (type go() to continue)'"
+ end
+
+ page.evaluate_script('window.hyper_spec_waiting_for_go = true')
+
+ loop do
+ sleep 0.25
+ break unless page.evaluate_script('window.hyper_spec_waiting_for_go')
+ end
+ end
+
+ def open_in_chrome
+ # if ['linux', 'freebsd'].include?(`uname`.downcase)
+ # `google-chrome http://#{page.server.host}:#{page.server.port}#{page.current_path}`
+ # else
+ `open http://#{page.server.host}:#{page.server.port}#{page.current_path}`
+ # end
+
+ loop do
+ sleep 1.hour
+ end
+ end
+
+ # short hand for use in pry sessions
+ alias c? internal_evaluate_ruby
+
+ def size_window(width = nil, height = nil)
+ # return if @window_cannot_be_resized
+ # original_width = evaluate_script('window.innerWidth')
+ # original_height = evaluate_script('window.innerHeight')
+ width, height = [height, width] if width == :portrait
+ width, height = width if width.is_a? Array
+ portrait = true if height == :portrait
+
+ case width
+ when :small
+ width, height = [480, 320]
+ when :mobile
+ width, height = [640, 480]
+ when :tablet
+ width, height = [960, 640]
+ when :large
+ width, height = [1920, 6000]
+ when :default, nil
+ width, height = [1024, 768]
+ end
+
+ width, height = [height, width] if portrait
+
+ unless RSpec.configuration.debugger_width
+ Capybara.current_session.current_window.resize_to(1000, 500)
+ sleep RSpec.configuration.wait_for_initialization_time
+ wait_for_size(1000, 500)
+ inner_width = evaluate_script('window.innerWidth')
+ RSpec.configuration.debugger_width = 1000 - inner_width
+ end
+ Capybara.current_session.current_window
+ .resize_to(width + RSpec.configuration.debugger_width, height)
+ wait_for_size(width + RSpec.configuration.debugger_width, height)
+ rescue StandardError
+ true
+ end
+ end
+end
diff --git a/ruby/hyper-spec/lib/hyper-spec/internal/client_execution.rb b/ruby/hyper-spec/lib/hyper-spec/internal/client_execution.rb
new file mode 100644
index 000000000..66c0004c4
--- /dev/null
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/client_execution.rb
@@ -0,0 +1,133 @@
+module HyperSpec
+ module Internal
+ module ClientExecution
+ def internal_evaluate_ruby(*args, &block)
+ insure_page_loaded
+ add_promise_execute_and_wait(*process_params(*args, &block))
+ end
+
+ private
+
+ PRIVATE_VARIABLES = %i[
+ @__inspect_output @__memoized @example @_hyperspec_private_client_code
+ @_hyperspec_private_html_block @fixture_cache
+ @fixture_connections @connection_subscriber @loaded_fixtures
+ @_hyperspec_private_client_options
+ b __ _ _ex_ pry_instance _out_ _in_ _dir_ _file_
+ ]
+
+ def add_locals(in_str, block)
+ b = block.binding
+
+ memoized = b.eval('__memoized').instance_variable_get(:@memoized)
+ in_str = memoized.inject(in_str) do |str, pair|
+ "#{str}\n#{set_local_var(pair.first, pair.last)}"
+ end if memoized
+
+ in_str = b.local_variables.inject(in_str) do |str, var|
+ next str if PRIVATE_VARIABLES.include? var
+
+ "#{str}\n#{set_local_var(var, b.local_variable_get(var))}"
+ end
+
+ in_str = b.eval('instance_variables').inject(in_str) do |str, var|
+ next str if PRIVATE_VARIABLES.include? var
+
+ "#{str}\n#{set_local_var(var, b.eval("instance_variable_get('#{var}')"))}"
+ end
+ in_str
+ end
+
+ def add_opal_block(str, block)
+ return str unless block
+
+ source = block.source
+ ast = Parser::CurrentRuby.parse(source)
+ ast = find_block(ast)
+ raise "could not find block within source: #{block.source}" unless ast
+
+ "#{add_locals(str, block)}\n#{Unparser.unparse ast.children.last}"
+ end
+
+ def add_promise_execute_and_wait(str, opts)
+ js = opal_compile(add_promise_wrapper(str))
+ page.execute_script("window.hyper_spec_promise_result = false; #{js}")
+ Timeout.timeout(Capybara.default_max_wait_time) do
+ loop do
+ break if page.evaluate_script('!!window.hyper_spec_promise_result')
+
+ sleep 0.25
+ end
+ end
+ JSON.parse(page.evaluate_script('window.hyper_spec_promise_result.$to_json()'), opts).first
+ end
+
+ def add_promise_wrapper(str)
+ <<~RUBY
+ (#{str}).tap do |r|
+ if defined?(Promise) && r.is_a?(Promise)
+ r.then { |args| `window.hyper_spec_promise_result = [args]` }
+ else
+ #after(0) do
+ #puts "setting window.hyper_spec_promise_result = [\#{r}]"
+ `window.hyper_spec_promise_result = [r]`
+ #end
+ end
+ end
+ RUBY
+ end
+
+ def find_block(node)
+ # find a block with the ast tree.
+
+ return false unless node.class == Parser::AST::Node
+ return node if the_node_you_are_looking_for?(node)
+
+ node.children.each do |child|
+ found = find_block(child)
+ return found if found
+ end
+ false
+ end
+
+ def process_params(*args, &block)
+ args = ['', *args] if args[0].is_a? Hash
+ args = [args[0], {}, args[1] || {}] if args.length < 3
+ str, opts, vars = args
+ vars.each do |name, value|
+ str = "#{name} = #{value.inspect}\n#{str}"
+ end
+ [add_opal_block(str, block), opts]
+ end
+
+ def the_node_you_are_looking_for?(node)
+ # we could also check that the block is going to the right method
+ # respond_to?(node.children.first.children[1]) &&
+ # method(node.children.first.children[1]) == method(:evaluate_ruby)
+ # however that does not work for expect { ... }.on_client_to ...
+ # because now the block is being sent to expect... so we could
+ # check the above OR node.children.first.children[1] == :expect
+ # but what if there are two blocks? on and on...
+ node.type == :block &&
+ node.children.first.class == Parser::AST::Node &&
+ node.children.first.type == :send
+ end
+
+ def set_local_var(name, object)
+ serialized = object.opal_serialize
+ if serialized
+ "#{name} = #{serialized}"
+ else
+ "self.class.define_method(:#{name}) "\
+ "{ raise 'Attempt to access the variable #{name} "\
+ 'that was defined in the spec, but its value could not be serialized '\
+ "so it is undefined on the client.' }"
+ end
+ end
+
+ def opal_compile(str, *)
+ Opal.hyperspec_compile(str)
+ end
+ end
+ end
+end
diff --git a/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb b/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb
new file mode 100644
index 000000000..f57524932
--- /dev/null
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb
@@ -0,0 +1,122 @@
+module HyperSpec
+ module Internal
+ module ComponentMount
+ private
+
+ TEST_CODE_KEY = 'hyper_spec_prerender_test_code.js'.freeze
+
+ # rubocop:disable Metrics/MethodLength
+ def add_block_with_helpers(component_name, opts, block)
+ return unless block || @_hyperspec_private_client_code || component_name.nil?
+
+ block_with_helpers = <<-RUBY
+ module ComponentHelpers
+ def self.js_eval(s)
+ `eval(s)`
+ end
+ def self.dasherize(s)
+ res = %x{
+ s.replace(/[-_\\s]+/g, '-')
+ .replace(/([A-Z\\d]+)([A-Z][a-z])/g, '$1-$2')
+ .replace(/([a-z\\d])([A-Z])/g, '$1-$2')
+ .toLowerCase()
+ }
+ res
+ end
+ def self.add_class(class_name, styles={})
+ style = styles.collect { |attr, value| "\#{dasherize(attr)}:\#{value}" }.join("; ")
+ cs = class_name.to_s
+ %x{
+ var style_el = document.createElement("style");
+ var css = "." + cs + " { " + style + " }";
+ style_el.type = "text/css";
+ if (style_el.styleSheet){
+ style_el.styleSheet.cssText = css;
+ } else {
+ style_el.appendChild(document.createTextNode(css));
+ }
+ document.head.appendChild(style_el);
+ }
+ end
+ end
+ #{test_dummy}
+ #{@_hyperspec_private_client_code}
+ #{Unparser.unparse(Parser::CurrentRuby.parse(block.source).children.last) if block}
+ RUBY
+ @_hyperspec_private_client_code = nil
+ opts[:code] = Opal.hyperspec_compile(block_with_helpers)
+ end
+ # rubocop:enable Metrics/MethodLength
+
+ def build_test_url_for(controller = nil, ping = nil)
+ id = ping ? 'ping' : Controller.test_id
+ "/#{route_root_for(controller)}/#{id}"
+ end
+
+ def insure_page_loaded(only_if_code_or_html_exists = nil)
+ return if only_if_code_or_html_exists && !@_hyperspec_private_client_code && !@_hyperspec_private_html_block
+ # if we are not resetting between examples, or think its mounted
+ # then look for Opal, but if we can't find it, then ping to clear and try again
+ if !HyperSpec.reset_between_examples? || page.instance_variable_get('@hyper_spec_mounted')
+ r = evaluate_script('Opal && true') rescue nil
+ return if r
+ page.visit build_test_url_for(nil, true) rescue nil
+ end
+ load_page
+ end
+
+ def internal_mount(component_name, params, opts, &block)
+ # TODO: refactor this
+ test_url = build_test_url_for(opts.delete(:controller))
+ add_block_with_helpers(component_name, opts, block)
+ send_params_to_controller_via_cache(test_url, component_name, params, opts)
+ setup_prerendering(opts)
+ page.instance_variable_set('@hyper_spec_mounted', false)
+ visit test_url
+ wait_for_ajax unless opts[:no_wait]
+ page.instance_variable_set('@hyper_spec_mounted', true)
+ Lolex.init(self, client_options[:time_zone], client_options[:clock_resolution])
+ end
+
+ def prerendering?(opts)
+ %i[both server_only].include?(opts[:render_on])
+ end
+
+ def send_params_to_controller_via_cache(test_url, component_name, params, opts)
+ component_name ||= 'Hyperstack::Internal::Component::TestDummy' if test_dummy
+ Controller.cache_write(
+ test_url,
+ [component_name, params, @_hyperspec_private_html_block, opts]
+ )
+ @_hyperspec_private_html_block = nil
+ end
+
+ def setup_prerendering(opts)
+ return unless defined?(::Hyperstack::Component) && prerendering?(opts)
+
+ @@original_server_render_files ||= ::Rails.configuration.react.server_renderer_options[:files]
+ ::Rails.configuration.react.server_renderer_options[:files] = @@original_server_render_files
+ if opts[:code].blank?
+ Controller.cache_delete(TEST_CODE_KEY)
+ else
+ Controller.cache_write(TEST_CODE_KEY, opts[:code])
+ @@original_server_render_files += [TEST_CODE_KEY]
+ end
+ ::React::ServerRendering.reset_pool
+ # make sure contexts are reloaded so they dont use code from cache, as the rails filewatcher
+ # doesnt look for cache changes
+ end
+
+ def test_dummy
+ return unless defined? ::Hyperstack::Component
+
+ <<-RUBY
+ class Hyperstack::Internal::Component::TestDummy
+ include Hyperstack::Component
+ render {}
+ end
+ RUBY
+ end
+ end
+ end
+end
diff --git a/ruby/hyper-spec/lib/hyper-spec/internal/controller.rb b/ruby/hyper-spec/lib/hyper-spec/internal/controller.rb
new file mode 100644
index 000000000..04de4251d
--- /dev/null
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/controller.rb
@@ -0,0 +1,70 @@
+module HyperSpec
+ module Internal
+ module Controller
+ class << self
+ attr_accessor :current_example
+ attr_accessor :description_displayed
+
+ def test_id
+ @_hyperspec_private_test_id ||= 0
+ @_hyperspec_private_test_id += 1
+ end
+
+ include ActionView::Helpers::JavaScriptHelper
+
+ def current_example_description!
+ title = "#{title}...continued." if description_displayed
+ self.description_displayed = true
+ "#{escape_javascript(current_example.description)}#{title}"
+ end
+
+ def file_cache
+ @file_cache ||= FileCache.new('cache', '/tmp/hyper-spec-caches', 30, 3)
+ end
+
+ def cache_read(key)
+ file_cache.get(key)
+ end
+
+ def cache_write(key, value)
+ file_cache.set(key, value)
+ end
+
+ def cache_delete(key)
+ file_cache.delete(key)
+ rescue StandardError
+ nil
+ end
+ end
+
+ # By default we assume we are operating in a Rails environment and will
+ # hook in using a rails controller. To override this define the
+ # HyperSpecController class in your spec helper. See the rack.rb file
+ # for an example of how to do this.
+
+ def hyper_spec_test_controller
+ return ::HyperSpecTestController if defined?(::HyperSpecTestController)
+
+ base = if defined? ApplicationController
+ Class.new ApplicationController
+ elsif defined? ::ActionController::Base
+ Class.new ::ActionController::Base
+ else
+ raise "Unless using Rails you must define the HyperSpecTestController\n"\
+ 'For rack apps try requiring hyper-spec/rack.'
+ end
+ Object.const_set('HyperSpecTestController', base)
+ end
+
+ # First insure we have a controller, then make sure it responds to the test method
+ # if not, then add the rails specific controller methods. The RailsControllerHelpers
+ # module will automatically add a top level route back to the controller.
+
+ def route_root_for(controller)
+ controller ||= hyper_spec_test_controller
+ controller.include RailsControllerHelpers unless controller.method_defined?(:test)
+ controller.route_root
+ end
+ end
+ end
+end
diff --git a/ruby/hyper-spec/lib/hyper-spec/patches.rb b/ruby/hyper-spec/lib/hyper-spec/internal/patches.rb
similarity index 61%
rename from ruby/hyper-spec/lib/hyper-spec/patches.rb
rename to ruby/hyper-spec/lib/hyper-spec/internal/patches.rb
index e88cc5111..eaebd2b90 100644
--- a/ruby/hyper-spec/lib/hyper-spec/patches.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/patches.rb
@@ -1,9 +1,25 @@
+module Opal
+ # strips off stuff that confuses things when transmitting to the client
+ # and prints offending code if it can't be compiled
+ def self.hyperspec_compile(str)
+ compile(str).gsub("// Prepare super implicit arguments\n", '')
+ .delete("\n").gsub('(Opal);', '(Opal)')
+ # rubocop:disable Lint/RescueException
+ # we are going to reraise it anyway, so its fine to catch EVERYTHING!
+ rescue Exception => e
+ puts "puts could not compile: \n\n#{str}\n\n"
+ raise e
+ end
+ # rubocop:enable Lint/RescueException
+end
+
module Unparser
class Emitter
# Emitter for send
class Send < self
def local_variable_clash?
- selector =~ /^[A-Z]/ || local_variable_scope.local_variable_defined_for_node?(node, selector)
+ selector =~ /^[A-Z]/ ||
+ local_variable_scope.local_variable_defined_for_node?(node, selector)
end
end
end
@@ -14,7 +30,7 @@ class << self
alias original_lines_for_before_hyper_spec lines_for
alias original_source_helper_before_hyper_spec source_helper
- def source_helper(source_location, name=nil)
+ def source_helper(source_location, name = nil)
source_location[1] = 1 if source_location[0] == '(pry)'
original_source_helper_before_hyper_spec source_location, name
end
@@ -37,7 +53,7 @@ def opal_serialize
class Hash
def opal_serialize
- "{#{collect { |k, v| "#{k.opal_serialize} => #{v.opal_serialize}"}.join(', ')}}"
+ "{#{collect { |k, v| "#{k.opal_serialize} => #{v.opal_serialize}" }.join(', ')}}"
end
end
@@ -53,6 +69,7 @@ def opal_serialize
end
end
+# rubocop:disable Lint/UnifiedInteger - patch for ruby prior to 2.4
if Gem::Version.new(RUBY_VERSION) < Gem::Version.new('2.4.0')
[Bignum, Fixnum].each do |klass|
klass.send(:define_method, :opal_serialize) do
@@ -60,6 +77,7 @@ def opal_serialize
end
end
end
+# rubocop:enable Lint/UnifiedInteger
class Time
def to_opal_expression
diff --git a/ruby/hyper-spec/lib/hyper-spec/internal/rails_controller_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/internal/rails_controller_helpers.rb
new file mode 100644
index 000000000..e36089858
--- /dev/null
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/rails_controller_helpers.rb
@@ -0,0 +1,50 @@
+module HyperSpec
+ module Internal
+ module RailsControllerHelpers
+ def self.included(base)
+ base.include ControllerHelpers
+ base.include Helpers
+ routes = ::Rails.application.routes
+ routes.disable_clear_and_finalize = true
+ routes.clear!
+ routes.draw { get "/#{base.route_root}/:id", to: "#{base.route_root}#test" }
+ ::Rails.application.routes_reloader.paths.each { |path| load(path) }
+ routes.finalize!
+ ActiveSupport.on_load(:action_controller) { routes.finalize! }
+ ensure
+ routes.disable_clear_and_finalize = false
+ end
+
+ module Helpers
+ def ping!
+ head(:no_content)
+ nil
+ end
+
+ def mount_component!
+ @page << '<%= react_component @component_name, @component_params, '\
+ "{ prerender: #{@render_on != :client_only} } %>"
+ end
+
+ def application!(file)
+ @page << "<%= javascript_include_tag '#{file}' %>"
+ end
+
+ def style_sheet!(file)
+ @page << "<%= stylesheet_link_tag '#{file}' %>"
+ end
+
+ def deliver!
+ @render_params[:inline] = @page
+ response.headers['Cache-Control'] = 'max-age=120'
+ response.headers['X-Tracking-ID'] = '123456'
+ render @render_params
+ end
+
+ def server_only?
+ @render_on == :server_only
+ end
+ end
+ end
+ end
+end
diff --git a/ruby/hyper-spec/lib/hyper-spec/time_cop.rb b/ruby/hyper-spec/lib/hyper-spec/internal/time_cop.rb
similarity index 96%
rename from ruby/hyper-spec/lib/hyper-spec/time_cop.rb
rename to ruby/hyper-spec/lib/hyper-spec/internal/time_cop.rb
index 0f4f9f521..faf8d8de8 100644
--- a/ruby/hyper-spec/lib/hyper-spec/time_cop.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/time_cop.rb
@@ -148,7 +148,7 @@ def pending_evaluations
def evaluate_ruby(&block)
if @capybara_page
- @capybara_page.evaluate_ruby(yield)
+ @capybara_page.on_client(yield)
else
pending_evaluations << block
end
@@ -156,9 +156,7 @@ def evaluate_ruby(&block)
def run_pending_evaluations
return if pending_evaluations.empty?
- puts "time cop evaluating ruby"
- @capybara_page.evaluate_ruby(pending_evaluations.collect(&:call).join("\n"))
- puts "done"
+ @capybara_page.on_client(pending_evaluations.collect(&:call).join("\n"))
@pending_evaluations ||= []
end
end
diff --git a/ruby/hyper-spec/lib/hyper-spec/internal/window_sizing.rb b/ruby/hyper-spec/lib/hyper-spec/internal/window_sizing.rb
new file mode 100644
index 000000000..5e7943cc0
--- /dev/null
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/window_sizing.rb
@@ -0,0 +1,23 @@
+module HyperSpec
+ module Internal
+ module WindowSizing
+ def wait_for_size(width, height)
+ start_time = Capybara::Helpers.monotonic_time
+ stable_count_w = 0
+ stable_count_h = 0
+ prev_size = [0, 0]
+ begin
+ sleep 0.05
+ curr_size = Capybara.current_session.current_window.size
+ return if [width, height] == curr_size
+ # some maximum or minimum is reached and size doesnt change anymore
+ stable_count_w += 1 if prev_size[0] == curr_size[0]
+ stable_count_h += 1 if prev_size[1] == curr_size[1]
+ return if stable_count_w > 2 || stable_count_h > 2
+ prev_size = curr_size
+ end while (Capybara::Helpers.monotonic_time - start_time) < Capybara.current_session.config.default_max_wait_time
+ raise Capybara::WindowError, "Window size not stable within #{Capybara.current_session.config.default_max_wait_time} seconds."
+ end
+ end
+ end
+end
diff --git a/ruby/hyper-spec/lib/hyper-spec/rails_controller_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/rails_controller_helpers.rb
deleted file mode 100644
index af953f5c0..000000000
--- a/ruby/hyper-spec/lib/hyper-spec/rails_controller_helpers.rb
+++ /dev/null
@@ -1,48 +0,0 @@
-module HyperSpec
- module RailsControllerHelpers
- def self.included(base)
- base.include ControllerHelpers
- base.include Helpers
- routes = ::Rails.application.routes
- routes.disable_clear_and_finalize = true
- routes.clear!
- routes.draw { get "/#{base.route_root}/:id", to: "#{base.route_root}#test" }
- ::Rails.application.routes_reloader.paths.each { |path| load(path) }
- routes.finalize!
- ActiveSupport.on_load(:action_controller) { routes.finalize! }
- ensure
- routes.disable_clear_and_finalize = false
- end
-
- module Helpers
- def ping!
- head(:no_content)
- nil
- end
-
- def mount_component!
- @page << '<%= react_component @component_name, @component_params, '\
- "{ prerender: #{@render_on != :client_only} } %>"
- end
-
- def application!(file)
- @page << "<%= javascript_include_tag '#{file}' %>"
- end
-
- def style_sheet!(file)
- @page << "<%= stylesheet_link_tag '#{file}' %>"
- end
-
- def deliver!
- @render_params[:inline] = @page
- response.headers['Cache-Control'] = 'max-age=120'
- response.headers['X-Tracking-ID'] = '123456'
- render @render_params
- end
-
- def server_only?
- @render_on == :server_only
- end
- end
- end
-end
diff --git a/ruby/hyper-spec/spec/hyper_spec.rb b/ruby/hyper-spec/spec/hyper_spec.rb
index 542f832e1..b2f7744cb 100644
--- a/ruby/hyper-spec/spec/hyper_spec.rb
+++ b/ruby/hyper-spec/spec/hyper_spec.rb
@@ -2,7 +2,7 @@
describe 'hyper-spec', js: true do
- after(:each) { |e| binding.pry if e.exception }
+ # after(:each) { |e| binding.pry if e.exception }
it 'can visit a page' do
visit 'test'
@@ -205,9 +205,9 @@ class StyledDiv
start_time = Time.now
sleep 1 # sleep is still in "real time" but Time will move 60 times faster
expect(start_time).to be_within(1).of(Time.now-1.minute)
- expect(evaluate_ruby('puts ""; Time.now.to_i')).to be_within(2).of(Time.now.to_i)
+ expect(evaluate_ruby('puts ""; Time.now.to_i')).to be_within(3).of(Time.now.to_i)
end
- expect(evaluate_ruby('Time.now.to_i')).to be_within(2).of(Time.now.to_i+@sync_gap)
+ expect(evaluate_ruby('Time.now.to_i')).to be_within(3).of(Time.now.to_i+@sync_gap)
end
it "will advance time along with time cop freezing" do
@@ -216,7 +216,7 @@ class StyledDiv
Timecop.freeze Time.now-2.years
expect(evaluate_ruby('puts ""; Time.now.to_i')).to be_within(1).of(Time.now.to_i)
Timecop.return
- expect(evaluate_ruby('puts ""; Time.now.to_i')).to be_within(2).of(Time.now.to_i+@sync_gap)
+ expect(evaluate_ruby('puts ""; Time.now.to_i')).to be_within(3).of(Time.now.to_i+@sync_gap)
end
it "can temporarily return to true time" do
From 840af31fc858f4d349a293a6bfb4f4d177edc9f8 Mon Sep 17 00:00:00 2001
From: catmando
Date: Thu, 4 Feb 2021 19:47:36 -0500
Subject: [PATCH 080/307] updated per latest changes in hyper-spec
---
ruby/hyper-component/spec/spec_helper.rb | 2 +-
ruby/hyper-i18n/spec/spec_helper.rb | 2 +-
ruby/hyper-model/spec/spec_helper.rb | 2 +-
ruby/hyper-operation/spec/spec_helper.rb | 2 +-
4 files changed, 4 insertions(+), 4 deletions(-)
diff --git a/ruby/hyper-component/spec/spec_helper.rb b/ruby/hyper-component/spec/spec_helper.rb
index 711eacab6..47c233658 100644
--- a/ruby/hyper-component/spec/spec_helper.rb
+++ b/ruby/hyper-component/spec/spec_helper.rb
@@ -65,7 +65,7 @@ class JavaScriptError < StandardError; end
end
end
- HyperSpec::ComponentTestHelpers.alias_method :on_client, :before_mount
+ HyperSpec::Helpers.alias_method :on_client, :before_mount
end
# Stubbing the React calls so we can test outside of Opal
diff --git a/ruby/hyper-i18n/spec/spec_helper.rb b/ruby/hyper-i18n/spec/spec_helper.rb
index cb505b28b..a5a678924 100644
--- a/ruby/hyper-i18n/spec/spec_helper.rb
+++ b/ruby/hyper-i18n/spec/spec_helper.rb
@@ -28,5 +28,5 @@
end
# Use legacy hyper-spec on_client behavior
- HyperSpec::ComponentTestHelpers.alias_method :on_client, :before_mount
+ HyperSpec::Helpers.alias_method :on_client, :before_mount
end
diff --git a/ruby/hyper-model/spec/spec_helper.rb b/ruby/hyper-model/spec/spec_helper.rb
index fe04f7b01..1cf662002 100644
--- a/ruby/hyper-model/spec/spec_helper.rb
+++ b/ruby/hyper-model/spec/spec_helper.rb
@@ -340,7 +340,7 @@ class JavaScriptError < StandardError; end
# end
# Use legacy hyper-spec on_client behavior
- HyperSpec::ComponentTestHelpers.alias_method :on_client, :before_mount
+ HyperSpec::Helpers.alias_method :on_client, :before_mount
end
FactoryBot.define do
diff --git a/ruby/hyper-operation/spec/spec_helper.rb b/ruby/hyper-operation/spec/spec_helper.rb
index e2260d48d..b7432f835 100644
--- a/ruby/hyper-operation/spec/spec_helper.rb
+++ b/ruby/hyper-operation/spec/spec_helper.rb
@@ -133,7 +133,7 @@ def self.on_server?
# end
# Use legacy hyper-spec on_client behavior
- HyperSpec::ComponentTestHelpers.alias_method :on_client, :before_mount
+ HyperSpec::Helpers.alias_method :on_client, :before_mount
end
module HyperSpec
From 8006a3a7b71155411c109f93dd89fcb95f09162e Mon Sep 17 00:00:00 2001
From: catmando
Date: Wed, 10 Feb 2021 10:56:01 -0500
Subject: [PATCH 081/307] wip - window sizing not reliable in chrome yet
---
ruby/hyper-spec/lib/hyper-spec/helpers.rb | 46 +++--------
.../lib/hyper-spec/internal/window_sizing.rb | 78 ++++++++++++++++---
ruby/hyper-spec/spec/hyper_spec.rb | 1 +
ruby/hyper-spec/spec/spec_helper.rb | 8 +-
4 files changed, 80 insertions(+), 53 deletions(-)
diff --git a/ruby/hyper-spec/lib/hyper-spec/helpers.rb b/ruby/hyper-spec/lib/hyper-spec/helpers.rb
index 0570bc9a2..162d6e552 100644
--- a/ruby/hyper-spec/lib/hyper-spec/helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/helpers.rb
@@ -124,6 +124,15 @@ def load_page
alias on_client internal_evaluate_ruby
+ # attempt to set the window to a particular size
+
+ def size_window(width = nil, height = nil)
+ hs_internal_resize_to(*adjust_size(width, height))
+ rescue StandardError => e
+ binding.pry
+ true
+ end
+
# same signature as on_client, but just returns the compiled
# js code. Useful for debugging suspected issues with the
# Opal compiler, etc.
@@ -201,42 +210,5 @@ def open_in_chrome
# short hand for use in pry sessions
alias c? internal_evaluate_ruby
-
- def size_window(width = nil, height = nil)
- # return if @window_cannot_be_resized
- # original_width = evaluate_script('window.innerWidth')
- # original_height = evaluate_script('window.innerHeight')
- width, height = [height, width] if width == :portrait
- width, height = width if width.is_a? Array
- portrait = true if height == :portrait
-
- case width
- when :small
- width, height = [480, 320]
- when :mobile
- width, height = [640, 480]
- when :tablet
- width, height = [960, 640]
- when :large
- width, height = [1920, 6000]
- when :default, nil
- width, height = [1024, 768]
- end
-
- width, height = [height, width] if portrait
-
- unless RSpec.configuration.debugger_width
- Capybara.current_session.current_window.resize_to(1000, 500)
- sleep RSpec.configuration.wait_for_initialization_time
- wait_for_size(1000, 500)
- inner_width = evaluate_script('window.innerWidth')
- RSpec.configuration.debugger_width = 1000 - inner_width
- end
- Capybara.current_session.current_window
- .resize_to(width + RSpec.configuration.debugger_width, height)
- wait_for_size(width + RSpec.configuration.debugger_width, height)
- rescue StandardError
- true
- end
end
end
diff --git a/ruby/hyper-spec/lib/hyper-spec/internal/window_sizing.rb b/ruby/hyper-spec/lib/hyper-spec/internal/window_sizing.rb
index 5e7943cc0..29755a2ed 100644
--- a/ruby/hyper-spec/lib/hyper-spec/internal/window_sizing.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/window_sizing.rb
@@ -1,22 +1,76 @@
module HyperSpec
module Internal
module WindowSizing
+
+ private
+
+ STD_SIZES = {
+ small: [480, 320],
+ mobile: [640, 480],
+ tablet: [960, 640],
+ large: [1920, 6000],
+ default: [1024, 768]
+ }
+
+ def adjust_size(width, height)
+ width, height = [height, width] if width == :portrait
+ width, height = width if width.is_a? Array
+ portrait = true if height == :portrait
+ width ||= :default
+ width, height = STD_SIZES[width] if STD_SIZES[width]
+ width, height = [height, width] if portrait
+ [width + debugger_width, height]
+ end
+
+ def debugger_width
+ RSpec.configuration.debugger_width ||= begin
+ hs_internal_resize_to(1000, 500) do
+ sleep RSpec.configuration.wait_for_initialization_time
+ end
+ inner_width = evaluate_script('window.innerWidth')
+ 1000 - inner_width
+ end
+ puts "debugger_width: #{RSpec.configuration.debugger_width}"
+ RSpec.configuration.debugger_width
+ end
+
+ def hs_internal_resize_to(width, height)
+ puts "hs_internal_resize_to(#{width}, #{height})"
+ Capybara.current_session.current_window.resize_to(width, height)
+ yield if block_given?
+ wait_for_size(width, height)
+ end
+
def wait_for_size(width, height)
- start_time = Capybara::Helpers.monotonic_time
- stable_count_w = 0
- stable_count_h = 0
+ @start_time = Capybara::Helpers.monotonic_time
+ @stable_count_w = @stable_count_h = 0
prev_size = [0, 0]
- begin
+ loop do
sleep 0.05
- curr_size = Capybara.current_session.current_window.size
- return if [width, height] == curr_size
- # some maximum or minimum is reached and size doesnt change anymore
- stable_count_w += 1 if prev_size[0] == curr_size[0]
- stable_count_h += 1 if prev_size[1] == curr_size[1]
- return if stable_count_w > 2 || stable_count_h > 2
+ curr_size = evaluate_script('[window.innerWidth, window.innerHeight]')
+ puts "waiting for size: #{width}, #{height} currently: #{curr_size}"
+
+ return true if curr_size == [width, height] || stalled?(prev_size, curr_size)
+
prev_size = curr_size
- end while (Capybara::Helpers.monotonic_time - start_time) < Capybara.current_session.config.default_max_wait_time
- raise Capybara::WindowError, "Window size not stable within #{Capybara.current_session.config.default_max_wait_time} seconds."
+ check_time!
+ end
+ end
+
+ def check_time!
+ if (Capybara::Helpers.monotonic_time - @start_time) >
+ Capybara.current_session.config.default_max_wait_time
+ raise Capybara::WindowError,
+ 'Window size not stable within '\
+ "#{Capybara.current_session.config.default_max_wait_time} seconds."
+ end
+ end
+
+ def stalled?(prev_size, curr_size)
+ # some maximum or minimum is reached and size doesn't change anymore
+ @stable_count_w += 1 if prev_size[0] == curr_size[0]
+ @stable_count_h += 1 if prev_size[1] == curr_size[1]
+ @stable_count_w > 4 || @stable_count_h > 4
end
end
end
diff --git a/ruby/hyper-spec/spec/hyper_spec.rb b/ruby/hyper-spec/spec/hyper_spec.rb
index b2f7744cb..934eb4ef1 100644
--- a/ruby/hyper-spec/spec/hyper_spec.rb
+++ b/ruby/hyper-spec/spec/hyper_spec.rb
@@ -317,6 +317,7 @@ class StyledDiv
it "the default portrait size" do
size_window(:portrait)
+ binding.pry
expect(dims).to eq(adjusted(768, 1024))
end
diff --git a/ruby/hyper-spec/spec/spec_helper.rb b/ruby/hyper-spec/spec/spec_helper.rb
index 413bbed44..3789c40a4 100644
--- a/ruby/hyper-spec/spec/spec_helper.rb
+++ b/ruby/hyper-spec/spec/spec_helper.rb
@@ -17,13 +17,13 @@ def computed_style(selector, prop)
end
def calculate_window_restrictions
return if @min_width
- size_window(100,100)
+ size_window(100, 100)
@min_width = width
- size_window(500,500)
- @height_adjust = 500-height
+ size_window(500, 500)
+ @height_adjust = 500 - height
size_window(6000, 6000)
@max_width = width
- @max_height = height
+ @max_height = height-@height_adjust
end
def height
evaluate_script('window.innerHeight')
From b70736c36af9e3251b623dc231d0265944460d94 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 13 Feb 2021 17:42:02 -0500
Subject: [PATCH 082/307] remove delay and interval file
---
ruby/hyper-operation/lib/hyper-operation.rb | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/ruby/hyper-operation/lib/hyper-operation.rb b/ruby/hyper-operation/lib/hyper-operation.rb
index e01d34d29..bb41ec4cf 100644
--- a/ruby/hyper-operation/lib/hyper-operation.rb
+++ b/ruby/hyper-operation/lib/hyper-operation.rb
@@ -45,7 +45,7 @@ def titleize
require 'hyper-operation/transport/client_drivers'
require 'hyper-operation/transport/acting_user'
require 'opal-activesupport'
- require 'hyper-operation/delay_and_interval'
+ # require 'hyper-operation/delay_and_interval'
require 'hyper-operation/exception'
require 'hyper-operation/promise'
require 'hyper-operation/railway'
From 38412b7e78060ddc6ad85ab1c42e41aded2908c3 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 13 Feb 2021 18:45:53 -0500
Subject: [PATCH 083/307] window sizing now working
---
ruby/hyper-spec/lib/hyper-spec/helpers.rb | 5 ++---
.../lib/hyper-spec/internal/window_sizing.rb | 6 +-----
ruby/hyper-spec/spec/hyper_spec.rb | 1 -
ruby/hyper-spec/spec/spec_helper.rb | 14 ++++++++++++--
4 files changed, 15 insertions(+), 11 deletions(-)
diff --git a/ruby/hyper-spec/lib/hyper-spec/helpers.rb b/ruby/hyper-spec/lib/hyper-spec/helpers.rb
index 162d6e552..19bb05559 100644
--- a/ruby/hyper-spec/lib/hyper-spec/helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/helpers.rb
@@ -127,9 +127,8 @@ def load_page
# attempt to set the window to a particular size
def size_window(width = nil, height = nil)
- hs_internal_resize_to(*adjust_size(width, height))
- rescue StandardError => e
- binding.pry
+ hs_internal_resize_to(*determine_size(width, height))
+ rescue StandardError
true
end
diff --git a/ruby/hyper-spec/lib/hyper-spec/internal/window_sizing.rb b/ruby/hyper-spec/lib/hyper-spec/internal/window_sizing.rb
index 29755a2ed..042f5be51 100644
--- a/ruby/hyper-spec/lib/hyper-spec/internal/window_sizing.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/window_sizing.rb
@@ -1,7 +1,6 @@
module HyperSpec
module Internal
module WindowSizing
-
private
STD_SIZES = {
@@ -12,7 +11,7 @@ module WindowSizing
default: [1024, 768]
}
- def adjust_size(width, height)
+ def determine_size(width, height)
width, height = [height, width] if width == :portrait
width, height = width if width.is_a? Array
portrait = true if height == :portrait
@@ -30,12 +29,10 @@ def debugger_width
inner_width = evaluate_script('window.innerWidth')
1000 - inner_width
end
- puts "debugger_width: #{RSpec.configuration.debugger_width}"
RSpec.configuration.debugger_width
end
def hs_internal_resize_to(width, height)
- puts "hs_internal_resize_to(#{width}, #{height})"
Capybara.current_session.current_window.resize_to(width, height)
yield if block_given?
wait_for_size(width, height)
@@ -48,7 +45,6 @@ def wait_for_size(width, height)
loop do
sleep 0.05
curr_size = evaluate_script('[window.innerWidth, window.innerHeight]')
- puts "waiting for size: #{width}, #{height} currently: #{curr_size}"
return true if curr_size == [width, height] || stalled?(prev_size, curr_size)
diff --git a/ruby/hyper-spec/spec/hyper_spec.rb b/ruby/hyper-spec/spec/hyper_spec.rb
index 934eb4ef1..b2f7744cb 100644
--- a/ruby/hyper-spec/spec/hyper_spec.rb
+++ b/ruby/hyper-spec/spec/hyper_spec.rb
@@ -317,7 +317,6 @@ class StyledDiv
it "the default portrait size" do
size_window(:portrait)
- binding.pry
expect(dims).to eq(adjusted(768, 1024))
end
diff --git a/ruby/hyper-spec/spec/spec_helper.rb b/ruby/hyper-spec/spec/spec_helper.rb
index 3789c40a4..2ed740a54 100644
--- a/ruby/hyper-spec/spec/spec_helper.rb
+++ b/ruby/hyper-spec/spec/spec_helper.rb
@@ -15,27 +15,37 @@ def computed_style(selector, prop)
"window.getComputedStyle(document.querySelector('#{selector}'))['#{prop}']"
)
end
+
def calculate_window_restrictions
return if @min_width
+
size_window(100, 100)
@min_width = width
+ @min_height = height
size_window(500, 500)
@height_adjust = 500 - height
size_window(6000, 6000)
@max_width = width
- @max_height = height-@height_adjust
+ @max_height = height
end
+
def height
evaluate_script('window.innerHeight')
end
+
def width
evaluate_script('window.innerWidth')
end
+
def dims
[width, height]
end
+
def adjusted(width, height)
- [[@max_width, [width, @min_width].max].min, [@max_height, height-@height_adjust].min]
+ [
+ [@max_width, [width, @min_width].max].min,
+ [@max_height, [height - @height_adjust, @min_height].max].min
+ ]
end
end
From 711aa5a40e3d136cc378bbb7755cbe5368c6fcc5 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 13 Feb 2021 22:44:23 -0500
Subject: [PATCH 084/307] changed how we access after and every on server
---
ruby/hyper-operation/lib/hyper-operation.rb | 3 ++-
.../lib/hyper-operation/async_sleep.rb | 23 +++++++++++++++++++
.../lib/hyper-operation/delay_and_interval.rb | 9 --------
.../spec/hyper-operation/basics_spec.rb | 1 +
4 files changed, 26 insertions(+), 10 deletions(-)
create mode 100644 ruby/hyper-operation/lib/hyper-operation/async_sleep.rb
delete mode 100644 ruby/hyper-operation/lib/hyper-operation/delay_and_interval.rb
diff --git a/ruby/hyper-operation/lib/hyper-operation.rb b/ruby/hyper-operation/lib/hyper-operation.rb
index bb41ec4cf..da470051f 100644
--- a/ruby/hyper-operation/lib/hyper-operation.rb
+++ b/ruby/hyper-operation/lib/hyper-operation.rb
@@ -28,6 +28,7 @@ def titleize
require 'hyper-operation/railway/validations'
require 'hyper-operation/server_op'
require 'hyper-operation/boot'
+ require 'hyper-operation/async_sleep'
else
require 'tty-table'
require 'hyperstack-config'
@@ -45,7 +46,7 @@ def titleize
require 'hyper-operation/transport/client_drivers'
require 'hyper-operation/transport/acting_user'
require 'opal-activesupport'
- # require 'hyper-operation/delay_and_interval'
+ require 'hyper-operation/async_sleep'
require 'hyper-operation/exception'
require 'hyper-operation/promise'
require 'hyper-operation/railway'
diff --git a/ruby/hyper-operation/lib/hyper-operation/async_sleep.rb b/ruby/hyper-operation/lib/hyper-operation/async_sleep.rb
new file mode 100644
index 000000000..800b5f20e
--- /dev/null
+++ b/ruby/hyper-operation/lib/hyper-operation/async_sleep.rb
@@ -0,0 +1,23 @@
+module Hyperstack
+ module AsyncSleep
+ if RUBY_ENGINE == 'opal'
+ def self.every(*args, &block)
+ every(*args, &block)
+ end
+
+ def self.after(*args, &block)
+ after(*args, &block)
+ end
+ else
+ extend self
+
+ def every(time, &block)
+ Thread.new { loop { sleep time; block.call } }
+ end
+
+ def after(time, &block)
+ Thread.new { sleep time; block.call }
+ end
+ end
+ end
+end
diff --git a/ruby/hyper-operation/lib/hyper-operation/delay_and_interval.rb b/ruby/hyper-operation/lib/hyper-operation/delay_and_interval.rb
deleted file mode 100644
index 3f1f11424..000000000
--- a/ruby/hyper-operation/lib/hyper-operation/delay_and_interval.rb
+++ /dev/null
@@ -1,9 +0,0 @@
-module Kernel
- def every(time, &block)
- Thread.new { loop { sleep time; block.call }}
- end
-
- def after(time, &block)
- Thread.new { sleep time; block.call }
- end
-end
diff --git a/ruby/hyper-operation/spec/hyper-operation/basics_spec.rb b/ruby/hyper-operation/spec/hyper-operation/basics_spec.rb
index b57bb68e0..7df0ad29e 100644
--- a/ruby/hyper-operation/spec/hyper-operation/basics_spec.rb
+++ b/ruby/hyper-operation/spec/hyper-operation/basics_spec.rb
@@ -189,6 +189,7 @@ def count
it "will use the promise returned by execute", js: true do
isomorphic do
class MyOperation < Hyperstack::Operation
+ include Hyperstack::AsyncSleep
param :wait, type: Float, min: 0
param :result
step do
From fdad03d0ffdb62132d9d06bd62eec92edd091523 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 16 Feb 2021 21:12:19 -0500
Subject: [PATCH 085/307] i hope this helps
---
.../lib/reactive_record/active_record/class_methods.rb | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/class_methods.rb b/ruby/hyper-model/lib/reactive_record/active_record/class_methods.rb
index 5f92c2b36..f9daab46a 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/class_methods.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/class_methods.rb
@@ -454,7 +454,7 @@ def _react_param_conversion(param, opt = nil)
[assoc.attribute, { id: [value]}]
end
else
- [key, [value]]
+ [*key, [value]]
end
end.compact
ReactiveRecord::Base.load_data do
From f8f7e34467f5bd002e927f22602bf2fb8fb02f5e Mon Sep 17 00:00:00 2001
From: catmando
Date: Thu, 18 Feb 2021 17:34:16 -0500
Subject: [PATCH 086/307] added docs
---
docs/hyper-spec/01-installation.md | 57 +++
docs/hyper-spec/02-tutorial | 122 ++++++
.../03-hyperspec-methods-and-features.md | 383 ++++++++++++++++++
docs/hyper-spec/README.md | 41 ++
.../lib/hyper-spec/controller_helpers.rb | 2 +-
5 files changed, 604 insertions(+), 1 deletion(-)
create mode 100644 docs/hyper-spec/01-installation.md
create mode 100644 docs/hyper-spec/02-tutorial
create mode 100644 docs/hyper-spec/03-hyperspec-methods-and-features.md
create mode 100644 docs/hyper-spec/README.md
diff --git a/docs/hyper-spec/01-installation.md b/docs/hyper-spec/01-installation.md
new file mode 100644
index 000000000..11a2b79d9
--- /dev/null
+++ b/docs/hyper-spec/01-installation.md
@@ -0,0 +1,57 @@
+# HyperSpec Installation
+
+Add `gem 'hyper-spec'` to your Gemfile in the usual way. Typically in a Rails app you will add this in the test section of your Gemfile:
+
+```ruby
+group :test do
+ gem 'hyper-spec', '~> 1.0.alpha1.0'
+end
+```
+
+Make sure to `bundle install`.
+
+> Note: if you want to use the unreleased edge branch your hyper-spec gem specification will be:
+>
+> ```ruby
+> gem 'hyper-spec',
+> git: 'git://github.com/hyperstack-org/hyperstack.git',
+> branch: 'edge',
+> glob: 'ruby/*/*.gemspec'
+> ```
+
+HyperSpec is integrated with the `pry` gem for debugging, so it is recommended to add the `pry` gem as well.
+
+HyperSpec will also use the `timecop` gem if present to allow you to control and synchronize time on the server and the client.
+
+A typical spec_helper file when using HyperSpec will look like this:
+
+```ruby
+# spec_helper.rb
+require 'hyper-spec'
+require 'pry' # optional
+
+ENV["RAILS_ENV"] ||= 'test'
+require File.expand_path('../test_app/config/environment', __FILE__)
+
+require 'rspec/rails'
+require 'timecop' # optional
+
+# any other rspec configuration you need
+# note HyperSpec will include chrome driver for providing the client
+# run time environment
+```
+
+To load the webdriver and client environment your spec should have the
+`:js` flag set:
+
+```ruby
+# the js flag can be set on the entire group of specs, or a context
+describe 'some hyper-specs', :js do
+ ...
+end
+
+# or for an individual spec
+ it 'an individual hyper-spec', :js do
+ ...
+ end
+```
diff --git a/docs/hyper-spec/02-tutorial b/docs/hyper-spec/02-tutorial
new file mode 100644
index 000000000..de4f01011
--- /dev/null
+++ b/docs/hyper-spec/02-tutorial
@@ -0,0 +1,122 @@
+# Tutorial
+
+For this quick tutorial lets assume you have an existing Rails app that
+already uses RSpec to which you have added a first Hyperstack component to
+try things out.
+
+For your trial, you have created a very simple component that shows
+the number of orders shipped by your companies website:
+
+```ruby
+class OrdersShipped < HyperComponent
+ def format_number(number)
+ number.to_s.reverse.gsub(/(\d{3})(?=\d)/, '\\1,').reverse
+ end
+
+ render(DIV, class: 'orders-shipped') do
+ format_number Order.shipped.count
+ end
+end
+```
+
+> Note that styling can be taken care of in the usual way by
+> providing styles for the `orders-shipped` css class. All we care
+> about here is the *function* of the component.
+
+Meanwhile `Order` is an ActiveRecord Model that would look something like this:
+
+```ruby
+class Order < ApplicationRecord
+ ...
+ scope :shipped, -> () { where(status: :shipped) }
+ ...
+end
+```
+
+> Note that when using ActiveRecord models in your specs you will
+> need to add the appropriate database setup and cleaner methods like you would
+> for any specs used with ActiveRecord. We assume here that as each
+> spec starts there are no records in the database
+
+The `OrdersShipped` component can be mounted on any page of your site,
+and assuming the proper policy permissions are provided it will
+show the total orders shipped, and will dynamically increase in
+realtime.
+
+A partial spec for this component might look like this:
+
+```ruby
+require 'spec_helper'
+
+describe 'OrdersShipped', :js do
+ it 'dynamically displays the orders shipped' do
+ mount 'OrdersShipped'
+ expect(find('div.orders-shipped')).to have_content(0)
+ Order.create(status: :shipped)
+ expect(find('div.orders-shipped')).to have_content(1)
+ Order.last.destroy
+ expect(find('div.orders-shipped')).to have_content(0)
+ end
+
+ it '#format method' do
+ on_client { @comp = OrdersShipped.new }
+ ['1,234,567', '123', '1,234'].each do |n|
+ expect { @comp.format_number(n.gsub(',','').to_i) }
+ .on_client_to eq(n)
+ end
+ end
+end
+```
+
+If you are familiar with Capybara then the first spec should
+look similar to an integration spec. The difference is instead
+of visiting a page, we `mount` the `OrdersShipped` component on a blank page
+that hyper-spec will set up for us. This let's us unit test
+components outside of any application specific view logic.
+
+> Note that like Capybara we indicate that a client environment should
+> be set up by adding the :js tag.
+
+Once mounted we can use Capybara finders and matchers, to check
+if our content is as expected. Because we are running on the server
+we can easily add and delete orders, and check the response on the UI.
+
+The second spec shows how we can do some white box unit testing of our
+component. Instead of mounting the component we just create a new
+instance which will be invisible since it was not mounted. For this we
+use the `on_client` method.
+
+The `on_client` method takes a block, and will
+compile that block using
+Opal, and execute it on the client. In this case we simply create a
+new `OrderShipped` instance, and assign it to an instance variable, which as you
+will see will continue to be available to us later in the spec.
+
+> Note, if you are an RSpec purist, you would probably prefer to see
+> something like `let` be used here instead of an instance variable. Shall we
+> say its on the todo list.
+
+Now that we have our test component setup we can test its `format_number`
+method. To do this we put the test expression in a block followed by
+`on_client_to`. Again the block will be compiled using Opal, executed on
+the client, and the result will be returned to the expectation.
+
+Notice that the server side variable `n` can be read (but not written) within
+the client block. All local variables, memoized variables, and instance variables can
+can be read in the client block as long as they represent objects that can be
+sensibly marshalled and unmarshalled.
+
+This has covered the basics of Hyperspec - in summary:
+
++ The `js` tag indicates the spec will be using a client environment.
++ `mount`: Mount a component on a blank page. This replaces the `visit` method
+for unit testing components.
++ `on_client`: Execute Ruby code on the client (and return the result).
++ `on_client_to`: Execute the expectation block on the client, and then check
+the expectation (on the server.)
++ Instance variables retain their values between client execution blocks.
++ All variables accessible to the spec are copied to the client if possible.
+
+There are many other features such as dealing with promises, passing data to
+and from a mounted component, using the `Timecop` gem, and working with a `pry`
+session. So read on.
diff --git a/docs/hyper-spec/03-hyperspec-methods-and-features.md b/docs/hyper-spec/03-hyperspec-methods-and-features.md
new file mode 100644
index 000000000..971bc62ec
--- /dev/null
+++ b/docs/hyper-spec/03-hyperspec-methods-and-features.md
@@ -0,0 +1,383 @@
+# Summary of Methods and Features
+
+### Expectation Helpers
+
+These can be used any where within your specs:
+
++ [`on_client`](#the-on_client-method) - executes code on the client
++ [`isomorphic`](#the-isomorphic-method) - executes code on the client *and* the server
++ [`mount`](#mounting-components) - mounts a hyperstack component in an empty window
++ [`before_mount`](#before_mount) - specifies a block of code to be executed before the first call to `mount`, `isomorphic` or `on_client`
++ [`client_options`](#client-initialization-options) - allows options to be specified globally
++ [`run_on_client`](#run_on_client) - same as `on_client` but no value is returned
++ [`reload_page`](#reload_page) - resets the page environment
++ [`add_class`](#add_class) - adds a CSS class
++ [`size_window`](#size_window) - specifies how big the client window should be
++ [`attributes_on_client`](#attributes_on_client) - returns any ActiveModel attributes loaded on the client
+
+These methods are used after mounting a component to retrieve
+events sent outwards from the component:
+
++ [`callback_history_for`](#retrieving-event-data-from-the-mounted-component)
++ [`last_callback_for`](#retrieving-event-data-from-the-mounted-component)
++ [`clear_callback_history_for`](#retrieving-event-data-from-the-mounted-component)
++ [`event_history_for`](#retrieving-event-data-from-the-mounted-component)
++ [`last_event_for`](#retrieving-event-data-from-the-mounted-component)
++ [`clear_event_history_for`](#retrieving-event-data-from-the-mounted-component)
+
+### Expectation Targets
+
+These can be used within expectations replacing the `to` and `not_to` methods. The expectation expression must be inclosed in a block.
+
++ [`on_client_to`](#client-expectation-targets), [`to_on_client_not`](#client-expectation-targets) - the expression will be evaluated on the client, and matched on the server.
+
+These methods have the following aliases to make your specs more readable:
++ [`to_on_client`](#client-expectation-targets)
++ [`on_client_to_not`](#client-expectation-targets)
++ [`on_client_not_to`](#client-expectation-targets)
++ [`to_not_on_client`](#client-expectation-targets)
++ [`not_to_on_client`](#client-expectation-targets)
++ [`to_then`](#client-expectation-targets)
++ [`then_to_not`](#client-expectation-targets)
++ [`then_not_to`](#client-expectation-targets)
++ [`to_not_then`](#client-expectation-targets)
++ [`not_to_then`](#client-expectation-targets)
+
+
++ [`with`](#client-expectation-targets) - can be chained with the above methods to pass data to initialize local variables on the client
+
+### Other Debugging Aids
+
+The following methods are used primarly at a debug break point, most require you use binding.pry as your debugger:
+
++ [`to_js`](#to_js) - returns the ruby code compiled to JS.
++ [`ppr`](#ppr) - print the results of the ruby expression on the client console.
++ [`debugger`](#debugger) - Sets a debug breakpoint on code running on the client.
++ [`open_in_chrome`](#open_in_chrome) - Opens a chrome browser that will load the current state.
++ [`pause`](#pause) - Halts execution on the server without blocking I/O.
+
+### Available Webdrivers
+
+HyperSpec comes integrated with Chrome and Chrome headless webdrivers. The default configuration will run using Chrome headless. To see what is going on set the `DRIVER` environment variable to `chrome`
+```bash
+DRIVER=chrome bundle exec rspec
+```
+
+### Timecop Integration
+
+You can use the Timecop gem to control the flow of time within your specs. Hyperspec will coordinate things with the client so the time on the client is kept in sync with the time on the server. So for example if you use Timecop to advance time 1 day on the server, time on the browser will also advance by one day.
+
+See the [Client Initialization Options](#client-initialization-options) section for how to control the client time zone, and clock resolution.
+
+# Details
+
+### The `on_client` method
+
+The on_client method takes a block. The ruby code inside the block will be executed on the client, and the result will be returned.
+
+```ruby
+ it 'will print a message on the client' do
+ on_client do
+ puts 'hey I am running here on the client!'
+ end
+ end
+```
+
+If the block returns a promise Hyperspec will wait for the promise to be resolved before returning. For example:
+
+```ruby
+ it 'waits for a promise' do
+ start_time = Time.now
+ result = on_client do
+ promise = Promise.new
+ after(10.seconds) { promise.resolve('done!') }
+ promise
+ end
+ expect(result).to eq('done!')
+ expect(Time.now-start_time).to be >= 10.seconds
+ end
+```
+> HyperSpec will do its best to reconstruct the result back on the server in some sensible way. Occasionally it just doesn't work, in which case you can end the block with a `nil` or some other simple expression, or use the `run_on_client` method, which does not return the result.
+
+### Accessing variables on the client
+
+It is often useful to pass variables from the spec to the client. Hyperspec will copy all your local variables, memoized variables, and instance variables known at the time the `on_client` block is compiled to the client.
+```ruby
+ let!(memoized) { 'a memoized variable' }
+ it 'will pass variables to the client' do
+ local = 'a local variable'
+ @instance = 'an instance variable'
+ result = on_client { [memoized, local, @instance] }
+ expect(result).to eq [memoized, local, @instance]
+ end
+```
+> Note that memoized variables are not initialized until first
+accessed, so you probably want to use the let! method unless you
+are sure you are accessing the memoized value before sending it to the client.
+
+The value of instance variables initialized on the client are preserved
+across blocks executed on the client. For example:
+```ruby
+ it 'remembers instance variables' do
+ on_client { @total = 0 }
+ 10.times do |i|
+ # note how we are passing i in
+ on_client { @total += i }
+ end
+ result = on_client { @total }
+ expect(result).to eq(10 * 11 / 2)
+ end
+```
+
+### The `isomorphic` method
+
+The `isomorphic` works the same as `on_client` but in addition it also executes the same block on the server. It is especially useful when doing some testing of
+ActiveRecord models, where you might want to modify the behavior of the model on server and the client.
+
+```ruby
+ it 'can run code the same everywhere!' do
+ isomorphic do
+ def factorial(x)
+ x.zero? ? 1 : x * factorial(x - 1)
+ end
+ end
+
+ on_the_client = on_client { factorial(7) }
+ on_the_server = factorial(7)
+ expect(on_the_client).to eq(on_the_server)
+ end
+```
+
+
+### Client Initialization Options
+
+The first time a spec runs code on the client, it has to initialize a browser context. You can use the `client_options` (aka `client_option`) method to specify the following options when the page is loaded.
+
++ `time_zone` - browsers always run in the local time zone, if you want to force the browser to act as if its in a different zone, you can use the time_zone option, and provide any valid zone that the rails `in_time_zone` method will accept.
+Example: `client_option 'WorldClock', time_zone: 'Hawaii'`
++ `render_on`: `:client_only` (default), `:server_only`, or `:both`
+Hyperstack components can be prerendered on the server. The `render_on` option controls this feature. For example `server_only` is useful to insure components are properly prerendered. *(See the mount method below for more details on rendering components)*
++ `clock_resolution`: Indicates the resolution that the simulated clock will run at on the client, when using the TimeCop gem. The default value is 20 (milliseconds).
++ `no_wait`: After the page is loaded the system will by default wait until all javascript requests to the server complete, before proceeding. Specifying `no_wait: true` will skip this.
++ `javascript`: The javascript asset to load when mounting the component. By default it will be `application` (.js is assumed). Note that the standard Hyperstack configuration will compile all the client side Ruby assets as well as javascript packages into the `application.js` file, so the default will work fine.
++ `style_sheet`: The style sheet asset to load when mounting the component. By default it will be `application` (.css is assumed).
++ `controller` - **expert zone** specify a controller that will be used to mount the
+component. By default hyper-spec will build a controller and route to handle the request from the client to mount the component.
+
+Any other options not listed above will be passed along to the Rail's controller `render` method. So for example you could specify some other specific layout using `client_option layout: 'special_layout'`
+
+Note that this method can be used in the before(:each) block of a spec context, to provide options for all the specs in the block.
+
+### Mounting Components
+
+The `mount` method is used to render a component on a page:
+
+```ruby
+ it 'can display a component for me' do
+ mount 'SayHello', name: 'Lannar' do
+ class SayHello < HyperComponent
+ param :name
+ render(DIV) do
+ "Hello #{name}!"
+ end
+ end
+ end
+
+ expect(page).to have_content('Hello Lannar')
+ end
+```
+
+The `mount` method has a few options. In it's simplest form you specify just the name of the component that is already defined in your hyperstack code and it will be mounted.
+
+You can add parameters that will be passed to the component as in the above example. As the above example also shows you can also define code within the block. The code does not have to be the component being mounted, but might be just some logic to help with the test.
+
+In addition `mount` can take any of the options provided to `client_options` (see above.) To provide these options, you must provide a (possibly) empty params hash. For example:
+```ruby
+mount 'MyComponent', {... params ... }, {... opts ... }
+```
+
+### Retrieving Event Data From the Mounted Component
+
+Components *receive* parameters, and may send callbacks and events back out. To test if a component has sent the appropriate data you can use the following methods:
+
++ `callback_history_for`
++ `last_callback_for`
++ `clear_callback_history_for`
++ `event_history_for`
++ `last_event_for`
++ `clear_event_history_for`
+
+```ruby
+ it 'can check on a clients events and callbacks' do
+ mount 'BigTalker' do
+ class BigTalker < HyperComponent
+ fires :i_was_clicked
+ param :call_me_back, type: Proc
+
+ before_mount { @click_counter = 0 }
+
+ render(DIV) do
+ BUTTON { 'click me' }.on(:click) do
+ @click_counter += 1
+ i_was_clicked!
+ call_me_back.call(@click_counter)
+ end
+ end
+ end
+ end
+ 3.times do
+ find('button').click
+ end
+ # the history is an array, one element for each item in the history
+ expect(event_history_for(:i_was_clicked).length).to eq(3)
+ # each item in the array is itself an array of the arguments
+ expect(last_call_back_for(:call_me_back)).to eq([3])
+ # clearing the history resets the array to empty
+ clear_event_history_for(:i_was_clicked)
+ expect(event_history_for(:i_was_clicked).length).to eq(0)
+ end
+```
+
+> Note that you must declare the params as type Proc, or use
+the fires method to declare an event, for the history mechanism to work.
+
+### Other Helpers
+
+#### `before_mount`
+
+Specifies a block of code to be executed before the first call to `mount`, `isomorphic` or `on_client`. This is primarly useful to add to a rspec before(:each) block containing common client code needed by all the specs in the context.
+
+> Unlike `mount`, `isomorphic` and `on_client`, `before_mount` does not load the client page, but will wait for the first of the other methods to be called.
+
+#### `run_on_client`
+
+same as `on_client` but no value is returned. Useful when the return value may be to complex to marshall and unmarshall using JSON.
+
+#### `reload_page`
+
+Shorthand for `mount` with no parameters. Useful if you need to reset the client within a spec.
+
+#### `add_class`
+
+Adds a CSS class. The first parameter is the name of the class, and the second is a hash of styles, represented in the react style format.
+
+Example: `add_class :some_class, borderStyle: :solid` adds a class with style `border-style: 'solid'`
+
+#### `size_window`
+
+Indicates the size of the browser window. The values can be given either symbolically or as two numbers (width and height). Predefined sizes are:
+
++ `:small`: 480 x 320
++ `:mobile` 640 x 480
++ `:tablet` 960 x 64,
++ `:large` 1920 x 6000
++ `:default` 1024 x 768
+
+All of the above can be modified by providing the `:portrait` option as the first or second parameter.
+
+So for example the following are all equivalent:
+
++ `size_window(:small, :portrait)`
++ `size_window(:portrait, :small)`
++ `size_window(320, 480)`
+
+#### `attributes_on_client`
+
+returns any `ActiveModel` attributes loaded on the client. HyperModel will normally begin a load cycle as soon as you access the attribute of a client. However it is sometimes useful to see what attributes have already been loaded.
+
+### Client Expectation Targets
+
+These can be used within expectations replacing the `to` and `not_to` methods. The expectation expression must be inclosed in a block.
+
+For example:
+
+```ruby
+it 'has built-in expectation targets' do
+ expect { RUBY_ENGINE }.on_client_to eq('opal')
+end
+```
+
+The above expectation is short for saying:
+
+```ruby
+ result = on_client { RUBY_ENGINE }
+ expect(result).to eq('opal')
+```
+
+These methods have the following aliases to make your specs more readable:
++ `to_on_client`
++ `on_client_to_not`
++ `on_client_not_to`
++ `to_not_on_client`
++ `not_to_on_client`
++ `to_then`
++ `then_to_not`
++ `then_not_to`
++ `to_not_then`
++ `not_to_then`
+
+The `then` variants are useful to note that the spec involves a promise, but it does no explicit checking that the result comes from a promise.
+
+In addition the `with` method can be chained with the above methods to pass data to initialize local variables on the client:
+
+```ruby
+ it 'can pass values to the client using the with method' do
+ expect { foo * foo }.with(foo: 12).to_on_client eq(144)
+ end
+```
+
+Note that there are other ways to pass values into the client context as noted above but the `with` might be preferable to some to keep things
+nicely localized.
+
+### Useful Debug Methods
+
+These methods are primarily designed to help debug code and specs.
+
+#### `to_js`
+
+Takes a block like `on_client` but rather than running the code on the client, simply returns the resulting code. This is useful for debugging obscure problems when the Opal compiler or some feature of
+Hyperspec is suspected as the issue.
+
+#### `ppr`
+
+Takes a block like `on_client` and prints the result on the client console using JS console.log. Equivalent to doing
+
+```ruby
+ on_client do
+ begin
+ ...
+ end.tap { |r| `console.log(r)` }
+ end
+```
+
+This is useful when the result cannot be usefully returned to the server,
+or when the result of interest is better looked at as the raw
+javascript object.
+
+#### `c?`
+
+Shorthand for `on_console`, useful for entering expressions in pry console, to investigate the state of the client.
+
+#### `debugger`
+
+This psuedo method can be inserted into any code executed on the client. It will cause the code to stop, and enter a *javascript* read-eval loop, within the debug console.
+
+Unfortunately ATM we do not have the technology to enter a *Ruby* read-eval loop at an arbitrary point on the client.
+
+> Note: due to a bug in the Opal compiler your code should not have `debugger` as the last expression in a method or a block. In this situation add any expression (such as nil) after the debugger statement.
+```ruby
+def foo
+ ... some code ...
+ debugger # this will fail with a compiler syntax error
+end
+```
+
+#### `open_in_chrome`
+By default specs are run with headless chrome, so there is no visible browser window. The `open_in_chrome` method will open a browser window, and load it with the current state.
+
+You can also run specs in a visible chrome window by setting the `DRIVER` environment variable to `CHROME`
+
+#### `pause`
+The method is typically not needed assuming you are using a multithreaded server like Puma. If for whatever reason the pry debug session is not multithreaded, *and* you want to try some kind of experiment on the javascript console, *and* those experiments make requests to the server, you may not get a response, because all threads are in use.
+
+You can resolve this by using the `pause` method in the debug session which will put the debug session into a non-blocking loop. You then release the pause by executing `go()` in the *javascript* debug console.
diff --git a/docs/hyper-spec/README.md b/docs/hyper-spec/README.md
new file mode 100644
index 000000000..44dd165e3
--- /dev/null
+++ b/docs/hyper-spec/README.md
@@ -0,0 +1,41 @@
+# HyperSpec
+
+## Adding client side testing to RSpec
+
+The `hyper-spec` gem supports the Hyperstack goals of programmer productivity and seamless web development by allowing testing to be done with minimal concern for the client-server interface.
+
+The `hyper-spec` gem adds functionality to the `rspec`, `capybara`, `timecop` and `pry` gems allowing you to do the following:
+
++ write component and integration tests using the rspec syntax and helpers
++ write specs that run on both the client and server
++ evaluate client side ruby expressions from within specs and while using `pry`
++ share data between the client and server within your specs
++ control and synchronize time on the client and the server
+
+HyperSpec can be used standalone, but if used as part of a Hyperstack application it allows straight forward testing of Hyperstack Components and your ActiveRecord Models.
+
+So for example here is part of a simple unit test of a TodoIndex component:
+
+```ruby
+it "will update the TodoIndex", js: true do
+ # mounts the TodoIndex component (client side)
+ mount 'TodoIndex'
+ # Todo is an ActiveRecord Model
+ # create a new Todo on the server (we could use FactoryBot of course)
+ todo_1 = Todo.create(title: 'this todo created on the server')
+ # verify that UI got updated
+ expect(find('.ToDoItem-Text').text).to eq todo_1.title
+ # verify that the count of Todos on the client side DB matches the server
+ expect { Todo.count }.on_client_to eq Todo.count
+ # now create another Todo on the client
+ new_todo_title = 'this todo created on the client'
+ # note that local variables are copied from the server to the client
+ on_client { Todo.create(title: new_todo_title) }
+ # the Todo should now be reflected on the server
+ expect(Todo.last.title).to eq new_todo_title
+end
+```
+
+When using HyperSpec all the specs execute on the server side, but they may also interrogate the state of the UI as well as the state
+of any of the client side objects. The specs can execute any valid Ruby code client side to create new test objects as well as do
+white box testing. This keeps the logic of your specs in one place.
diff --git a/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb b/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
index b2a6a0b4d..5aa2129c5 100644
--- a/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/controller_helpers.rb
@@ -31,7 +31,7 @@ def style_sheet!(_file_)
# deliver the page. The @page variable will contain the html ready to go,
# any additional options that are passed through from the spec will be
- # in the @render_params variable. For example layout: 'my special layout'
+ # in the @render_params variable. For example layout: 'my_special_layout'
def deliver!
raise 'must implement'
From 54e5a1cf5abf7edd6be3a9d242cd14e75704d3c4 Mon Sep 17 00:00:00 2001
From: Mitch VanDuyn
Date: Thu, 18 Feb 2021 17:41:16 -0500
Subject: [PATCH 087/307] Update 03-hyperspec-methods-and-features.md
fixed spacing problem
---
docs/hyper-spec/03-hyperspec-methods-and-features.md | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/docs/hyper-spec/03-hyperspec-methods-and-features.md b/docs/hyper-spec/03-hyperspec-methods-and-features.md
index 971bc62ec..00216fc16 100644
--- a/docs/hyper-spec/03-hyperspec-methods-and-features.md
+++ b/docs/hyper-spec/03-hyperspec-methods-and-features.md
@@ -43,7 +43,7 @@ These methods have the following aliases to make your specs more readable:
+ [`to_not_then`](#client-expectation-targets)
+ [`not_to_then`](#client-expectation-targets)
-
+in addition
+ [`with`](#client-expectation-targets) - can be chained with the above methods to pass data to initialize local variables on the client
### Other Debugging Aids
From 78b271837cc08f4bfec0303cda7fbf85166d9a65 Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 19 Feb 2021 19:31:59 -0500
Subject: [PATCH 088/307] updated docs fixed prerendering issue
---
docs/hyper-spec/02-tutorial | 4 +-
.../03-hyperspec-methods-and-features.md | 76 +++++--
.../server_rendering/hyper_asset_container.rb | 6 +-
ruby/hyper-spec/lib/hyper-spec.rb | 1 +
ruby/hyper-spec/lib/hyper-spec/helpers.rb | 3 +
.../hyper-spec/internal/client_execution.rb | 41 ----
.../hyper-spec/internal/component_mount.rb | 18 +-
.../lib/hyper-spec/internal/copy_locals.rb | 103 ++++++++++
ruby/hyper-spec/spec/hyper_spec.rb | 190 +++++++++++++++---
9 files changed, 352 insertions(+), 90 deletions(-)
create mode 100644 ruby/hyper-spec/lib/hyper-spec/internal/copy_locals.rb
diff --git a/docs/hyper-spec/02-tutorial b/docs/hyper-spec/02-tutorial
index de4f01011..8d99964a4 100644
--- a/docs/hyper-spec/02-tutorial
+++ b/docs/hyper-spec/02-tutorial
@@ -96,7 +96,7 @@ will see will continue to be available to us later in the spec.
> something like `let` be used here instead of an instance variable. Shall we
> say its on the todo list.
-Now that we have our test component setup we can test its `format_number`
+Now that we have our test component setup we can test it's `format_number`
method. To do this we put the test expression in a block followed by
`on_client_to`. Again the block will be compiled using Opal, executed on
the client, and the result will be returned to the expectation.
@@ -113,7 +113,7 @@ This has covered the basics of Hyperspec - in summary:
for unit testing components.
+ `on_client`: Execute Ruby code on the client (and return the result).
+ `on_client_to`: Execute the expectation block on the client, and then check
-the expectation (on the server.)
+the expectation (on the server.)
+ Instance variables retain their values between client execution blocks.
+ All variables accessible to the spec are copied to the client if possible.
diff --git a/docs/hyper-spec/03-hyperspec-methods-and-features.md b/docs/hyper-spec/03-hyperspec-methods-and-features.md
index 971bc62ec..8883d99bf 100644
--- a/docs/hyper-spec/03-hyperspec-methods-and-features.md
+++ b/docs/hyper-spec/03-hyperspec-methods-and-features.md
@@ -1,4 +1,4 @@
-# Summary of Methods and Features
+# HyperSpec Methods and Features
### Expectation Helpers
@@ -69,6 +69,10 @@ You can use the Timecop gem to control the flow of time within your specs. Hype
See the [Client Initialization Options](#client-initialization-options) section for how to control the client time zone, and clock resolution.
+### The `no_reset` flag
+
+By default the client environment will be reinitialized at the beginning of every spec. If this is not needed you can speed things up by adding the `no_reset` flag to a block of specs.
+
# Details
### The `on_client` method
@@ -129,9 +133,42 @@ across blocks executed on the client. For example:
end
```
+> Be especially careful of this this when using the [`no_reset`](#the-no_reset-flag) as instance variables will retain their values between each spec in this mode.
+
+#### White and Black Listing Variables
+
+By default all local variables, memoized variables, and instance variables in scope in the spec will be copied to the client. This can be controlled through the `include_vars` and `exclude_vars` [client options](#client-initialization-options).
+
+`include_vars` can be set to
++ an array of symbols: only those vars will be copied,
++ a single symbol: only that var will be copied,
++ any other truthy value: all vars will be copied (the default)
++ or nil, false, or an empty array: no vars will be copied.
+
+`exclude_vars` can be set to
++ an array of symbols - those vars will **not** be copied,
++ a single symbol - only that var will be excluded,
++ any other truthy value - no vars will be copied,
++ or nil, false, or an empty array - all vars will be copied (the default).
+
+Examples:
+
+```Ruby
+ # don't copy vars at all.
+ client_option exclude_vars: true
+ # only copy var1 and the instance var @var2
+ client_option include_vars: [:var1, :@var2]
+ # only exclude foo_var
+ client_option exclude_vars: :foo_var
+```
+
+Note that the exclude_vars list will take precedence over the include_vars list.
+
+The exclude/include lists can be overridden on an individual spec using the `with` method - See [Client Expectation Targets](#client-expectation-targets).
+
### The `isomorphic` method
-The `isomorphic` works the same as `on_client` but in addition it also executes the same block on the server. It is especially useful when doing some testing of
+The `isomorphic` method works the same as `on_client` but in addition it also executes the same block on the server. It is especially useful when doing some testing of
ActiveRecord models, where you might want to modify the behavior of the model on server and the client.
```ruby
@@ -148,25 +185,26 @@ ActiveRecord models, where you might want to modify the behavior of the model on
end
```
-
### Client Initialization Options
The first time a spec runs code on the client, it has to initialize a browser context. You can use the `client_options` (aka `client_option`) method to specify the following options when the page is loaded.
+ `time_zone` - browsers always run in the local time zone, if you want to force the browser to act as if its in a different zone, you can use the time_zone option, and provide any valid zone that the rails `in_time_zone` method will accept.
-Example: `client_option 'WorldClock', time_zone: 'Hawaii'`
-+ `render_on`: `:client_only` (default), `:server_only`, or `:both`
-Hyperstack components can be prerendered on the server. The `render_on` option controls this feature. For example `server_only` is useful to insure components are properly prerendered. *(See the mount method below for more details on rendering components)*
+Example: `client_option time_zone: 'Hawaii'`
+ `clock_resolution`: Indicates the resolution that the simulated clock will run at on the client, when using the TimeCop gem. The default value is 20 (milliseconds).
++ `include_vars`: white list of all vars to be copied to the client. See [Accessing Variables on the Client](#accessing-variables-on-the-client) for details.
++ `exclude_vars`: black list of all vars not to be copied to the client. See [Accessing Variables on the Client](#accessing-variables-on-the-client) for details.
++ `render_on`: `:client_only` (default), `:server_only`, or `:both`
+Hyperstack components can be prerendered on the server. The `render_on` option controls this feature. For example `server_only` is useful to insure components are properly prerendered. *See the `mount` method [below](#mounting-components) for more details on rendering components*
+ `no_wait`: After the page is loaded the system will by default wait until all javascript requests to the server complete, before proceeding. Specifying `no_wait: true` will skip this.
+ `javascript`: The javascript asset to load when mounting the component. By default it will be `application` (.js is assumed). Note that the standard Hyperstack configuration will compile all the client side Ruby assets as well as javascript packages into the `application.js` file, so the default will work fine.
+ `style_sheet`: The style sheet asset to load when mounting the component. By default it will be `application` (.css is assumed).
-+ `controller` - **expert zone** specify a controller that will be used to mount the
++ `controller` - **(expert zone!)** specify a controller that will be used to mount the
component. By default hyper-spec will build a controller and route to handle the request from the client to mount the component.
Any other options not listed above will be passed along to the Rail's controller `render` method. So for example you could specify some other specific layout using `client_option layout: 'special_layout'`
-Note that this method can be used in the before(:each) block of a spec context, to provide options for all the specs in the block.
+Note that this method can be used in the `before(:each)` block of a spec context to provide options for all the specs in the block.
### Mounting Components
@@ -189,7 +227,7 @@ The `mount` method is used to render a component on a page:
The `mount` method has a few options. In it's simplest form you specify just the name of the component that is already defined in your hyperstack code and it will be mounted.
-You can add parameters that will be passed to the component as in the above example. As the above example also shows you can also define code within the block. The code does not have to be the component being mounted, but might be just some logic to help with the test.
+You can add parameters that will be passed to the component as in the above example. As the above example also shows you can also define code within the block. This is just shorthand for defining the code before hand using `on_client`. The code does not have to be the component being mounted, but might be just some logic to help with the test.
In addition `mount` can take any of the options provided to `client_options` (see above.) To provide these options, you must provide a (possibly) empty params hash. For example:
```ruby
@@ -238,20 +276,20 @@ Components *receive* parameters, and may send callbacks and events back out. To
end
```
-> Note that you must declare the params as type Proc, or use
-the fires method to declare an event, for the history mechanism to work.
+> Note that you must declare the params as type `Proc`, or use
+the `fires` method to declare an event for the history mechanism to work.
### Other Helpers
#### `before_mount`
-Specifies a block of code to be executed before the first call to `mount`, `isomorphic` or `on_client`. This is primarly useful to add to a rspec before(:each) block containing common client code needed by all the specs in the context.
+Specifies a block of code to be executed before the first call to `mount`, `isomorphic` or `on_client`. This is primarly useful to add to an rspec `before(:each)` block containing common client code needed by all the specs in the context.
> Unlike `mount`, `isomorphic` and `on_client`, `before_mount` does not load the client page, but will wait for the first of the other methods to be called.
#### `run_on_client`
-same as `on_client` but no value is returned. Useful when the return value may be to complex to marshall and unmarshall using JSON.
+same as `on_client` but no value is returned. Useful when the return value may be too complex to marshall and unmarshall using JSON.
#### `reload_page`
@@ -259,7 +297,7 @@ Shorthand for `mount` with no parameters. Useful if you need to reset the clie
#### `add_class`
-Adds a CSS class. The first parameter is the name of the class, and the second is a hash of styles, represented in the react style format.
+Adds a CSS class. The first parameter is the name of the class, and the second is a hash of styles, represented in the React [style format.](https://reactjs.org/docs/dom-elements.html#style)
Example: `add_class :some_class, borderStyle: :solid` adds a class with style `border-style: 'solid'`
@@ -283,7 +321,7 @@ So for example the following are all equivalent:
#### `attributes_on_client`
-returns any `ActiveModel` attributes loaded on the client. HyperModel will normally begin a load cycle as soon as you access the attribute of a client. However it is sometimes useful to see what attributes have already been loaded.
+returns any `ActiveModel` attributes loaded on the client. HyperModel will normally begin a load cycle as soon as you access the attribute on the client. However it is sometimes useful to see what attributes have already been loaded.
### Client Expectation Targets
@@ -326,8 +364,7 @@ In addition the `with` method can be chained with the above methods to pass data
end
```
-Note that there are other ways to pass values into the client context as noted above but the `with` might be preferable to some to keep things
-nicely localized.
+By default HyperSpec will copy all local variables, memoized variables, and instance variables defined in a spec to the client. The specific variables can also be white listed and black listed. The `with` method overrides any white or black listed values. So for example if you prefer to use the more explicit `with` method to pass values to the client, you can add `client_option exclude_vars: true` in a `before(:all)` block in your spec helper. See [Accessing Variables on the Client](#accessing-variables-on-the-client) for details.
### Useful Debug Methods
@@ -358,6 +395,11 @@ javascript object.
Shorthand for `on_console`, useful for entering expressions in pry console, to investigate the state of the client.
+```ruby
+pry:> c? { puts 'hello on the console' } # prints hello on the client
+-> nil
+```
+
#### `debugger`
This psuedo method can be inserted into any code executed on the client. It will cause the code to stop, and enter a *javascript* read-eval loop, within the debug console.
diff --git a/ruby/hyper-component/lib/hyperstack/internal/component/rails/server_rendering/hyper_asset_container.rb b/ruby/hyper-component/lib/hyperstack/internal/component/rails/server_rendering/hyper_asset_container.rb
index 2b9dfbb5a..f253a671e 100644
--- a/ruby/hyper-component/lib/hyperstack/internal/component/rails/server_rendering/hyper_asset_container.rb
+++ b/ruby/hyper-component/lib/hyperstack/internal/component/rails/server_rendering/hyper_asset_container.rb
@@ -9,7 +9,9 @@ module Rails
module ServerRendering
class HyperTestAssetContainer
def find_asset(logical_path)
- HyperSpec::ComponentTestHelpers.cache_read(logical_path)
+ # we skip the container if it raises an error so we
+ # don't care if we are running under hyperspec or not
+ HyperSpec::Internal::Controller.cache_read(logical_path)
end
end
@@ -24,7 +26,7 @@ def initialize
if React::ServerRendering::WebpackerManifestContainer.compatible?
@ass_containers << React::ServerRendering::WebpackerManifestContainer.new
end
- @ass_containers << HyperTestAssetContainer.new if ::Rails.env.test?
+ @ass_containers << HyperTestAssetContainer.new
end
def find_asset(logical_path)
diff --git a/ruby/hyper-spec/lib/hyper-spec.rb b/ruby/hyper-spec/lib/hyper-spec.rb
index 720054a1c..07f8a1927 100644
--- a/ruby/hyper-spec/lib/hyper-spec.rb
+++ b/ruby/hyper-spec/lib/hyper-spec.rb
@@ -9,6 +9,7 @@
require 'hyper-spec/internal/client_execution'
require 'hyper-spec/internal/component_mount'
require 'hyper-spec/internal/controller'
+require 'hyper-spec/internal/copy_locals'
require 'hyper-spec/internal/patches'
require 'hyper-spec/internal/rails_controller_helpers'
require 'hyper-spec/internal/time_cop.rb'
diff --git a/ruby/hyper-spec/lib/hyper-spec/helpers.rb b/ruby/hyper-spec/lib/hyper-spec/helpers.rb
index 19bb05559..b769d6146 100644
--- a/ruby/hyper-spec/lib/hyper-spec/helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/helpers.rb
@@ -3,6 +3,7 @@ module Helpers
include Internal::ClientExecution
include Internal::Controller
include Internal::ComponentMount
+ include Internal::CopyLocals
include Internal::WindowSizing
##
@@ -90,6 +91,8 @@ def isomorphic(&block)
def client_option(opts = {})
@_hyperspec_private_client_options ||= {}
@_hyperspec_private_client_options.merge! opts
+ build_var_inclusion_lists
+ @_hyperspec_private_client_options
end
alias client_options client_option
diff --git a/ruby/hyper-spec/lib/hyper-spec/internal/client_execution.rb b/ruby/hyper-spec/lib/hyper-spec/internal/client_execution.rb
index 66c0004c4..51f65c52f 100644
--- a/ruby/hyper-spec/lib/hyper-spec/internal/client_execution.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/client_execution.rb
@@ -8,36 +8,6 @@ def internal_evaluate_ruby(*args, &block)
private
- PRIVATE_VARIABLES = %i[
- @__inspect_output @__memoized @example @_hyperspec_private_client_code
- @_hyperspec_private_html_block @fixture_cache
- @fixture_connections @connection_subscriber @loaded_fixtures
- @_hyperspec_private_client_options
- b __ _ _ex_ pry_instance _out_ _in_ _dir_ _file_
- ]
-
- def add_locals(in_str, block)
- b = block.binding
-
- memoized = b.eval('__memoized').instance_variable_get(:@memoized)
- in_str = memoized.inject(in_str) do |str, pair|
- "#{str}\n#{set_local_var(pair.first, pair.last)}"
- end if memoized
-
- in_str = b.local_variables.inject(in_str) do |str, var|
- next str if PRIVATE_VARIABLES.include? var
-
- "#{str}\n#{set_local_var(var, b.local_variable_get(var))}"
- end
-
- in_str = b.eval('instance_variables').inject(in_str) do |str, var|
- next str if PRIVATE_VARIABLES.include? var
-
- "#{str}\n#{set_local_var(var, b.eval("instance_variable_get('#{var}')"))}"
- end
- in_str
- end
-
def add_opal_block(str, block)
return str unless block
@@ -113,17 +83,6 @@ def the_node_you_are_looking_for?(node)
node.children.first.type == :send
end
- def set_local_var(name, object)
- serialized = object.opal_serialize
- if serialized
- "#{name} = #{serialized}"
- else
- "self.class.define_method(:#{name}) "\
- "{ raise 'Attempt to access the variable #{name} "\
- 'that was defined in the spec, but its value could not be serialized '\
- "so it is undefined on the client.' }"
- end
- end
def opal_compile(str, *)
Opal.hyperspec_compile(str)
diff --git a/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb b/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb
index f57524932..04d90a11e 100644
--- a/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb
@@ -91,6 +91,22 @@ def send_params_to_controller_via_cache(test_url, component_name, params, opts)
@_hyperspec_private_html_block = nil
end
+ # test_code_key = "hyper_spec_prerender_test_code.js"
+ # if defined? ::Hyperstack::Component
+ # @@original_server_render_files ||= ::Rails.configuration.react.server_renderer_options[:files]
+ # if opts[:render_on] == :both || opts[:render_on] == :server_only
+ # unless opts[:code].blank?
+ # ComponentTestHelpers.cache_write(test_code_key, opts[:code])
+ # ::Rails.configuration.react.server_renderer_options[:files] = @@original_server_render_files + [test_code_key]
+ # ::React::ServerRendering.reset_pool # make sure contexts are reloaded so they dont use code from cache, as the rails filewatcher doesnt look for cache changes
+ # else
+ # ComponentTestHelpers.cache_delete(test_code_key)
+ # ::Rails.configuration.react.server_renderer_options[:files] = @@original_server_render_files
+ # ::React::ServerRendering.reset_pool # make sure contexts are reloaded so they dont use code from cache, as the rails filewatcher doesnt look for cache changes
+ # end
+ # end
+ # end
+
def setup_prerendering(opts)
return unless defined?(::Hyperstack::Component) && prerendering?(opts)
@@ -100,7 +116,7 @@ def setup_prerendering(opts)
Controller.cache_delete(TEST_CODE_KEY)
else
Controller.cache_write(TEST_CODE_KEY, opts[:code])
- @@original_server_render_files += [TEST_CODE_KEY]
+ ::Rails.configuration.react.server_renderer_options[:files] += [TEST_CODE_KEY]
end
::React::ServerRendering.reset_pool
# make sure contexts are reloaded so they dont use code from cache, as the rails filewatcher
diff --git a/ruby/hyper-spec/lib/hyper-spec/internal/copy_locals.rb b/ruby/hyper-spec/lib/hyper-spec/internal/copy_locals.rb
new file mode 100644
index 000000000..6ba1e8a33
--- /dev/null
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/copy_locals.rb
@@ -0,0 +1,103 @@
+module HyperSpec
+ module Internal
+ module CopyLocals
+ private
+
+ def build_var_inclusion_lists
+ build_included_list
+ build_excluded_list
+ end
+
+ def build_included_list
+ @_hyperspec_private_included_vars = nil
+ return unless @_hyperspec_private_client_options.key? :include_vars
+
+ included = @_hyperspec_private_client_options[:include_vars]
+ if included.is_a? Symbol
+ @_hyperspec_private_included_vars = [included]
+ elsif included.is_a?(Array)
+ @_hyperspec_private_included_vars = included
+ elsif !included
+ @_hyperspec_private_included_vars = []
+ end
+ end
+
+ PRIVATE_VARIABLES = %i[
+ @__inspect_output @__memoized @example @_hyperspec_private_client_code
+ @_hyperspec_private_html_block @fixture_cache
+ @fixture_connections @connection_subscriber @loaded_fixtures
+ @_hyperspec_private_client_options
+ @_hyperspec_private_included_vars
+ @_hyperspec_private_excluded_vars
+ b __ _ _ex_ pry_instance _out_ _in_ _dir_ _file_
+ ]
+
+ def build_excluded_list
+ return unless @_hyperspec_private_client_options
+
+ excluded = @_hyperspec_private_client_options[:exclude_vars]
+ if excluded.is_a? Symbol
+ @_hyperspec_private_excluded_vars = [excluded]
+ elsif excluded.is_a?(Array)
+ @_hyperspec_private_excluded_vars = excluded
+ elsif excluded
+ @_hyperspec_private_included_vars = []
+ end
+ end
+
+ def var_excluded?(var, binding)
+ return true if PRIVATE_VARIABLES.include? var
+
+ excluded = binding.eval('instance_variable_get(:@_hyperspec_private_excluded_vars)')
+ return true if excluded&.include?(var)
+
+ included = binding.eval('instance_variable_get(:@_hyperspec_private_included_vars)')
+ included && !included.include?(var)
+ end
+
+ def add_locals(in_str, block)
+ b = block.binding
+ add_instance_vars(b, add_local_vars(b, add_memoized_vars(b, in_str)))
+ end
+
+ def add_memoized_vars(binding, in_str)
+ memoized = binding.eval('__memoized').instance_variable_get(:@memoized)
+ return in_str unless memoized
+
+ memoized.inject(in_str) do |str, pair|
+ next str if var_excluded?(pair.first, binding)
+
+ "#{str}\n#{set_local_var(pair.first, pair.last)}"
+ end
+ end
+
+ def add_local_vars(binding, in_str)
+ binding.local_variables.inject(in_str) do |str, var|
+ next str if var_excluded?(var, binding)
+
+ "#{str}\n#{set_local_var(var, binding.local_variable_get(var))}"
+ end
+ end
+
+ def add_instance_vars(binding, in_str)
+ binding.eval('instance_variables').inject(in_str) do |str, var|
+ next str if var_excluded?(var, binding)
+
+ "#{str}\n#{set_local_var(var, binding.eval("instance_variable_get('#{var}')"))}"
+ end
+ end
+
+ def set_local_var(name, object)
+ serialized = object.opal_serialize
+ if serialized
+ "#{name} = #{serialized}"
+ else
+ "self.class.define_method(:#{name}) "\
+ "{ raise 'Attempt to access the variable #{name} "\
+ 'that was defined in the spec, but its value could not be serialized '\
+ "so it is undefined on the client.' }"
+ end
+ end
+ end
+ end
+end
diff --git a/ruby/hyper-spec/spec/hyper_spec.rb b/ruby/hyper-spec/spec/hyper_spec.rb
index b2f7744cb..f9456502a 100644
--- a/ruby/hyper-spec/spec/hyper_spec.rb
+++ b/ruby/hyper-spec/spec/hyper_spec.rb
@@ -32,6 +32,21 @@ class ShowOff
expect(evaluate_script('typeof React')).to eq('undefined')
end
+ it "can render server side only with code defined in the mount", :prerendering_on do
+ client_option render_on: :server_only
+ mount 'SayHello2', name: 'George' do
+ class SayHello2
+ include Hyperstack::Component
+ param :name
+ render(DIV) do
+ "Hello there #{@Name}"
+ end
+ end
+ end
+ expect(page).to have_content('Hello there George')
+ expect(evaluate_script('typeof React')).to eq('undefined')
+ end
+
it "can use the application's layout" do
client_option layout: 'application'
mount 'SayHello', name: 'Sam'
@@ -230,6 +245,28 @@ class StyledDiv
end
end
+ context 'the no-reset flag', :no_reset do
+ it 'will mount the component first' do
+ mount 'TestComponent' do
+ class TestComponent
+ include Hyperstack::Component
+ include Hyperstack::State::Observable
+ class << self
+ state_accessor :title
+ end
+ render(DIV) do
+ TestComponent.title
+ end
+ end
+ end
+ on_client { TestComponent.title = 'The Title' }
+ expect(page).to have_content('The Title')
+ end
+ it 'but will not mount it again' do
+ expect(page).to have_content('The Title')
+ end
+ end
+
context "new style rspec expressions", no_reset: true do
before(:each) do
@@ -259,38 +296,137 @@ class StyledDiv
end.to_then eq('done')
end
- it 'will copy local vars to the client' do
- str = 'hello'
- expect { str.reverse }.on_client_to eq str.reverse
- end
+ context 'copying local vars:' do
+ let!(:memoized_var) { true }
+ let!(:another_memoized_var) { true }
+ before(:each) do
+ on_client do
+ send(:remove_instance_variable, :@instance_var) rescue nil
+ send(:remove_instance_variable, :@another_instance_var) rescue nil
+ end
+ end
- it 'will copy instance vars to the client' do
- expect { @str.reverse }.on_client_to eq @str.reverse
- end
+ it 'will copy local vars to the client' do
+ str = 'hello'
+ expect { str.reverse }.on_client_to eq str.reverse
+ end
- it 'will copy memoized values to the client' do
- expect { another_string.gsub(/\W/, '') }.on_client_to eq another_string.gsub(/\W/, '')
- end
+ it 'will copy instance vars to the client' do
+ expect { @str.reverse }.on_client_to eq @str.reverse
+ end
- it 'will deal with unserailized local vars, instance vars and memoized values correctly' do
- foo_bar = page
- expect do
- evaluate_ruby { foo_bar }
- end.to raise_error(Exception, /foo_bar/)
- end
+ it 'will copy memoized values to the client' do
+ expect { another_string.gsub(/\W/, '') }.on_client_to eq another_string.gsub(/\W/, '')
+ end
- it 'will ignore unserailized local vars, instance vars and memoized values if not accessed' do
- foo_bar = page
- good_value = 12
- expect { good_value * 2 }.on_client_to eq good_value * 2
- end
+ it 'will deal with unserailized local vars, instance vars and memoized values correctly' do
+ foo_bar = page
+ expect do
+ evaluate_ruby { foo_bar }
+ end.to raise_error(Exception, /foo_bar/)
+ end
- it 'will allow unserailized local vars, instance vars and memoized values can be redefined on the client' do
- foo_bar = page
- expect do
- foo_bar = 12
- foo_bar * 2
- end.on_client_to eq 24
+ it 'will ignore unserailized local vars, instance vars and memoized values if not accessed' do
+ foo_bar = page
+ good_value = 12
+ expect { good_value * 2 }.on_client_to eq good_value * 2
+ end
+
+ it 'will allow unserailized local vars, instance vars and memoized values can be redefined on the client' do
+ foo_bar = page
+ expect do
+ foo_bar = 12
+ foo_bar * 2
+ end.on_client_to eq 24
+ end
+
+ context 'the include_vars option' do
+ [false, nil, []].each do |include_vars|
+ it "will not copy any vars if the include_vars option is #{include_vars}" do
+ client_option include_vars: include_vars
+ @instance_var = true
+ local_var = true
+ expect { @instance_var }.on_client_to be_nil
+ expect { defined?(local_var) }.on_client_to be_falsy
+ expect { defined?(memoized_var) }.on_client_to be_falsy
+ end
+ end
+ it "will copy all the vars if the include_vars option is a non-array truthy value" do
+ client_option include_vars: 123
+ @instance_var = true
+ local_var = true
+ expect { @instance_var }.on_client_to be true
+ expect { local_var }.on_client_to be true
+ expect { memoized_var }.on_client_to be true
+ end
+ %i[@instance_var memoized_var local_var].each do |var|
+ it "will copy only a single var if the include_vars option is a name like #{var}" do
+ client_option include_vars: var
+ @instance_var = true
+ local_var = true
+ expect { @instance_var.nil? }.on_client_to eq(var != :@instance_var)
+ expect { !!defined?(local_var) }.on_client_to eq(var == :local_var)
+ expect { !!defined?(memoized_var) }.on_client_to eq(var == :memoized_var)
+ end
+ end
+ it 'will only copy vars listed in the include_vars option' do
+ client_option include_vars: [:another_memoized_var, :@another_instance_var, :another_local_var]
+ @instance_var = true
+ local_var = true
+ @another_instance_var = true
+ another_local_var = true
+ expect { @instance_var }.on_client_to be_nil
+ expect { defined?(local_var) }.on_client_to be_falsy
+ expect { defined?(memoized_var) }.on_client_to be_falsy
+ expect { @another_instance_var }.on_client_to be true
+ expect { another_local_var }.on_client_to be true
+ expect { another_memoized_var }.on_client_to be true
+ end
+ end
+
+ context 'the exclude_vars option' do
+ [false, nil, []].each do |exclude_vars|
+ it "will copy all vars if the exclude_vars option is #{exclude_vars}" do
+ client_option exclude_vars: exclude_vars
+ @instance_var = true
+ local_var = true
+ expect { @instance_var }.on_client_to be true
+ expect { local_var }.on_client_to be true
+ expect { memoized_var }.on_client_to be true
+ end
+ end
+ it "will not copy any vars if the exclude_vars option is a non-array truthy value" do
+ client_option exclude_vars: 123
+ @instance_var = true
+ local_var = true
+ expect { @instance_var }.on_client_to be_nil
+ expect { defined?(local_var) }.on_client_to be_falsy
+ expect { defined?(memoized_var) }.on_client_to be_falsy
+ end
+ %i[@instance_var memoized_var local_var].each do |var|
+ it "will exclude a single var if the exclude_vars option is a name like #{var}" do
+ client_option exclude_vars: var
+ @instance_var = true
+ local_var = true
+ expect { @instance_var.nil? }.on_client_to eq(var == :@instance_var)
+ expect { !!defined?(local_var) }.on_client_to eq(var != :local_var)
+ expect { !!defined?(memoized_var) }.on_client_to eq(var != :memoized_var)
+ end
+ end
+ it 'will not copy vars listed in the exclude_vars option' do
+ client_option exclude_vars: [:memoized_var, :@instance_var, :local_var]
+ @instance_var = true
+ local_var = true
+ @another_instance_var = true
+ another_local_var = true
+ expect { @instance_var }.on_client_to be_nil
+ expect { defined?(local_var) }.on_client_to be_falsy
+ expect { defined?(memoized_var) }.on_client_to be_falsy
+ expect { @another_instance_var }.on_client_to be true
+ expect { another_local_var }.on_client_to be true
+ expect { another_memoized_var }.on_client_to be true
+ end
+ end
end
it 'aliases evaluate_ruby as on_client and c?' do
From 17e99db5b8004775734401032f528087e0d64ee9 Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 19 Feb 2021 20:40:36 -0500
Subject: [PATCH 089/307] fixed hyper-operation monkey patch for new hyper-spec
compatibility
---
ruby/hyper-operation/spec/spec_helper.rb | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/ruby/hyper-operation/spec/spec_helper.rb b/ruby/hyper-operation/spec/spec_helper.rb
index b7432f835..c773c3b06 100644
--- a/ruby/hyper-operation/spec/spec_helper.rb
+++ b/ruby/hyper-operation/spec/spec_helper.rb
@@ -137,7 +137,7 @@ def self.on_server?
end
module HyperSpec
- module ComponentTestHelpers
+ module Helpers
alias old_expect_promise expect_promise
def expect_promise(str_or_promise = nil, &block)
if str_or_promise.is_a? Promise
From cbfd8de4abc7241bb8e0d861234e04ff860fcaec Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 19 Feb 2021 21:38:26 -0500
Subject: [PATCH 090/307] use internal_evaluate_ruby instead of on_client for
backwards compatibility
---
docs/hyper-spec/{02-tutorial => 02-tutorial.md} | 0
ruby/hyper-spec/lib/hyper-spec/internal/time_cop.rb | 4 ++--
2 files changed, 2 insertions(+), 2 deletions(-)
rename docs/hyper-spec/{02-tutorial => 02-tutorial.md} (100%)
diff --git a/docs/hyper-spec/02-tutorial b/docs/hyper-spec/02-tutorial.md
similarity index 100%
rename from docs/hyper-spec/02-tutorial
rename to docs/hyper-spec/02-tutorial.md
diff --git a/ruby/hyper-spec/lib/hyper-spec/internal/time_cop.rb b/ruby/hyper-spec/lib/hyper-spec/internal/time_cop.rb
index faf8d8de8..35437a9f2 100644
--- a/ruby/hyper-spec/lib/hyper-spec/internal/time_cop.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/time_cop.rb
@@ -148,7 +148,7 @@ def pending_evaluations
def evaluate_ruby(&block)
if @capybara_page
- @capybara_page.on_client(yield)
+ @capybara_page.internal_evaluate_ruby(yield)
else
pending_evaluations << block
end
@@ -156,7 +156,7 @@ def evaluate_ruby(&block)
def run_pending_evaluations
return if pending_evaluations.empty?
- @capybara_page.on_client(pending_evaluations.collect(&:call).join("\n"))
+ @capybara_page.internal_evaluate_ruby(pending_evaluations.collect(&:call).join("\n"))
@pending_evaluations ||= []
end
end
From 8c3be119bd5183c5f6bfa9f9dcece87e70267678 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 20 Feb 2021 10:17:37 -0500
Subject: [PATCH 091/307] doc and code cleanups added insert_html spec
---
docs/hyper-spec/02-tutorial.md | 6 +-
.../03-hyperspec-methods-and-features.md | 57 ++++++++++++-------
.../hyper-spec/internal/component_mount.rb | 2 +
ruby/hyper-spec/spec/hyper_spec.rb | 10 +++-
4 files changed, 49 insertions(+), 26 deletions(-)
diff --git a/docs/hyper-spec/02-tutorial.md b/docs/hyper-spec/02-tutorial.md
index 8d99964a4..d988dc86c 100644
--- a/docs/hyper-spec/02-tutorial.md
+++ b/docs/hyper-spec/02-tutorial.md
@@ -71,13 +71,13 @@ end
If you are familiar with Capybara then the first spec should
look similar to an integration spec. The difference is instead
of visiting a page, we `mount` the `OrdersShipped` component on a blank page
-that hyper-spec will set up for us. This let's us unit test
+that hyper-spec will set up for us. This lets us unit test
components outside of any application specific view logic.
> Note that like Capybara we indicate that a client environment should
> be set up by adding the :js tag.
-Once mounted we can use Capybara finders and matchers, to check
+Once mounted we can use Capybara finders and matchers to check
if our content is as expected. Because we are running on the server
we can easily add and delete orders, and check the response on the UI.
@@ -96,7 +96,7 @@ will see will continue to be available to us later in the spec.
> something like `let` be used here instead of an instance variable. Shall we
> say its on the todo list.
-Now that we have our test component setup we can test it's `format_number`
+Now that we have our test component setup we can test its `format_number`
method. To do this we put the test expression in a block followed by
`on_client_to`. Again the block will be compiled using Opal, executed on
the client, and the result will be returned to the expectation.
diff --git a/docs/hyper-spec/03-hyperspec-methods-and-features.md b/docs/hyper-spec/03-hyperspec-methods-and-features.md
index dc33a4434..448bd0d57 100644
--- a/docs/hyper-spec/03-hyperspec-methods-and-features.md
+++ b/docs/hyper-spec/03-hyperspec-methods-and-features.md
@@ -8,6 +8,7 @@ These can be used any where within your specs:
+ [`isomorphic`](#the-isomorphic-method) - executes code on the client *and* the server
+ [`mount`](#mounting-components) - mounts a hyperstack component in an empty window
+ [`before_mount`](#before_mount) - specifies a block of code to be executed before the first call to `mount`, `isomorphic` or `on_client`
++ [`insert_html`](#insert_html) - insert some html into a page
+ [`client_options`](#client-initialization-options) - allows options to be specified globally
+ [`run_on_client`](#run_on_client) - same as `on_client` but no value is returned
+ [`reload_page`](#reload_page) - resets the page environment
@@ -50,7 +51,8 @@ in addition
The following methods are used primarly at a debug break point, most require you use binding.pry as your debugger:
-+ [`to_js`](#to_js) - returns the ruby code compiled to JS.
++ [`to_js`](#to_js) - returns the ruby code compiled to JS.
++ [`c?`](#c?) - alias for `on_client`.
+ [`ppr`](#ppr) - print the results of the ruby expression on the client console.
+ [`debugger`](#debugger) - Sets a debug breakpoint on code running on the client.
+ [`open_in_chrome`](#open_in_chrome) - Opens a chrome browser that will load the current state.
@@ -65,7 +67,7 @@ DRIVER=chrome bundle exec rspec
### Timecop Integration
-You can use the Timecop gem to control the flow of time within your specs. Hyperspec will coordinate things with the client so the time on the client is kept in sync with the time on the server. So for example if you use Timecop to advance time 1 day on the server, time on the browser will also advance by one day.
+You can use the [`timecop` gem](https://github.com/travisjeffery/timecop) to control the flow of time within your specs. Hyperspec will coordinate things with the client so the time on the client is kept in sync with the time on the server. So for example if you use Timecop to advance time 1 day on the server, time on the browser will also advance by one day.
See the [Client Initialization Options](#client-initialization-options) section for how to control the client time zone, and clock resolution.
@@ -133,7 +135,7 @@ across blocks executed on the client. For example:
end
```
-> Be especially careful of this this when using the [`no_reset`](#the-no_reset-flag) as instance variables will retain their values between each spec in this mode.
+> Be especially careful of this when using the [`no_reset`](#the-no_reset-flag) as instance variables will retain their values between each spec in this mode.
#### White and Black Listing Variables
@@ -164,7 +166,15 @@ Examples:
Note that the exclude_vars list will take precedence over the include_vars list.
-The exclude/include lists can be overridden on an individual spec using the `with` method - See [Client Expectation Targets](#client-expectation-targets).
+The exclude/include lists can be overridden on an individual call to on_client by providing a hash of names and values to on_client:
+
+```ruby
+ result = on_client(var: 12) { var * var }
+ expect(result).to eq(144)
+```
+
+You can do the same thing on expectations using the `with` method - See [Client Expectation Targets](#client-expectation-targets).
+
### The `isomorphic` method
@@ -196,7 +206,7 @@ Example: `client_option time_zone: 'Hawaii'`
+ `exclude_vars`: black list of all vars not to be copied to the client. See [Accessing Variables on the Client](#accessing-variables-on-the-client) for details.
+ `render_on`: `:client_only` (default), `:server_only`, or `:both`
Hyperstack components can be prerendered on the server. The `render_on` option controls this feature. For example `server_only` is useful to insure components are properly prerendered. *See the `mount` method [below](#mounting-components) for more details on rendering components*
-+ `no_wait`: After the page is loaded the system will by default wait until all javascript requests to the server complete, before proceeding. Specifying `no_wait: true` will skip this.
++ `no_wait`: After the page is loaded the system will by default wait until all javascript requests to the server complete before proceeding. Specifying `no_wait: true` will skip this.
+ `javascript`: The javascript asset to load when mounting the component. By default it will be `application` (.js is assumed). Note that the standard Hyperstack configuration will compile all the client side Ruby assets as well as javascript packages into the `application.js` file, so the default will work fine.
+ `style_sheet`: The style sheet asset to load when mounting the component. By default it will be `application` (.css is assumed).
+ `controller` - **(expert zone!)** specify a controller that will be used to mount the
@@ -287,6 +297,12 @@ Specifies a block of code to be executed before the first call to `mount`, `isom
> Unlike `mount`, `isomorphic` and `on_client`, `before_mount` does not load the client page, but will wait for the first of the other methods to be called.
+#### `add_class`
+
+Adds a CSS class. The first parameter is the name of the class, and the second is a hash of styles, represented in the React [style format.](https://reactjs.org/docs/dom-elements.html#style)
+
+Example: `add_class :some_class, borderStyle: :solid` adds a class with style `border-style: 'solid'`
+
#### `run_on_client`
same as `on_client` but no value is returned. Useful when the return value may be too complex to marshall and unmarshall using JSON.
@@ -295,12 +311,6 @@ same as `on_client` but no value is returned. Useful when the return value may
Shorthand for `mount` with no parameters. Useful if you need to reset the client within a spec.
-#### `add_class`
-
-Adds a CSS class. The first parameter is the name of the class, and the second is a hash of styles, represented in the React [style format.](https://reactjs.org/docs/dom-elements.html#style)
-
-Example: `add_class :some_class, borderStyle: :solid` adds a class with style `border-style: 'solid'`
-
#### `size_window`
Indicates the size of the browser window. The values can be given either symbolically or as two numbers (width and height). Predefined sizes are:
@@ -323,6 +333,11 @@ So for example the following are all equivalent:
returns any `ActiveModel` attributes loaded on the client. HyperModel will normally begin a load cycle as soon as you access the attribute on the client. However it is sometimes useful to see what attributes have already been loaded.
+#### `insert_html`
+
+takes a string and inserts it into test page when it is mounted. Useful for testing code that is not dependent on Hyper Components.
+For example an Opal library that adds some jQuery extensions.
+
### Client Expectation Targets
These can be used within expectations replacing the `to` and `not_to` methods. The expectation expression must be inclosed in a block.
@@ -370,6 +385,15 @@ By default HyperSpec will copy all local variables, memoized variables, and inst
These methods are primarily designed to help debug code and specs.
+#### `c?`
+
+Shorthand for `on_console`, useful for entering expressions in pry console, to investigate the state of the client.
+
+```ruby
+pry:> c? { puts 'hello on the console' } # prints hello on the client
+-> nil
+```
+
#### `to_js`
Takes a block like `on_client` but rather than running the code on the client, simply returns the resulting code. This is useful for debugging obscure problems when the Opal compiler or some feature of
@@ -391,15 +415,6 @@ This is useful when the result cannot be usefully returned to the server,
or when the result of interest is better looked at as the raw
javascript object.
-#### `c?`
-
-Shorthand for `on_console`, useful for entering expressions in pry console, to investigate the state of the client.
-
-```ruby
-pry:> c? { puts 'hello on the console' } # prints hello on the client
--> nil
-```
-
#### `debugger`
This psuedo method can be inserted into any code executed on the client. It will cause the code to stop, and enter a *javascript* read-eval loop, within the debug console.
@@ -422,4 +437,4 @@ You can also run specs in a visible chrome window by setting the `DRIVER` enviro
#### `pause`
The method is typically not needed assuming you are using a multithreaded server like Puma. If for whatever reason the pry debug session is not multithreaded, *and* you want to try some kind of experiment on the javascript console, *and* those experiments make requests to the server, you may not get a response, because all threads are in use.
-You can resolve this by using the `pause` method in the debug session which will put the debug session into a non-blocking loop. You then release the pause by executing `go()` in the *javascript* debug console.
+You can resolve this by using the `pause` method in the debug session which will put the server debug session into a non-blocking loop. You can then experiment in the JS console, and when done release the pause by executing `go()` in the *javascript* debug console.
diff --git a/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb b/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb
index 04d90a11e..380121be3 100644
--- a/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb
@@ -55,11 +55,13 @@ def build_test_url_for(controller = nil, ping = nil)
def insure_page_loaded(only_if_code_or_html_exists = nil)
return if only_if_code_or_html_exists && !@_hyperspec_private_client_code && !@_hyperspec_private_html_block
+
# if we are not resetting between examples, or think its mounted
# then look for Opal, but if we can't find it, then ping to clear and try again
if !HyperSpec.reset_between_examples? || page.instance_variable_get('@hyper_spec_mounted')
r = evaluate_script('Opal && true') rescue nil
return if r
+
page.visit build_test_url_for(nil, true) rescue nil
end
load_page
diff --git a/ruby/hyper-spec/spec/hyper_spec.rb b/ruby/hyper-spec/spec/hyper_spec.rb
index f9456502a..7d14a4f2c 100644
--- a/ruby/hyper-spec/spec/hyper_spec.rb
+++ b/ruby/hyper-spec/spec/hyper_spec.rb
@@ -2,8 +2,6 @@
describe 'hyper-spec', js: true do
- # after(:each) { |e| binding.pry if e.exception }
-
it 'can visit a page' do
visit 'test'
end
@@ -23,6 +21,14 @@ class ShowOff
expect(page).to have_content('Now how cool is that???')
end
+ it 'can add some html code before mounting' do
+ insert_html <<-HTML
+
insert some code
+ HTML
+ mount
+ expect(page).to have_content('insert some code')
+ end
+
context "the client_option method" do
it "can render server side only", :prerendering_on do
From fd5e4ad17feab31611a3fbc0a020bc945b748d4c Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 20 Feb 2021 10:20:08 -0500
Subject: [PATCH 092/307] removed libv8 dependency
---
ruby/hyper-spec/hyper-spec.gemspec | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/ruby/hyper-spec/hyper-spec.gemspec b/ruby/hyper-spec/hyper-spec.gemspec
index b86e9fce3..2efb449dc 100644
--- a/ruby/hyper-spec/hyper-spec.gemspec
+++ b/ruby/hyper-spec/hyper-spec.gemspec
@@ -28,7 +28,7 @@ Gem::Specification.new do |spec| # rubocop:disable Metrics/BlockLength
spec.add_dependency 'capybara'
spec.add_dependency 'chromedriver-helper', '1.2.0'
spec.add_dependency 'filecache'
- spec.add_dependency 'libv8', '~> 7.3.492.27.1'
+ # spec.add_dependency 'libv8', '~> 7.3.492.27.1'
spec.add_dependency 'method_source'
spec.add_dependency 'opal', ENV['OPAL_VERSION'] || '>= 0.11.0', '< 2.0'
spec.add_dependency 'parser', '>= 2.3.3.1' # on rails-6 this is now >= 2.3
From 260fea483a982bc114d02b17c4b76a20b1275039 Mon Sep 17 00:00:00 2001
From: Michail
Date: Sat, 20 Feb 2021 17:43:50 +0200
Subject: [PATCH 093/307] correctly set react variant in production
---
ruby/hyper-component/lib/react/react-source.rb | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/ruby/hyper-component/lib/react/react-source.rb b/ruby/hyper-component/lib/react/react-source.rb
index 23acdcf1d..cbe9b9f07 100644
--- a/ruby/hyper-component/lib/react/react-source.rb
+++ b/ruby/hyper-component/lib/react/react-source.rb
@@ -11,7 +11,7 @@
else
require "hyperstack/internal/component"
require "react/rails/asset_variant"
- variant = Hyperstack.env.production? ? 'production' : 'development'
- react_directory = React::Rails::AssetVariant.new({environment: variant}).react_directory
+ variant = Hyperstack.env.production? ? :production : :development
+ react_directory = React::Rails::AssetVariant.new({ variant: variant }).react_directory
Opal.append_path react_directory.untaint
end
From 8052a7ea083315ebc695a641daedaa0a74e7fa66 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 20 Feb 2021 11:19:19 -0500
Subject: [PATCH 094/307] closes #353
---
.../batch1/policies/regulate_broadcast_spec.rb | 15 ++++++++++++++-
.../lib/hyper-operation/transport/policy.rb | 11 ++++++++---
2 files changed, 22 insertions(+), 4 deletions(-)
diff --git a/ruby/hyper-model/spec/batch1/policies/regulate_broadcast_spec.rb b/ruby/hyper-model/spec/batch1/policies/regulate_broadcast_spec.rb
index c5d412dc8..fc9e626a3 100644
--- a/ruby/hyper-model/spec/batch1/policies/regulate_broadcast_spec.rb
+++ b/ruby/hyper-model/spec/batch1/policies/regulate_broadcast_spec.rb
@@ -56,7 +56,7 @@ def saved_changes
)
end
- it "will raise an error if the policy is not sent" do
+ it "will raise an error if the to method is not used" do
stub_const "TestModel1Policy", Class.new
TestModel1Policy.class_eval do
regulate_broadcast do | policy |
@@ -68,6 +68,19 @@ def saved_changes
to raise_error("TestModel1 instance broadcast policy not sent to any channel")
end
+ it "will not raise an error if sending to the empty set" do
+ stub_const "TestModel1Policy", Class.new
+ TestModel1Policy.class_eval do
+ regulate_broadcast do | policy |
+ policy.send_all.to
+ end
+ end
+ model = TestModel1.new(id: 1, attr1: 1, attr2: 2, attr3: 3, attr4: 4, attr5: 5)
+ expect { |b| Hyperstack::InternalPolicy.regulate_broadcast(model, &b) }.
+ not_to raise_error("TestModel1 instance broadcast policy not sent to any channel")
+ end
+
+
it "will intersect all policies for the same channel" do
stub_const "TestModel1Policy", Class.new
TestModel1Policy.class_eval do
diff --git a/ruby/hyper-operation/lib/hyper-operation/transport/policy.rb b/ruby/hyper-operation/lib/hyper-operation/transport/policy.rb
index b7dc4c118..ee362d878 100644
--- a/ruby/hyper-operation/lib/hyper-operation/transport/policy.rb
+++ b/ruby/hyper-operation/lib/hyper-operation/transport/policy.rb
@@ -328,9 +328,9 @@ def self.broadcast(instance, policy)
regulations[instance].regulations.each do |regulation|
instance.instance_exec wrap_policy(policy, regulation), ®ulation
end
- if policy.has_unassigned_sets?
- raise "#{instance.class.name} instance broadcast policy not sent to any channel"
- end
+ return if policy.has_to_been_called?
+
+ raise "#{instance.class.name} instance broadcast policy not sent to any channel"
end
end
@@ -425,12 +425,17 @@ def add_unassigned_send_set(send_set)
end
def send_set_to(send_set, channels)
+ @to_has_been_called = true
channels.flatten(1).each do |channel|
merge_set(send_set, channel) if channel_available? channel
@unassigned_send_sets.delete(send_set)
end
end
+ def has_to_been_called?
+ !has_unassigned_sets? || @to_has_been_called
+ end
+
def merge_set(send_set, channel)
return unless channel
channel = channel.name if channel.is_a?(Class) && channel.name
From a5ccc5a280874529257d8b535bebedb0b4654406 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 20 Feb 2021 12:46:59 -0500
Subject: [PATCH 095/307] fixing hyper-router dependency problem
---
ruby/hyper-router/hyper-router.gemspec | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/ruby/hyper-router/hyper-router.gemspec b/ruby/hyper-router/hyper-router.gemspec
index a7447895c..2418fc684 100644
--- a/ruby/hyper-router/hyper-router.gemspec
+++ b/ruby/hyper-router/hyper-router.gemspec
@@ -23,7 +23,7 @@ Gem::Specification.new do |spec|
spec.add_development_dependency 'hyper-spec', HyperRouter::VERSION
spec.add_development_dependency 'hyper-store', HyperRouter::VERSION
spec.add_development_dependency 'listen'
- spec.add_development_dependency 'mini_racer', '~> 0.2.6'
+ spec.add_development_dependency 'mini_racer'
spec.add_development_dependency 'opal-rails', '>= 0.9.4', '< 2.0.0'
spec.add_development_dependency 'pry-rescue'
spec.add_development_dependency 'pry-stack_explorer'
From 5bb9541584c7c28aabdec5fb00fe1a40c5bfc9c1 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 20 Feb 2021 14:33:51 -0500
Subject: [PATCH 096/307] closes #347
---
ruby/hyper-component/hyper-component.gemspec | 1 -
.../lib/generators/hyperstack/install_generator.rb | 12 +++++++++---
2 files changed, 9 insertions(+), 4 deletions(-)
diff --git a/ruby/hyper-component/hyper-component.gemspec b/ruby/hyper-component/hyper-component.gemspec
index 4fd919aed..28c736877 100644
--- a/ruby/hyper-component/hyper-component.gemspec
+++ b/ruby/hyper-component/hyper-component.gemspec
@@ -23,7 +23,6 @@ Gem::Specification.new do |spec|
spec.add_dependency 'hyper-state', Hyperstack::Component::VERSION
spec.add_dependency 'hyperstack-config', Hyperstack::Component::VERSION
- # spec.add_dependency 'libv8', '~> 7.3.492.27.1'
spec.add_dependency 'opal-activesupport', '~> 0.3.1'
spec.add_dependency 'react-rails', '>= 2.4.0', '< 2.5.0'
diff --git a/ruby/rails-hyperstack/lib/generators/hyperstack/install_generator.rb b/ruby/rails-hyperstack/lib/generators/hyperstack/install_generator.rb
index c6e1c7529..9b6b5b15a 100644
--- a/ruby/rails-hyperstack/lib/generators/hyperstack/install_generator.rb
+++ b/ruby/rails-hyperstack/lib/generators/hyperstack/install_generator.rb
@@ -92,6 +92,7 @@ def add_webpacker_manifests
def add_webpacks
return if skip_webpack?
+
yarn 'react', '16'
yarn 'react-dom', '16'
yarn 'react-router', '^5.0.0'
@@ -102,10 +103,15 @@ def add_webpacks
end
def cancel_react_source_import
- return if skip_webpack?
inject_into_initializer(
- "Hyperstack.cancel_import 'react/react-source-browser' "\
- '# bring your own React and ReactRouter via Yarn/Webpacker'
+ if skip_webpack?
+ "Hyperstack.import 'react/react-source-browser' "\
+ "# bring in hyperstack's copy of react, comment this out "\
+ 'if you bring it in from webpacker'
+ else
+ "# Hyperstack.import 'react/react-source-browser' "\
+ '# uncomment this line if you want hyperstack to use its copy of react'
+ end
)
end
From 7bf2bb1638c4c55abc3df5ff1ff0503ffb90da29 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 20 Feb 2021 14:53:53 -0500
Subject: [PATCH 097/307] removed hard dependency on Firefox driver
---
ruby/hyper-spec/lib/hyper-spec.rb | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/ruby/hyper-spec/lib/hyper-spec.rb b/ruby/hyper-spec/lib/hyper-spec.rb
index 07f8a1927..2b9749689 100644
--- a/ruby/hyper-spec/lib/hyper-spec.rb
+++ b/ruby/hyper-spec/lib/hyper-spec.rb
@@ -203,7 +203,7 @@ def self.on_server?
options = Selenium::WebDriver::Firefox::Options.new
options.headless!
Capybara::Selenium::Driver.new(app, browser: :firefox, options: options)
- end
+ end if defined?(Selenium::WebDriver::Firefox)
Capybara.register_driver :selenium_with_firebug do |app|
profile = Selenium::WebDriver::Firefox::Profile.new
@@ -211,7 +211,7 @@ def self.on_server?
profile.enable_firebug
options = Selenium::WebDriver::Firefox::Options.new(profile: profile)
Capybara::Selenium::Driver.new(app, browser: :firefox, options: options)
- end
+ end if defined?(Selenium::WebDriver::Firefox)
Capybara.register_driver :safari do |app|
Capybara::Selenium::Driver.new(app, browser: :safari)
From 9e6a341a6602cd207a37c2a16ec160bf7939fa29 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 20 Feb 2021 15:01:57 -0500
Subject: [PATCH 098/307] still fixing the missing firefox problem
---
ruby/hyper-spec/lib/hyper-spec.rb | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/ruby/hyper-spec/lib/hyper-spec.rb b/ruby/hyper-spec/lib/hyper-spec.rb
index 2b9749689..c64643980 100644
--- a/ruby/hyper-spec/lib/hyper-spec.rb
+++ b/ruby/hyper-spec/lib/hyper-spec.rb
@@ -23,7 +23,7 @@
require 'hyper-spec/expectations'
require 'parser/current'
-require 'selenium/web_driver/firefox/profile'
+require 'selenium/web_driver/firefox/profile' if defined?(Selenium::WebDriver::Firefox)
require 'selenium-webdriver'
require 'hyper-spec/version'
From aff85599827359205c0b2fc67cd1a7d6f9628820 Mon Sep 17 00:00:00 2001
From: catmando
Date: Mon, 22 Feb 2021 14:44:16 -0500
Subject: [PATCH 099/307] first attempt a fix for #358
---
.../lib/reactive_record/active_record/instance_methods.rb | 3 ---
ruby/hyper-model/lib/reactive_record/server_data_cache.rb | 4 ++--
2 files changed, 2 insertions(+), 5 deletions(-)
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/instance_methods.rb b/ruby/hyper-model/lib/reactive_record/active_record/instance_methods.rb
index 7b3969884..361b6844d 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/instance_methods.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/instance_methods.rb
@@ -44,9 +44,6 @@ def method_missing(missing, *args, &block)
end
end
- # ignore load_from_json when it calls _hyperstack_internal_setter_id
- def _hyperstack_internal_setter_id(*); end
-
# the system assumes that there is "virtual" model_name and type attribute so
# we define the internal setter here. If the user defines some other attributes
# or uses these names no harm is done since the exact same method would have been
diff --git a/ruby/hyper-model/lib/reactive_record/server_data_cache.rb b/ruby/hyper-model/lib/reactive_record/server_data_cache.rb
index 40b460098..e7f942953 100644
--- a/ruby/hyper-model/lib/reactive_record/server_data_cache.rb
+++ b/ruby/hyper-model/lib/reactive_record/server_data_cache.rb
@@ -474,7 +474,7 @@ def self.load_from_json(tree, target = nil)
end
end
- if id_value = tree["id"] and id_value.is_a? Array
+ if (id_value = tree[target.class.try(:primary_key)]) && id_value.is_a?(Array)
target.id = id_value.first
end
tree.each do |method, value|
@@ -506,7 +506,7 @@ def self.load_from_json(tree, target = nil)
target.send "#{method}=", value.first
elsif value.is_a? Array
- target.send("_hyperstack_internal_setter_#{method}", value.first)
+ target.send("_hyperstack_internal_setter_#{method}", value.first) unless method == target.class.primary_key
elsif value.is_a?(Hash) && value[:id] && value[:id].first && (association = target.class.reflect_on_association(method))
# not sure if its necessary to check the id above... is it possible to for the method to be an association but not have an id?
klass = value[:model_name] ? Object.const_get(value[:model_name].first) : association.klass
From 0c9ecedc43be7dfb2248dca4cb9c2a3c0c59769a Mon Sep 17 00:00:00 2001
From: catmando
Date: Mon, 22 Feb 2021 17:30:21 -0500
Subject: [PATCH 100/307] fixed pause with argument
---
ruby/hyper-spec/lib/hyper-spec/helpers.rb | 2 +-
ruby/hyper-spec/spec/hyper_spec.rb | 11 +++++++++++
2 files changed, 12 insertions(+), 1 deletion(-)
diff --git a/ruby/hyper-spec/lib/hyper-spec/helpers.rb b/ruby/hyper-spec/lib/hyper-spec/helpers.rb
index b769d6146..8fc2b5185 100644
--- a/ruby/hyper-spec/lib/hyper-spec/helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/helpers.rb
@@ -187,7 +187,7 @@ def attributes_on_client(model)
def pause(message = nil)
if message
puts message
- page.evaluate_ruby "puts #{message.inspect}.to_s + ' (type go() to continue)'"
+ internal_evaluate_ruby "puts #{message.inspect}.to_s + ' (type go() to continue)'"
end
page.evaluate_script('window.hyper_spec_waiting_for_go = true')
diff --git a/ruby/hyper-spec/spec/hyper_spec.rb b/ruby/hyper-spec/spec/hyper_spec.rb
index 7d14a4f2c..90cd4e8a7 100644
--- a/ruby/hyper-spec/spec/hyper_spec.rb
+++ b/ruby/hyper-spec/spec/hyper_spec.rb
@@ -29,6 +29,17 @@ class ShowOff
expect(page).to have_content('insert some code')
end
+ it 'can pause the server', skip: 'unreliable' do
+ # this is pretty ugly with these dead waits, but any attempt to do an evaluate_script "go()" without the
+ # wait breaks
+ th = Thread.new { pause('hello') }
+ sleep 5
+ expect(th).to be_alive
+ evaluate_script "go()"
+ sleep 1
+ expect(th).not_to be_alive
+ end
+
context "the client_option method" do
it "can render server side only", :prerendering_on do
From a5ada4f43c91b1b48aa5a910c386cce0657ba39f Mon Sep 17 00:00:00 2001
From: catmando
Date: Mon, 22 Feb 2021 19:14:59 -0500
Subject: [PATCH 101/307] first cut adding json attribute types plus using
postgresql on CI
---
.travis.yml | 150 +++++++++---------
ruby/hyper-model/hyper-model.gemspec | 2 +-
.../reactive_record/dummy_value.rb | 6 +
.../batch1/column_types/column_type_spec.rb | 38 +++--
.../app/hyperstack/models/default_test.rb | 2 +
.../app/hyperstack/models/type_test.rb | 4 +-
.../spec/test_app/config/database.yml | 43 +++--
ruby/hyper-model/spec/test_app/db/schema.rb | 119 --------------
8 files changed, 131 insertions(+), 233 deletions(-)
delete mode 100644 ruby/hyper-model/spec/test_app/db/schema.rb
diff --git a/.travis.yml b/.travis.yml
index 9bee9afb7..10ee1e4ce 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -1,3 +1,5 @@
+services:
+ - postgresql
language: bash
cache:
bundler: true
@@ -54,86 +56,86 @@ _deploy_gem: &_deploy_gem
tags: true
jobs:
include:
- - <<: *_test_gem
- env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1
- - <<: *_test_gem
- env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1
- - <<: *_test_gem
- env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
- - <<: *_test_gem
- env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1
- - <<: *_test_gem
- env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
- - <<: *_test_gem
- env: COMPONENT=hyper-component RUBY_VERSION=2.5.1
- - <<: *_test_gem
- env: COMPONENT=hyper-router RUBY_VERSION=2.5.1
- - <<: *_test_gem
- env: COMPONENT=hyper-store RUBY_VERSION=2.5.1
- - <<: *_test_gem
- env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1
- <<: *_test_gem
env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
- <<: *_test_gem
env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part2
- <<: *_test_gem
env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part3
- - <<: *_test_gem
- env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1
-
- - <<: *_test_gem
- env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
- - <<: *_test_gem
- env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-
- - <<: *_test_gem
- env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
- - <<: *_test_gem
- env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1
+ #
+ # - <<: *_test_gem
+ # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ #
+ # - <<: *_test_gem
+ # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- <<: *_deploy_gem
env: COMPONENT=hyper-i18n
diff --git a/ruby/hyper-model/hyper-model.gemspec b/ruby/hyper-model/hyper-model.gemspec
index 99c76614b..20e35b6b5 100644
--- a/ruby/hyper-model/hyper-model.gemspec
+++ b/ruby/hyper-model/hyper-model.gemspec
@@ -34,7 +34,7 @@ Gem::Specification.new do |spec|
spec.add_development_dependency 'factory_bot_rails'
spec.add_development_dependency 'hyper-spec', HyperModel::VERSION
spec.add_development_dependency 'mini_racer'
- spec.add_development_dependency 'mysql2'
+ spec.add_development_dependency 'pg'
spec.add_development_dependency 'opal-rails', '>= 0.9.4', '< 2.0'
spec.add_development_dependency 'pry-rescue'
spec.add_development_dependency 'pry-stack_explorer'
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/dummy_value.rb b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/dummy_value.rb
index d025a6e35..6b2b24e7c 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/dummy_value.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/dummy_value.rb
@@ -32,6 +32,12 @@ def build_default_value_for_nil
@column_hash[:default] || nil
end
+ def build_default_value_for_json
+ ::JSON.parse(@column_hash[:default]) if @column_hash[:default]
+ end
+
+ alias build_default_value_for_jsonb build_default_value_for_json
+
def build_default_value_for_datetime
if @column_hash[:default]
::Time.parse(@column_hash[:default].gsub(' ','T')+'+00:00')
diff --git a/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb b/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb
index c6ad92680..7c54007d2 100644
--- a/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb
+++ b/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb
@@ -35,7 +35,7 @@ def as_json
def time_only
utc_time = Timex.new(self).utc
start_time = Time.parse('2000-01-01T00:00:00.000-00:00').utc
- Timex.new (start_time+(utc_time-utc_time.beginning_of_day.to_i).to_i).localtime
+ Timex.new(start_time+(utc_time-utc_time.beginning_of_day.to_i).to_i).localtime
end
class << self
@@ -131,15 +131,17 @@ class DefaultTest < ActiveRecord::Base
string: "hello",
text: "goodby",
time: t,
- timestamp: t
+ timestamp: t,
+ json: {kind: :json},
+ jsonb: {kind: :jsonb}
)
- expect_evaluate_ruby do
+ expect do
TypeTest.columns_hash.collect do |attr, _info|
TypeTest.find(1).send(attr).class
end
- end.to eq([
+ end.to_on_client eq([
'Number', 'NilClass', 'Boolean', 'Date', 'Time', 'Number', 'Number', 'Number',
- 'Number', 'String', 'String', 'Time', 'Time'
+ 'Number', 'String', 'String', 'Time', 'Time', 'NilClass', 'NilClass'
])
check_errors
end
@@ -169,15 +171,15 @@ class DefaultTest < ActiveRecord::Base
string: "hello",
text: "goodby",
time: t,
- timestamp: t
+ timestamp: t # see default tests below for json and jsonb
)
- expect_evaluate_ruby do
+ expect do
t = TypeTest.find(1)
[
!t.boolean, t.date+1, t.datetime+2.days, t.decimal + 5, t.float + 6, t.integer + 7,
t.bigint + 8, t.string.length, t.text.length, t.time+3.days, t.timestamp+4.days
]
- end.to eq([
+ end.on_client_to eq([
true, "2001-01-02", (Timex.sqlmin+2.days).as_json, 5, 6, 7,
8, 0, 0, (Timex.sqlmin+3.days).as_json, (Timex.sqlmin+4.days).as_json
])
@@ -197,15 +199,17 @@ class DefaultTest < ActiveRecord::Base
string: "hello",
text: "goodby",
time: t.time,
- timestamp: t.time
+ timestamp: t.time,
+ json: {kind: :json},
+ jsonb: {kind: :jsonb}
)
- expect_promise do
- ReactiveRecord.load do
+ expect do
+ Hyperstack::Model.load do
TypeTest.columns_hash.collect do |attr, _info|
[TypeTest.find(1).send(attr).class, TypeTest.find(1).send(attr)]
end.flatten
end
- end.to eq([
+ end.to_then eq([
'Number', 1,
'NilClass', nil,
'Boolean', true,
@@ -218,7 +222,9 @@ class DefaultTest < ActiveRecord::Base
'String', 'hello',
'String', 'goodby',
'Time', t.time_only.as_json, # date is indeterminate for active record time
- 'Time', t.as_json
+ 'Time', t.as_json,
+ 'Hash', {'kind' => 'json'},
+ 'Hash', {'kind' => 'jsonb'}
])
check_errors
end
@@ -302,12 +308,14 @@ class DefaultTest < ActiveRecord::Base
[
t.string, t.date, t.datetime, t.integer_from_string, t.integer_from_int,
t.float_from_string, t.float_from_float,
- t.boolean_from_falsy_string, t.boolean_from_truthy_string, t.boolean_from_falsy_value
+ t.boolean_from_falsy_string, t.boolean_from_truthy_string, t.boolean_from_falsy_value,
+ t.json[:kind], t.jsonb[:kind] # the default for json and jsonb is nil so we will test dummy operations here
]
end.to eq([
"I'm a string!", r.date.as_json, Timex.new(r.datetime.localtime).as_json, 99, 98,
0.02, 0.01,
- false, true, false
+ false, true, false,
+ 'json', 'jsonb'
])
check_errors
end
diff --git a/ruby/hyper-model/spec/test_app/app/hyperstack/models/default_test.rb b/ruby/hyper-model/spec/test_app/app/hyperstack/models/default_test.rb
index f7433d6dc..82ce7fbd4 100644
--- a/ruby/hyper-model/spec/test_app/app/hyperstack/models/default_test.rb
+++ b/ruby/hyper-model/spec/test_app/app/hyperstack/models/default_test.rb
@@ -11,6 +11,8 @@ def self.build_tables
t.boolean :boolean_from_falsy_string, default: "OFF"
t.boolean :boolean_from_truthy_string, default: "something-else"
t.boolean :boolean_from_falsy_value, default: false
+ t.json :json, default: {kind: :json}
+ t.jsonb :jsonb, default: {kind: :jsonb}
end
end
end
diff --git a/ruby/hyper-model/spec/test_app/app/hyperstack/models/type_test.rb b/ruby/hyper-model/spec/test_app/app/hyperstack/models/type_test.rb
index 86b319a72..50fc55d53 100644
--- a/ruby/hyper-model/spec/test_app/app/hyperstack/models/type_test.rb
+++ b/ruby/hyper-model/spec/test_app/app/hyperstack/models/type_test.rb
@@ -13,6 +13,8 @@ def self.build_tables
t.text(:text)
t.time(:time)
t.timestamp(:timestamp)
+ t.json(:json)
+ t.jsonb(:jsonb)
end
end
-end
\ No newline at end of file
+end
diff --git a/ruby/hyper-model/spec/test_app/config/database.yml b/ruby/hyper-model/spec/test_app/config/database.yml
index ffe0fdf4f..ad8c9dd1c 100644
--- a/ruby/hyper-model/spec/test_app/config/database.yml
+++ b/ruby/hyper-model/spec/test_app/config/database.yml
@@ -4,10 +4,27 @@
# Ensure the SQLite 3 gem is defined in your Gemfile
# gem 'sqlite3'
#
+# default: &default
+# adapter: mysql2
+# encoding: utf8
+# username: root
+#
+# development:
+# <<: *default
+# database: hyper_mesh_development_db
+#
+# test:
+# <<: *default
+# database: hyper_mesh_test_db
+#
+# production:
+# <<: *default
+# database: hyper_mesh_production_db
+
default: &default
- adapter: mysql2
- encoding: utf8
- username: root
+ adapter: postgresql
+ pool: 5
+ timeout: 5000
development:
<<: *default
@@ -20,23 +37,3 @@ test:
production:
<<: *default
database: hyper_mesh_production_db
-
-# default: &default
-# adapter: sqlite3
-# pool: 5
-# timeout: 10000
-#
-# development:
-# <<: *default
-# database: db/development.sqlite3
-#
-# # Warning: The database defined as "test" will be erased and
-# # re-generated from your development database when you run "rake".
-# # Do not set this db to the same as development or production.
-# test:
-# <<: *default
-# database: db/test.sqlite3
-#
-# production:
-# <<: *default
-# database: db/production.sqlite3
diff --git a/ruby/hyper-model/spec/test_app/db/schema.rb b/ruby/hyper-model/spec/test_app/db/schema.rb
deleted file mode 100644
index d5f44084b..000000000
--- a/ruby/hyper-model/spec/test_app/db/schema.rb
+++ /dev/null
@@ -1,119 +0,0 @@
-# This file is auto-generated from the current state of the database. Instead
-# of editing this file, please use the migrations feature of Active Record to
-# incrementally modify your database, and then regenerate this schema definition.
-#
-# Note that this schema.rb definition is the authoritative source for your
-# database schema. If you need to create the application database on another
-# system, you should be using db:schema:load, not running all the migrations
-# from scratch. The latter is a flawed and unsustainable approach (the more migrations
-# you'll amass, the slower it'll run and the greater likelihood for issues).
-#
-# It's strongly recommended that you check this file into your version control system.
-
-ActiveRecord::Schema.define(version: 2016_07_31_182106) do
-
- create_table "addresses", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
- t.string "street"
- t.string "city"
- t.string "state"
- t.string "zip"
- t.datetime "created_at"
- t.datetime "updated_at"
- end
-
- create_table "bones", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
- t.integer "dog_id"
- end
-
- create_table "child_models", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
- t.string "child_attribute"
- t.bigint "test_model_id"
- t.index ["test_model_id"], name: "index_child_models_on_test_model_id"
- end
-
- create_table "comments", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
- t.text "comment"
- t.datetime "created_at"
- t.datetime "updated_at"
- t.bigint "todo_id"
- t.bigint "author_id"
- t.integer "user_id"
- t.integer "todo_item_id"
- t.index ["author_id"], name: "index_comments_on_author_id"
- t.index ["todo_id"], name: "index_comments_on_todo_id"
- end
-
- create_table "hyperstack_connections", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
- t.string "channel"
- t.string "session"
- t.datetime "created_at"
- t.datetime "expires_at"
- t.datetime "refresh_at"
- end
-
- create_table "hyperstack_queued_messages", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
- t.text "data"
- t.integer "connection_id"
- end
-
- create_table "pets", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
- t.integer "owner_id"
- end
-
- create_table "scratching_posts", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
- t.integer "cat_id"
- end
-
- create_table "test_models", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
- t.string "test_attribute"
- t.boolean "completed"
- t.datetime "created_at", null: false
- t.datetime "updated_at", null: false
- end
-
- create_table "todo_items", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
- t.string "title"
- t.text "description"
- t.boolean "complete"
- t.datetime "created_at"
- t.datetime "updated_at"
- t.integer "user_id"
- t.integer "comment_id"
- end
-
- create_table "todos", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
- t.string "title"
- t.text "description"
- t.datetime "created_at", null: false
- t.datetime "updated_at", null: false
- t.boolean "completed", default: false, null: false
- t.bigint "created_by_id"
- t.bigint "owner_id"
- t.index ["created_by_id"], name: "index_todos_on_created_by_id"
- t.index ["owner_id"], name: "index_todos_on_owner_id"
- end
-
- create_table "users", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
- t.string "role"
- t.bigint "manager_id"
- t.string "first_name"
- t.string "last_name"
- t.string "email"
- t.datetime "created_at"
- t.datetime "updated_at"
- t.string "address_street"
- t.string "address_city"
- t.string "address_state"
- t.string "address_zip"
- t.integer "address_id"
- t.string "address2_street"
- t.string "address2_city"
- t.string "address2_state"
- t.string "address2_zip"
- t.string "data_string"
- t.integer "data_times"
- t.integer "test_enum"
- t.index ["manager_id"], name: "index_users_on_manager_id"
- end
-
-end
From a2d066fb032d240e70087e19649c0c7e36a77ae4 Mon Sep 17 00:00:00 2001
From: catmando
Date: Mon, 22 Feb 2021 19:29:06 -0500
Subject: [PATCH 102/307] trying to get travis working
---
.travis.yml | 1 +
1 file changed, 1 insertion(+)
diff --git a/.travis.yml b/.travis.yml
index 10ee1e4ce..975294295 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -34,6 +34,7 @@ _test_gem: &_test_gem
- echo before_script $COMPONENT
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
+ - psql -c 'create database hyper_mesh_test_db;' -U postgres
- bundle exec rake spec:prepare
- google-chrome --version
- which google-chrome
From 579b5438aa192031f8433bc5307258a5712b516c Mon Sep 17 00:00:00 2001
From: catmando
Date: Mon, 22 Feb 2021 19:37:22 -0500
Subject: [PATCH 103/307] trying to get travis working
---
.travis.yml | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 975294295..93e60ba60 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -1,5 +1,3 @@
-services:
- - postgresql
language: bash
cache:
bundler: true
@@ -8,6 +6,8 @@ cache:
_test_gem: &_test_gem
stage: test
+ services:
+ - postgresql
addons:
apt:
sources:
@@ -20,7 +20,7 @@ _test_gem: &_test_gem
- google-chrome-stable
- yarn
- redis-server
- mariadb: '10.3'
+ #mariadb: '10.3'
before_install:
- echo installing $COMPONENT
# yarn is in /usr/local/bin/yarn version 1.3.2 and is not a package
From 5385607df0dbd0f70722eda4afa4246ebaff1cc7 Mon Sep 17 00:00:00 2001
From: catmando
Date: Mon, 22 Feb 2021 19:47:22 -0500
Subject: [PATCH 104/307] trying to get travis working
---
.travis.yml | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/.travis.yml b/.travis.yml
index 93e60ba60..aa50fc486 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -20,7 +20,8 @@ _test_gem: &_test_gem
- google-chrome-stable
- yarn
- redis-server
- #mariadb: '10.3'
+ mariadb: '10.3'
+ postgresql: '11.2'
before_install:
- echo installing $COMPONENT
# yarn is in /usr/local/bin/yarn version 1.3.2 and is not a package
From fc0fb0c53ca1f4607fed9474b0cd24428180829f Mon Sep 17 00:00:00 2001
From: catmando
Date: Mon, 22 Feb 2021 20:57:17 -0500
Subject: [PATCH 105/307] trying to get travis working
---
.travis.yml | 330 ++++++++++++++++++++++++++--------------------------
1 file changed, 168 insertions(+), 162 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index aa50fc486..9557bbd21 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -1,163 +1,169 @@
language: bash
-cache:
- bundler: true
- directories:
- - node_modules # NPM packages
-
-_test_gem: &_test_gem
- stage: test
- services:
- - postgresql
- addons:
- apt:
- sources:
- - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
- key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
- - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
- key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
- packages:
- - chromium-chromedriver
- - google-chrome-stable
- - yarn
- - redis-server
- mariadb: '10.3'
- postgresql: '11.2'
- before_install:
- - echo installing $COMPONENT
- # yarn is in /usr/local/bin/yarn version 1.3.2 and is not a package
- # must remove this zombie for new yarn to work
- - sudo rm -f /usr/local/bin/yarn
- - nvm install 10
- - rvm install 2.6.3 # was 2.5.1
- - gem install bundler
- - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
- before_script:
- - echo before_script $COMPONENT
- - cd ruby/$COMPONENT
- - bundle install --jobs=3 --retry=3
- - psql -c 'create database hyper_mesh_test_db;' -U postgres
- - bundle exec rake spec:prepare
- - google-chrome --version
- - which google-chrome
- - yarn install
- script:
- - echo running script $COMPONENT
- - DRIVER=travis bundle exec rake $TASK
-
-_deploy_gem: &_deploy_gem
- stage: release gems
- before_script:
- - cd ruby/$COMPONENT
- script:
- - echo deploying $COMPONENT
- deploy:
- - provider: rubygems
- api_key:
- secure: "ORJMyp20YFCkvujBfxoDPwEZy8R8YJaKwRhHZUDTPZPiS84mJA7Mqd0JjvRlF0mlH/WzspruM7hZV0CuMU8F/0raRhSUU9RBh5veZ/4ij9kboCYnfuqBVt6qPRtaf8DgKe7CWGioUrTISJCVKLnygY6gZd2aFXCEbqZMrkUvC7y43ymOoFoeyCLsXC0j5uJxdHgNfbaIUetIl2DQJUbC2Rgq1Iaxvi72Ae97TR2xRCu+ko8DopRpQCug6U81IhzXftizGfKwzecqVFjuMn3XEf+UDlU6xbvwWWkcwjYNAbP2Kk+mWwUMx36s+1Pyx8MOveYLTwnQJ6gHocZHzh7WJOD548JNU3F5oXIlUB4EzD20bCSIeRKOdxTuKrNk7W3a5qGERuQi4rkIlkKaFIBP55IkliUxvYxqr0WujsjO2reRcNhNcLVGCOaX6LZbWFR5bf0WiEOL4vOxPNw66sI2JVHoMmQeAYtL2ghxikdSPXKRc+inT3QiRBsh+ns8YrAP7sV4lX6r/qyWUtPh6kY8xIeTP4VzMviyf20m5u++omao/FSEtVnU3cro5KjrZLg3ILg4NpNG+xoRqPS/Hmxry5ZPrggqNrxoqWuO7pLd/NnV/AnLiT8rd2P0PTriP9uRIM8+fFfyOeGwbplOLrbWUPnCdQVWp6dYOrNgE2yDJ/I="
- on:
- tags: true
-jobs:
- include:
- # - <<: *_test_gem
- # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part2
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part3
- # - <<: *_test_gem
- # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1
- #
- # - <<: *_test_gem
- # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
- # - <<: *_test_gem
- # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- #
- # - <<: *_test_gem
- # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
- # - <<: *_test_gem
- # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-
- - <<: *_deploy_gem
- env: COMPONENT=hyper-i18n
- - <<: *_deploy_gem
- env: COMPONENT=hyper-trace
- - <<: *_deploy_gem
- env: COMPONENT=hyper-state
- - <<: *_deploy_gem
- env: COMPONENT=hyper-component
- - <<: *_deploy_gem
- env: COMPONENT=hyper-model
- - <<: *_deploy_gem
- env: COMPONENT=hyper-operation
- - <<: *_deploy_gem
- env: COMPONENT=hyper-router
- - <<: *_deploy_gem
- env: COMPONENT=hyper-spec
- - <<: *_deploy_gem
- env: COMPONENT=hyper-store
- - <<: *_deploy_gem
- env: COMPONENT=rails-hyperstack
- - <<: *_deploy_gem
- env: COMPONENT=hyperstack-config
+# cache:
+# bundler: true
+# directories:
+# - node_modules # NPM packages
+services:
+ - postgresql
+addons:
+ postgresql: '11.2'
+before_script:
+ - psql -c 'create database hyper_mesh_test_db;' -U postgres
+#
+# _test_gem: &_test_gem
+# stage: test
+# services:
+# - postgresql
+# addons:
+# apt:
+# sources:
+# - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
+# key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
+# - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
+# key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
+# packages:
+# - chromium-chromedriver
+# - google-chrome-stable
+# - yarn
+# - redis-server
+# mariadb: '10.3'
+# postgresql: '11.2'
+# before_install:
+# - echo installing $COMPONENT
+# # yarn is in /usr/local/bin/yarn version 1.3.2 and is not a package
+# # must remove this zombie for new yarn to work
+# - sudo rm -f /usr/local/bin/yarn
+# - nvm install 10
+# - rvm install 2.6.3 # was 2.5.1
+# - gem install bundler
+# - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
+# before_script:
+# - echo before_script $COMPONENT
+# - cd ruby/$COMPONENT
+# - bundle install --jobs=3 --retry=3
+# - psql -c 'create database hyper_mesh_test_db;' -U postgres
+# - bundle exec rake spec:prepare
+# - google-chrome --version
+# - which google-chrome
+# - yarn install
+# script:
+# - echo running script $COMPONENT
+# - DRIVER=travis bundle exec rake $TASK
+#
+# _deploy_gem: &_deploy_gem
+# stage: release gems
+# before_script:
+# - cd ruby/$COMPONENT
+# script:
+# - echo deploying $COMPONENT
+# deploy:
+# - provider: rubygems
+# api_key:
+# secure: "ORJMyp20YFCkvujBfxoDPwEZy8R8YJaKwRhHZUDTPZPiS84mJA7Mqd0JjvRlF0mlH/WzspruM7hZV0CuMU8F/0raRhSUU9RBh5veZ/4ij9kboCYnfuqBVt6qPRtaf8DgKe7CWGioUrTISJCVKLnygY6gZd2aFXCEbqZMrkUvC7y43ymOoFoeyCLsXC0j5uJxdHgNfbaIUetIl2DQJUbC2Rgq1Iaxvi72Ae97TR2xRCu+ko8DopRpQCug6U81IhzXftizGfKwzecqVFjuMn3XEf+UDlU6xbvwWWkcwjYNAbP2Kk+mWwUMx36s+1Pyx8MOveYLTwnQJ6gHocZHzh7WJOD548JNU3F5oXIlUB4EzD20bCSIeRKOdxTuKrNk7W3a5qGERuQi4rkIlkKaFIBP55IkliUxvYxqr0WujsjO2reRcNhNcLVGCOaX6LZbWFR5bf0WiEOL4vOxPNw66sI2JVHoMmQeAYtL2ghxikdSPXKRc+inT3QiRBsh+ns8YrAP7sV4lX6r/qyWUtPh6kY8xIeTP4VzMviyf20m5u++omao/FSEtVnU3cro5KjrZLg3ILg4NpNG+xoRqPS/Hmxry5ZPrggqNrxoqWuO7pLd/NnV/AnLiT8rd2P0PTriP9uRIM8+fFfyOeGwbplOLrbWUPnCdQVWp6dYOrNgE2yDJ/I="
+# on:
+# tags: true
+# jobs:
+# include:
+# # - <<: *_test_gem
+# # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1
+# - <<: *_test_gem
+# env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
+# - <<: *_test_gem
+# env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part2
+# - <<: *_test_gem
+# env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part3
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1
+# #
+# # - <<: *_test_gem
+# # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# #
+# # - <<: *_test_gem
+# # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+#
+# - <<: *_deploy_gem
+# env: COMPONENT=hyper-i18n
+# - <<: *_deploy_gem
+# env: COMPONENT=hyper-trace
+# - <<: *_deploy_gem
+# env: COMPONENT=hyper-state
+# - <<: *_deploy_gem
+# env: COMPONENT=hyper-component
+# - <<: *_deploy_gem
+# env: COMPONENT=hyper-model
+# - <<: *_deploy_gem
+# env: COMPONENT=hyper-operation
+# - <<: *_deploy_gem
+# env: COMPONENT=hyper-router
+# - <<: *_deploy_gem
+# env: COMPONENT=hyper-spec
+# - <<: *_deploy_gem
+# env: COMPONENT=hyper-store
+# - <<: *_deploy_gem
+# env: COMPONENT=rails-hyperstack
+# - <<: *_deploy_gem
+# env: COMPONENT=hyperstack-config
From 81b8cfb31c6f0726e821b27c46600af57d65e350 Mon Sep 17 00:00:00 2001
From: catmando
Date: Mon, 22 Feb 2021 21:04:54 -0500
Subject: [PATCH 106/307] trying to get travis working
---
.travis.yml | 10 +++++++++-
1 file changed, 9 insertions(+), 1 deletion(-)
diff --git a/.travis.yml b/.travis.yml
index 9557bbd21..c9886bfe7 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -6,9 +6,17 @@ language: bash
services:
- postgresql
addons:
- postgresql: '11.2'
+ postgresql: "10"
+ apt:
+ packages:
+ - postgresql-10
+ - postgresql-client-10
+env:
+ global:
+ - PGPORT=5433
before_script:
- psql -c 'create database hyper_mesh_test_db;' -U postgres
+
#
# _test_gem: &_test_gem
# stage: test
From 6fd5f9a2b5958ab5d9198c2b2ae40c4b3e253c74 Mon Sep 17 00:00:00 2001
From: catmando
Date: Mon, 22 Feb 2021 21:09:12 -0500
Subject: [PATCH 107/307] trying to get travis working
---
.travis.yml | 28 ++++++++++++++++++----------
1 file changed, 18 insertions(+), 10 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index c9886bfe7..e4aa48c9b 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -1,19 +1,27 @@
-language: bash
+#language: bash
# cache:
# bundler: true
# directories:
# - node_modules # NPM packages
+# services:
+# - postgresql
+# addons:
+# postgresql: "10"
+# apt:
+# packages:
+# - postgresql-10
+# - postgresql-client-10
+# env:
+# global:
+# - PGPORT=5433
+# before_script:
+# - psql -c 'create database hyper_mesh_test_db;' -U postgres
services:
- - postgresql
+ - postgresql
+
addons:
- postgresql: "10"
- apt:
- packages:
- - postgresql-10
- - postgresql-client-10
-env:
- global:
- - PGPORT=5433
+ postgresql: '9.6'
+
before_script:
- psql -c 'create database hyper_mesh_test_db;' -U postgres
From 33f290e7945ca9149cc212a488ddd799cb1732d5 Mon Sep 17 00:00:00 2001
From: catmando
Date: Mon, 22 Feb 2021 21:15:22 -0500
Subject: [PATCH 108/307] trying to get travis working
---
.travis.yml | 29 +++++++++++++++++++++++------
1 file changed, 23 insertions(+), 6 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index e4aa48c9b..0701c7b9f 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -16,14 +16,31 @@
# - PGPORT=5433
# before_script:
# - psql -c 'create database hyper_mesh_test_db;' -U postgres
-services:
- - postgresql
-
-addons:
- postgresql: '9.6'
+# services:
+# - postgresql
+#
+# addons:
+# postgresql: '9.6'
+#
+# before_script:
+# - psql -c 'create database hyper_mesh_test_db;' -U postgres
+before_install:
+ - sudo apt-get update
+ - sudo apt-get --yes remove postgresql\*
+ - sudo apt-get install -y postgresql-11 postgresql-client-11
+ - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+ - sudo service postgresql restart 11
before_script:
- - psql -c 'create database hyper_mesh_test_db;' -U postgres
+ - psql --version
+ - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
+ - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
+ # - cp config/database.yml.travis config/database.yml
+# script: bundle exec rake spec
+services:
+ - postgresql
+addons:
+ postgresql: "11.2"
#
# _test_gem: &_test_gem
From 2ac23cc4f7777d936d89e6d93c7807847b24a56c Mon Sep 17 00:00:00 2001
From: catmando
Date: Mon, 22 Feb 2021 21:20:10 -0500
Subject: [PATCH 109/307] trying to get travis working
---
.travis.yml | 3 +++
1 file changed, 3 insertions(+)
diff --git a/.travis.yml b/.travis.yml
index 0701c7b9f..6bb53ed34 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -41,6 +41,9 @@ services:
- postgresql
addons:
postgresql: "11.2"
+env:
+ global:
+ - PGPORT=5433
#
# _test_gem: &_test_gem
From 5715da40907984e30c862b82c65bc74575473696 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 23 Feb 2021 07:54:53 -0500
Subject: [PATCH 110/307] after getting a simple test to load pg, moving to
running rspec
---
.travis.yml | 379 ++++++++++++++++++++++++++--------------------------
1 file changed, 187 insertions(+), 192 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 6bb53ed34..0e6d8b7de 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -1,21 +1,9 @@
-#language: bash
-# cache:
-# bundler: true
-# directories:
-# - node_modules # NPM packages
-# services:
-# - postgresql
-# addons:
-# postgresql: "10"
-# apt:
-# packages:
-# - postgresql-10
-# - postgresql-client-10
-# env:
-# global:
-# - PGPORT=5433
-# before_script:
-# - psql -c 'create database hyper_mesh_test_db;' -U postgres
+language: bash
+cache:
+ bundler: true
+ directories:
+ - node_modules # NPM packages
+
# services:
# - postgresql
#
@@ -25,181 +13,188 @@
# before_script:
# - psql -c 'create database hyper_mesh_test_db;' -U postgres
-before_install:
- - sudo apt-get update
- - sudo apt-get --yes remove postgresql\*
- - sudo apt-get install -y postgresql-11 postgresql-client-11
- - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- - sudo service postgresql restart 11
-before_script:
- - psql --version
- - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
- - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
- # - cp config/database.yml.travis config/database.yml
-# script: bundle exec rake spec
-services:
- - postgresql
-addons:
- postgresql: "11.2"
+# before_install:
+# - sudo apt-get update
+# - sudo apt-get --yes remove postgresql\*
+# - sudo apt-get install -y postgresql-11 postgresql-client-11
+# - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+# - sudo service postgresql restart 11
+# before_script:
+# - psql --version
+# - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
+# - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
+# services:
+# - postgresql
+# addons:
+# postgresql: "11.2"
env:
global:
- PGPORT=5433
-#
-# _test_gem: &_test_gem
-# stage: test
-# services:
-# - postgresql
-# addons:
-# apt:
-# sources:
-# - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
-# key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
-# - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
-# key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
-# packages:
-# - chromium-chromedriver
-# - google-chrome-stable
-# - yarn
-# - redis-server
-# mariadb: '10.3'
-# postgresql: '11.2'
-# before_install:
-# - echo installing $COMPONENT
-# # yarn is in /usr/local/bin/yarn version 1.3.2 and is not a package
-# # must remove this zombie for new yarn to work
-# - sudo rm -f /usr/local/bin/yarn
-# - nvm install 10
-# - rvm install 2.6.3 # was 2.5.1
-# - gem install bundler
-# - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
-# before_script:
-# - echo before_script $COMPONENT
-# - cd ruby/$COMPONENT
-# - bundle install --jobs=3 --retry=3
-# - psql -c 'create database hyper_mesh_test_db;' -U postgres
-# - bundle exec rake spec:prepare
-# - google-chrome --version
-# - which google-chrome
-# - yarn install
-# script:
-# - echo running script $COMPONENT
-# - DRIVER=travis bundle exec rake $TASK
-#
-# _deploy_gem: &_deploy_gem
-# stage: release gems
-# before_script:
-# - cd ruby/$COMPONENT
-# script:
-# - echo deploying $COMPONENT
-# deploy:
-# - provider: rubygems
-# api_key:
-# secure: "ORJMyp20YFCkvujBfxoDPwEZy8R8YJaKwRhHZUDTPZPiS84mJA7Mqd0JjvRlF0mlH/WzspruM7hZV0CuMU8F/0raRhSUU9RBh5veZ/4ij9kboCYnfuqBVt6qPRtaf8DgKe7CWGioUrTISJCVKLnygY6gZd2aFXCEbqZMrkUvC7y43ymOoFoeyCLsXC0j5uJxdHgNfbaIUetIl2DQJUbC2Rgq1Iaxvi72Ae97TR2xRCu+ko8DopRpQCug6U81IhzXftizGfKwzecqVFjuMn3XEf+UDlU6xbvwWWkcwjYNAbP2Kk+mWwUMx36s+1Pyx8MOveYLTwnQJ6gHocZHzh7WJOD548JNU3F5oXIlUB4EzD20bCSIeRKOdxTuKrNk7W3a5qGERuQi4rkIlkKaFIBP55IkliUxvYxqr0WujsjO2reRcNhNcLVGCOaX6LZbWFR5bf0WiEOL4vOxPNw66sI2JVHoMmQeAYtL2ghxikdSPXKRc+inT3QiRBsh+ns8YrAP7sV4lX6r/qyWUtPh6kY8xIeTP4VzMviyf20m5u++omao/FSEtVnU3cro5KjrZLg3ILg4NpNG+xoRqPS/Hmxry5ZPrggqNrxoqWuO7pLd/NnV/AnLiT8rd2P0PTriP9uRIM8+fFfyOeGwbplOLrbWUPnCdQVWp6dYOrNgE2yDJ/I="
-# on:
-# tags: true
-# jobs:
-# include:
-# # - <<: *_test_gem
-# # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1
-# - <<: *_test_gem
-# env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
-# - <<: *_test_gem
-# env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part2
-# - <<: *_test_gem
-# env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part3
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1
-# #
-# # - <<: *_test_gem
-# # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# #
-# # - <<: *_test_gem
-# # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-#
-# - <<: *_deploy_gem
-# env: COMPONENT=hyper-i18n
-# - <<: *_deploy_gem
-# env: COMPONENT=hyper-trace
-# - <<: *_deploy_gem
-# env: COMPONENT=hyper-state
-# - <<: *_deploy_gem
-# env: COMPONENT=hyper-component
-# - <<: *_deploy_gem
-# env: COMPONENT=hyper-model
-# - <<: *_deploy_gem
-# env: COMPONENT=hyper-operation
-# - <<: *_deploy_gem
-# env: COMPONENT=hyper-router
-# - <<: *_deploy_gem
-# env: COMPONENT=hyper-spec
-# - <<: *_deploy_gem
-# env: COMPONENT=hyper-store
-# - <<: *_deploy_gem
-# env: COMPONENT=rails-hyperstack
-# - <<: *_deploy_gem
-# env: COMPONENT=hyperstack-config
+_test_gem: &_test_gem
+ stage: test
+ services:
+ - postgresql
+ addons:
+ apt:
+ sources:
+ - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
+ key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
+ - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
+ key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
+ packages:
+ - chromium-chromedriver
+ - google-chrome-stable
+ - yarn
+ - redis-server
+ mariadb: '10.3'
+ postgresql: "11.2"
+ before_install:
+ - echo 'installing PG 11'
+ - sudo apt-get update
+ - sudo apt-get --yes remove postgresql\*
+ - sudo apt-get install -y postgresql-11 postgresql-client-11
+ - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+ - sudo service postgresql restart 11
+ - echo installing $COMPONENT
+ # yarn is in /usr/local/bin/yarn version 1.3.2 and is not a package
+ # must remove this zombie for new yarn to work
+ - sudo rm -f /usr/local/bin/yarn
+ - nvm install 10
+ - rvm install 2.6.3 # was 2.5.1
+ - gem install bundler
+ - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
+ before_script:
+ - echo creating pg database hyper_mesh_test_db
+ - psql --version
+ - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
+ - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
+ - echo before_script $COMPONENT
+ - cd ruby/$COMPONENT
+ - bundle install --jobs=3 --retry=3
+ - psql -c 'create database hyper_mesh_test_db;' -U postgres
+ - bundle exec rake spec:prepare
+ - google-chrome --version
+ - which google-chrome
+ - yarn install
+ script:
+ - echo running script $COMPONENT
+ - DRIVER=travis bundle exec rake $TASK
+
+_deploy_gem: &_deploy_gem
+ stage: release gems
+ before_script:
+ - cd ruby/$COMPONENT
+ script:
+ - echo deploying $COMPONENT
+ deploy:
+ - provider: rubygems
+ api_key:
+ secure: "ORJMyp20YFCkvujBfxoDPwEZy8R8YJaKwRhHZUDTPZPiS84mJA7Mqd0JjvRlF0mlH/WzspruM7hZV0CuMU8F/0raRhSUU9RBh5veZ/4ij9kboCYnfuqBVt6qPRtaf8DgKe7CWGioUrTISJCVKLnygY6gZd2aFXCEbqZMrkUvC7y43ymOoFoeyCLsXC0j5uJxdHgNfbaIUetIl2DQJUbC2Rgq1Iaxvi72Ae97TR2xRCu+ko8DopRpQCug6U81IhzXftizGfKwzecqVFjuMn3XEf+UDlU6xbvwWWkcwjYNAbP2Kk+mWwUMx36s+1Pyx8MOveYLTwnQJ6gHocZHzh7WJOD548JNU3F5oXIlUB4EzD20bCSIeRKOdxTuKrNk7W3a5qGERuQi4rkIlkKaFIBP55IkliUxvYxqr0WujsjO2reRcNhNcLVGCOaX6LZbWFR5bf0WiEOL4vOxPNw66sI2JVHoMmQeAYtL2ghxikdSPXKRc+inT3QiRBsh+ns8YrAP7sV4lX6r/qyWUtPh6kY8xIeTP4VzMviyf20m5u++omao/FSEtVnU3cro5KjrZLg3ILg4NpNG+xoRqPS/Hmxry5ZPrggqNrxoqWuO7pLd/NnV/AnLiT8rd2P0PTriP9uRIM8+fFfyOeGwbplOLrbWUPnCdQVWp6dYOrNgE2yDJ/I="
+ on:
+ tags: true
+jobs:
+ include:
+ # - <<: *_test_gem
+ # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part2
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part3
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1
+ #
+ # - <<: *_test_gem
+ # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ #
+ # - <<: *_test_gem
+ # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-i18n
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-trace
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-state
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-component
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-model
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-operation
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-router
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-spec
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-store
+ - <<: *_deploy_gem
+ env: COMPONENT=rails-hyperstack
+ - <<: *_deploy_gem
+ env: COMPONENT=hyperstack-config
From df255a2740f95e1feac030026c381eff27b3e361 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 23 Feb 2021 08:03:26 -0500
Subject: [PATCH 111/307] before_install failed - moving to outer layer
---
.travis.yml | 18 ++++++------------
1 file changed, 6 insertions(+), 12 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 0e6d8b7de..d16f8b0e5 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -13,12 +13,12 @@ cache:
# before_script:
# - psql -c 'create database hyper_mesh_test_db;' -U postgres
-# before_install:
-# - sudo apt-get update
-# - sudo apt-get --yes remove postgresql\*
-# - sudo apt-get install -y postgresql-11 postgresql-client-11
-# - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
-# - sudo service postgresql restart 11
+before_install:
+ - sudo apt-get update
+ - sudo apt-get --yes remove postgresql\*
+ - sudo apt-get install -y postgresql-11 postgresql-client-11
+ - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+ - sudo service postgresql restart 11
# before_script:
# - psql --version
# - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
@@ -50,12 +50,6 @@ _test_gem: &_test_gem
mariadb: '10.3'
postgresql: "11.2"
before_install:
- - echo 'installing PG 11'
- - sudo apt-get update
- - sudo apt-get --yes remove postgresql\*
- - sudo apt-get install -y postgresql-11 postgresql-client-11
- - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- - sudo service postgresql restart 11
- echo installing $COMPONENT
# yarn is in /usr/local/bin/yarn version 1.3.2 and is not a package
# must remove this zombie for new yarn to work
From 5a108713096124b33e15e6ad212f41352d771a73 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 23 Feb 2021 08:24:29 -0500
Subject: [PATCH 112/307] before_install failed - moving more to outer layer
---
.travis.yml | 29 +++++++++++++++--------------
1 file changed, 15 insertions(+), 14 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index d16f8b0e5..2c75c67b6 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -19,14 +19,15 @@ before_install:
- sudo apt-get install -y postgresql-11 postgresql-client-11
- sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- sudo service postgresql restart 11
-# before_script:
-# - psql --version
-# - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
-# - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
-# services:
-# - postgresql
-# addons:
-# postgresql: "11.2"
+before_script:
+ - echo creating pg database hyper_mesh_test_db
+ - psql --version
+ - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
+ - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
+services:
+ - postgresql
+addons:
+ postgresql: "11.2"
env:
global:
- PGPORT=5433
@@ -48,7 +49,7 @@ _test_gem: &_test_gem
- yarn
- redis-server
mariadb: '10.3'
- postgresql: "11.2"
+ # postgresql: "11.2"
before_install:
- echo installing $COMPONENT
# yarn is in /usr/local/bin/yarn version 1.3.2 and is not a package
@@ -59,11 +60,11 @@ _test_gem: &_test_gem
- gem install bundler
- ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
before_script:
- - echo creating pg database hyper_mesh_test_db
- - psql --version
- - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
- - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
- - echo before_script $COMPONENT
+ # - echo creating pg database hyper_mesh_test_db
+ # - psql --version
+ # - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
+ # - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
+ # - echo before_script $COMPONENT
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
- psql -c 'create database hyper_mesh_test_db;' -U postgres
From 5909e654f615994218ec3f5e4e79f78ef1ae3498 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 23 Feb 2021 09:05:01 -0500
Subject: [PATCH 113/307] install in the outer level restart in the inner
---
.travis.yml | 11 ++++++-----
1 file changed, 6 insertions(+), 5 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 2c75c67b6..8dc1f1319 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -51,6 +51,7 @@ _test_gem: &_test_gem
mariadb: '10.3'
# postgresql: "11.2"
before_install:
+ - sudo service postgresql restart 11
- echo installing $COMPONENT
# yarn is in /usr/local/bin/yarn version 1.3.2 and is not a package
# must remove this zombie for new yarn to work
@@ -60,11 +61,11 @@ _test_gem: &_test_gem
- gem install bundler
- ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
before_script:
- # - echo creating pg database hyper_mesh_test_db
- # - psql --version
- # - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
- # - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
- # - echo before_script $COMPONENT
+ - echo creating pg database hyper_mesh_test_db
+ - psql --version
+ - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
+ - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
+ - echo before_script $COMPONENT
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
- psql -c 'create database hyper_mesh_test_db;' -U postgres
From 9ec08065091f3c784cfac6f39a5d3bb571e80b51 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 23 Feb 2021 09:19:11 -0500
Subject: [PATCH 114/307] why doesnt the cp of the config work
---
.travis.yml | 28 +++++++++++++++++-----------
1 file changed, 17 insertions(+), 11 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 8dc1f1319..3036942b8 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -13,17 +13,17 @@ cache:
# before_script:
# - psql -c 'create database hyper_mesh_test_db;' -U postgres
-before_install:
- - sudo apt-get update
- - sudo apt-get --yes remove postgresql\*
- - sudo apt-get install -y postgresql-11 postgresql-client-11
- - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- - sudo service postgresql restart 11
-before_script:
- - echo creating pg database hyper_mesh_test_db
- - psql --version
- - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
- - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
+# before_install:
+# - sudo apt-get update
+# - sudo apt-get --yes remove postgresql\*
+# - sudo apt-get install -y postgresql-11 postgresql-client-11
+# - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+# - sudo service postgresql restart 11
+# before_script:
+# - echo creating pg database hyper_mesh_test_db
+# - psql --version
+# - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
+# - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
services:
- postgresql
addons:
@@ -51,6 +51,12 @@ _test_gem: &_test_gem
mariadb: '10.3'
# postgresql: "11.2"
before_install:
+ - sudo apt-get update
+ - sudo apt-get --yes remove postgresql\*
+ - sudo apt-get install -y postgresql-11 postgresql-client-11
+ #- sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+ - sudo ls /etc
+ - sudo ls /etc/postgresql/
- sudo service postgresql restart 11
- echo installing $COMPONENT
# yarn is in /usr/local/bin/yarn version 1.3.2 and is not a package
From 1caadadf7c934f2215583b8d3999297d10fdfbf2 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 23 Feb 2021 09:35:28 -0500
Subject: [PATCH 115/307] save config before starting
---
.travis.yml | 6 ++++--
1 file changed, 4 insertions(+), 2 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 3036942b8..f3a133734 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -13,11 +13,12 @@ cache:
# before_script:
# - psql -c 'create database hyper_mesh_test_db;' -U postgres
-# before_install:
+before_install:
# - sudo apt-get update
# - sudo apt-get --yes remove postgresql\*
# - sudo apt-get install -y postgresql-11 postgresql-client-11
# - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+ - sudo cp /etc/postgresql/9.6/main/pg_hba.conf /etc/tmp/pga_hba.conf
# - sudo service postgresql restart 11
# before_script:
# - echo creating pg database hyper_mesh_test_db
@@ -56,7 +57,8 @@ _test_gem: &_test_gem
- sudo apt-get install -y postgresql-11 postgresql-client-11
#- sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- sudo ls /etc
- - sudo ls /etc/postgresql/
+ - sudo ls /etc/tmp
+ - sudo cp /etc/tmp/pg_hba.conf /etc/postgresql/11/main/pg_hba.conf
- sudo service postgresql restart 11
- echo installing $COMPONENT
# yarn is in /usr/local/bin/yarn version 1.3.2 and is not a package
From 1957e9adc24f5a68f0a2a4616d22637e82862504 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 23 Feb 2021 09:47:29 -0500
Subject: [PATCH 116/307] dump 9.6 config
---
.travis.yml | 29 +++++++++++++++++------------
1 file changed, 17 insertions(+), 12 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index f3a133734..1e1f81e54 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -18,22 +18,25 @@ before_install:
# - sudo apt-get --yes remove postgresql\*
# - sudo apt-get install -y postgresql-11 postgresql-client-11
# - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- - sudo cp /etc/postgresql/9.6/main/pg_hba.conf /etc/tmp/pga_hba.conf
+ - sudo cat /etc/postgresql/9.6/main/pg_hba.conf
# - sudo service postgresql restart 11
# before_script:
# - echo creating pg database hyper_mesh_test_db
# - psql --version
# - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
# - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
-services:
- - postgresql
-addons:
- postgresql: "11.2"
-env:
- global:
- - PGPORT=5433
+# services:
+# - postgresql
+# addons:
+# postgresql: "11.2"
+# env:
+# global:
+# - PGPORT=5433
_test_gem: &_test_gem
+ env:
+ global:
+ - PGPORT=5433
stage: test
services:
- postgresql
@@ -50,15 +53,17 @@ _test_gem: &_test_gem
- yarn
- redis-server
mariadb: '10.3'
- # postgresql: "11.2"
+ postgresql: "11.2"
before_install:
- sudo apt-get update
- sudo apt-get --yes remove postgresql\*
- sudo apt-get install -y postgresql-11 postgresql-client-11
+ - sudo cat /etc/postgresql/11/main/pg_hba.conf
#- sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- - sudo ls /etc
- - sudo ls /etc/tmp
- - sudo cp /etc/tmp/pg_hba.conf /etc/postgresql/11/main/pg_hba.conf
+ # - sudo ls /etc
+ # - sudo ls /etc/tmp
+ # - sudo cp /etc/tmp/pg_hba.conf /etc/postgresql/11/main/pg_hba.conf
+
- sudo service postgresql restart 11
- echo installing $COMPONENT
# yarn is in /usr/local/bin/yarn version 1.3.2 and is not a package
From be12f1aafc4e82cfd0c723138a83a169fd680275 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 23 Feb 2021 10:04:42 -0500
Subject: [PATCH 117/307] lets get it working with 9.6
---
.travis.yml | 28 ++++++++++++++--------------
1 file changed, 14 insertions(+), 14 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 1e1f81e54..22523ade6 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -34,9 +34,9 @@ before_install:
# - PGPORT=5433
_test_gem: &_test_gem
- env:
- global:
- - PGPORT=5433
+ # env:
+ # global:
+ # - PGPORT=5433
stage: test
services:
- postgresql
@@ -53,18 +53,18 @@ _test_gem: &_test_gem
- yarn
- redis-server
mariadb: '10.3'
- postgresql: "11.2"
+ postgresql: "9.6"
before_install:
- - sudo apt-get update
- - sudo apt-get --yes remove postgresql\*
- - sudo apt-get install -y postgresql-11 postgresql-client-11
- - sudo cat /etc/postgresql/11/main/pg_hba.conf
- #- sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- # - sudo ls /etc
- # - sudo ls /etc/tmp
- # - sudo cp /etc/tmp/pg_hba.conf /etc/postgresql/11/main/pg_hba.conf
-
- - sudo service postgresql restart 11
+ # - sudo apt-get update
+ # - sudo apt-get --yes remove postgresql\*
+ # - sudo apt-get install -y postgresql-11 postgresql-client-11
+ # - sudo cat /etc/postgresql/11/main/pg_hba.conf
+ # #- sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+ # # - sudo ls /etc
+ # # - sudo ls /etc/tmp
+ # # - sudo cp /etc/tmp/pg_hba.conf /etc/postgresql/11/main/pg_hba.conf
+ #
+ # - sudo service postgresql restart 11
- echo installing $COMPONENT
# yarn is in /usr/local/bin/yarn version 1.3.2 and is not a package
# must remove this zombie for new yarn to work
From 3347f45a7fa5957750bd367de93b47521e1cc111 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 23 Feb 2021 10:17:58 -0500
Subject: [PATCH 118/307] simple case with mariadb
---
.travis.yml | 355 +++++++++++++++++++++++++++++++---------------------
1 file changed, 211 insertions(+), 144 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 22523ade6..b4f73ed4d 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -3,36 +3,6 @@ cache:
bundler: true
directories:
- node_modules # NPM packages
-
-# services:
-# - postgresql
-#
-# addons:
-# postgresql: '9.6'
-#
-# before_script:
-# - psql -c 'create database hyper_mesh_test_db;' -U postgres
-
-before_install:
-# - sudo apt-get update
-# - sudo apt-get --yes remove postgresql\*
-# - sudo apt-get install -y postgresql-11 postgresql-client-11
-# - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- - sudo cat /etc/postgresql/9.6/main/pg_hba.conf
-# - sudo service postgresql restart 11
-# before_script:
-# - echo creating pg database hyper_mesh_test_db
-# - psql --version
-# - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
-# - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
-# services:
-# - postgresql
-# addons:
-# postgresql: "11.2"
-# env:
-# global:
-# - PGPORT=5433
-
_test_gem: &_test_gem
# env:
# global:
@@ -52,22 +22,10 @@ _test_gem: &_test_gem
- google-chrome-stable
- yarn
- redis-server
- mariadb: '10.3'
- postgresql: "9.6"
+ mariadb: '10.3' # mariadb works fine...
+ # postgresql: "9.6"
before_install:
- # - sudo apt-get update
- # - sudo apt-get --yes remove postgresql\*
- # - sudo apt-get install -y postgresql-11 postgresql-client-11
- # - sudo cat /etc/postgresql/11/main/pg_hba.conf
- # #- sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- # # - sudo ls /etc
- # # - sudo ls /etc/tmp
- # # - sudo cp /etc/tmp/pg_hba.conf /etc/postgresql/11/main/pg_hba.conf
- #
- # - sudo service postgresql restart 11
- echo installing $COMPONENT
- # yarn is in /usr/local/bin/yarn version 1.3.2 and is not a package
- # must remove this zombie for new yarn to work
- sudo rm -f /usr/local/bin/yarn
- nvm install 10
- rvm install 2.6.3 # was 2.5.1
@@ -104,106 +62,215 @@ _deploy_gem: &_deploy_gem
tags: true
jobs:
include:
- # - <<: *_test_gem
- # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1
- <<: *_test_gem
env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part2
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part3
- # - <<: *_test_gem
- # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1
- #
- # - <<: *_test_gem
- # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
- # - <<: *_test_gem
- # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- #
- # - <<: *_test_gem
- # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
- # - <<: *_test_gem
- # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_deploy_gem
- env: COMPONENT=hyper-i18n
- - <<: *_deploy_gem
- env: COMPONENT=hyper-trace
- - <<: *_deploy_gem
- env: COMPONENT=hyper-state
- - <<: *_deploy_gem
- env: COMPONENT=hyper-component
- - <<: *_deploy_gem
- env: COMPONENT=hyper-model
- - <<: *_deploy_gem
- env: COMPONENT=hyper-operation
- - <<: *_deploy_gem
- env: COMPONENT=hyper-router
- - <<: *_deploy_gem
- env: COMPONENT=hyper-spec
- - <<: *_deploy_gem
- env: COMPONENT=hyper-store
- - <<: *_deploy_gem
- env: COMPONENT=rails-hyperstack
- - <<: *_deploy_gem
- env: COMPONENT=hyperstack-config
+# language: bash
+# cache:
+# bundler: true
+# directories:
+# - node_modules # NPM packages
+#
+# # services:
+# # - postgresql
+# #
+# # addons:
+# # postgresql: '9.6'
+# #
+# # before_script:
+# # - psql -c 'create database hyper_mesh_test_db;' -U postgres
+#
+# before_install:
+# # - sudo apt-get update
+# # - sudo apt-get --yes remove postgresql\*
+# # - sudo apt-get install -y postgresql-11 postgresql-client-11
+# # - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+# - sudo cat /etc/postgresql/9.6/main/pg_hba.conf
+# # - sudo service postgresql restart 11
+# # before_script:
+# # - echo creating pg database hyper_mesh_test_db
+# # - psql --version
+# # - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
+# # - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
+# # services:
+# # - postgresql
+# # addons:
+# # postgresql: "11.2"
+# # env:
+# # global:
+# # - PGPORT=5433
+#
+# _test_gem: &_test_gem
+# # env:
+# # global:
+# # - PGPORT=5433
+# stage: test
+# services:
+# - postgresql
+# addons:
+# apt:
+# sources:
+# - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
+# key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
+# - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
+# key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
+# packages:
+# - chromium-chromedriver
+# - google-chrome-stable
+# - yarn
+# - redis-server
+# mariadb: '10.3'
+# postgresql: "9.6"
+# before_install:
+# # - sudo apt-get update
+# # - sudo apt-get --yes remove postgresql\*
+# # - sudo apt-get install -y postgresql-11 postgresql-client-11
+# # - sudo cat /etc/postgresql/11/main/pg_hba.conf
+# # #- sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+# # # - sudo ls /etc
+# # # - sudo ls /etc/tmp
+# # # - sudo cp /etc/tmp/pg_hba.conf /etc/postgresql/11/main/pg_hba.conf
+# #
+# # - sudo service postgresql restart 11
+# - echo installing $COMPONENT
+# # yarn is in /usr/local/bin/yarn version 1.3.2 and is not a package
+# # must remove this zombie for new yarn to work
+# - sudo rm -f /usr/local/bin/yarn
+# - nvm install 10
+# - rvm install 2.6.3 # was 2.5.1
+# - gem install bundler
+# - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
+# before_script:
+# - echo creating pg database hyper_mesh_test_db
+# - psql --version
+# - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
+# - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
+# - echo before_script $COMPONENT
+# - cd ruby/$COMPONENT
+# - bundle install --jobs=3 --retry=3
+# - psql -c 'create database hyper_mesh_test_db;' -U postgres
+# - bundle exec rake spec:prepare
+# - google-chrome --version
+# - which google-chrome
+# - yarn install
+# script:
+# - echo running script $COMPONENT
+# - DRIVER=travis bundle exec rake $TASK
+#
+# _deploy_gem: &_deploy_gem
+# stage: release gems
+# before_script:
+# - cd ruby/$COMPONENT
+# script:
+# - echo deploying $COMPONENT
+# deploy:
+# - provider: rubygems
+# api_key:
+# secure: "ORJMyp20YFCkvujBfxoDPwEZy8R8YJaKwRhHZUDTPZPiS84mJA7Mqd0JjvRlF0mlH/WzspruM7hZV0CuMU8F/0raRhSUU9RBh5veZ/4ij9kboCYnfuqBVt6qPRtaf8DgKe7CWGioUrTISJCVKLnygY6gZd2aFXCEbqZMrkUvC7y43ymOoFoeyCLsXC0j5uJxdHgNfbaIUetIl2DQJUbC2Rgq1Iaxvi72Ae97TR2xRCu+ko8DopRpQCug6U81IhzXftizGfKwzecqVFjuMn3XEf+UDlU6xbvwWWkcwjYNAbP2Kk+mWwUMx36s+1Pyx8MOveYLTwnQJ6gHocZHzh7WJOD548JNU3F5oXIlUB4EzD20bCSIeRKOdxTuKrNk7W3a5qGERuQi4rkIlkKaFIBP55IkliUxvYxqr0WujsjO2reRcNhNcLVGCOaX6LZbWFR5bf0WiEOL4vOxPNw66sI2JVHoMmQeAYtL2ghxikdSPXKRc+inT3QiRBsh+ns8YrAP7sV4lX6r/qyWUtPh6kY8xIeTP4VzMviyf20m5u++omao/FSEtVnU3cro5KjrZLg3ILg4NpNG+xoRqPS/Hmxry5ZPrggqNrxoqWuO7pLd/NnV/AnLiT8rd2P0PTriP9uRIM8+fFfyOeGwbplOLrbWUPnCdQVWp6dYOrNgE2yDJ/I="
+# on:
+# tags: true
+# jobs:
+# include:
+# # - <<: *_test_gem
+# # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1
+# - <<: *_test_gem
+# env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
+# - <<: *_test_gem
+# env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part2
+# - <<: *_test_gem
+# env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part3
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1
+# #
+# # - <<: *_test_gem
+# # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+# #
+# # - <<: *_test_gem
+# # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
+# # - <<: *_test_gem
+# # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+#
+# - <<: *_deploy_gem
+# env: COMPONENT=hyper-i18n
+# - <<: *_deploy_gem
+# env: COMPONENT=hyper-trace
+# - <<: *_deploy_gem
+# env: COMPONENT=hyper-state
+# - <<: *_deploy_gem
+# env: COMPONENT=hyper-component
+# - <<: *_deploy_gem
+# env: COMPONENT=hyper-model
+# - <<: *_deploy_gem
+# env: COMPONENT=hyper-operation
+# - <<: *_deploy_gem
+# env: COMPONENT=hyper-router
+# - <<: *_deploy_gem
+# env: COMPONENT=hyper-spec
+# - <<: *_deploy_gem
+# env: COMPONENT=hyper-store
+# - <<: *_deploy_gem
+# env: COMPONENT=rails-hyperstack
+# - <<: *_deploy_gem
+# env: COMPONENT=hyperstack-config
From 7aee7beccf2502366dcc219c1fac2f762dbbad33 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 23 Feb 2021 10:36:59 -0500
Subject: [PATCH 119/307] simple case with mariadb round 2
---
.travis.yml | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index b4f73ed4d..e64608b69 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -33,9 +33,9 @@ _test_gem: &_test_gem
- ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
before_script:
- echo creating pg database hyper_mesh_test_db
- - psql --version
- - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
- - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
+ # - psql --version
+ # - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
+ # - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
- echo before_script $COMPONENT
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
From c2ae281ae3cbaffc9580d84ca208a8c586c84aa9 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 23 Feb 2021 10:49:09 -0500
Subject: [PATCH 120/307] simple case with mariadb round 3
---
.travis.yml | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/.travis.yml b/.travis.yml
index e64608b69..383a31650 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -39,7 +39,7 @@ _test_gem: &_test_gem
- echo before_script $COMPONENT
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
- - psql -c 'create database hyper_mesh_test_db;' -U postgres
+ # - psql -c 'create database hyper_mesh_test_db;' -U postgres
- bundle exec rake spec:prepare
- google-chrome --version
- which google-chrome
From bba3437e8cf6218d88ae9b7c69b897a0b3a167a3 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 23 Feb 2021 10:56:10 -0500
Subject: [PATCH 121/307] simple case with postgresql
---
.travis.yml | 11 +++++------
1 file changed, 5 insertions(+), 6 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 383a31650..a9adfd625 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -22,8 +22,8 @@ _test_gem: &_test_gem
- google-chrome-stable
- yarn
- redis-server
- mariadb: '10.3' # mariadb works fine...
- # postgresql: "9.6"
+ # mariadb: '10.3' # mariadb works fine...
+ postgresql: "9.6"
before_install:
- echo installing $COMPONENT
- sudo rm -f /usr/local/bin/yarn
@@ -33,13 +33,12 @@ _test_gem: &_test_gem
- ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
before_script:
- echo creating pg database hyper_mesh_test_db
- # - psql --version
- # - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
- # - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
+ - psql --version
+ - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
+ - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
- echo before_script $COMPONENT
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
- # - psql -c 'create database hyper_mesh_test_db;' -U postgres
- bundle exec rake spec:prepare
- google-chrome --version
- which google-chrome
From 91998e0e0e72139b553a1a39f7be88f1e8105812 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 23 Feb 2021 11:07:31 -0500
Subject: [PATCH 122/307] trying a different way to set pg port
---
.travis.yml | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/.travis.yml b/.travis.yml
index a9adfd625..01a7e29a5 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -62,7 +62,7 @@ _deploy_gem: &_deploy_gem
jobs:
include:
- <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
+ env: PGPORT=5433 COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
# language: bash
# cache:
From e2d8be4fd75af4210e97da5ec8403a5aeaeab4f2 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 23 Feb 2021 22:32:34 -0500
Subject: [PATCH 123/307] tweaks to primary_key and trying another round of
postgresql
---
.travis.yml | 2 ++
.../lib/reactive_record/active_record/class_methods.rb | 2 +-
.../reactive_record/active_record/instance_methods.rb | 2 +-
ruby/hyper-model/lib/reactive_record/broadcast.rb | 10 +++++-----
.../lib/reactive_record/server_data_cache.rb | 2 +-
5 files changed, 10 insertions(+), 8 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 01a7e29a5..7e26ffb08 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -25,6 +25,8 @@ _test_gem: &_test_gem
# mariadb: '10.3' # mariadb works fine...
postgresql: "9.6"
before_install:
+ # - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+ - sudo ls /etc/postgresql/
- echo installing $COMPONENT
- sudo rm -f /usr/local/bin/yarn
- nvm install 10
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/class_methods.rb b/ruby/hyper-model/lib/reactive_record/active_record/class_methods.rb
index f9daab46a..dd467d728 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/class_methods.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/class_methods.rb
@@ -364,7 +364,7 @@ def server_method(name, default: nil)
def define_attribute_methods
columns_hash.each do |name, column_hash|
- next if name == primary_key
+ next if name == :id
# only add serialized key if its serialized. This just makes testing a bit
# easier by keeping the columns_hash the same if there are no seralized strings
# see rspec ./spec/batch1/column_types/column_type_spec.rb:100
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/instance_methods.rb b/ruby/hyper-model/lib/reactive_record/active_record/instance_methods.rb
index 361b6844d..453ca8124 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/instance_methods.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/instance_methods.rb
@@ -92,7 +92,7 @@ def initialize(hash = {})
end
self.class.load_data do
h.each do |attribute, value|
- next if attribute == primary_key
+ next if attribute == :id
@ar_instance[attribute] = value
changed_attributes << attribute
end
diff --git a/ruby/hyper-model/lib/reactive_record/broadcast.rb b/ruby/hyper-model/lib/reactive_record/broadcast.rb
index 7fff8a1fb..699ed9f3e 100644
--- a/ruby/hyper-model/lib/reactive_record/broadcast.rb
+++ b/ruby/hyper-model/lib/reactive_record/broadcast.rb
@@ -88,7 +88,7 @@ def self.to_self(record, data = {})
def record_with_current_values
ReactiveRecord::Base.load_data do
- backing_record = @backing_record || klass.find(record[:id]).backing_record
+ backing_record = @backing_record || klass.find(record[klass.primary_key]).backing_record
if destroyed?
backing_record.ar_instance
else
@@ -148,7 +148,7 @@ def local(operation, record, data)
@klass = record.class.name
@record = data
record.backing_record.destroyed = false
- @record[:id] = record.id if record.id
+ @record[@klass.primary_key] = record.id if record.id
record.backing_record.destroyed = @destroyed
@backing_record = record.backing_record
@previous_changes = record.changes
@@ -163,7 +163,7 @@ def receive(params)
@record.merge! params.record
@previous_changes.merge! params.previous_changes
ReactiveRecord::Base.when_not_saving(klass) do
- @backing_record = ReactiveRecord::Base.exists?(klass, params.record[:id])
+ @backing_record = ReactiveRecord::Base.exists?(klass, params.record[klass.primary_key])
# first check to see if we already destroyed it and if so exit the block
return if @backing_record&.destroyed
@@ -180,7 +180,7 @@ def receive(params)
# it is possible that we are recieving data on a record for which we are also waiting
# on an an inital data load in which case we have not yet set the loaded id, so we
# set if now.
- @backing_record&.loaded_id = params.record[:id]
+ @backing_record&.loaded_id = params.record[klass.primary_key]
# once we have received all the data from all the channels (applies to create and update only)
# we yield and process the record
@@ -234,7 +234,7 @@ def process_previous_changes
def merge_current_values(br)
current_values = Hash[*@previous_changes.collect do |attr, values|
- value = attr == :id ? record[:id] : values.first
+ value = attr == klass.primary_key ? record[klass.primary_key] : values.first
if br.attributes.key?(attr) &&
br.attributes[attr] != br.convert(attr, value) &&
br.attributes[attr] != br.convert(attr, values.last)
diff --git a/ruby/hyper-model/lib/reactive_record/server_data_cache.rb b/ruby/hyper-model/lib/reactive_record/server_data_cache.rb
index e7f942953..002075915 100644
--- a/ruby/hyper-model/lib/reactive_record/server_data_cache.rb
+++ b/ruby/hyper-model/lib/reactive_record/server_data_cache.rb
@@ -474,7 +474,7 @@ def self.load_from_json(tree, target = nil)
end
end
- if (id_value = tree[target.class.try(:primary_key)]) && id_value.is_a?(Array)
+ if (id_value = tree[target.class.try(:primary_key)] || tree[:id]) && id_value.is_a?(Array)
target.id = id_value.first
end
tree.each do |method, value|
From 3f15072d55579f0041c1c89666de08b57fd1de2f Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 23 Feb 2021 22:57:57 -0500
Subject: [PATCH 124/307] back to getting base config for mysql
---
.travis.yml | 132 ++++++++++++++++++++++++++--------------------------
1 file changed, 66 insertions(+), 66 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 7e26ffb08..f8126dc8e 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -1,70 +1,70 @@
-language: bash
-cache:
- bundler: true
- directories:
- - node_modules # NPM packages
-_test_gem: &_test_gem
- # env:
- # global:
- # - PGPORT=5433
- stage: test
- services:
- - postgresql
- addons:
- apt:
- sources:
- - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
- key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
- - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
- key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
- packages:
- - chromium-chromedriver
- - google-chrome-stable
- - yarn
- - redis-server
- # mariadb: '10.3' # mariadb works fine...
- postgresql: "9.6"
- before_install:
- # - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- - sudo ls /etc/postgresql/
- - echo installing $COMPONENT
- - sudo rm -f /usr/local/bin/yarn
- - nvm install 10
- - rvm install 2.6.3 # was 2.5.1
- - gem install bundler
- - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
- before_script:
- - echo creating pg database hyper_mesh_test_db
- - psql --version
- - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
- - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
- - echo before_script $COMPONENT
- - cd ruby/$COMPONENT
- - bundle install --jobs=3 --retry=3
- - bundle exec rake spec:prepare
- - google-chrome --version
- - which google-chrome
- - yarn install
- script:
- - echo running script $COMPONENT
- - DRIVER=travis bundle exec rake $TASK
+# language: bash
+# cache:
+# bundler: true
+# directories:
+# - node_modules # NPM packages
+# _test_gem: &_test_gem
+# # env:
+# # global:
+# # - PGPORT=5433
+# stage: test
+services:
+ - postgresql
+addons:
+ apt:
+ sources:
+ - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
+ key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
+ - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
+ key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
+ packages:
+ - chromium-chromedriver
+ - google-chrome-stable
+ - yarn
+ - redis-server
+ # mariadb: '10.3' # mariadb works fine...
+ postgresql: "9.6"
+before_install:
+ # - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+ - sudo ls /etc/postgresql/
+ - echo installing $COMPONENT
+ - sudo rm -f /usr/local/bin/yarn
+ - nvm install 10
+ - rvm install 2.6.3 # was 2.5.1
+ - gem install bundler
+ - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
+before_script:
+ - echo creating pg database hyper_mesh_test_db
+ - psql --version
+ - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
+ - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
+ - echo before_script $COMPONENT
+ - cd ruby/$COMPONENT
+ - bundle install --jobs=3 --retry=3
+ - bundle exec rake spec:prepare
+ - google-chrome --version
+ - which google-chrome
+ - yarn install
+script:
+ - echo running script $COMPONENT
+ - DRIVER=travis bundle exec rake $TASK
-_deploy_gem: &_deploy_gem
- stage: release gems
- before_script:
- - cd ruby/$COMPONENT
- script:
- - echo deploying $COMPONENT
- deploy:
- - provider: rubygems
- api_key:
- secure: "ORJMyp20YFCkvujBfxoDPwEZy8R8YJaKwRhHZUDTPZPiS84mJA7Mqd0JjvRlF0mlH/WzspruM7hZV0CuMU8F/0raRhSUU9RBh5veZ/4ij9kboCYnfuqBVt6qPRtaf8DgKe7CWGioUrTISJCVKLnygY6gZd2aFXCEbqZMrkUvC7y43ymOoFoeyCLsXC0j5uJxdHgNfbaIUetIl2DQJUbC2Rgq1Iaxvi72Ae97TR2xRCu+ko8DopRpQCug6U81IhzXftizGfKwzecqVFjuMn3XEf+UDlU6xbvwWWkcwjYNAbP2Kk+mWwUMx36s+1Pyx8MOveYLTwnQJ6gHocZHzh7WJOD548JNU3F5oXIlUB4EzD20bCSIeRKOdxTuKrNk7W3a5qGERuQi4rkIlkKaFIBP55IkliUxvYxqr0WujsjO2reRcNhNcLVGCOaX6LZbWFR5bf0WiEOL4vOxPNw66sI2JVHoMmQeAYtL2ghxikdSPXKRc+inT3QiRBsh+ns8YrAP7sV4lX6r/qyWUtPh6kY8xIeTP4VzMviyf20m5u++omao/FSEtVnU3cro5KjrZLg3ILg4NpNG+xoRqPS/Hmxry5ZPrggqNrxoqWuO7pLd/NnV/AnLiT8rd2P0PTriP9uRIM8+fFfyOeGwbplOLrbWUPnCdQVWp6dYOrNgE2yDJ/I="
- on:
- tags: true
-jobs:
- include:
- - <<: *_test_gem
- env: PGPORT=5433 COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
+# _deploy_gem: &_deploy_gem
+# stage: release gems
+# before_script:
+# - cd ruby/$COMPONENT
+# script:
+# - echo deploying $COMPONENT
+# deploy:
+# - provider: rubygems
+# api_key:
+# secure: "ORJMyp20YFCkvujBfxoDPwEZy8R8YJaKwRhHZUDTPZPiS84mJA7Mqd0JjvRlF0mlH/WzspruM7hZV0CuMU8F/0raRhSUU9RBh5veZ/4ij9kboCYnfuqBVt6qPRtaf8DgKe7CWGioUrTISJCVKLnygY6gZd2aFXCEbqZMrkUvC7y43ymOoFoeyCLsXC0j5uJxdHgNfbaIUetIl2DQJUbC2Rgq1Iaxvi72Ae97TR2xRCu+ko8DopRpQCug6U81IhzXftizGfKwzecqVFjuMn3XEf+UDlU6xbvwWWkcwjYNAbP2Kk+mWwUMx36s+1Pyx8MOveYLTwnQJ6gHocZHzh7WJOD548JNU3F5oXIlUB4EzD20bCSIeRKOdxTuKrNk7W3a5qGERuQi4rkIlkKaFIBP55IkliUxvYxqr0WujsjO2reRcNhNcLVGCOaX6LZbWFR5bf0WiEOL4vOxPNw66sI2JVHoMmQeAYtL2ghxikdSPXKRc+inT3QiRBsh+ns8YrAP7sV4lX6r/qyWUtPh6kY8xIeTP4VzMviyf20m5u++omao/FSEtVnU3cro5KjrZLg3ILg4NpNG+xoRqPS/Hmxry5ZPrggqNrxoqWuO7pLd/NnV/AnLiT8rd2P0PTriP9uRIM8+fFfyOeGwbplOLrbWUPnCdQVWp6dYOrNgE2yDJ/I="
+# on:
+# tags: true
+# jobs:
+# include:
+# - <<: *_test_gem
+# env: PGPORT=5433 COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
# language: bash
# cache:
From e7494ca9f9ccd95b32f1c291c8dd780f3a382c58 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 23 Feb 2021 23:07:13 -0500
Subject: [PATCH 125/307] trying to get config
---
.travis.yml | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/.travis.yml b/.travis.yml
index f8126dc8e..6def0f8c7 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -26,7 +26,7 @@ addons:
postgresql: "9.6"
before_install:
# - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- - sudo ls /etc/postgresql/
+ - sudo cat /etc/postgresql/10/main/pg_hba.conf
- echo installing $COMPONENT
- sudo rm -f /usr/local/bin/yarn
- nvm install 10
From 32c2c8837e084d291b4603d75f76ee781efdbc5b Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 23 Feb 2021 23:19:59 -0500
Subject: [PATCH 126/307] now trying to get 11 config
---
.travis.yml | 135 +++++++++++++++++++++++++++-------------------------
1 file changed, 69 insertions(+), 66 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 6def0f8c7..d78cdecd0 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -1,70 +1,73 @@
-# language: bash
-# cache:
-# bundler: true
-# directories:
-# - node_modules # NPM packages
-# _test_gem: &_test_gem
-# # env:
-# # global:
-# # - PGPORT=5433
-# stage: test
-services:
- - postgresql
-addons:
- apt:
- sources:
- - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
- key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
- - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
- key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
- packages:
- - chromium-chromedriver
- - google-chrome-stable
- - yarn
- - redis-server
- # mariadb: '10.3' # mariadb works fine...
- postgresql: "9.6"
-before_install:
- # - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- - sudo cat /etc/postgresql/10/main/pg_hba.conf
- - echo installing $COMPONENT
- - sudo rm -f /usr/local/bin/yarn
- - nvm install 10
- - rvm install 2.6.3 # was 2.5.1
- - gem install bundler
- - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
-before_script:
- - echo creating pg database hyper_mesh_test_db
- - psql --version
- - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
- - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
- - echo before_script $COMPONENT
- - cd ruby/$COMPONENT
- - bundle install --jobs=3 --retry=3
- - bundle exec rake spec:prepare
- - google-chrome --version
- - which google-chrome
- - yarn install
-script:
- - echo running script $COMPONENT
- - DRIVER=travis bundle exec rake $TASK
+language: bash
+cache:
+ bundler: true
+ directories:
+ - node_modules # NPM packages
+_test_gem: &_test_gem
+ # env:
+ # global:
+ # - PGPORT=5433
+ stage: test
+ services:
+ - postgresql
+ addons:
+ apt:
+ sources:
+ - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
+ key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
+ - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
+ key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
+ packages:
+ - chromium-chromedriver
+ - google-chrome-stable
+ - yarn
+ - redis-server
+ # mariadb: '10.3' # mariadb works fine...
+ postgresql: "11.2"
+ before_install:
+ - sudo apt-get update
+ - sudo apt-get --yes remove postgresql\*
+ - sudo apt-get install -y postgresql-11 postgresql-client-11
+ # - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+ - sudo cat /etc/postgressql/11/main/pg_hba.conf
+ - echo installing $COMPONENT
+ - sudo rm -f /usr/local/bin/yarn
+ - nvm install 10
+ - rvm install 2.6.3 # was 2.5.1
+ - gem install bundler
+ - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
+ before_script:
+ - echo creating pg database hyper_mesh_test_db
+ - psql --version
+ - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
+ - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
+ - echo before_script $COMPONENT
+ - cd ruby/$COMPONENT
+ - bundle install --jobs=3 --retry=3
+ - bundle exec rake spec:prepare
+ - google-chrome --version
+ - which google-chrome
+ - yarn install
+ script:
+ - echo running script $COMPONENT
+ - DRIVER=travis bundle exec rake $TASK
-# _deploy_gem: &_deploy_gem
-# stage: release gems
-# before_script:
-# - cd ruby/$COMPONENT
-# script:
-# - echo deploying $COMPONENT
-# deploy:
-# - provider: rubygems
-# api_key:
-# secure: "ORJMyp20YFCkvujBfxoDPwEZy8R8YJaKwRhHZUDTPZPiS84mJA7Mqd0JjvRlF0mlH/WzspruM7hZV0CuMU8F/0raRhSUU9RBh5veZ/4ij9kboCYnfuqBVt6qPRtaf8DgKe7CWGioUrTISJCVKLnygY6gZd2aFXCEbqZMrkUvC7y43ymOoFoeyCLsXC0j5uJxdHgNfbaIUetIl2DQJUbC2Rgq1Iaxvi72Ae97TR2xRCu+ko8DopRpQCug6U81IhzXftizGfKwzecqVFjuMn3XEf+UDlU6xbvwWWkcwjYNAbP2Kk+mWwUMx36s+1Pyx8MOveYLTwnQJ6gHocZHzh7WJOD548JNU3F5oXIlUB4EzD20bCSIeRKOdxTuKrNk7W3a5qGERuQi4rkIlkKaFIBP55IkliUxvYxqr0WujsjO2reRcNhNcLVGCOaX6LZbWFR5bf0WiEOL4vOxPNw66sI2JVHoMmQeAYtL2ghxikdSPXKRc+inT3QiRBsh+ns8YrAP7sV4lX6r/qyWUtPh6kY8xIeTP4VzMviyf20m5u++omao/FSEtVnU3cro5KjrZLg3ILg4NpNG+xoRqPS/Hmxry5ZPrggqNrxoqWuO7pLd/NnV/AnLiT8rd2P0PTriP9uRIM8+fFfyOeGwbplOLrbWUPnCdQVWp6dYOrNgE2yDJ/I="
-# on:
-# tags: true
-# jobs:
-# include:
-# - <<: *_test_gem
-# env: PGPORT=5433 COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
+_deploy_gem: &_deploy_gem
+ stage: release gems
+ before_script:
+ - cd ruby/$COMPONENT
+ script:
+ - echo deploying $COMPONENT
+ deploy:
+ - provider: rubygems
+ api_key:
+ secure: "ORJMyp20YFCkvujBfxoDPwEZy8R8YJaKwRhHZUDTPZPiS84mJA7Mqd0JjvRlF0mlH/WzspruM7hZV0CuMU8F/0raRhSUU9RBh5veZ/4ij9kboCYnfuqBVt6qPRtaf8DgKe7CWGioUrTISJCVKLnygY6gZd2aFXCEbqZMrkUvC7y43ymOoFoeyCLsXC0j5uJxdHgNfbaIUetIl2DQJUbC2Rgq1Iaxvi72Ae97TR2xRCu+ko8DopRpQCug6U81IhzXftizGfKwzecqVFjuMn3XEf+UDlU6xbvwWWkcwjYNAbP2Kk+mWwUMx36s+1Pyx8MOveYLTwnQJ6gHocZHzh7WJOD548JNU3F5oXIlUB4EzD20bCSIeRKOdxTuKrNk7W3a5qGERuQi4rkIlkKaFIBP55IkliUxvYxqr0WujsjO2reRcNhNcLVGCOaX6LZbWFR5bf0WiEOL4vOxPNw66sI2JVHoMmQeAYtL2ghxikdSPXKRc+inT3QiRBsh+ns8YrAP7sV4lX6r/qyWUtPh6kY8xIeTP4VzMviyf20m5u++omao/FSEtVnU3cro5KjrZLg3ILg4NpNG+xoRqPS/Hmxry5ZPrggqNrxoqWuO7pLd/NnV/AnLiT8rd2P0PTriP9uRIM8+fFfyOeGwbplOLrbWUPnCdQVWp6dYOrNgE2yDJ/I="
+ on:
+ tags: true
+jobs:
+ include:
+ - <<: *_test_gem
+ env: PGPORT=5433 COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
# language: bash
# cache:
From cf29e695cf8484288e91d68ada7acdf5e747d6b3 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 23 Feb 2021 23:49:11 -0500
Subject: [PATCH 127/307] now trying to get 11 config 2
---
.travis.yml | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/.travis.yml b/.travis.yml
index d78cdecd0..53534a09b 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -29,7 +29,7 @@ _test_gem: &_test_gem
- sudo apt-get --yes remove postgresql\*
- sudo apt-get install -y postgresql-11 postgresql-client-11
# - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- - sudo cat /etc/postgressql/11/main/pg_hba.conf
+ - sudo cat /etc/postgresql/11/main/pg_hba.conf
- echo installing $COMPONENT
- sudo rm -f /usr/local/bin/yarn
- nvm install 10
From e0787e7c45310c3f5dd6084d6c0ef3b0b2f466bb Mon Sep 17 00:00:00 2001
From: catmando
Date: Wed, 24 Feb 2021 10:33:01 -0500
Subject: [PATCH 128/307] trying to create the config file
---
.travis.yml | 9 ++++++++-
1 file changed, 8 insertions(+), 1 deletion(-)
diff --git a/.travis.yml b/.travis.yml
index 53534a09b..5043fec8f 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -22,12 +22,19 @@ _test_gem: &_test_gem
- google-chrome-stable
- yarn
- redis-server
- # mariadb: '10.3' # mariadb works fine...
+ mariadb: '10.3' # mariadb works fine...
postgresql: "11.2"
before_install:
- sudo apt-get update
- sudo apt-get --yes remove postgresql\*
- sudo apt-get install -y postgresql-11 postgresql-client-11
+ - |
+ cat </etc/postgresql/11/main/pg_hba.conf
+ local all postgres trust
+ local all all trust
+ host all all 127.0.0.1/32 trust
+ host all all ::1/128 trust
+ EOF
# - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- sudo cat /etc/postgresql/11/main/pg_hba.conf
- echo installing $COMPONENT
From 8cb246d17a66968fdc377df58a51010498b62077 Mon Sep 17 00:00:00 2001
From: catmando
Date: Wed, 24 Feb 2021 10:41:26 -0500
Subject: [PATCH 129/307] trying to create the config file 2
---
.travis.yml | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/.travis.yml b/.travis.yml
index 5043fec8f..c552dec9b 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -29,7 +29,7 @@ _test_gem: &_test_gem
- sudo apt-get --yes remove postgresql\*
- sudo apt-get install -y postgresql-11 postgresql-client-11
- |
- cat </etc/postgresql/11/main/pg_hba.conf
+ sudo cat </etc/postgresql/11/main/pg_hba.conf
local all postgres trust
local all all trust
host all all 127.0.0.1/32 trust
From a55b56f6a570960e5306ab8682e21731204b0c11 Mon Sep 17 00:00:00 2001
From: catmando
Date: Wed, 24 Feb 2021 10:50:45 -0500
Subject: [PATCH 130/307] trying to create the config file 3
---
.travis.yml | 12 ++++++------
1 file changed, 6 insertions(+), 6 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index c552dec9b..29a91d3cc 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -29,12 +29,12 @@ _test_gem: &_test_gem
- sudo apt-get --yes remove postgresql\*
- sudo apt-get install -y postgresql-11 postgresql-client-11
- |
- sudo cat </etc/postgresql/11/main/pg_hba.conf
- local all postgres trust
- local all all trust
- host all all 127.0.0.1/32 trust
- host all all ::1/128 trust
- EOF
+ sudo cat </etc/postgresql/11/main/pg_hba.conf
+ local all postgres trust
+ local all all trust
+ host all all 127.0.0.1/32 trust
+ host all all ::1/128 trust
+ EOF
# - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- sudo cat /etc/postgresql/11/main/pg_hba.conf
- echo installing $COMPONENT
From 46b7e04c992ddafdb623e3fb84468e05d6c6a4e6 Mon Sep 17 00:00:00 2001
From: catmando
Date: Wed, 24 Feb 2021 16:18:52 -0500
Subject: [PATCH 131/307] reverted changes to do with postgresql
---
.travis.yml | 342 ++++++------------
ruby/hyper-model/hyper-model.gemspec | 2 +-
.../batch1/column_types/column_type_spec.rb | 22 +-
.../app/hyperstack/models/default_test.rb | 2 -
.../app/hyperstack/models/type_test.rb | 2 -
.../spec/test_app/config/database.yml | 28 +-
6 files changed, 118 insertions(+), 280 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 29a91d3cc..e852a5744 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -1,15 +1,11 @@
-language: bash
+language: bash
cache:
bundler: true
directories:
- - node_modules # NPM packages
+ - node_modules # NPM packages
+
_test_gem: &_test_gem
- # env:
- # global:
- # - PGPORT=5433
stage: test
- services:
- - postgresql
addons:
apt:
sources:
@@ -22,32 +18,17 @@ _test_gem: &_test_gem
- google-chrome-stable
- yarn
- redis-server
- mariadb: '10.3' # mariadb works fine...
- postgresql: "11.2"
+ mariadb: '10.3'
before_install:
- - sudo apt-get update
- - sudo apt-get --yes remove postgresql\*
- - sudo apt-get install -y postgresql-11 postgresql-client-11
- - |
- sudo cat </etc/postgresql/11/main/pg_hba.conf
- local all postgres trust
- local all all trust
- host all all 127.0.0.1/32 trust
- host all all ::1/128 trust
- EOF
- # - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- - sudo cat /etc/postgresql/11/main/pg_hba.conf
- echo installing $COMPONENT
+ # yarn is in /usr/local/bin/yarn version 1.3.2 and is not a package
+ # must remove this zombie for new yarn to work
- sudo rm -f /usr/local/bin/yarn
- nvm install 10
- rvm install 2.6.3 # was 2.5.1
- gem install bundler
- ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
before_script:
- - echo creating pg database hyper_mesh_test_db
- - psql --version
- - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
- - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
- echo before_script $COMPONENT
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
@@ -74,214 +55,105 @@ _deploy_gem: &_deploy_gem
jobs:
include:
- <<: *_test_gem
- env: PGPORT=5433 COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
+ env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-component RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-router RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-store RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part2
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part3
+ - <<: *_test_gem
+ env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1
+
+ - <<: *_test_gem
+ env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
+ - <<: *_test_gem
+ env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+
+ - <<: *_test_gem
+ env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
+ - <<: *_test_gem
+ env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# language: bash
-# cache:
-# bundler: true
-# directories:
-# - node_modules # NPM packages
-#
-# # services:
-# # - postgresql
-# #
-# # addons:
-# # postgresql: '9.6'
-# #
-# # before_script:
-# # - psql -c 'create database hyper_mesh_test_db;' -U postgres
-#
-# before_install:
-# # - sudo apt-get update
-# # - sudo apt-get --yes remove postgresql\*
-# # - sudo apt-get install -y postgresql-11 postgresql-client-11
-# # - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
-# - sudo cat /etc/postgresql/9.6/main/pg_hba.conf
-# # - sudo service postgresql restart 11
-# # before_script:
-# # - echo creating pg database hyper_mesh_test_db
-# # - psql --version
-# # - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
-# # - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
-# # services:
-# # - postgresql
-# # addons:
-# # postgresql: "11.2"
-# # env:
-# # global:
-# # - PGPORT=5433
-#
-# _test_gem: &_test_gem
-# # env:
-# # global:
-# # - PGPORT=5433
-# stage: test
-# services:
-# - postgresql
-# addons:
-# apt:
-# sources:
-# - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
-# key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
-# - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
-# key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
-# packages:
-# - chromium-chromedriver
-# - google-chrome-stable
-# - yarn
-# - redis-server
-# mariadb: '10.3'
-# postgresql: "9.6"
-# before_install:
-# # - sudo apt-get update
-# # - sudo apt-get --yes remove postgresql\*
-# # - sudo apt-get install -y postgresql-11 postgresql-client-11
-# # - sudo cat /etc/postgresql/11/main/pg_hba.conf
-# # #- sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
-# # # - sudo ls /etc
-# # # - sudo ls /etc/tmp
-# # # - sudo cp /etc/tmp/pg_hba.conf /etc/postgresql/11/main/pg_hba.conf
-# #
-# # - sudo service postgresql restart 11
-# - echo installing $COMPONENT
-# # yarn is in /usr/local/bin/yarn version 1.3.2 and is not a package
-# # must remove this zombie for new yarn to work
-# - sudo rm -f /usr/local/bin/yarn
-# - nvm install 10
-# - rvm install 2.6.3 # was 2.5.1
-# - gem install bundler
-# - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
-# before_script:
-# - echo creating pg database hyper_mesh_test_db
-# - psql --version
-# - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
-# - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
-# - echo before_script $COMPONENT
-# - cd ruby/$COMPONENT
-# - bundle install --jobs=3 --retry=3
-# - psql -c 'create database hyper_mesh_test_db;' -U postgres
-# - bundle exec rake spec:prepare
-# - google-chrome --version
-# - which google-chrome
-# - yarn install
-# script:
-# - echo running script $COMPONENT
-# - DRIVER=travis bundle exec rake $TASK
-#
-# _deploy_gem: &_deploy_gem
-# stage: release gems
-# before_script:
-# - cd ruby/$COMPONENT
-# script:
-# - echo deploying $COMPONENT
-# deploy:
-# - provider: rubygems
-# api_key:
-# secure: "ORJMyp20YFCkvujBfxoDPwEZy8R8YJaKwRhHZUDTPZPiS84mJA7Mqd0JjvRlF0mlH/WzspruM7hZV0CuMU8F/0raRhSUU9RBh5veZ/4ij9kboCYnfuqBVt6qPRtaf8DgKe7CWGioUrTISJCVKLnygY6gZd2aFXCEbqZMrkUvC7y43ymOoFoeyCLsXC0j5uJxdHgNfbaIUetIl2DQJUbC2Rgq1Iaxvi72Ae97TR2xRCu+ko8DopRpQCug6U81IhzXftizGfKwzecqVFjuMn3XEf+UDlU6xbvwWWkcwjYNAbP2Kk+mWwUMx36s+1Pyx8MOveYLTwnQJ6gHocZHzh7WJOD548JNU3F5oXIlUB4EzD20bCSIeRKOdxTuKrNk7W3a5qGERuQi4rkIlkKaFIBP55IkliUxvYxqr0WujsjO2reRcNhNcLVGCOaX6LZbWFR5bf0WiEOL4vOxPNw66sI2JVHoMmQeAYtL2ghxikdSPXKRc+inT3QiRBsh+ns8YrAP7sV4lX6r/qyWUtPh6kY8xIeTP4VzMviyf20m5u++omao/FSEtVnU3cro5KjrZLg3ILg4NpNG+xoRqPS/Hmxry5ZPrggqNrxoqWuO7pLd/NnV/AnLiT8rd2P0PTriP9uRIM8+fFfyOeGwbplOLrbWUPnCdQVWp6dYOrNgE2yDJ/I="
-# on:
-# tags: true
-# jobs:
-# include:
-# # - <<: *_test_gem
-# # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1
-# - <<: *_test_gem
-# env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
-# - <<: *_test_gem
-# env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part2
-# - <<: *_test_gem
-# env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part3
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1
-# #
-# # - <<: *_test_gem
-# # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-# #
-# # - <<: *_test_gem
-# # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
-# # - <<: *_test_gem
-# # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-#
-# - <<: *_deploy_gem
-# env: COMPONENT=hyper-i18n
-# - <<: *_deploy_gem
-# env: COMPONENT=hyper-trace
-# - <<: *_deploy_gem
-# env: COMPONENT=hyper-state
-# - <<: *_deploy_gem
-# env: COMPONENT=hyper-component
-# - <<: *_deploy_gem
-# env: COMPONENT=hyper-model
-# - <<: *_deploy_gem
-# env: COMPONENT=hyper-operation
-# - <<: *_deploy_gem
-# env: COMPONENT=hyper-router
-# - <<: *_deploy_gem
-# env: COMPONENT=hyper-spec
-# - <<: *_deploy_gem
-# env: COMPONENT=hyper-store
-# - <<: *_deploy_gem
-# env: COMPONENT=rails-hyperstack
-# - <<: *_deploy_gem
-# env: COMPONENT=hyperstack-config
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-i18n
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-trace
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-state
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-component
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-model
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-operation
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-router
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-spec
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-store
+ - <<: *_deploy_gem
+ env: COMPONENT=rails-hyperstack
+ - <<: *_deploy_gem
+ env: COMPONENT=hyperstack-config
diff --git a/ruby/hyper-model/hyper-model.gemspec b/ruby/hyper-model/hyper-model.gemspec
index 20e35b6b5..99c76614b 100644
--- a/ruby/hyper-model/hyper-model.gemspec
+++ b/ruby/hyper-model/hyper-model.gemspec
@@ -34,7 +34,7 @@ Gem::Specification.new do |spec|
spec.add_development_dependency 'factory_bot_rails'
spec.add_development_dependency 'hyper-spec', HyperModel::VERSION
spec.add_development_dependency 'mini_racer'
- spec.add_development_dependency 'pg'
+ spec.add_development_dependency 'mysql2'
spec.add_development_dependency 'opal-rails', '>= 0.9.4', '< 2.0'
spec.add_development_dependency 'pry-rescue'
spec.add_development_dependency 'pry-stack_explorer'
diff --git a/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb b/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb
index 7c54007d2..51a4c49fa 100644
--- a/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb
+++ b/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb
@@ -131,9 +131,7 @@ class DefaultTest < ActiveRecord::Base
string: "hello",
text: "goodby",
time: t,
- timestamp: t,
- json: {kind: :json},
- jsonb: {kind: :jsonb}
+ timestamp: t
)
expect do
TypeTest.columns_hash.collect do |attr, _info|
@@ -141,7 +139,7 @@ class DefaultTest < ActiveRecord::Base
end
end.to_on_client eq([
'Number', 'NilClass', 'Boolean', 'Date', 'Time', 'Number', 'Number', 'Number',
- 'Number', 'String', 'String', 'Time', 'Time', 'NilClass', 'NilClass'
+ 'Number', 'String', 'String', 'Time', 'Time'
])
check_errors
end
@@ -171,7 +169,7 @@ class DefaultTest < ActiveRecord::Base
string: "hello",
text: "goodby",
time: t,
- timestamp: t # see default tests below for json and jsonb
+ timestamp: t
)
expect do
t = TypeTest.find(1)
@@ -199,9 +197,7 @@ class DefaultTest < ActiveRecord::Base
string: "hello",
text: "goodby",
time: t.time,
- timestamp: t.time,
- json: {kind: :json},
- jsonb: {kind: :jsonb}
+ timestamp: t.time
)
expect do
Hyperstack::Model.load do
@@ -222,9 +218,7 @@ class DefaultTest < ActiveRecord::Base
'String', 'hello',
'String', 'goodby',
'Time', t.time_only.as_json, # date is indeterminate for active record time
- 'Time', t.as_json,
- 'Hash', {'kind' => 'json'},
- 'Hash', {'kind' => 'jsonb'}
+ 'Time', t.as_json
])
check_errors
end
@@ -308,14 +302,12 @@ class DefaultTest < ActiveRecord::Base
[
t.string, t.date, t.datetime, t.integer_from_string, t.integer_from_int,
t.float_from_string, t.float_from_float,
- t.boolean_from_falsy_string, t.boolean_from_truthy_string, t.boolean_from_falsy_value,
- t.json[:kind], t.jsonb[:kind] # the default for json and jsonb is nil so we will test dummy operations here
+ t.boolean_from_falsy_string, t.boolean_from_truthy_string, t.boolean_from_falsy_value
]
end.to eq([
"I'm a string!", r.date.as_json, Timex.new(r.datetime.localtime).as_json, 99, 98,
0.02, 0.01,
- false, true, false,
- 'json', 'jsonb'
+ false, true, false
])
check_errors
end
diff --git a/ruby/hyper-model/spec/test_app/app/hyperstack/models/default_test.rb b/ruby/hyper-model/spec/test_app/app/hyperstack/models/default_test.rb
index 82ce7fbd4..f7433d6dc 100644
--- a/ruby/hyper-model/spec/test_app/app/hyperstack/models/default_test.rb
+++ b/ruby/hyper-model/spec/test_app/app/hyperstack/models/default_test.rb
@@ -11,8 +11,6 @@ def self.build_tables
t.boolean :boolean_from_falsy_string, default: "OFF"
t.boolean :boolean_from_truthy_string, default: "something-else"
t.boolean :boolean_from_falsy_value, default: false
- t.json :json, default: {kind: :json}
- t.jsonb :jsonb, default: {kind: :jsonb}
end
end
end
diff --git a/ruby/hyper-model/spec/test_app/app/hyperstack/models/type_test.rb b/ruby/hyper-model/spec/test_app/app/hyperstack/models/type_test.rb
index 50fc55d53..3f8920a16 100644
--- a/ruby/hyper-model/spec/test_app/app/hyperstack/models/type_test.rb
+++ b/ruby/hyper-model/spec/test_app/app/hyperstack/models/type_test.rb
@@ -13,8 +13,6 @@ def self.build_tables
t.text(:text)
t.time(:time)
t.timestamp(:timestamp)
- t.json(:json)
- t.jsonb(:jsonb)
end
end
end
diff --git a/ruby/hyper-model/spec/test_app/config/database.yml b/ruby/hyper-model/spec/test_app/config/database.yml
index ad8c9dd1c..92191c367 100644
--- a/ruby/hyper-model/spec/test_app/config/database.yml
+++ b/ruby/hyper-model/spec/test_app/config/database.yml
@@ -1,30 +1,8 @@
-# SQLite version 3.x
-# gem install sqlite3
-#
-# Ensure the SQLite 3 gem is defined in your Gemfile
-# gem 'sqlite3'
-#
-# default: &default
-# adapter: mysql2
-# encoding: utf8
-# username: root
-#
-# development:
-# <<: *default
-# database: hyper_mesh_development_db
-#
-# test:
-# <<: *default
-# database: hyper_mesh_test_db
-#
-# production:
-# <<: *default
-# database: hyper_mesh_production_db
default: &default
- adapter: postgresql
- pool: 5
- timeout: 5000
+ adapter: mysql2
+ encoding: utf8
+ username: root
development:
<<: *default
From 27d06046ae693eae2dbad1b7c7f41e8396297c9c Mon Sep 17 00:00:00 2001
From: catmando
Date: Wed, 24 Feb 2021 17:05:58 -0500
Subject: [PATCH 132/307] latest rails compatibility and put schema back for
hyper-model
---
ruby/hyper-model/spec/test_app/db/schema.rb | 101 ++++++++++++++++++
.../test_app/app/assets/config/manifest.js | 2 +
2 files changed, 103 insertions(+)
create mode 100644 ruby/hyper-model/spec/test_app/db/schema.rb
create mode 100644 ruby/hyper-spec/spec/test_app/app/assets/config/manifest.js
diff --git a/ruby/hyper-model/spec/test_app/db/schema.rb b/ruby/hyper-model/spec/test_app/db/schema.rb
new file mode 100644
index 000000000..03ed1ad18
--- /dev/null
+++ b/ruby/hyper-model/spec/test_app/db/schema.rb
@@ -0,0 +1,101 @@
+# This file is auto-generated from the current state of the database. Instead
+# of editing this file, please use the migrations feature of Active Record to
+# incrementally modify your database, and then regenerate this schema definition.
+#
+# This file is the source Rails uses to define your schema when running `rails
+# db:schema:load`. When creating a new database, `rails db:schema:load` tends to
+# be faster and is potentially less error prone than running all of your
+# migrations from scratch. Old migrations may fail to apply correctly if those
+# migrations use external dependencies or application code.
+#
+# It's strongly recommended that you check this file into your version control system.
+
+ActiveRecord::Schema.define(version: 2016_07_31_182106) do
+
+ create_table "addresses", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
+ t.string "street"
+ t.string "city"
+ t.string "state"
+ t.string "zip"
+ t.datetime "created_at"
+ t.datetime "updated_at"
+ end
+
+ create_table "child_models", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
+ t.string "child_attribute"
+ t.integer "test_model_id"
+ end
+
+ create_table "comments", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
+ t.text "comment"
+ t.datetime "created_at"
+ t.datetime "updated_at"
+ t.integer "todo_id"
+ t.integer "author_id"
+ t.integer "user_id"
+ t.integer "todo_item_id"
+ end
+
+ create_table "hyperstack_connections", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
+ t.string "channel"
+ t.string "session"
+ t.datetime "created_at"
+ t.datetime "expires_at"
+ t.datetime "refresh_at"
+ end
+
+ create_table "hyperstack_queued_messages", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
+ t.text "data"
+ t.integer "connection_id"
+ end
+
+ create_table "test_models", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
+ t.string "test_attribute"
+ t.boolean "completed"
+ t.datetime "created_at", null: false
+ t.datetime "updated_at", null: false
+ end
+
+ create_table "todo_items", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
+ t.string "title"
+ t.text "description"
+ t.boolean "complete"
+ t.datetime "created_at"
+ t.datetime "updated_at"
+ t.integer "user_id"
+ t.integer "comment_id"
+ end
+
+ create_table "todos", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
+ t.string "title"
+ t.text "description"
+ t.datetime "created_at", null: false
+ t.datetime "updated_at", null: false
+ t.boolean "completed", default: false, null: false
+ t.integer "created_by_id"
+ t.integer "owner_id"
+ end
+
+ create_table "users", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
+ t.string "role"
+ t.integer "manager_id"
+ t.string "first_name"
+ t.string "last_name"
+ t.string "email"
+ t.datetime "created_at"
+ t.datetime "updated_at"
+ t.string "address_street"
+ t.string "address_city"
+ t.string "address_state"
+ t.string "address_zip"
+ t.integer "address_id"
+ t.string "address2_street"
+ t.string "address2_city"
+ t.string "address2_state"
+ t.string "address2_zip"
+ t.string "data_string"
+ t.integer "data_times"
+ t.integer "test_enum"
+ end
+
+end
diff --git a/ruby/hyper-spec/spec/test_app/app/assets/config/manifest.js b/ruby/hyper-spec/spec/test_app/app/assets/config/manifest.js
new file mode 100644
index 000000000..21a78805c
--- /dev/null
+++ b/ruby/hyper-spec/spec/test_app/app/assets/config/manifest.js
@@ -0,0 +1,2 @@
+//= link_directory ../javascripts .js
+//= link_directory ../stylesheets .css
From 41fd864a32f9bf10951c344c54bce1061bbdb32d Mon Sep 17 00:00:00 2001
From: catmando
Date: Wed, 24 Feb 2021 23:14:56 -0500
Subject: [PATCH 133/307] fixed primary_key against string instead of class
---
ruby/hyper-model/lib/reactive_record/broadcast.rb | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/ruby/hyper-model/lib/reactive_record/broadcast.rb b/ruby/hyper-model/lib/reactive_record/broadcast.rb
index 699ed9f3e..bf3214818 100644
--- a/ruby/hyper-model/lib/reactive_record/broadcast.rb
+++ b/ruby/hyper-model/lib/reactive_record/broadcast.rb
@@ -148,7 +148,7 @@ def local(operation, record, data)
@klass = record.class.name
@record = data
record.backing_record.destroyed = false
- @record[@klass.primary_key] = record.id if record.id
+ @record[record.primary_key] = record.id if record.id
record.backing_record.destroyed = @destroyed
@backing_record = record.backing_record
@previous_changes = record.changes
From ce50af2ac4229acf2a168fe229d5d28f08379bcd Mon Sep 17 00:00:00 2001
From: catmando
Date: Thu, 25 Feb 2021 08:50:59 -0500
Subject: [PATCH 134/307] following travis cs instructions
---
.travis.yml | 195 ++++++++++++++++++++++++++++++++--------------------
1 file changed, 119 insertions(+), 76 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 29a91d3cc..6ede77e6b 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -1,80 +1,123 @@
-language: bash
-cache:
- bundler: true
- directories:
- - node_modules # NPM packages
-_test_gem: &_test_gem
- # env:
- # global:
- # - PGPORT=5433
- stage: test
- services:
- - postgresql
- addons:
- apt:
- sources:
- - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
- key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
- - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
- key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
- packages:
- - chromium-chromedriver
- - google-chrome-stable
- - yarn
- - redis-server
- mariadb: '10.3' # mariadb works fine...
- postgresql: "11.2"
- before_install:
- - sudo apt-get update
- - sudo apt-get --yes remove postgresql\*
- - sudo apt-get install -y postgresql-11 postgresql-client-11
- - |
- sudo cat </etc/postgresql/11/main/pg_hba.conf
- local all postgres trust
- local all all trust
- host all all 127.0.0.1/32 trust
- host all all ::1/128 trust
- EOF
- # - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- - sudo cat /etc/postgresql/11/main/pg_hba.conf
- - echo installing $COMPONENT
- - sudo rm -f /usr/local/bin/yarn
- - nvm install 10
- - rvm install 2.6.3 # was 2.5.1
- - gem install bundler
- - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
- before_script:
- - echo creating pg database hyper_mesh_test_db
- - psql --version
- - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
- - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
- - echo before_script $COMPONENT
- - cd ruby/$COMPONENT
- - bundle install --jobs=3 --retry=3
- - bundle exec rake spec:prepare
- - google-chrome --version
- - which google-chrome
- - yarn install
- script:
- - echo running script $COMPONENT
- - DRIVER=travis bundle exec rake $TASK
+dist: xenial
-_deploy_gem: &_deploy_gem
- stage: release gems
- before_script:
- - cd ruby/$COMPONENT
- script:
- - echo deploying $COMPONENT
- deploy:
- - provider: rubygems
- api_key:
- secure: "ORJMyp20YFCkvujBfxoDPwEZy8R8YJaKwRhHZUDTPZPiS84mJA7Mqd0JjvRlF0mlH/WzspruM7hZV0CuMU8F/0raRhSUU9RBh5veZ/4ij9kboCYnfuqBVt6qPRtaf8DgKe7CWGioUrTISJCVKLnygY6gZd2aFXCEbqZMrkUvC7y43ymOoFoeyCLsXC0j5uJxdHgNfbaIUetIl2DQJUbC2Rgq1Iaxvi72Ae97TR2xRCu+ko8DopRpQCug6U81IhzXftizGfKwzecqVFjuMn3XEf+UDlU6xbvwWWkcwjYNAbP2Kk+mWwUMx36s+1Pyx8MOveYLTwnQJ6gHocZHzh7WJOD548JNU3F5oXIlUB4EzD20bCSIeRKOdxTuKrNk7W3a5qGERuQi4rkIlkKaFIBP55IkliUxvYxqr0WujsjO2reRcNhNcLVGCOaX6LZbWFR5bf0WiEOL4vOxPNw66sI2JVHoMmQeAYtL2ghxikdSPXKRc+inT3QiRBsh+ns8YrAP7sV4lX6r/qyWUtPh6kY8xIeTP4VzMviyf20m5u++omao/FSEtVnU3cro5KjrZLg3ILg4NpNG+xoRqPS/Hmxry5ZPrggqNrxoqWuO7pLd/NnV/AnLiT8rd2P0PTriP9uRIM8+fFfyOeGwbplOLrbWUPnCdQVWp6dYOrNgE2yDJ/I="
- on:
- tags: true
-jobs:
- include:
- - <<: *_test_gem
- env: PGPORT=5433 COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
+addons:
+ apt:
+ sources:
+ - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
+ key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
+ - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
+ key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
+ packages:
+ - postgresql-11
+ - chromium-chromedriver
+ - google-chrome-stable
+ - yarn
+ - redis-server
+ postgresql: '11'
+
+before_install:
+ - sudo sed -i 's/port = 5433/port = 5432/' /etc/postgresql/11/main/postgresql.conf
+ - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+ - sudo service postgresql stop
+ - sudo service postgresql start 11
+ - postgres --version
+ - sudo rm -f /usr/local/bin/yarn
+ - nvm install 10
+ - rvm install 2.6.3 # was 2.5.1
+ - gem install bundler
+ - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
+ - echo 'install completed'
+
+before_script:
+ - psql -c 'create database hyper_mesh_test_db;' -U postgres
+ - cd ruby/hyper-model
+ - bundle install --jobs=3 --retry=3
+ - bundle exec rake spec:prepare
+ - google-chrome --version
+ - which google-chrome
+ - yarn install
+script:
+ - DRIVER=travis bundle exec rspec spec/batch1/column_types/column_types_spec.rb:121
+#
+#
+#
+# language: bash
+# cache:
+# bundler: true
+# directories:
+# - node_modules # NPM packages
+# _test_gem: &_test_gem
+# # env:
+# # global:
+# # - PGPORT=5433
+# stage: test
+# services:
+# - postgresql
+# addons:
+# apt:
+# sources:
+# - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
+# key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
+# - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
+# key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
+# packages:
+# - chromium-chromedriver
+# - google-chrome-stable
+# - yarn
+# - redis-server
+# mariadb: '10.3' # mariadb works fine...
+# postgresql: "11.2"
+# before_install:
+# - sudo apt-get update
+# - sudo apt-get --yes remove postgresql\*
+# - sudo apt-get install -y postgresql-11 postgresql-client-11
+# - |
+# sudo cat </etc/postgresql/11/main/pg_hba.conf
+# local all postgres trust
+# local all all trust
+# host all all 127.0.0.1/32 trust
+# host all all ::1/128 trust
+# EOF
+# # - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+# - sudo cat /etc/postgresql/11/main/pg_hba.conf
+# - echo installing $COMPONENT
+# - sudo rm -f /usr/local/bin/yarn
+# - nvm install 10
+# - rvm install 2.6.3 # was 2.5.1
+# - gem install bundler
+# - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
+# before_script:
+# - echo creating pg database hyper_mesh_test_db
+# - psql --version
+# - psql -c 'CREATE DATABASE hyper_mesh_test_db;' -U postgres
+# - psql -c 'CREATE ROLE travis SUPERUSER LOGIN CREATEDB;' -U postgres
+# - echo before_script $COMPONENT
+# - cd ruby/$COMPONENT
+# - bundle install --jobs=3 --retry=3
+# - bundle exec rake spec:prepare
+# - google-chrome --version
+# - which google-chrome
+# - yarn install
+# script:
+# - echo running script $COMPONENT
+# - DRIVER=travis bundle exec rake $TASK
+#
+# _deploy_gem: &_deploy_gem
+# stage: release gems
+# before_script:
+# - cd ruby/$COMPONENT
+# script:
+# - echo deploying $COMPONENT
+# deploy:
+# - provider: rubygems
+# api_key:
+# secure: "ORJMyp20YFCkvujBfxoDPwEZy8R8YJaKwRhHZUDTPZPiS84mJA7Mqd0JjvRlF0mlH/WzspruM7hZV0CuMU8F/0raRhSUU9RBh5veZ/4ij9kboCYnfuqBVt6qPRtaf8DgKe7CWGioUrTISJCVKLnygY6gZd2aFXCEbqZMrkUvC7y43ymOoFoeyCLsXC0j5uJxdHgNfbaIUetIl2DQJUbC2Rgq1Iaxvi72Ae97TR2xRCu+ko8DopRpQCug6U81IhzXftizGfKwzecqVFjuMn3XEf+UDlU6xbvwWWkcwjYNAbP2Kk+mWwUMx36s+1Pyx8MOveYLTwnQJ6gHocZHzh7WJOD548JNU3F5oXIlUB4EzD20bCSIeRKOdxTuKrNk7W3a5qGERuQi4rkIlkKaFIBP55IkliUxvYxqr0WujsjO2reRcNhNcLVGCOaX6LZbWFR5bf0WiEOL4vOxPNw66sI2JVHoMmQeAYtL2ghxikdSPXKRc+inT3QiRBsh+ns8YrAP7sV4lX6r/qyWUtPh6kY8xIeTP4VzMviyf20m5u++omao/FSEtVnU3cro5KjrZLg3ILg4NpNG+xoRqPS/Hmxry5ZPrggqNrxoqWuO7pLd/NnV/AnLiT8rd2P0PTriP9uRIM8+fFfyOeGwbplOLrbWUPnCdQVWp6dYOrNgE2yDJ/I="
+# on:
+# tags: true
+# jobs:
+# include:
+# - <<: *_test_gem
+# env: PGPORT=5433 COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
# language: bash
# cache:
From 62076e095a40ba1a8f2770629b37717702922923 Mon Sep 17 00:00:00 2001
From: catmando
Date: Thu, 25 Feb 2021 09:00:18 -0500
Subject: [PATCH 135/307] removed spec prepare for now
---
.travis.yml | 1 -
1 file changed, 1 deletion(-)
diff --git a/.travis.yml b/.travis.yml
index 6ede77e6b..83045b73d 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -32,7 +32,6 @@ before_script:
- psql -c 'create database hyper_mesh_test_db;' -U postgres
- cd ruby/hyper-model
- bundle install --jobs=3 --retry=3
- - bundle exec rake spec:prepare
- google-chrome --version
- which google-chrome
- yarn install
From 893a185716db5f7f6cc833d30632f3ef4ee34662 Mon Sep 17 00:00:00 2001
From: catmando
Date: Thu, 25 Feb 2021 09:04:48 -0500
Subject: [PATCH 136/307] typo in name of example spec
---
.travis.yml | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/.travis.yml b/.travis.yml
index 83045b73d..104c7edf6 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -36,7 +36,7 @@ before_script:
- which google-chrome
- yarn install
script:
- - DRIVER=travis bundle exec rspec spec/batch1/column_types/column_types_spec.rb:121
+ - DRIVER=travis bundle exec rspec spec/batch1/column_types/column_type_spec.rb:121
#
#
#
From b9a0a836066150b1a8c3aec6e3e44b149326c4e0 Mon Sep 17 00:00:00 2001
From: catmando
Date: Thu, 25 Feb 2021 09:17:05 -0500
Subject: [PATCH 137/307] now moving the actual spec to a job with install
outside the job
---
.travis.yml | 69 ++++++++++++++++++++++++++++++++++++++++++++++-------
1 file changed, 61 insertions(+), 8 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 104c7edf6..00d0dc5f9 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -1,3 +1,45 @@
+# This works: See build 717 https://travis-ci.com/github/hyperstack-org/hyperstack/builds/218241993
+
+# dist: xenial
+#
+# addons:
+# apt:
+# sources:
+# - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
+# key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
+# - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
+# key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
+# packages:
+# - postgresql-11
+# - chromium-chromedriver
+# - google-chrome-stable
+# - yarn
+# - redis-server
+# postgresql: '11'
+#
+# before_install:
+# - sudo sed -i 's/port = 5433/port = 5432/' /etc/postgresql/11/main/postgresql.conf
+# - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+# - sudo service postgresql stop
+# - sudo service postgresql start 11
+# - postgres --version
+# - sudo rm -f /usr/local/bin/yarn
+# - nvm install 10
+# - rvm install 2.6.3 # was 2.5.1
+# - gem install bundler
+# - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
+# - echo 'install completed'
+#
+# before_script:
+# - psql -c 'create database hyper_mesh_test_db;' -U postgres
+# - cd ruby/hyper-model
+# - bundle install --jobs=3 --retry=3
+# - google-chrome --version
+# - which google-chrome
+# - yarn install
+# script:
+# - DRIVER=travis bundle exec rspec spec/batch1/column_types/column_type_spec.rb:121
+#---------------------------------------------------------------------------------------
dist: xenial
addons:
@@ -29,14 +71,25 @@ before_install:
- echo 'install completed'
before_script:
- - psql -c 'create database hyper_mesh_test_db;' -U postgres
- - cd ruby/hyper-model
- - bundle install --jobs=3 --retry=3
- - google-chrome --version
- - which google-chrome
- - yarn install
-script:
- - DRIVER=travis bundle exec rspec spec/batch1/column_types/column_type_spec.rb:121
+ - psql -c 'create database hyper_mesh_test_db;' -U postgres
+
+_test_gem: &_test_gem
+ before_script:
+ - cd ruby/$COMPONENT
+ - bundle install --jobs=3 --retry=3
+ - google-chrome --version
+ - which google-chrome
+ - yarn install
+ script:
+ - DRIVER=travis bundle exec rspec spec/batch1/column_types/column_type_spec.rb:121
+
+jobs:
+ include:
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model
+
+# ------------------
+
#
#
#
From d92ec281dc45e395e8d27c33f1a9053fc8322b17 Mon Sep 17 00:00:00 2001
From: catmando
Date: Thu, 25 Feb 2021 09:26:56 -0500
Subject: [PATCH 138/307] now moving the pg install inside the job
---
.travis.yml | 87 ++++++++++++++++++++++++++++++++++++++++++-----------
1 file changed, 70 insertions(+), 17 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 00d0dc5f9..43d800f07 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -40,6 +40,62 @@
# script:
# - DRIVER=travis bundle exec rspec spec/batch1/column_types/column_type_spec.rb:121
#---------------------------------------------------------------------------------------
+#
+# This fails because within the job the db does not exist
+# see job 718: https://travis-ci.com/github/hyperstack-org/hyperstack/builds/218243353
+#
+# dist: xenial
+#
+# addons:
+# apt:
+# sources:
+# - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
+# key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
+# - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
+# key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
+# packages:
+# - postgresql-11
+# - chromium-chromedriver
+# - google-chrome-stable
+# - yarn
+# - redis-server
+# postgresql: '11'
+#
+# before_install:
+# - sudo sed -i 's/port = 5433/port = 5432/' /etc/postgresql/11/main/postgresql.conf
+# - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+# - sudo service postgresql stop
+# - sudo service postgresql start 11
+# - postgres --version
+# - sudo rm -f /usr/local/bin/yarn
+# - nvm install 10
+# - rvm install 2.6.3 # was 2.5.1
+# - gem install bundler
+# - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
+# - echo 'install completed'
+#
+# before_script:
+# - psql -c 'create database hyper_mesh_test_db;' -U postgres
+#
+# _test_gem: &_test_gem
+# before_script:
+# - cd ruby/$COMPONENT
+# - bundle install --jobs=3 --retry=3
+# - google-chrome --version
+# - which google-chrome
+# - yarn install
+# script:
+# - DRIVER=travis bundle exec rspec spec/batch1/column_types/column_type_spec.rb:121
+#
+# jobs:
+# include:
+# - <<: *_test_gem
+# env: COMPONENT=hyper-model
+#---------------------------------------------------------------------------------------
+#
+# This fails because within the job the db does not exist
+# see job 718: https://travis-ci.com/github/hyperstack-org/hyperstack/builds/218243353
+#
dist: xenial
addons:
@@ -57,24 +113,22 @@ addons:
- redis-server
postgresql: '11'
-before_install:
- - sudo sed -i 's/port = 5433/port = 5432/' /etc/postgresql/11/main/postgresql.conf
- - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- - sudo service postgresql stop
- - sudo service postgresql start 11
- - postgres --version
- - sudo rm -f /usr/local/bin/yarn
- - nvm install 10
- - rvm install 2.6.3 # was 2.5.1
- - gem install bundler
- - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
- - echo 'install completed'
-
-before_script:
- - psql -c 'create database hyper_mesh_test_db;' -U postgres
-
_test_gem: &_test_gem
+ before_install:
+ - sudo sed -i 's/port = 5433/port = 5432/' /etc/postgresql/11/main/postgresql.conf
+ - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+ - sudo service postgresql stop
+ - sudo service postgresql start 11
+ - postgres --version
+ - sudo rm -f /usr/local/bin/yarn
+ - nvm install 10
+ - rvm install 2.6.3 # was 2.5.1
+ - gem install bundler
+ - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
+ - echo 'install completed'
+
before_script:
+ - psql -c 'create database hyper_mesh_test_db;' -U postgres
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
- google-chrome --version
@@ -87,7 +141,6 @@ jobs:
include:
- <<: *_test_gem
env: COMPONENT=hyper-model
-
# ------------------
#
From c8c3798666ad9b096d7874c4904fd08bcfe1e92b Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 27 Feb 2021 13:39:27 -0500
Subject: [PATCH 139/307] adding conditional
---
.travis.yml | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/.travis.yml b/.travis.yml
index 43d800f07..73a08fdd5 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -115,6 +115,7 @@ addons:
_test_gem: &_test_gem
before_install:
+ - [ ! -z "${USE_PG}" ] && echo 'installing postgresql'
- sudo sed -i 's/port = 5433/port = 5432/' /etc/postgresql/11/main/postgresql.conf
- sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- sudo service postgresql stop
@@ -140,7 +141,7 @@ _test_gem: &_test_gem
jobs:
include:
- <<: *_test_gem
- env: COMPONENT=hyper-model
+ env: COMPONENT=hyper-model USE_PG=hyper_mesh_test_db
# ------------------
#
From 163f27fa8d7a1bd7c5bf33cff1502e6f14f2f073 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 27 Feb 2021 14:39:01 -0500
Subject: [PATCH 140/307] trying it this way
---
.travis.yml | 10 +++++-----
1 file changed, 5 insertions(+), 5 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 73a08fdd5..ea341495d 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -113,9 +113,9 @@ addons:
- redis-server
postgresql: '11'
-_test_gem: &_test_gem
+_test_gem_pg: &_test_gem_pg
before_install:
- - [ ! -z "${USE_PG}" ] && echo 'installing postgresql'
+ - echo 'installing postgresql'
- sudo sed -i 's/port = 5433/port = 5432/' /etc/postgresql/11/main/postgresql.conf
- sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
- sudo service postgresql stop
@@ -129,7 +129,7 @@ _test_gem: &_test_gem
- echo 'install completed'
before_script:
- - psql -c 'create database hyper_mesh_test_db;' -U postgres
+ - psql -c 'create database $DB;' -U postgres
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
- google-chrome --version
@@ -140,8 +140,8 @@ _test_gem: &_test_gem
jobs:
include:
- - <<: *_test_gem
- env: COMPONENT=hyper-model USE_PG=hyper_mesh_test_db
+ - <<: *_test_gem_pg
+ env: COMPONENT=hyper-model DB=hyper_mesh_test_db
# ------------------
#
From 6a6ecea8ed90658409aaa7afb20bed740812689c Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 27 Feb 2021 16:59:27 -0500
Subject: [PATCH 141/307] trying again
---
.travis.yml | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/.travis.yml b/.travis.yml
index ea341495d..47e20eb1b 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -129,7 +129,7 @@ _test_gem_pg: &_test_gem_pg
- echo 'install completed'
before_script:
- - psql -c 'create database $DB;' -U postgres
+ - psql -c "create database ${DB};" -U postgres
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
- google-chrome --version
From 29e177fb8605be3007513244a720f7a2ad5dc442 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 27 Feb 2021 17:23:10 -0500
Subject: [PATCH 142/307] git git git
---
.postgresql.travis.yml | 46 ++++++++++++++++++++++++++++++++++++++++++
1 file changed, 46 insertions(+)
create mode 100644 .postgresql.travis.yml
diff --git a/.postgresql.travis.yml b/.postgresql.travis.yml
new file mode 100644
index 000000000..fe8744287
--- /dev/null
+++ b/.postgresql.travis.yml
@@ -0,0 +1,46 @@
+dist: xenial
+
+addons:
+ apt:
+ sources:
+ - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
+ key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
+ - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
+ key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
+ packages:
+ - postgresql-11
+ - chromium-chromedriver
+ - google-chrome-stable
+ - yarn
+ - redis-server
+ postgresql: '11'
+
+_test_gem_pg: &_test_gem_pg
+ before_install:
+ - echo 'installing postgresql'
+ - sudo sed -i 's/port = 5433/port = 5432/' /etc/postgresql/11/main/postgresql.conf
+ - sudo cp /etc/postgresql/{9.6,11}/main/pg_hba.conf
+ - sudo service postgresql stop
+ - sudo service postgresql start 11
+ - postgres --version
+ - sudo rm -f /usr/local/bin/yarn
+ - nvm install 10
+ - rvm install 2.6.3 # was 2.5.1
+ - gem install bundler
+ - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
+ - echo 'install completed'
+
+ before_script:
+ - psql -c "create database ${DB};" -U postgres
+ - cd ruby/$COMPONENT
+ - bundle install --jobs=3 --retry=3
+ - google-chrome --version
+ - which google-chrome
+ - yarn install
+ script:
+ - DRIVER=travis bundle exec rspec spec/batch1/column_types/column_type_spec.rb:121
+
+jobs:
+ include:
+ - <<: *_test_gem_pg
+ env: COMPONENT=hyper-model DB=hyper_mesh_test_db
From 9007b95f1983e48027381a9f9edf0e7294aa1f16 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 27 Feb 2021 17:46:47 -0500
Subject: [PATCH 143/307] integrating postgre hyper-model specs
---
ruby/hyper-model/hyper-model.gemspec | 2 +-
.../batch1/column_types/column_type_spec.rb | 22 ++++++++++-----
.../app/hyperstack/models/default_test.rb | 2 ++
.../app/hyperstack/models/type_test.rb | 2 ++
.../spec/test_app/config/database.yml | 28 +++++++++++++++++--
5 files changed, 45 insertions(+), 11 deletions(-)
diff --git a/ruby/hyper-model/hyper-model.gemspec b/ruby/hyper-model/hyper-model.gemspec
index 99c76614b..20e35b6b5 100644
--- a/ruby/hyper-model/hyper-model.gemspec
+++ b/ruby/hyper-model/hyper-model.gemspec
@@ -34,7 +34,7 @@ Gem::Specification.new do |spec|
spec.add_development_dependency 'factory_bot_rails'
spec.add_development_dependency 'hyper-spec', HyperModel::VERSION
spec.add_development_dependency 'mini_racer'
- spec.add_development_dependency 'mysql2'
+ spec.add_development_dependency 'pg'
spec.add_development_dependency 'opal-rails', '>= 0.9.4', '< 2.0'
spec.add_development_dependency 'pry-rescue'
spec.add_development_dependency 'pry-stack_explorer'
diff --git a/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb b/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb
index 51a4c49fa..7c54007d2 100644
--- a/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb
+++ b/ruby/hyper-model/spec/batch1/column_types/column_type_spec.rb
@@ -131,7 +131,9 @@ class DefaultTest < ActiveRecord::Base
string: "hello",
text: "goodby",
time: t,
- timestamp: t
+ timestamp: t,
+ json: {kind: :json},
+ jsonb: {kind: :jsonb}
)
expect do
TypeTest.columns_hash.collect do |attr, _info|
@@ -139,7 +141,7 @@ class DefaultTest < ActiveRecord::Base
end
end.to_on_client eq([
'Number', 'NilClass', 'Boolean', 'Date', 'Time', 'Number', 'Number', 'Number',
- 'Number', 'String', 'String', 'Time', 'Time'
+ 'Number', 'String', 'String', 'Time', 'Time', 'NilClass', 'NilClass'
])
check_errors
end
@@ -169,7 +171,7 @@ class DefaultTest < ActiveRecord::Base
string: "hello",
text: "goodby",
time: t,
- timestamp: t
+ timestamp: t # see default tests below for json and jsonb
)
expect do
t = TypeTest.find(1)
@@ -197,7 +199,9 @@ class DefaultTest < ActiveRecord::Base
string: "hello",
text: "goodby",
time: t.time,
- timestamp: t.time
+ timestamp: t.time,
+ json: {kind: :json},
+ jsonb: {kind: :jsonb}
)
expect do
Hyperstack::Model.load do
@@ -218,7 +222,9 @@ class DefaultTest < ActiveRecord::Base
'String', 'hello',
'String', 'goodby',
'Time', t.time_only.as_json, # date is indeterminate for active record time
- 'Time', t.as_json
+ 'Time', t.as_json,
+ 'Hash', {'kind' => 'json'},
+ 'Hash', {'kind' => 'jsonb'}
])
check_errors
end
@@ -302,12 +308,14 @@ class DefaultTest < ActiveRecord::Base
[
t.string, t.date, t.datetime, t.integer_from_string, t.integer_from_int,
t.float_from_string, t.float_from_float,
- t.boolean_from_falsy_string, t.boolean_from_truthy_string, t.boolean_from_falsy_value
+ t.boolean_from_falsy_string, t.boolean_from_truthy_string, t.boolean_from_falsy_value,
+ t.json[:kind], t.jsonb[:kind] # the default for json and jsonb is nil so we will test dummy operations here
]
end.to eq([
"I'm a string!", r.date.as_json, Timex.new(r.datetime.localtime).as_json, 99, 98,
0.02, 0.01,
- false, true, false
+ false, true, false,
+ 'json', 'jsonb'
])
check_errors
end
diff --git a/ruby/hyper-model/spec/test_app/app/hyperstack/models/default_test.rb b/ruby/hyper-model/spec/test_app/app/hyperstack/models/default_test.rb
index f7433d6dc..82ce7fbd4 100644
--- a/ruby/hyper-model/spec/test_app/app/hyperstack/models/default_test.rb
+++ b/ruby/hyper-model/spec/test_app/app/hyperstack/models/default_test.rb
@@ -11,6 +11,8 @@ def self.build_tables
t.boolean :boolean_from_falsy_string, default: "OFF"
t.boolean :boolean_from_truthy_string, default: "something-else"
t.boolean :boolean_from_falsy_value, default: false
+ t.json :json, default: {kind: :json}
+ t.jsonb :jsonb, default: {kind: :jsonb}
end
end
end
diff --git a/ruby/hyper-model/spec/test_app/app/hyperstack/models/type_test.rb b/ruby/hyper-model/spec/test_app/app/hyperstack/models/type_test.rb
index 3f8920a16..50fc55d53 100644
--- a/ruby/hyper-model/spec/test_app/app/hyperstack/models/type_test.rb
+++ b/ruby/hyper-model/spec/test_app/app/hyperstack/models/type_test.rb
@@ -13,6 +13,8 @@ def self.build_tables
t.text(:text)
t.time(:time)
t.timestamp(:timestamp)
+ t.json(:json)
+ t.jsonb(:jsonb)
end
end
end
diff --git a/ruby/hyper-model/spec/test_app/config/database.yml b/ruby/hyper-model/spec/test_app/config/database.yml
index 92191c367..ad8c9dd1c 100644
--- a/ruby/hyper-model/spec/test_app/config/database.yml
+++ b/ruby/hyper-model/spec/test_app/config/database.yml
@@ -1,8 +1,30 @@
+# SQLite version 3.x
+# gem install sqlite3
+#
+# Ensure the SQLite 3 gem is defined in your Gemfile
+# gem 'sqlite3'
+#
+# default: &default
+# adapter: mysql2
+# encoding: utf8
+# username: root
+#
+# development:
+# <<: *default
+# database: hyper_mesh_development_db
+#
+# test:
+# <<: *default
+# database: hyper_mesh_test_db
+#
+# production:
+# <<: *default
+# database: hyper_mesh_production_db
default: &default
- adapter: mysql2
- encoding: utf8
- username: root
+ adapter: postgresql
+ pool: 5
+ timeout: 5000
development:
<<: *default
From 11234e8cd727ca7dc01a9a15432a81dedcd048f7 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 27 Feb 2021 17:51:51 -0500
Subject: [PATCH 144/307] trying one more time
---
.travis.yml | 10 +++++-----
1 file changed, 5 insertions(+), 5 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index d27d40cfc..ed6dfb411 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -1,10 +1,10 @@
dist: xenial
-language: bash
-cache:
- bundler: true
- directories:
- - node_modules # NPM packages
+# language: bash
+# cache:
+# bundler: true
+# directories:
+# - node_modules # NPM packages
addons:
apt:
From 679077b40629e40bc4cbfa6a5f65846dec97d77d Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 27 Feb 2021 18:05:03 -0500
Subject: [PATCH 145/307] lets see if this works
---
.travis.yml | 212 ++++++++++++++++++++++++++--------------------------
1 file changed, 106 insertions(+), 106 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index ed6dfb411..c30e2343a 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -44,7 +44,8 @@ _test_gem_pg: &_test_gem_pg
- which google-chrome
- yarn install
script:
- - DRIVER=travis bundle exec rspec spec/batch1/column_types/column_type_spec.rb:121
+ - echo running script $COMPONENT
+ - DRIVER=travis bundle exec rake $TASK
_test_gem: &_test_gem
stage: test
@@ -80,112 +81,111 @@ _test_gem: &_test_gem
- which google-chrome
- yarn install
script:
- - DRIVER=travis bundle exec rspec spec/batch1/column_types/column_type_spec.rb:121
+ - echo running script $COMPONENT
+ - DRIVER=travis bundle exec rake $TASK
jobs:
include:
+ - <<: *_test_gem
+ env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-component RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-router RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-store RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1
- <<: *_test_gem_pg
- env: COMPONENT=hyper-model DB=hyper_mesh_test_db
- # - <<: *_test_gem
- # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part2
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part3
- # - <<: *_test_gem
- # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1
- #
- # - <<: *_test_gem
- # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
- # - <<: *_test_gem
- # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- #
- # - <<: *_test_gem
- # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
- # - <<: *_test_gem
- # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- #
- # - <<: *_deploy_gem
- # env: COMPONENT=hyper-i18n
- # - <<: *_deploy_gem
- # env: COMPONENT=hyper-trace
- # - <<: *_deploy_gem
- # env: COMPONENT=hyper-state
- # - <<: *_deploy_gem
- # env: COMPONENT=hyper-component
- # - <<: *_deploy_gem
- # env: COMPONENT=hyper-model
- # - <<: *_deploy_gem
- # env: COMPONENT=hyper-operation
- # - <<: *_deploy_gem
- # env: COMPONENT=hyper-router
- # - <<: *_deploy_gem
- # env: COMPONENT=hyper-spec
- # - <<: *_deploy_gem
- # env: COMPONENT=hyper-store
- # - <<: *_deploy_gem
- # env: COMPONENT=rails-hyperstack
- # - <<: *_deploy_gem
- # env: COMPONENT=hyperstack-config
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1 DB=hyper_mesh_test_db
+ - <<: *_test_gem_pg
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part2 DB=hyper_mesh_test_db
+ - <<: *_test_gem_pg
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part3 DB=hyper_mesh_test_db
+ - <<: *_test_gem
+ env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1
+
+ - <<: *_test_gem
+ env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
+ - <<: *_test_gem
+ env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+
+ - <<: *_test_gem
+ env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
+ - <<: *_test_gem
+ env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-i18n
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-trace
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-state
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-component
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-model
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-operation
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-router
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-spec
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-store
+ - <<: *_deploy_gem
+ env: COMPONENT=rails-hyperstack
+ - <<: *_deploy_gem
+ env: COMPONENT=hyperstack-config
From 82d563a7c2831ab6c52da4b512739a6e4afc4162 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 28 Feb 2021 15:37:27 -0500
Subject: [PATCH 146/307] adjustments to run postgresql
---
ruby/hyper-model/Rakefile | 2 +-
.../batch2/non_ar_aggregations_tbdspec.rb | 1 -
.../spec/batch5/load_from_json_xspec.rb | 1 -
.../config/initializers/hyperstack.rb | 1 +
.../20210228200459_add_connection_tables.rb | 16 ++++
ruby/hyper-model/spec/test_app/db/schema.rb | 89 +++++++++++++++----
6 files changed, 89 insertions(+), 21 deletions(-)
create mode 100644 ruby/hyper-model/spec/test_app/db/migrate/20210228200459_add_connection_tables.rb
diff --git a/ruby/hyper-model/Rakefile b/ruby/hyper-model/Rakefile
index 1f5cc17e0..eeb360644 100644
--- a/ruby/hyper-model/Rakefile
+++ b/ruby/hyper-model/Rakefile
@@ -32,7 +32,7 @@ end
namespace :spec do
task :prepare do
- sh %(cd spec/test_app; bundle exec rails db:setup)
+ sh %(cd spec/test_app; rm db/schema.rb; RAILS_ENV=test bundle exec rails db:setup; RAILS_ENV=test bundle exec rails db:migrate)
end
(1..7).each do |batch|
RSpec::Core::RakeTask.new(:"batch#{batch}") do |t|
diff --git a/ruby/hyper-model/spec/batch2/non_ar_aggregations_tbdspec.rb b/ruby/hyper-model/spec/batch2/non_ar_aggregations_tbdspec.rb
index 7b56b1474..ed7ba687c 100644
--- a/ruby/hyper-model/spec/batch2/non_ar_aggregations_tbdspec.rb
+++ b/ruby/hyper-model/spec/batch2/non_ar_aggregations_tbdspec.rb
@@ -41,7 +41,6 @@
User.find_by_first_name("Data").save
end
expect(User.find_by_first_name("Data").data.big_string).to eq("hellohellohello")
- binding.pry
end
it "read it" do
diff --git a/ruby/hyper-model/spec/batch5/load_from_json_xspec.rb b/ruby/hyper-model/spec/batch5/load_from_json_xspec.rb
index dfca078ce..4066adb2c 100644
--- a/ruby/hyper-model/spec/batch5/load_from_json_xspec.rb
+++ b/ruby/hyper-model/spec/batch5/load_from_json_xspec.rb
@@ -26,7 +26,6 @@
end
it '*all key' do
- binding.pry
evaluate_ruby do
User.all.count
end
diff --git a/ruby/hyper-model/spec/test_app/config/initializers/hyperstack.rb b/ruby/hyper-model/spec/test_app/config/initializers/hyperstack.rb
index 1d1a370cd..7eca39707 100644
--- a/ruby/hyper-model/spec/test_app/config/initializers/hyperstack.rb
+++ b/ruby/hyper-model/spec/test_app/config/initializers/hyperstack.rb
@@ -2,3 +2,4 @@
Hyperstack.cancel_import 'hyperstack/autoloader'
Hyperstack.cancel_import 'hyperstack/autoloader_starter'
Hyperstack.cancel_import 'config/initializers/inflections.rb'
+def (Hyperstack::Connection).build_tables?; false; end
diff --git a/ruby/hyper-model/spec/test_app/db/migrate/20210228200459_add_connection_tables.rb b/ruby/hyper-model/spec/test_app/db/migrate/20210228200459_add_connection_tables.rb
new file mode 100644
index 000000000..e2faf1096
--- /dev/null
+++ b/ruby/hyper-model/spec/test_app/db/migrate/20210228200459_add_connection_tables.rb
@@ -0,0 +1,16 @@
+class AddConnectionTables < ActiveRecord::Migration[5.2]
+ def change
+ create_table "hyperstack_connections", force: :cascade do |t|
+ t.string "channel"
+ t.string "session"
+ t.datetime "created_at"
+ t.datetime "expires_at"
+ t.datetime "refresh_at"
+ end
+
+ create_table "hyperstack_queued_messages", force: :cascade do |t|
+ t.text "data"
+ t.integer "connection_id"
+ end
+ end
+end
diff --git a/ruby/hyper-model/spec/test_app/db/schema.rb b/ruby/hyper-model/spec/test_app/db/schema.rb
index 03ed1ad18..23819ff59 100644
--- a/ruby/hyper-model/spec/test_app/db/schema.rb
+++ b/ruby/hyper-model/spec/test_app/db/schema.rb
@@ -10,9 +10,12 @@
#
# It's strongly recommended that you check this file into your version control system.
-ActiveRecord::Schema.define(version: 2016_07_31_182106) do
+ActiveRecord::Schema.define(version: 2021_02_28_200459) do
- create_table "addresses", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
+ # These are extensions that must be enabled in order to support this database
+ enable_extension "plpgsql"
+
+ create_table "addresses", force: :cascade do |t|
t.string "street"
t.string "city"
t.string "state"
@@ -21,22 +24,44 @@
t.datetime "updated_at"
end
- create_table "child_models", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
+ create_table "bones", force: :cascade do |t|
+ t.integer "dog_id"
+ end
+
+ create_table "child_models", force: :cascade do |t|
t.string "child_attribute"
- t.integer "test_model_id"
+ t.bigint "test_model_id"
+ t.index ["test_model_id"], name: "index_child_models_on_test_model_id"
end
- create_table "comments", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
+ create_table "comments", force: :cascade do |t|
t.text "comment"
- t.datetime "created_at"
- t.datetime "updated_at"
- t.integer "todo_id"
- t.integer "author_id"
+ t.datetime "created_at", null: false
+ t.datetime "updated_at", null: false
+ t.bigint "todo_id"
+ t.bigint "author_id"
t.integer "user_id"
t.integer "todo_item_id"
+ t.index ["author_id"], name: "index_comments_on_author_id"
+ t.index ["todo_id"], name: "index_comments_on_todo_id"
+ end
+
+ create_table "default_tests", force: :cascade do |t|
+ t.string "string", default: "I'm a string!"
+ t.date "date", default: "2021-02-27"
+ t.datetime "datetime", default: "2021-02-27 22:45:41"
+ t.integer "integer_from_string", default: 99
+ t.integer "integer_from_int", default: 98
+ t.float "float_from_string", default: 0.02
+ t.float "float_from_float", default: 0.01
+ t.boolean "boolean_from_falsy_string", default: false
+ t.boolean "boolean_from_truthy_string", default: true
+ t.boolean "boolean_from_falsy_value", default: false
+ t.json "json", default: {"kind"=>"json"}
+ t.jsonb "jsonb", default: {"kind"=>"jsonb"}
end
- create_table "hyperstack_connections", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
+ create_table "hyperstack_connections", force: :cascade do |t|
t.string "channel"
t.string "session"
t.datetime "created_at"
@@ -44,19 +69,27 @@
t.datetime "refresh_at"
end
- create_table "hyperstack_queued_messages", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
+ create_table "hyperstack_queued_messages", force: :cascade do |t|
t.text "data"
t.integer "connection_id"
end
- create_table "test_models", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
+ create_table "pets", force: :cascade do |t|
+ t.integer "owner_id"
+ end
+
+ create_table "scratching_posts", force: :cascade do |t|
+ t.integer "cat_id"
+ end
+
+ create_table "test_models", force: :cascade do |t|
t.string "test_attribute"
t.boolean "completed"
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
end
- create_table "todo_items", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
+ create_table "todo_items", force: :cascade do |t|
t.string "title"
t.text "description"
t.boolean "complete"
@@ -66,19 +99,38 @@
t.integer "comment_id"
end
- create_table "todos", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
+ create_table "todos", force: :cascade do |t|
t.string "title"
t.text "description"
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
t.boolean "completed", default: false, null: false
- t.integer "created_by_id"
- t.integer "owner_id"
+ t.bigint "created_by_id"
+ t.bigint "owner_id"
+ t.index ["created_by_id"], name: "index_todos_on_created_by_id"
+ t.index ["owner_id"], name: "index_todos_on_owner_id"
+ end
+
+ create_table "type_tests", force: :cascade do |t|
+ t.binary "binary"
+ t.boolean "boolean"
+ t.date "date"
+ t.datetime "datetime"
+ t.decimal "decimal", precision: 5, scale: 2
+ t.float "float"
+ t.integer "integer"
+ t.bigint "bigint"
+ t.string "string"
+ t.text "text"
+ t.time "time"
+ t.datetime "timestamp"
+ t.json "json"
+ t.jsonb "jsonb"
end
- create_table "users", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8", force: :cascade do |t|
+ create_table "users", force: :cascade do |t|
t.string "role"
- t.integer "manager_id"
+ t.bigint "manager_id"
t.string "first_name"
t.string "last_name"
t.string "email"
@@ -96,6 +148,7 @@
t.string "data_string"
t.integer "data_times"
t.integer "test_enum"
+ t.index ["manager_id"], name: "index_users_on_manager_id"
end
end
From 376853b5a82bbe9364e87581dbe70ea4bc77b10e Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 28 Feb 2021 16:02:21 -0500
Subject: [PATCH 147/307] ignore certain errors with PG
---
.../transport/connection_adapter/active_record.rb | 2 ++
1 file changed, 2 insertions(+)
diff --git a/ruby/hyper-operation/lib/hyper-operation/transport/connection_adapter/active_record.rb b/ruby/hyper-operation/lib/hyper-operation/transport/connection_adapter/active_record.rb
index fa7938199..f503b0c24 100644
--- a/ruby/hyper-operation/lib/hyper-operation/transport/connection_adapter/active_record.rb
+++ b/ruby/hyper-operation/lib/hyper-operation/transport/connection_adapter/active_record.rb
@@ -38,6 +38,8 @@ def active
end
Connection.all.pluck(:channel).uniq
+ rescue ::ActiveRecord::StatementInvalid
+ []
end
def open(channel, session = nil, root_path = nil)
From 18d194b6aaac0945a2492e066f648e05d1ba609c Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 28 Feb 2021 16:57:03 -0500
Subject: [PATCH 148/307] put the spec:prepare back in
---
.travis.yml | 4 +++-
1 file changed, 3 insertions(+), 1 deletion(-)
diff --git a/.travis.yml b/.travis.yml
index c30e2343a..ad3ed7b48 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -37,9 +37,10 @@ _test_gem_pg: &_test_gem_pg
- echo 'install completed'
before_script:
- - psql -c "create database ${DB};" -U postgres
+ - echo before_script $COMPONENT
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
+ - bundle exec rake spec:prepare
- google-chrome --version
- which google-chrome
- yarn install
@@ -77,6 +78,7 @@ _test_gem: &_test_gem
- echo before_script $COMPONENT
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
+ - bundle exec rake spec:prepare
- google-chrome --version
- which google-chrome
- yarn install
From 4473e8d1c12dfc9870a95a547215fe773602d293 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 28 Feb 2021 17:11:13 -0500
Subject: [PATCH 149/307] more fixups
---
.../test_app/db/migrate/20160731182106_create_test_models.rb | 1 -
1 file changed, 1 deletion(-)
diff --git a/ruby/hyper-model/spec/test_app/db/migrate/20160731182106_create_test_models.rb b/ruby/hyper-model/spec/test_app/db/migrate/20160731182106_create_test_models.rb
index 86dec7925..f4d8c58a3 100644
--- a/ruby/hyper-model/spec/test_app/db/migrate/20160731182106_create_test_models.rb
+++ b/ruby/hyper-model/spec/test_app/db/migrate/20160731182106_create_test_models.rb
@@ -49,7 +49,6 @@ def change
t.references :author
t.integer "user_id"
t.integer "todo_item_id"
- t.datetime "created_at"
t.datetime "updated_at"
end
From befc563e010a1957eb46f6df52573ba7c1323fa2 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 28 Feb 2021 17:21:46 -0500
Subject: [PATCH 150/307] one more time fixing these migrations
---
.../test_app/db/migrate/20160731182106_create_test_models.rb | 1 -
1 file changed, 1 deletion(-)
diff --git a/ruby/hyper-model/spec/test_app/db/migrate/20160731182106_create_test_models.rb b/ruby/hyper-model/spec/test_app/db/migrate/20160731182106_create_test_models.rb
index f4d8c58a3..03022f4ba 100644
--- a/ruby/hyper-model/spec/test_app/db/migrate/20160731182106_create_test_models.rb
+++ b/ruby/hyper-model/spec/test_app/db/migrate/20160731182106_create_test_models.rb
@@ -49,7 +49,6 @@ def change
t.references :author
t.integer "user_id"
t.integer "todo_item_id"
- t.datetime "updated_at"
end
create_table "addresses" do |t|
From 2d348d8fb48fbc6b21db3d3750c35288122b5780 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 28 Feb 2021 18:23:03 -0500
Subject: [PATCH 151/307] attempt to get operation spec working
---
.travis.yml | 204 +++++++++---------
.../spec/batch7/poly_assoc_spec.rb | 13 +-
2 files changed, 106 insertions(+), 111 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index ad3ed7b48..ab1acaefc 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -63,6 +63,8 @@ _test_gem: &_test_gem
- yarn
- redis-server
mariadb: '10.3'
+ services:
+ - redis-server
before_install:
- echo installing $COMPONENT
# yarn is in /usr/local/bin/yarn version 1.3.2 and is not a package
@@ -88,106 +90,106 @@ _test_gem: &_test_gem
jobs:
include:
- - <<: *_test_gem
- env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1
- - <<: *_test_gem
- env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1
- - <<: *_test_gem
- env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
- - <<: *_test_gem
- env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1
- - <<: *_test_gem
- env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
- - <<: *_test_gem
- env: COMPONENT=hyper-component RUBY_VERSION=2.5.1
- - <<: *_test_gem
- env: COMPONENT=hyper-router RUBY_VERSION=2.5.1
- - <<: *_test_gem
- env: COMPONENT=hyper-store RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1
- <<: *_test_gem
env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1
- - <<: *_test_gem_pg
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1 DB=hyper_mesh_test_db
- - <<: *_test_gem_pg
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part2 DB=hyper_mesh_test_db
- - <<: *_test_gem_pg
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part3 DB=hyper_mesh_test_db
- - <<: *_test_gem
- env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1
-
- - <<: *_test_gem
- env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
- - <<: *_test_gem
- env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
-
- - <<: *_test_gem
- env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
- - <<: *_test_gem
- env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
-
- - <<: *_deploy_gem
- env: COMPONENT=hyper-i18n
- - <<: *_deploy_gem
- env: COMPONENT=hyper-trace
- - <<: *_deploy_gem
- env: COMPONENT=hyper-state
- - <<: *_deploy_gem
- env: COMPONENT=hyper-component
- - <<: *_deploy_gem
- env: COMPONENT=hyper-model
- - <<: *_deploy_gem
- env: COMPONENT=hyper-operation
- - <<: *_deploy_gem
- env: COMPONENT=hyper-router
- - <<: *_deploy_gem
- env: COMPONENT=hyper-spec
- - <<: *_deploy_gem
- env: COMPONENT=hyper-store
- - <<: *_deploy_gem
- env: COMPONENT=rails-hyperstack
- - <<: *_deploy_gem
- env: COMPONENT=hyperstack-config
+ # - <<: *_test_gem_pg
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1 DB=hyper_mesh_test_db
+ # - <<: *_test_gem_pg
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part2 DB=hyper_mesh_test_db
+ # - <<: *_test_gem_pg
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part3 DB=hyper_mesh_test_db
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1
+ #
+ # - <<: *_test_gem
+ # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ #
+ # - <<: *_test_gem
+ # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
+ # - <<: *_test_gem
+ # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ #
+ # - <<: *_deploy_gem
+ # env: COMPONENT=hyper-i18n
+ # - <<: *_deploy_gem
+ # env: COMPONENT=hyper-trace
+ # - <<: *_deploy_gem
+ # env: COMPONENT=hyper-state
+ # - <<: *_deploy_gem
+ # env: COMPONENT=hyper-component
+ # - <<: *_deploy_gem
+ # env: COMPONENT=hyper-model
+ # - <<: *_deploy_gem
+ # env: COMPONENT=hyper-operation
+ # - <<: *_deploy_gem
+ # env: COMPONENT=hyper-router
+ # - <<: *_deploy_gem
+ # env: COMPONENT=hyper-spec
+ # - <<: *_deploy_gem
+ # env: COMPONENT=hyper-store
+ # - <<: *_deploy_gem
+ # env: COMPONENT=rails-hyperstack
+ # - <<: *_deploy_gem
+ # env: COMPONENT=hyperstack-config
diff --git a/ruby/hyper-model/spec/batch7/poly_assoc_spec.rb b/ruby/hyper-model/spec/batch7/poly_assoc_spec.rb
index 0e416ac77..92fa07491 100644
--- a/ruby/hyper-model/spec/batch7/poly_assoc_spec.rb
+++ b/ruby/hyper-model/spec/batch7/poly_assoc_spec.rb
@@ -240,32 +240,25 @@ def compare_to_server(model, expression, expected_result, load=true)
end
it 'changing belongs to relationship on client' do
- # not working yet
compare_to_server @imageable1, 'pictures.collect(&:name)', ['picture11', 'picture12']
compare_to_server @imageable2, 'pictures.collect(&:name)', ['picture21', 'picture22']
- evaluate_promise do
+ on_client do
p = Picture.find(1)
p.imageable = Product.find(1)
p.save
end
- # wait_for_ajax # so pusher can initialize
compare_to_server @imageable1, 'pictures.collect(&:name)', ['picture12'], false
- compare_to_server @imageable2, 'pictures.collect(&:name)', ['picture11', 'picture21', 'picture22'], false
+ compare_to_server @imageable2, 'pictures.collect(&:name)', ['picture21', 'picture22', 'picture11'], false
end
it 'changing belongs to relationship on server' do
- # compare_to_server @picture11, 'imageable.name', 'imageable1' # here for debug assist
- # compare_to_server @picture11, 'imageable.ss', '123' # here for debug assist
-
- # just debugging here... when id doesn't change we don't realize that data is changing
compare_to_server @imageable1, 'pictures.collect(&:name)', ['picture11', 'picture12']
compare_to_server @imageable2, 'pictures.collect(&:name)', ['picture21', 'picture22']
p = Picture.find_by_name('picture11')
p.imageable = @imageable2
p.save
- # wait_for_ajax # so pusher can initialize
compare_to_server @imageable1, 'pictures.collect(&:name)', ['picture12']
- compare_to_server @imageable2, 'pictures.collect(&:name)', ['picture11', 'picture21', 'picture22']
+ compare_to_server @imageable2, 'pictures.collect(&:name)', ['picture21', 'picture22', 'picture11']
end
From 179a9a15fa51881e96dce08636e1db862c3f1034 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 28 Feb 2021 18:38:24 -0500
Subject: [PATCH 152/307] hopefully final change to .travis.yml
---
.travis.yml | 202 ++++++++++++++++++++++++++--------------------------
1 file changed, 101 insertions(+), 101 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index ab1acaefc..5305d767c 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -90,106 +90,106 @@ _test_gem: &_test_gem
jobs:
include:
- # - <<: *_test_gem
- # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-component RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-router RUBY_VERSION=2.5.1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-store RUBY_VERSION=2.5.1
- <<: *_test_gem
env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1
- # - <<: *_test_gem_pg
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1 DB=hyper_mesh_test_db
- # - <<: *_test_gem_pg
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part2 DB=hyper_mesh_test_db
- # - <<: *_test_gem_pg
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part3 DB=hyper_mesh_test_db
- # - <<: *_test_gem
- # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1
- #
- # - <<: *_test_gem
- # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
- # - <<: *_test_gem
- # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- #
- # - <<: *_test_gem
- # env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
- # - <<: *_test_gem
- # env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
- # - <<: *_test_gem
- # env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- #
- # - <<: *_deploy_gem
- # env: COMPONENT=hyper-i18n
- # - <<: *_deploy_gem
- # env: COMPONENT=hyper-trace
- # - <<: *_deploy_gem
- # env: COMPONENT=hyper-state
- # - <<: *_deploy_gem
- # env: COMPONENT=hyper-component
- # - <<: *_deploy_gem
- # env: COMPONENT=hyper-model
- # - <<: *_deploy_gem
- # env: COMPONENT=hyper-operation
- # - <<: *_deploy_gem
- # env: COMPONENT=hyper-router
- # - <<: *_deploy_gem
- # env: COMPONENT=hyper-spec
- # - <<: *_deploy_gem
- # env: COMPONENT=hyper-store
- # - <<: *_deploy_gem
- # env: COMPONENT=rails-hyperstack
- # - <<: *_deploy_gem
- # env: COMPONENT=hyperstack-config
+ - <<: *_test_gem_pg
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part1 DB=hyper_mesh_test_db
+ - <<: *_test_gem_pg
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part2 DB=hyper_mesh_test_db
+ - <<: *_test_gem_pg
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 TASK=part3 DB=hyper_mesh_test_db
+ - <<: *_test_gem
+ env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1
+
+ - <<: *_test_gem
+ env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
+ - <<: *_test_gem
+ env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
+
+ - <<: *_test_gem
+ env: COMPONENT=rails-hyperstack RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-spec RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-state RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-component RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-router RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
+ - <<: *_test_gem
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
+ - <<: *_test_gem
+ env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
+
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-i18n
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-trace
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-state
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-component
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-model
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-operation
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-router
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-spec
+ - <<: *_deploy_gem
+ env: COMPONENT=hyper-store
+ - <<: *_deploy_gem
+ env: COMPONENT=rails-hyperstack
+ - <<: *_deploy_gem
+ env: COMPONENT=hyperstack-config
From 2bc94bef2b358b857d8e0fd7a6d586d2356138ca Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 28 Feb 2021 19:40:31 -0500
Subject: [PATCH 153/307] run all hyper-model specs with pg, and fied
regression in spec
---
.travis.yml | 24 +++++++++----------
.../spec/batch7/poly_assoc_spec.rb | 2 +-
2 files changed, 13 insertions(+), 13 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 5305d767c..3a37e5803 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -135,12 +135,12 @@ jobs:
env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- <<: *_test_gem
env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3
+ - <<: *_test_gem_pg
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part1 DB=hyper_mesh_test_db
+ - <<: *_test_gem_pg
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part2 DB=hyper_mesh_test_db
+ - <<: *_test_gem_pg
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11' TASK=part3 DB=hyper_mesh_test_db
- <<: *_test_gem
env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 OPAL_VERSION='~>0.11'
@@ -162,12 +162,12 @@ jobs:
env: COMPONENT=hyper-store RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- <<: *_test_gem
env: COMPONENT=hyper-operation RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2
- - <<: *_test_gem
- env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3
+ - <<: *_test_gem_pg
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part1 DB=hyper_mesh_test_db
+ - <<: *_test_gem_pg
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part2 DB=hyper_mesh_test_db
+ - <<: *_test_gem_pg
+ env: COMPONENT=hyper-model RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0' TASK=part3 DB=hyper_mesh_test_db
- <<: *_test_gem
env: COMPONENT=hyper-i18n RUBY_VERSION=2.5.1 RAILS_VERSION='~>5.0'
diff --git a/ruby/hyper-model/spec/batch7/poly_assoc_spec.rb b/ruby/hyper-model/spec/batch7/poly_assoc_spec.rb
index 92fa07491..22082cfc8 100644
--- a/ruby/hyper-model/spec/batch7/poly_assoc_spec.rb
+++ b/ruby/hyper-model/spec/batch7/poly_assoc_spec.rb
@@ -242,7 +242,7 @@ def compare_to_server(model, expression, expected_result, load=true)
it 'changing belongs to relationship on client' do
compare_to_server @imageable1, 'pictures.collect(&:name)', ['picture11', 'picture12']
compare_to_server @imageable2, 'pictures.collect(&:name)', ['picture21', 'picture22']
- on_client do
+ evaluate_ruby do
p = Picture.find(1)
p.imageable = Product.find(1)
p.save
From a3eb1d6a43012eee82154aaca7ff1f7f9198e377 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 28 Feb 2021 20:46:18 -0500
Subject: [PATCH 154/307] closes #365
---
.travis.yml | 13 ++++++++
.../active_record/instance_methods.rb | 8 +++++
.../spec/batch3/instance_methods_spec.rb | 33 +++++++++++++++++++
3 files changed, 54 insertions(+)
create mode 100644 ruby/hyper-model/spec/batch3/instance_methods_spec.rb
diff --git a/.travis.yml b/.travis.yml
index 3a37e5803..6c0366e60 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -88,6 +88,19 @@ _test_gem: &_test_gem
- echo running script $COMPONENT
- DRIVER=travis bundle exec rake $TASK
+_deploy_gem: &_deploy_gem
+ stage: release gems
+ before_script:
+ - cd ruby/$COMPONENT
+ script:
+ - echo deploying $COMPONENT
+ deploy:
+ - provider: rubygems
+ api_key:
+ secure: "ORJMyp20YFCkvujBfxoDPwEZy8R8YJaKwRhHZUDTPZPiS84mJA7Mqd0JjvRlF0mlH/WzspruM7hZV0CuMU8F/0raRhSUU9RBh5veZ/4ij9kboCYnfuqBVt6qPRtaf8DgKe7CWGioUrTISJCVKLnygY6gZd2aFXCEbqZMrkUvC7y43ymOoFoeyCLsXC0j5uJxdHgNfbaIUetIl2DQJUbC2Rgq1Iaxvi72Ae97TR2xRCu+ko8DopRpQCug6U81IhzXftizGfKwzecqVFjuMn3XEf+UDlU6xbvwWWkcwjYNAbP2Kk+mWwUMx36s+1Pyx8MOveYLTwnQJ6gHocZHzh7WJOD548JNU3F5oXIlUB4EzD20bCSIeRKOdxTuKrNk7W3a5qGERuQi4rkIlkKaFIBP55IkliUxvYxqr0WujsjO2reRcNhNcLVGCOaX6LZbWFR5bf0WiEOL4vOxPNw66sI2JVHoMmQeAYtL2ghxikdSPXKRc+inT3QiRBsh+ns8YrAP7sV4lX6r/qyWUtPh6kY8xIeTP4VzMviyf20m5u++omao/FSEtVnU3cro5KjrZLg3ILg4NpNG+xoRqPS/Hmxry5ZPrggqNrxoqWuO7pLd/NnV/AnLiT8rd2P0PTriP9uRIM8+fFfyOeGwbplOLrbWUPnCdQVWp6dYOrNgE2yDJ/I="
+ on:
+ tags: true
+
jobs:
include:
- <<: *_test_gem
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/instance_methods.rb b/ruby/hyper-model/lib/reactive_record/active_record/instance_methods.rb
index 453ca8124..0cddc3367 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/instance_methods.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/instance_methods.rb
@@ -162,6 +162,14 @@ def itself
# end
end
+ def increment!(attr)
+ load(attr).then { |current_value| update(attr => current_value + 1) }
+ end
+
+ def decrement!(attr)
+ load(attr).then { |current_value| update(attr => current_value - 1) }
+ end
+
def load(*attributes, &block)
first_time = true
ReactiveRecord.load do
diff --git a/ruby/hyper-model/spec/batch3/instance_methods_spec.rb b/ruby/hyper-model/spec/batch3/instance_methods_spec.rb
new file mode 100644
index 000000000..72f1de57d
--- /dev/null
+++ b/ruby/hyper-model/spec/batch3/instance_methods_spec.rb
@@ -0,0 +1,33 @@
+require 'spec_helper'
+require 'test_components'
+
+describe "Misc Instance Methods", :no_reset, js: true do
+
+ before(:each) do
+ # spec_helper resets the policy system after each test so we have to setup
+ # before each test
+ stub_const 'TestApplication', Class.new
+ stub_const 'TestApplicationPolicy', Class.new
+ TestApplicationPolicy.class_eval do
+ always_allow_connection
+ regulate_all_broadcasts { |policy| policy.send_all }
+ allow_change(to: :all) { true }
+ end
+ end
+
+ it "increment!" do
+ user = FactoryBot.create(:user, first_name: 'zero', data_times: 0)
+ user_id = user.id
+ evaluate_ruby { User.find(user_id).increment!(:data_times) }
+ expect(user.reload.data_times).to eq(1)
+ expect { User.find(user_id).data_times }.to_on_client eq(1)
+ end
+
+ it "decrement!" do
+ user = FactoryBot.create(:user, first_name: 'one', data_times: 1)
+ user_id = user.id
+ evaluate_ruby { User.find(user_id).decrement!(:data_times) }
+ expect(user.reload.data_times).to eq(0)
+ expect { User.find(user_id).data_times }.to_on_client eq(0)
+ end
+end
From 3e86d39a98137e90cfa34b1cef5dc3c11bfb23fd Mon Sep 17 00:00:00 2001
From: catmando
Date: Mon, 1 Mar 2021 11:06:01 -0500
Subject: [PATCH 155/307] hyper-spec no_reset was not clearing after leaving
spec block - fixed
---
ruby/hyper-spec/lib/hyper-spec.rb | 11 +++++++----
1 file changed, 7 insertions(+), 4 deletions(-)
diff --git a/ruby/hyper-spec/lib/hyper-spec.rb b/ruby/hyper-spec/lib/hyper-spec.rb
index c64643980..5b802ce2e 100644
--- a/ruby/hyper-spec/lib/hyper-spec.rb
+++ b/ruby/hyper-spec/lib/hyper-spec.rb
@@ -53,8 +53,8 @@ class << self
end
end
- def self.reset_between_examples=(value)
- RSpec.configuration.reset_between_examples = value
+ def self.reset_between_examples
+ @reset_between_examples ||= []
end
def self.reset_between_examples?
@@ -106,13 +106,16 @@ def reset_sessions!
RSpec.configure do |config|
config.add_setting :reset_between_examples, default: true
config.before(:all, no_reset: true) do
- HyperSpec.reset_between_examples = false
+ HyperSpec.reset_between_examples << RSpec.configuration.reset_between_examples
+ RSpec.configuration.reset_between_examples = false
end
config.before(:all, no_reset: false) do
- HyperSpec.reset_between_examples = true
+ HyperSpec.reset_between_examples << RSpec.configuration.reset_between_examples
+ RSpec.configuration.reset_between_examples = true
end
config.after(:all) do
HyperSpec.reset_sessions! unless HyperSpec.reset_between_examples?
+ RSpec.configuration.reset_between_examples = HyperSpec.reset_between_examples.pop
end
config.before(:each) do |example|
insure_page_loaded(true) if example.metadata[:js] && !HyperSpec.reset_between_examples?
From 36516765f840eade6a8862682dd5a12774b259cd Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 5 Mar 2021 15:08:24 -0500
Subject: [PATCH 156/307] closes #364 and gets hypertrace working with opal 1.x
---
.travis.yml | 15 +-
.../refs_element_method_spec.rb | 1 -
ruby/hyper-model/Gemfile | 8 +-
ruby/hyper-model/hyper-model.gemspec | 1 +
ruby/hyper-model/lib/active_record_base.rb | 51 +++++--
.../active_record/associations.rb | 6 +-
.../lib/reactive_record/active_record/base.rb | 2 +-
.../active_record/class_methods.rb | 8 ++
.../active_record/instance_methods.rb | 4 +-
.../active_record/reactive_record/base.rb | 1 +
.../reactive_record/collection.rb | 27 +++-
.../reactive_record/dummy_value.rb | 2 +-
.../reactive_record/isomorphic_base.rb | 26 ++--
.../reactive_record/operations.rb | 2 +-
.../active_record/reactive_record/setters.rb | 5 +-
.../lib/reactive_record/broadcast.rb | 9 +-
.../lib/reactive_record/server_data_cache.rb | 2 +-
.../batch3/has_and_belongs_to_many_spec.rb | 112 +++++++++++++++
ruby/hyper-model/spec/spec_helper.rb | 2 +-
.../spec/test_app/config/application.rb | 2 +-
ruby/hyper-model/spec/test_components.rb | 2 +-
.../transport/client_drivers.rb | 2 +-
.../lib/hyperstack/internal/state/variable.rb | 4 +-
.../lib/hyper_trace/hyper_trace.rb | 130 +++++++++++-------
24 files changed, 318 insertions(+), 106 deletions(-)
create mode 100644 ruby/hyper-model/spec/batch3/has_and_belongs_to_many_spec.rb
diff --git a/.travis.yml b/.travis.yml
index 6c0366e60..ba19b4098 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -1,10 +1,6 @@
dist: xenial
-# language: bash
-# cache:
-# bundler: true
-# directories:
-# - node_modules # NPM packages
+language: bash
addons:
apt:
@@ -22,6 +18,11 @@ addons:
postgresql: '11'
_test_gem_pg: &_test_gem_pg
+ stage: test
+ cache:
+ bundler: true
+ directories:
+ - node_modules # NPM packages
before_install:
- echo 'installing postgresql'
- sudo sed -i 's/port = 5433/port = 5432/' /etc/postgresql/11/main/postgresql.conf
@@ -50,6 +51,10 @@ _test_gem_pg: &_test_gem_pg
_test_gem: &_test_gem
stage: test
+ cache:
+ bundler: true
+ directories:
+ - node_modules # NPM packages
addons:
apt:
sources:
diff --git a/ruby/hyper-component/spec/client_features/refs_element_method_spec.rb b/ruby/hyper-component/spec/client_features/refs_element_method_spec.rb
index ac0e9530e..5f2978d3c 100644
--- a/ruby/hyper-component/spec/client_features/refs_element_method_spec.rb
+++ b/ruby/hyper-component/spec/client_features/refs_element_method_spec.rb
@@ -76,7 +76,6 @@ class AnotherComponent < HyperComponent
render(DIV) { "another component named #{@Others[:foo]}"}
end
class TestComponent < HyperComponent
- after_mount { debugger unless @ref_1.ref == @ref_2.ref; nil }
render do
@ref_1 = AnotherComponent().as_node
@ref_2 = @ref_1.render(foo: :bar)
diff --git a/ruby/hyper-model/Gemfile b/ruby/hyper-model/Gemfile
index a5a0cd35b..5eb536166 100644
--- a/ruby/hyper-model/Gemfile
+++ b/ruby/hyper-model/Gemfile
@@ -1,11 +1,11 @@
source 'https://rubygems.org'
-#gem "opal-jquery", git: "https://github.com/opal/opal-jquery.git", branch: "master"
-# hyper-model is still using an ancient inlined version of hyper-spec
-#gem 'hyper-spec', path: '../hyper-spec'
gem 'hyper-state', path: '../hyper-state'
gem 'hyper-component', path: '../hyper-component'
gem 'hyper-operation', path: '../hyper-operation'
gem 'hyper-spec', path: '../hyper-spec'
+gem 'hyper-trace', path: '../hyper-trace'
gem 'hyperstack-config', path: '../hyperstack-config'
-
+unless ENV['OPAL_VERSION']&.match("0.11")
+ gem 'opal-browser', git: 'https://github.com/opal/opal-browser'
+end
gemspec
diff --git a/ruby/hyper-model/hyper-model.gemspec b/ruby/hyper-model/hyper-model.gemspec
index 20e35b6b5..4c53ce7b5 100644
--- a/ruby/hyper-model/hyper-model.gemspec
+++ b/ruby/hyper-model/hyper-model.gemspec
@@ -33,6 +33,7 @@ Gem::Specification.new do |spec|
spec.add_development_dependency 'database_cleaner'
spec.add_development_dependency 'factory_bot_rails'
spec.add_development_dependency 'hyper-spec', HyperModel::VERSION
+ spec.add_development_dependency 'hyper-trace', HyperModel::VERSION
spec.add_development_dependency 'mini_racer'
spec.add_development_dependency 'pg'
spec.add_development_dependency 'opal-rails', '>= 0.9.4', '< 2.0'
diff --git a/ruby/hyper-model/lib/active_record_base.rb b/ruby/hyper-model/lib/active_record_base.rb
index d98716c99..373d842cd 100644
--- a/ruby/hyper-model/lib/active_record_base.rb
+++ b/ruby/hyper-model/lib/active_record_base.rb
@@ -5,17 +5,46 @@ module ActiveRecord
# processes these arguments, and the will always leave the true server side scoping
# proc in the `:server` opts. This method is common to client and server.
class Base
- def self._synchromesh_scope_args_check(args)
- opts = if args.count == 2 && args[1].is_a?(Hash)
- args[1].merge(server: args[0])
- elsif args[0].is_a? Hash
- args[0]
- else
- { server: args[0] }
- end
- return opts if opts && opts[:server].respond_to?(:call)
- raise 'must provide either a proc as the first arg or by the '\
- '`:server` option to scope and default_scope methods'
+ class << self
+ def _synchromesh_scope_args_check(args)
+ opts = if args.count == 2 && args[1].is_a?(Hash)
+ args[1].merge(server: args[0])
+ elsif args[0].is_a? Hash
+ args[0]
+ else
+ { server: args[0] }
+ end
+ return opts if opts && opts[:server].respond_to?(:call)
+ raise 'must provide either a proc as the first arg or by the '\
+ '`:server` option to scope and default_scope methods'
+ end
+
+ alias pre_hyperstack_has_and_belongs_to_many has_and_belongs_to_many unless RUBY_ENGINE == 'opal'
+
+ def has_and_belongs_to_many(other, opts = {}, &block)
+ join_table_name = [other.to_s, table_name].sort.join('_')
+ join_model_name = "HyperstackInternalHabtm#{join_table_name.singularize.camelize}"
+ join_model =
+ if Object.const_defined? join_model_name
+ Object.const_get(join_model_name)
+ else
+ Object.const_set(join_model_name, Class.new(ActiveRecord::Base))
+ end
+
+ join_model.class_eval { belongs_to other.to_s.singularize.to_sym }
+
+ has_many join_model_name.underscore.pluralize.to_sym
+
+ if RUBY_ENGINE == 'opal'
+ Object.const_set("HABTM_#{other.to_s.camelize}", join_model)
+ join_model.inheritance_column = nil
+ has_many other, through: join_model_name.underscore.pluralize.to_sym
+ else
+ join_model.table_name = join_table_name
+ join_model.belongs_to other
+ pre_hyperstack_has_and_belongs_to_many(other, opts, &block)
+ end
+ end
end
end
if RUBY_ENGINE != 'opal'
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/associations.rb b/ruby/hyper-model/lib/reactive_record/active_record/associations.rb
index 35a32a722..1ec9a664f 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/associations.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/associations.rb
@@ -32,7 +32,7 @@ def self.reflection_finder(&block)
module Associations
class AssociationReflection
-
+ attr_reader :klass_name
attr_reader :association_foreign_key
attr_reader :attribute
attr_reader :macro
@@ -79,6 +79,10 @@ def singular?
@macro != :has_many
end
+ def habtm?
+ through_association&.klass_name =~ /^HyperstackInternalHabtm/
+ end
+
def through_association
return unless @options[:through]
@through_association ||= @owner_class.reflect_on_all_associations.detect do |association|
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/base.rb b/ruby/hyper-model/lib/reactive_record/active_record/base.rb
index ae09951ff..b6b5e5eec 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/base.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/base.rb
@@ -16,7 +16,7 @@ class Base
)
def self.__hyperstack_internal_scoped_find_by(attrs)
- collection = all.apply_scope(:___hyperstack_internal_scoped_find_by, attrs)
+ collection = all.apply_scope(:___hyperstack_internal_scoped_find_by, attrs).observed
if !collection.collection
collection._find_by_initializer(self, attrs)
else
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/class_methods.rb b/ruby/hyper-model/lib/reactive_record/active_record/class_methods.rb
index dd467d728..4e7a75b79 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/class_methods.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/class_methods.rb
@@ -317,6 +317,14 @@ def abstract_class=(val)
end
end
+ def table_name
+ @table_name || name.downcase.pluralize
+ end
+
+ def table_name=(name)
+ @table_name = name
+ end
+
def composed_of(name, opts = {})
reflection = Aggregations::AggregationReflection.new(base_class, :composed_of, name, opts)
if reflection.klass < ActiveRecord::Base
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/instance_methods.rb b/ruby/hyper-model/lib/reactive_record/active_record/instance_methods.rb
index 0cddc3367..d2c03a3ab 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/instance_methods.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/instance_methods.rb
@@ -126,8 +126,8 @@ def revert
@backing_record.revert
end
- def changed?
- @backing_record.changed?
+ def changed?(attr = nil)
+ @backing_record.changed?(*attr)
end
def dup
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/base.rb b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/base.rb
index 5645b687d..b231103dc 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/base.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/base.rb
@@ -38,6 +38,7 @@ class Base
attr_accessor :aggregate_owner
attr_accessor :aggregate_attribute
attr_accessor :destroyed
+ attr_accessor :being_destroyed
attr_accessor :updated_during
attr_accessor :synced_attributes
attr_accessor :virgin
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/collection.rb b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/collection.rb
index 2188a4286..27f30b903 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/collection.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/collection.rb
@@ -141,6 +141,7 @@ class TestModel < ApplicationRecord
=end
+
def sync_scopes(broadcast)
# record_with_current_values will return nil if data between
# the broadcast record and the value on the client is out of sync
@@ -336,26 +337,25 @@ def reload_from_db(force = nil)
end
def observed
- return if @observing || ReactiveRecord::Base.data_loading?
+ return self if @observing || ReactiveRecord::Base.data_loading?
begin
@observing = true
link_to_parent
reload_from_db(true) if @out_of_date
Hyperstack::Internal::State::Variable.get(self, :collection)
+ self
ensure
@observing = false
end
end
- def set_count_state(val)
+ def count_state=(val)
unless ReactiveRecord::WhileLoading.observed?
Hyperstack::Internal::State::Variable.set(self, :collection, collection, true)
end
@count = val
end
-
-
def _count_internal(load_from_client)
# when count is called on a leaf, count_internal is called for each
# ancestor. Only the outermost count has load_from_client == true
@@ -557,7 +557,7 @@ def internal_replace(new_array)
notify_of_change new_array
end
- def delete(item)
+ def destroy_non_habtm(item)
Hyperstack::Internal::State::Mapper.bulk_update do
unsaved_children.delete(item)
if @owner && @association
@@ -573,6 +573,23 @@ def delete(item)
end
end
+ def destroy(item)
+ return destroy_non_habtm(item) unless @association&.habtm?
+
+ ta = @association.through_association
+ item_foreign_key = @association.source_belongs_to_association.association_foreign_key
+ join_record = ta.klass.find_by(
+ ta.association_foreign_key => @owner.id,
+ item_foreign_key => item.id
+ )
+ return destroy_non_habtm(item) if join_record.nil? ||
+ join_record.backing_record.being_destroyed
+
+ join_record&.destroy
+ end
+
+ alias delete destroy
+
def delete_internal(item)
if collection
all.delete(item)
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/dummy_value.rb b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/dummy_value.rb
index 6b2b24e7c..cce04f31f 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/dummy_value.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/dummy_value.rb
@@ -230,7 +230,7 @@ def acts_as_string?
def respond_to?(method)
return true if method == :acts_as_string?
return true if %i[inspect to_date to_f to_i to_numeric to_number to_s to_time].include? method
- return @object.respond_to? if @object
+ return @object.respond_to?(method) if @object
false
end
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/isomorphic_base.rb b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/isomorphic_base.rb
index c841192a9..e7cbe756f 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/isomorphic_base.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/isomorphic_base.rb
@@ -457,7 +457,7 @@ def self.save_records(models, associations, acting_user, validate, save)
parent.send("#{association[:attribute]}=", aggregate)
#puts "updated is frozen? #{aggregate.frozen?}, parent attributes = #{parent.send(association[:attribute]).attributes}"
elsif parent.class.reflect_on_association(association[:attribute].to_sym).nil?
- raise "Missing association :#{association[:attribute]} for #{parent.class.name}. Was association defined on opal side only?"
+ raise "Missing association :#{association[:attribute]} for #{parent.class.name}. Was association defined on opal side only?"
elsif parent.class.reflect_on_association(association[:attribute].to_sym).collection?
#puts ">>>>>>>>>> #{parent.class.name}.send('#{association[:attribute]}') << #{reactive_records[association[:child_id]]})"
dont_save_list.delete(parent)
@@ -549,13 +549,11 @@ def self.save_records(models, associations, acting_user, validate, save)
if RUBY_ENGINE == 'opal'
def destroy(&block)
+ return if @destroyed || @being_destroyed
- return if @destroyed
-
- #destroy_associations
+ # destroy_associations
promise = Promise.new
-
if !data_loading? && (id || vector)
Operations::Destroy.run(model: ar_instance.model_name.to_s, id: id, vector: vector)
.then do |response|
@@ -567,7 +565,7 @@ def destroy(&block)
destroy_associations
# sync_unscoped_collection! # ? should we do this here was NOT being done before hypermesh integration
yield true, nil if block
- promise.resolve({success: true})
+ promise.resolve(success: true)
end
# DO NOT CLEAR ATTRIBUTES. Records that are not found, are destroyed, and if they are searched for again, we want to make
@@ -587,18 +585,16 @@ def destroy(&block)
def self.destroy_record(model, id, vector, acting_user)
model = Object.const_get(model)
record = if id
- model.find(id)
- else
- ServerDataCache.new(acting_user, {})[*vector]
- end
-
+ model.find(id)
+ else
+ ServerDataCache.new(acting_user, {})[*vector].value
+ end
record.check_permission_with_acting_user(acting_user, :destroy_permitted?).destroy
- {success: true, attributes: {}}
-
+ { success: true, attributes: {} }
rescue Exception => e
- #ReactiveRecord::Pry.rescued(e)
- {success: false, record: record, message: e}
+ # ReactiveRecord::Pry.rescued(e)
+ { success: false, record: record, message: e }
end
end
end
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/operations.rb b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/operations.rb
index a141bf7b3..3b1f73c87 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/operations.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/operations.rb
@@ -93,7 +93,7 @@ class Save < Base
class Destroy < Base
param :acting_user, nils: true
param :model
- param :id
+ param :id, nils: true
param :vector
step do
ReactiveRecord::Base.destroy_record(
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/setters.rb b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/setters.rb
index a3458e12b..52fecd72c 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/setters.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/setters.rb
@@ -94,7 +94,7 @@ def set_common(attr, value)
end
def set_attribute_change_status_and_notify(attr, changed, new_value)
- if @virgin
+ if @virgin || @being_destroyed
@attributes[attr] = new_value
else
change_status_and_notify_helper(attr, changed) do |had_key, current_value|
@@ -108,14 +108,13 @@ def set_attribute_change_status_and_notify(attr, changed, new_value)
end
def set_change_status_and_notify_only(attr, changed)
- return if @virgin
+ return if @virgin || @being_destroyed
change_status_and_notify_helper(attr, changed) do
Hyperstack::Internal::State::Variable.set(self, attr, nil) unless data_loading?
end
end
def change_status_and_notify_helper(attr, changed)
- return if @being_destroyed
empty_before = changed_attributes.empty?
if !changed || data_loading?
changed_attributes.delete(attr)
diff --git a/ruby/hyper-model/lib/reactive_record/broadcast.rb b/ruby/hyper-model/lib/reactive_record/broadcast.rb
index bf3214818..944fd7a51 100644
--- a/ruby/hyper-model/lib/reactive_record/broadcast.rb
+++ b/ruby/hyper-model/lib/reactive_record/broadcast.rb
@@ -115,6 +115,10 @@ def destroyed?
@destroyed
end
+ def local?
+ @is_local
+ end
+
def klass
Object.const_get(@klass)
end
@@ -135,7 +139,7 @@ def self.in_transit
@in_transit ||= Hash.new { |h, k| h[k] = new(k) }
end
- def initialize(id)
+ def initialize(id = nil)
@id = id
@received = Set.new
@record = {}
@@ -144,6 +148,7 @@ def initialize(id)
def local(operation, record, data)
@destroyed = operation == :destroy
+ @is_local = true
@is_new = operation == :create
@klass = record.class.name
@record = data
@@ -166,7 +171,7 @@ def receive(params)
@backing_record = ReactiveRecord::Base.exists?(klass, params.record[klass.primary_key])
# first check to see if we already destroyed it and if so exit the block
- return if @backing_record&.destroyed
+ break if @backing_record&.destroyed
# We ignore whether the record is being created or not, and just check and see if in our
# local copy we have ever loaded this id before. If we have then its not new to us.
diff --git a/ruby/hyper-model/lib/reactive_record/server_data_cache.rb b/ruby/hyper-model/lib/reactive_record/server_data_cache.rb
index 002075915..23a709a02 100644
--- a/ruby/hyper-model/lib/reactive_record/server_data_cache.rb
+++ b/ruby/hyper-model/lib/reactive_record/server_data_cache.rb
@@ -486,7 +486,7 @@ def self.load_from_json(tree, target = nil)
elsif !target
load_from_json(value, Object.const_get(method))
elsif method == "*count"
- target.set_count_state(value.first)
+ target.count_state = value.first
elsif method.is_a? Integer or method =~ /^[0-9]+$/
new_target = target.push_and_update_belongs_to(method)
elsif method.is_a? Array
diff --git a/ruby/hyper-model/spec/batch3/has_and_belongs_to_many_spec.rb b/ruby/hyper-model/spec/batch3/has_and_belongs_to_many_spec.rb
new file mode 100644
index 000000000..f5671dcbe
--- /dev/null
+++ b/ruby/hyper-model/spec/batch3/has_and_belongs_to_many_spec.rb
@@ -0,0 +1,112 @@
+require 'spec_helper'
+require 'test_components'
+
+describe "has_and_belongs_to_many", js: true do
+
+ alias_method :on_client, :evaluate_ruby
+
+ before(:all) do
+ require 'pusher'
+ require 'pusher-fake'
+ Pusher.app_id = "MY_TEST_ID"
+ Pusher.key = "MY_TEST_KEY"
+ Pusher.secret = "MY_TEST_SECRET"
+ require "pusher-fake/support/base"
+
+ Hyperstack.configuration do |config|
+ config.transport = :pusher
+ config.channel_prefix = "synchromesh"
+ config.opts = {app_id: Pusher.app_id, key: Pusher.key, secret: Pusher.secret}.merge(PusherFake.configuration.web_options)
+ end
+
+ class ActiveRecord::Base
+ class << self
+ def public_columns_hash
+ @public_columns_hash ||= {}
+ end
+ end
+ end
+
+ class Physician < ActiveRecord::Base
+ def self.build_tables
+ connection.create_table :physicians, force: true do |t|
+ t.string :name
+ t.timestamps
+ end
+ ActiveRecord::Base.public_columns_hash[name] = columns_hash
+ end
+ end
+
+ class Patient < ActiveRecord::Base
+ def self.build_tables
+ connection.create_table :patients, force: true do |t|
+ t.string :name
+ t.timestamps
+ end
+ ActiveRecord::Base.public_columns_hash[name] = columns_hash
+ end
+ end
+
+ class PatientsPhysicianStub < ActiveRecord::Base
+ def self.build_tables
+ connection.create_table :patients_physicians, force: true do |t|
+ t.belongs_to :physician, index: true
+ t.belongs_to :patient, index: true
+ end
+ end
+ end
+
+ Physician.build_tables #rescue nil
+ PatientsPhysicianStub.build_tables #rescue nil
+ Patient.build_tables #rescue nil
+
+ isomorphic do
+ class Physician < ActiveRecord::Base
+ has_and_belongs_to_many :patients
+ end
+
+ class Patient < ActiveRecord::Base
+ has_and_belongs_to_many :physicians
+ end
+ end
+ end
+
+ before(:each) do
+ stub_const 'ApplicationPolicy', Class.new
+ ApplicationPolicy.class_eval do
+ always_allow_connection
+ regulate_all_broadcasts { |policy| policy.send_all }
+ allow_change(to: :all, on: [:create, :update, :destroy]) { true }
+ end
+
+ size_window(:medium)
+ end
+
+ it 'works' do
+ mccoy = Physician.create(name: 'Dr. McCoy')
+ Patient.create(name: 'James T. Kirk').physicians << mccoy
+ expect { Physician.first.patients.count }.on_client_to eq(1)
+
+ Patient.create(name: 'Spock').physicians << mccoy
+ expect { Physician.first.patients.count }.on_client_to eq(2)
+
+ on_client { Patient.create(name: 'Uhuru') }
+ 2.times do
+ on_client { Patient.find(3).physicians << Physician.first }
+ expect { Patient.find(3).physicians.count }.on_client_to eq(1)
+ wait_for { Patient.find(3).physicians.count }.to eq(1)
+ expect { Physician.first.patients.count }.on_client_to eq(3)
+ expect(Physician.first.patients.count).to eq(3)
+
+ on_client { Patient.find(3).physicians.destroy(Physician.first) }
+ expect { Patient.find(3).physicians.count }.on_client_to eq(0)
+ wait_for { Patient.find(3).physicians.count }.to eq(0)
+ expect { Physician.first.patients.count }.on_client_to eq(2)
+ expect(Physician.first.patients.count).to eq(2)
+ end
+
+ on_client { Patient.find(3).physicians.delete(Physician.first) }
+ expect { Patient.find(3).physicians.count }.on_client_to eq(0)
+ expect(Patient.find(3).physicians.count).to eq(0)
+ end
+end
diff --git a/ruby/hyper-model/spec/spec_helper.rb b/ruby/hyper-model/spec/spec_helper.rb
index 1cf662002..b860162e1 100644
--- a/ruby/hyper-model/spec/spec_helper.rb
+++ b/ruby/hyper-model/spec/spec_helper.rb
@@ -243,7 +243,7 @@ class ActiveRecord::Base
end
end
- config.before(:each, :js => true) do
+ config.before(:each, js: true) do
DatabaseCleaner.strategy = :truncation
end
diff --git a/ruby/hyper-model/spec/test_app/config/application.rb b/ruby/hyper-model/spec/test_app/config/application.rb
index a9a04996a..864804bf0 100644
--- a/ruby/hyper-model/spec/test_app/config/application.rb
+++ b/ruby/hyper-model/spec/test_app/config/application.rb
@@ -17,7 +17,7 @@ class Application < Rails::Application
config.assets.paths << ::Rails.root.join('app', 'models').to_s
config.opal.method_missing = true
config.opal.optimized_operators = true
- config.opal.arity_check = false
+ config.opal.arity_check_enabled = false
config.opal.const_missing = true
config.opal.dynamic_require_severity = :ignore
config.opal.enable_specs = true
diff --git a/ruby/hyper-model/spec/test_components.rb b/ruby/hyper-model/spec/test_components.rb
index 775e16433..133e477cb 100644
--- a/ruby/hyper-model/spec/test_components.rb
+++ b/ruby/hyper-model/spec/test_components.rb
@@ -1,6 +1,6 @@
RSpec.configure do |config|
config.before(:all) do
- on_client do
+ before_mount do
class TestComponent < HyperComponent
param scope: :all
render(DIV) do
diff --git a/ruby/hyper-operation/lib/hyper-operation/transport/client_drivers.rb b/ruby/hyper-operation/lib/hyper-operation/transport/client_drivers.rb
index 4f93c4ba8..54b185d88 100644
--- a/ruby/hyper-operation/lib/hyper-operation/transport/client_drivers.rb
+++ b/ruby/hyper-operation/lib/hyper-operation/transport/client_drivers.rb
@@ -97,7 +97,7 @@ def self.connect_to(channel_name, id = nil)
%x{
var channel = #{ClientDrivers.opts[:pusher_api]}.subscribe(#{channel.gsub('::', '==')});
channel.bind('dispatch', #{ClientDrivers.opts[:dispatch]})
- channel.bind('pusher:subscription_succeeded', #{lambda {ClientDrivers.get_queued_data("connect-to-transport", channel_string)}})
+ channel.bind('pusher:subscription_succeeded', #{->(*) { ClientDrivers.get_queued_data("connect-to-transport", channel_string)}})
}
@pusher_dispatcher_registered = true
elsif ClientDrivers.opts[:transport] == :action_cable
diff --git a/ruby/hyper-state/lib/hyperstack/internal/state/variable.rb b/ruby/hyper-state/lib/hyperstack/internal/state/variable.rb
index c39ad20a1..7d745c1bf 100644
--- a/ruby/hyper-state/lib/hyperstack/internal/state/variable.rb
+++ b/ruby/hyper-state/lib/hyperstack/internal/state/variable.rb
@@ -13,7 +13,9 @@ def get(obj, name)
map_object[0]
end
- def set(obj, name, value)
+ def set(obj, name, value, _x = nil)
+ # _x is some legacy function, which I think queued up state changes to the end
+ # which is perhaps now the default.
map_object = legacy_map[obj][name]
map_object[0] = value
Hyperstack::Internal::State::Mapper.mutated!(map_object.object_id)
diff --git a/ruby/hyper-trace/lib/hyper_trace/hyper_trace.rb b/ruby/hyper-trace/lib/hyper_trace/hyper_trace.rb
index 2bf6ec316..134437a0e 100644
--- a/ruby/hyper-trace/lib/hyper_trace/hyper_trace.rb
+++ b/ruby/hyper-trace/lib/hyper_trace/hyper_trace.rb
@@ -6,17 +6,7 @@ def hyper_trace(*args, &block)
alias hypertrace hyper_trace
end
-class Method
- def parameters
- /.*function[^(]*\(([^)]*)\)/
- .match(`#{@method}.toString()`)[1]
- .split(',')
- .collect { |param| [:req, param.strip.to_sym] }
- end
-end
-
module HyperTrace
-
class Config
def initialize(klass, instrument_class, opts, &block)
@klass = klass
@@ -116,15 +106,11 @@ def exclusions
def instrumentation_off(config)
if config.instrument_class?
config.klass.methods.grep(/^__hyper_trace_pre_.+$/).each do |method|
- config.klass.class_eval do
- class << self
- alias_method method.gsub(/^__hyper_trace_pre_/, ''), method
- end
- end
+ config.klass.singleton_class.alias_method method.gsub(/^__hyper_trace_pre_/, ''), method
end
else
config.klass.instance_methods.grep(/^__hyper_trace_pre_.+$/).each do |method|
- config.klass.class_eval { alias_method method.gsub(/^__hyper_trace_pre_/, ''), method }
+ config.klass.alias_method method.gsub(/^__hyper_trace_pre_/, ''), method
end
end
end
@@ -145,17 +131,12 @@ def all_methods(config)
def instrument_method(method, config)
if config.instrument_class?
- config.klass.class_eval do
- class << self
- alias_method "__hyper_trace_pre_#{method}", method unless method_defined? "__pre_hyper_trace_#{method}"
- end
+ unless config.klass.singleton_class.method_defined? "__pre_hyper_trace_#{method}" # is this right?
+ config.klass.singleton_class.alias_method "__hyper_trace_pre_#{method}", method
end
- add_hyper_trace_method(method, config)
else
unless config.klass.method_defined? "__pre_hyper_trace_#{method}"
- config.klass.class_eval do
- alias_method "__hyper_trace_pre_#{method}", method
- end
+ config.klass.alias_method "__hyper_trace_pre_#{method}", method
end
end
add_hyper_trace_method(method, config)
@@ -194,28 +175,77 @@ def instance_tag(instance, prefix = ' - ')
end
end
+ def required(arity, actual_length)
+ if arity.negative?
+ req_count = - arity - 1
+ raise ArgumentError, "missing required arguments: #{actual_length} for #{req_count}" if req_count > actual_length
+ else
+ req_count = arity
+ raise ArgumentError, "incorrect number of arguments, expected #{req_count} got #{actual_length}" if req_count != actual_length
+ end
+ req_count
+ end
+
+ # [["req", "x"], ["opt", "y"], ["rest"], ["keyreq", "z"], ["key", "opt"], ["block", "flop"]]
+
+ def map_parameters(instance, name, actual, format = true)
+ method = instance.method("__hyper_trace_pre_#{name}")
+ map_with_specs(method, actual.dup, format) || map_without_specs(actual, format)
+ end
+
+ def key?(actual, key)
+ actual&.last&.respond_to?(:key?) && actual.last.key?(key)
+ end
+
+ def map_with_specs(method, actual, show_blank_rest)
+ specs = method.parameters
+ req_count = required(method.arity, actual.length)
+ args = {}
+
+ specs.each do |type, key|
+ case type
+ when :req
+ args[key] = actual.shift
+ req_count -= 1
+ when :opt
+ args[key] = actual.shift if actual.length > req_count
+ when (key || show_blank_rest) && :rest
+ args[key || '*'] = [*actual[0..-req_count - 1]]
+ when :keyreq
+ raise ArgumentError, "missing keyword argument: #{key}" unless key?(actual, key)
+
+ args[key] = actual.last[key]
+ when key?(actual, key) && :key
+ args[key] = actual.last[key]
+ end
+ end
+ args
+ rescue ArgumentError, Interrupt, SignalException => e
+ raise e
+ rescue Exception => e
+ nil
+ end
+
+ def map_without_specs(actual, format)
+ args = {}
+ prefix = 'p' unless format
+ actual.each_with_index { |value, i| args["#{prefix}#{i + 1}"] = value }
+ args
+ end
+
def format_head(instance, name, args, &block)
@formatting = true
- method = instance.method("__hyper_trace_pre_#{name}")
if args.any?
group(" #{name}(...)#{instance_tag(instance)}") do
- params = method.parameters
- group("args:", collapsed: true) do
- params.each_with_index do |param_spec, i|
- arg_name = param_spec[1]
- if arg_name == '$a_rest'
- arg_name = '*'
- arg = args[i..-1]
- else
- arg = args[i]
- end
- if safe_i(arg).length > 30 || show_js_object(arg)
- group "#{arg_name}: #{safe_s(arg)}"[0..29], collapsed: true do
- puts safe_i(arg)
- log arg if show_js_object(arg)
+ group("args: (#{args.length})", collapsed: true) do
+ map_parameters(instance, name, args).each do |arg, value|
+ if safe_i(value).length > 30 || show_js_object(value)
+ group "#{arg}: #{safe_s(value)}"[0..29], collapsed: true do
+ puts safe_i(value)
+ log value if show_js_object(value)
end
else
- group "#{arg_name}: #{safe_i(arg)}"
+ group "#{arg}: #{safe_i(value)}"
end
end
end
@@ -286,7 +316,10 @@ def format_exception(result)
@formatting = true
if safe_i(result).length > 40
group "raised: #{safe_s(result)}"[0..40], collapsed: true do
- puts safe_i(result)
+ puts result.backtrace[0]
+ result.backtrace[1..-1].each do |line|
+ log line
+ end
end
else
group "raised: #{safe_i(result)}"
@@ -305,24 +338,23 @@ def should_break?(location, config, name, args, instance, result)
def breakpoint(location, config, name, args, instance, result = nil)
if should_break? location, config, name, args, instance, result
- method = instance.method("__hyper_trace_pre_#{name}")
+ params = map_parameters(instance, name, args, false)
fn_def = ['RESULT']
- fn_def += method.parameters.collect { |p| p[1] }
+ fn_def += params.keys
fn_def += ["//break on #{location} of #{name}\nvar self = this;\ndebugger;\n;"]
puts "break on #{location} of #{name}"
fn = `Function.apply(#{self}, #{fn_def}).bind(#{instance})`
- fn.call(result, *args)
+ fn.call(result, *params.values)
end
end
- def call_original(instance, method, *args, &block)
+ def call_original(instance, method, args, &block)
@formatting = false
instance.send "__hyper_trace_pre_#{method}", *args, &block
ensure
@formatting = true
end
-
def add_hyper_trace_method(method, config)
def_method = config.instrument_class? ? :define_singleton_method : :define_method
config.klass.send(def_method, method) do |*args, &block|
@@ -330,7 +362,7 @@ def add_hyper_trace_method(method, config)
if HyperTrace.formatting?
begin
send "__hyper_trace_pre_#{method}", *args, &block
- rescue Exception
+ rescue StandardError
"???"
end
else
@@ -338,11 +370,13 @@ def add_hyper_trace_method(method, config)
HyperTrace.format_head(self, method, args) do
HyperTrace.format_instance_internal(self)
HyperTrace.breakpoint(:enter, config, method, args, self)
- result = HyperTrace.call_original self, method, *args, &block
+ result = HyperTrace.call_original self, method, args, &block
HyperTrace.format_result(result)
HyperTrace.breakpoint(:exit, config, method, args, self, result)
result
end
+ rescue Interrupt, SignalException => e
+ raise e
rescue Exception => e
HyperTrace.format_exception(e)
debugger unless HyperTrace.exclusions[self.class][:rescue].include? :method
From efdfc99cf09c5fb04d8e5c778d7e1b6527189ebd Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 5 Mar 2021 15:17:30 -0500
Subject: [PATCH 157/307] reverting last travis change
---
.travis.yml | 15 +++++----------
1 file changed, 5 insertions(+), 10 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index ba19b4098..6c0366e60 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -1,6 +1,10 @@
dist: xenial
-language: bash
+# language: bash
+# cache:
+# bundler: true
+# directories:
+# - node_modules # NPM packages
addons:
apt:
@@ -18,11 +22,6 @@ addons:
postgresql: '11'
_test_gem_pg: &_test_gem_pg
- stage: test
- cache:
- bundler: true
- directories:
- - node_modules # NPM packages
before_install:
- echo 'installing postgresql'
- sudo sed -i 's/port = 5433/port = 5432/' /etc/postgresql/11/main/postgresql.conf
@@ -51,10 +50,6 @@ _test_gem_pg: &_test_gem_pg
_test_gem: &_test_gem
stage: test
- cache:
- bundler: true
- directories:
- - node_modules # NPM packages
addons:
apt:
sources:
From 9e195725d2001d89a66381bc4ebf6000b4f7524b Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 5 Mar 2021 17:25:58 -0500
Subject: [PATCH 158/307] trying to update chrome driver to latest
---
.travis.yml | 4 ++++
1 file changed, 4 insertions(+)
diff --git a/.travis.yml b/.travis.yml
index 6c0366e60..c51d21205 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -38,6 +38,8 @@ _test_gem_pg: &_test_gem_pg
before_script:
- echo before_script $COMPONENT
+ - echo updating chrome driver
+ - chromedriver-update 89.0.4389.23
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
- bundle exec rake spec:prepare
@@ -78,6 +80,8 @@ _test_gem: &_test_gem
before_script:
- echo before_script $COMPONENT
+ - echo updating chrome driver
+ - chromedriver-update 89.0.4389.23
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
- bundle exec rake spec:prepare
From 2e413fb0615d474f7393add47b0c68b55090e07f Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 5 Mar 2021 17:53:46 -0500
Subject: [PATCH 159/307] more attempts to update chromedriver
---
.travis.yml | 4 ++--
ruby/hyper-model/Rakefile | 2 ++
ruby/hyperstack-config/Rakefile | 2 ++
3 files changed, 6 insertions(+), 2 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index c51d21205..d006d0860 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -80,13 +80,13 @@ _test_gem: &_test_gem
before_script:
- echo before_script $COMPONENT
- - echo updating chrome driver
- - chromedriver-update 89.0.4389.23
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
- bundle exec rake spec:prepare
- google-chrome --version
- which google-chrome
+ - echo updating chrome driver
+ - bundle exec rake webdrivers:chromedriver:update
- yarn install
script:
- echo running script $COMPONENT
diff --git a/ruby/hyper-model/Rakefile b/ruby/hyper-model/Rakefile
index eeb360644..622689717 100644
--- a/ruby/hyper-model/Rakefile
+++ b/ruby/hyper-model/Rakefile
@@ -1,5 +1,7 @@
require "bundler/gem_tasks"
require "rspec/core/rake_task"
+require 'webdrivers'
+load 'webdrivers/Rakefile'
def run_batches(batches)
failed = false
diff --git a/ruby/hyperstack-config/Rakefile b/ruby/hyperstack-config/Rakefile
index 17cf89f90..86c3f30eb 100644
--- a/ruby/hyperstack-config/Rakefile
+++ b/ruby/hyperstack-config/Rakefile
@@ -1,5 +1,7 @@
require "bundler/gem_tasks"
require "rspec/core/rake_task"
+require 'webdrivers'
+load 'webdrivers/Rakefile'
RSpec::Core::RakeTask.new(:spec)
From f817a459d3bf87fea919dfc885d017ac76854871 Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 5 Mar 2021 18:03:45 -0500
Subject: [PATCH 160/307] more attempts to update chromedriver 2
---
.travis.yml | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/.travis.yml b/.travis.yml
index d006d0860..f3c640fe2 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -75,7 +75,7 @@ _test_gem: &_test_gem
- nvm install 10
- rvm install 2.6.3 # was 2.5.1
- gem install bundler
- - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
+ # - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
- echo 'install completed'
before_script:
From be4899b93b7ad2ae73109a26ece4d16c47b71598 Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 5 Mar 2021 22:20:38 -0500
Subject: [PATCH 161/307] another attempt to update chromedriver
---
.travis.yml | 2 --
ruby/hyper-spec/lib/hyper-spec.rb | 6 +++++-
2 files changed, 5 insertions(+), 3 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index f3c640fe2..76b7d9a39 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -85,8 +85,6 @@ _test_gem: &_test_gem
- bundle exec rake spec:prepare
- google-chrome --version
- which google-chrome
- - echo updating chrome driver
- - bundle exec rake webdrivers:chromedriver:update
- yarn install
script:
- echo running script $COMPONENT
diff --git a/ruby/hyper-spec/lib/hyper-spec.rb b/ruby/hyper-spec/lib/hyper-spec.rb
index 5b802ce2e..f9f3d5e0b 100644
--- a/ruby/hyper-spec/lib/hyper-spec.rb
+++ b/ruby/hyper-spec/lib/hyper-spec.rb
@@ -23,7 +23,11 @@
require 'hyper-spec/expectations'
require 'parser/current'
-require 'selenium/web_driver/firefox/profile' if defined?(Selenium::WebDriver::Firefox)
+require 'webdrivers/chromedriver'
+if defined?(Selenium::WebDriver::Firefox)
+ require 'selenium/web_driver/firefox/profile'
+ require 'webdrivers/geckodriver'
+end
require 'selenium-webdriver'
require 'hyper-spec/version'
From 289fddad8f1ab58fa416ba0ee4923a8f62ddb4eb Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 5 Mar 2021 22:39:35 -0500
Subject: [PATCH 162/307] another attempt to update chromedriver 2
---
ruby/hyper-spec/lib/hyper-spec.rb | 1 +
1 file changed, 1 insertion(+)
diff --git a/ruby/hyper-spec/lib/hyper-spec.rb b/ruby/hyper-spec/lib/hyper-spec.rb
index f9f3d5e0b..699662484 100644
--- a/ruby/hyper-spec/lib/hyper-spec.rb
+++ b/ruby/hyper-spec/lib/hyper-spec.rb
@@ -24,6 +24,7 @@
require 'parser/current'
require 'webdrivers/chromedriver'
+Webdrivers.logger.level = :DEBUG
if defined?(Selenium::WebDriver::Firefox)
require 'selenium/web_driver/firefox/profile'
require 'webdrivers/geckodriver'
From 42034091d81eb87c53642b748b41eaedf7ef1713 Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 5 Mar 2021 22:49:18 -0500
Subject: [PATCH 163/307] trying to at least get logging going
---
ruby/hyper-spec/lib/hyper-spec.rb | 1 +
1 file changed, 1 insertion(+)
diff --git a/ruby/hyper-spec/lib/hyper-spec.rb b/ruby/hyper-spec/lib/hyper-spec.rb
index 699662484..7a4708b76 100644
--- a/ruby/hyper-spec/lib/hyper-spec.rb
+++ b/ruby/hyper-spec/lib/hyper-spec.rb
@@ -25,6 +25,7 @@
require 'parser/current'
require 'webdrivers/chromedriver'
Webdrivers.logger.level = :DEBUG
+puts 'logger level set to :DEBUG'
if defined?(Selenium::WebDriver::Firefox)
require 'selenium/web_driver/firefox/profile'
require 'webdrivers/geckodriver'
From 9ea584d70d525619369a6ac06b207fdfe366edbb Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 5 Mar 2021 23:24:03 -0500
Subject: [PATCH 164/307] trying another solution
---
.travis.yml | 25 +++++++++++++------------
1 file changed, 13 insertions(+), 12 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 76b7d9a39..2e2edb4c6 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -8,14 +8,14 @@ dist: xenial
addons:
apt:
- sources:
- - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
- key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
- - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
- key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
+ # sources:
+ # - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
+ # key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
+ # - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
+ # key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
packages:
- postgresql-11
- - chromium-chromedriver
+ # - chromium-chromedriver
- google-chrome-stable
- yarn
- redis-server
@@ -54,13 +54,13 @@ _test_gem: &_test_gem
stage: test
addons:
apt:
- sources:
- - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
- key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
- - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
- key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
+ # sources:
+ # - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
+ # key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
+ # - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
+ # key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
packages:
- - chromium-chromedriver
+ # - chromium-chromedriver
- google-chrome-stable
- yarn
- redis-server
@@ -82,6 +82,7 @@ _test_gem: &_test_gem
- echo before_script $COMPONENT
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
+ - rake webdrivers:chromedriver:version
- bundle exec rake spec:prepare
- google-chrome --version
- which google-chrome
From d50e3e740fbacc27d406a6046a0e47d405354be8 Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 5 Mar 2021 23:28:33 -0500
Subject: [PATCH 165/307] trying another solution 2
---
.travis.yml | 20 ++++++++++----------
1 file changed, 10 insertions(+), 10 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 2e2edb4c6..83520f390 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -8,11 +8,11 @@ dist: xenial
addons:
apt:
- # sources:
- # - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
- # key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
- # - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
- # key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
+ sources:
+ - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
+ key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
+ - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
+ key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
packages:
- postgresql-11
# - chromium-chromedriver
@@ -54,11 +54,11 @@ _test_gem: &_test_gem
stage: test
addons:
apt:
- # sources:
- # - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
- # key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
- # - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
- # key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
+ sources:
+ - sourceline: 'deb http://dl.yarnpkg.com/debian/ stable main'
+ key_url: 'http://dl.yarnpkg.com/debian/pubkey.gpg'
+ - sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
+ key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
packages:
# - chromium-chromedriver
- google-chrome-stable
From 70fbf5d097c9b4dc3c0c72f55f45d429f3bfe5db Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 5 Mar 2021 23:38:36 -0500
Subject: [PATCH 166/307] trying another solution 3
---
.travis.yml | 5 +++--
1 file changed, 3 insertions(+), 2 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 83520f390..7100d7d47 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -15,7 +15,7 @@ addons:
key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
packages:
- postgresql-11
- # - chromium-chromedriver
+ - chromium-chromedriver
- google-chrome-stable
- yarn
- redis-server
@@ -60,7 +60,7 @@ _test_gem: &_test_gem
- sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
packages:
- # - chromium-chromedriver
+ - chromium-chromedriver
- google-chrome-stable
- yarn
- redis-server
@@ -75,6 +75,7 @@ _test_gem: &_test_gem
- nvm install 10
- rvm install 2.6.3 # was 2.5.1
- gem install bundler
+ # /usr/lib/chromium-browser/chromedriver
# - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
- echo 'install completed'
From 4f5ee675311d037ee153cb49217d6c2100a88a6f Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 5 Mar 2021 23:58:14 -0500
Subject: [PATCH 167/307] trying another solution 4
---
.travis.yml | 5 +++--
1 file changed, 3 insertions(+), 2 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 7100d7d47..d98c349e8 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -75,7 +75,7 @@ _test_gem: &_test_gem
- nvm install 10
- rvm install 2.6.3 # was 2.5.1
- gem install bundler
- # /usr/lib/chromium-browser/chromedriver
+ # /usr/lib/chromium-browser/chromedriver <- is that a dir of a file?
# - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
- echo 'install completed'
@@ -84,6 +84,7 @@ _test_gem: &_test_gem
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
- rake webdrivers:chromedriver:version
+ - ls $WD_INSTALL_DIR
- bundle exec rake spec:prepare
- google-chrome --version
- which google-chrome
@@ -114,7 +115,7 @@ jobs:
- <<: *_test_gem
env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
- <<: *_test_gem
- env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1
+ env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 WD_INSTALL_DIR="/usr/lib/chromium-browser/"
- <<: *_test_gem
env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
- <<: *_test_gem
From 225605c0d0c86f584115146764a25bd130955413 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 6 Mar 2021 00:08:44 -0500
Subject: [PATCH 168/307] trying another solution 5
---
.travis.yml | 2 ++
1 file changed, 2 insertions(+)
diff --git a/.travis.yml b/.travis.yml
index d98c349e8..5c0a575bc 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -84,6 +84,8 @@ _test_gem: &_test_gem
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
- rake webdrivers:chromedriver:version
+ - rake webdrivers:chromedriver:update
+ - rake webdrivers:chromedriver:version
- ls $WD_INSTALL_DIR
- bundle exec rake spec:prepare
- google-chrome --version
From d439a5fb2a189c782fe1eedbda7e29f826c6b771 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 6 Mar 2021 00:16:12 -0500
Subject: [PATCH 169/307] trying another solution 6
---
.travis.yml | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 5c0a575bc..dd205fa08 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -84,7 +84,7 @@ _test_gem: &_test_gem
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
- rake webdrivers:chromedriver:version
- - rake webdrivers:chromedriver:update
+ - sudo rake webdrivers:chromedriver:update
- rake webdrivers:chromedriver:version
- ls $WD_INSTALL_DIR
- bundle exec rake spec:prepare
@@ -117,7 +117,7 @@ jobs:
- <<: *_test_gem
env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
- <<: *_test_gem
- env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 WD_INSTALL_DIR="/usr/lib/chromium-browser/"
+ env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 WD_INSTALL_DIR="/usr/lib/chromium-browser"
- <<: *_test_gem
env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
- <<: *_test_gem
From 8c52aa14a310752f92eaba5ce265b72e999731e3 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 6 Mar 2021 00:24:08 -0500
Subject: [PATCH 170/307] trying another solution 7
---
.travis.yml | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index dd205fa08..8151809f1 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -83,9 +83,9 @@ _test_gem: &_test_gem
- echo before_script $COMPONENT
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
- - rake webdrivers:chromedriver:version
- - sudo rake webdrivers:chromedriver:update
- - rake webdrivers:chromedriver:version
+ - bundle exec rake webdrivers:chromedriver:version
+ - bundle exec sudo rake webdrivers:chromedriver:update
+ - bundle exec rake webdrivers:chromedriver:version
- ls $WD_INSTALL_DIR
- bundle exec rake spec:prepare
- google-chrome --version
From c592aac939352eef7146a6b85d83b8d432fb4611 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 6 Mar 2021 00:25:00 -0500
Subject: [PATCH 171/307] trying another solution 8
---
.travis.yml | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/.travis.yml b/.travis.yml
index 8151809f1..6270122c9 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -84,7 +84,7 @@ _test_gem: &_test_gem
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
- bundle exec rake webdrivers:chromedriver:version
- - bundle exec sudo rake webdrivers:chromedriver:update
+ - sudo bundle exec rake webdrivers:chromedriver:update
- bundle exec rake webdrivers:chromedriver:version
- ls $WD_INSTALL_DIR
- bundle exec rake spec:prepare
From d425b8d08c8ade90de3a484188e7e06c24a39074 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 6 Mar 2021 00:44:53 -0500
Subject: [PATCH 172/307] trying another solution 9
---
.travis.yml | 14 +++++++++-----
1 file changed, 9 insertions(+), 5 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 6270122c9..3b18bbbc9 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -83,13 +83,17 @@ _test_gem: &_test_gem
- echo before_script $COMPONENT
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
+ - google-chrome --version
+ - which google-chrome
- bundle exec rake webdrivers:chromedriver:version
- - sudo bundle exec rake webdrivers:chromedriver:update
+ - bundle exec rake webdrivers:chromedriver:update
+ - ls -la ~/bin/.webdrivers
+ - sudo ln -s ~/bin/.webdrivers/chromedriver /usr/lib/chromium-browser/chromedriver
- bundle exec rake webdrivers:chromedriver:version
- - ls $WD_INSTALL_DIR
+ - bundle exec rake webdrivers:chromedriver:version WD_INSTALL_DIR='/usr/lib/chromium-browser'
+ - ls /usr/lib/chromium-browser
- bundle exec rake spec:prepare
- - google-chrome --version
- - which google-chrome
+
- yarn install
script:
- echo running script $COMPONENT
@@ -117,7 +121,7 @@ jobs:
- <<: *_test_gem
env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
- <<: *_test_gem
- env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 WD_INSTALL_DIR="/usr/lib/chromium-browser"
+ env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 WD_INSTALL_DIRX="/usr/lib/chromium-browser"
- <<: *_test_gem
env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
- <<: *_test_gem
From d025b0376145db87cdb0dce19207e7a75df5fc61 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 6 Mar 2021 00:52:07 -0500
Subject: [PATCH 173/307] trying another solution 10
---
.travis.yml | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 3b18bbbc9..763187663 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -87,8 +87,8 @@ _test_gem: &_test_gem
- which google-chrome
- bundle exec rake webdrivers:chromedriver:version
- bundle exec rake webdrivers:chromedriver:update
- - ls -la ~/bin/.webdrivers
- - sudo ln -s ~/bin/.webdrivers/chromedriver /usr/lib/chromium-browser/chromedriver
+ - ls -la ~/.webdrivers
+ - sudo ln -s ~/.webdrivers/chromedriver /usr/lib/chromium-browser/chromedriver
- bundle exec rake webdrivers:chromedriver:version
- bundle exec rake webdrivers:chromedriver:version WD_INSTALL_DIR='/usr/lib/chromium-browser'
- ls /usr/lib/chromium-browser
From 17370456ed3c34a37bd36400bdd78e0a8b8b7789 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 6 Mar 2021 01:02:17 -0500
Subject: [PATCH 174/307] trying another solution 11
---
.travis.yml | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/.travis.yml b/.travis.yml
index 763187663..450be2d0d 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -88,7 +88,7 @@ _test_gem: &_test_gem
- bundle exec rake webdrivers:chromedriver:version
- bundle exec rake webdrivers:chromedriver:update
- ls -la ~/.webdrivers
- - sudo ln -s ~/.webdrivers/chromedriver /usr/lib/chromium-browser/chromedriver
+ - sudo cp ~/.webdrivers/chromedriver /usr/lib/chromium-browser/chromedriver
- bundle exec rake webdrivers:chromedriver:version
- bundle exec rake webdrivers:chromedriver:version WD_INSTALL_DIR='/usr/lib/chromium-browser'
- ls /usr/lib/chromium-browser
From 264e54cd89a48f533b764395213dc16d3be317ff Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 6 Mar 2021 07:58:28 -0500
Subject: [PATCH 175/307] cleaning up travis
---
.travis.yml | 18 ++++++++++--------
1 file changed, 10 insertions(+), 8 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 450be2d0d..8dbad4baa 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -15,7 +15,7 @@ addons:
key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
packages:
- postgresql-11
- - chromium-chromedriver
+ # - chromium-chromedriver
- google-chrome-stable
- yarn
- redis-server
@@ -60,7 +60,7 @@ _test_gem: &_test_gem
- sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
packages:
- - chromium-chromedriver
+ # - chromium-chromedriver
- google-chrome-stable
- yarn
- redis-server
@@ -77,6 +77,7 @@ _test_gem: &_test_gem
- gem install bundler
# /usr/lib/chromium-browser/chromedriver <- is that a dir of a file?
# - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
+ - sudo ln -s /usr/lib/chromium-browser ~/.webdrivers
- echo 'install completed'
before_script:
@@ -85,12 +86,13 @@ _test_gem: &_test_gem
- bundle install --jobs=3 --retry=3
- google-chrome --version
- which google-chrome
- - bundle exec rake webdrivers:chromedriver:version
- - bundle exec rake webdrivers:chromedriver:update
- - ls -la ~/.webdrivers
- - sudo cp ~/.webdrivers/chromedriver /usr/lib/chromium-browser/chromedriver
- - bundle exec rake webdrivers:chromedriver:version
- - bundle exec rake webdrivers:chromedriver:version WD_INSTALL_DIR='/usr/lib/chromium-browser'
+ - bundle exec ruby -e 'require "webdrivers"; Webdrivers::Chromedriver.update; puts Webdrivers::Chromedriver.current_version'
+ # - bundle exec rake webdrivers:chromedriver:version
+ # - bundle exec rake webdrivers:chromedriver:update
+ # - ls -la ~/.webdrivers
+ # - sudo cp ~/.webdrivers/chromedriver /usr/lib/chromium-browser/chromedriver
+ # - bundle exec rake webdrivers:chromedriver:version
+ # - bundle exec rake webdrivers:chromedriver:version WD_INSTALL_DIR='/usr/lib/chromium-browser'
- ls /usr/lib/chromium-browser
- bundle exec rake spec:prepare
From 444dcd0d91006deec014c40cd9fdcd9272308343 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 6 Mar 2021 08:07:52 -0500
Subject: [PATCH 176/307] cleaning up travis 2
---
.travis.yml | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 8dbad4baa..1278590f8 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -77,7 +77,7 @@ _test_gem: &_test_gem
- gem install bundler
# /usr/lib/chromium-browser/chromedriver <- is that a dir of a file?
# - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
- - sudo ln -s /usr/lib/chromium-browser ~/.webdrivers
+ # - sudo ln -s /usr/lib/chromium-browser ~/.webdrivers
- echo 'install completed'
before_script:
@@ -90,7 +90,7 @@ _test_gem: &_test_gem
# - bundle exec rake webdrivers:chromedriver:version
# - bundle exec rake webdrivers:chromedriver:update
# - ls -la ~/.webdrivers
- # - sudo cp ~/.webdrivers/chromedriver /usr/lib/chromium-browser/chromedriver
+ - sudo cp ~/.webdrivers/chromedriver /usr/lib/chromium-browser/chromedriver
# - bundle exec rake webdrivers:chromedriver:version
# - bundle exec rake webdrivers:chromedriver:version WD_INSTALL_DIR='/usr/lib/chromium-browser'
- ls /usr/lib/chromium-browser
From 2b86f31c47a4200e2c5770694dbc3783fa537eb1 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 6 Mar 2021 08:15:52 -0500
Subject: [PATCH 177/307] cleaning up travis 3
---
.travis.yml | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 1278590f8..4d24c749f 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -15,7 +15,7 @@ addons:
key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
packages:
- postgresql-11
- # - chromium-chromedriver
+ - chromium-chromedriver
- google-chrome-stable
- yarn
- redis-server
@@ -60,7 +60,7 @@ _test_gem: &_test_gem
- sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
packages:
- # - chromium-chromedriver
+ - chromium-chromedriver
- google-chrome-stable
- yarn
- redis-server
@@ -89,7 +89,7 @@ _test_gem: &_test_gem
- bundle exec ruby -e 'require "webdrivers"; Webdrivers::Chromedriver.update; puts Webdrivers::Chromedriver.current_version'
# - bundle exec rake webdrivers:chromedriver:version
# - bundle exec rake webdrivers:chromedriver:update
- # - ls -la ~/.webdrivers
+ - ls -la ~/.webdrivers
- sudo cp ~/.webdrivers/chromedriver /usr/lib/chromium-browser/chromedriver
# - bundle exec rake webdrivers:chromedriver:version
# - bundle exec rake webdrivers:chromedriver:version WD_INSTALL_DIR='/usr/lib/chromium-browser'
From 392138892f68ab4b8941864134a9cdf4ae286135 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 6 Mar 2021 08:23:42 -0500
Subject: [PATCH 178/307] cleaning up travis 4
---
.travis.yml | 8 ++++----
1 file changed, 4 insertions(+), 4 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 4d24c749f..147f1e156 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -15,7 +15,7 @@ addons:
key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
packages:
- postgresql-11
- - chromium-chromedriver
+ # - chromium-chromedriver
- google-chrome-stable
- yarn
- redis-server
@@ -39,7 +39,7 @@ _test_gem_pg: &_test_gem_pg
before_script:
- echo before_script $COMPONENT
- echo updating chrome driver
- - chromedriver-update 89.0.4389.23
+ # - chromedriver-update 89.0.4389.23
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
- bundle exec rake spec:prepare
@@ -60,8 +60,8 @@ _test_gem: &_test_gem
- sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
packages:
- - chromium-chromedriver
- - google-chrome-stable
+ # - chromium-chromedriver
+ # - google-chrome-stable
- yarn
- redis-server
mariadb: '10.3'
From 4dd0fe981b344b7e58c77e52b774ca0470f0a07e Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 6 Mar 2021 08:28:50 -0500
Subject: [PATCH 179/307] cleaning up travis 5
---
.travis.yml | 2 +-
ruby/hyper-spec/lib/hyper-spec.rb | 2 --
2 files changed, 1 insertion(+), 3 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 147f1e156..08946bad3 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -15,7 +15,7 @@ addons:
key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
packages:
- postgresql-11
- # - chromium-chromedriver
+ - chromium-chromedriver
- google-chrome-stable
- yarn
- redis-server
diff --git a/ruby/hyper-spec/lib/hyper-spec.rb b/ruby/hyper-spec/lib/hyper-spec.rb
index 7a4708b76..f9f3d5e0b 100644
--- a/ruby/hyper-spec/lib/hyper-spec.rb
+++ b/ruby/hyper-spec/lib/hyper-spec.rb
@@ -24,8 +24,6 @@
require 'parser/current'
require 'webdrivers/chromedriver'
-Webdrivers.logger.level = :DEBUG
-puts 'logger level set to :DEBUG'
if defined?(Selenium::WebDriver::Firefox)
require 'selenium/web_driver/firefox/profile'
require 'webdrivers/geckodriver'
From a183c7fe06e42602b85efe741c5c94cee7eab9e7 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 6 Mar 2021 08:38:44 -0500
Subject: [PATCH 180/307] cleaning up travis 6
---
.travis.yml | 12 +++++++-----
1 file changed, 7 insertions(+), 5 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 08946bad3..8e7e0bdd6 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -39,9 +39,11 @@ _test_gem_pg: &_test_gem_pg
before_script:
- echo before_script $COMPONENT
- echo updating chrome driver
- # - chromedriver-update 89.0.4389.23
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
+ - bundle exec ruby -e 'require "webdrivers"; Webdrivers::Chromedriver.update; puts Webdrivers::Chromedriver.current_version'
+ - ls -la ~/.webdrivers
+ - sudo cp ~/.webdrivers/chromedriver /usr/lib/chromium-browser/chromedriver
- bundle exec rake spec:prepare
- google-chrome --version
- which google-chrome
@@ -60,8 +62,8 @@ _test_gem: &_test_gem
- sourceline: 'deb http://dl.google.com/linux/chrome/deb/ stable main'
key_url: 'https://dl-ssl.google.com/linux/linux_signing_key.pub'
packages:
- # - chromium-chromedriver
- # - google-chrome-stable
+ - chromium-chromedriver
+ - google-chrome-stable
- yarn
- redis-server
mariadb: '10.3'
@@ -85,7 +87,7 @@ _test_gem: &_test_gem
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
- google-chrome --version
- - which google-chrome
+ #- which google-chrome
- bundle exec ruby -e 'require "webdrivers"; Webdrivers::Chromedriver.update; puts Webdrivers::Chromedriver.current_version'
# - bundle exec rake webdrivers:chromedriver:version
# - bundle exec rake webdrivers:chromedriver:update
@@ -93,7 +95,7 @@ _test_gem: &_test_gem
- sudo cp ~/.webdrivers/chromedriver /usr/lib/chromium-browser/chromedriver
# - bundle exec rake webdrivers:chromedriver:version
# - bundle exec rake webdrivers:chromedriver:version WD_INSTALL_DIR='/usr/lib/chromium-browser'
- - ls /usr/lib/chromium-browser
+ #- ls /usr/lib/chromium-browser
- bundle exec rake spec:prepare
- yarn install
From 23393f7f7611eea60c559b8874f70e3f3be5865e Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 6 Mar 2021 08:51:12 -0500
Subject: [PATCH 181/307] trying to get bundle caching working
---
.travis.yml | 21 +++++++++++++++------
1 file changed, 15 insertions(+), 6 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 8e7e0bdd6..0df61e2d7 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -1,11 +1,5 @@
dist: xenial
-# language: bash
-# cache:
-# bundler: true
-# directories:
-# - node_modules # NPM packages
-
addons:
apt:
sources:
@@ -22,6 +16,14 @@ addons:
postgresql: '11'
_test_gem_pg: &_test_gem_pg
+ stage: test
+
+ language: ruby
+ cache:
+ bundler: true
+ directories:
+ - node_modules # NPM packages
+
before_install:
- echo 'installing postgresql'
- sudo sed -i 's/port = 5433/port = 5432/' /etc/postgresql/11/main/postgresql.conf
@@ -54,6 +56,13 @@ _test_gem_pg: &_test_gem_pg
_test_gem: &_test_gem
stage: test
+
+ language: ruby
+ cache:
+ bundler: true
+ directories:
+ - node_modules # NPM packages
+
addons:
apt:
sources:
From 690517a3ba9efbf9fad3f3947fd9f972b5f3472e Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 6 Mar 2021 09:32:31 -0500
Subject: [PATCH 182/307] final (hopefully) cleanups to travis chrome issue
---
.travis.yml | 14 ++------------
ruby/hyper-model/Rakefile | 2 --
ruby/hyper-spec/lib/hyper-spec.rb | 2 --
ruby/hyperstack-config/Rakefile | 2 --
4 files changed, 2 insertions(+), 18 deletions(-)
diff --git a/.travis.yml b/.travis.yml
index 0df61e2d7..65497785a 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -56,7 +56,7 @@ _test_gem_pg: &_test_gem_pg
_test_gem: &_test_gem
stage: test
-
+
language: ruby
cache:
bundler: true
@@ -86,9 +86,6 @@ _test_gem: &_test_gem
- nvm install 10
- rvm install 2.6.3 # was 2.5.1
- gem install bundler
- # /usr/lib/chromium-browser/chromedriver <- is that a dir of a file?
- # - ln -s /usr/lib/chromium-browser/chromedriver ~/bin/chromedriver
- # - sudo ln -s /usr/lib/chromium-browser ~/.webdrivers
- echo 'install completed'
before_script:
@@ -96,17 +93,10 @@ _test_gem: &_test_gem
- cd ruby/$COMPONENT
- bundle install --jobs=3 --retry=3
- google-chrome --version
- #- which google-chrome
- bundle exec ruby -e 'require "webdrivers"; Webdrivers::Chromedriver.update; puts Webdrivers::Chromedriver.current_version'
- # - bundle exec rake webdrivers:chromedriver:version
- # - bundle exec rake webdrivers:chromedriver:update
- ls -la ~/.webdrivers
- sudo cp ~/.webdrivers/chromedriver /usr/lib/chromium-browser/chromedriver
- # - bundle exec rake webdrivers:chromedriver:version
- # - bundle exec rake webdrivers:chromedriver:version WD_INSTALL_DIR='/usr/lib/chromium-browser'
- #- ls /usr/lib/chromium-browser
- bundle exec rake spec:prepare
-
- yarn install
script:
- echo running script $COMPONENT
@@ -134,7 +124,7 @@ jobs:
- <<: *_test_gem
env: COMPONENT=hyper-trace RUBY_VERSION=2.5.1
- <<: *_test_gem
- env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1 WD_INSTALL_DIRX="/usr/lib/chromium-browser"
+ env: COMPONENT=hyperstack-config RUBY_VERSION=2.5.1
- <<: *_test_gem
env: COMPONENT=hyper-state RUBY_VERSION=2.5.1
- <<: *_test_gem
diff --git a/ruby/hyper-model/Rakefile b/ruby/hyper-model/Rakefile
index 622689717..eeb360644 100644
--- a/ruby/hyper-model/Rakefile
+++ b/ruby/hyper-model/Rakefile
@@ -1,7 +1,5 @@
require "bundler/gem_tasks"
require "rspec/core/rake_task"
-require 'webdrivers'
-load 'webdrivers/Rakefile'
def run_batches(batches)
failed = false
diff --git a/ruby/hyper-spec/lib/hyper-spec.rb b/ruby/hyper-spec/lib/hyper-spec.rb
index f9f3d5e0b..67b830366 100644
--- a/ruby/hyper-spec/lib/hyper-spec.rb
+++ b/ruby/hyper-spec/lib/hyper-spec.rb
@@ -23,10 +23,8 @@
require 'hyper-spec/expectations'
require 'parser/current'
-require 'webdrivers/chromedriver'
if defined?(Selenium::WebDriver::Firefox)
require 'selenium/web_driver/firefox/profile'
- require 'webdrivers/geckodriver'
end
require 'selenium-webdriver'
diff --git a/ruby/hyperstack-config/Rakefile b/ruby/hyperstack-config/Rakefile
index 86c3f30eb..17cf89f90 100644
--- a/ruby/hyperstack-config/Rakefile
+++ b/ruby/hyperstack-config/Rakefile
@@ -1,7 +1,5 @@
require "bundler/gem_tasks"
require "rspec/core/rake_task"
-require 'webdrivers'
-load 'webdrivers/Rakefile'
RSpec::Core::RakeTask.new(:spec)
From 013af18b350478d1a10b17d5f33848635ab12277 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 6 Mar 2021 14:56:58 -0500
Subject: [PATCH 183/307] fixed hyper-spec rspec-steps interaction
---
ruby/hyper-spec/lib/hyper-spec.rb | 5 +++++
1 file changed, 5 insertions(+)
diff --git a/ruby/hyper-spec/lib/hyper-spec.rb b/ruby/hyper-spec/lib/hyper-spec.rb
index 67b830366..a2492f324 100644
--- a/ruby/hyper-spec/lib/hyper-spec.rb
+++ b/ruby/hyper-spec/lib/hyper-spec.rb
@@ -117,6 +117,11 @@ def reset_sessions!
end
config.after(:all) do
HyperSpec.reset_sessions! unless HyperSpec.reset_between_examples?
+ # If rspecs step is used first in a file, it will NOT call config.before(:all) causing the
+ # reset_between_examples stack to be mismatched, so we check, if its already empty we
+ # just leave.
+ next if HyperSpec.reset_between_examples.empty?
+
RSpec.configuration.reset_between_examples = HyperSpec.reset_between_examples.pop
end
config.before(:each) do |example|
From d68e36655ee1cb57bdc479d4963cba4c36cd3183 Mon Sep 17 00:00:00 2001
From: R Mitchell VanDuyn
Date: Tue, 9 Mar 2021 11:26:52 -0500
Subject: [PATCH 184/307] closes #371
---
.rubocop.yml | 24 ++++--
.../internal/component/rendering_context.rb | 77 +++++++++++++------
.../spec/client_features/component_spec.rb | 29 ++++---
ruby/hyper-model/spec/test_app/db/schema.rb | 32 --------
4 files changed, 93 insertions(+), 69 deletions(-)
diff --git a/.rubocop.yml b/.rubocop.yml
index 805c0fb68..585f1cfd8 100644
--- a/.rubocop.yml
+++ b/.rubocop.yml
@@ -1,5 +1,4 @@
AllCops:
- TargetRubyVersion: 2.3
Exclude:
- 'db/schema.rb'
- 'db/seeds.rb'
@@ -31,14 +30,11 @@ Metrics/BlockLength:
Description: 'Avoid long blocks with many lines.'
Enabled: false
-Metrics/LineLength:
- Max: 100
-
## Performance
-Performance/RegexpMatch:
- Enabled: false
+# Performance/RegexpMatch:
+# Enabled: false
## Style
@@ -139,3 +135,19 @@ Style/MutableConstant:
Style/SafeNavigation:
Enabled: false
+
+Style/StringLiterals:
+ EnforcedStyle: double_quotes
+ Exclude:
+ - Gemfile
+
+Style/FrozenStringLiteralComment:
+ Enabled: false
+ Exclude:
+ - app/hyperstack/components
+ - app/hyperstack/libs
+
+Layout/MultilineMethodCallIndentation:
+ Exclude:
+ - 'bin/yarn'
+ - app/hyperstack/components
diff --git a/ruby/hyper-component/lib/hyperstack/internal/component/rendering_context.rb b/ruby/hyper-component/lib/hyperstack/internal/component/rendering_context.rb
index 145ccd6c6..f6dba2817 100644
--- a/ruby/hyper-component/lib/hyperstack/internal/component/rendering_context.rb
+++ b/ruby/hyper-component/lib/hyperstack/internal/component/rendering_context.rb
@@ -91,12 +91,12 @@ def remove_nodes_from_args(args)
# two child Elements will be generated.
#
# the final value of the block should either be
- # 1 an object that responds to :acts_as_string?
- # 2 a string,
- # 3 an element that is NOT yet pushed on the rendering buffer
- # 4 or the last element pushed on the buffer
+ # 1 a hyper model dummy value that is being loaded,
+ # 2 a string (or if the buffer is empty any value to which to_s can be applied)
+ # 3 an Element that is NOT yet pushed on the rendering buffer
+ # 4 or the last Element pushed on the buffer
#
- # in case 1 we render a span
+ # in case 1 we render a span wrapping the dummy value
# in case 2 we automatically push the string onto the buffer
# in case 3 we also push the Element onto the buffer IF the buffer is empty
# case 4 requires no special processing
@@ -105,31 +105,62 @@ def remove_nodes_from_args(args)
# outer rendering scope. In this case react only allows us to generate 1 Element
# so we insure that is the case, and also check to make sure that element in the buffer
# is the element returned
+ #
+ # Note that the reason we only allow Strings to be automatically pushed is to avoid
+ # confusing results in situations like this:
+ # DIV { collection.each { |item| SPAN { item } } }
+ # If we accepted any object to be rendered this would generate:
+ # DIV { SPAN { collection[0] } SPAN { collection[n] } collection.to_s }
+ # which is probably not the desired output. If it was you would just append to_s
+ # to the end of the expression, to force it to be added to the output buffer.
+ #
+ # However if the buffer is empty then it makes sense to automatically apply the `.to_s`
+ # to the value, and push it on the buffer
def run_child_block(is_outer_scope)
result = yield
- if result.respond_to?(:acts_as_string?) && result.acts_as_string?
- # hyper-mesh DummyValues respond to acts_as_string, and must
+ if dummy_value?(result)
+ # hyper-mesh DummyValues must
# be converted to spans INSIDE the parent, otherwise the waiting_on_resources
# flag will get set in the wrong context
RenderingContext.render(:span) { result.to_s }
- elsif result.is_a?(String) || (result.is_a?(Hyperstack::Component::Element) && @buffer.empty?)
+ elsif pushable?(result)
@buffer << result
end
- raise_render_error(result) if is_outer_scope && @buffer != [result]
+ buffer_integrity_error if is_outer_scope && @buffer != [result]
+ end
+
+ def dummy_value?(result)
+ result.respond_to?(:loading?) && result.loading?
+ end
+
+ def pushable?(result)
+ # if result is an Element, and buffer is empty then push the Element on, otherwise assume
+ # it has been pushed on already, and the integrity check will confirm
+ return @buffer.empty? if result.is_a?(Hyperstack::Component::Element)
+
+ # check for a common error of saying (for example) DIV (without parens)
+ # which returns the DIV component class instead of a rendered DIV
+ if result.try :hyper_component?
+ improper_render "Instead the component class #{result} was returned.",
+ "Did you mean #{result}()?"
+ end
+
+ # if the buffer is not empty we will only push on strings, and ignore anything else
+ return result.is_a?(String) unless @buffer.empty?
+
+ # if the buffer IS empty then we can push on anything
+ true
end
- # heurestically raise a meaningful error based on the situation
-
- def raise_render_error(result)
- improper_render 'A different element was returned than was generated within the DSL.',
- 'Possibly improper use of Element#delete.' if @buffer.count == 1
- improper_render "Instead #{@buffer.count} elements were generated.",
- 'Do you want to wrap your elements in a div?' if @buffer.count > 1
- improper_render "Instead the component #{result} was returned.",
- "Did you mean #{result}()?" if result.try :hyper_component?
- improper_render "Instead the #{result.class} #{result} was returned.",
- 'You may need to convert this to a string.'
+ def buffer_integrity_error
+ if @buffer.count == 1
+ improper_render "A different element was returned than was generated within the DSL.",
+ "Possibly improper use of Element#delete."
+ else
+ improper_render "Instead #{@buffer.count} elements were generated.",
+ "Do you want to wrap your elements in a div?"
+ end
end
def improper_render(message, solution)
@@ -143,7 +174,7 @@ def improper_render(message, solution)
end
class Object
- [:span, :td, :th].each do |tag|
+ %i[span td th].each do |tag|
define_method(tag) do |*args, &block|
args.unshift(tag)
# legacy hyperloop allowed tags to be lower case as well so if self is a component
@@ -155,21 +186,23 @@ class Object
# in the component.
# If we fully deprecate lowercase tags, then this next line can go...
return send(*args, &block) if respond_to?(:hyper_component?) && hyper_component?
+
Hyperstack::Internal::Component::RenderingContext.render(*args) { to_s }
end
end
-
def para(*args, &block)
args.unshift(:p)
# see above comment
return send(*args, &block) if respond_to?(:hyper_component?) && hyper_component?
+
Hyperstack::Internal::Component::RenderingContext.render(*args) { to_s }
end
def br
# see above comment
return send(:br) if respond_to?(:hyper_component?) && hyper_component?
+
Hyperstack::Internal::Component::RenderingContext.render(:span) do
Hyperstack::Internal::Component::RenderingContext.render(to_s)
Hyperstack::Internal::Component::RenderingContext.render(:br)
diff --git a/ruby/hyper-component/spec/client_features/component_spec.rb b/ruby/hyper-component/spec/client_features/component_spec.rb
index 836501a07..a23db83b3 100644
--- a/ruby/hyper-component/spec/client_features/component_spec.rb
+++ b/ruby/hyper-component/spec/client_features/component_spec.rb
@@ -237,6 +237,26 @@ class Foo < Hyperloop::Component
expect(page).to have_content("paramchildparamchild")
end
+ it "will convert only the final value to a string if the buffer is empty" do
+ mount 'Foo' do
+ class Foo < Hyperloop::Component
+ render { {'foo' => 'bar'} }
+ end
+ end
+ expect(page).to have_content("#{{'foo' => 'bar'}}")
+ end
+
+ it "will convert only the final value to a string if the buffer is empty" do
+ # note that the spec 'can create an element without buffering' effectively
+ # checks other cases where the return value is elements have been rendered to the buffer
+ mount 'Foo' do
+ class Foo < Hyperloop::Component
+ render { DIV { SPAN { 'foo-' }; 'bar' } }
+ end
+ end
+ expect(page).to have_content("foo-bar")
+ end
+
it 'can receive and render a component class' do
mount 'Baz' do
class Bar < Hyperloop::Component
@@ -505,15 +525,6 @@ class Foo
end
describe 'Render Error Handling' do
- it "will generate a message if render returns something other than an Element or a String" do
- mount 'Foo' do
- class Foo < Hyperloop::Component
- render { Hash.new }
- end
- end
- expect(page.driver.browser.manage.logs.get(:browser).map { |m| m.message.gsub(/\\n/, "\n") }.to_a.join("\n"))
- .to match(/You may need to convert this to a string./)
- end
it "will generate a message if render returns a Component class" do
mount 'Foo' do
class Foo < Hyperloop::Component
diff --git a/ruby/hyper-model/spec/test_app/db/schema.rb b/ruby/hyper-model/spec/test_app/db/schema.rb
index 23819ff59..82639473f 100644
--- a/ruby/hyper-model/spec/test_app/db/schema.rb
+++ b/ruby/hyper-model/spec/test_app/db/schema.rb
@@ -46,21 +46,6 @@
t.index ["todo_id"], name: "index_comments_on_todo_id"
end
- create_table "default_tests", force: :cascade do |t|
- t.string "string", default: "I'm a string!"
- t.date "date", default: "2021-02-27"
- t.datetime "datetime", default: "2021-02-27 22:45:41"
- t.integer "integer_from_string", default: 99
- t.integer "integer_from_int", default: 98
- t.float "float_from_string", default: 0.02
- t.float "float_from_float", default: 0.01
- t.boolean "boolean_from_falsy_string", default: false
- t.boolean "boolean_from_truthy_string", default: true
- t.boolean "boolean_from_falsy_value", default: false
- t.json "json", default: {"kind"=>"json"}
- t.jsonb "jsonb", default: {"kind"=>"jsonb"}
- end
-
create_table "hyperstack_connections", force: :cascade do |t|
t.string "channel"
t.string "session"
@@ -111,23 +96,6 @@
t.index ["owner_id"], name: "index_todos_on_owner_id"
end
- create_table "type_tests", force: :cascade do |t|
- t.binary "binary"
- t.boolean "boolean"
- t.date "date"
- t.datetime "datetime"
- t.decimal "decimal", precision: 5, scale: 2
- t.float "float"
- t.integer "integer"
- t.bigint "bigint"
- t.string "string"
- t.text "text"
- t.time "time"
- t.datetime "timestamp"
- t.json "json"
- t.jsonb "jsonb"
- end
-
create_table "users", force: :cascade do |t|
t.string "role"
t.bigint "manager_id"
From e2c2456686236c341defb8ed1d7e970c543c8859 Mon Sep 17 00:00:00 2001
From: R Mitchell VanDuyn
Date: Tue, 9 Mar 2021 20:05:10 -0500
Subject: [PATCH 185/307] closes #158
---
.../internal/component/react_wrapper.rb | 2 +-
.../internal/component/rendering_context.rb | 104 +++++++++---------
.../lib/hyperstack/internal/component/tags.rb | 8 ++
.../spec/active_support_spec.rb | 2 +-
.../spec/client_features/component_spec.rb | 58 ++++++----
.../spec/client_features/dsl_spec.rb | 9 ++
6 files changed, 109 insertions(+), 74 deletions(-)
diff --git a/ruby/hyper-component/lib/hyperstack/internal/component/react_wrapper.rb b/ruby/hyper-component/lib/hyperstack/internal/component/react_wrapper.rb
index ed3026957..768b10273 100644
--- a/ruby/hyper-component/lib/hyperstack/internal/component/react_wrapper.rb
+++ b/ruby/hyper-component/lib/hyperstack/internal/component/react_wrapper.rb
@@ -19,7 +19,7 @@ class ReactWrapper
@@component_classes = {}
def self.stateless?(ncc)
- `typeof #{ncc} === 'function' && !(#{ncc}.prototype && #{ncc}.prototype.isReactComponent)`
+ `typeof #{ncc} === 'symbol' || (typeof #{ncc} === 'function' && !(#{ncc}.prototype && #{ncc}.prototype.isReactComponent))`
end
def self.import_native_component(opal_class, native_class)
diff --git a/ruby/hyper-component/lib/hyperstack/internal/component/rendering_context.rb b/ruby/hyper-component/lib/hyperstack/internal/component/rendering_context.rb
index f6dba2817..9f0125c79 100644
--- a/ruby/hyper-component/lib/hyperstack/internal/component/rendering_context.rb
+++ b/ruby/hyper-component/lib/hyperstack/internal/component/rendering_context.rb
@@ -28,18 +28,27 @@ def render(name, *args, &block)
element = build do
saved_waiting_on_resources = nil #waiting_on_resources what was the purpose of this its used below to or in with the current elements waiting_for_resources
self.waiting_on_resources = nil
- run_child_block(name.nil?, &block)
+ run_child_block(&block)
if name
buffer = @buffer.dup
ReactWrapper.create_element(name, *args) { buffer }.tap do |element|
element.waiting_on_resources = saved_waiting_on_resources || !!buffer.detect { |e| e.waiting_on_resources if e.respond_to?(:waiting_on_resources) }
element.waiting_on_resources ||= waiting_on_resources if buffer.last.is_a?(String)
end
- elsif @buffer.last.is_a? Hyperstack::Component::Element
- @buffer.last.tap { |element| element.waiting_on_resources ||= saved_waiting_on_resources }
else
- buffer_s = @buffer.last.to_s
- RenderingContext.render(:span) { buffer_s }.tap { |element| element.waiting_on_resources = saved_waiting_on_resources }
+ buffer = @buffer.collect do |item|
+ if item.is_a? Hyperstack::Component::Element
+ item.waiting_on_resources ||= saved_waiting_on_resources
+ item
+ else
+ RenderingContext.render(:span) { item.to_s }.tap { |element| element.waiting_on_resources = saved_waiting_on_resources }
+ end
+ end
+ if buffer.length > 1
+ buffer
+ else
+ buffer.first
+ end
end
end
elsif name.is_a? Hyperstack::Component::Element
@@ -65,6 +74,7 @@ def build
def delete(element)
@buffer.delete(element)
+ @last_deleted = element
element
end
alias as_node delete
@@ -86,28 +96,23 @@ def remove_nodes_from_args(args)
end if args[0] && args[0].is_a?(Hash)
end
- # run_child_block gathers the element(s) generated by a child block.
+ # run_child_block yields to the child rendering block which will put any
+ # elements to be rendered into the current rendering buffer.
+ #
# for example when rendering this div: div { "hello".span; "goodby".span }
# two child Elements will be generated.
#
- # the final value of the block should either be
- # 1 a hyper model dummy value that is being loaded,
- # 2 a string (or if the buffer is empty any value to which to_s can be applied)
- # 3 an Element that is NOT yet pushed on the rendering buffer
- # 4 or the last Element pushed on the buffer
+ # However the block itself will return a value, which in some cases should
+ # also added to the buffer:
#
- # in case 1 we render a span wrapping the dummy value
- # in case 2 we automatically push the string onto the buffer
- # in case 3 we also push the Element onto the buffer IF the buffer is empty
- # case 4 requires no special processing
+ # If the final value of the block is a
#
- # Once we have taken care of these special cases we do a check IF we are in an
- # outer rendering scope. In this case react only allows us to generate 1 Element
- # so we insure that is the case, and also check to make sure that element in the buffer
- # is the element returned
- #
- # Note that the reason we only allow Strings to be automatically pushed is to avoid
- # confusing results in situations like this:
+ # a hyper model dummy value that is being loaded, then wrap it in a span and add it to the buffer
+ # a string (or if the buffer is empty any value), then add it to the buffer
+ # an Element, then add it on the buffer unless it has been just deleted
+ # #
+ # Note that the reason we don't always allow Strings to be automatically pushed is
+ # to avoid confusing results in situations like this:
# DIV { collection.each { |item| SPAN { item } } }
# If we accepted any object to be rendered this would generate:
# DIV { SPAN { collection[0] } SPAN { collection[n] } collection.to_s }
@@ -115,57 +120,50 @@ def remove_nodes_from_args(args)
# to the end of the expression, to force it to be added to the output buffer.
#
# However if the buffer is empty then it makes sense to automatically apply the `.to_s`
- # to the value, and push it on the buffer
+ # to the value, and push it on the buffer, unless it is a falsy value or an array
- def run_child_block(is_outer_scope)
+ def run_child_block
result = yield
+ check_for_component_return(result)
if dummy_value?(result)
# hyper-mesh DummyValues must
# be converted to spans INSIDE the parent, otherwise the waiting_on_resources
# flag will get set in the wrong context
RenderingContext.render(:span) { result.to_s }
- elsif pushable?(result)
- @buffer << result
+ elsif result.is_a?(Hyperstack::Component::Element)
+ @buffer << result if @buffer.empty? unless @last_deleted == result
+ elsif pushable_string?(result)
+ @buffer << result.to_s
end
- buffer_integrity_error if is_outer_scope && @buffer != [result]
+ @last_deleted = nil
+ end
+
+ def check_for_component_return(result)
+ # check for a common error of saying (for example) DIV (without parens)
+ # which returns the DIV component class instead of a rendered DIV
+ return unless result.try :hyper_component?
+
+ Hyperstack::Component::IsomorphicHelpers.log(
+ "a component's render method returned the component class #{result}, did you mean to say #{result}()",
+ :warning
+ )
end
def dummy_value?(result)
result.respond_to?(:loading?) && result.loading?
end
- def pushable?(result)
- # if result is an Element, and buffer is empty then push the Element on, otherwise assume
- # it has been pushed on already, and the integrity check will confirm
- return @buffer.empty? if result.is_a?(Hyperstack::Component::Element)
-
- # check for a common error of saying (for example) DIV (without parens)
- # which returns the DIV component class instead of a rendered DIV
- if result.try :hyper_component?
- improper_render "Instead the component class #{result} was returned.",
- "Did you mean #{result}()?"
- end
-
+ def pushable_string?(result)
# if the buffer is not empty we will only push on strings, and ignore anything else
return result.is_a?(String) unless @buffer.empty?
- # if the buffer IS empty then we can push on anything
- true
- end
-
- def buffer_integrity_error
- if @buffer.count == 1
- improper_render "A different element was returned than was generated within the DSL.",
- "Possibly improper use of Element#delete."
- else
- improper_render "Instead #{@buffer.count} elements were generated.",
- "Do you want to wrap your elements in a div?"
- end
+ # if the buffer IS empty then we can push on anything except we avoid nil, false and arrays
+ # as these are almost never what you want to render, and if you do there are mechanisms
+ # to render them explicitly
+ result && result.respond_to?(:to_n) && !result.is_a?(Array)
end
def improper_render(message, solution)
- raise "a component's render method must generate and return exactly 1 element or a string.\n"\
- " #{message} #{solution}"
end
end
end
diff --git a/ruby/hyper-component/lib/hyperstack/internal/component/tags.rb b/ruby/hyper-component/lib/hyperstack/internal/component/tags.rb
index c8e010a08..62314587d 100644
--- a/ruby/hyper-component/lib/hyperstack/internal/component/tags.rb
+++ b/ruby/hyper-component/lib/hyperstack/internal/component/tags.rb
@@ -32,6 +32,14 @@ module Tags
const_set tag.upcase, tag
end
+ const_set "FRAGMENT", (
+ Class.new do
+ include Hyperstack::Component
+ render {}
+ Hyperstack::Internal::Component::ReactWrapper.import_native_component(self, `React.Fragment`)
+ end
+ )
+
# this is used for haml style (i.e. DIV.foo.bar) class tags which is deprecated
def self.html_tag_class_for(tag)
downcased_tag = tag.downcase
diff --git a/ruby/hyper-component/spec/active_support_spec.rb b/ruby/hyper-component/spec/active_support_spec.rb
index 04ca6f3ec..8d0546730 100644
--- a/ruby/hyper-component/spec/active_support_spec.rb
+++ b/ruby/hyper-component/spec/active_support_spec.rb
@@ -51,7 +51,7 @@ def numbers
expect_evaluate_ruby do
odd_numbers = numbers.extract! { |number| number.odd? }
end.to eq [1, 3, 5, 7, 9]
- expect_evaluate_ruby do
+ expect_evaluate_ruby do
numbers.extract! { |number| number.odd? }
numbers
end.to eq [0, 2, 4, 6, 8]
diff --git a/ruby/hyper-component/spec/client_features/component_spec.rb b/ruby/hyper-component/spec/client_features/component_spec.rb
index a23db83b3..17d51a30d 100644
--- a/ruby/hyper-component/spec/client_features/component_spec.rb
+++ b/ruby/hyper-component/spec/client_features/component_spec.rb
@@ -208,6 +208,44 @@ class << self
expect_evaluate_ruby('Foo.instance == Foo.instance.force_update!').to be_truthy
end
+ it "can generate multiple elements on outer render using FRAGMENT" do
+ mount 'Foo' do
+ class Foo < Hyperloop::Component
+ render(FRAGMENT) do
+ UL do
+ SomeLIs()
+ LI { "the end" }
+ end
+ "random string at the end"
+ end
+ end
+ class SomeLIs < Hyperloop::Component
+ render(FRAGMENT) { LI { "hello" }; LI { "goodby" } }
+ end
+ end
+ expect(page.find('ul').all('li').collect(&:text)).to eq(['hello', 'goodby', 'the end'])
+ expect(page.find('div').text).to end_with("random string at the end")
+ end
+
+ it "can generate multiple elements on outer render by returning arrays" do
+ mount 'Foo' do
+ class Foo < Hyperloop::Component
+ render do
+ UL(key: 1) do
+ SomeLIs()
+ LI(key: 3) { "the end" }
+ end
+ "random string at the end".span(key: 2)
+ end
+ end
+ class SomeLIs < Hyperloop::Component
+ render { LI(key: 1) { "hello" }; LI(key: 2) { "goodby" } }
+ end
+ end
+ expect(page.find('ul').all('li').collect(&:text)).to eq(['hello', 'goodby', 'the end'])
+ expect(page.find('div').text).to end_with("random string at the end")
+ end
+
it 'can buffer an element' do
mount 'Foo' do
class Bar < Hyperloop::Component
@@ -532,25 +570,7 @@ class Foo < Hyperloop::Component
end
end
expect(page.driver.browser.manage.logs.get(:browser).map { |m| m.message.gsub(/\\n/, "\n") }.to_a.join("\n"))
- .to match(/Did you mean Foo()/)
- end
- it "will generate a message if more than 1 element is generated" do
- mount 'Foo' do
- class Foo < Hyperloop::Component
- render { "hello".span; "goodby".span }
- end
- end
- expect(page.driver.browser.manage.logs.get(:browser).map { |m| m.message.gsub(/\\n/, "\n") }.to_a.join("\n"))
- .to match(/Do you want to wrap your elements in a div?/)
- end
- it "will generate a message if the element generated is not the element returned" do
- mount 'Foo' do
- class Foo < Hyperloop::Component
- render { "hello".span; "goodby".span.delete }
- end
- end
- expect(page.driver.browser.manage.logs.get(:browser).map { |m| m.message.gsub(/\\n/, "\n") }.to_a.join("\n"))
- .to match(/Possibly improper use of Element#delete./)
+ .to match(/did you mean to say Foo()/)
end
end
diff --git a/ruby/hyper-component/spec/client_features/dsl_spec.rb b/ruby/hyper-component/spec/client_features/dsl_spec.rb
index 16c996d21..50836cca7 100644
--- a/ruby/hyper-component/spec/client_features/dsl_spec.rb
+++ b/ruby/hyper-component/spec/client_features/dsl_spec.rb
@@ -250,6 +250,15 @@ class Foo
expect(page.body[-80..-19]).to include('Hyperstack::Component::Element')
end
+ it "the delete method (alias as_node) removes the node from the render buffer" do
+ mount 'Foo' do
+ class Foo < Hyperloop::Component
+ render { "hello".span; "goodby".span.delete }
+ end
+ end
+ expect(find('span').text).to eq('hello')
+ end
+
it "has a dom_node method" do
mount 'Foo' do
class Foo
From eff57d8ce3126eddaf4791ff8d074b73ded490e4 Mon Sep 17 00:00:00 2001
From: catmando
Date: Wed, 10 Mar 2021 14:39:43 -0500
Subject: [PATCH 186/307] closes #373
---
.../lib/hyperstack/component.rb | 31 +++++++--
.../internal/component/react_wrapper.rb | 10 +--
.../spec/client_features/component_spec.rb | 2 +-
.../spec/deprecation_notices/render.rb | 18 ------
.../spec/deprecation_notices/render_spec.rb | 64 +++++++++++++++++++
.../batch3/has_and_belongs_to_many_spec.rb | 2 +-
.../lib/hyperstack/internal/callbacks.rb | 2 +-
7 files changed, 98 insertions(+), 31 deletions(-)
delete mode 100644 ruby/hyper-component/spec/deprecation_notices/render.rb
create mode 100644 ruby/hyper-component/spec/deprecation_notices/render_spec.rb
diff --git a/ruby/hyper-component/lib/hyperstack/component.rb b/ruby/hyper-component/lib/hyperstack/component.rb
index 40eb43879..6eb000e83 100644
--- a/ruby/hyper-component/lib/hyperstack/component.rb
+++ b/ruby/hyper-component/lib/hyperstack/component.rb
@@ -21,13 +21,22 @@ def self.included(base)
class_attribute :initial_state
define_callback :before_mount
define_callback :after_mount
- define_callback :before_new_params
- define_callback :before_update
+ define_callback :before_new_params do |klass|
+ klass.deprecation_warning "`before_new_params` has been deprecated. "\
+ "The base method componentWillReceiveProps is deprecated in React without replacement"
+ end
+ define_callback(:before_update) do |klass, *args, &block|
+ [*args, *block].detect do |method|
+ method = klass.instance_method(method) unless method.is_a?(Proc)
+ next if method.arity.zero?
+
+ klass.deprecation_warning "In the future before_update callbacks will not receive any parameters."
+ end
+ end
define_callback :after_update
define_callback :__hyperstack_component_after_render_hook
define_callback :__hyperstack_component_rescue_hook
- #define_callback :before_unmount defined already by Async module
- define_callback(:after_error) { Hyperstack::Internal::Component::ReactWrapper.add_after_error_hook(base) }
+ define_callback(:after_error) { |klass| Hyperstack::Internal::Component::ReactWrapper.add_after_error_hook(klass) }
end
base.extend(Hyperstack::Internal::Component::ClassMethods)
unless `Opal.__hyperstack_component_original_defn`
@@ -168,10 +177,22 @@ def __hyperstack_component_run_post_render_hooks(element)
run_callback(:__hyperstack_component_after_render_hook, element) { |*args| args }.first
end
+ def _run_before_render_callbacks
+ # eventually add before_update if @__component_mounted
+ # but that will not perfectly match the current React behavior.
+ # However that behavior is deprecated, and so once we have
+ # given a chance for the code to be updated we can switch this over
+ # and switch the deprecation notice to an error.
+ component_will_mount unless @__component_mounted
+ @__component_mounted = true
+ end
+
+
def _render_wrapper
+ _run_before_render_callbacks
observing(rendering: true) do
element = Hyperstack::Internal::Component::RenderingContext.render(nil) do
- render || ''
+ render || ""
end
@__hyperstack_component_waiting_on_resources =
element.waiting_on_resources if element.respond_to? :waiting_on_resources
diff --git a/ruby/hyper-component/lib/hyperstack/internal/component/react_wrapper.rb b/ruby/hyper-component/lib/hyperstack/internal/component/react_wrapper.rb
index 768b10273..4a8c30612 100644
--- a/ruby/hyper-component/lib/hyperstack/internal/component/react_wrapper.rb
+++ b/ruby/hyper-component/lib/hyperstack/internal/component/react_wrapper.rb
@@ -66,9 +66,9 @@ def self.add_after_error_hook_to_native(native_comp)
def self.create_native_react_class(type)
raise "createReactClass is undefined. Add the 'react-create-class' npm module, and import it as 'createReactClass'" if `typeof(createReactClass)=='undefined'`
raise "Provided class should define `render` method" if !(type.method_defined? :render)
- render_fn = (type.method_defined? :_render_wrapper) ? :_render_wrapper : :render
+ old_school = !type.method_defined?(:_render_wrapper)
+ render_fn = old_school ? :render : :_render_wrapper
# this was hashing type.to_s, not sure why but .to_s does not work as it Foo::Bar::View.to_s just returns "View"
-
@@component_classes[type] ||= begin
comp = %x{
createReactClass({
@@ -88,7 +88,7 @@ def self.create_native_react_class(type)
return #{type.respond_to?(:default_props) ? type.default_props.to_n : `{}`};
},
propTypes: #{type.respond_to?(:prop_types) ? type.prop_types.to_n : `{}`},
- componentWillMount: function() {
+ componentWillMount: old_school && function() {
if (#{type.method_defined? :component_will_mount}) {
this.__opalInstanceSyncSetState = true;
this.__opalInstance.$component_will_mount();
@@ -102,7 +102,7 @@ def self.create_native_react_class(type)
this.__opalInstance.$component_did_mount();
}
},
- componentWillReceiveProps: function(next_props) {
+ UNSAFE_componentWillReceiveProps: function(next_props) {
if (#{type.method_defined? :component_will_receive_props}) {
this.__opalInstanceSyncSetState = true;
this.__opalInstance.$component_will_receive_props(Opal.Hash.$new(next_props));
@@ -115,7 +115,7 @@ def self.create_native_react_class(type)
return this.__opalInstance["$should_component_update?"](Opal.Hash.$new(next_props), Opal.Hash.$new(next_state));
} else { return true; }
},
- componentWillUpdate: function(next_props, next_state) {
+ UNSAFE_componentWillUpdate: function(next_props, next_state) {
if (#{type.method_defined? :component_will_update}) {
this.__opalInstanceSyncSetState = false;
this.__opalInstance.$component_will_update(Opal.Hash.$new(next_props), Opal.Hash.$new(next_state));
diff --git a/ruby/hyper-component/spec/client_features/component_spec.rb b/ruby/hyper-component/spec/client_features/component_spec.rb
index 17d51a30d..251d806df 100644
--- a/ruby/hyper-component/spec/client_features/component_spec.rb
+++ b/ruby/hyper-component/spec/client_features/component_spec.rb
@@ -122,7 +122,7 @@ class Foo
mount 'Foo' do
class Foo
include Hyperstack::Component
- before_mount { @count = 0}
+ before_mount { @count = 0 }
after_render do
@count += 1
after(0) { force_update! } if @count <= 2
diff --git a/ruby/hyper-component/spec/deprecation_notices/render.rb b/ruby/hyper-component/spec/deprecation_notices/render.rb
deleted file mode 100644
index de0cc912a..000000000
--- a/ruby/hyper-component/spec/deprecation_notices/render.rb
+++ /dev/null
@@ -1,18 +0,0 @@
-require 'spec_helper'
-
-describe 'Deprecation Notices', js: true do
-
- it "using `defx render` will give a deprecation notice, but still allow render to work" do
- mount "TestComp" do
- class TestComp < HyperComponent
- def render
- 'hello'
- end
- end
- end
- expect(page).to have_content('hello')
- expect_evaluate_ruby("Hyperstack.instance_variable_get('@deprecation_messages')").to eq(
- ["Warning: Deprecated feature used in TestComp. Do not directly define the render method. Use the render macro instead."]
- )
- end
-end
diff --git a/ruby/hyper-component/spec/deprecation_notices/render_spec.rb b/ruby/hyper-component/spec/deprecation_notices/render_spec.rb
new file mode 100644
index 000000000..312883501
--- /dev/null
+++ b/ruby/hyper-component/spec/deprecation_notices/render_spec.rb
@@ -0,0 +1,64 @@
+require 'spec_helper'
+
+describe 'Deprecation Notices', js: true do
+
+ it "using `def render` will give a deprecation notice, but still allow render to work" do
+ mount "TestComp" do
+ class TestComp < HyperComponent
+ def render
+ 'hello'
+ end
+ end
+ end
+ expect(page).to have_content('hello')
+ expect_evaluate_ruby("Hyperstack.instance_variable_get('@deprecation_messages')").to eq(
+ ["Warning: Deprecated feature used in TestComp. Do not directly define the render method. Use the render macro instead."]
+ )
+ end
+
+ it "when using before_new_params" do
+ mount "TestComp" do
+ class TestComp < HyperComponent
+ before_new_params { 'bingo' }
+ render { 'hello' }
+ end
+ end
+ expect(page).to have_content('hello')
+ expect_evaluate_ruby("Hyperstack.instance_variable_get('@deprecation_messages')").to eq(
+ ["Warning: Deprecated feature used in TestComp. `before_new_params` has been deprecated. "\
+ "The base method componentWillReceiveProps is deprecated in React without replacement"
+ ]
+ )
+ end
+
+ context "when params are expected in the before_update callback" do
+ it "when providing a block" do
+ mount "TestComp" do
+ class TestComp < HyperComponent
+ before_update { |x, y| }
+ render { 'hello' }
+ end
+ end
+ expect(page).to have_content('hello')
+ expect_evaluate_ruby("Hyperstack.instance_variable_get('@deprecation_messages')").to eq(
+ ["Warning: Deprecated feature used in TestComp. In the future before_update callbacks will not receive any parameters."]
+ )
+ end
+
+ it "when providing a method name" do
+ mount "TestComp" do
+ class TestComp < HyperComponent
+ def foo(x, y)
+ end
+ before_update :foo
+ render { 'hello' }
+ end
+ end
+ expect(page).to have_content('hello')
+ expect_evaluate_ruby("Hyperstack.instance_variable_get('@deprecation_messages')").to eq(
+ ["Warning: Deprecated feature used in TestComp. In the future before_update callbacks will not receive any parameters."]
+ )
+ end
+ end
+
+end
diff --git a/ruby/hyper-model/spec/batch3/has_and_belongs_to_many_spec.rb b/ruby/hyper-model/spec/batch3/has_and_belongs_to_many_spec.rb
index f5671dcbe..9667387ab 100644
--- a/ruby/hyper-model/spec/batch3/has_and_belongs_to_many_spec.rb
+++ b/ruby/hyper-model/spec/batch3/has_and_belongs_to_many_spec.rb
@@ -88,7 +88,7 @@ class Patient < ActiveRecord::Base
expect { Physician.first.patients.count }.on_client_to eq(1)
Patient.create(name: 'Spock').physicians << mccoy
- expect { Physician.first.patients.count }.on_client_to eq(2)
+ expect { Physician.first.patients.count }.on_client_to eq(2) # this line fails intermittently with == 3!
on_client { Patient.create(name: 'Uhuru') }
2.times do
diff --git a/ruby/hyper-state/lib/hyperstack/internal/callbacks.rb b/ruby/hyper-state/lib/hyperstack/internal/callbacks.rb
index 4e77b346a..f7062c5df 100644
--- a/ruby/hyper-state/lib/hyperstack/internal/callbacks.rb
+++ b/ruby/hyper-state/lib/hyperstack/internal/callbacks.rb
@@ -34,7 +34,7 @@ def define_callback(callback_name, &after_define_hook)
Hotloader.when_file_updates do
send(wrapper_name).delete_if { |item| item.equal? args }
end
- after_define_hook.call(*args, &block) if after_define_hook
+ after_define_hook.call(self, *args, &block) if after_define_hook
end
end
From 566a06b51e986812520c795c96b34f40b291b48c Mon Sep 17 00:00:00 2001
From: catmando
Date: Thu, 11 Mar 2021 02:04:19 -0500
Subject: [PATCH 187/307] closes #375
---
ruby/hyper-model/lib/active_record_base.rb | 10 +++
.../reactive_record/collection.rb | 47 +++++++++-----
.../reactive_record/operations.rb | 6 ++
.../lib/reactive_record/broadcast.rb | 5 +-
.../spec/batch3/aaa_edge_cases_spec.rb | 65 +++++++++++++++++++
5 files changed, 117 insertions(+), 16 deletions(-)
diff --git a/ruby/hyper-model/lib/active_record_base.rb b/ruby/hyper-model/lib/active_record_base.rb
index 373d842cd..85e8b08c0 100644
--- a/ruby/hyper-model/lib/active_record_base.rb
+++ b/ruby/hyper-model/lib/active_record_base.rb
@@ -321,6 +321,16 @@ def do_not_synchronize?
self.class.do_not_synchronize?
end
+ before_create :synchromesh_mark_update_time
+ before_update :synchromesh_mark_update_time
+ before_destroy :synchromesh_mark_update_time
+
+ attr_reader :__synchromesh_update_time
+
+ def synchromesh_mark_update_time
+ @__synchromesh_update_time = Time.now.to_f
+ end
+
after_commit :synchromesh_after_create, on: [:create]
after_commit :synchromesh_after_change, on: [:update]
after_commit :synchromesh_after_destroy, on: [:destroy]
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/collection.rb b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/collection.rb
index 27f30b903..b0262fbcf 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/collection.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/collection.rb
@@ -141,8 +141,10 @@ class TestModel < ApplicationRecord
=end
+ attr_accessor :broadcast_updated_at
def sync_scopes(broadcast)
+ self.broadcast_updated_at = broadcast.updated_at
# record_with_current_values will return nil if data between
# the broadcast record and the value on the client is out of sync
# not running set_pre_sync_related_records will cause sync scopes
@@ -160,6 +162,8 @@ def sync_scopes(broadcast)
)
record.backing_record.sync_unscoped_collection! if record.destroyed? || broadcast.new?
end
+ ensure
+ self.broadcast_updated_at = nil
end
def apply_to_all_collections(method, record, dont_gather)
@@ -353,6 +357,7 @@ def count_state=(val)
unless ReactiveRecord::WhileLoading.observed?
Hyperstack::Internal::State::Variable.set(self, :collection, collection, true)
end
+ @count_updated_at = ReactiveRecord::Operations::Base.last_response_sent_at
@count = val
end
@@ -462,16 +467,18 @@ def push(item)
alias << push
def _internal_push(item)
- item.itself # force get of at least the id
- if collection
- self.force_push item
- else
- unsaved_children << item
- update_child(item)
- @owner.backing_record.sync_has_many(@association.attribute) if @owner && @association
- if !@count.nil?
- @count += item.destroyed? ? -1 : 1
- notify_of_change self
+ insure_sync do
+ item.itself # force get of at least the id
+ if collection
+ self.force_push item
+ else
+ unsaved_children << item
+ update_child(item)
+ @owner.backing_record.sync_has_many(@association.attribute) if @owner && @association
+ if !@count.nil?
+ @count += (item.destroyed? ? -1 : 1)
+ notify_of_change self
+ end
end
end
self
@@ -588,15 +595,25 @@ def destroy(item)
join_record&.destroy
end
+ def insure_sync
+ if Collection.broadcast_updated_at && @count_updated_at && Collection.broadcast_updated_at < @count_updated_at
+ reload_from_db
+ else
+ yield
+ end
+ end
+
alias delete destroy
def delete_internal(item)
- if collection
- all.delete(item)
- elsif !@count.nil?
- @count -= 1
+ insure_sync do
+ if collection
+ all.delete(item)
+ elsif !@count.nil?
+ @count -= 1
+ end
+ yield if block_given? # was yield item, but item is not used
end
- yield if block_given? # was yield item, but item is not used
item
end
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/operations.rb b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/operations.rb
index 3b1f73c87..65b7072ab 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/operations.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/operations.rb
@@ -12,6 +12,10 @@ class Base < Hyperstack::ControllerOp
FORMAT = '0x%x'
+ class << self
+ attr_accessor :last_response_sent_at
+ end
+
def self.serialize_params(hash)
hash['associations'].each do |assoc|
assoc['parent_id'] = FORMAT % assoc['parent_id']
@@ -38,6 +42,7 @@ def self.serialize_response(response)
response[:saved_models].each do |saved_model|
saved_model[0] = FORMAT % saved_model[0]
end if response.is_a?(Hash) && response[:saved_models]
+ response[:sent_at] = Time.now.to_f
response
end
@@ -45,6 +50,7 @@ def self.deserialize_response(response)
response[:saved_models].each do |saved_model|
saved_model[0] = saved_model[0].to_i(16)
end if response.is_a?(Hash) && response[:saved_models]
+ Base.last_response_sent_at = response.delete(:sent_at)
response
end
end
diff --git a/ruby/hyper-model/lib/reactive_record/broadcast.rb b/ruby/hyper-model/lib/reactive_record/broadcast.rb
index 944fd7a51..5c554efb1 100644
--- a/ruby/hyper-model/lib/reactive_record/broadcast.rb
+++ b/ruby/hyper-model/lib/reactive_record/broadcast.rb
@@ -11,7 +11,7 @@ def self.after_commit(operation, model)
if !Hyperstack.on_server? && Hyperstack::Connection.root_path
send_to_server(operation, data) rescue nil # fails if server no longer running so ignore
else
- SendPacket.run(data, operation: operation)
+ SendPacket.run(data, operation: operation, updated_at: model.__synchromesh_update_time)
end
end
rescue ActiveRecord::StatementInvalid => e
@@ -47,6 +47,7 @@ class SendPacket < Hyperstack::ServerOp
param :record
param :operation
param :previous_changes
+ param :updated_at
unless RUBY_ENGINE == 'opal'
validate do
@@ -130,6 +131,7 @@ def to_s
# private
attr_reader :record
+ attr_reader :updated_at
def self.open_channels
@open_channels ||= Set.new
@@ -167,6 +169,7 @@ def receive(params)
@klass ||= params.klass
@record.merge! params.record
@previous_changes.merge! params.previous_changes
+ @updated_at = params.updated_at
ReactiveRecord::Base.when_not_saving(klass) do
@backing_record = ReactiveRecord::Base.exists?(klass, params.record[klass.primary_key])
diff --git a/ruby/hyper-model/spec/batch3/aaa_edge_cases_spec.rb b/ruby/hyper-model/spec/batch3/aaa_edge_cases_spec.rb
index 768adce75..2bca9ba51 100644
--- a/ruby/hyper-model/spec/batch3/aaa_edge_cases_spec.rb
+++ b/ruby/hyper-model/spec/batch3/aaa_edge_cases_spec.rb
@@ -143,6 +143,71 @@ class TestComponent77 < HyperComponent
end.to be_nil
end
+ it "will reload scopes when data arrives too late" do
+ class ActiveRecord::Base
+ class << self
+ def public_columns_hash
+ @public_columns_hash ||= {}
+ end
+ end
+ end
+
+ class BelongsToModel < ActiveRecord::Base
+ def self.build_tables
+ connection.create_table :belongs_to_models, force: true do |t|
+ t.string :name
+ t.belongs_to :has_many_model
+ t.timestamps
+ end
+ ActiveRecord::Base.public_columns_hash[name] = columns_hash
+ end
+ end
+
+ class HasManyModel < ActiveRecord::Base
+ def self.build_tables
+ connection.create_table :has_many_models, force: true do |t|
+ t.string :name
+ t.timestamps
+ end
+ ActiveRecord::Base.public_columns_hash[name] = columns_hash
+ end
+ end
+
+ BelongsToModel.build_tables #rescue nil
+ HasManyModel.build_tables #rescue nil
+
+ isomorphic do
+ class BelongsToModel < ActiveRecord::Base
+ belongs_to :has_many_model
+ end
+
+ class HasManyModel < ActiveRecord::Base
+ has_many :belongs_to_models
+ end
+ end
+
+ class HasManyModel < ActiveRecord::Base
+ def belongs_to_models
+ sleep 0.3 if name == "sleepy-time"
+ super
+ end
+ end
+
+ class ActiveRecord::Base
+ alias orig_synchromesh_after_create synchromesh_after_create
+ def synchromesh_after_create
+ sleep 0.4 if try(:name) == "sleepy-time"
+ orig_synchromesh_after_create
+ end
+ end
+
+ has_many1 = HasManyModel.create(name: "has_many1")
+ 2.times { |i| BelongsToModel.create(name: "belongs_to_#{i}", has_many_model: has_many1) }
+ expect { HasManyModel.first.belongs_to_models.count }.on_client_to eq(1)
+ BelongsToModel.create(name: "sleepy-time", has_many_model: has_many1)
+ expect { Hyperstack::Model.load { HasManyModel.first.belongs_to_models.count } }.on_client_to eq(3)
+ end
+
describe 'can use finder methods on scopes' do
before(:each) do
From 5dcc6814b82f3ef81dde293d40b44f65ca91897d Mon Sep 17 00:00:00 2001
From: catmando
Date: Thu, 11 Mar 2021 09:23:38 -0500
Subject: [PATCH 188/307] spec was missing Model.load causing race
---
ruby/hyper-model/spec/batch3/has_and_belongs_to_many_spec.rb | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/ruby/hyper-model/spec/batch3/has_and_belongs_to_many_spec.rb b/ruby/hyper-model/spec/batch3/has_and_belongs_to_many_spec.rb
index 9667387ab..ad9f315ab 100644
--- a/ruby/hyper-model/spec/batch3/has_and_belongs_to_many_spec.rb
+++ b/ruby/hyper-model/spec/batch3/has_and_belongs_to_many_spec.rb
@@ -88,7 +88,7 @@ class Patient < ActiveRecord::Base
expect { Physician.first.patients.count }.on_client_to eq(1)
Patient.create(name: 'Spock').physicians << mccoy
- expect { Physician.first.patients.count }.on_client_to eq(2) # this line fails intermittently with == 3!
+ expect { Hyperstack::Model.load { Physician.first.patients.count } }.on_client_to eq(2)
on_client { Patient.create(name: 'Uhuru') }
2.times do
From f86dd19829045d4a60d07cbb657de97070b8b472 Mon Sep 17 00:00:00 2001
From: catmando
Date: Thu, 11 Mar 2021 10:31:04 -0500
Subject: [PATCH 189/307] arity check on for all gems
---
.../spec/test_app/config/application.rb | 2 +-
ruby/hyper-i18n/spec/test_app/config/application.rb | 1 +
ruby/hyper-model/spec/test_app/config/application.rb | 2 +-
.../spec/test_app/config/application.rb | 2 +-
.../lib/hyperstack/internal/router/helpers.rb | 10 +++++-----
ruby/hyper-router/spec/test_app/config/application.rb | 1 +
ruby/hyper-spec/spec/test_app/config/application.rb | 2 +-
ruby/hyper-state/spec/test_app/config/application.rb | 1 +
.../spec/test_app/config/application.rb | 1 +
9 files changed, 13 insertions(+), 9 deletions(-)
diff --git a/ruby/hyper-component/spec/test_app/config/application.rb b/ruby/hyper-component/spec/test_app/config/application.rb
index b8866a00e..8ce8665a8 100644
--- a/ruby/hyper-component/spec/test_app/config/application.rb
+++ b/ruby/hyper-component/spec/test_app/config/application.rb
@@ -19,7 +19,7 @@ module TestApp
class Application < Rails::Application
config.opal.method_missing = true
config.opal.optimized_operators = true
- config.opal.arity_check = false
+ config.opal.arity_check = true
config.opal.const_missing = true
config.opal.dynamic_require_severity = :ignore
config.opal.enable_specs = true
diff --git a/ruby/hyper-i18n/spec/test_app/config/application.rb b/ruby/hyper-i18n/spec/test_app/config/application.rb
index 9c6e80a28..525527648 100644
--- a/ruby/hyper-i18n/spec/test_app/config/application.rb
+++ b/ruby/hyper-i18n/spec/test_app/config/application.rb
@@ -6,6 +6,7 @@
Bundler.require(*Rails.groups(assets: %w(development test)))
module TestApp
class Application < Rails::Application
+ config.opal.arity_check_enabled = true
# Settings in config/environments/* take precedence over those specified here.
# Application configuration should go into files in config/initializers
# -- all .rb files in that directory are automatically loaded.
diff --git a/ruby/hyper-model/spec/test_app/config/application.rb b/ruby/hyper-model/spec/test_app/config/application.rb
index 864804bf0..c3c7f580a 100644
--- a/ruby/hyper-model/spec/test_app/config/application.rb
+++ b/ruby/hyper-model/spec/test_app/config/application.rb
@@ -17,7 +17,7 @@ class Application < Rails::Application
config.assets.paths << ::Rails.root.join('app', 'models').to_s
config.opal.method_missing = true
config.opal.optimized_operators = true
- config.opal.arity_check_enabled = false
+ config.opal.arity_check_enabled = true
config.opal.const_missing = true
config.opal.dynamic_require_severity = :ignore
config.opal.enable_specs = true
diff --git a/ruby/hyper-operation/spec/test_app/config/application.rb b/ruby/hyper-operation/spec/test_app/config/application.rb
index 266fdf6c0..0dcdf77e3 100644
--- a/ruby/hyper-operation/spec/test_app/config/application.rb
+++ b/ruby/hyper-operation/spec/test_app/config/application.rb
@@ -17,7 +17,7 @@ class Application < Rails::Application
config.assets.paths << ::Rails.root.join('app', 'models').to_s
config.opal.method_missing = true
config.opal.optimized_operators = true
- config.opal.arity_check = false
+ config.opal.arity_check = true
config.opal.const_missing = true
config.opal.dynamic_require_severity = :ignore
config.opal.enable_specs = true
diff --git a/ruby/hyper-router/lib/hyperstack/internal/router/helpers.rb b/ruby/hyper-router/lib/hyperstack/internal/router/helpers.rb
index b8874955c..c2c1b71d3 100644
--- a/ruby/hyper-router/lib/hyperstack/internal/router/helpers.rb
+++ b/ruby/hyper-router/lib/hyperstack/internal/router/helpers.rb
@@ -31,7 +31,7 @@ def Redirect(to, opts = {})
React::Router::Redirect(opts)
end
- def format_params(e)
+ def format_params(e, *)
{
match: Hyperstack::Router::Match.new(`#{e}.match`),
location: Hyperstack::Router::Location.new(`#{e}.location`),
@@ -47,16 +47,16 @@ def Route(to, opts = {}, &block)
if opts[:mounts]
component = opts.delete(:mounts)
- opts[:component] = lambda do |e|
- route_params = format_params(e)
+ opts[:component] = lambda do |*e|
+ route_params = format_params(*e)
Hyperstack::Component::ReactAPI.create_element(component, route_params).to_n
end
end
if block
- opts[:render] = lambda do |e|
- route_params = format_params(e)
+ opts[:render] = lambda do |*e|
+ route_params = format_params(*e)
yield(*route_params.values).to_n
end
diff --git a/ruby/hyper-router/spec/test_app/config/application.rb b/ruby/hyper-router/spec/test_app/config/application.rb
index 179355aa7..a3ff759e6 100644
--- a/ruby/hyper-router/spec/test_app/config/application.rb
+++ b/ruby/hyper-router/spec/test_app/config/application.rb
@@ -14,6 +14,7 @@
module TestApp
class Application < Rails::Application
+ config.opal.arity_check_enabled = true
# config.opal.method_missing = true
# config.opal.optimized_operators = true
# config.opal.arity_check = false
diff --git a/ruby/hyper-spec/spec/test_app/config/application.rb b/ruby/hyper-spec/spec/test_app/config/application.rb
index 6c87017c3..732a9aeba 100644
--- a/ruby/hyper-spec/spec/test_app/config/application.rb
+++ b/ruby/hyper-spec/spec/test_app/config/application.rb
@@ -26,7 +26,7 @@ class Application < Rails::Application
config.assets.paths << ::Rails.root.join('app', 'models').to_s
config.opal.method_missing = true
config.opal.optimized_operators = true
- config.opal.arity_check = false
+ config.opal.arity_check = true
config.opal.const_missing = true
config.opal.dynamic_require_severity = :ignore
config.opal.enable_specs = true
diff --git a/ruby/hyper-state/spec/test_app/config/application.rb b/ruby/hyper-state/spec/test_app/config/application.rb
index 3e63522da..43f4c8d39 100644
--- a/ruby/hyper-state/spec/test_app/config/application.rb
+++ b/ruby/hyper-state/spec/test_app/config/application.rb
@@ -10,6 +10,7 @@
module TestApp
class Application < Rails::Application
+ config.opal.arity_check_enabled = true
# Settings in config/environments/* take precedence over those specified here.
# Application configuration should go into files in config/initializers
# -- all .rb files in that directory are automatically loaded.
diff --git a/ruby/hyperstack-config/spec/test_app/config/application.rb b/ruby/hyperstack-config/spec/test_app/config/application.rb
index 4d3cbf81e..f59d088bc 100644
--- a/ruby/hyperstack-config/spec/test_app/config/application.rb
+++ b/ruby/hyperstack-config/spec/test_app/config/application.rb
@@ -7,6 +7,7 @@
module TestApp
class Application < Rails::Application
+ config.opal.arity_check_enabled = true
# Settings in config/environments/* take precedence over those specified here.
# Application configuration should go into files in config/initializers
# -- all .rb files in that directory are automatically loaded.
From 5056ff72bb050477ee9d937593cd62dea0ba2923 Mon Sep 17 00:00:00 2001
From: catmando
Date: Thu, 11 Mar 2021 14:27:58 -0500
Subject: [PATCH 190/307] arity fixes
---
.../lib/hyperstack/component.rb | 27 ++++++++++++-------
.../component/isomorphic_helpers.rb | 1 -
.../spec/deprecation_notices/render_spec.rb | 6 +++++
.../hyperstack/components/no_params_please.rb | 8 ++++++
.../spec/test_app/config/application.rb | 2 +-
.../active_record/reactive_record/base.rb | 3 +--
.../reactive_record/dummy_value.rb | 4 +--
.../reactive_record/while_loading.rb | 2 +-
.../spec/batch4/default_value_spec.rb | 2 +-
.../spec/test_app/config/application.rb | 2 +-
.../lib/hyper-spec/internal/patches.rb | 4 +--
.../spec/test_app/config/application.rb | 2 +-
12 files changed, 42 insertions(+), 21 deletions(-)
create mode 100644 ruby/hyper-component/spec/test_app/app/hyperstack/components/no_params_please.rb
diff --git a/ruby/hyper-component/lib/hyperstack/component.rb b/ruby/hyper-component/lib/hyperstack/component.rb
index 6eb000e83..c86309198 100644
--- a/ruby/hyper-component/lib/hyperstack/component.rb
+++ b/ruby/hyper-component/lib/hyperstack/component.rb
@@ -25,18 +25,24 @@ def self.included(base)
klass.deprecation_warning "`before_new_params` has been deprecated. "\
"The base method componentWillReceiveProps is deprecated in React without replacement"
end
- define_callback(:before_update) do |klass, *args, &block|
- [*args, *block].detect do |method|
- method = klass.instance_method(method) unless method.is_a?(Proc)
- next if method.arity.zero?
-
- klass.deprecation_warning "In the future before_update callbacks will not receive any parameters."
- end
- end
+ define_callback(:__hyperstack_deprecated_before_update)
+ define_callback(:__hyperstack_new_style_before_update)
define_callback :after_update
define_callback :__hyperstack_component_after_render_hook
define_callback :__hyperstack_component_rescue_hook
define_callback(:after_error) { |klass| Hyperstack::Internal::Component::ReactWrapper.add_after_error_hook(klass) }
+
+ define_singleton_method(:before_update) do |*methods, &block|
+ methods << block if block
+ methods.each do |method|
+ if (method.is_a?(Proc) ? method : instance_method(method)).arity.zero?
+ __hyperstack_new_style_before_update method
+ else
+ deprecation_warning "In the future before_update callbacks will not receive any parameters."
+ __hyperstack_deprecated_before_update method
+ end
+ end
+ end
end
base.extend(Hyperstack::Internal::Component::ClassMethods)
unless `Opal.__hyperstack_component_original_defn`
@@ -116,7 +122,10 @@ def component_will_receive_props(next_props)
end
def component_will_update(next_props, next_state)
- observing { run_callback(:before_update, next_props, next_state) }
+ observing do
+ run_callback(:__hyperstack_deprecated_before_update, next_props, next_state)
+ run_callback(:__hyperstack_new_style_before_update)
+ end
if @__hyperstack_component_receiving_props
@__hyperstack_component_params_wrapper.reload(next_props)
end
diff --git a/ruby/hyper-component/lib/hyperstack/component/isomorphic_helpers.rb b/ruby/hyper-component/lib/hyperstack/component/isomorphic_helpers.rb
index b622d1be1..38e84655e 100644
--- a/ruby/hyper-component/lib/hyperstack/component/isomorphic_helpers.rb
+++ b/ruby/hyper-component/lib/hyperstack/component/isomorphic_helpers.rb
@@ -145,7 +145,6 @@ def eval(js)
def send_to_opal(method_name, *args)
return unless @ctx
- args = [1] if args.length == 0
Hyperstack::Internal::Component::Rails::ComponentLoader.new(@ctx).load!
method_args = args.collect do |arg|
quarg = "#{arg}".tr('"', "'")
diff --git a/ruby/hyper-component/spec/deprecation_notices/render_spec.rb b/ruby/hyper-component/spec/deprecation_notices/render_spec.rb
index 312883501..980bd0f0c 100644
--- a/ruby/hyper-component/spec/deprecation_notices/render_spec.rb
+++ b/ruby/hyper-component/spec/deprecation_notices/render_spec.rb
@@ -32,6 +32,12 @@ class TestComp < HyperComponent
end
context "when params are expected in the before_update callback" do
+
+ it "no errors if no params" do
+ mount "NoParamsPlease"
+ expect(page).to have_content('hello')
+ end
+
it "when providing a block" do
mount "TestComp" do
class TestComp < HyperComponent
diff --git a/ruby/hyper-component/spec/test_app/app/hyperstack/components/no_params_please.rb b/ruby/hyper-component/spec/test_app/app/hyperstack/components/no_params_please.rb
new file mode 100644
index 000000000..8f8a724ad
--- /dev/null
+++ b/ruby/hyper-component/spec/test_app/app/hyperstack/components/no_params_please.rb
@@ -0,0 +1,8 @@
+class NoParamsPlease < HyperComponent
+ def no_params_please
+ @message = "hello"
+ end
+ after_mount { mutate @message = "goodby" }
+ before_update :no_params_please
+ render { @message }
+end
diff --git a/ruby/hyper-component/spec/test_app/config/application.rb b/ruby/hyper-component/spec/test_app/config/application.rb
index 8ce8665a8..383ddfaec 100644
--- a/ruby/hyper-component/spec/test_app/config/application.rb
+++ b/ruby/hyper-component/spec/test_app/config/application.rb
@@ -19,7 +19,7 @@ module TestApp
class Application < Rails::Application
config.opal.method_missing = true
config.opal.optimized_operators = true
- config.opal.arity_check = true
+ config.opal.arity_check_enabled = true
config.opal.const_missing = true
config.opal.dynamic_require_severity = :ignore
config.opal.enable_specs = true
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/base.rb b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/base.rb
index b231103dc..4cf628f3c 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/base.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/base.rb
@@ -311,7 +311,7 @@ def saving!
@saving = true
end
- def errors!(hash, saving)
+ def errors!(hash, saving = false)
@errors_at_last_sync = hash if saving
notify_waiting_for_save
errors.clear && return unless hash
@@ -324,7 +324,6 @@ def errors!(hash, saving)
end
def revert_errors!
- puts "#{inspect}.revert_errors! @errors_at_last_sync: #{@errors_at_last_sync}"
errors!(@errors_at_last_sync)
end
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/dummy_value.rb b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/dummy_value.rb
index cce04f31f..b56d34812 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/dummy_value.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/dummy_value.rb
@@ -227,10 +227,10 @@ def acts_as_string?
# to convert it to a string, for rendering
# advantage over a try(:method) is, that it doesnt raise und thus is faster
# which is important during render
- def respond_to?(method)
+ def respond_to?(method, all = false)
return true if method == :acts_as_string?
return true if %i[inspect to_date to_f to_i to_numeric to_number to_s to_time].include? method
- return @object.respond_to?(method) if @object
+ return @object.respond_to?(method, all) if @object
false
end
diff --git a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/while_loading.rb b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/while_loading.rb
index 96c6a3dca..76d54fcf5 100644
--- a/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/while_loading.rb
+++ b/ruby/hyper-model/lib/reactive_record/active_record/reactive_record/while_loading.rb
@@ -353,7 +353,7 @@ def add_style_sheet
end
- def after_mount_and_update
+ def after_mount_and_update(*)
@waiting_on_resources = @Loading
node = dom_node
%x{
diff --git a/ruby/hyper-model/spec/batch4/default_value_spec.rb b/ruby/hyper-model/spec/batch4/default_value_spec.rb
index 635d76810..1933ba2b1 100644
--- a/ruby/hyper-model/spec/batch4/default_value_spec.rb
+++ b/ruby/hyper-model/spec/batch4/default_value_spec.rb
@@ -210,7 +210,7 @@ class InputTester < HyperComponent
expect(find('#controlled-select').value).to eq('another value')
expect(find('#controlled-textarea').value).to eq('another value')
- find('#uncontrolled-input').set 'I was set by the user'
+ find('#uncontrolled-input').set 'I was set by the user', clear: :backspace
expect(find('#uncontrolled-input').value).to eq('I was set by the user')
find('#uncontrolled-checkbox').set(false)
diff --git a/ruby/hyper-operation/spec/test_app/config/application.rb b/ruby/hyper-operation/spec/test_app/config/application.rb
index 0dcdf77e3..424c42ada 100644
--- a/ruby/hyper-operation/spec/test_app/config/application.rb
+++ b/ruby/hyper-operation/spec/test_app/config/application.rb
@@ -17,7 +17,7 @@ class Application < Rails::Application
config.assets.paths << ::Rails.root.join('app', 'models').to_s
config.opal.method_missing = true
config.opal.optimized_operators = true
- config.opal.arity_check = true
+ config.opal.arity_check_enabled = true
config.opal.const_missing = true
config.opal.dynamic_require_severity = :ignore
config.opal.enable_specs = true
diff --git a/ruby/hyper-spec/lib/hyper-spec/internal/patches.rb b/ruby/hyper-spec/lib/hyper-spec/internal/patches.rb
index eaebd2b90..d5f13c3f6 100644
--- a/ruby/hyper-spec/lib/hyper-spec/internal/patches.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/patches.rb
@@ -1,8 +1,8 @@
module Opal
# strips off stuff that confuses things when transmitting to the client
# and prints offending code if it can't be compiled
- def self.hyperspec_compile(str)
- compile(str).gsub("// Prepare super implicit arguments\n", '')
+ def self.hyperspec_compile(str, opts = {})
+ compile(str, opts).gsub("// Prepare super implicit arguments\n", '')
.delete("\n").gsub('(Opal);', '(Opal)')
# rubocop:disable Lint/RescueException
# we are going to reraise it anyway, so its fine to catch EVERYTHING!
diff --git a/ruby/hyper-spec/spec/test_app/config/application.rb b/ruby/hyper-spec/spec/test_app/config/application.rb
index 732a9aeba..87e81cf44 100644
--- a/ruby/hyper-spec/spec/test_app/config/application.rb
+++ b/ruby/hyper-spec/spec/test_app/config/application.rb
@@ -26,7 +26,7 @@ class Application < Rails::Application
config.assets.paths << ::Rails.root.join('app', 'models').to_s
config.opal.method_missing = true
config.opal.optimized_operators = true
- config.opal.arity_check = true
+ config.opal.arity_check_enabled = true
config.opal.const_missing = true
config.opal.dynamic_require_severity = :ignore
config.opal.enable_specs = true
From da69ea7968c7bb44d1c8b6a007f576314317f782 Mon Sep 17 00:00:00 2001
From: catmando
Date: Thu, 11 Mar 2021 16:27:11 -0500
Subject: [PATCH 191/307] fixed a few more arity issues
---
.../collection_aggregate_methods_spec.rb | 70 +++++++++----------
.../lib/hyper-operation/railway/run.rb | 5 +-
.../spec/hyper-operation/server_op_spec.rb | 4 +-
ruby/hyper-spec/lib/hyper-spec/helpers.rb | 2 +-
.../hyper-spec/internal/client_execution.rb | 4 +-
.../hyper-spec/internal/component_mount.rb | 2 +-
ruby/hyper-spec/spec/hyper_spec.rb | 7 ++
7 files changed, 49 insertions(+), 45 deletions(-)
diff --git a/ruby/hyper-model/spec/batch2/collection_aggregate_methods_spec.rb b/ruby/hyper-model/spec/batch2/collection_aggregate_methods_spec.rb
index dfc08b7d6..9cabaf5d2 100644
--- a/ruby/hyper-model/spec/batch2/collection_aggregate_methods_spec.rb
+++ b/ruby/hyper-model/spec/batch2/collection_aggregate_methods_spec.rb
@@ -36,57 +36,51 @@
it "will not retrieve the entire collection when using #{method}" do
FactoryBot.create(:test_model)
- expect_promise(
- <<~RUBY
- Hyperstack::Model
- .load { TestModel.#{method} }
- .then do |val|
- if TestModel.all.instance_variable_get('@collection')
- "unnecessary fetch of all"
- else
- val
- end
+ expect do
+ Hyperstack::Model
+ .load { TestModel.send(method) }
+ .then do |val|
+ if TestModel.all.instance_variable_get('@collection')
+ "unnecessary fetch of all"
+ else
+ val
end
- RUBY
- ).to eq(TestModel.all.send(method))
+ end
+ end.on_client_to eq(TestModel.all.send(method))
end
end
%i[any? none?].each do |method|
- it 'will retrieve the entire collection when using any? if an arg is passed in' do
+ it "will retrieve the entire collection when using #{method} if an arg is passed in" do
FactoryBot.create(:test_model)
- expect_promise(
- <<~RUBY
- Hyperstack::Model.load do
- TestModel.#{method}(TestModel)
- end.then do |val|
- if TestModel.all.instance_variable_get('@collection')
- 'necessary fetch of all'
- else
- val
- end
+ expect do
+ Hyperstack::Model.load do
+ TestModel.send(method, TestModel)
+ end.then do |val|
+ if TestModel.all.instance_variable_get('@collection')
+ 'necessary fetch of all'
+ else
+ val
end
- RUBY
- ).to eq('necessary fetch of all')
- end
+ end
+ end.on_client_to eq('necessary fetch of all')
+ end unless Opal::VERSION.split('.')[0..1] == ['0', '11'] # opal 0.11 didn't support a value passed to any
it 'will retrieve the entire collection when using any? if a block is passed in' do
FactoryBot.create(:test_model)
- expect_promise(
- <<~RUBY
- Hyperstack::Model.load do
- TestModel.#{method} { |test_model| test_model }
- end.then do |val|
- if TestModel.all.instance_variable_get('@collection')
- 'necessary fetch of all'
- else
- val
- end
+ expect do
+ Hyperstack::Model.load do
+ TestModel.send(method) { |test_model| test_model }
+ end.then do |val|
+ if TestModel.all.instance_variable_get('@collection')
+ 'necessary fetch of all'
+ else
+ val
end
- RUBY
- ).to eq('necessary fetch of all')
+ end
+ end.on_client_to eq('necessary fetch of all')
end
end
end
diff --git a/ruby/hyper-operation/lib/hyper-operation/railway/run.rb b/ruby/hyper-operation/lib/hyper-operation/railway/run.rb
index c724843e8..69a7ca445 100644
--- a/ruby/hyper-operation/lib/hyper-operation/railway/run.rb
+++ b/ruby/hyper-operation/lib/hyper-operation/railway/run.rb
@@ -4,10 +4,13 @@ class Operation
class Exit < StandardError
attr_reader :state
attr_reader :result
- def initialize(state, result)
+ def initialize(state, result = nil)
@state = state
@result = result
end
+ def to_s
+ @state
+ end
end
class Railway
diff --git a/ruby/hyper-operation/spec/hyper-operation/server_op_spec.rb b/ruby/hyper-operation/spec/hyper-operation/server_op_spec.rb
index a8e1d24cc..7d8371952 100644
--- a/ruby/hyper-operation/spec/hyper-operation/server_op_spec.rb
+++ b/ruby/hyper-operation/spec/hyper-operation/server_op_spec.rb
@@ -89,11 +89,11 @@ def fact(x)
class ServerFacts < Hyperstack::ServerOp
step { abort! }
end
- expect_promise do
+ expect do
ServerFacts.run(n: 5).fail do |exception|
Promise.new.resolve(exception.inspect)
end
- end.to eq('#')
+ end.on_client_to eq("#")
expect(response_spy).to have_received(:status=).with(500)
end
diff --git a/ruby/hyper-spec/lib/hyper-spec/helpers.rb b/ruby/hyper-spec/lib/hyper-spec/helpers.rb
index 8fc2b5185..579362822 100644
--- a/ruby/hyper-spec/lib/hyper-spec/helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/helpers.rb
@@ -164,7 +164,7 @@ def insert_html(str)
end
def ppr(str)
- js = Opal.hyperspec_compile(str)
+ js = opal_compile(str)
execute_script("console.log(#{js})")
end
diff --git a/ruby/hyper-spec/lib/hyper-spec/internal/client_execution.rb b/ruby/hyper-spec/lib/hyper-spec/internal/client_execution.rb
index 51f65c52f..e5a4fb8fc 100644
--- a/ruby/hyper-spec/lib/hyper-spec/internal/client_execution.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/client_execution.rb
@@ -84,8 +84,8 @@ def the_node_you_are_looking_for?(node)
end
- def opal_compile(str, *)
- Opal.hyperspec_compile(str)
+ def opal_compile(str)
+ Opal.hyperspec_compile(str, arity_check: client_options[:arity_check])
end
end
end
diff --git a/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb b/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb
index 380121be3..f91b74a10 100644
--- a/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb
@@ -44,7 +44,7 @@ def self.add_class(class_name, styles={})
#{Unparser.unparse(Parser::CurrentRuby.parse(block.source).children.last) if block}
RUBY
@_hyperspec_private_client_code = nil
- opts[:code] = Opal.hyperspec_compile(block_with_helpers)
+ opts[:code] = opal_compile(block_with_helpers)
end
# rubocop:enable Metrics/MethodLength
diff --git a/ruby/hyper-spec/spec/hyper_spec.rb b/ruby/hyper-spec/spec/hyper_spec.rb
index 90cd4e8a7..c0844c350 100644
--- a/ruby/hyper-spec/spec/hyper_spec.rb
+++ b/ruby/hyper-spec/spec/hyper_spec.rb
@@ -455,6 +455,13 @@ class << self
expect { with_var * 2 }.with(with_var: 4).on_client_to eq(8)
end
end
+
+ it "will use the arity_check option" do
+ client_option arity_check: true
+ expect { -> (x, y: 2) { }.parameters }.on_client_to eq [["req", "x"], ["key", "y"]]
+ client_option arity_check: false
+ expect { -> (x, y: 2) { }.parameters }.on_client_to eq []
+ end
end
RSpec::Steps.steps "will size_window to", js: true do
From 6e5fec4f585e0f936d4af610ddf590927e2f58dd Mon Sep 17 00:00:00 2001
From: catmando
Date: Fri, 12 Mar 2021 07:49:43 -0500
Subject: [PATCH 192/307] closes #376
---
.../spec/deprecation_notices/render_spec.rb | 11 ++++++++++-
.../spec/aaa_run_first/transports_spec.rb | 2 +-
ruby/hyper-spec/lib/hyper-spec/helpers.rb | 6 +++++-
ruby/hyper-spec/spec/hyper_spec.rb | 4 +++-
4 files changed, 19 insertions(+), 4 deletions(-)
diff --git a/ruby/hyper-component/spec/deprecation_notices/render_spec.rb b/ruby/hyper-component/spec/deprecation_notices/render_spec.rb
index 980bd0f0c..d50163a9a 100644
--- a/ruby/hyper-component/spec/deprecation_notices/render_spec.rb
+++ b/ruby/hyper-component/spec/deprecation_notices/render_spec.rb
@@ -34,7 +34,16 @@ class TestComp < HyperComponent
context "when params are expected in the before_update callback" do
it "no errors if no params" do
- mount "NoParamsPlease"
+ mount "TestComp" do
+ class TestComp < HyperComponent
+ def no_params_please
+ @message = "hello"
+ end
+ after_mount { mutate @message = "goodby" }
+ before_update :no_params_please
+ render { @message }
+ end
+ end
expect(page).to have_content('hello')
end
diff --git a/ruby/hyper-operation/spec/aaa_run_first/transports_spec.rb b/ruby/hyper-operation/spec/aaa_run_first/transports_spec.rb
index 59313fa32..cf2c646be 100644
--- a/ruby/hyper-operation/spec/aaa_run_first/transports_spec.rb
+++ b/ruby/hyper-operation/spec/aaa_run_first/transports_spec.rb
@@ -373,7 +373,7 @@ def connect(*args)
expect_evaluate_ruby('Hyperstack.anti_csrf_token').to be_present
end
- it 'wait for an instance channel to be loaded before connecting' do
+ it 'wait for an instance channel to be loaded before connecting' do # 2 = action_cable
# Make a pretend mini model, and allow it to be accessed by user-123
stub_const "UserModelPolicy", Class.new
stub_const "UserModel", Class.new
diff --git a/ruby/hyper-spec/lib/hyper-spec/helpers.rb b/ruby/hyper-spec/lib/hyper-spec/helpers.rb
index 579362822..5ec0dfc73 100644
--- a/ruby/hyper-spec/lib/hyper-spec/helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/helpers.rb
@@ -89,12 +89,16 @@ def isomorphic(&block)
# Allows options to the mount method to be specified globally
def client_option(opts = {})
- @_hyperspec_private_client_options ||= {}
+ @_hyperspec_private_client_options ||= { arity_check: default_arity_check }
@_hyperspec_private_client_options.merge! opts
build_var_inclusion_lists
@_hyperspec_private_client_options
end
+ def default_arity_check
+ Rails&.application&.config&.opal&.arity_check_enabled if defined? Rails
+ end
+
alias client_options client_option
##
diff --git a/ruby/hyper-spec/spec/hyper_spec.rb b/ruby/hyper-spec/spec/hyper_spec.rb
index c0844c350..8f4e6e333 100644
--- a/ruby/hyper-spec/spec/hyper_spec.rb
+++ b/ruby/hyper-spec/spec/hyper_spec.rb
@@ -457,10 +457,12 @@ class << self
end
it "will use the arity_check option" do
- client_option arity_check: true
+ # We run the specs with arity_check_enabled so this should default to being on
expect { -> (x, y: 2) { }.parameters }.on_client_to eq [["req", "x"], ["key", "y"]]
client_option arity_check: false
expect { -> (x, y: 2) { }.parameters }.on_client_to eq []
+ client_option arity_check: true
+ expect { -> (x, y: 2) { }.parameters }.on_client_to eq [["req", "x"], ["key", "y"]]
end
end
From b625905100aa7aa739c31fbc35a81e9c28ebf46c Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 13 Mar 2021 11:09:42 -0500
Subject: [PATCH 193/307] more arity check fixes
---
.../lib/hyperstack/component.rb | 61 +++++++------
.../internal/component/rescue_wrapper.rb | 2 +-
.../spec/deprecation_notices/render_spec.rb | 86 +++++++++++--------
.../hyperstack/components/no_params_please.rb | 8 --
.../spec/aaa_run_first/transports_spec.rb | 21 +++--
ruby/hyper-spec/lib/hyper-spec/helpers.rb | 3 +-
.../hyper-spec/internal/component_mount.rb | 2 +-
.../lib/hyperstack/internal/callbacks.rb | 17 ++--
.../spec/internal/callbacks_spec.rb | 60 ++++++++-----
9 files changed, 148 insertions(+), 112 deletions(-)
delete mode 100644 ruby/hyper-component/spec/test_app/app/hyperstack/components/no_params_please.rb
diff --git a/ruby/hyper-component/lib/hyperstack/component.rb b/ruby/hyper-component/lib/hyperstack/component.rb
index c86309198..49271dc45 100644
--- a/ruby/hyper-component/lib/hyperstack/component.rb
+++ b/ruby/hyper-component/lib/hyperstack/component.rb
@@ -19,30 +19,40 @@ def self.included(base)
base.include(Hyperstack::Internal::Component::ShouldComponentUpdate)
base.class_eval do
class_attribute :initial_state
- define_callback :before_mount
- define_callback :after_mount
- define_callback :before_new_params do |klass|
- klass.deprecation_warning "`before_new_params` has been deprecated. "\
- "The base method componentWillReceiveProps is deprecated in React without replacement"
- end
- define_callback(:__hyperstack_deprecated_before_update)
- define_callback(:__hyperstack_new_style_before_update)
- define_callback :after_update
- define_callback :__hyperstack_component_after_render_hook
- define_callback :__hyperstack_component_rescue_hook
- define_callback(:after_error) { |klass| Hyperstack::Internal::Component::ReactWrapper.add_after_error_hook(klass) }
-
- define_singleton_method(:before_update) do |*methods, &block|
- methods << block if block
- methods.each do |method|
- if (method.is_a?(Proc) ? method : instance_method(method)).arity.zero?
- __hyperstack_new_style_before_update method
- else
- deprecation_warning "In the future before_update callbacks will not receive any parameters."
- __hyperstack_deprecated_before_update method
- end
+
+ method_args_deprecation_check = lambda do |name, sself, proc, *args|
+ if proc.arity.zero?
+ args = []
+ else
+ deprecation_warning "In the future #{name} callbacks will not receive any parameters."
end
+ sself.instance_exec(*args, &proc)
+ args
end
+
+ define_callback :before_mount, before_call_hook: method_args_deprecation_check
+ define_callback :after_mount
+ define_callback(
+ :before_new_params,
+ after_define_hook: lambda do |klass|
+ klass.deprecation_warning "`before_new_params` has been deprecated. The base "\
+ "method componentWillReceiveProps is deprecated in React without replacement"
+ end
+ )
+ define_callback(:before_update, before_call_hook: method_args_deprecation_check)
+ define_callback :after_update
+ define_callback(
+ :__hyperstack_component_after_render_hook,
+ before_call_hook: ->(_, sself, proc, *args) { [*sself.instance_exec(*args, &proc)] }
+ )
+ define_callback(
+ :__hyperstack_component_rescue_hook,
+ before_call_hook: ->(_, sself, proc, *args) { sself.instance_exec(*args, &proc) }
+ )
+ define_callback(
+ :after_error,
+ after_define_hook: ->(klass) { Hyperstack::Internal::Component::ReactWrapper.add_after_error_hook(klass) }
+ )
end
base.extend(Hyperstack::Internal::Component::ClassMethods)
unless `Opal.__hyperstack_component_original_defn`
@@ -122,10 +132,7 @@ def component_will_receive_props(next_props)
end
def component_will_update(next_props, next_state)
- observing do
- run_callback(:__hyperstack_deprecated_before_update, next_props, next_state)
- run_callback(:__hyperstack_new_style_before_update)
- end
+ observing { run_callback(:before_update, next_props, next_state) }
if @__hyperstack_component_receiving_props
@__hyperstack_component_params_wrapper.reload(next_props)
end
@@ -183,7 +190,7 @@ def waiting_on_resources
end
def __hyperstack_component_run_post_render_hooks(element)
- run_callback(:__hyperstack_component_after_render_hook, element) { |*args| args }.first
+ run_callback(:__hyperstack_component_after_render_hook, element).first
end
def _run_before_render_callbacks
diff --git a/ruby/hyper-component/lib/hyperstack/internal/component/rescue_wrapper.rb b/ruby/hyper-component/lib/hyperstack/internal/component/rescue_wrapper.rb
index 429a59780..d3deb43ca 100644
--- a/ruby/hyper-component/lib/hyperstack/internal/component/rescue_wrapper.rb
+++ b/ruby/hyper-component/lib/hyperstack/internal/component/rescue_wrapper.rb
@@ -27,7 +27,7 @@ class << self
after_error do |error, info|
args = RescueWrapper.after_error_args || [error, info]
- found, * = @Child.run_callback(:__hyperstack_component_rescue_hook, found, *args) { |a| a }
+ found, * = @Child.run_callback(:__hyperstack_component_rescue_hook, found, *args)
unless found
RescueWrapper.after_error_args = args
raise error
diff --git a/ruby/hyper-component/spec/deprecation_notices/render_spec.rb b/ruby/hyper-component/spec/deprecation_notices/render_spec.rb
index d50163a9a..dc79cf031 100644
--- a/ruby/hyper-component/spec/deprecation_notices/render_spec.rb
+++ b/ruby/hyper-component/spec/deprecation_notices/render_spec.rb
@@ -23,57 +23,67 @@ class TestComp < HyperComponent
render { 'hello' }
end
end
- expect(page).to have_content('hello')
+ expect(page).to have_content("hello")
expect_evaluate_ruby("Hyperstack.instance_variable_get('@deprecation_messages')").to eq(
- ["Warning: Deprecated feature used in TestComp. `before_new_params` has been deprecated. "\
- "The base method componentWillReceiveProps is deprecated in React without replacement"
- ]
- )
- end
+ [
+ "Warning: Deprecated feature used in TestComp. `before_new_params` has been deprecated. "\
+ "The base method componentWillReceiveProps is deprecated in React without replacement"
+ ]
+ )
+ end
- context "when params are expected in the before_update callback" do
+ %i[mount update].each do |callback_name|
+ context "when params are expected in the before_#{callback_name} callback" do
+
+ before(:all) do
+ before_mount { CALLBACK_NAME = "before_#{callback_name}" }
+ end
- it "no errors if no params" do
- mount "TestComp" do
- class TestComp < HyperComponent
- def no_params_please
- @message = "hello"
+ it "no errors if no params" do
+ mount "TestComp" do
+ class TestComp < HyperComponent
+ def no_params_please
+ @message = "hello"
+ end
+ send(CALLBACK_NAME, :no_params_please)
+ after_mount { mutate @message = "goodby" unless @message }
+ render { @message }
end
- after_mount { mutate @message = "goodby" }
- before_update :no_params_please
- render { @message }
end
+ expect(page).to have_content('hello')
+ expect_evaluate_ruby("Hyperstack.instance_variable_get('@deprecation_messages')").to be_nil
end
- expect(page).to have_content('hello')
- end
- it "when providing a block" do
- mount "TestComp" do
- class TestComp < HyperComponent
- before_update { |x, y| }
- render { 'hello' }
+ it "when providing a block" do
+ mount "TestComp" do
+ class TestComp < HyperComponent
+ send(CALLBACK_NAME) { |x, y| @message = "hello" }
+ after_mount { mutate @message = "goodby" unless @message }
+ render { @message }
+ end
end
+ expect(page).to have_content('hello')
+ expect_evaluate_ruby("Hyperstack.instance_variable_get('@deprecation_messages')").to eq(
+ ["Warning: Deprecated feature used in TestComp. In the future before_#{callback_name} callbacks will not receive any parameters."]
+ )
end
- expect(page).to have_content('hello')
- expect_evaluate_ruby("Hyperstack.instance_variable_get('@deprecation_messages')").to eq(
- ["Warning: Deprecated feature used in TestComp. In the future before_update callbacks will not receive any parameters."]
- )
- end
- it "when providing a method name" do
- mount "TestComp" do
- class TestComp < HyperComponent
- def foo(x, y)
+ it "when providing a method name" do
+ mount "TestComp" do
+ class TestComp < HyperComponent
+ def foo(x, y=nil) # so it works with both before_mount (1 arg) and before_update (2 args)
+ @message = "hello"
+ end
+ send(CALLBACK_NAME, :foo)
+ after_mount { mutate @message = "goodby" unless @message}
+ render { @message }
end
- before_update :foo
- render { 'hello' }
end
+ expect(page).to have_content('hello')
+ expect_evaluate_ruby("Hyperstack.instance_variable_get('@deprecation_messages')").to eq(
+ ["Warning: Deprecated feature used in TestComp. In the future before_#{callback_name} callbacks will not receive any parameters."]
+ )
end
- expect(page).to have_content('hello')
- expect_evaluate_ruby("Hyperstack.instance_variable_get('@deprecation_messages')").to eq(
- ["Warning: Deprecated feature used in TestComp. In the future before_update callbacks will not receive any parameters."]
- )
end
end
-
end
diff --git a/ruby/hyper-component/spec/test_app/app/hyperstack/components/no_params_please.rb b/ruby/hyper-component/spec/test_app/app/hyperstack/components/no_params_please.rb
deleted file mode 100644
index 8f8a724ad..000000000
--- a/ruby/hyper-component/spec/test_app/app/hyperstack/components/no_params_please.rb
+++ /dev/null
@@ -1,8 +0,0 @@
-class NoParamsPlease < HyperComponent
- def no_params_please
- @message = "hello"
- end
- after_mount { mutate @message = "goodby" }
- before_update :no_params_please
- render { @message }
-end
diff --git a/ruby/hyper-operation/spec/aaa_run_first/transports_spec.rb b/ruby/hyper-operation/spec/aaa_run_first/transports_spec.rb
index cf2c646be..49e060210 100644
--- a/ruby/hyper-operation/spec/aaa_run_first/transports_spec.rb
+++ b/ruby/hyper-operation/spec/aaa_run_first/transports_spec.rb
@@ -373,6 +373,10 @@ def connect(*args)
expect_evaluate_ruby('Hyperstack.anti_csrf_token').to be_present
end
+ # after(:each) do |example|
+ # binding.pry #if example.exception
+ # end
+
it 'wait for an instance channel to be loaded before connecting' do # 2 = action_cable
# Make a pretend mini model, and allow it to be accessed by user-123
stub_const "UserModelPolicy", Class.new
@@ -399,8 +403,8 @@ def id
isomorphic do
class CheckIn < Hyperstack::ControllerOp
param :id
- validate { params.id == '123' }
- step { params.id }
+ validate { puts "validating params.id == '123': #{params.id == '123'}"; params.id == '123' }
+ step { params.id } # return the id to the client simulating checkin of valid user
end
end
@@ -408,9 +412,11 @@ class CheckIn < Hyperstack::ControllerOp
# Stub the user model on the client
class UserModel
def initialize(id)
+ puts "UserModel.new(#{id})"
@id = id
end
def id
+ puts "self.id = #{@id}"
@id.to_s
end
end
@@ -419,6 +425,7 @@ def id
module Hyperstack
module Model
def self.load
+ puts "loading id from server - simulating HyperModel load of id for an object"
CheckIn.run(id: yield)
end
end
@@ -433,11 +440,15 @@ def self.load
end
expect(CheckIn).to receive(:run).and_call_original
- evaluate_ruby 'Hyperstack.connect(UserModel.new(123))'
+ evaluate_ruby { puts "setting up connecting"; Hyperstack.connect(UserModel.new(123)) }
# the suite previously redefined connect so we have to call this to initiate
# the connection
- evaluate_ruby 'Hyperstack.go_ahead_and_connect'
- wait(10.seconds).for { Hyperstack::Connection.active }.to eq(['UserModel-123'])
+ evaluate_ruby { puts "connecting"; Hyperstack.go_ahead_and_connect }
+ Timecop.travel(Time.now + Hyperstack::Connection.transport.expire_new_connection_in)
+ wait_for do
+ sleep 0.25
+ Hyperstack::Connection.active.tap { |c| puts "active = [#{c}]"}
+ end.to eq(['UserModel-123'])
end
end
end
diff --git a/ruby/hyper-spec/lib/hyper-spec/helpers.rb b/ruby/hyper-spec/lib/hyper-spec/helpers.rb
index 5ec0dfc73..ac881d813 100644
--- a/ruby/hyper-spec/lib/hyper-spec/helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/helpers.rb
@@ -74,8 +74,7 @@ def mount(component_name = nil, params = nil, opts = {}, &block)
def before_mount(&block)
@_hyperspec_private_client_code =
- "#{@_hyperspec_private_client_code}"\
- "#{Unparser.unparse Parser::CurrentRuby.parse(block.source).children.last}\n"
+ "#{@_hyperspec_private_client_code}#{add_opal_block('', block)}"
end
# Execute the block both on the client and on the server. Useful
diff --git a/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb b/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb
index f91b74a10..366ea71a7 100644
--- a/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/component_mount.rb
@@ -41,7 +41,7 @@ def self.add_class(class_name, styles={})
end
#{test_dummy}
#{@_hyperspec_private_client_code}
- #{Unparser.unparse(Parser::CurrentRuby.parse(block.source).children.last) if block}
+ #{"#{add_locals('', block)}\n#{Unparser.unparse(Parser::CurrentRuby.parse(block.source).children.last)}" if block}
RUBY
@_hyperspec_private_client_code = nil
opts[:code] = opal_compile(block_with_helpers)
diff --git a/ruby/hyper-state/lib/hyperstack/internal/callbacks.rb b/ruby/hyper-state/lib/hyperstack/internal/callbacks.rb
index f7062c5df..3b1709c04 100644
--- a/ruby/hyper-state/lib/hyperstack/internal/callbacks.rb
+++ b/ruby/hyper-state/lib/hyperstack/internal/callbacks.rb
@@ -12,29 +12,30 @@ def self.included(base)
def run_callback(name, *args)
self.class.callbacks_for(name).flatten.each do |callback|
- result = if callback.is_a?(Proc)
- instance_exec(*args, &callback)
- else
- send(callback, *args)
- end
- args = yield(result) if block_given?
+ callback = method(callback) unless callback.is_a? Proc
+ args = self.class.send("_#{name}_before_call_hook", name, self, callback, *args)
end
args
end
module ClassMethods
- def define_callback(callback_name, &after_define_hook)
+ def define_callback(callback_name, before_call_hook: nil, after_define_hook: nil)
wrapper_name = "_#{callback_name}_callbacks"
define_singleton_method(wrapper_name) do
Context.set_var(self, "@#{wrapper_name}", force: true) { [] }
end
+ before_call_hook ||= lambda do |_name, sself, proc, *args|
+ sself.instance_exec(*args, &proc)
+ args
+ end
+ define_singleton_method("_#{callback_name}_before_call_hook", &before_call_hook)
define_singleton_method(callback_name) do |*args, &block|
args << block if block_given?
send(wrapper_name).push args
Hotloader.when_file_updates do
send(wrapper_name).delete_if { |item| item.equal? args }
end
- after_define_hook.call(self, *args, &block) if after_define_hook
+ after_define_hook.call(self) if after_define_hook
end
end
diff --git a/ruby/hyper-state/spec/internal/callbacks_spec.rb b/ruby/hyper-state/spec/internal/callbacks_spec.rb
index 21f1dbbd1..04f3d15d6 100644
--- a/ruby/hyper-state/spec/internal/callbacks_spec.rb
+++ b/ruby/hyper-state/spec/internal/callbacks_spec.rb
@@ -25,48 +25,64 @@ class Foo
define_callback :before_dinner
before_dinner :wash_hands, :turn_off_laptop
- def wash_hands;end
- def turn_off_laptop;end
+ attr_reader :washed_hands
+ attr_reader :turned_off_laptop
+
+ def wash_hands(*args)
+ @washed_hands = args
+ end
+ def turn_off_laptop(*args)
+ @turned_off_laptop = args
+ end
end
end
- expect_evaluate_ruby do
- instance = Foo.new
- [ instance.respond_to?(:wash_hands),
- instance.respond_to?(:turn_off_laptop),
- instance.run_callback(:before_dinner, 1, 2, 3) ]
- end.to eq([true, true, [1, 2, 3]])
+ evaluate_ruby { @instance = Foo.new }
+ expect { @instance.respond_to?(:wash_hands) }.on_client_to be_truthy
+ expect { @instance.respond_to?(:turn_off_laptop) }.on_client_to be_truthy
+ expect { @instance.run_callback(:before_dinner, 1, 2, 3) }.on_client_to eq [1, 2, 3]
+ expect { @instance.washed_hands }.on_client_to eq [1, 2, 3]
+ expect { @instance.turned_off_laptop }.on_client_to eq [1, 2, 3]
end
context 'using Hyperloop::Context.reset!' do
- #after(:all) do
- # Hyperloop::Context.instance_variable_set(:@context, nil)
- #end
it 'clears callbacks on Hyperloop::Context.reset!' do
on_client do
Hyperstack::Context.reset!
-
class Foo
include Hyperstack::Internal::Callbacks
define_callback :before_dinner
-
before_dinner :wash_hands, :turn_off_laptop
- def wash_hands;end
+ attr_reader :washed_hands
+ attr_reader :turned_off_laptop
- def turn_off_laptop;end
+ def wash_hands(*args)
+ @washed_hands = args
+ end
+ def turn_off_laptop(*args)
+ @turned_off_laptop = args
+ end
end
end
- expect_evaluate_ruby do
- instance = Foo.new
-
+ evaluate_ruby { @instance = Foo.new }
+ expect { @instance.run_callback(:before_dinner, 1, 2, 3) }.on_client_to eq [1, 2, 3]
+ expect { @instance.washed_hands }.on_client_to eq [1, 2, 3]
+ expect { @instance.turned_off_laptop }.on_client_to eq [1, 2, 3]
+ evaluate_ruby do
+ @instance = Foo.new
Hyperstack::Context.reset!
-
+ end
+ expect { @instance.run_callback(:before_dinner, 1, 2, 3) }.on_client_to eq [1, 2, 3]
+ expect { @instance.washed_hands }.on_client_to be_nil
+ expect { @instance.turned_off_laptop }.on_client_to be_nil
+ evaluate_ruby do
Foo.class_eval do
before_dinner :wash_hands
end
-
- instance.run_callback(:before_dinner, 1, 2, 3)
- end.to eq([1, 2, 3])
+ end
+ expect { @instance.run_callback(:before_dinner, 4, 5) }.on_client_to eq [4, 5]
+ expect { @instance.washed_hands }.on_client_to eq [4, 5]
+ expect { @instance.turned_off_laptop }.on_client_to be_nil
end
end
From cb7f4a75dd0b36aca260f9a2b2ab68644a338d4f Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 13 Mar 2021 22:20:47 -0500
Subject: [PATCH 194/307] closes more arity issues and closes #378 and closes
#379
---
ruby/hyper-operation/lib/hyper-operation/api.rb | 3 ++-
.../lib/hyper-operation/railway/dispatcher.rb | 1 -
.../spec/hyper-operation/execution_spec.rb | 4 ++--
.../spec/hyper-operation/reset_context_spec.rb | 10 +++++-----
.../lib/hyper-spec/internal/client_execution.rb | 2 ++
ruby/hyper-spec/spec/hyper_spec.rb | 8 ++++++++
6 files changed, 19 insertions(+), 9 deletions(-)
diff --git a/ruby/hyper-operation/lib/hyper-operation/api.rb b/ruby/hyper-operation/lib/hyper-operation/api.rb
index 7ba464595..7ba4653cd 100644
--- a/ruby/hyper-operation/lib/hyper-operation/api.rb
+++ b/ruby/hyper-operation/lib/hyper-operation/api.rb
@@ -47,7 +47,8 @@ def _run(*args)
@_railway.process_validations
@_railway.run
@_railway.dispatch
- @_railway.result
+ # return the result from dispatch in case there is an error
+ # @_railway.result
end
end
diff --git a/ruby/hyper-operation/lib/hyper-operation/railway/dispatcher.rb b/ruby/hyper-operation/lib/hyper-operation/railway/dispatcher.rb
index 8e80c5da2..54b0d6809 100644
--- a/ruby/hyper-operation/lib/hyper-operation/railway/dispatcher.rb
+++ b/ruby/hyper-operation/lib/hyper-operation/railway/dispatcher.rb
@@ -1,7 +1,6 @@
module Hyperstack
class Operation
class Railway
-
def receivers
self.class.receivers
end
diff --git a/ruby/hyper-operation/spec/hyper-operation/execution_spec.rb b/ruby/hyper-operation/spec/hyper-operation/execution_spec.rb
index 164aeeed8..867b783b7 100644
--- a/ruby/hyper-operation/spec/hyper-operation/execution_spec.rb
+++ b/ruby/hyper-operation/spec/hyper-operation/execution_spec.rb
@@ -381,8 +381,8 @@ class SayHelloOp < Hyperstack::Operation
TestOperation.class_eval do
param :xxx
extend HelloCounter
- def say_hello(test = false)
- self.class.say_hello(test)
+ def say_hello
+ self.class.say_hello
end
step { say_hello }
step :say_hello
diff --git a/ruby/hyper-operation/spec/hyper-operation/reset_context_spec.rb b/ruby/hyper-operation/spec/hyper-operation/reset_context_spec.rb
index add0f085a..3b7094c60 100644
--- a/ruby/hyper-operation/spec/hyper-operation/reset_context_spec.rb
+++ b/ruby/hyper-operation/spec/hyper-operation/reset_context_spec.rb
@@ -52,12 +52,12 @@ class Store
class << self
attr_reader :boot_calls
attr_reader :another_receiver_calls
- def booted
+ def booted(*)
puts " booted called"
@boot_calls ||= 0
@boot_calls += 1
end
- def another_receiver
+ def another_receiver(*)
puts " receiver called"
@another_receiver_calls ||= 0
@another_receiver_calls += 1
@@ -72,14 +72,14 @@ class Store
receives Hyperstack::Application::Boot, :another_receiver
end
end
- evaluate_ruby("puts '>>booting'") # do a separate evaluation to get initial boot completed
+ evaluate_ruby { puts '>>booting' } # do a separate evaluation to get initial boot completed
evaluate_ruby do
puts '>>resetting again'
Hyperstack::Context.reset!(nil)
puts '>>booting again'
Hyperstack::Application::Boot.run
end
- expect_evaluate_ruby('Store.boot_calls').to eq(2)
- expect_evaluate_ruby('Store.another_receiver_calls').to eq(1)
+ expect { Store.boot_calls }.on_client_to eq(2)
+ expect { Store.another_receiver_calls }.on_client_to eq(1)
end
end
diff --git a/ruby/hyper-spec/lib/hyper-spec/internal/client_execution.rb b/ruby/hyper-spec/lib/hyper-spec/internal/client_execution.rb
index e5a4fb8fc..39d3666fb 100644
--- a/ruby/hyper-spec/lib/hyper-spec/internal/client_execution.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/internal/client_execution.rb
@@ -25,6 +25,7 @@ def add_promise_execute_and_wait(str, opts)
Timeout.timeout(Capybara.default_max_wait_time) do
loop do
break if page.evaluate_script('!!window.hyper_spec_promise_result')
+ page.evaluate_script('!!window.hyper_spec_promise_failed && Opal.Opal.$raise(window.hyper_spec_promise_failed)')
sleep 0.25
end
@@ -37,6 +38,7 @@ def add_promise_wrapper(str)
(#{str}).tap do |r|
if defined?(Promise) && r.is_a?(Promise)
r.then { |args| `window.hyper_spec_promise_result = [args]` }
+ .fail { |e| `window.hyper_spec_promise_failed = e` }
else
#after(0) do
#puts "setting window.hyper_spec_promise_result = [\#{r}]"
diff --git a/ruby/hyper-spec/spec/hyper_spec.rb b/ruby/hyper-spec/spec/hyper_spec.rb
index 8f4e6e333..d32900a94 100644
--- a/ruby/hyper-spec/spec/hyper_spec.rb
+++ b/ruby/hyper-spec/spec/hyper_spec.rb
@@ -137,6 +137,14 @@ def wait(seconds)
end.to eq(DELAY)
expect(Time.now-start).to be >= DELAY
end
+
+ it "will raise an error if a promise is rejected" do
+ begin
+ on_client { Promise.new.reject("foo") }
+ rescue StandardError => e
+ expect(e.message).to start_with "javascript error: foo\n"
+ end
+ end
end
context 'event and callback handlers' do
From f5d379805c2fa436b8bb0de1410c16557a4692a6 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sat, 13 Mar 2021 22:51:43 -0500
Subject: [PATCH 195/307] closes #379
---
ruby/hyper-operation/lib/hyper-operation/api.rb | 7 +++++--
1 file changed, 5 insertions(+), 2 deletions(-)
diff --git a/ruby/hyper-operation/lib/hyper-operation/api.rb b/ruby/hyper-operation/lib/hyper-operation/api.rb
index 7ba4653cd..5b11e3d4f 100644
--- a/ruby/hyper-operation/lib/hyper-operation/api.rb
+++ b/ruby/hyper-operation/lib/hyper-operation/api.rb
@@ -46,9 +46,12 @@ def _run(*args)
@_railway.process_params(args)
@_railway.process_validations
@_railway.run
- @_railway.dispatch
# return the result from dispatch in case there is an error
- # @_railway.result
+ if (dispatch_result = @_railway.dispatch).rejected?
+ dispatch_result
+ else
+ @_railway.result
+ end
end
end
From 7c4f5c7f747873792312f41a23f96718233cea30 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 14 Mar 2021 15:52:22 -0400
Subject: [PATCH 196/307] attempting to fix intermittent transport specs
---
docs/hyper-spec/03-hyperspec-methods-and-features.md | 8 ++++----
.../hyper-operation/spec/aaa_run_first/transports_spec.rb | 6 +++---
2 files changed, 7 insertions(+), 7 deletions(-)
diff --git a/docs/hyper-spec/03-hyperspec-methods-and-features.md b/docs/hyper-spec/03-hyperspec-methods-and-features.md
index 448bd0d57..8fec6d0c6 100644
--- a/docs/hyper-spec/03-hyperspec-methods-and-features.md
+++ b/docs/hyper-spec/03-hyperspec-methods-and-features.md
@@ -89,7 +89,7 @@ The on_client method takes a block. The ruby code inside the block will be exec
end
```
-If the block returns a promise Hyperspec will wait for the promise to be resolved before returning. For example:
+If the block returns a promise Hyperspec will wait for the promise to be resolved (or rejected) before returning. For example:
```ruby
it 'waits for a promise' do
@@ -135,7 +135,7 @@ across blocks executed on the client. For example:
end
```
-> Be especially careful of this when using the [`no_reset`](#the-no_reset-flag) as instance variables will retain their values between each spec in this mode.
+> Be especially careful of this when using the [`no_reset` flag](#the-no_reset-flag) as instance variables will retain their values between each spec in this mode.
#### White and Black Listing Variables
@@ -387,7 +387,7 @@ These methods are primarily designed to help debug code and specs.
#### `c?`
-Shorthand for `on_console`, useful for entering expressions in pry console, to investigate the state of the client.
+Shorthand for `on_client`, useful for entering expressions in the pry console, to investigate the state of the client.
```ruby
pry:> c? { puts 'hello on the console' } # prints hello on the client
@@ -432,7 +432,7 @@ end
#### `open_in_chrome`
By default specs are run with headless chrome, so there is no visible browser window. The `open_in_chrome` method will open a browser window, and load it with the current state.
-You can also run specs in a visible chrome window by setting the `DRIVER` environment variable to `CHROME`
+You can also run specs in a visible chrome window by setting the `DRIVER` environment variable to `chrome`. i.e. (`DRIVER=chrome bundle exec rspec ...`)
#### `pause`
The method is typically not needed assuming you are using a multithreaded server like Puma. If for whatever reason the pry debug session is not multithreaded, *and* you want to try some kind of experiment on the javascript console, *and* those experiments make requests to the server, you may not get a response, because all threads are in use.
diff --git a/ruby/hyper-operation/spec/aaa_run_first/transports_spec.rb b/ruby/hyper-operation/spec/aaa_run_first/transports_spec.rb
index 49e060210..a10608b1b 100644
--- a/ruby/hyper-operation/spec/aaa_run_first/transports_spec.rb
+++ b/ruby/hyper-operation/spec/aaa_run_first/transports_spec.rb
@@ -181,7 +181,7 @@ def connect(*args)
it 'opens the connection' do
mount 'TestComponent'
evaluate_ruby 'Hyperstack.go_ahead_and_connect'
- Timecop.travel(Time.now + Hyperstack::Connection.transport.expire_new_connection_in)
+ Timecop.travel(Time.now + Hyperstack::Connection.transport.expire_new_connection_in - 1)
wait_for do
sleep 0.25
Hyperstack::Connection.active
@@ -201,7 +201,7 @@ def connect(*args)
it 'sees the connection going offline' do
mount 'TestComponent'
evaluate_ruby 'Hyperstack.go_ahead_and_connect'
- Timecop.travel(Time.now + Hyperstack::Connection.transport.expire_new_connection_in)
+ Timecop.travel(Time.now + Hyperstack::Connection.transport.expire_new_connection_in - 1)
wait_for do
sleep 0.25
Hyperstack::Connection.active
@@ -260,7 +260,7 @@ def connect(*args)
it 'opens the connection' do
mount 'TestComponent'
evaluate_ruby 'Hyperstack.go_ahead_and_connect'
- Timecop.travel(Time.now + Hyperstack::Connection.transport.expire_new_connection_in)
+ Timecop.travel(Time.now + Hyperstack::Connection.transport.expire_new_connection_in - 1)
wait_for do
sleep 0.25
Hyperstack::Connection.active
From bae7a8a3f924477f49e2d9123309146b68f0bd92 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 14 Mar 2021 17:07:25 -0400
Subject: [PATCH 197/307] added sinatra sample app and support and doc
---
docs/hyper-spec/04-using-with-rack.md | 56 ++++++
ruby/examples/misc/sinatra_app/Gemfile | 14 ++
ruby/examples/misc/sinatra_app/Gemfile.lock | 159 ++++++++++++++++++
ruby/examples/misc/sinatra_app/app.rb | 32 ++++
.../misc/sinatra_app/app/application.rb | 3 +
ruby/examples/misc/sinatra_app/config.ru | 3 +
.../misc/sinatra_app/spec/spec_helper.rb | 18 ++
.../misc/sinatra_app/spec/test_spec.rb | 6 +
ruby/hyper-spec/lib/hyper-spec/helpers.rb | 4 +-
9 files changed, 294 insertions(+), 1 deletion(-)
create mode 100644 docs/hyper-spec/04-using-with-rack.md
create mode 100644 ruby/examples/misc/sinatra_app/Gemfile
create mode 100644 ruby/examples/misc/sinatra_app/Gemfile.lock
create mode 100644 ruby/examples/misc/sinatra_app/app.rb
create mode 100644 ruby/examples/misc/sinatra_app/app/application.rb
create mode 100644 ruby/examples/misc/sinatra_app/config.ru
create mode 100644 ruby/examples/misc/sinatra_app/spec/spec_helper.rb
create mode 100644 ruby/examples/misc/sinatra_app/spec/test_spec.rb
diff --git a/docs/hyper-spec/04-using-with-rack.md b/docs/hyper-spec/04-using-with-rack.md
new file mode 100644
index 000000000..7c5147f40
--- /dev/null
+++ b/docs/hyper-spec/04-using-with-rack.md
@@ -0,0 +1,56 @@
+# Using Hyperspec with Rack
+
+Hyperspec will run with Rails out of the box, but you can also use Hyperspec with any Rack application, with just a little more setup. For example here is a sample configuration setup with Sinatra:
+
+```ruby
+# Gemfile
+...
+
+gem "sinatra"
+gem "rspec"
+gem "pry"
+gem "opal"
+gem "opal-sprockets"
+gem "rack"
+gem "puma"
+group :test do
+ # gem 'hyper-spec', '~> 1.0.alpha1.0'
+ # or to use edge:
+ gem 'hyper-spec',
+ git: 'git://github.com/hyperstack-org/hyperstack.git',
+ branch: 'edge',
+ glob: 'ruby/*/*.gemspec'
+end
+```
+
+```ruby
+# spec/spec_helper.rb
+
+require "bundler"
+Bundler.require
+ENV["RACK_ENV"] ||= "test"
+
+# require your application files as needed
+require File.join(File.dirname(__FILE__), "..", "app.rb")
+
+# bring in needed support files
+require "rspec"
+require "rack/test"
+require "hyper-spec/rack"
+
+# assumes your sinatra app is named app
+Capybara.app = HyperSpecTestController.wrap(app: app)
+
+set :environment, :test
+set :run, false
+set :raise_errors, true
+set :logging, false
+```
+
+### Details
+
+The interface between Hyperspec and your application environment is defined by the `HyperspecTestController` class. This file typically includes a set of helper methods from `HyperSpec::ControllerHelpers`, which can then be overridden to give whatever behavior your specific framework needs. Have a look at the `hyper-spec/rack.rb` and `hyper-spec/controller_helpers.rb` files in the Hyperspec gem directory.
+
+### Example
+
+A complete (but very simple) example is in this repos `ruby/examples/misc/sinatra_app` directory
diff --git a/ruby/examples/misc/sinatra_app/Gemfile b/ruby/examples/misc/sinatra_app/Gemfile
new file mode 100644
index 000000000..f95cfe828
--- /dev/null
+++ b/ruby/examples/misc/sinatra_app/Gemfile
@@ -0,0 +1,14 @@
+source "https://rubygems.org"
+
+gem "sinatra"
+gem "rspec"
+gem "pry"
+gem "opal"
+gem "opal-sprockets"
+gem "rack"
+gem "puma"
+gem "hyper-spec", path: "../../../hyper-spec"
+# gem 'hyper-spec',
+# git: 'git://github.com/hyperstack-org/hyperstack.git',
+# branch: 'edge',
+# glob: 'ruby/*/*.gemspec'
diff --git a/ruby/examples/misc/sinatra_app/Gemfile.lock b/ruby/examples/misc/sinatra_app/Gemfile.lock
new file mode 100644
index 000000000..72b796b6e
--- /dev/null
+++ b/ruby/examples/misc/sinatra_app/Gemfile.lock
@@ -0,0 +1,159 @@
+PATH
+ remote: ../../../hyper-spec
+ specs:
+ hyper-spec (1.0.alpha1.5)
+ actionview
+ capybara
+ chromedriver-helper (= 1.2.0)
+ filecache
+ method_source
+ opal (>= 0.11.0, < 2.0)
+ parser (>= 2.3.3.1)
+ rspec
+ selenium-webdriver
+ timecop (~> 0.8.1)
+ uglifier
+ unparser (>= 0.4.2)
+ webdrivers
+
+GEM
+ remote: https://rubygems.org/
+ specs:
+ actionview (6.1.3)
+ activesupport (= 6.1.3)
+ builder (~> 3.1)
+ erubi (~> 1.4)
+ rails-dom-testing (~> 2.0)
+ rails-html-sanitizer (~> 1.1, >= 1.2.0)
+ activesupport (6.1.3)
+ concurrent-ruby (~> 1.0, >= 1.0.2)
+ i18n (>= 1.6, < 2)
+ minitest (>= 5.1)
+ tzinfo (~> 2.0)
+ zeitwerk (~> 2.3)
+ addressable (2.7.0)
+ public_suffix (>= 2.0.2, < 5.0)
+ archive-zip (0.12.0)
+ io-like (~> 0.3.0)
+ ast (2.4.2)
+ builder (3.2.4)
+ capybara (3.35.3)
+ addressable
+ mini_mime (>= 0.1.3)
+ nokogiri (~> 1.8)
+ rack (>= 1.6.0)
+ rack-test (>= 0.6.3)
+ regexp_parser (>= 1.5, < 3.0)
+ xpath (~> 3.2)
+ childprocess (3.0.0)
+ chromedriver-helper (1.2.0)
+ archive-zip (~> 0.10)
+ nokogiri (~> 1.8)
+ coderay (1.1.3)
+ concurrent-ruby (1.1.8)
+ crass (1.0.6)
+ diff-lcs (1.4.4)
+ erubi (1.10.0)
+ execjs (2.7.0)
+ filecache (1.0.2)
+ i18n (1.8.9)
+ concurrent-ruby (~> 1.0)
+ io-like (0.3.1)
+ loofah (2.9.0)
+ crass (~> 1.0.2)
+ nokogiri (>= 1.5.9)
+ method_source (1.0.0)
+ mini_mime (1.0.2)
+ mini_portile2 (2.5.0)
+ minitest (5.14.4)
+ mustermann (1.1.1)
+ ruby2_keywords (~> 0.0.1)
+ nio4r (2.5.7)
+ nokogiri (1.11.2)
+ mini_portile2 (~> 2.5.0)
+ racc (~> 1.4)
+ opal (1.1.1)
+ ast (>= 2.3.0)
+ parser (~> 3.0)
+ opal-sprockets (1.0.0)
+ opal (>= 1.0, < 1.2)
+ sprockets (~> 4.0)
+ tilt (>= 1.4)
+ parser (3.0.0.0)
+ ast (~> 2.4.1)
+ pry (0.14.0)
+ coderay (~> 1.1)
+ method_source (~> 1.0)
+ public_suffix (4.0.6)
+ puma (5.2.2)
+ nio4r (~> 2.0)
+ racc (1.5.2)
+ rack (2.2.3)
+ rack-protection (2.1.0)
+ rack
+ rack-test (1.1.0)
+ rack (>= 1.0, < 3)
+ rails-dom-testing (2.0.3)
+ activesupport (>= 4.2.0)
+ nokogiri (>= 1.6)
+ rails-html-sanitizer (1.3.0)
+ loofah (~> 2.3)
+ regexp_parser (2.1.1)
+ rspec (3.10.0)
+ rspec-core (~> 3.10.0)
+ rspec-expectations (~> 3.10.0)
+ rspec-mocks (~> 3.10.0)
+ rspec-core (3.10.1)
+ rspec-support (~> 3.10.0)
+ rspec-expectations (3.10.1)
+ diff-lcs (>= 1.2.0, < 2.0)
+ rspec-support (~> 3.10.0)
+ rspec-mocks (3.10.2)
+ diff-lcs (>= 1.2.0, < 2.0)
+ rspec-support (~> 3.10.0)
+ rspec-support (3.10.2)
+ ruby2_keywords (0.0.4)
+ rubyzip (2.3.0)
+ selenium-webdriver (3.142.7)
+ childprocess (>= 0.5, < 4.0)
+ rubyzip (>= 1.2.2)
+ sinatra (2.1.0)
+ mustermann (~> 1.0)
+ rack (~> 2.2)
+ rack-protection (= 2.1.0)
+ tilt (~> 2.0)
+ sprockets (4.0.2)
+ concurrent-ruby (~> 1.0)
+ rack (> 1, < 3)
+ tilt (2.0.10)
+ timecop (0.8.1)
+ tzinfo (2.0.4)
+ concurrent-ruby (~> 1.0)
+ uglifier (4.2.0)
+ execjs (>= 0.3.0, < 3)
+ unparser (0.6.0)
+ diff-lcs (~> 1.3)
+ parser (>= 3.0.0)
+ webdrivers (4.6.0)
+ nokogiri (~> 1.6)
+ rubyzip (>= 1.3.0)
+ selenium-webdriver (>= 3.0, < 4.0)
+ xpath (3.2.0)
+ nokogiri (~> 1.8)
+ zeitwerk (2.4.2)
+
+PLATFORMS
+ ruby
+
+DEPENDENCIES
+ hyper-spec!
+ opal
+ opal-sprockets
+ pry
+ puma
+ rack
+ rspec
+ sinatra
+
+BUNDLED WITH
+ 2.1.4
diff --git a/ruby/examples/misc/sinatra_app/app.rb b/ruby/examples/misc/sinatra_app/app.rb
new file mode 100644
index 000000000..e6897f9be
--- /dev/null
+++ b/ruby/examples/misc/sinatra_app/app.rb
@@ -0,0 +1,32 @@
+require "bundler"
+Bundler.require
+
+module OpalSprocketsServer
+ def self.opal
+ @opal ||= Opal::Sprockets::Server.new do |s|
+ s.append_path "app"
+ s.main = "application"
+ s.debug = ENV["RACK_ENV"] != "production"
+ end
+ end
+end
+
+get "/" do
+ <<~HTML
+
+
+
+ #{Opal::Sprockets.javascript_include_tag('application', debug: OpalSprocketsServer.opal.debug, sprockets: OpalSprocketsServer.opal.sprockets, prefix: '/assets')}
+
+
+ HTML
+end
+
+def app
+ Rack::Builder.app do
+ map "/assets" do
+ run OpalSprocketsServer.opal.sprockets
+ end
+ run Sinatra::Application
+ end
+end
diff --git a/ruby/examples/misc/sinatra_app/app/application.rb b/ruby/examples/misc/sinatra_app/app/application.rb
new file mode 100644
index 000000000..42ddc8e00
--- /dev/null
+++ b/ruby/examples/misc/sinatra_app/app/application.rb
@@ -0,0 +1,3 @@
+require 'opal'
+
+puts 'hello world'
diff --git a/ruby/examples/misc/sinatra_app/config.ru b/ruby/examples/misc/sinatra_app/config.ru
new file mode 100644
index 000000000..565f58587
--- /dev/null
+++ b/ruby/examples/misc/sinatra_app/config.ru
@@ -0,0 +1,3 @@
+require "./app.rb"
+
+run app
diff --git a/ruby/examples/misc/sinatra_app/spec/spec_helper.rb b/ruby/examples/misc/sinatra_app/spec/spec_helper.rb
new file mode 100644
index 000000000..5a5daab18
--- /dev/null
+++ b/ruby/examples/misc/sinatra_app/spec/spec_helper.rb
@@ -0,0 +1,18 @@
+# spec/spec_helper.rb
+
+require "bundler"
+Bundler.require
+ENV["RACK_ENV"] ||= "test"
+
+require File.join(File.dirname(__FILE__), "..", "app.rb")
+
+require "rspec"
+require "rack/test"
+require "hyper-spec/rack"
+
+Capybara.app = HyperSpecTestController.wrap(app: app)
+
+set :environment, :test
+set :run, false
+set :raise_errors, true
+set :logging, false
diff --git a/ruby/examples/misc/sinatra_app/spec/test_spec.rb b/ruby/examples/misc/sinatra_app/spec/test_spec.rb
new file mode 100644
index 000000000..d5353b91f
--- /dev/null
+++ b/ruby/examples/misc/sinatra_app/spec/test_spec.rb
@@ -0,0 +1,6 @@
+require "spec_helper"
+describe "The App", no_reset: true, js: true do
+ it "works" do
+ expect { 12 + 12 }.on_client_to eq 24
+ end
+end
diff --git a/ruby/hyper-spec/lib/hyper-spec/helpers.rb b/ruby/hyper-spec/lib/hyper-spec/helpers.rb
index ac881d813..c5d05df04 100644
--- a/ruby/hyper-spec/lib/hyper-spec/helpers.rb
+++ b/ruby/hyper-spec/lib/hyper-spec/helpers.rb
@@ -95,7 +95,9 @@ def client_option(opts = {})
end
def default_arity_check
- Rails&.application&.config&.opal&.arity_check_enabled if defined? Rails
+ Rails.application.config.opal.arity_check_enabled if defined? Rails
+ rescue StandardError
+ false
end
alias client_options client_option
From 10adb71b9b19d1fe0da1f8584613680651c57e70 Mon Sep 17 00:00:00 2001
From: Mitch VanDuyn
Date: Sun, 14 Mar 2021 19:21:55 -0400
Subject: [PATCH 198/307] Update html-css.md
test update
---
docs/client-dsl/html-css.md | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/docs/client-dsl/html-css.md b/docs/client-dsl/html-css.md
index df6ed1876..eb14c5d06 100644
--- a/docs/client-dsl/html-css.md
+++ b/docs/client-dsl/html-css.md
@@ -8,7 +8,7 @@ A Hyperstack user-interface is composed of HTML elements, conditional logic and
```ruby
UL do
- 10.times { |n| LI { "Number #{n}" }}
+ 5.times { |n| LI { "Number #{n}" }}
end
```
@@ -86,4 +86,4 @@ For `style` you need to pass a hash:
```ruby
PARA(style: { display: item[:some_property] == "some state" ? :block : :none })
-```
\ No newline at end of file
+```
From 1975f42418e4005684226111057f7f59f45a87d5 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 14 Mar 2021 20:05:50 -0400
Subject: [PATCH 199/307] updated hyper-spec docs
---
docs/SUMMARY.md | 7 +-
docs/development-workflow/hyper-spec.md | 422 -----------------
docs/hyper-spec/01-installation.md | 57 ---
docs/hyper-spec/02-tutorial.md | 122 -----
.../03-hyperspec-methods-and-features.md | 440 ------------------
docs/hyper-spec/04-using-with-rack.md | 56 ---
docs/hyper-spec/README.md | 41 --
7 files changed, 5 insertions(+), 1140 deletions(-)
delete mode 100644 docs/development-workflow/hyper-spec.md
delete mode 100644 docs/hyper-spec/01-installation.md
delete mode 100644 docs/hyper-spec/02-tutorial.md
delete mode 100644 docs/hyper-spec/03-hyperspec-methods-and-features.md
delete mode 100644 docs/hyper-spec/04-using-with-rack.md
delete mode 100644 docs/hyper-spec/README.md
diff --git a/docs/SUMMARY.md b/docs/SUMMARY.md
index 479a46bd8..5b96f359b 100644
--- a/docs/SUMMARY.md
+++ b/docs/SUMMARY.md
@@ -23,10 +23,13 @@
* [Development Workflow](development-workflow/README.md)
* [Debugging](development-workflow/debugging.md)
* [Internationalization](development-workflow/hyper-i18n.md)
- * [HyperSpec](development-workflow/hyper-spec.md)
+ * [HyperSpec](development-workflow/hyper-spec/README.md)
+ * [Installation](development-workflow/hyper-spec/01-installation.md)
+ * [Tutorial](development-workflow/hyper-spec/02-tutorial.md)
+ * [Methods and Features](development-workflow/hyper-spec/03-methods-and-features.md)
+ * [Using with Rack](development-workflow/hyper-spec/04-using-with-rack.md)
* [Tools](development-workflow/tools.md)
* [Tutorial](tutorial/README.md)
* [TodoMVC Tutorial Part I](tutorial/todo.md)
* [TodoMVC Tutorial Part II](tutorial/todo-part-2.md)
* [Community](community.md)
-
diff --git a/docs/development-workflow/hyper-spec.md b/docs/development-workflow/hyper-spec.md
deleted file mode 100644
index a6341f6a3..000000000
--- a/docs/development-workflow/hyper-spec.md
+++ /dev/null
@@ -1,422 +0,0 @@
-# HyperSpec
-
-With HyperSpec you can run _isomorphic_ specs for all your Hyperstack code using RSpec. Everything runs as standard RSpec test specs.
-
-For example if you have a component like this:
-
-```ruby
-class SayHello < HyperComponent
- param :name
- render(DIV) do
- "Hello there #{name}"
- end
-end
-```
-
-Your test spec would look like this:
-
-```ruby
-describe 'SayHello', js: true do
- it 'has the correct content' do
- mount "SayHello", name: 'Fred'
- expect(page).to have_content('Hello there Fred')
- end
-end
-```
-
-The `mount` method will setup a blank client window, and _mount_ the named component in the window, passing any parameters.
-
-Notice that the spec will need a client environment so we must set `js: true`.
-
-The `mount` method can also take a block which will be recompiled and sent to the client before mounting the component. You can place any client side code in the mount block including the definition of components.
-
-```ruby
-describe "the mount's code block", js: true do
- it 'will be recompiled on the client' do
- mount 'ShowOff' do
- class ShowOff < HyperComponent
- render(DIV) { 'Now how cool is that???' }
- end
- end
- expect(page).to have_content('Now how cool is that???' )
- end
-end
-```
-
-## Why?
-
-Hyperstack wants to make the server-client divide as transparent to the developer as practical. Given this, it makes sense that the testing should also be done with as little concern for client versus server.
-
-HyperSpec allows you to directly use tools like FactoryBot \(or Hyperstack Operations\) to setup some test data, then run a spec to make sure that a component correctly displays, or modifies that data. You can use Timecop to manipulate time and keep in sync between the server and client. This makes testing easier and more realistic without writing a lot of redundant code.
-
-## Installation
-
-These instructions are assuming you are using Rails as the backend. However the `hyper-spec` gem itself does not require Rails, so you can adapt these instructions as needed.
-
-### Add the gems
-
-In your `Gemfile` add
-
-```ruby
-group :test do
- gem 'hyper-spec', path: '../hyperstack/ruby/hyper-spec'
- gem 'database_cleaner' # optional but we find it works best due to the concurrency of hyperstack
-end
-```
-
-and `bundle install`
-
-### Install RSpec files
-
-`bundle exec rails g rspec:install`
-
-> Skip this step if rspec is already installed.
-
-### Configure HyperSpec
-
-Update your `spec/rails_helper.rb` so it looks like this:
-
-```ruby
-# This file is copied to spec/ when you run 'rails generate rspec:install'
-require 'spec_helper'
-ENV['RAILS_ENV'] ||= 'test'
-require File.expand_path('../../config/environment', __FILE__)
-# Prevent database truncation if the environment is production
-abort("The Rails environment is running in production mode!") if Rails.env.production?
-require 'rspec/rails'
-# Add additional requires below this line. Rails is not loaded until this point!
-
-# THESE ARE LINES WE ARE ADDING
-# JUST MAKE SURE THEY ARE AFTER `require 'rspec/rails'`
-
-# pull in the hyper-spec code.
-require 'hyper-spec'
-
-# If you are using DatabaseCleaner here is where
-# you set the mode. We recommend truncation.
-DatabaseCleaner.strategy = :truncation
-
-# Now we setup Rspec details
-RSpec.configure do |config|
-
- # This is only needed if you are using DatabaseCleaner
- config.before(:each) do
- DatabaseCleaner.clean
- end
-
- # If you are NOT using webpacker remove this block
- config.before(:suite) do # compile front-end
- Webpacker.compile
- end
-end
-...
-```
-
-### Create an install smoke test
-
-Make sure your installation is working by creating a simple smoke test like this:
-
-```ruby
-# spec/hyperspec_smoke_test.rb
-require 'rails_helper'
-
-describe 'Hyperspec', js: true do
- it 'can mount and test a component' do
- mount "HyperSpecTest" do
- class HyperSpecTest < HyperComponent
- render(DIV) do
- "It's Alive!"
- end
- end
- end
- expect(page).to have_content("It's Alive!")
- end
- it 'can evaluate and test expressions on the client' do
- expect_evaluate_ruby do
- [1, 2, 3].reverse
- end.to eq [3, 2, 1]
- end
-end
-```
-
-To run it do a
-`bundle exec rspec spec/hyperspec_smoke_test.rb`
-
-> Note that because the test does not end in `_spec.rb` it will not be run with the rest of your specs.
-
-## Environment Variables
-
-You can set `DRIVER` to `chrome` to run the client in chrome and see what is going on. By default tests will run in chrome headless mode which is quicker, but harder to debug problems.
-
-```text
-DRIVER=chrome bundle exec rspec
-```
-
-## Spec Helpers
-
-HyperSpec adds the following spec helpers to your test environment
-
-* `mount`
-* `client_option` and `client_options`
-* `on_client`
-* `isomorphic`
-* `evaluate_ruby`
-* `expect_evaluate_ruby`
-* `expect_promise`
-* call back and event history methods
-* `pause`
-* `attributes_on_client`
-* `size_window`
-* `add_class`
-
-#### The `mount` Method
-
-`mount` takes the name of a component, prepares an empty test window, and mounts the named component in the window.
-You may give a block to `mount` which will be recompiled on the client, and run _before_ mounting. This means that the component mounted may be actually defined in the block, which is useful for setting up top level wrapper components, which will invoke your component under test. You can also modify existing components for white box testing, or local fixture data, constants, etc.
-
-`mount` may also be given a hash of the parameters to be passed to the component.
-
-```ruby
-mount 'Display', test: 123 do
- class Display < HyperComponent
- param :test
- render(DIV) { test.to_s }
- end
-end
-```
-
-#### The `client_option` Method
-
-There are several options that control the mounting process. Use `client_option` \(or `client_options`\) before accessing any client side to set any of these options:
-
-* `render_on`: `:server_only`, `:client_only`, or `:both`, default is client\_only.
-* `layout`: specify the layout to be used. Default is :none.
-* `style_sheet`: specify the name of the style sheet to be loaded. Defaults to the application stylesheet.
-* `javascript`: specify the name of the javascript asset file to be loaded. Defaults to the application js file.
-
-For example:
-
-```ruby
-it "can be rendered server side only" do
- client_option render_on: :server_only
- mount 'SayHello', name: 'George'
- expect(page).to have_content('Hello there George')
- # Server only means no code is downloaded to the client
- expect(evaluate_script('typeof React')).to eq('undefined')
-end
-```
-
-If you need to pull in alternative style sheets and javascript files, the recommended way to do this is to
-
-1. Add them to a `specs/assets/stylesheets` and `specs/assets/javascripts` directory and
-2. Add the following line to your `config/environment/test.rb` file:
-
- ```ruby
- config.assets.paths << ::Rails.root.join('spec', 'assets', 'stylesheets').to_s
- config.assets.paths << ::Rails.root.join('spec', 'assets', 'javascripts').to_s
- ```
-
-This way you will not pollute your application with these 'test only' files.
-
-_The javascript spec asset files can be `.rb` files and contain ruby code as well. See the specs for examples!_
-
-#### The `on_client` Method
-
-`on_client` takes a block and compiles and runs it on the client. This is useful in setting up test constants and client only fixtures.
-
-Note that `on_client` needs to _proceed_ any calls to `mount`, `evaluate_ruby`, `expect_evaluate_ruby` or `expect_promise` as these methods will initiate the client load process.
-
-#### The `isomorphic` Method
-
-Similar to `on_client` but the block is _also_ run on the server. This is useful for setting constants shared by both client and server, and modifying behavior of isomorphic classes such as ActiveRecord models, and HyperOperations.
-
-```ruby
-isomorphic do
- class SomeModel < ActiveRecord::Base
- def fake_attribute
- 12
- end
- end
-end
-```
-
-#### The `evaluate_ruby` Method
-
-Takes either a string or a block, dynamically compiles it, downloads it to the client and runs it.
-
-```ruby
-evaluate_ruby do
- i = 12
- i * 2
-end
-# returns 24
-
-isomorphic do
- def factorial(n)
- n == 1 ? 1 : n * factorial(n-1)
- end
-end
-
-expect(evaluate_ruby("factorial(5)")).to eq(factorial(5))
-```
-
-`evaluate_ruby` can also be very useful for debug. Set a breakpoint in your test, then use `evaluate_ruby` to interrogate the state of the client.
-
-#### The `expect_evaluate_ruby` Method
-
-Combines expect and evaluate methods:
-
-```ruby
-expect_evaluate_ruby do
- i = 1
- 5.times { |n| i = i*n }
- i
-end.to eq(120)
-```
-
-#### The `expect_promise` Method
-
-Works like `expect_evaluate_ruby` but is used with promises. `expect_promise` will hang until the promise resolves and then return to the results.
-
-```ruby
-expect_promise do
- Promise.new.tap do |p|
- after(2) { p.resolve('hello') }
- end
-end.to eq('hello')
-```
-
-#### Call Back and Event History Methods
-
-HyperReact components can _generate_ events and perform callbacks. HyperSpec provides methods to test if an event or callback was made.
-
-```ruby
-mount 'CallBackOnEveryThirdClick' do
- class CallBackOnEveryThirdClick < HyperComponent
- fires :click3
- def increment_click
- @clicks ||= 0
- @clicks = (@clicks + 1)
- click3!(@clicks) if @clicks % 3 == 0
- end
- render do
- DIV(class: :tp_clicker) { "click me" }
- .on(:click) { increment_click }
- end
- end
-end
-
-7.times { page.click('#tp_clicker') }
-expect(callback_history_for(:click3)).to eq([[3], [6]])
-```
-
-* `callback_history_for`: the entire history given as an array of arrays
-* `last_callback_for`: same as `callback_history_for(xxx).last`
-* `clear_callback_history_for`: clears the array \(userful for repeating test variations without remounting\)
-* `event_history_for, last_event_for, clear_event_history_for`: same but for events.
-
-#### The `pause` Method
-
-For debugging. Everything stops, until you type `go()` in the client console. Running `binding.pry` also has this effect, and is often sufficient, however it will also block the server from responding unless you have a multithreaded server.
-
-#### The `attributes_on_client` Method
-
-_This feature is currently untested - use at your own risk._
-
-This reads the value of active record model attributes on the client.
-
-In other words the method `attributes_on_client` is added to all ActiveRecord models. You then take a model you have instance of on the server, and by passing the Capybara page object, you get back the attributes for that same model instance, currently on the client.
-
-```ruby
-expect(some_record_on_server.attributes_on_client(page)[:fred]).to eq(12)
-```
-
-> Note that after persisting a record the client and server will be synced so this is mainly useful for debug or in rare cases where it is important to interrogate the value on the client before its persisted.
-
-#### The `size_window` Method
-
-Sets the size of the test window. You can say: `size_window(width, height)` or pass one of the following standard sizes: to one of the following standard sizes:
-
-* small: 480 X 320
-* mobile: 640 X 480
-* tablet: 960 X 640
-* large: 1920 X 6000
-* default: 1024 X 768
-
-example: `size_window(:mobile)`
-
-You can also modify the standard sizes with `:portrait`
-
-example: `size_window(:table, :portrait)`
-
-You can also specify the size by providing the width and height.
-
-example: `size_window(600, 600)`
-
-size\_window with no parameters is the same as `size_window(:default)`
-
-Typically you will use this in a `before(:each)` or `before(:step)` block
-
-#### The `add_class` Method
-
-Sometimes it's useful to change styles during testing \(mainly for debug so that changes on screen are visible.\)
-
-The `add_class` method takes a class name \(as a symbol or string\), and hash representing the style.
-
-```ruby
-it "can add classes during testing" do
- add_class :some_class, borderStyle: :solid
- mount 'StyledDiv' do
- class StyledDiv < HyperComponent
- render(DIV, id: 'hello', class: 'some_class') do
- 'Hello!'
- end
- end
- end
- expect(page.find('#hello').native.css_value('border-right-style')).to eq('solid')
-end
-```
-
-## Integration with the Steps gem
-
-The [rspec-steps gem](https://github.com/LRDesign/rspec-steps) can be useful in doing client side testing. Without rspec-steps, each test spec will cause a reload of the browser window. While this insures that each test runs in a clean environment, it is typically not necessary and can really slow down testing.
-
-The rspec-steps gem will run each test without reloading the window, which is usually fine.
-
-Checkout the rspec-steps example in the `hyper_spec.rb` file for an example.
-
-> Note that hopefully in the near future we are going to build a custom capybara driver that will just directly talk to Hyperstack on the client side. Once this is in place these troubles should go away! - Volunteers welcome to help!\*
-
-## Timecop Integration
-
-HyperSpec is integrated with [Timecop](https://github.com/travisjeffery/timecop) to freeze, move and speed up time. The client and server times will be kept in sync when you use any these Timecop methods:
-
-* `freeze`: Freezes time at the specified point in time \(default is Time.now\)
-* `travel`: Time runs normally forward from the point specified.
-* `scale`: Like travel but times runs faster.
-* `return`: Return to normal system time.
-
-For example:
-
-```ruby
-Timecop.freeze # freeze time at current time
-# ... test some stuff
-Timecop.freeze Time.now+10.minutes # move time forward 10 minutes
-# ... check to see if expected events happened etc
-Timecop.return
-```
-
-```ruby
-Timecop.scale 60, Time.now-1.year do
- # Time will begin 1 year ago but advance 60 times faster than normal
- sleep 10
- # still sleeps for 10 seconds YOUR time, but server and client will
- # think 10 minutes have passed
-end
-# no need for Timecop.return if using the block style
-```
-
-See the Timecop [README](https://github.com/travisjeffery/timecop/blob/master/README.markdown) for more details.
-
-> There is one confusing thing to note: On the server if you `sleep` then you will sleep for the specified number of seconds when viewed _outside_ of the test. However inside the test environment if you look at Time.now, you will see it advancing according to the scale factor. Likewise if you have a `after` or `every` block on the client, you will wait according to _simulated_ time.
-
diff --git a/docs/hyper-spec/01-installation.md b/docs/hyper-spec/01-installation.md
deleted file mode 100644
index 11a2b79d9..000000000
--- a/docs/hyper-spec/01-installation.md
+++ /dev/null
@@ -1,57 +0,0 @@
-# HyperSpec Installation
-
-Add `gem 'hyper-spec'` to your Gemfile in the usual way. Typically in a Rails app you will add this in the test section of your Gemfile:
-
-```ruby
-group :test do
- gem 'hyper-spec', '~> 1.0.alpha1.0'
-end
-```
-
-Make sure to `bundle install`.
-
-> Note: if you want to use the unreleased edge branch your hyper-spec gem specification will be:
->
-> ```ruby
-> gem 'hyper-spec',
-> git: 'git://github.com/hyperstack-org/hyperstack.git',
-> branch: 'edge',
-> glob: 'ruby/*/*.gemspec'
-> ```
-
-HyperSpec is integrated with the `pry` gem for debugging, so it is recommended to add the `pry` gem as well.
-
-HyperSpec will also use the `timecop` gem if present to allow you to control and synchronize time on the server and the client.
-
-A typical spec_helper file when using HyperSpec will look like this:
-
-```ruby
-# spec_helper.rb
-require 'hyper-spec'
-require 'pry' # optional
-
-ENV["RAILS_ENV"] ||= 'test'
-require File.expand_path('../test_app/config/environment', __FILE__)
-
-require 'rspec/rails'
-require 'timecop' # optional
-
-# any other rspec configuration you need
-# note HyperSpec will include chrome driver for providing the client
-# run time environment
-```
-
-To load the webdriver and client environment your spec should have the
-`:js` flag set:
-
-```ruby
-# the js flag can be set on the entire group of specs, or a context
-describe 'some hyper-specs', :js do
- ...
-end
-
-# or for an individual spec
- it 'an individual hyper-spec', :js do
- ...
- end
-```
diff --git a/docs/hyper-spec/02-tutorial.md b/docs/hyper-spec/02-tutorial.md
deleted file mode 100644
index d988dc86c..000000000
--- a/docs/hyper-spec/02-tutorial.md
+++ /dev/null
@@ -1,122 +0,0 @@
-# Tutorial
-
-For this quick tutorial lets assume you have an existing Rails app that
-already uses RSpec to which you have added a first Hyperstack component to
-try things out.
-
-For your trial, you have created a very simple component that shows
-the number of orders shipped by your companies website:
-
-```ruby
-class OrdersShipped < HyperComponent
- def format_number(number)
- number.to_s.reverse.gsub(/(\d{3})(?=\d)/, '\\1,').reverse
- end
-
- render(DIV, class: 'orders-shipped') do
- format_number Order.shipped.count
- end
-end
-```
-
-> Note that styling can be taken care of in the usual way by
-> providing styles for the `orders-shipped` css class. All we care
-> about here is the *function* of the component.
-
-Meanwhile `Order` is an ActiveRecord Model that would look something like this:
-
-```ruby
-class Order < ApplicationRecord
- ...
- scope :shipped, -> () { where(status: :shipped) }
- ...
-end
-```
-
-> Note that when using ActiveRecord models in your specs you will
-> need to add the appropriate database setup and cleaner methods like you would
-> for any specs used with ActiveRecord. We assume here that as each
-> spec starts there are no records in the database
-
-The `OrdersShipped` component can be mounted on any page of your site,
-and assuming the proper policy permissions are provided it will
-show the total orders shipped, and will dynamically increase in
-realtime.
-
-A partial spec for this component might look like this:
-
-```ruby
-require 'spec_helper'
-
-describe 'OrdersShipped', :js do
- it 'dynamically displays the orders shipped' do
- mount 'OrdersShipped'
- expect(find('div.orders-shipped')).to have_content(0)
- Order.create(status: :shipped)
- expect(find('div.orders-shipped')).to have_content(1)
- Order.last.destroy
- expect(find('div.orders-shipped')).to have_content(0)
- end
-
- it '#format method' do
- on_client { @comp = OrdersShipped.new }
- ['1,234,567', '123', '1,234'].each do |n|
- expect { @comp.format_number(n.gsub(',','').to_i) }
- .on_client_to eq(n)
- end
- end
-end
-```
-
-If you are familiar with Capybara then the first spec should
-look similar to an integration spec. The difference is instead
-of visiting a page, we `mount` the `OrdersShipped` component on a blank page
-that hyper-spec will set up for us. This lets us unit test
-components outside of any application specific view logic.
-
-> Note that like Capybara we indicate that a client environment should
-> be set up by adding the :js tag.
-
-Once mounted we can use Capybara finders and matchers to check
-if our content is as expected. Because we are running on the server
-we can easily add and delete orders, and check the response on the UI.
-
-The second spec shows how we can do some white box unit testing of our
-component. Instead of mounting the component we just create a new
-instance which will be invisible since it was not mounted. For this we
-use the `on_client` method.
-
-The `on_client` method takes a block, and will
-compile that block using
-Opal, and execute it on the client. In this case we simply create a
-new `OrderShipped` instance, and assign it to an instance variable, which as you
-will see will continue to be available to us later in the spec.
-
-> Note, if you are an RSpec purist, you would probably prefer to see
-> something like `let` be used here instead of an instance variable. Shall we
-> say its on the todo list.
-
-Now that we have our test component setup we can test its `format_number`
-method. To do this we put the test expression in a block followed by
-`on_client_to`. Again the block will be compiled using Opal, executed on
-the client, and the result will be returned to the expectation.
-
-Notice that the server side variable `n` can be read (but not written) within
-the client block. All local variables, memoized variables, and instance variables can
-can be read in the client block as long as they represent objects that can be
-sensibly marshalled and unmarshalled.
-
-This has covered the basics of Hyperspec - in summary:
-
-+ The `js` tag indicates the spec will be using a client environment.
-+ `mount`: Mount a component on a blank page. This replaces the `visit` method
-for unit testing components.
-+ `on_client`: Execute Ruby code on the client (and return the result).
-+ `on_client_to`: Execute the expectation block on the client, and then check
-the expectation (on the server.)
-+ Instance variables retain their values between client execution blocks.
-+ All variables accessible to the spec are copied to the client if possible.
-
-There are many other features such as dealing with promises, passing data to
-and from a mounted component, using the `Timecop` gem, and working with a `pry`
-session. So read on.
diff --git a/docs/hyper-spec/03-hyperspec-methods-and-features.md b/docs/hyper-spec/03-hyperspec-methods-and-features.md
deleted file mode 100644
index 8fec6d0c6..000000000
--- a/docs/hyper-spec/03-hyperspec-methods-and-features.md
+++ /dev/null
@@ -1,440 +0,0 @@
-# HyperSpec Methods and Features
-
-### Expectation Helpers
-
-These can be used any where within your specs:
-
-+ [`on_client`](#the-on_client-method) - executes code on the client
-+ [`isomorphic`](#the-isomorphic-method) - executes code on the client *and* the server
-+ [`mount`](#mounting-components) - mounts a hyperstack component in an empty window
-+ [`before_mount`](#before_mount) - specifies a block of code to be executed before the first call to `mount`, `isomorphic` or `on_client`
-+ [`insert_html`](#insert_html) - insert some html into a page
-+ [`client_options`](#client-initialization-options) - allows options to be specified globally
-+ [`run_on_client`](#run_on_client) - same as `on_client` but no value is returned
-+ [`reload_page`](#reload_page) - resets the page environment
-+ [`add_class`](#add_class) - adds a CSS class
-+ [`size_window`](#size_window) - specifies how big the client window should be
-+ [`attributes_on_client`](#attributes_on_client) - returns any ActiveModel attributes loaded on the client
-
-These methods are used after mounting a component to retrieve
-events sent outwards from the component:
-
-+ [`callback_history_for`](#retrieving-event-data-from-the-mounted-component)
-+ [`last_callback_for`](#retrieving-event-data-from-the-mounted-component)
-+ [`clear_callback_history_for`](#retrieving-event-data-from-the-mounted-component)
-+ [`event_history_for`](#retrieving-event-data-from-the-mounted-component)
-+ [`last_event_for`](#retrieving-event-data-from-the-mounted-component)
-+ [`clear_event_history_for`](#retrieving-event-data-from-the-mounted-component)
-
-### Expectation Targets
-
-These can be used within expectations replacing the `to` and `not_to` methods. The expectation expression must be inclosed in a block.
-
-+ [`on_client_to`](#client-expectation-targets), [`to_on_client_not`](#client-expectation-targets) - the expression will be evaluated on the client, and matched on the server.
-
-These methods have the following aliases to make your specs more readable:
-+ [`to_on_client`](#client-expectation-targets)
-+ [`on_client_to_not`](#client-expectation-targets)
-+ [`on_client_not_to`](#client-expectation-targets)
-+ [`to_not_on_client`](#client-expectation-targets)
-+ [`not_to_on_client`](#client-expectation-targets)
-+ [`to_then`](#client-expectation-targets)
-+ [`then_to_not`](#client-expectation-targets)
-+ [`then_not_to`](#client-expectation-targets)
-+ [`to_not_then`](#client-expectation-targets)
-+ [`not_to_then`](#client-expectation-targets)
-
-in addition
-+ [`with`](#client-expectation-targets) - can be chained with the above methods to pass data to initialize local variables on the client
-
-### Other Debugging Aids
-
-The following methods are used primarly at a debug break point, most require you use binding.pry as your debugger:
-
-+ [`to_js`](#to_js) - returns the ruby code compiled to JS.
-+ [`c?`](#c?) - alias for `on_client`.
-+ [`ppr`](#ppr) - print the results of the ruby expression on the client console.
-+ [`debugger`](#debugger) - Sets a debug breakpoint on code running on the client.
-+ [`open_in_chrome`](#open_in_chrome) - Opens a chrome browser that will load the current state.
-+ [`pause`](#pause) - Halts execution on the server without blocking I/O.
-
-### Available Webdrivers
-
-HyperSpec comes integrated with Chrome and Chrome headless webdrivers. The default configuration will run using Chrome headless. To see what is going on set the `DRIVER` environment variable to `chrome`
-```bash
-DRIVER=chrome bundle exec rspec
-```
-
-### Timecop Integration
-
-You can use the [`timecop` gem](https://github.com/travisjeffery/timecop) to control the flow of time within your specs. Hyperspec will coordinate things with the client so the time on the client is kept in sync with the time on the server. So for example if you use Timecop to advance time 1 day on the server, time on the browser will also advance by one day.
-
-See the [Client Initialization Options](#client-initialization-options) section for how to control the client time zone, and clock resolution.
-
-### The `no_reset` flag
-
-By default the client environment will be reinitialized at the beginning of every spec. If this is not needed you can speed things up by adding the `no_reset` flag to a block of specs.
-
-# Details
-
-### The `on_client` method
-
-The on_client method takes a block. The ruby code inside the block will be executed on the client, and the result will be returned.
-
-```ruby
- it 'will print a message on the client' do
- on_client do
- puts 'hey I am running here on the client!'
- end
- end
-```
-
-If the block returns a promise Hyperspec will wait for the promise to be resolved (or rejected) before returning. For example:
-
-```ruby
- it 'waits for a promise' do
- start_time = Time.now
- result = on_client do
- promise = Promise.new
- after(10.seconds) { promise.resolve('done!') }
- promise
- end
- expect(result).to eq('done!')
- expect(Time.now-start_time).to be >= 10.seconds
- end
-```
-> HyperSpec will do its best to reconstruct the result back on the server in some sensible way. Occasionally it just doesn't work, in which case you can end the block with a `nil` or some other simple expression, or use the `run_on_client` method, which does not return the result.
-
-### Accessing variables on the client
-
-It is often useful to pass variables from the spec to the client. Hyperspec will copy all your local variables, memoized variables, and instance variables known at the time the `on_client` block is compiled to the client.
-```ruby
- let!(memoized) { 'a memoized variable' }
- it 'will pass variables to the client' do
- local = 'a local variable'
- @instance = 'an instance variable'
- result = on_client { [memoized, local, @instance] }
- expect(result).to eq [memoized, local, @instance]
- end
-```
-> Note that memoized variables are not initialized until first
-accessed, so you probably want to use the let! method unless you
-are sure you are accessing the memoized value before sending it to the client.
-
-The value of instance variables initialized on the client are preserved
-across blocks executed on the client. For example:
-```ruby
- it 'remembers instance variables' do
- on_client { @total = 0 }
- 10.times do |i|
- # note how we are passing i in
- on_client { @total += i }
- end
- result = on_client { @total }
- expect(result).to eq(10 * 11 / 2)
- end
-```
-
-> Be especially careful of this when using the [`no_reset` flag](#the-no_reset-flag) as instance variables will retain their values between each spec in this mode.
-
-#### White and Black Listing Variables
-
-By default all local variables, memoized variables, and instance variables in scope in the spec will be copied to the client. This can be controlled through the `include_vars` and `exclude_vars` [client options](#client-initialization-options).
-
-`include_vars` can be set to
-+ an array of symbols: only those vars will be copied,
-+ a single symbol: only that var will be copied,
-+ any other truthy value: all vars will be copied (the default)
-+ or nil, false, or an empty array: no vars will be copied.
-
-`exclude_vars` can be set to
-+ an array of symbols - those vars will **not** be copied,
-+ a single symbol - only that var will be excluded,
-+ any other truthy value - no vars will be copied,
-+ or nil, false, or an empty array - all vars will be copied (the default).
-
-Examples:
-
-```Ruby
- # don't copy vars at all.
- client_option exclude_vars: true
- # only copy var1 and the instance var @var2
- client_option include_vars: [:var1, :@var2]
- # only exclude foo_var
- client_option exclude_vars: :foo_var
-```
-
-Note that the exclude_vars list will take precedence over the include_vars list.
-
-The exclude/include lists can be overridden on an individual call to on_client by providing a hash of names and values to on_client:
-
-```ruby
- result = on_client(var: 12) { var * var }
- expect(result).to eq(144)
-```
-
-You can do the same thing on expectations using the `with` method - See [Client Expectation Targets](#client-expectation-targets).
-
-
-### The `isomorphic` method
-
-The `isomorphic` method works the same as `on_client` but in addition it also executes the same block on the server. It is especially useful when doing some testing of
-ActiveRecord models, where you might want to modify the behavior of the model on server and the client.
-
-```ruby
- it 'can run code the same everywhere!' do
- isomorphic do
- def factorial(x)
- x.zero? ? 1 : x * factorial(x - 1)
- end
- end
-
- on_the_client = on_client { factorial(7) }
- on_the_server = factorial(7)
- expect(on_the_client).to eq(on_the_server)
- end
-```
-
-### Client Initialization Options
-
-The first time a spec runs code on the client, it has to initialize a browser context. You can use the `client_options` (aka `client_option`) method to specify the following options when the page is loaded.
-
-+ `time_zone` - browsers always run in the local time zone, if you want to force the browser to act as if its in a different zone, you can use the time_zone option, and provide any valid zone that the rails `in_time_zone` method will accept.
-Example: `client_option time_zone: 'Hawaii'`
-+ `clock_resolution`: Indicates the resolution that the simulated clock will run at on the client, when using the TimeCop gem. The default value is 20 (milliseconds).
-+ `include_vars`: white list of all vars to be copied to the client. See [Accessing Variables on the Client](#accessing-variables-on-the-client) for details.
-+ `exclude_vars`: black list of all vars not to be copied to the client. See [Accessing Variables on the Client](#accessing-variables-on-the-client) for details.
-+ `render_on`: `:client_only` (default), `:server_only`, or `:both`
-Hyperstack components can be prerendered on the server. The `render_on` option controls this feature. For example `server_only` is useful to insure components are properly prerendered. *See the `mount` method [below](#mounting-components) for more details on rendering components*
-+ `no_wait`: After the page is loaded the system will by default wait until all javascript requests to the server complete before proceeding. Specifying `no_wait: true` will skip this.
-+ `javascript`: The javascript asset to load when mounting the component. By default it will be `application` (.js is assumed). Note that the standard Hyperstack configuration will compile all the client side Ruby assets as well as javascript packages into the `application.js` file, so the default will work fine.
-+ `style_sheet`: The style sheet asset to load when mounting the component. By default it will be `application` (.css is assumed).
-+ `controller` - **(expert zone!)** specify a controller that will be used to mount the
-component. By default hyper-spec will build a controller and route to handle the request from the client to mount the component.
-
-Any other options not listed above will be passed along to the Rail's controller `render` method. So for example you could specify some other specific layout using `client_option layout: 'special_layout'`
-
-Note that this method can be used in the `before(:each)` block of a spec context to provide options for all the specs in the block.
-
-### Mounting Components
-
-The `mount` method is used to render a component on a page:
-
-```ruby
- it 'can display a component for me' do
- mount 'SayHello', name: 'Lannar' do
- class SayHello < HyperComponent
- param :name
- render(DIV) do
- "Hello #{name}!"
- end
- end
- end
-
- expect(page).to have_content('Hello Lannar')
- end
-```
-
-The `mount` method has a few options. In it's simplest form you specify just the name of the component that is already defined in your hyperstack code and it will be mounted.
-
-You can add parameters that will be passed to the component as in the above example. As the above example also shows you can also define code within the block. This is just shorthand for defining the code before hand using `on_client`. The code does not have to be the component being mounted, but might be just some logic to help with the test.
-
-In addition `mount` can take any of the options provided to `client_options` (see above.) To provide these options, you must provide a (possibly) empty params hash. For example:
-```ruby
-mount 'MyComponent', {... params ... }, {... opts ... }
-```
-
-### Retrieving Event Data From the Mounted Component
-
-Components *receive* parameters, and may send callbacks and events back out. To test if a component has sent the appropriate data you can use the following methods:
-
-+ `callback_history_for`
-+ `last_callback_for`
-+ `clear_callback_history_for`
-+ `event_history_for`
-+ `last_event_for`
-+ `clear_event_history_for`
-
-```ruby
- it 'can check on a clients events and callbacks' do
- mount 'BigTalker' do
- class BigTalker < HyperComponent
- fires :i_was_clicked
- param :call_me_back, type: Proc
-
- before_mount { @click_counter = 0 }
-
- render(DIV) do
- BUTTON { 'click me' }.on(:click) do
- @click_counter += 1
- i_was_clicked!
- call_me_back.call(@click_counter)
- end
- end
- end
- end
- 3.times do
- find('button').click
- end
- # the history is an array, one element for each item in the history
- expect(event_history_for(:i_was_clicked).length).to eq(3)
- # each item in the array is itself an array of the arguments
- expect(last_call_back_for(:call_me_back)).to eq([3])
- # clearing the history resets the array to empty
- clear_event_history_for(:i_was_clicked)
- expect(event_history_for(:i_was_clicked).length).to eq(0)
- end
-```
-
-> Note that you must declare the params as type `Proc`, or use
-the `fires` method to declare an event for the history mechanism to work.
-
-### Other Helpers
-
-#### `before_mount`
-
-Specifies a block of code to be executed before the first call to `mount`, `isomorphic` or `on_client`. This is primarly useful to add to an rspec `before(:each)` block containing common client code needed by all the specs in the context.
-
-> Unlike `mount`, `isomorphic` and `on_client`, `before_mount` does not load the client page, but will wait for the first of the other methods to be called.
-
-#### `add_class`
-
-Adds a CSS class. The first parameter is the name of the class, and the second is a hash of styles, represented in the React [style format.](https://reactjs.org/docs/dom-elements.html#style)
-
-Example: `add_class :some_class, borderStyle: :solid` adds a class with style `border-style: 'solid'`
-
-#### `run_on_client`
-
-same as `on_client` but no value is returned. Useful when the return value may be too complex to marshall and unmarshall using JSON.
-
-#### `reload_page`
-
-Shorthand for `mount` with no parameters. Useful if you need to reset the client within a spec.
-
-#### `size_window`
-
-Indicates the size of the browser window. The values can be given either symbolically or as two numbers (width and height). Predefined sizes are:
-
-+ `:small`: 480 x 320
-+ `:mobile` 640 x 480
-+ `:tablet` 960 x 64,
-+ `:large` 1920 x 6000
-+ `:default` 1024 x 768
-
-All of the above can be modified by providing the `:portrait` option as the first or second parameter.
-
-So for example the following are all equivalent:
-
-+ `size_window(:small, :portrait)`
-+ `size_window(:portrait, :small)`
-+ `size_window(320, 480)`
-
-#### `attributes_on_client`
-
-returns any `ActiveModel` attributes loaded on the client. HyperModel will normally begin a load cycle as soon as you access the attribute on the client. However it is sometimes useful to see what attributes have already been loaded.
-
-#### `insert_html`
-
-takes a string and inserts it into test page when it is mounted. Useful for testing code that is not dependent on Hyper Components.
-For example an Opal library that adds some jQuery extensions.
-
-### Client Expectation Targets
-
-These can be used within expectations replacing the `to` and `not_to` methods. The expectation expression must be inclosed in a block.
-
-For example:
-
-```ruby
-it 'has built-in expectation targets' do
- expect { RUBY_ENGINE }.on_client_to eq('opal')
-end
-```
-
-The above expectation is short for saying:
-
-```ruby
- result = on_client { RUBY_ENGINE }
- expect(result).to eq('opal')
-```
-
-These methods have the following aliases to make your specs more readable:
-+ `to_on_client`
-+ `on_client_to_not`
-+ `on_client_not_to`
-+ `to_not_on_client`
-+ `not_to_on_client`
-+ `to_then`
-+ `then_to_not`
-+ `then_not_to`
-+ `to_not_then`
-+ `not_to_then`
-
-The `then` variants are useful to note that the spec involves a promise, but it does no explicit checking that the result comes from a promise.
-
-In addition the `with` method can be chained with the above methods to pass data to initialize local variables on the client:
-
-```ruby
- it 'can pass values to the client using the with method' do
- expect { foo * foo }.with(foo: 12).to_on_client eq(144)
- end
-```
-
-By default HyperSpec will copy all local variables, memoized variables, and instance variables defined in a spec to the client. The specific variables can also be white listed and black listed. The `with` method overrides any white or black listed values. So for example if you prefer to use the more explicit `with` method to pass values to the client, you can add `client_option exclude_vars: true` in a `before(:all)` block in your spec helper. See [Accessing Variables on the Client](#accessing-variables-on-the-client) for details.
-
-### Useful Debug Methods
-
-These methods are primarily designed to help debug code and specs.
-
-#### `c?`
-
-Shorthand for `on_client`, useful for entering expressions in the pry console, to investigate the state of the client.
-
-```ruby
-pry:> c? { puts 'hello on the console' } # prints hello on the client
--> nil
-```
-
-#### `to_js`
-
-Takes a block like `on_client` but rather than running the code on the client, simply returns the resulting code. This is useful for debugging obscure problems when the Opal compiler or some feature of
-Hyperspec is suspected as the issue.
-
-#### `ppr`
-
-Takes a block like `on_client` and prints the result on the client console using JS console.log. Equivalent to doing
-
-```ruby
- on_client do
- begin
- ...
- end.tap { |r| `console.log(r)` }
- end
-```
-
-This is useful when the result cannot be usefully returned to the server,
-or when the result of interest is better looked at as the raw
-javascript object.
-
-#### `debugger`
-
-This psuedo method can be inserted into any code executed on the client. It will cause the code to stop, and enter a *javascript* read-eval loop, within the debug console.
-
-Unfortunately ATM we do not have the technology to enter a *Ruby* read-eval loop at an arbitrary point on the client.
-
-> Note: due to a bug in the Opal compiler your code should not have `debugger` as the last expression in a method or a block. In this situation add any expression (such as nil) after the debugger statement.
-```ruby
-def foo
- ... some code ...
- debugger # this will fail with a compiler syntax error
-end
-```
-
-#### `open_in_chrome`
-By default specs are run with headless chrome, so there is no visible browser window. The `open_in_chrome` method will open a browser window, and load it with the current state.
-
-You can also run specs in a visible chrome window by setting the `DRIVER` environment variable to `chrome`. i.e. (`DRIVER=chrome bundle exec rspec ...`)
-
-#### `pause`
-The method is typically not needed assuming you are using a multithreaded server like Puma. If for whatever reason the pry debug session is not multithreaded, *and* you want to try some kind of experiment on the javascript console, *and* those experiments make requests to the server, you may not get a response, because all threads are in use.
-
-You can resolve this by using the `pause` method in the debug session which will put the server debug session into a non-blocking loop. You can then experiment in the JS console, and when done release the pause by executing `go()` in the *javascript* debug console.
diff --git a/docs/hyper-spec/04-using-with-rack.md b/docs/hyper-spec/04-using-with-rack.md
deleted file mode 100644
index 7c5147f40..000000000
--- a/docs/hyper-spec/04-using-with-rack.md
+++ /dev/null
@@ -1,56 +0,0 @@
-# Using Hyperspec with Rack
-
-Hyperspec will run with Rails out of the box, but you can also use Hyperspec with any Rack application, with just a little more setup. For example here is a sample configuration setup with Sinatra:
-
-```ruby
-# Gemfile
-...
-
-gem "sinatra"
-gem "rspec"
-gem "pry"
-gem "opal"
-gem "opal-sprockets"
-gem "rack"
-gem "puma"
-group :test do
- # gem 'hyper-spec', '~> 1.0.alpha1.0'
- # or to use edge:
- gem 'hyper-spec',
- git: 'git://github.com/hyperstack-org/hyperstack.git',
- branch: 'edge',
- glob: 'ruby/*/*.gemspec'
-end
-```
-
-```ruby
-# spec/spec_helper.rb
-
-require "bundler"
-Bundler.require
-ENV["RACK_ENV"] ||= "test"
-
-# require your application files as needed
-require File.join(File.dirname(__FILE__), "..", "app.rb")
-
-# bring in needed support files
-require "rspec"
-require "rack/test"
-require "hyper-spec/rack"
-
-# assumes your sinatra app is named app
-Capybara.app = HyperSpecTestController.wrap(app: app)
-
-set :environment, :test
-set :run, false
-set :raise_errors, true
-set :logging, false
-```
-
-### Details
-
-The interface between Hyperspec and your application environment is defined by the `HyperspecTestController` class. This file typically includes a set of helper methods from `HyperSpec::ControllerHelpers`, which can then be overridden to give whatever behavior your specific framework needs. Have a look at the `hyper-spec/rack.rb` and `hyper-spec/controller_helpers.rb` files in the Hyperspec gem directory.
-
-### Example
-
-A complete (but very simple) example is in this repos `ruby/examples/misc/sinatra_app` directory
diff --git a/docs/hyper-spec/README.md b/docs/hyper-spec/README.md
deleted file mode 100644
index 44dd165e3..000000000
--- a/docs/hyper-spec/README.md
+++ /dev/null
@@ -1,41 +0,0 @@
-# HyperSpec
-
-## Adding client side testing to RSpec
-
-The `hyper-spec` gem supports the Hyperstack goals of programmer productivity and seamless web development by allowing testing to be done with minimal concern for the client-server interface.
-
-The `hyper-spec` gem adds functionality to the `rspec`, `capybara`, `timecop` and `pry` gems allowing you to do the following:
-
-+ write component and integration tests using the rspec syntax and helpers
-+ write specs that run on both the client and server
-+ evaluate client side ruby expressions from within specs and while using `pry`
-+ share data between the client and server within your specs
-+ control and synchronize time on the client and the server
-
-HyperSpec can be used standalone, but if used as part of a Hyperstack application it allows straight forward testing of Hyperstack Components and your ActiveRecord Models.
-
-So for example here is part of a simple unit test of a TodoIndex component:
-
-```ruby
-it "will update the TodoIndex", js: true do
- # mounts the TodoIndex component (client side)
- mount 'TodoIndex'
- # Todo is an ActiveRecord Model
- # create a new Todo on the server (we could use FactoryBot of course)
- todo_1 = Todo.create(title: 'this todo created on the server')
- # verify that UI got updated
- expect(find('.ToDoItem-Text').text).to eq todo_1.title
- # verify that the count of Todos on the client side DB matches the server
- expect { Todo.count }.on_client_to eq Todo.count
- # now create another Todo on the client
- new_todo_title = 'this todo created on the client'
- # note that local variables are copied from the server to the client
- on_client { Todo.create(title: new_todo_title) }
- # the Todo should now be reflected on the server
- expect(Todo.last.title).to eq new_todo_title
-end
-```
-
-When using HyperSpec all the specs execute on the server side, but they may also interrogate the state of the UI as well as the state
-of any of the client side objects. The specs can execute any valid Ruby code client side to create new test objects as well as do
-white box testing. This keeps the logic of your specs in one place.
From 38bead6c7f3ce6ca55d3a615d7b433fef0e8ca52 Mon Sep 17 00:00:00 2001
From: catmando
Date: Sun, 14 Mar 2021 20:23:58 -0400
Subject: [PATCH 200/307] added hyperspec docs
---
.../hyper-spec/01-installation.md | 58 +++
.../hyper-spec/02-tutorial.md | 122 +++++
.../hyper-spec/03-methods-and-features.md | 440 ++++++++++++++++++
.../hyper-spec/04-using-with-rack.md | 56 +++
.../development-workflow/hyper-spec/README.md | 41 ++
5 files changed, 717 insertions(+)
create mode 100644 docs/development-workflow/hyper-spec/01-installation.md
create mode 100644 docs/development-workflow/hyper-spec/02-tutorial.md
create mode 100644 docs/development-workflow/hyper-spec/03-methods-and-features.md
create mode 100644 docs/development-workflow/hyper-spec/04-using-with-rack.md
create mode 100644 docs/development-workflow/hyper-spec/README.md
diff --git a/docs/development-workflow/hyper-spec/01-installation.md b/docs/development-workflow/hyper-spec/01-installation.md
new file mode 100644
index 000000000..86deea4be
--- /dev/null
+++ b/docs/development-workflow/hyper-spec/01-installation.md
@@ -0,0 +1,58 @@
+# HyperSpec Installation
+
+Add `gem 'hyper-spec'` to your Gemfile in the usual way.
+Typically in a Rails app you will add this in the test section of your Gemfile:
+
+```ruby
+group :test do
+ gem 'hyper-spec', '~> 1.0.alpha1.0'
+end
+```
+
+Make sure to `bundle install`.
+
+> Note: if you want to use the unreleased edge branch your hyper-spec gem specification will be:
+>
+> ```ruby
+> gem 'hyper-spec',
+> git: 'git://github.com/hyperstack-org/hyperstack.git',
+> branch: 'edge',
+> glob: 'ruby/*/*.gemspec'
+> ```
+
+HyperSpec is integrated with the `pry` gem for debugging, so it is recommended to add the `pry` gem as well.
+
+HyperSpec will also use the `timecop` gem if present to allow you to control and synchronize time on the server and the client.
+
+A typical spec_helper file when using HyperSpec will look like this:
+
+```ruby
+# spec_helper.rb
+require 'hyper-spec'
+require 'pry' # optional
+
+ENV["RAILS_ENV"] ||= 'test'
+require File.expand_path('../test_app/config/environment', __FILE__)
+
+require 'rspec/rails'
+require 'timecop' # optional
+
+# any other rspec configuration you need
+# note HyperSpec will include chrome driver for providing the client
+# run time environment
+```
+
+To load the webdriver and client environment your spec should have the
+`:js` flag set:
+
+```ruby
+# the js flag can be set on the entire group of specs, or a context
+describe 'some hyper-specs', :js do
+ ...
+end
+
+# or for an individual spec
+ it 'an individual hyper-spec', :js do
+ ...
+ end
+```
diff --git a/docs/development-workflow/hyper-spec/02-tutorial.md b/docs/development-workflow/hyper-spec/02-tutorial.md
new file mode 100644
index 000000000..d988dc86c
--- /dev/null
+++ b/docs/development-workflow/hyper-spec/02-tutorial.md
@@ -0,0 +1,122 @@
+# Tutorial
+
+For this quick tutorial lets assume you have an existing Rails app that
+already uses RSpec to which you have added a first Hyperstack component to
+try things out.
+
+For your trial, you have created a very simple component that shows
+the number of orders shipped by your companies website:
+
+```ruby
+class OrdersShipped < HyperComponent
+ def format_number(number)
+ number.to_s.reverse.gsub(/(\d{3})(?=\d)/, '\\1,').reverse
+ end
+
+ render(DIV, class: 'orders-shipped') do
+ format_number Order.shipped.count
+ end
+end
+```
+
+> Note that styling can be taken care of in the usual way by
+> providing styles for the `orders-shipped` css class. All we care
+> about here is the *function* of the component.
+
+Meanwhile `Order` is an ActiveRecord Model that would look something like this:
+
+```ruby
+class Order < ApplicationRecord
+ ...
+ scope :shipped, -> () { where(status: :shipped) }
+ ...
+end
+```
+
+> Note that when using ActiveRecord models in your specs you will
+> need to add the appropriate database setup and cleaner methods like you would
+> for any specs used with ActiveRecord. We assume here that as each
+> spec starts there are no records in the database
+
+The `OrdersShipped` component can be mounted on any page of your site,
+and assuming the proper policy permissions are provided it will
+show the total orders shipped, and will dynamically increase in
+realtime.
+
+A partial spec for this component might look like this:
+
+```ruby
+require 'spec_helper'
+
+describe 'OrdersShipped', :js do
+ it 'dynamically displays the orders shipped' do
+ mount 'OrdersShipped'
+ expect(find('div.orders-shipped')).to have_content(0)
+ Order.create(status: :shipped)
+ expect(find('div.orders-shipped')).to have_content(1)
+ Order.last.destroy
+ expect(find('div.orders-shipped')).to have_content(0)
+ end
+
+ it '#format method' do
+ on_client { @comp = OrdersShipped.new }
+ ['1,234,567', '123', '1,234'].each do |n|
+ expect { @comp.format_number(n.gsub(',','').to_i) }
+ .on_client_to eq(n)
+ end
+ end
+end
+```
+
+If you are familiar with Capybara then the first spec should
+look similar to an integration spec. The difference is instead
+of visiting a page, we `mount` the `OrdersShipped` component on a blank page
+that hyper-spec will set up for us. This lets us unit test
+components outside of any application specific view logic.
+
+> Note that like Capybara we indicate that a client environment should
+> be set up by adding the :js tag.
+
+Once mounted we can use Capybara finders and matchers to check
+if our content is as expected. Because we are running on the server
+we can easily add and delete orders, and check the response on the UI.
+
+The second spec shows how we can do some white box unit testing of our
+component. Instead of mounting the component we just create a new
+instance which will be invisible since it was not mounted. For this we
+use the `on_client` method.
+
+The `on_client` method takes a block, and will
+compile that block using
+Opal, and execute it on the client. In this case we simply create a
+new `OrderShipped` instance, and assign it to an instance variable, which as you
+will see will continue to be available to us later in the spec.
+
+> Note, if you are an RSpec purist, you would probably prefer to see
+> something like `let` be used here instead of an instance variable. Shall we
+> say its on the todo list.
+
+Now that we have our test component setup we can test its `format_number`
+method. To do this we put the test expression in a block followed by
+`on_client_to`. Again the block will be compiled using Opal, executed on
+the client, and the result will be returned to the expectation.
+
+Notice that the server side variable `n` can be read (but not written) within
+the client block. All local variables, memoized variables, and instance variables can
+can be read in the client block as long as they represent objects that can be
+sensibly marshalled and unmarshalled.
+
+This has covered the basics of Hyperspec - in summary:
+
++ The `js` tag indicates the spec will be using a client environment.
++ `mount`: Mount a component on a blank page. This replaces the `visit` method
+for unit testing components.
++ `on_client`: Execute Ruby code on the client (and return the result).
++ `on_client_to`: Execute the expectation block on the client, and then check
+the expectation (on the server.)
++ Instance variables retain their values between client execution blocks.
++ All variables accessible to the spec are copied to the client if possible.
+
+There are many other features such as dealing with promises, passing data to
+and from a mounted component, using the `Timecop` gem, and working with a `pry`
+session. So read on.
diff --git a/docs/development-workflow/hyper-spec/03-methods-and-features.md b/docs/development-workflow/hyper-spec/03-methods-and-features.md
new file mode 100644
index 000000000..8fec6d0c6
--- /dev/null
+++ b/docs/development-workflow/hyper-spec/03-methods-and-features.md
@@ -0,0 +1,440 @@
+# HyperSpec Methods and Features
+
+### Expectation Helpers
+
+These can be used any where within your specs:
+
++ [`on_client`](#the-on_client-method) - executes code on the client
++ [`isomorphic`](#the-isomorphic-method) - executes code on the client *and* the server
++ [`mount`](#mounting-components) - mounts a hyperstack component in an empty window
++ [`before_mount`](#before_mount) - specifies a block of code to be executed before the first call to `mount`, `isomorphic` or `on_client`
++ [`insert_html`](#insert_html) - insert some html into a page
++ [`client_options`](#client-initialization-options) - allows options to be specified globally
++ [`run_on_client`](#run_on_client) - same as `on_client` but no value is returned
++ [`reload_page`](#reload_page) - resets the page environment
++ [`add_class`](#add_class) - adds a CSS class
++ [`size_window`](#size_window) - specifies how big the client window should be
++ [`attributes_on_client`](#attributes_on_client) - returns any ActiveModel attributes loaded on the client
+
+These methods are used after mounting a component to retrieve
+events sent outwards from the component:
+
++ [`callback_history_for`](#retrieving-event-data-from-the-mounted-component)
++ [`last_callback_for`](#retrieving-event-data-from-the-mounted-component)
++ [`clear_callback_history_for`](#retrieving-event-data-from-the-mounted-component)
++ [`event_history_for`](#retrieving-event-data-from-the-mounted-component)
++ [`last_event_for`](#retrieving-event-data-from-the-mounted-component)
++ [`clear_event_history_for`](#retrieving-event-data-from-the-mounted-component)
+
+### Expectation Targets
+
+These can be used within expectations replacing the `to` and `not_to` methods. The expectation expression must be inclosed in a block.
+
++ [`on_client_to`](#client-expectation-targets), [`to_on_client_not`](#client-expectation-targets) - the expression will be evaluated on the client, and matched on the server.
+
+These methods have the following aliases to make your specs more readable:
++ [`to_on_client`](#client-expectation-targets)
++ [`on_client_to_not`](#client-expectation-targets)
++ [`on_client_not_to`](#client-expectation-targets)
++ [`to_not_on_client`](#client-expectation-targets)
++ [`not_to_on_client`](#client-expectation-targets)
++ [`to_then`](#client-expectation-targets)
++ [`then_to_not`](#client-expectation-targets)
++ [`then_not_to`](#client-expectation-targets)
++ [`to_not_then`](#client-expectation-targets)
++ [`not_to_then`](#client-expectation-targets)
+
+in addition
++ [`with`](#client-expectation-targets) - can be chained with the above methods to pass data to initialize local variables on the client
+
+### Other Debugging Aids
+
+The following methods are used primarly at a debug break point, most require you use binding.pry as your debugger:
+
++ [`to_js`](#to_js) - returns the ruby code compiled to JS.
++ [`c?`](#c?) - alias for `on_client`.
++ [`ppr`](#ppr) - print the results of the ruby expression on the client console.
++ [`debugger`](#debugger) - Sets a debug breakpoint on code running on the client.
++ [`open_in_chrome`](#open_in_chrome) - Opens a chrome browser that will load the current state.
++ [`pause`](#pause) - Halts execution on the server without blocking I/O.
+
+### Available Webdrivers
+
+HyperSpec comes integrated with Chrome and Chrome headless webdrivers. The default configuration will run using Chrome headless. To see what is going on set the `DRIVER` environment variable to `chrome`
+```bash
+DRIVER=chrome bundle exec rspec
+```
+
+### Timecop Integration
+
+You can use the [`timecop` gem](https://github.com/travisjeffery/timecop) to control the flow of time within your specs. Hyperspec will coordinate things with the client so the time on the client is kept in sync with the time on the server. So for example if you use Timecop to advance time 1 day on the server, time on the browser will also advance by one day.
+
+See the [Client Initialization Options](#client-initialization-options) section for how to control the client time zone, and clock resolution.
+
+### The `no_reset` flag
+
+By default the client environment will be reinitialized at the beginning of every spec. If this is not needed you can speed things up by adding the `no_reset` flag to a block of specs.
+
+# Details
+
+### The `on_client` method
+
+The on_client method takes a block. The ruby code inside the block will be executed on the client, and the result will be returned.
+
+```ruby
+ it 'will print a message on the client' do
+ on_client do
+ puts 'hey I am running here on the client!'
+ end
+ end
+```
+
+If the block returns a promise Hyperspec will wait for the promise to be resolved (or rejected) before returning. For example:
+
+```ruby
+ it 'waits for a promise' do
+ start_time = Time.now
+ result = on_client do
+ promise = Promise.new
+ after(10.seconds) { promise.resolve('done!') }
+ promise
+ end
+ expect(result).to eq('done!')
+ expect(Time.now-start_time).to be >= 10.seconds
+ end
+```
+> HyperSpec will do its best to reconstruct the result back on the server in some sensible way. Occasionally it just doesn't work, in which case you can end the block with a `nil` or some other simple expression, or use the `run_on_client` method, which does not return the result.
+
+### Accessing variables on the client
+
+It is often useful to pass variables from the spec to the client. Hyperspec will copy all your local variables, memoized variables, and instance variables known at the time the `on_client` block is compiled to the client.
+```ruby
+ let!(memoized) { 'a memoized variable' }
+ it 'will pass variables to the client' do
+ local = 'a local variable'
+ @instance = 'an instance variable'
+ result = on_client { [memoized, local, @instance] }
+ expect(result).to eq [memoized, local, @instance]
+ end
+```
+> Note that memoized variables are not initialized until first
+accessed, so you probably want to use the let! method unless you
+are sure you are accessing the memoized value before sending it to the client.
+
+The value of instance variables initialized on the client are preserved
+across blocks executed on the client. For example:
+```ruby
+ it 'remembers instance variables' do
+ on_client { @total = 0 }
+ 10.times do |i|
+ # note how we are passing i in
+ on_client { @total += i }
+ end
+ result = on_client { @total }
+ expect(result).to eq(10 * 11 / 2)
+ end
+```
+
+> Be especially careful of this when using the [`no_reset` flag](#the-no_reset-flag) as instance variables will retain their values between each spec in this mode.
+
+#### White and Black Listing Variables
+
+By default all local variables, memoized variables, and instance variables in scope in the spec will be copied to the client. This can be controlled through the `include_vars` and `exclude_vars` [client options](#client-initialization-options).
+
+`include_vars` can be set to
++ an array of symbols: only those vars will be copied,
++ a single symbol: only that var will be copied,
++ any other truthy value: all vars will be copied (the default)
++ or nil, false, or an empty array: no vars will be copied.
+
+`exclude_vars` can be set to
++ an array of symbols - those vars will **not** be copied,
++ a single symbol - only that var will be excluded,
++ any other truthy value - no vars will be copied,
++ or nil, false, or an empty array - all vars will be copied (the default).
+
+Examples:
+
+```Ruby
+ # don't copy vars at all.
+ client_option exclude_vars: true
+ # only copy var1 and the instance var @var2
+ client_option include_vars: [:var1, :@var2]
+ # only exclude foo_var
+ client_option exclude_vars: :foo_var
+```
+
+Note that the exclude_vars list will take precedence over the include_vars list.
+
+The exclude/include lists can be overridden on an individual call to on_client by providing a hash of names and values to on_client:
+
+```ruby
+ result = on_client(var: 12) { var * var }
+ expect(result).to eq(144)
+```
+
+You can do the same thing on expectations using the `with` method - See [Client Expectation Targets](#client-expectation-targets).
+
+
+### The `isomorphic` method
+
+The `isomorphic` method works the same as `on_client` but in addition it also executes the same block on the server. It is especially useful when doing some testing of
+ActiveRecord models, where you might want to modify the behavior of the model on server and the client.
+
+```ruby
+ it 'can run code the same everywhere!' do
+ isomorphic do
+ def factorial(x)
+ x.zero? ? 1 : x * factorial(x - 1)
+ end
+ end
+
+ on_the_client = on_client { factorial(7) }
+ on_the_server = factorial(7)
+ expect(on_the_client).to eq(on_the_server)
+ end
+```
+
+### Client Initialization Options
+
+The first time a spec runs code on the client, it has to initialize a browser context. You can use the `client_options` (aka `client_option`) method to specify the following options when the page is loaded.
+
++ `time_zone` - browsers always run in the local time zone, if you want to force the browser to act as if its in a different zone, you can use the time_zone option, and provide any valid zone that the rails `in_time_zone` method will accept.
+Example: `client_option time_zone: 'Hawaii'`
++ `clock_resolution`: Indicates the resolution that the simulated clock will run at on the client, when using the TimeCop gem. The default value is 20 (milliseconds).
++ `include_vars`: white list of all vars to be copied to the client. See [Accessing Variables on the Client](#accessing-variables-on-the-client) for details.
++ `exclude_vars`: black list of all vars not to be copied to the client. See [Accessing Variables on the Client](#accessing-variables-on-the-client) for details.
++ `render_on`: `:client_only` (default), `:server_only`, or `:both`
+Hyperstack components can be prerendered on the server. The `render_on` option controls this feature. For example `server_only` is useful to insure components are properly prerendered. *See the `mount` method [below](#mounting-components) for more details on rendering components*
++ `no_wait`: After the page is loaded the system will by default wait until all javascript requests to the server complete before proceeding. Specifying `no_wait: true` will skip this.
++ `javascript`: The javascript asset to load when mounting the component. By default it will be `application` (.js is assumed). Note that the standard Hyperstack configuration will compile all the client side Ruby assets as well as javascript packages into the `application.js` file, so the default will work fine.
++ `style_sheet`: The style sheet asset to load when mounting the component. By default it will be `application` (.css is assumed).
++ `controller` - **(expert zone!)** specify a controller that will be used to mount the
+component. By default hyper-spec will build a controller and route to handle the request from the client to mount the component.
+
+Any other options not listed above will be passed along to the Rail's controller `render` method. So for example you could specify some other specific layout using `client_option layout: 'special_layout'`
+
+Note that this method can be used in the `before(:each)` block of a spec context to provide options for all the specs in the block.
+
+### Mounting Components
+
+The `mount` method is used to render a component on a page:
+
+```ruby
+ it 'can display a component for me' do
+ mount 'SayHello', name: 'Lannar' do
+ class SayHello < HyperComponent
+ param :name
+ render(DIV) do
+ "Hello #{name}!"
+ end
+ end
+ end
+
+ expect(page).to have_content('Hello Lannar')
+ end
+```
+
+The `mount` method has a few options. In it's simplest form you specify just the name of the component that is already defined in your hyperstack code and it will be mounted.
+
+You can add parameters that will be passed to the component as in the above example. As the above example also shows you can also define code within the block. This is just shorthand for defining the code before hand using `on_client`. The code does not have to be the component being mounted, but might be just some logic to help with the test.
+
+In addition `mount` can take any of the options provided to `client_options` (see above.) To provide these options, you must provide a (possibly) empty params hash. For example:
+```ruby
+mount 'MyComponent', {... params ... }, {... opts ... }
+```
+
+### Retrieving Event Data From the Mounted Component
+
+Components *receive* parameters, and may send callbacks and events back out. To test if a component has sent the appropriate data you can use the following methods:
+
++ `callback_history_for`
++ `last_callback_for`
++ `clear_callback_history_for`
++ `event_history_for`
++ `last_event_for`
++ `clear_event_history_for`
+
+```ruby
+ it 'can check on a clients events and callbacks' do
+ mount 'BigTalker' do
+ class BigTalker < HyperComponent
+ fires :i_was_clicked
+ param :call_me_back, type: Proc
+
+ before_mount { @click_counter = 0 }
+
+ render(DIV) do
+ BUTTON { 'click me' }.on(:click) do
+ @click_counter += 1
+ i_was_clicked!
+ call_me_back.call(@click_counter)
+ end
+ end
+ end
+ end
+ 3.times do
+ find('button').click
+ end
+ # the history is an array, one element for each item in the history
+ expect(event_history_for(:i_was_clicked).length).to eq(3)
+ # each item in the array is itself an array of the arguments
+ expect(last_call_back_for(:call_me_back)).to eq([3])
+ # clearing the history resets the array to empty
+ clear_event_history_for(:i_was_clicked)
+ expect(event_history_for(:i_was_clicked).length).to eq(0)
+ end
+```
+
+> Note that you must declare the params as type `Proc`, or use
+the `fires` method to declare an event for the history mechanism to work.
+
+### Other Helpers
+
+#### `before_mount`
+
+Specifies a block of code to be executed before the first call to `mount`, `isomorphic` or `on_client`. This is primarly useful to add to an rspec `before(:each)` block containing common client code needed by all the specs in the context.
+
+> Unlike `mount`, `isomorphic` and `on_client`, `before_mount` does not load the client page, but will wait for the first of the other methods to be called.
+
+#### `add_class`
+
+Adds a CSS class. The first parameter is the name of the class, and the second is a hash of styles, represented in the React [style format.](https://reactjs.org/docs/dom-elements.html#style)
+
+Example: `add_class :some_class, borderStyle: :solid` adds a class with style `border-style: 'solid'`
+
+#### `run_on_client`
+
+same as `on_client` but no value is returned. Useful when the return value may be too complex to marshall and unmarshall using JSON.
+
+#### `reload_page`
+
+Shorthand for `mount` with no parameters. Useful if you need to reset the client within a spec.
+
+#### `size_window`
+
+Indicates the size of the browser window. The values can be given either symbolically or as two numbers (width and height). Predefined sizes are:
+
++ `:small`: 480 x 320
++ `:mobile` 640 x 480
++ `:tablet` 960 x 64,
++ `:large` 1920 x 6000
++ `:default` 1024 x 768
+
+All of the above can be modified by providing the `:portrait` option as the first or second parameter.
+
+So for example the following are all equivalent:
+
++ `size_window(:small, :portrait)`
++ `size_window(:portrait, :small)`
++ `size_window(320, 480)`
+
+#### `attributes_on_client`
+
+returns any `ActiveModel` attributes loaded on the client. HyperModel will normally begin a load cycle as soon as you access the attribute on the client. However it is sometimes useful to see what attributes have already been loaded.
+
+#### `insert_html`
+
+takes a string and inserts it into test page when it is mounted. Useful for testing code that is not dependent on Hyper Components.
+For example an Opal library that adds some jQuery extensions.
+
+### Client Expectation Targets
+
+These can be used within expectations replacing the `to` and `not_to` methods. The expectation expression must be inclosed in a block.
+
+For example:
+
+```ruby
+it 'has built-in expectation targets' do
+ expect { RUBY_ENGINE }.on_client_to eq('opal')
+end
+```
+
+The above expectation is short for saying:
+
+```ruby
+ result = on_client { RUBY_ENGINE }
+ expect(result).to eq('opal')
+```
+
+These methods have the following aliases to make your specs more readable:
++ `to_on_client`
++ `on_client_to_not`
++ `on_client_not_to`
++ `to_not_on_client`
++ `not_to_on_client`
++ `to_then`
++ `then_to_not`
++ `then_not_to`
++ `to_not_then`
++ `not_to_then`
+
+The `then` variants are useful to note that the spec involves a promise, but it does no explicit checking that the result comes from a promise.
+
+In addition the `with` method can be chained with the above methods to pass data to initialize local variables on the client:
+
+```ruby
+ it 'can pass values to the client using the with method' do
+ expect { foo * foo }.with(foo: 12).to_on_client eq(144)
+ end
+```
+
+By default HyperSpec will copy all local variables, memoized variables, and instance variables defined in a spec to the client. The specific variables can also be white listed and black listed. The `with` method overrides any white or black listed values. So for example if you prefer to use the more explicit `with` method to pass values to the client, you can add `client_option exclude_vars: true` in a `before(:all)` block in your spec helper. See [Accessing Variables on the Client](#accessing-variables-on-the-client) for details.
+
+### Useful Debug Methods
+
+These methods are primarily designed to help debug code and specs.
+
+#### `c?`
+
+Shorthand for `on_client`, useful for entering expressions in the pry console, to investigate the state of the client.
+
+```ruby
+pry:> c? { puts 'hello on the console' } # prints hello on the client
+-> nil
+```
+
+#### `to_js`
+
+Takes a block like `on_client` but rather than running the code on the client, simply returns the resulting code. This is useful for debugging obscure problems when the Opal compiler or some feature of
+Hyperspec is suspected as the issue.
+
+#### `ppr`
+
+Takes a block like `on_client` and prints the result on the client console using JS console.log. Equivalent to doing
+
+```ruby
+ on_client do
+ begin
+ ...
+ end.tap { |r| `console.log(r)` }
+ end
+```
+
+This is useful when the result cannot be usefully returned to the server,
+or when the result of interest is better looked at as the raw
+javascript object.
+
+#### `debugger`
+
+This psuedo method can be inserted into any code executed on the client. It will cause the code to stop, and enter a *javascript* read-eval loop, within the debug console.
+
+Unfortunately ATM we do not have the technology to enter a *Ruby* read-eval loop at an arbitrary point on the client.
+
+> Note: due to a bug in the Opal compiler your code should not have `debugger` as the last expression in a method or a block. In this situation add any expression (such as nil) after the debugger statement.
+```ruby
+def foo
+ ... some code ...
+ debugger # this will fail with a compiler syntax error
+end
+```
+
+#### `open_in_chrome`
+By default specs are run with headless chrome, so there is no visible browser window. The `open_in_chrome` method will open a browser window, and load it with the current state.
+
+You can also run specs in a visible chrome window by setting the `DRIVER` environment variable to `chrome`. i.e. (`DRIVER=chrome bundle exec rspec ...`)
+
+#### `pause`
+The method is typically not needed assuming you are using a multithreaded server like Puma. If for whatever reason the pry debug session is not multithreaded, *and* you want to try some kind of experiment on the javascript console, *and* those experiments make requests to the server, you may not get a response, because all threads are in use.
+
+You can resolve this by using the `pause` method in the debug session which will put the server debug session into a non-blocking loop. You can then experiment in the JS console, and when done release the pause by executing `go()` in the *javascript* debug console.
diff --git a/docs/development-workflow/hyper-spec/04-using-with-rack.md b/docs/development-workflow/hyper-spec/04-using-with-rack.md
new file mode 100644
index 000000000..7c5147f40
--- /dev/null
+++ b/docs/development-workflow/hyper-spec/04-using-with-rack.md
@@ -0,0 +1,56 @@
+# Using Hyperspec with Rack
+
+Hyperspec will run with Rails out of the box, but you can also use Hyperspec with any Rack application, with just a little more setup. For example here is a sample configuration setup with Sinatra:
+
+```ruby
+# Gemfile
+...
+
+gem "sinatra"
+gem "rspec"
+gem "pry"
+gem "opal"
+gem "opal-sprockets"
+gem "rack"
+gem "puma"
+group :test do
+ # gem 'hyper-spec', '~> 1.0.alpha1.0'
+ # or to use edge:
+ gem 'hyper-spec',
+ git: 'git://github.com/hyperstack-org/hyperstack.git',
+ branch: 'edge',
+ glob: 'ruby/*/*.gemspec'
+end
+```
+
+```ruby
+# spec/spec_helper.rb
+
+require "bundler"
+Bundler.require
+ENV["RACK_ENV"] ||= "test"
+
+# require your application files as needed
+require File.join(File.dirname(__FILE__), "..", "app.rb")
+
+# bring in needed support files
+require "rspec"
+require "rack/test"
+require "hyper-spec/rack"
+
+# assumes your sinatra app is named app
+Capybara.app = HyperSpecTestController.wrap(app: app)
+
+set :environment, :test
+set :run, false
+set :raise_errors, true
+set :logging, false
+```
+
+### Details
+
+The interface between Hyperspec and your application environment is defined by the `HyperspecTestController` class. This file typically includes a set of helper methods from `HyperSpec::ControllerHelpers`, which can then be overridden to give whatever behavior your specific framework needs. Have a look at the `hyper-spec/rack.rb` and `hyper-spec/controller_helpers.rb` files in the Hyperspec gem directory.
+
+### Example
+
+A complete (but very simple) example is in this repos `ruby/examples/misc/sinatra_app` directory
diff --git a/docs/development-workflow/hyper-spec/README.md b/docs/development-workflow/hyper-spec/README.md
new file mode 100644
index 000000000..44dd165e3
--- /dev/null
+++ b/docs/development-workflow/hyper-spec/README.md
@@ -0,0 +1,41 @@
+# HyperSpec
+
+## Adding client side testing to RSpec
+
+The `hyper-spec` gem supports the Hyperstack goals of programmer productivity and seamless web development by allowing testing to be done with minimal concern for the client-server interface.
+
+The `hyper-spec` gem adds functionality to the `rspec`, `capybara`, `timecop` and `pry` gems allowing you to do the following:
+
++ write component and integration tests using the rspec syntax and helpers
++ write specs that run on both the client and server
++ evaluate client side ruby expressions from within specs and while using `pry`
++ share data between the client and server within your specs
++ control and synchronize time on the client and the server
+
+HyperSpec can be used standalone, but if used as part of a Hyperstack application it allows straight forward testing of Hyperstack Components and your ActiveRecord Models.
+
+So for example here is part of a simple unit test of a TodoIndex component:
+
+```ruby
+it "will update the TodoIndex", js: true do
+ # mounts the TodoIndex component (client side)
+ mount 'TodoIndex'
+ # Todo is an ActiveRecord Model
+ # create a new Todo on the server (we could use FactoryBot of course)
+ todo_1 = Todo.create(title: 'this todo created on the server')
+ # verify that UI got updated
+ expect(find('.ToDoItem-Text').text).to eq todo_1.title
+ # verify that the count of Todos on the client side DB matches the server
+ expect { Todo.count }.on_client_to eq Todo.count
+ # now create another Todo on the client
+ new_todo_title = 'this todo created on the client'
+ # note that local variables are copied from the server to the client
+ on_client { Todo.create(title: new_todo_title) }
+ # the Todo should now be reflected on the server
+ expect(Todo.last.title).to eq new_todo_title
+end
+```
+
+When using HyperSpec all the specs execute on the server side, but they may also interrogate the state of the UI as well as the state
+of any of the client side objects. The specs can execute any valid Ruby code client side to create new test objects as well as do
+white box testing. This keeps the logic of your specs in one place.
From aa6cfdd6c887e6dc02f414245bf0515a0d6aafe8 Mon Sep 17 00:00:00 2001
From: catmando
Date: Mon, 15 Mar 2021 23:11:13 -0400
Subject: [PATCH 201/307] closes #369 closes #370 closes #368
---
docs/client-dsl/README.md | 36 +++++++++---
docs/client-dsl/components.md | 55 ++++++++++++++++---
docs/client-dsl/html-css.md | 48 ++++++++++++++--
docs/installation/man-installation.md | 31 ++---------
.../lib/hyperstack/internal/component/tags.rb | 1 +
.../spec/client_features/component_spec.rb | 45 ++++++++++++++-
ruby/rails-hyperstack/.ruby-version | 2 +-
ruby/rails-hyperstack/Rakefile | 4 +-
.../hyperstack/install_generator.rb | 22 ++++----
.../install/hyperstack_generator.rb | 2 +-
.../rails-hyperstack/rails-hyperstack.gemspec | 4 +-
11 files changed, 184 insertions(+), 66 deletions(-)
diff --git a/docs/client-dsl/README.md b/docs/client-dsl/README.md
index c4c706201..f726f40bd 100644
--- a/docs/client-dsl/README.md
+++ b/docs/client-dsl/README.md
@@ -1,19 +1,37 @@
# Client DSL
-## HTML DSL and Hyperstack Component classes
+## Hyperstack Component Classes and DSL
-A key design goal of the DSL \(Domain Specific Language\) is to make it work seamlessly with the rest of Ruby and easy to work with HTML elements and Components. Additionally, the DSL provides an abstraction layer between your code and the underlying \(fast moving\) technology stack. Hyperstack always uses the very latest versions of React and React Router yet our DSL does not change often. We believe that a stable DSL abstraction is an advantage.
+Your Hyperstack Application is built from a series of *Components* which are Ruby Classes that display portions of the UI. Hyperstack Components are implemented using [React](https://reactjs.org/), and can interoperate with existing React components and libraries. Here is a simple example that displays a ticking clock:
-This documentation will cover the following core concepts:
+```ruby
+# Components inherit from the HyperComponent base class
+# which supplies the DSL to translate from Ruby into React
+# function calls
+class Clock < HyperComponent
+ # before_mount is an example of a life cycle method
+ before_mount { every(1.second) { mutate @current_time = Time.now } }
+ # every component has a render block which describes what will be
+ # drawn on the UI
+ render do
+ # conponents can render other components or primitive HTML or SVG
+ # tags. Components also use their state to determine what to render,
+ # in this case the @current_time instance variable
+ DIV { @current_time.strftime("%m/%d/%Y %I:%M:%S")
+ end
+end
+```
-+ [HTML & CSS DSL](html-css.md) which provided Ruby implementations of all of the HTML and CSS elements
+This documentation will cover the following core concepts, many of which
+are touched on in the above simple example:
+
++ [HTML & CSS DSL](html-css.md) which provides Ruby implementations of all of the HTML and CSS elements
+ [Component DSL](components.md) is a Ruby DSL which wraps ReactJS Components
+ [Lifecycle Methods](lifecycle-methods.md) are methods which are invoked before, during and after rendering
-+ [State](state.md) governs all rendering in ReactJS
-+ [Event Handlers](event-handlers.md) allow any HTML element or Component can respond to an event
-+ [JavaScript Components](javascript-components.md) for the full universe of JS libraries in your Ruby code
++ [State](state.md) - components rerender as needed when state changes.
++ [Event Handlers](event-handlers.md) allow any HTML element or Component to respond to an event, plus custom events can be described.
++ [JavaScript Components](javascript-components.md) access to the full universe of JS libraries in your Ruby code
+ [Client-side Routing](hyper-router.md) a Ruby DSL which wraps ReactRouter
+ [Stores](hyper-store.md) for application level state and Component communication
-+ [Elements and Rendering](elements-and-rendering.md) which are seldom used but useful to know
++ [Elements and Rendering](elements-and-rendering.md) details of the underlying mechanisms.
+ [Further Reading](further-reading.md) on React and Opal
-
diff --git a/docs/client-dsl/components.md b/docs/client-dsl/components.md
index 8b28ce662..2e4fd4fe3 100644
--- a/docs/client-dsl/components.md
+++ b/docs/client-dsl/components.md
@@ -1,10 +1,10 @@
# Hyperstack Component DSL
-Hyperstack Component DSL is a set of class and instance methods that are used to describe React components and render the user-interface.
+The Hyperstack Component DSL is a set of class and instance methods that are used to describe React components and render the user-interface.
The DSL has the following major areas:
-* The `Hyperstack::Component` mixin or your own `HyperComponent` class
+* The `HyperComponent` class
* HTML DSL elements
* Component Lifecycle Methods \(`before_mount`, `render`, `after_mount`, `after_update`, `after_error`\)
* The `param` and `render` methods
@@ -13,18 +13,24 @@ The DSL has the following major areas:
## HyperComponent
-Hyperstack Components classes include the `Hyperstack::Component` mixin or \(for ease of use\) are a subclass of a `HyperComponent` class which includes the mixin:
+By convention your Hyperstack Components will inherit from the `HyperComponent` class, which at a minimum looks like this:
```ruby
class HyperComponent
include Hyperstack::Component
end
+# and is used like this:
+
class AnotherComponent < HyperComponent
end
```
-At a minimum every component class must define a `render` method which returns **one single** child element. That child may in turn have an arbitrarily deep structure.
+Having an Application wide HyperComponent class allows you to modify component behavior on an application basis, similar to the way Rails uses `ApplicationRecord` and `ApplicationController` classes.
+
+## The `render` Callback
+
+At a minimum every component class must define a `render` callback which returns one or more child elements. Those children may in turn have an arbitrarily deep structure.
```ruby
class Component < HyperComponent
@@ -34,7 +40,7 @@ class Component < HyperComponent
end
```
-You may also include the top level element to be rendered:
+To save a little typing you can also include the top level element to be rendered:
```ruby
class Component < HyperComponent
@@ -130,9 +136,8 @@ Parent { Child() }
```ruby
param :items
render do
- # notice how the items param is accessed in CamelCase (to indicate that it is read-only)
items.each do |item|
- PARA do
+ P do
item[:text]
end
end
@@ -230,6 +235,41 @@ class IndentEachLine < HyperComponent
end
```
+### Rendering Multiple Values and the FRAGMENT component
+
+A render block may generate multiple values. React assumes when a Component generates multiple items, the item order and quantity may
+change over time and so will give a warning unless each element has a key:
+
+```ruby
+class ListItems < HyperComponent
+ render do
+ LI(key: 1) { 'item 1' }
+ LI(key: 2) { 'item 2' }
+ LI(key: 3) { 'item 3' }
+ end
+end
+
+# somewhere else:
+ UL do
+ ListItems()
+ end
+```
+
+If you are sure that the order and number of elements will not change over time you may wrap the items in the FRAGMENT pseudo component:
+
+```ruby
+class ListItems < HyperComponent
+ render(FRAGMENT) do
+ LI { 'item 1' }
+ LI { 'item 2' }
+ LI { 'item 3' }
+ end
+end
+```
+
+The only param that FRAGMENT may take is a key, which is useful if there will be multiple fragments being merged, at some higher level.
+
+
### Data Flow
In React, data flows from owner to owned component through the params as discussed above. This is effectively one-way data binding: owners bind their owned component's param to some value the owner has computed based on its `params` or `state`. Since this process happens recursively, data changes are automatically reflected everywhere they are used.
@@ -424,4 +464,3 @@ end
```
Note: `collect_other_params_as` builds a hash, so you can merge other data in or even delete elements out as needed.
-
diff --git a/docs/client-dsl/html-css.md b/docs/client-dsl/html-css.md
index eb14c5d06..1f1e8b91d 100644
--- a/docs/client-dsl/html-css.md
+++ b/docs/client-dsl/html-css.md
@@ -47,21 +47,57 @@ TABLE(class: 'ui celled table') do
end
```
-The following HTML elements are available:
+The following HTML and SVG elements are available:
+
+
+HTML Tags
```markup
-A ABBR ADDRESS AREA ARTICLE ASIDE AUDIO B BASE BDI BDO BIG BLOCKQUOTE BODY BR BUTTON CANVAS CAPTION CITE CODE COL COLGROUP DATA DATALIST DD DEL DETAILS DFN DIALOG DIV DL DT EM EMBED FIELDSET FIGCAPTION FIGURE FOOTER FORM H1 H2 H3 H4 H5 H6 HEAD HEADER HR HTML I IFRAME IMG INPUT INS KBD KEYGEN LABEL LEGEND LI LINK MAIN MAP MARK MENU MENUITEM META METER NAV NOSCRIPT OBJECT OL OPTGROUP OPTION OUTPUT P PARAM PICTURE PRE PROGRESS Q RP RT RUBY S SAMP SCRIPT SECTION SELECT SMALL SOURCE SPAN STRONG STYLE SUB SUMMARY SUP TABLE TBODY TD TEXTAREA TFOOT TH THEAD TIME TITLE TR TRACK U UL VAR VIDEO WBR
+A ABBR ADDRESS AREA ARTICLE ASIDE AUDIO
+B BASE BDI BDO BIG BLOCKQUOTE BODY BR BUTTON
+CANVAS CAPTION CITE CODE COL COLGROUP
+DATA DATALIST DD DEL DETAILS DFN DIALOG DIV DL DT
+EM EMBED
+FIELDSET FIGCAPTION FIGURE FOOTER FORM
+H1 H2 H3 H4 H5 H6 HEAD HEADER HR HTML
+I IFRAME IMG INPUT INS
+KBD KEYGEN
+LABEL LEGEND LI LINK
+MAIN MAP MARK MENU MENUITEM META METER
+NAV NOSCRIPT
+OBJECT OL OPTGROUP OPTION OUTPUT
+P PARAM PICTURE PRE PROGRESS
+Q
+RP RT RUBY
+S SAMP SCRIPT SECTION SELECT SMALL SOURCE SPAN STRONG STYLE SUB SUMMARY SUP
+TABLE TBODY TD TEXTAREA TFOOT TH THEAD TIME TITLE TR TRACK
+U UL
+VAR VIDEO
+WBR
```
+
-And also the SVG elements:
+
+SVG Tags
```markup
-CIRCLE CLIPPATH DEFS ELLIPSE G LINE LINEARGRADIENT MASK PATH PATTERN POLYGON POLYLINE RADIALGRADIENT RECT STOP SVG TEXT TSPAN
+CIRCLE CLIPPATH
+DEFS
+ELLIPSE
+G
+LINE LINEARGRADIENT
+MASK
+PATH PATTERN POLYGON POLYLINE
+RADIALGRADIENT RECT
+STOP
+SVG
+TEXT TSPAN
```
+
### HTML parameters
-You can pass any expected parameter to a HTML element:
+You can pass any expected parameter to a HTML or SVG element:
```ruby
A(href: '/') { 'Click me' } # Click me
@@ -82,7 +118,7 @@ P(class: :bright) { }
P(class: [:bright, :blue]) { } # class='bright blue'
```
-For `style` you need to pass a hash:
+For `style` you need to pass a hash using the [React style conventions](https://reactjs.org/docs/dom-elements.html#style):
```ruby
PARA(style: { display: item[:some_property] == "some state" ? :block : :none })
diff --git a/docs/installation/man-installation.md b/docs/installation/man-installation.md
index f2772802d..4b1056520 100644
--- a/docs/installation/man-installation.md
+++ b/docs/installation/man-installation.md
@@ -2,40 +2,20 @@
You can install Hyperstack either
-* using a template - best for new applications \(not working for Rails 6\) yet;
-* using a Rails generator - best for existing Rails apps;
+* using a Rails generator,
* or manually walking through the detailed installation instructions below.
-Even if you use the template or generator, later reading through the detailed installation instructions can be helpful to understand how the system fits together and the generators work.
+Even if you use the generator later reading through the detailed installation instructions can be helpful to understand how the system fits together and the generators work.
## Pre-Requisites
-#### - Rails 5.x [Install Instructions](http://railsinstaller.org/en)
+#### - Rails >= 5.x [Install Instructions](http://railsinstaller.org/en)
-And for a full system as setup by the template or install generator you will need
+And for a full system as setup generator you will need
#### - Yarn [Install Instructions](https://yarnpkg.com/en/docs/install#mac-stable)
-## Installing using the template
-
-This template will create a **new** Rails app with Webpacker from Hyperstack edge branch. This is the easiest way to get started.
-
-### Run the template
-
-Simply run the command below to create a new Rails app with Hyperstack all configured:
-
-```text
-rails new MyApp -T -m https://rawgit.com/hyperstack-org/hyperstack/edge/install/rails-webpacker.rb
-```
-
-> Note: The -T flag will not install minitest directories, leaving room for Rspec and Hyperspec. See the HyperSpec readme under "Tools" for more info.
-
-### Start the Rails app
-
-* `foreman start` to start Rails and the Hotloader
-* Navigate to `http://localhost:5000/`
-
-## Installing in an Existing Rails App
+## Installing Using the Generator
If you have an existing Rails app, you can use the built in generator to install Hyperstack. Best to create a new branch of course before trying this out.
@@ -702,4 +682,3 @@ Another approach is to add a simple component using the component generator:
and then mount this component using ERB from within an existing view:
`<% render_component 'HyperTest' %>`
-
diff --git a/ruby/hyper-component/lib/hyperstack/internal/component/tags.rb b/ruby/hyper-component/lib/hyperstack/internal/component/tags.rb
index 62314587d..d4b5b6e49 100644
--- a/ruby/hyper-component/lib/hyperstack/internal/component/tags.rb
+++ b/ruby/hyper-component/lib/hyperstack/internal/component/tags.rb
@@ -93,6 +93,7 @@ def find_component(name)
def lookup_const(name)
return nil unless name =~ /^[A-Z]/
+ return Hyperstack::Internal::Component::Tags::FRAGMENT if name == "FRAGMENT"
scopes = self.class.name.to_s.split('::').inject([Object]) do |nesting, next_const|
nesting + [nesting.last.const_get(next_const)]
end.reverse
diff --git a/ruby/hyper-component/spec/client_features/component_spec.rb b/ruby/hyper-component/spec/client_features/component_spec.rb
index 251d806df..b004caace 100644
--- a/ruby/hyper-component/spec/client_features/component_spec.rb
+++ b/ruby/hyper-component/spec/client_features/component_spec.rb
@@ -227,7 +227,7 @@ class SomeLIs < Hyperloop::Component
expect(page.find('div').text).to end_with("random string at the end")
end
- it "can generate multiple elements on outer render by returning arrays" do
+ it "can generate multiple elements on outer render by rendering multiple values" do
mount 'Foo' do
class Foo < Hyperloop::Component
render do
@@ -246,6 +246,49 @@ class SomeLIs < Hyperloop::Component
expect(page.find('div').text).to end_with("random string at the end")
end
+ it "fragments can be nested and have keys" do
+ mount 'Foo' do
+ class Foo < Hyperloop::Component
+ render do
+ UL(key: 1) do
+ 3.times do |i|
+ FRAGMENT(key: i) do
+ LI { "first #{i}" }
+ LI { "second #{i}" }
+ end
+ end
+ end
+ end
+ end
+ end
+ expect(page.find('ul').all('li').collect(&:text)).to eq([*0..2].collect { |i| ["first #{i}", "second #{i}"] }.flatten)
+ end
+
+ xit "will only render once" do # see issue #329
+ mount "Parent" do
+ class Child
+ include Hyperstack::Component
+ param_accessor_style :accessors
+ param :do_something
+ render do
+ puts "child: #{do_something.object_id}"
+ end
+ end
+ class Parent
+ include Hyperstack::Component
+ param_accessor_style :accessors
+ before_mount do
+ @do_something = -> { puts "we did it!" }
+ after(2) { force_update! }
+ end
+ render do
+ puts "parent: #{@do_something.object_id}"
+ Child(do_something: @do_something)
+ end
+ end
+ end
+ end
+
it 'can buffer an element' do
mount 'Foo' do
class Bar < Hyperloop::Component
diff --git a/ruby/rails-hyperstack/.ruby-version b/ruby/rails-hyperstack/.ruby-version
index ec1cf33c3..37c2961c2 100644
--- a/ruby/rails-hyperstack/.ruby-version
+++ b/ruby/rails-hyperstack/.ruby-version
@@ -1 +1 @@
-2.6.3
+2.7.2
diff --git a/ruby/rails-hyperstack/Rakefile b/ruby/rails-hyperstack/Rakefile
index 38da6d1f5..845f0bc09 100644
--- a/ruby/rails-hyperstack/Rakefile
+++ b/ruby/rails-hyperstack/Rakefile
@@ -10,10 +10,10 @@ namespace :spec do
opal_version = `bundle info opal`.match(/\* opal \((.+)\)/)[1]
Dir.chdir('spec') do
sh('rm -rf test_app')
- Bundler.with_clean_env do
+ Bundler.with_unbundled_env do
sh("rails _#{rails_version}_ new test_app -T")
end
- Bundler.with_clean_env do
+ Bundler.with_unbundled_env do
Dir.chdir('test_app') do
sh('cat ../gems.rb >> Gemfile')
sh("echo 'gem \"opal\", \"#{opal_version}\"' >> Gemfile")
diff --git a/ruby/rails-hyperstack/lib/generators/hyperstack/install_generator.rb b/ruby/rails-hyperstack/lib/generators/hyperstack/install_generator.rb
index 9b6b5b15a..5294278d1 100644
--- a/ruby/rails-hyperstack/lib/generators/hyperstack/install_generator.rb
+++ b/ruby/rails-hyperstack/lib/generators/hyperstack/install_generator.rb
@@ -9,13 +9,6 @@ class InstallGenerator < Rails::Generators::Base
class_option 'webpack-only', type: :boolean
class_option 'hyper-model-only', type: :boolean
- # def add_clexer
- # gem 'c_lexer'
- # Bundler.with_clean_env do
- # run 'bundle update'
- # end
- # end
-
def add_component
if skip_adding_component?
# normally this is handled by the hyper:component
@@ -117,14 +110,23 @@ def cancel_react_source_import
def install_webpacker
return if skip_webpack?
- gem 'webpacker'
- Bundler.with_clean_env do
- run 'bundle install'
+
+ gem "webpacker" unless defined? ::Webpacker
+ Bundler.with_unbundled_env do
+ run "bundle install"
end
`spring stop`
Dir.chdir(Rails.root.join.to_s) { run 'bundle exec rails webpacker:install' }
end
+ def check_javascript_link_directory
+ manifest_js_file = Rails.root.join("app", "assets", "config", "manifest.js")
+ return unless File.exist? manifest_js_file
+ return unless File.readlines(manifest_js_file).grep(/javascript \.js/).empty?
+
+ append_file manifest_js_file, "//= link_directory ../javascripts .js\n"
+ end
+
def create_policies_directory
return if skip_hyper_model?
policy_file = Rails.root.join('app', 'policies', 'hyperstack', 'application_policy.rb')
diff --git a/ruby/rails-hyperstack/lib/generators/install/hyperstack_generator.rb b/ruby/rails-hyperstack/lib/generators/install/hyperstack_generator.rb
index 448b6e8e1..8a1d30a4c 100644
--- a/ruby/rails-hyperstack/lib/generators/install/hyperstack_generator.rb
+++ b/ruby/rails-hyperstack/lib/generators/install/hyperstack_generator.rb
@@ -214,7 +214,7 @@ def add_gems
end
def install
- Bundler.with_clean_env do
+ Bundler.with_unbundled_env do
run "bundle install"
end
run 'bundle exec rails webpacker:install'
diff --git a/ruby/rails-hyperstack/rails-hyperstack.gemspec b/ruby/rails-hyperstack/rails-hyperstack.gemspec
index b38872ea9..2e5e7d425 100644
--- a/ruby/rails-hyperstack/rails-hyperstack.gemspec
+++ b/ruby/rails-hyperstack/rails-hyperstack.gemspec
@@ -57,7 +57,7 @@ You can control how much of the stack gets installed as well:
spec.add_dependency 'hyper-model', Hyperstack::VERSION
spec.add_dependency 'hyper-router', Hyperstack::ROUTERVERSION
spec.add_dependency 'hyperstack-config', Hyperstack::VERSION
- spec.add_dependency 'opal-rails'#, '~> 1.0'
+ spec.add_dependency 'opal-rails' #, '~> 2.0'
spec.add_dependency 'opal-browser', '~> 0.2.0'
spec.add_dependency 'react-rails', '>= 2.4.0', '< 2.5.0'
@@ -74,7 +74,7 @@ You can control how much of the stack gets installed as well:
spec.add_development_dependency 'rspec-rails'
spec.add_development_dependency 'rubocop', '~> 0.51.0'
spec.add_development_dependency 'sqlite3', '~> 1.4' # was 1.3.6 -- see https://github.com/rails/rails/issues/35153
- spec.add_development_dependency 'sass-rails', '~> 5.0'
+ spec.add_development_dependency 'sass-rails', '>= 5.0'
# Use Uglifier as compressor for JavaScript assets
spec.add_development_dependency 'uglifier', '>= 1.3.0'
# See https://github.com/rails/execjs#readme for more supported runtimes
From 0a395e8ffe1c0b5ca7fe3ca07c58c05a2099c445 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 16 Mar 2021 00:22:00 -0400
Subject: [PATCH 202/307] more doc updates and intermittent hyper-operation
spec fixes
---
docs/client-dsl/README.md | 13 +++--
docs/client-dsl/components.md | 50 +++++++++++--------
docs/client-dsl/html-css.md | 25 ++++++++--
.../spec/aaa_run_first/transports_spec.rb | 3 +-
4 files changed, 60 insertions(+), 31 deletions(-)
diff --git a/docs/client-dsl/README.md b/docs/client-dsl/README.md
index f726f40bd..1464343d5 100644
--- a/docs/client-dsl/README.md
+++ b/docs/client-dsl/README.md
@@ -9,12 +9,17 @@ Your Hyperstack Application is built from a series of *Components* which are Rub
# which supplies the DSL to translate from Ruby into React
# function calls
class Clock < HyperComponent
- # before_mount is an example of a life cycle method
- before_mount { every(1.second) { mutate @current_time = Time.now } }
+ # before_mount is an example of a life cycle method.
+ before_mount do
+ # before the component is first rendered (mounted)
+ # we setup a periodic timer that will update the
+ # current_time instance variable every second.
+ every(1.second) { mutate @current_time = Time.now }
+ end
# every component has a render block which describes what will be
# drawn on the UI
render do
- # conponents can render other components or primitive HTML or SVG
+ # Components can render other components or primitive HTML or SVG
# tags. Components also use their state to determine what to render,
# in this case the @current_time instance variable
DIV { @current_time.strftime("%m/%d/%Y %I:%M:%S")
@@ -26,7 +31,7 @@ This documentation will cover the following core concepts, many of which
are touched on in the above simple example:
+ [HTML & CSS DSL](html-css.md) which provides Ruby implementations of all of the HTML and CSS elements
-+ [Component DSL](components.md) is a Ruby DSL which wraps ReactJS Components
++ [The Component DSL](components.md) is a Ruby DSL which wraps ReactJS Components
+ [Lifecycle Methods](lifecycle-methods.md) are methods which are invoked before, during and after rendering
+ [State](state.md) - components rerender as needed when state changes.
+ [Event Handlers](event-handlers.md) allow any HTML element or Component to respond to an event, plus custom events can be described.
diff --git a/docs/client-dsl/components.md b/docs/client-dsl/components.md
index 2e4fd4fe3..21999b408 100644
--- a/docs/client-dsl/components.md
+++ b/docs/client-dsl/components.md
@@ -6,7 +6,7 @@ The DSL has the following major areas:
* The `HyperComponent` class
* HTML DSL elements
-* Component Lifecycle Methods \(`before_mount`, `render`, `after_mount`, `after_update`, `after_error`\)
+* Component Lifecycle Methods \(`before_mount`, `after_mount`, `after_update`\)
* The `param` and `render` methods
* Event handlers
* Miscellaneous methods
@@ -23,6 +23,7 @@ end
# and is used like this:
class AnotherComponent < HyperComponent
+ ...
end
```
@@ -30,7 +31,7 @@ Having an Application wide HyperComponent class allows you to modify component b
## The `render` Callback
-At a minimum every component class must define a `render` callback which returns one or more child elements. Those children may in turn have an arbitrarily deep structure.
+At a minimum every component class must define a `render` block which returns one or more child elements. Those children may in turn have an arbitrarily deep structure.
```ruby
class Component < HyperComponent
@@ -40,7 +41,7 @@ class Component < HyperComponent
end
```
-To save a little typing you can also include the top level element to be rendered:
+To save a little typing you can also specify the top level element to be rendered:
```ruby
class Component < HyperComponent
@@ -50,7 +51,7 @@ class Component < HyperComponent
end
```
-To render a component, you reference its class name in the DSL as a method call. This creates a new instance, passes any parameters proceeds with the component lifecycle.
+To render a component, you reference its class name as a method call from another component. This creates a new instance, passes any parameters and proceeds with the component lifecycle.
```ruby
class FirstComponent < HyperComponent
@@ -60,17 +61,18 @@ class FirstComponent < HyperComponent
end
```
-Note that you should never redefine the `new` or `initialize` methods, or call them directly. The equivalent of `initialize` is the `before_mount` method.
+Note that you should never redefine the `new` or `initialize` methods, or call them directly. The equivalent of `initialize` is the `before_mount` method.
+
+> The one exception to using `new` is within a spec to create a "headless" component in order to access its internal state and methods.
### Invoking Components
> Note: when invoking a component **you must have** a \(possibly empty\) parameter list or \(possibly empty\) block.
-
-```ruby
+> ```ruby
MyCustomComponent() # ok
MyCustomComponent {} # ok
MyCustomComponent # <--- breaks
-```
+> ```
## Multiple Components
@@ -89,9 +91,9 @@ class Avatar < HyperComponent
param :user_name
render(DIV) do
- # the user_name param has been converted to @UserName immutable instance variable
- ProfilePic(user_name: @UserName)
- ProfileLink(user_name: @UserName)
+ # for each param a method with the same name is defined
+ ProfilePic(user_name: user_name)
+ ProfileLink(user_name: user_name)
end
end
@@ -99,15 +101,15 @@ class ProfilePic < HyperComponent
param :user_name
render do
- IMG(src: "https://graph.facebook.com/#{@UserName}/picture")
+ IMG(src: "https://graph.facebook.com/#{user_name}/picture")
end
end
class ProfileLink < HyperComponent
param :user_name
render do
- A(href: "https://www.facebook.com/#{@UserName}") do
- @UserName
+ A(href: "https://www.facebook.com/#{user_name}") do
+ user_name
end
end
end
@@ -207,16 +209,20 @@ class MyComponent < HyperComponent
end
```
-### The children method
+> The `to_key` method: Any ruby object can be a key. Under the hood the HyperComponent DSL will call the object's `to_key` method which will respond with a unique value representing the object. For example if you pass an ActiveRecord model instance as a key, the result will be the database id of the model.
+
+### The children and render methods
-Along with params components may be passed a block which is used to build the components children.
+Along with the params hash components may be passed a block which is used to build the components children.
-The instance method `children` returns an enumerable that is used to access the unrendered children of a component.
+The instance method `children` returns an enumerable that is used to access the *unrendered* children of a component. The children can then be rendered
+using the `render` method which will merge any additional parameters and
+render the child.
```ruby
class Indenter < HyperComponent
render(DIV) do
- IndentEachLine(by: 100) do # see IndentEachLine below
+ IndentEachLine(by: 10) do # see IndentEachLine below
DIV {"Line 1"}
DIV {"Line 2"}
DIV {"Line 3"}
@@ -267,7 +273,7 @@ class ListItems < HyperComponent
end
```
-The only param that FRAGMENT may take is a key, which is useful if there will be multiple fragments being merged, at some higher level.
+The only param that FRAGMENT may take is a key, which is useful if there will be multiple fragments being merged at some higher level.
### Data Flow
@@ -276,7 +282,7 @@ In React, data flows from owner to owned component through the params as discuss
### Stores
-Managing state between components is best done using Stores as many Components can access one store. This saves passing data btween Components. Please see the [Store documentation](https://github.com/hyperstack-org/hyperstack/tree/a530e3955296c5bd837c648fd452617e0a67a6ed/docs/dsl-client/hyper-store/README.md) for details.
+Managing state between components is best done using Stores as many Components can access one store. This saves passing data between Components. Please see the [Store documentation](https://docs.hyperstack.org/client-dsl/hyper-store) for details.
### Reusable Components
@@ -294,7 +300,7 @@ Examples:
```ruby
param :foo # declares that we must be provided with a parameter foo when the component is instantiated or re-rerendered.
-param :foo, alias: :something # the alias name will be used for the param (instead of @Foo)
+param :foo, alias: :something # the alias name will be used for the param (instead of Foo)
param :foo => "some default" # declares that foo is optional, and if not present the value "some default" will be used.
param foo: "some default" # same as above using ruby 1.9 JSON style syntax
param :foo, default: "some default" # same as above but uses explicit default key
@@ -324,6 +330,8 @@ end
A core design concept taken from React is that data flows down to child Components via params and params \(called props in React\) are immutable.
+However for complex objects
+
In Hyperstack, there are **two exceptions** to this rule:
* An instance of a **Store** \(passed as a param\) is mutable and changes to the state of the Store will cause a re-render
diff --git a/docs/client-dsl/html-css.md b/docs/client-dsl/html-css.md
index 1f1e8b91d..eae83d52f 100644
--- a/docs/client-dsl/html-css.md
+++ b/docs/client-dsl/html-css.md
@@ -14,19 +14,19 @@ end
> **Notice that the HTML elements \(BUTTON, DIV, etc.\) are in CAPS**. We know this is bending the standard Ruby style rules, but we think it reads better this way.
-For example, to render a `
`:
+For example
```ruby
DIV(class: 'green-text') { "Let's gets started!" }
```
-Would create the following HTML:
+would create the following HTML:
```markup
Let's gets started!
```
-And to render a table:
+And this would render a table:
```ruby
TABLE(class: 'ui celled table') do
@@ -52,7 +52,7 @@ The following HTML and SVG elements are available:
HTML Tags
-```markup
+```
A ABBR ADDRESS AREA ARTICLE ASIDE AUDIO
B BASE BDI BDO BIG BLOCKQUOTE BODY BR BUTTON
CANVAS CAPTION CITE CODE COL COLGROUP
@@ -80,7 +80,7 @@ WBR
SVG Tags
-```markup
+```
CIRCLE CLIPPATH
DEFS
ELLIPSE
@@ -123,3 +123,18 @@ For `style` you need to pass a hash using the [React style conventions](https://
```ruby
PARA(style: { display: item[:some_property] == "some state" ? :block : :none })
```
+
+### Complex Arguments
+
+You can pass multiple hashes which will be merged, and any individual symbols
+(or strings) will be treated as `=true`. For example
+
+```ruby
+A(:flag, {href: '/'}, {class: 'my_class'})
+```
+
+will generate
+
+```HTML
+
+```
diff --git a/ruby/hyper-operation/spec/aaa_run_first/transports_spec.rb b/ruby/hyper-operation/spec/aaa_run_first/transports_spec.rb
index a10608b1b..34afce014 100644
--- a/ruby/hyper-operation/spec/aaa_run_first/transports_spec.rb
+++ b/ruby/hyper-operation/spec/aaa_run_first/transports_spec.rb
@@ -200,11 +200,12 @@ def connect(*args)
it 'sees the connection going offline' do
mount 'TestComponent'
+ puts "active connections after mounting: #{Hyperstack::Connection.active}"
evaluate_ruby 'Hyperstack.go_ahead_and_connect'
Timecop.travel(Time.now + Hyperstack::Connection.transport.expire_new_connection_in - 1)
wait_for do
sleep 0.25
- Hyperstack::Connection.active
+ Hyperstack::Connection.active.tap { |c| puts "active connections now = #{c}"}
end.to eq(['ScopeIt::TestApplication'])
ApplicationController.acting_user = true
mount 'TestComponent'
From 836946c9ace52000d6b3d1ad2baab3ba74f1fe3f Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 16 Mar 2021 11:44:50 -0400
Subject: [PATCH 203/307] closes #361
---
docs/client-dsl/components.md | 10 ++++-
ruby/rails-hyperstack/Rakefile | 1 +
.../hyperstack/install_generator.rb | 25 ++++++++----
.../spec/rails_hyperstack_spec.rb | 38 +++++++++++--------
4 files changed, 48 insertions(+), 26 deletions(-)
diff --git a/docs/client-dsl/components.md b/docs/client-dsl/components.md
index 21999b408..d69bd35c3 100644
--- a/docs/client-dsl/components.md
+++ b/docs/client-dsl/components.md
@@ -13,11 +13,17 @@ The DSL has the following major areas:
## HyperComponent
-By convention your Hyperstack Components will inherit from the `HyperComponent` class, which at a minimum looks like this:
+By convention your Hyperstack Components will inherit from the `HyperComponent` class, which typically would look like this:
```ruby
class HyperComponent
+ # All component classes must include Hyperstack::Component
include Hyperstack::Component
+ # The Observable module adds state handling
+ include Hyperstack::State::Observable
+ # The following turns on the new style param accessor
+ # i.e. param :foo is accessed by the foo method
+ param_accessor_style :accessors
end
# and is used like this:
@@ -330,7 +336,7 @@ end
A core design concept taken from React is that data flows down to child Components via params and params \(called props in React\) are immutable.
-However for complex objects
+However for complex objects
In Hyperstack, there are **two exceptions** to this rule:
diff --git a/ruby/rails-hyperstack/Rakefile b/ruby/rails-hyperstack/Rakefile
index 845f0bc09..70271475f 100644
--- a/ruby/rails-hyperstack/Rakefile
+++ b/ruby/rails-hyperstack/Rakefile
@@ -22,6 +22,7 @@ namespace :spec do
sh('bundle exec rails g hyperstack:install')
sh('bundle exec rails generate model Sample name:string description:text')
sh('mv app/models/sample.rb app/hyperstack/models/sample.rb')
+ sh("cat ../server_side_sample.rb >> app/models/sample.rb")
sh('bundle exec rake db:migrate')
sh('RAILS_ENV=test bundle exec rake db:setup')
# sh('bundle exec rails dev:cache') # not tested yet...
diff --git a/ruby/rails-hyperstack/lib/generators/hyperstack/install_generator.rb b/ruby/rails-hyperstack/lib/generators/hyperstack/install_generator.rb
index 5294278d1..2bd69bcd8 100644
--- a/ruby/rails-hyperstack/lib/generators/hyperstack/install_generator.rb
+++ b/ruby/rails-hyperstack/lib/generators/hyperstack/install_generator.rb
@@ -122,7 +122,7 @@ def install_webpacker
def check_javascript_link_directory
manifest_js_file = Rails.root.join("app", "assets", "config", "manifest.js")
return unless File.exist? manifest_js_file
- return unless File.readlines(manifest_js_file).grep(/javascript \.js/).empty?
+ return unless File.readlines(manifest_js_file).grep(/javascripts \.js/).empty?
append_file manifest_js_file, "//= link_directory ../javascripts .js\n"
end
@@ -162,13 +162,13 @@ def move_and_update_application_record
unless File.exist? hyper_app_record_file
empty_directory Rails.root.join('app', 'hyperstack', 'models')
`mv #{rails_app_record_file} #{hyper_app_record_file}`
- create_file rails_app_record_file, <<-RUBY
-# #{rails_app_record_file}
-# the presence of this file prevents rails migrations from recreating application_record.rb
-# see https://github.com/rails/rails/issues/29407
-
-require 'models/application_record.rb'
- RUBY
+# create_file rails_app_record_file, <<-RUBY
+# # #{rails_app_record_file}
+# # the presence of this file prevents rails migrations from recreating application_record.rb
+# # see https://github.com/rails/rails/issues/29407
+#
+# require 'models/application_record.rb'
+# RUBY
end
end
@@ -245,6 +245,15 @@ def inject_into_initializer(s)
else
create_file file_name, <<-RUBY
#{s}
+# server_side_auto_require will patch the ActiveSupport Dependencies module
+# so that you can define classes and modules with files in both the
+# app/hyperstack/xxx and app/xxx directories. For example you can split
+# a Todo model into server and client related definitions and place this
+# in `app/hyperstack/models/todo.rb`, and place any server only definitions in
+# `app/models/todo.rb`.
+
+require "hyperstack/server_side_auto_require.rb"
+
# set the component base class
Hyperstack.component_base_class = 'HyperComponent' # i.e. 'ApplicationComponent'
diff --git a/ruby/rails-hyperstack/spec/rails_hyperstack_spec.rb b/ruby/rails-hyperstack/spec/rails_hyperstack_spec.rb
index 619c4a8bd..70b9680be 100644
--- a/ruby/rails-hyperstack/spec/rails_hyperstack_spec.rb
+++ b/ruby/rails-hyperstack/spec/rails_hyperstack_spec.rb
@@ -1,24 +1,30 @@
-require 'spec_helper'
+require "spec_helper"
-describe 'rails-hyperstack' do
- it 'builds a working app', js: true do
- visit '/'
- expect(page).to have_content('App')
+describe "rails-hyperstack" do
+ it "builds a working app", js: true do
+ visit "/"
+ expect(page).to have_content("App")
end
- it 'installs hyper-model and friends', js: true do
- visit '/'
- expect_promise do
+
+ it "installs hyper-model and friends", js: true do
+ visit "/"
+ expect do
Hyperstack::Model.load { Sample.count }
- end.to eq(0)
- evaluate_ruby do
- Sample.create(name: 'sample1', description: 'the first sample')
+ end.on_client_to eq(0)
+ on_client do
+ Sample.create(name: "sample1", description: "the first sample")
end
wait_for_ajax
expect(Sample.count).to eq(1)
- expect(Sample.first.name).to eq('sample1')
- expect(Sample.first.description).to eq('the first sample')
- expect_evaluate_ruby do
- Sample.count
- end.to eq(1)
+ expect(Sample.first.name).to eq("sample1")
+ expect(Sample.first.description).to eq("the first sample")
+ expect { Sample.count }.on_client_to eq(1)
+ end
+
+ it "implements server_side_auto_require", js: true do
+ expect(Sample.super_secret_server_side_method).to be true
+ expect do
+ Sample.respond_to? :super_secret_server_side_method
+ end.on_client_to be_falsy
end
end
From 748d88c87f7e6c8ec854f05bf9c140812a0486de Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 16 Mar 2021 12:03:41 -0400
Subject: [PATCH 204/307] forgot to add new server_side_auto_require.rb file
---
.../hyperstack/server_side_auto_require.rb | 39 +++++++++++++++++++
1 file changed, 39 insertions(+)
create mode 100644 ruby/rails-hyperstack/lib/hyperstack/server_side_auto_require.rb
diff --git a/ruby/rails-hyperstack/lib/hyperstack/server_side_auto_require.rb b/ruby/rails-hyperstack/lib/hyperstack/server_side_auto_require.rb
new file mode 100644
index 000000000..a3388d127
--- /dev/null
+++ b/ruby/rails-hyperstack/lib/hyperstack/server_side_auto_require.rb
@@ -0,0 +1,39 @@
+Rails.configuration.autoloader = :classic
+
+module ActiveSupport
+ module Dependencies
+ HYPERSTACK_DIR = "hyperstack"
+ class << self
+ alias original_require_or_load require_or_load
+
+ # before requiring_or_loading a file, first check if
+ # we have the same file in the server side directory
+ # and add that as a dependency
+
+ def require_or_load(file_name, const_path = nil)
+ add_server_side_dependency(file_name)
+ original_require_or_load(file_name, const_path)
+ end
+
+ # search the filename path from the end towards the beginning
+ # for the HYPERSTACK_DIR directory. If found, remove it from
+ # the filename, and if a ruby file exists at that location then
+ # add it as a dependency
+
+ def add_server_side_dependency(file_name)
+ path = File.expand_path(file_name.chomp(".rb"))
+ .split(File::SEPARATOR).reverse
+ hs_index = path.find_index(HYPERSTACK_DIR)
+
+ return unless hs_index # no hyperstack directory here
+
+ new_path = (path[0..hs_index - 1] + path[hs_index + 1..-1]).reverse
+ load_path = new_path.join(File::SEPARATOR)
+
+ return unless File.exist? "#{load_path}.rb"
+
+ require_dependency load_path
+ end
+ end
+ end
+end
From bb87febf6f99cdaaacf0056995fd66db4edb7b54 Mon Sep 17 00:00:00 2001
From: catmando
Date: Tue, 16 Mar 2021 12:14:29 -0400
Subject: [PATCH 205/307] and I forgot this file too
---
ruby/rails-hyperstack/spec/server_side_sample.rb | 5 +++++
1 file changed, 5 insertions(+)
create mode 100644 ruby/rails-hyperstack/spec/server_side_sample.rb
diff --git a/ruby/rails-hyperstack/spec/server_side_sample.rb b/ruby/rails-hyperstack/spec/server_side_sample.rb
new file mode 100644
index 000000000..556d67f79
--- /dev/null
+++ b/ruby/rails-hyperstack/spec/server_side_sample.rb
@@ -0,0 +1,5 @@
+class Sample < ApplicationRecord
+ def self.super_secret_server_side_method
+ true
+ end
+end
From 4fa7b2a097f2392861646ca1f4e65e634d13fc81 Mon Sep 17 00:00:00 2001
From: catmando
Date: Wed, 17 Mar 2021 17:19:53 -0400
Subject: [PATCH 206/307] updated docs fixed some generator issues plus a
regression from #375
---
docs/SUMMARY.md | 11 +-
docs/installation/README.md | 51 ++++
docs/installation/man-installation.md | 59 +----
docs/rails-installation/README.md | 19 ++
docs/rails-installation/file-structure.md | 241 ++++++++++++++++++
docs/rails-installation/generators.md | 114 +++++++++
docs/rails-installation/other_details.md | 115 +++++++++
docs/rails-installation/prerequisites.md | 35 +++
.../rails-installation/using-the-installer.md | 38 +++
docs/tutorial/intro_to_hyper_components.md | 132 ++++++++++
release-notes/1.0.alpha1.5.md | 42 +++
release-notes/1.0.alpha1.6.md | 52 ++++
.../component/rails/component_mount.rb | 3 +
.../lib/reactive_record/broadcast.rb | 5 +-
.../hyper/templates/component_template.rb | 2 +-
.../hyperstack/install_generator.rb | 186 +++-----------
.../hyperstack/install_generator_base.rb | 170 +++++++++++-
17 files changed, 1066 insertions(+), 209 deletions(-)
create mode 100644 docs/rails-installation/README.md
create mode 100644 docs/rails-installation/file-structure.md
create mode 100644 docs/rails-installation/generators.md
create mode 100644 docs/rails-installation/other_details.md
create mode 100644 docs/rails-installation/prerequisites.md
create mode 100644 docs/rails-installation/using-the-installer.md
create mode 100644 docs/tutorial/intro_to_hyper_components.md
create mode 100644 release-notes/1.0.alpha1.5.md
create mode 100644 release-notes/1.0.alpha1.6.md
diff --git a/docs/SUMMARY.md b/docs/SUMMARY.md
index 5b96f359b..4f3c9f354 100644
--- a/docs/SUMMARY.md
+++ b/docs/SUMMARY.md
@@ -1,10 +1,12 @@
# Table of contents
* [Welcome](README.md)
-* [Installation](installation/README.md)
- * [Installation](installation/man-installation.md)
- * [Configuration](installation/config.md)
- * [Upgrading from legacy Hyperloop](installation/upgrading.md)
+* [Rails Installation and Configuration](rails-installation/README.md)
+ * [Prerequisites](rails-installation/prerequistes.md)
+ * [Using the Hyperstack Installer](rails-installation/using-the-installer.md)
+ * [Using the Generators](rails-installation/generators.md)
+ * [File Structure](rails-installation/file-structure.md)
+ * [Other Rails Configuration Details](rails-installation/other-details.md)
* [Client DSL](client-dsl/README.md)
* [HTML & CSS DSL](client-dsl/html-css.md)
* [Component DSL](client-dsl/components.md)
@@ -29,6 +31,7 @@
* [Methods and Features](development-workflow/hyper-spec/03-methods-and-features.md)
* [Using with Rack](development-workflow/hyper-spec/04-using-with-rack.md)
* [Tools](development-workflow/tools.md)
+ * [Deploy To Heroku](development-workflow/deploy-to-heroku.md)
* [Tutorial](tutorial/README.md)
* [TodoMVC Tutorial Part I](tutorial/todo.md)
* [TodoMVC Tutorial Part II](tutorial/todo-part-2.md)
diff --git a/docs/installation/README.md b/docs/installation/README.md
index 4026317a8..7ba05740e 100644
--- a/docs/installation/README.md
+++ b/docs/installation/README.md
@@ -1,2 +1,53 @@
# Installation
+The easiest way to install Hyperstack in either a new or existing Rails app is to run installer.
+
+## Pre-Requisites
+
+#### - Rails >= 5.x
+
+[Rails Install Instructions](http://railsinstaller.org/en)
+
+#### - Yarn
+
+For a full system install including webpacker for managing javascript assets you will
+need yarn. To skip adding webpacker use `hyperstack:install:skip-webpack`
+
+[Yarn Install Instructions](https://yarnpkg.com/en/docs/install#mac-stable)
+
+## - Creating a New Rails App
+
+If you don't have an existing Rails app to add Hyperstack to, you can create a new Rails app
+with the following command line:
+
+```
+bundle exec rails new NameOfYourApp -T
+```
+
+To avoid much pain, do not name your app `Application` as this will conflict with all sorts of
+things in Rails and Hyperstack.
+
+Once you have created the app cd into the newly created directory.
+
+> The -T option will skip adding minitest directories, as Hyperstack prefers RSpec.
+
+## - Installing HyperStack
+
+* add `gem 'rails-hyperstack', "~> 1.0.alpha1.0"` to your gem file
+* run `bundle install`
+* run `bundle exec rails hyperstack:install`
+
+> Note: if you want to use the unreleased edge branch your gem specification will be:
+>
+> ```ruby
+> gem 'rails-hyperstack',
+> git: 'git://github.com/hyperstack-org/hyperstack.git',
+> branch: 'edge',
+> glob: 'ruby/*/*.gemspec'
+> ```
+>
+
+## - Start the Rails app
+
+* `bundle exec foreman start` to start Rails and the Hotloader
+* Navigate to `http://localhost:5000/`
diff --git a/docs/installation/man-installation.md b/docs/installation/man-installation.md
index 4b1056520..07ce23e82 100644
--- a/docs/installation/man-installation.md
+++ b/docs/installation/man-installation.md
@@ -1,45 +1,4 @@
-# Installation
-
-You can install Hyperstack either
-
-* using a Rails generator,
-* or manually walking through the detailed installation instructions below.
-
-Even if you use the generator later reading through the detailed installation instructions can be helpful to understand how the system fits together and the generators work.
-
-## Pre-Requisites
-
-#### - Rails >= 5.x [Install Instructions](http://railsinstaller.org/en)
-
-And for a full system as setup generator you will need
-
-#### - Yarn [Install Instructions](https://yarnpkg.com/en/docs/install#mac-stable)
-
-## Installing Using the Generator
-
-If you have an existing Rails app, you can use the built in generator to install Hyperstack. Best to create a new branch of course before trying this out.
-
-* add `gem 'rails-hyperstack', "~> 1.0.alpha1.0"` to your gem file
-* run `bundle install`
-* run `bundle exec rails g hyperstack:install`
-
-> Note: if you want to use the unreleased edge branch your gem specification will be:
->
-> ```ruby
-> gem 'rails-hyperstack',
-> git: 'git://github.com/hyperstack-org/hyperstack.git',
-> branch: 'edge',
-> glob: 'ruby/*/*.gemspec'
-> ```
->
-> ### Start the Rails app
-
-* `bundle exec foreman start` to start Rails and the Hotloader
-* Navigate to `http://localhost:5000/`
-
-> Note that the generator will add a wild card route to the beginning of your routes file. This will let you immediately test Hyperstack, but will also mean that all of your existing routes are now unreachable. So after getting Hyperstack up, you will want to adjust things to your needs. See the first in the **Manual Installation** section for more info.
-
-## Manual Installation
+# Manual Installation
To manually install a complete Hyperstack system there are quite a few steps. However these can be broken down into six separate activities each of which will leave your system in a working and testable state:
@@ -87,6 +46,7 @@ and visit `localhost:3000/test` and you will see **TestApp** displayed.
This command accomplishes four tasks which you can also manually perform if you prefer:
1. Insure that the `hyperstack-loader` is required in your `application.js` file;
+2. Insure that the webpacker manifest file is loading JS files;
2. Insure that you have a `HyperComponent` base class defined;
3. Add a skeleton `TestApp` component and
4. Add a route to the `TestApp` component in your rails routes file.
@@ -104,7 +64,15 @@ The `hyperstack-loader` is a dynamically generated asset manifest that will load
//= require_tree .
```
-Once this is added to your `application.js` file you will see the hyperstack asset manifest on the Rails console and the browser's debug console which looks like this:
+#### Check the webpacker manifest file
+
+In Rails 6 the webpacker default installation no longer links to the javascripts directory, but because Opal uses sprockets we need to add it back in. Check to see if you have a `app/assets/config/manifest.js` file, and if you do, insure it has the following line:
+
+```javascript
+//= link_directory ../javascripts .js
+```
+
+Once hyperstack-loader and link_directory directives are added you can reload any page you will see the hyperstack asset manifest on the Rails console and the browser's debug console which looks like this:
```text
require 'opal'
@@ -133,7 +101,7 @@ require 'config/initializers/inflections.rb'
All your Hyperstack code goes into the `app/hyperstack` directory, which is at the same level as `app/models`, `app/views`, `app/controllers`, etc.
-Inside this directory are subdirectories for each of the different parts of you hyperstack application code. Components go in the `app/hyperstack/components` directory.
+Inside this directory are subdirectories for each of the different parts of you Hyperstack application code. Components go in the `app/hyperstack/components` directory.
Like Rails models, and Rails controllers, Hyperstack components by convention inherit from an application defined base class. So while a typical Rails model inherits from the `ApplicationRecord` class, your Hyperstack components will inherit from the `HyperComponent` class.
@@ -222,7 +190,6 @@ will render the component named `TestApp` at that position in your view.
You can also use `render_component` in a controller in place of the standard Rails render method. Like the `render_component` view helper you can pass the component parameters in from the controller.
-There are quite a few steps, but each has a specific, and understandable purpose.
## Installing the Hotloader
@@ -232,7 +199,7 @@ There are three steps to installing the Hotloader:
1. Importing Hotloader into your `hyperstack-loader` manifest;
2. Adding the `foreman` gem to your `Gemfile` and
-3. Adding a `Procfile` to the root of our application directory.
+3. Adding a `Procfile` to the root of our application directory.``
By default the Hotloader is **not** included in the hyperstack manifest so the first step is to add the `config/initializers/hyperstack.rb` initializer file, and _import_ the Hotloader:
diff --git a/docs/rails-installation/README.md b/docs/rails-installation/README.md
new file mode 100644
index 000000000..e88322214
--- /dev/null
+++ b/docs/rails-installation/README.md
@@ -0,0 +1,19 @@
+## Rails Installation
+
+The easiest way to get the full benefit of Hyperstack is to integrate it with a Rails application.
+
+Adding Hyperstack to your existing Rails App is as simple as adding the gem and running the installer.
+
+Read on to make sure you have the necessary prerequisites.
+> #### Why Rails?
+>
+>Rails provides a robust, tried and true tool chain that takes care of much of the day to day details of building your app. Hyperstack builds on the Rails philosophy of convention over configuration, meaning that there is almost no boiler plate code in your Rails-Hyperstack application. Almost every line that you write for your Hyperstack application will deal with the application requirements. We have seen real reductions of up to 400% in the lines of code needed to deliver high quality functionality.
+>
+>People sometimes balk at Rails because when they see the huge number of files and directories generated by the Rails installer, it looks crazy, complex, and ineffecient. Keep in mind that this has very little if any impact on your applications performance, and when developing code 90% of your time will be spent in the following directories: `app/models` and `app/hyperstack`. The rest of the files are there to hold configuration files, and seldom used content, so they have a place out of the way of your main development activities.
+>
+>Developers often believe that Rails modules like ActionController and ActiveRecord while powerful are slow.
+In the case of Hyperstack this is largely irrelevant since one of our goals is to offload as much work to the client as possible. For example rather than have a multitude of controllers delivering different page views and updates, your client side Hyperstack code is now responsible for that. The role of the server becomes the central database, and the place where secure operations are executed (such as sending mail, authenticating users etc.)
+>
+>### How about other Rack Frameworks
+>
+>But still you may have specific needs for a lighter weight system, or have an existing Sinatra app (for example) that you would like to use with Hyperstack. For now we will say its in the plan, and its just a matter of time. If you are interested leave a comment on this issue: https://github.com/hyperstack-org/hyperstack/issues/340
diff --git a/docs/rails-installation/file-structure.md b/docs/rails-installation/file-structure.md
new file mode 100644
index 000000000..e822b729f
--- /dev/null
+++ b/docs/rails-installation/file-structure.md
@@ -0,0 +1,241 @@
+## Application File Structure
+
+Hyperstack adds the following files and directories to your Rails
+application:
+
+```
+/app/hyperstack
+/app/operations
+/app/policies
+/config/initializers/hyperstack.rb
+/app/javascript/packs/client_and_server.js
+/app/javascript/packs/client_only.js
+```
+
+In addition there are configuration settings in existing Rails files that are explained in the next section. Below we cover the purpose of each these files, and their contents.
+
+### The `/app/hyperstack/` Directory
+
+Here lives all your Hyperstack code. Some of the subdirectories are *isomorphic* meaning the code is shared between the client and the server, other directories are client only.
+
+Within the `hyperstack` directory there will be the following sub-directories:
+
++ `components` *(client-only)* is where your components live.
+ Following Rails conventions a component with a class of Bar::None::FooManchu should be in a file named `components/bar/none/foo_manchu.rb`
+
++ `models` *(isomorphic)* is where ActiveRecord models are shared with the client. More on this below.
+
++ `operations` *(isomorphic)* is where Hyperstack Operations will live.
+
++ `shared` *(isomorphic)* is where you can put shared code that are not models or operations.
+
++ Any other subdirectory (such as `libs` and `client-ops`) will be considered client-only.
+
+### Sharing Models and Operations
+
+Files in the `hyperstack` `/models` and `/operations` directories are loaded on the client and the server. So when you place a model's class definition in the `hyperstack/models` directory the class is available on the client.
+
+```Ruby
+ Todo.count # will return the same value on the client and the server
+```
+
+> See the Policy section below for how access to the actual data is controlled. Remember a Model *describes* some data, but the actual data is stored in the database, and protected by Policies.
+
+Likewise Operations placed in the `/operations` directory can be run on the client or the server, or in the case of a `ServerOp` the operation can be invoked on the client, but will run on the server.
+
+Hyperstack sets things up so that Rails will first look in the `hyperstack` `/models` and `/operations` directories, and then in the server only `app/models` and `app/operations` directories. So if you don't want some model shared you can just leave it in the normal `app` directory.
+
+### Splitting Class Definitions
+
+There are cases where you would like split a class definition into its shared and server-only aspects. For example there may be code in a model that cannot be sensibly run on the client. Hyperstack augments the Rails dependency lookup mechanism so that when a file is found in a `hyperstack` directory we will *also* load any matching file in the normal `app` directory.
+
+This works because Ruby classes are *open*, so that you can define a class (or module) in multiple places.
+
+### Server Side Operations
+
+Operations are Hyperstack's way of providing *Service Objects*: classes that perform some operation not strictly belonging to a single model, and often involving other services such as remote APIs.
+
+As such Operations can be useful strictly on the server side, and so can be added to the `app/operations` directory.
+
+Server side operations can also be remotely run from the client. Such operations are defined as subclasses of `Hyperstack::ServerOp`.
+
+The right way to define a `ServerOp` is to place its basic definition including its parameter signature in the `hyperstack/operations` directory, and then placing the rest of the operations definition in the `app/operations` directory.
+
+### Policies
+
+Hyperstack uses Policies to define access rights to your models. Policies are placed in the `app/policies` directory. For example the policies for the `Todo` model would defined by the `TodoPolicy` class located at `app/policies/todo_policy.rb` Details on policies can be found [Policy section of this document.](https://docs.hyperstack.org/isomorphic-dsl/hyper-policy).
+
+### Example Directory Structure
+```
+└── app/
+ ├── models/
+ │ └── user.rb # private section of User model
+ ├── operations/
+ │ └── email_the_owner.rb # server code
+ ├── hyperstack/
+ │ ├── components/
+ │ │ ├── app.rb
+ │ │ ├── edit_todo.rb
+ │ │ ├── footer.rb
+ │ │ ├── header.rb
+ │ │ ├── show_todo.rb
+ │ │ └── todo_index.rb
+ │ ├── models/
+ │ │ ├── application_record.rb # usually no need to split this
+ │ │ ├── todo.rb # note all of Todo definition is public
+ │ │ └── user.rb # user has a public and private section
+ │ └── operations/
+ │ └── email_the_owner.rb # serverop interface only
+ └── policies/
+ ├── todo_policy.rb
+ └── user_policy.rb
+
+```
+
+These directories are where most of your work will be done during Hyperstack development.
+
+> #### What about Controllers and Views?
+Hyperstack works alongside Rails controllers and views. In a clean-sheet Hyperstack app you never need to create a controller or a view. On the other hand if you have existing code or aspects of your project that you feel would work better using a traditional MVC approach everything will work fine. You can also merge the two worlds: Hyperstack includes two helpers that allow you to mount components either from a controller or from within a view.
+
+### The Hyperstack Initializer
+
+The Hyperstack configuration can be controlled via the `config/initializers/hyperstack.rb` initializer file. Using the installer will set up a reasonable set of of options, which you can tweak as needed.
+
+Here is a summary of the various configuration settings:
+
+```ruby
+# config/initializers/hyperstack.rb
+
+# server_side_auto_require will patch the ActiveSupport Dependencies module
+# so that you can define classes and modules with files in both the
+# app/hyperstack/xxx and app/xxx directories.
+
+require "hyperstack/server_side_auto_require.rb"
+
+# By default the generators will generate new components as subclasses of
+# HyperComponent. You can change this using the component_base_class setting.
+
+Hyperstack.component_base_class = 'HyperComponent' # i.e. 'ApplicationComponent'
+
+# prerendering is default :off, you should wait until your
+# application is relatively well debugged before turning on.
+
+Hyperstack.prerendering = :off # or :on
+
+# The transport setting controls how push (websocket) communications are
+# implemented. The default is :none, but will be set to :action_cable if you
+# install hyper-model.
+
+# Other possibilities are :action_cable, :pusher (see www.pusher.com)
+# or :simple_poller which is sometimes handy during system debug.
+
+Hyperstack.transport = :action_cable # :pusher, :simple_poller or :none
+
+# hotloader settings:
+# sets the port hotloader will listen on. Note this must match the value used
+# to start the hotloader typically in the foreman Procfile.
+Hyperstack.hotloader_port = 25222
+# seconds between pings over the hotloader websocket. Normally not needed.
+Hyperstack.hotloader_ping = nil
+# hotloader will automatically reload callbacks when effected classes are
+# reloaded. Not recommended to change this.
+Hyperstack.hotloader_ignore_callback_mapping = false
+
+# Transport settings
+# seconds before timeout when sending messages between the rails console and
+# the server.
+Hyperstack.send_to_server_timeout = 10
+
+# Transport specific options
+Hyperstack.opts, {
+ # pusher specific options
+ app_id: 'your pusher app id',
+ key: 'your pusher key',
+ secret: 'your pusher secret',
+ cluster: 'mt1', # pusher cluster defaults to mt1
+ encrypted: true, # encrypt pusher comms, defaults to true
+ refresh_channels_every: 2.minutes, # how often to check which channels are alive
+
+ # simple poller specific options
+ expire_polled_connection_in: 5.minutes, # when to kill simple poller connections
+ seconds_between_poll: 5.seconds, # how fast to poll when using simple poller
+ expire_new_connection_in: 10.seconds, # how long to keep initial sessions alive
+}
+
+# Namespace used to keep hyperstack communication separate from other websockets
+Hyperstack.channel_prefix = 'synchromesh'
+
+# If there a JS console available should websocket comms be logged?
+Hyperstack.client_logging = true
+
+# Automatically create a (possibly temporary) websocket connection as each
+# browser session starts. Usually this is needed for further authentication and
+# should be left as true
+Hyperstack.connect_session = true
+
+# Where to store the connection tables. Default is :active_record but you
+# can also specify redis. If specifying redis the redis url defaults to
+# redis://127.0.0.1:6379
+Hyperstack.connection = [adapter: :active_record] # or
+ # [adapter: :redis, redis_url: 'redis://127.0.0.1:6379]
+
+# The import directive loads optional portions of the various hyperstack gems.
+# Here are the common imports typically included:
+
+Hyperstack.import 'hyperstack/hotloader', client_only: true if Rails.env.development?
+
+# and these are typically not imported:
+
+# React source is normally brought in through webpacker
+# Hyperstack.import 'react/react-source-browser'
+
+# add this line if you need jQuery AND ARE NOT USING WEBPACK
+# Hyperstack.import 'hyperstack/component/jquery', client_only: true
+
+# The following are less common settings which you should never have to change:
+Hyperstack.prerendering_files = ['hyperstack-prerender-loader.js']
+Hyperstack.public_model_directories = ['app/hyperstack/models']
+
+
+# change definition of on_error to control how errors such as validation
+# exceptions are reported on the server
+module Hyperstack
+ def self.on_error(operation, err, params, formatted_error_message)
+ ::Rails.logger.debug(
+ "#{formatted_error_message}\n\n" +
+ Pastel.new.red(
+ 'To further investigate you may want to add a debugging '\
+ 'breakpoint to the on_error method in config/initializers/hyperstack.rb'
+ )
+ )
+ end
+end if Rails.env.development?
+```
+
+### Hyperstack Packs
+
+Rails `webpacker` organizes javascript into *packs*. Hyperstack will look for and load one of two packs depending on if you are prerendering or not.
+
+The default content of these packs are as follows:
+
+```javascript
+//app/javascript/packs/client_and_server.js
+// these packages will be loaded both during prerendering and on the client
+React = require('react'); // react-js library
+createReactClass = require('create-react-class'); // backwards compatibility with ECMA5
+History = require('history'); // react-router history library
+ReactRouter = require('react-router'); // react-router js library
+ReactRouterDOM = require('react-router-dom'); // react-router DOM interface
+ReactRailsUJS = require('react_ujs'); // interface to react-rails
+// to add additional NPM packages run `yarn add package-name@version`
+// then add the require here.
+```
+
+```javascript
+//app/javascript/packs/client_only.js
+// add any requires for packages that will run client side only
+ReactDOM = require('react-dom'); // react-js client side code
+jQuery = require('jquery'); // remove if you don't need jQuery
+// to add additional NPM packages call run yarn add package-name@version
+// then add the require here.
+```
diff --git a/docs/rails-installation/generators.md b/docs/rails-installation/generators.md
new file mode 100644
index 000000000..dbb8e6872
--- /dev/null
+++ b/docs/rails-installation/generators.md
@@ -0,0 +1,114 @@
+## Hyperstack Generators
+
+As well as the installer Hyperstack includes two generators to create
+basic component skeletons.
+
+### Summary:
+
+```
+bundle exec rails g hyper:component ComponentName # add a new component
+bundle exec rails g hyper:router RouterName # add a new router component
+```
+
+both support the following flags:
+
++ `--no-help` don't add extra comments and method examples
++ `--add-route=...` add a route to this component to the Rails routes file
++ `--base-class=...` change the base class name from the default
+
+### The Component Generator
+
+To add a new component skeleton use the `hyper:component` generator:
+
+```
+bundle exec rails g hyper:component ComponentName
+```
+
+#### File directories and Name Spacing Components
+
+The above will create a new class definition for `ComponentName` in a file named `component_name.rb` and place it in
+the `app/hyperstack/components/` directory. The component may be name spaced and
+will be placed in the appropriate subdirectory. I.e. `Foo::BarSki` will generate
+`app/hyperstack/components/foo/barski.rb`
+
+#### The `--no-help` flag
+
+By default the skeleton will be verbose and contain examples of the most often used
+class methods which you can keep or delete as needed. You can generate a minimal
+component with the `--no-help` flag.
+
+### Router Generator
+
+Typically your top level component will be a *Router* which will take care of dispatching to specific components as the URL changes. This provides the essence of a *Single Page App* where as the user moves between parts of
+the application the URL is updated, the back and forward buttons work, but the page is **not** reloaded from the server.
+
+A component becomes a router by including the `Hyperstack::Router` module
+which provides a number of methods that will be used in the router
+component.
+
+To generate a new router skeleton use the `hyper:router` generator:
+
+```
+bundle exec rails g hyper:router App
+```
+
+Note that we now have two routers to deal with. The server still has the `routes.rb` file that maps incoming requests to a Rails controller which
+will provide the appropriate response.
+
+On the client the router there maps the current url to a component.
+
+#### Routing to Your Components from Rails
+
+Components can be directly mounted from the Rails `routes.rb` file, using the builtin Hyperstack controller.
+
+For example a Rails `routes.rb` file containing
+
+```ruby
+ get 'some_page/(*others)', to: 'hyperstack#some_component'
+```
+
+will route all urls beginning with `some_page` to `SomeComponent`.
+
+When you generate a new component you can use the `--add-route` option to add the route for you. For example:
+
+```
+bundle exec rails g hyper:router SomeComponent \
+ --add-route="some_page/(*others)"
+```
+
+would add the route shown above.
+
+Note that typically the Rails route will be going to a Hyperstack Router Component. That is why we add the wild card to the Rails route so that all urls beginning with `some_page/` will all be handled by `SomeComponent`.
+
+Also note that for the purposes of the example we are using rather dubious names, a more logical setup would be:
+
+```ruby
+ get `/(*others)`, to 'hyperstack#app'
+```
+
+Which you could generate with
+```
+bundle exec rails g hyper:router App --add-route="/(*others)"
+```
+
+#### Changing the Base Class
+
+By default components will inherit from the `HyperComponent` base class.
+
+You can globally override this by changing the value `Hyperstack.component_base_class` in the `hyperstack.rb` initializer.
+
+For example some teams prefer `ApplicationComponent` as their base class name.
+
+You can also override the base class name when generating a component using the `--base-class` option.
+
+This is useful when you have a common library subclass that other classes will inherit from. For example:
+
+```
+bundle exec rails g hyper:component UserBio --base-class=TextArea
+```
+will generate
+```
+class UserBio < TextArea
+...
+end
+```
diff --git a/docs/rails-installation/other_details.md b/docs/rails-installation/other_details.md
new file mode 100644
index 000000000..a647d55a6
--- /dev/null
+++ b/docs/rails-installation/other_details.md
@@ -0,0 +1,115 @@
+## Other Rails Configuration Details
+
+Hyperstack sets a number of Rails configurations as outlined below.
+
+>These are all setup
+automatically by the hyperstack generators and installers. They are documented here for advanced configuration or in the sad chance that something gets broken during your setup. Please report any issues with setup, or if you feel you have to manually tweak things.
+
+#### Require the `hyperstack-loader`
+
+The `app/assets/javascripts/application.js` file needs to require the hyperstack-loader.
+
+```javascript
+//= require hyperstack-loader // add as the last require directive
+```
+
+The loader handles bringing in client side code, getting it compiled (using sprockets) and adding it to the webpacks (if using webpacker.)
+
+> Note that now that Rails is using webpacker by default you may have to create
+this file, and the single line above. If so be sure to checkout your layout
+file, as the javascript_include_tag will also be missing there.
+
+#### `app/assets/config/manifest.js`
+
+If you are using webpacker this file must exist and contain the following line:
+
+```Ruby
+//= link_directory ../javascripts .js
+```
+
+This line insures that the any javascript in the assets directory are included in the webpacks. In older versions of Rails, this line will already be there, and if not
+using webpacker its actually not necessary (but doesn't hurt anything.)
+
+#### The application layout
+
+If using a recent version of rails with webpacker you may find that the application.html.erb file longer loads the application.js file. Make sure that your layout file has this line:
+
+```html
+ <%= javascript_include_tag 'application' %>
+```
+
+#### Required NPM modules
+
+If using Webpacker Hyperstack needs the following NPM modules:
+
+```
+yarn 'react', '16'
+yarn 'react-dom', '16'
+yarn 'react-router', '^5.0.0'
+yarn 'react-router-dom', '^5.0.0'
+yarn 'react_ujs', '^2.5.0'
+yarn 'jquery', '^3.4.1' # this is only needed if using jquery
+yarn 'create-react-class'
+```
+
+#### Routing
+
+If using hyper-model you need to mount the Hyperstack engine in the routes file like this:
+
+```ruby
+# config/routes.rb
+Rails.application.routes.draw do
+ # this route should be first in the routes file so it always matches'
+ mount Hyperstack::Engine => '/hyperstack' # you can use any path you choose
+ ...
+```
+
+To directly route from a URL to a component you can use the builting Hyperstack
+controller with a route like this:
+
+```ruby
+ get "hyperstack-page/(*others)", "hyperstack#comp_name"
+```
+
+Where `comp_name` is the underscored name of the component you want to mount. I.e. `MyComp` becomes `my_comp`. The `/(*others)` indicates that all routes beginning with
+`hyperstack-page/` will be matched, if that is your desired behavior.
+
+> Note that the engine mount point can be any string you wish but the controller routed to above is always `hyperstack`.
+
+#### Other Rails Configuration Settings
+
+Hyperstack will by default set a number of Rails configuration settings. To disable this
+set
+```ruby
+ config.hyperstack.auto_config = false
+```
+In your Rails application.rb configuration file.
+
+Otherwise the following settings are automatically applied in test and staging:
+
+```ruby
+# This will prevent any data transmitted by HyperOperation from appearing in logs
+config.filter_parameters << :hyperstack_secured_json
+
+# Add the hyperstack directories
+config.eager_load_paths += %W(#{config.root}/app/hyperstack/models)
+config.eager_load_paths += %W(#{config.root}/app/hyperstack/models/concerns)
+config.eager_load_paths += %W(#{config.root}/app/hyperstack/operations)
+config.eager_load_paths += %W(#{config.root}/app/hyperstack/shared)
+
+# But remove the outer hyperstack directory so rails doesn't try to load its
+# contents directly
+delete_first config.eager_load_paths, "#{config.root}/app/hyperstack"
+```
+but in production we autoload instead of eager load.
+```ruby
+ # add the hyperstack directories to the auto load paths
+ config.autoload_paths += %W(#{config.root}/app/hyperstack/models)
+ config.autoload_paths += %W(#{config.root}/app/hyperstack/models/concerns)
+ config.autoload_paths += %W(#{config.root}/app/hyperstack/operations)
+ config.autoload_paths += %W(#{config.root}/app/hyperstack/shared)
+
+ # except for the outer hyperstack directory
+ delete_first config.autoload_paths, "#{config.root}/app/hyperstack"
+end
+```
diff --git a/docs/rails-installation/prerequisites.md b/docs/rails-installation/prerequisites.md
new file mode 100644
index 000000000..61443e8e6
--- /dev/null
+++ b/docs/rails-installation/prerequisites.md
@@ -0,0 +1,35 @@
+## Prerequisites
+
+#### Rails
+
+Hyperstack is currently tested on Rails ~> 5.0 and ~> 6.0, if you are on Rails 4.0 it might be time to upgrade, but that said you probably can manually install Hyperstack on Rails 4.0 and get it working.
+
+[Rails Install Instructions](http://railsinstaller.org/en)
+
+#### Yarn
+
+For a full system install including webpacker for managing javascript assets you will
+need yarn. To skip adding webpacker use `hyperstack:install:skip-webpack` when installing Hyperstack.
+
+[Yarn Install Instructions](https://yarnpkg.com/en/docs/install#mac-stable)
+
+#### - Database
+
+To fully utilize Hyperstack's capabilities you will be need an SQL database that has an ActiveRecord adapter. If you have a choice we have found Postgresql works best (and it also deploys to Heroku without issue.) If you are new to Rails, then the default Sqlite database (which rails will install) will work fine.
+> Why Don't You Support NoSql databases? The biggest reasons are security and effeciency. Hyperstack access policies are based on known table names and attributes, and after commit hooks. Keep in mind that modern DBs (and Hyperstack support the json and jsonb attribute types allowing you to add arbitrary json based data to your database)
+
+### Creating a New Rails App
+
+If you don't have an existing Rails app to add Hyperstack to, you can create a new Rails app
+with the following command line:
+
+```
+bundle exec rails new NameOfYourApp -T
+```
+
+To avoid much pain, do not name your app `Application` as this will conflict with all sorts of
+things in Rails and Hyperstack.
+
+Once you have created the app cd into the newly created directory.
+
+> The -T option will skip adding minitest directories as Hyperstack prefers RSpec. However if you have an existing app with minitest that is okay too.
diff --git a/docs/rails-installation/using-the-installer.md b/docs/rails-installation/using-the-installer.md
new file mode 100644
index 000000000..dde69b6a3
--- /dev/null
+++ b/docs/rails-installation/using-the-installer.md
@@ -0,0 +1,38 @@
+## Installing HyperStack
+
+* add `gem 'rails-hyperstack', "~> 1.0.alpha1.0"` to your gem file
+* run `bundle install`
+* run `bundle exec rails hyperstack:install`
+
+> Note: if you want to use the unreleased edge branch your gem specification will be:
+>
+> ```ruby
+> gem 'rails-hyperstack',
+> git: 'git://github.com/hyperstack-org/hyperstack.git',
+> branch: 'edge',
+> glob: 'ruby/*/*.gemspec'
+> ```
+
+### Start the Rails app
+
+* `bundle exec foreman start` to start Rails and the Hotloader
+* Navigate to `http://localhost:5000/`
+
+You will see an empty page with the word "App" displayed.
+
+### Installer Options
+
+You can control what gets installed with the following options:
+
+```
+bundle exec rails hyperstack:install:webpack # just add webpack
+bundle exec rails hyperstack:install:skip-webpack # all but webpack
+bundle exec rails hyperstack:install:hyper-model # just add hyper-model
+bundle exec rails hyperstack:install:skip-hyper-model # all but hyper-model
+bundle exec rails hyperstack:install:hotloader # just add the hotloader
+bundle exec rails hyperstack:install:skip-hotloader # skip the hotloader
+```
+
+> Note that the `:webpack` and `:skip-webpack` options control whether the installer will
+add the webpacker Gem. If webpacker is already installed in the Gemfile then the
+installer will always integrate with webpacker.
diff --git a/docs/tutorial/intro_to_hyper_components.md b/docs/tutorial/intro_to_hyper_components.md
new file mode 100644
index 000000000..e9b4a2632
--- /dev/null
+++ b/docs/tutorial/intro_to_hyper_components.md
@@ -0,0 +1,132 @@
+#Tutorial: Intro to React
+
+This tutorial doesn’t assume any existing HyperStack or React knowledge.
+
+##Before We Start the Tutorial
+
+> This tutorial is shamelessly stolen for pedagogical reasons from this [React tutorial](https://reactjs.org/tutorial/tutorial.html)
+
+In this tutorial you will build a small game. Even though its just a small game, the techniques you’ll learn are fundamental to building any HyperStack app, and mastering it will give you a deep understanding of not only Hyper Conponents but also of React.
+
+
+> Tip: This tutorial is designed for people who prefer to learn by doing. If you prefer learning concepts from the ground up, check out our step-by-step guide. You might find this tutorial and the guide complementary to each other.
+
+The tutorial is divided into several sections:
+
++ Setup for the Tutorial will give you a starting point to follow the tutorial.
++ Overview will teach you the fundamentals of HyperStack: Components, Params and State.
++ Completing the game will teach you the most common techniques in Hyperstack development.
++ Adding Time Travel will give you a deeper insight into the unique strengths of HyperStack and the underlying React technologies.
+
+You don’t have to complete all of the sections at once to get the value out of this tutorial. Try to get as far as you can — even if it’s one or two sections.
+
+### What Are We Building?
+
+In this tutorial, we’ll show how to build an interactive tic-tac-toe game with HyperStack.
+
+###Prerequisites
+
+We’ll assume that you have some familiarity with HTML and Ruby, but you should be able to follow along even if you’re coming from a different programming language such as Javascript, or if you have familiarit with React. We’ll also assume that you’re familiar with programming concepts like methods (functions), objects, arrays, and to a lesser extent, classes.
+
+Setup for the Tutorial
+There are two ways to complete this tutorial: you can either write the code in your browser, or you can set up a local development environment on your computer.
+
+Setup Option 1: Write Code in the Browser
+This is the quickest way to get started!
+
+First, open this Starter Code in a new tab. The new tab should display an empty tic-tac-toe game board and React code. We will be editing the React code in this tutorial.
+
+You can now skip the second setup option, and go to the Overview section to get an overview of React.
+
+Setup Option 2: Local Development Environment
+This is completely optional and not required for this tutorial!
+
+
+Optional: Instructions for following along locally using your preferred text editor
+Help, I’m Stuck!
+If you get stuck, check out the community support resources. In particular, Reactiflux Chat is a great way to get help quickly. If you don’t receive an answer, or if you remain stuck, please file an issue, and we’ll help you out.
+
+Overview
+Now that you’re set up, let’s get an overview of React!
+
+What Is React?
+React is a declarative, efficient, and flexible JavaScript library for building user interfaces. It lets you compose complex UIs from small and isolated pieces of code called “components”.
+
+React has a few different kinds of components, but we’ll start with React.Component subclasses:
+
+class ShoppingList extends React.Component {
+ render() {
+ return (
+
+
Shopping List for {this.props.name}
+
+
Instagram
+
WhatsApp
+
Oculus
+
+
+ );
+ }
+}
+
+// Example usage:
+We’ll get to the funny XML-like tags soon. We use components to tell React what we want to see on the screen. When our data changes, React will efficiently update and re-render our components.
+
+Here, ShoppingList is a React component class, or React component type. A component takes in parameters, called props (short for “properties”), and returns a hierarchy of views to display via the render method.
+
+The render method returns a description of what you want to see on the screen. React takes the description and displays the result. In particular, render returns a React element, which is a lightweight description of what to render. Most React developers use a special syntax called “JSX” which makes these structures easier to write. The syntax is transformed at build time to React.createElement('div'). The example above is equivalent to:
+
+return React.createElement('div', {className: 'shopping-list'},
+ React.createElement('h1', /* ... h1 children ... */),
+ React.createElement('ul', /* ... ul children ... */)
+);
+See full expanded version.
+
+If you’re curious, createElement() is described in more detail in the API reference, but we won’t be using it in this tutorial. Instead, we will keep using JSX.
+
+JSX comes with the full power of JavaScript. You can put any JavaScript expressions within braces inside JSX. Each React element is a JavaScript object that you can store in a variable or pass around in your program.
+
+The ShoppingList component above only renders built-in DOM components like and . But you can compose and render custom React components too. For example, we can now refer to the whole shopping list by writing . Each React component is encapsulated and can operate independently; this allows you to build complex UIs from simple components.
+
+Inspecting the Starter Code
+If you’re going to work on the tutorial in your browser, open this code in a new tab: Starter Code. If you’re going to work on the tutorial locally, instead open src/index.js in your project folder (you have already touched this file during the setup).
+
+This Starter Code is the base of what we’re building. We’ve provided the CSS styling so that you only need to focus on learning React and programming the tic-tac-toe game.
+
+By inspecting the code, you’ll notice that we have three React components:
+
+Square
+Board
+Game
+The Square component renders a single