From 012c85254ccc0f21af64be22876f31464a06e96a Mon Sep 17 00:00:00 2001 From: keyasuda Date: Sun, 1 Jan 2023 21:08:55 +0900 Subject: [PATCH 1/3] use evalAsync to use JS::Object#await --- npm/src/ruby.js | 32 +++++++++++++++++++++----------- test-app/js/app.js | 6 +++--- test-app/spec/test_app_spec.rb | 11 ++++++++++- test-app/src/app.rb | 6 ++++++ test-app/src/views/index.erb | 3 ++- 5 files changed, 42 insertions(+), 16 deletions(-) diff --git a/npm/src/ruby.js b/npm/src/ruby.js index e1fc300..e26fe65 100644 --- a/npm/src/ruby.js +++ b/npm/src/ruby.js @@ -11,7 +11,7 @@ const currentPath = () => location.href.replace(location.origin, '') export const router = hr export const mount = () => router.always(() => request('get', currentPath())) -export const request = ( +export const request = async ( method, path, payload = '', @@ -19,7 +19,7 @@ export const request = ( ) => { const target = document.querySelector('#bormashino-application') - const ret = requestToServer(method, path, payload, referer) + const ret = await requestToServer(method, path, payload, referer) if (applyServerResult(JSON.parse(ret.toJS()), target, router)) hookTransitionElements(target, request) } @@ -47,6 +47,9 @@ export const initVmFromRubyModule = async ( ) => { const wasmFs = new WasmFs() const wasi = new WASI({ + env: { + RUBY_FIBER_MACHINE_STACK_SIZE: String(1024 * 1024 * 20), + }, bindings: Object.assign(Object.assign({}, WASI.defaultBindings), { fs: wasmFs.fs, }), @@ -93,15 +96,22 @@ export const initVmFromRubyModule = async ( return vm } -const requestToServer = (method, path, payload, referer) => { - const server = vm.eval('Bormashino::Server') - const ret = server.call( - 'request', - toRbValue(method.toUpperCase()), - toRbValue(path), - toRbValue(payload), - toRbValue(referer) - ) +const requestToServer = async (method, path, payload, referer) => { + window.bormashino.requestSrc = JSON.stringify({ + method, + path, + payload, + referer, + }) + const ret = await vm.evalAsync(` + src = JSON.parse(JS.global[:window][:bormashino][:requestSrc].inspect) + Bormashino::Server.request( + src['method'].upcase, + src['path'], + src['payload'], + src['referer'] + ) + `) return ret } diff --git a/test-app/js/app.js b/test-app/js/app.js index 09045ee..f9069ea 100644 --- a/test-app/js/app.js +++ b/test-app/js/app.js @@ -20,12 +20,12 @@ const main = async () => { 'dispatched: ' + Number(new Date()) }) + window.bormashino = RubyApplication + window.rubyVM = vm + const currentPath = () => location.href.replace(location.origin, '') RubyApplication.request('get', currentPath()) RubyApplication.mount() - - window.bormashino = RubyApplication - window.rubyVM = vm } main() diff --git a/test-app/spec/test_app_spec.rb b/test-app/spec/test_app_spec.rb index 39597ff..98bb45b 100644 --- a/test-app/spec/test_app_spec.rb +++ b/test-app/spec/test_app_spec.rb @@ -62,7 +62,7 @@ it { is_expected.to have_text('2nd form has submitted') } end - describe 'fetch api' do + describe 'Bormashino::Fetch' do before do click_link 'fetch test' sleep 1 @@ -71,6 +71,15 @@ it { is_expected.to have_text('{"status"=>"200", "payload"=>"fetched text\n", "options"=>"{\"param1\":\"value1\",\"param2\":\"value2\"}"}') } end + describe 'async/await' do + before do + click_link 'JS::Object#await fetch' + sleep 1 + end + + it { is_expected.to have_text('fetched text') } + end + describe 'LocalStorage' do before do click_link 'localstorage test' diff --git a/test-app/src/app.rb b/test-app/src/app.rb index 4052494..7a989fc 100644 --- a/test-app/src/app.rb +++ b/test-app/src/app.rb @@ -38,6 +38,12 @@ class App < Sinatra::Base 'initiated' end + get '/fetch2' do + result = JS.global.fetch('/fetch.txt').await + ret = result.text.await + ret.to_s + end + post '/fetched' do params.inspect end diff --git a/test-app/src/views/index.erb b/test-app/src/views/index.erb index 7d7f524..95ac69b 100644 --- a/test-app/src/views/index.erb +++ b/test-app/src/views/index.erb @@ -1,7 +1,8 @@

ruby appが初期化されました。

link

-

fetch test

+

fetch test(Bormashino::Fetch)

+

JS::Object#await fetch

From 1420181b0ca144c2f3695bb8acac87a94a87488b Mon Sep 17 00:00:00 2001 From: keyasuda Date: Mon, 2 Jan 2023 17:42:04 +0900 Subject: [PATCH 2/3] remove toRbValue, use JS::Object#to_s --- gem/lib/bormashino/ext/js.rb | 2 +- npm/src/ruby.js | 11 +---------- 2 files changed, 2 insertions(+), 11 deletions(-) diff --git a/gem/lib/bormashino/ext/js.rb b/gem/lib/bormashino/ext/js.rb index 5a850e2..83388e8 100644 --- a/gem/lib/bormashino/ext/js.rb +++ b/gem/lib/bormashino/ext/js.rb @@ -4,7 +4,7 @@ module JS # extends ruby.wasm JS::Object to intract with JS class Object def to_rb - JSON.parse(JS.global[:JSON].call(:stringify, self).inspect) + JSON.parse(JS.global[:JSON].call(:stringify, self).to_s) end end end diff --git a/npm/src/ruby.js b/npm/src/ruby.js index e26fe65..4e61cf4 100644 --- a/npm/src/ruby.js +++ b/npm/src/ruby.js @@ -24,15 +24,6 @@ export const request = async ( hookTransitionElements(target, request) } -// JSでの値をRubyでの値に変換する -// JS obj -> JSON -> url-encoded str -> (vm.eval) -> JSON -> Ruby obj -const toRbValue = (v) => { - const input = "'" + encodeURIComponent(JSON.stringify(v)) + "'" - return vm - .eval('JSON') - .call('parse', vm.eval('CGI').call('unescape', vm.eval(input))) -} - export const initVm = async ( rubyUri, initializeOption = ['ruby.wasm', '-I/stub', '-EUTF-8', '-e_=0'] @@ -104,7 +95,7 @@ const requestToServer = async (method, path, payload, referer) => { referer, }) const ret = await vm.evalAsync(` - src = JSON.parse(JS.global[:window][:bormashino][:requestSrc].inspect) + src = JSON.parse(JS.global[:window][:bormashino][:requestSrc].to_s) Bormashino::Server.request( src['method'].upcase, src['path'], From 0dc05f59a8c02046ba6fb7b674270aee622585b8 Mon Sep 17 00:00:00 2001 From: keyasuda Date: Mon, 2 Jan 2023 18:10:06 +0900 Subject: [PATCH 3/3] deprecate Bormashino::Fetch --- gem/lib/bormashino/fetch.rb | 2 ++ 1 file changed, 2 insertions(+) diff --git a/gem/lib/bormashino/fetch.rb b/gem/lib/bormashino/fetch.rb index cd4bf41..fb976ca 100644 --- a/gem/lib/bormashino/fetch.rb +++ b/gem/lib/bormashino/fetch.rb @@ -8,6 +8,8 @@ class Fetch attr_accessor :resource, :init, :resolved_to, :options def initialize(resource:, resolved_to:, init: {}, options: {}) + JS.eval("console.warn('Bormashino::Fetch is deprecated. Use Fetch API and JS::Object#await')") + @resource = resource @init = init @resolved_to = resolved_to