Class: Sequel::Dataset

Inherits:
Object
  • Object
show all
Defined in:
lib/sequel_opal_runtime_patches.rb,
lib/sequel_opal_async_dataset_patches.rb

Direct Known Subclasses

Sequel::D1::Dataset

Instance Method Summary collapse

Instance Method Details

#__homura_orig__insert_values_sqlObject



114
# File 'lib/sequel_opal_runtime_patches.rb', line 114

alias_method :__homura_orig__insert_values_sql, :_insert_values_sql

#__homura_orig_literal_appendObject

upstream literal_append Symbol branch:

l = String.new
literal_symbol_append(l, v)
db.literal_symbol_set(v, l)

homura: use Buffer for the append accumulator; cache the rendered String form on the db so subsequent calls hit the cache without re-creating a Buffer.



88
# File 'lib/sequel_opal_runtime_patches.rb', line 88

alias_method :__homura_orig_literal_append, :literal_append

#__homura_orig_update_sql_values_hashObject



108
# File 'lib/sequel_opal_runtime_patches.rb', line 108

alias_method :__homura_orig_update_sql_values_hash, :update_sql_values_hash

#_all(block) ⇒ Object

upstream: a = []; yield a; post_load(a); a.each(&block) if block; a homura: yield(a) returns a Promise when the caller block crosses the D1 adapter’s async boundary (Dataset#all’s block is async-compiled). Await so ‘a` is populated before post_load.



51
52
53
54
55
56
57
# File 'lib/sequel_opal_async_dataset_patches.rb', line 51

def _all(block)
  a = []
  yield(a).__await__
  post_load(a)
  a.each(&block) if block
  a
end

#_insert_values_sql(sql, values) ⇒ Object



115
116
117
118
119
120
# File 'lib/sequel_opal_runtime_patches.rb', line 115

def _insert_values_sql(sql, values)
  if values.is_a?(Array)
    values = values.map { |v| homura_sql_value(v) }
  end
  __homura_orig__insert_values_sql(sql, values)
end

#eachObject

upstream each:

if rp = row_proc; fetch_rows(select_sql){|r| yield rp.call(r)}
else              fetch_rows(select_sql){|r| yield r}
end; self

homura: fetch_rows is async (D1 adapter awaits the Promise chain). If we leave each sync, the block passed to fetch_rows never runs before each returns. Await fetch_rows to let the inner block fire first.



38
39
40
41
42
43
44
45
# File 'lib/sequel_opal_async_dataset_patches.rb', line 38

def each
  if rp = row_proc
    fetch_rows(select_sql){|r| yield rp.call(r)}.__await__
  else
    fetch_rows(select_sql){|r| yield r}.__await__
  end
  self
end

#literal_append(sql, v) ⇒ Object



89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
# File 'lib/sequel_opal_runtime_patches.rb', line 89

def literal_append(sql, v)
  if v.is_a?(::HomuraSqlStringLiteral)
    v.sql_literal_append(self, sql)
  elsif v.is_a?(Symbol)
    if skip_symbol_cache?
      literal_symbol_append(sql, v)
    else
      unless l = db.literal_symbol(v)
        l = sql_string_origin
        literal_symbol_append(l, v)
        db.literal_symbol_set(v, l.to_s)
      end
      sql << l
    end
  else
    __homura_orig_literal_append(sql, v)
  end
end

#single_valueObject

upstream: single_value_ds.each{|r| r.each{|_, v| return v}}; nil homura: capture first value using sentinel flag. Relies on each awaiting the D1 Promise chain.



91
92
93
94
95
96
97
98
99
100
101
102
103
104
# File 'lib/sequel_opal_async_dataset_patches.rb', line 91

def single_value
  value = nil
  found = false
  # each is async (patched in this file); must await.
  (single_value_ds.each do |r|
    next if found
    r.each do |_, v|
      next if found
      value = v
      found = true
    end
  end).__await__
  found ? value : nil
end

#sql_string_originObject



66
67
68
# File 'lib/sequel_opal_runtime_patches.rb', line 66

def sql_string_origin
  ::HomuraSqlBuffer.new
end

#update_sql_values_hash(sql, values) ⇒ Object



109
110
111
112
# File 'lib/sequel_opal_runtime_patches.rb', line 109

def update_sql_values_hash(sql, values)
  values = values.each_with_object({}) { |(k, v), acc| acc[k] = homura_sql_value(v) }
  __homura_orig_update_sql_values_hash(sql, values)
end

#with_sql_each(sql) ⇒ Object

upstream: with_sql_each(sql){|r| yield r}; self (sync, but fetch_rows returns a Promise under the D1 adapter, so the block body doesn’t run before the caller’s sync flow resumes — the Promise is dropped). homura: reopen with ‘.__await__` so the async fetch_rows resolves before this method returns. Required for #first / #with_sql_first / #with_sql_single_value which expect the block to have fired.



65
66
67
68
69
70
71
72
# File 'lib/sequel_opal_async_dataset_patches.rb', line 65

def with_sql_each(sql)
  if rp = row_proc
    _with_sql_dataset.fetch_rows(sql){|r| yield rp.call(r)}.__await__
  else
    _with_sql_dataset.fetch_rows(sql){|r| yield r}.__await__
  end
  self
end

#with_sql_first(sql) ⇒ Object

upstream: with_sql_each(sql){|r| return r}; nil homura: capture first row without ‘return`; callers always clone with limit(1) so the no-break form is equivalent. Needs with_sql_each to actually await its fetch_rows (see above).



78
79
80
81
82
83
84
85
86
# File 'lib/sequel_opal_async_dataset_patches.rb', line 78

def with_sql_first(sql)
  result = nil
  # with_sql_each is async now (awaits fetch_rows internally); we must
  # await here so `result` is populated before returning.
  (with_sql_each(sql) do |r|
    result = r if result.nil?
  end).__await__
  result
end

#with_sql_single_value(sql) ⇒ Object

upstream: if r = with_sql_first(sql); r.each{|_, v| return v}; end homura: same capture-first-value pattern via sentinel.



108
109
110
111
112
113
114
115
116
117
118
119
# File 'lib/sequel_opal_async_dataset_patches.rb', line 108

def with_sql_single_value(sql)
  if r = with_sql_first(sql)
    value = nil
    captured = false
    r.each do |_, v|
      next if captured
      value = v
      captured = true
    end
    value
  end
end