rubydb 0.1.5 → 0.1.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.gitignore +4 -0
- data/CHANGELOG.md +14 -0
- data/Gemfile.lock +1 -1
- data/README.md +296 -227
- data/Rakefile +6 -1
- data/accelerator/bin/SHA256SUMS +6 -0
- data/accelerator/bin/rubydb-accelerator-darwin-amd64 +0 -0
- data/accelerator/bin/rubydb-accelerator-darwin-arm64 +0 -0
- data/accelerator/bin/rubydb-accelerator-linux-amd64 +0 -0
- data/accelerator/bin/rubydb-accelerator-linux-arm64 +0 -0
- data/accelerator/bin/rubydb-accelerator-windows-amd64.exe +0 -0
- data/accelerator/bin/rubydb-accelerator-windows-arm64.exe +0 -0
- data/accelerator/cmd/rubydb-accelerator/main.go +11 -0
- data/accelerator/go.mod +3 -0
- data/accelerator/internal/execution/aggregate.go +94 -0
- data/accelerator/internal/execution/distinct.go +22 -0
- data/accelerator/internal/execution/filter.go +73 -0
- data/accelerator/internal/execution/join.go +79 -0
- data/accelerator/internal/execution/operators.go +167 -0
- data/accelerator/internal/execution/scan.go +20 -0
- data/accelerator/internal/execution/sort.go +62 -0
- data/accelerator/internal/execution/types.go +136 -0
- data/accelerator/internal/execution/value.go +67 -0
- data/accelerator/internal/memory/arena.go +47 -0
- data/accelerator/internal/memory/reuse.go +22 -0
- data/accelerator/internal/metrics/registry.go +67 -0
- data/accelerator/internal/parallel/bounded_queue.go +56 -0
- data/accelerator/internal/parallel/scheduler.go +47 -0
- data/accelerator/internal/parallel/worker_pool.go +53 -0
- data/accelerator/internal/protocol/cancellation.go +48 -0
- data/accelerator/internal/protocol/columnar.go +263 -0
- data/accelerator/internal/protocol/frame.go +187 -0
- data/accelerator/internal/runtime/worker.go +521 -0
- data/accelerator/internal/storage/page_reader.go +81 -0
- data/accelerator/internal/storage/snapshot_scan.go +539 -0
- data/accelerator/internal/wal/checksum.go +13 -0
- data/accelerator/internal/wal/compression.go +41 -0
- data/accelerator/internal/wal/group_commit.go +24 -0
- data/accelerator/internal/wal/record_encoder.go +40 -0
- data/adapters/activerecord/README.md +8 -3
- data/adapters/activerecord/lib/active_record/connection_adapters/rubydb_adapter.rb +50 -42
- data/adapters/activerecord/rubydb-activerecord.gemspec +1 -1
- data/docs/README.md +3 -1
- data/docs/architecture/go-accelerator.md +179 -0
- data/docs/cli.md +24 -0
- data/docs/contributing/benchmarking.md +16 -0
- data/docs/developer/local-development.md +32 -0
- data/docs/release.md +2 -2
- data/lessons/02-local-development.md +2 -2
- data/lessons/04-rails-complex-apps.md +2 -2
- data/lessons/05-rubydb-production-server.md +2 -2
- data/lessons/07-hybrid-microservices.md +175 -90
- data/lessons/10-release-readiness.md +184 -117
- data/lessons/11-community-adapter.md +323 -0
- data/lessons/12-rails-ecommerce-pressure.md +263 -0
- data/lib/rubydb/accelerator/client.rb +451 -0
- data/lib/rubydb/accelerator/error.rb +22 -0
- data/lib/rubydb/accelerator/manager.rb +606 -0
- data/lib/rubydb/accelerator.rb +13 -0
- data/lib/rubydb/cli/application.rb +6 -1
- data/lib/rubydb/cli/commands/accelerator.rb +72 -0
- data/lib/rubydb/cli/commands/doctor.rb +3 -0
- data/lib/rubydb/client/client.rb +7 -0
- data/lib/rubydb/client/connection.rb +15 -0
- data/lib/rubydb/client/result.rb +5 -1
- data/lib/rubydb/configuration/defaults.rb +12 -0
- data/lib/rubydb/configuration/validation.rb +8 -1
- data/lib/rubydb/execution/accelerator_dispatch.rb +30 -0
- data/lib/rubydb/execution/cost_model.rb +72 -0
- data/lib/rubydb/execution/executor.rb +373 -11
- data/lib/rubydb/execution/operator_selection.rb +57 -0
- data/lib/rubydb/execution/physical_plan.rb +47 -0
- data/lib/rubydb/execution/planner.rb +12 -46
- data/lib/rubydb/execution/sort_executor.rb +22 -8
- data/lib/rubydb/indexes/btree.rb +31 -2
- data/lib/rubydb/rubydb.rb +7 -1
- data/lib/rubydb/server/session.rb +45 -0
- data/lib/rubydb/storage/engine.rb +74 -12
- data/lib/rubydb/storage/snapshot_reader.rb +167 -0
- data/lib/rubydb/version.rb +1 -1
- data/lib/rubydb/wal/archive.rb +17 -0
- data/lib/rubydb/wal/wal.rb +1 -0
- data/rubydb.gemspec +12 -2
- data/scripts/build_accelerator +49 -0
- data/scripts/release +34 -4
- data/scripts/replication_failover_drill +2 -2
- metadata +49 -1
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
#!/usr/bin/env ruby
|
|
2
|
+
# frozen_string_literal: true
|
|
3
|
+
|
|
4
|
+
require "fileutils"
|
|
5
|
+
require "digest"
|
|
6
|
+
require "rbconfig"
|
|
7
|
+
|
|
8
|
+
root = File.expand_path("..", __dir__)
|
|
9
|
+
accelerator = File.join(root, "accelerator")
|
|
10
|
+
output_dir = File.join(accelerator, "bin")
|
|
11
|
+
FileUtils.mkdir_p(output_dir)
|
|
12
|
+
|
|
13
|
+
go = ENV["GO"]
|
|
14
|
+
if go.nil? || go.empty?
|
|
15
|
+
candidates = [
|
|
16
|
+
File.join(ENV.fetch("ProgramFiles", "C:/Program Files"), "Go", "bin", "go.exe"),
|
|
17
|
+
File.join(ENV.fetch("ProgramW6432", "C:/Program Files"), "Go", "bin", "go.exe"),
|
|
18
|
+
"go"
|
|
19
|
+
]
|
|
20
|
+
go = candidates.find { |candidate| candidate == "go" || File.file?(candidate) }
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
abort "Go compiler not found. Set GO to the go executable or install Go." unless go
|
|
24
|
+
|
|
25
|
+
targets = ENV.fetch("RUBYDB_ACCELERATOR_TARGETS", "windows-amd64,windows-arm64,linux-amd64,linux-arm64,darwin-amd64,darwin-arm64").split(",").map(&:strip).reject(&:empty?)
|
|
26
|
+
targets = ["#{ENV.fetch("GOOS", RbConfig::CONFIG["host_os"].to_s.match?(/mswin|mingw|cygwin/i) ? "windows" : "linux")}-#{ENV.fetch("GOARCH", "amd64")}"] if ENV["RUBYDB_ACCELERATOR_TARGETS"] == "current"
|
|
27
|
+
|
|
28
|
+
targets.each do |target|
|
|
29
|
+
os, arch = target.split("-", 2)
|
|
30
|
+
abort "Invalid accelerator target #{target.inspect}; use os-arch" unless os && arch
|
|
31
|
+
|
|
32
|
+
extension = (os == "windows") ? ".exe" : ""
|
|
33
|
+
output = File.join(output_dir, "rubydb-accelerator-#{os}-#{arch}#{extension}")
|
|
34
|
+
env = {"GOOS" => os, "GOARCH" => arch, "CGO_ENABLED" => "0"}
|
|
35
|
+
command = [go, "build", "-trimpath", "-ldflags=-s -w", "-o", output, "./cmd/rubydb-accelerator"]
|
|
36
|
+
puts "Building #{os}/#{arch} -> #{output}"
|
|
37
|
+
Dir.chdir(accelerator) do
|
|
38
|
+
abort "Go build failed for #{target}" unless system(env, *command)
|
|
39
|
+
end
|
|
40
|
+
FileUtils.chmod(0o755, output) unless os == "windows"
|
|
41
|
+
end
|
|
42
|
+
|
|
43
|
+
manifest = Dir[File.join(output_dir, "rubydb-accelerator-*")].sort.filter_map do |path|
|
|
44
|
+
next unless File.file?(path)
|
|
45
|
+
|
|
46
|
+
"#{Digest::SHA256.file(path).hexdigest} #{File.basename(path)}"
|
|
47
|
+
end
|
|
48
|
+
File.write(File.join(output_dir, "SHA256SUMS"), "#{manifest.join("\n")}\n")
|
|
49
|
+
puts "RubyDB accelerator binaries are ready in #{output_dir}"
|
data/scripts/release
CHANGED
|
@@ -2,6 +2,7 @@
|
|
|
2
2
|
# frozen_string_literal: true
|
|
3
3
|
|
|
4
4
|
require "digest"
|
|
5
|
+
require "fileutils"
|
|
5
6
|
require "rbconfig"
|
|
6
7
|
require "rubygems"
|
|
7
8
|
|
|
@@ -9,13 +10,14 @@ root = File.expand_path("..", __dir__)
|
|
|
9
10
|
Dir.chdir(root)
|
|
10
11
|
|
|
11
12
|
abort "release metadata preflight failed" unless system(RbConfig.ruby, File.join(root, "scripts", "release_check"))
|
|
13
|
+
abort "Go accelerator build failed" unless system(RbConfig.ruby, File.join(root, "scripts", "build_accelerator"))
|
|
12
14
|
|
|
13
15
|
release_descriptors = [
|
|
14
16
|
"rubydb.gemspec",
|
|
15
17
|
"adapters/activerecord/rubydb-activerecord.gemspec",
|
|
16
18
|
"packaging/homebrew/rubydb.rb"
|
|
17
19
|
]
|
|
18
|
-
untracked_runtime_files = `git ls-files --others --exclude-standard -- lib exe rubydb.gemspec`.lines.map(&:chomp)
|
|
20
|
+
untracked_runtime_files = `git ls-files --others --exclude-standard -- lib exe accelerator rubydb.gemspec`.lines.map(&:chomp)
|
|
19
21
|
unless untracked_runtime_files.empty?
|
|
20
22
|
abort "Runtime files are untracked and would be omitted from the gem: #{untracked_runtime_files.join(", ")}. Commit them before publishing."
|
|
21
23
|
end
|
|
@@ -42,14 +44,42 @@ expected = File.read(checksum_path).split.first
|
|
|
42
44
|
actual = Digest::SHA512.file(gem_path).hexdigest
|
|
43
45
|
abort "Checksum verification failed" unless expected == actual
|
|
44
46
|
|
|
47
|
+
# Build the ActiveRecord adapter alongside the core release. Its version is
|
|
48
|
+
# intentionally independent so Rails applications can pin the adapter while
|
|
49
|
+
# remaining on the RubyDB 0.1.x compatibility line.
|
|
50
|
+
adapter_dir = File.join(root, "adapters", "activerecord")
|
|
51
|
+
adapter_spec = Dir.chdir(adapter_dir) { Gem::Specification.load("rubydb-activerecord.gemspec") }
|
|
52
|
+
abort "Unable to load ActiveRecord adapter gemspec" unless adapter_spec
|
|
53
|
+
adapter_pkg_dir = File.join(adapter_dir, "pkg")
|
|
54
|
+
FileUtils.mkdir_p(adapter_pkg_dir)
|
|
55
|
+
adapter_gem_path = File.join(adapter_pkg_dir, "rubydb-activerecord-#{adapter_spec.version}.gem")
|
|
56
|
+
abort "ActiveRecord adapter gem build failed" unless system(
|
|
57
|
+
"gem", "build", "-V", "rubydb-activerecord.gemspec", "--output", adapter_gem_path,
|
|
58
|
+
chdir: adapter_dir
|
|
59
|
+
)
|
|
60
|
+
adapter_checksum_dir = File.join(root, "checksums")
|
|
61
|
+
FileUtils.mkdir_p(adapter_checksum_dir)
|
|
62
|
+
adapter_checksum_path = File.join(adapter_checksum_dir, "#{File.basename(adapter_gem_path)}.sha512")
|
|
63
|
+
adapter_expected = Digest::SHA512.file(adapter_gem_path).hexdigest
|
|
64
|
+
File.write(adapter_checksum_path, "#{adapter_expected} #{File.basename(adapter_gem_path)}\n")
|
|
65
|
+
abort "ActiveRecord adapter checksum verification failed" unless
|
|
66
|
+
Digest::SHA512.file(adapter_gem_path).hexdigest == File.read(adapter_checksum_path).split.first
|
|
67
|
+
puts "Adapter #{adapter_spec.name} #{adapter_spec.version} built to #{adapter_gem_path}."
|
|
68
|
+
puts "Adapter checksum written to #{adapter_checksum_path}"
|
|
69
|
+
|
|
45
70
|
if ENV["RUBYDB_PUBLISH"] == "1"
|
|
71
|
+
puts "RubyGems 2FA/OTP settings: https://rubygems.org/profile/edit"
|
|
72
|
+
puts "If prompted for an OTP, enter the current code from your authenticator."
|
|
46
73
|
api_key = ENV.fetch("GEM_HOST_API_KEY", "")
|
|
47
74
|
credentials_path = Gem.configuration.credentials_path
|
|
48
75
|
credentials_available = File.file?(credentials_path) && !File.zero?(credentials_path)
|
|
49
76
|
abort "Set GEM_HOST_API_KEY or configure RubyGems credentials at #{credentials_path}" if api_key.empty? && !credentials_available
|
|
50
|
-
|
|
51
|
-
|
|
77
|
+
[gem_path, adapter_gem_path].each do |artifact|
|
|
78
|
+
abort "gem push failed for #{artifact}" unless system("gem", "push", artifact)
|
|
79
|
+
puts "Published #{artifact}"
|
|
80
|
+
end
|
|
52
81
|
else
|
|
53
82
|
puts "Release artifact verified: #{gem_path}"
|
|
54
|
-
puts "
|
|
83
|
+
puts "Release artifact verified: #{adapter_gem_path}"
|
|
84
|
+
puts "To publish both: RUBYDB_PUBLISH=1 GEM_HOST_API_KEY=<RubyGems API key> ruby scripts/release"
|
|
55
85
|
end
|
|
@@ -125,7 +125,7 @@ def spawn_node(role, directory, port, fence_path)
|
|
|
125
125
|
{stdin: stdin, stdout: stdout, stderr: stderr, wait: wait_thread, stderr_thread: stderr_thread}
|
|
126
126
|
end
|
|
127
127
|
|
|
128
|
-
def read_event(node, timeout:
|
|
128
|
+
def read_event(node, timeout: 60)
|
|
129
129
|
Timeout.timeout(timeout) do
|
|
130
130
|
loop do
|
|
131
131
|
ready = IO.select([node[:stdout]], nil, nil, 0.1)
|
|
@@ -145,7 +145,7 @@ def command(node, name, payload = {})
|
|
|
145
145
|
read_event(node)
|
|
146
146
|
end
|
|
147
147
|
|
|
148
|
-
def wait_until(timeout:
|
|
148
|
+
def wait_until(timeout: 60)
|
|
149
149
|
Timeout.timeout(timeout) do
|
|
150
150
|
loop do
|
|
151
151
|
return true if yield
|
metadata
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: rubydb
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 0.1.
|
|
4
|
+
version: 0.1.6
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Aldane Hutchinson
|
|
@@ -154,6 +154,40 @@ files:
|
|
|
154
154
|
- Rakefile
|
|
155
155
|
- SECURITY.md
|
|
156
156
|
- SUPPORT.md
|
|
157
|
+
- accelerator/bin/SHA256SUMS
|
|
158
|
+
- accelerator/bin/rubydb-accelerator-darwin-amd64
|
|
159
|
+
- accelerator/bin/rubydb-accelerator-darwin-arm64
|
|
160
|
+
- accelerator/bin/rubydb-accelerator-linux-amd64
|
|
161
|
+
- accelerator/bin/rubydb-accelerator-linux-arm64
|
|
162
|
+
- accelerator/bin/rubydb-accelerator-windows-amd64.exe
|
|
163
|
+
- accelerator/bin/rubydb-accelerator-windows-arm64.exe
|
|
164
|
+
- accelerator/cmd/rubydb-accelerator/main.go
|
|
165
|
+
- accelerator/go.mod
|
|
166
|
+
- accelerator/internal/execution/aggregate.go
|
|
167
|
+
- accelerator/internal/execution/distinct.go
|
|
168
|
+
- accelerator/internal/execution/filter.go
|
|
169
|
+
- accelerator/internal/execution/join.go
|
|
170
|
+
- accelerator/internal/execution/operators.go
|
|
171
|
+
- accelerator/internal/execution/scan.go
|
|
172
|
+
- accelerator/internal/execution/sort.go
|
|
173
|
+
- accelerator/internal/execution/types.go
|
|
174
|
+
- accelerator/internal/execution/value.go
|
|
175
|
+
- accelerator/internal/memory/arena.go
|
|
176
|
+
- accelerator/internal/memory/reuse.go
|
|
177
|
+
- accelerator/internal/metrics/registry.go
|
|
178
|
+
- accelerator/internal/parallel/bounded_queue.go
|
|
179
|
+
- accelerator/internal/parallel/scheduler.go
|
|
180
|
+
- accelerator/internal/parallel/worker_pool.go
|
|
181
|
+
- accelerator/internal/protocol/cancellation.go
|
|
182
|
+
- accelerator/internal/protocol/columnar.go
|
|
183
|
+
- accelerator/internal/protocol/frame.go
|
|
184
|
+
- accelerator/internal/runtime/worker.go
|
|
185
|
+
- accelerator/internal/storage/page_reader.go
|
|
186
|
+
- accelerator/internal/storage/snapshot_scan.go
|
|
187
|
+
- accelerator/internal/wal/checksum.go
|
|
188
|
+
- accelerator/internal/wal/compression.go
|
|
189
|
+
- accelerator/internal/wal/group_commit.go
|
|
190
|
+
- accelerator/internal/wal/record_encoder.go
|
|
157
191
|
- adapters/activerecord/Gemfile
|
|
158
192
|
- adapters/activerecord/README.md
|
|
159
193
|
- adapters/activerecord/lib/active_record/connection_adapters/rubydb_adapter.rb
|
|
@@ -171,6 +205,7 @@ files:
|
|
|
171
205
|
- docs/architecture/concurrency.md
|
|
172
206
|
- docs/architecture/current-state.md
|
|
173
207
|
- docs/architecture/execution-engine.md
|
|
208
|
+
- docs/architecture/go-accelerator.md
|
|
174
209
|
- docs/architecture/indexes.md
|
|
175
210
|
- docs/architecture/mvcc.md
|
|
176
211
|
- docs/architecture/overview.md
|
|
@@ -252,7 +287,13 @@ files:
|
|
|
252
287
|
- lessons/08-migrations-backups-recovery.md
|
|
253
288
|
- lessons/09-observability-security-scale.md
|
|
254
289
|
- lessons/10-release-readiness.md
|
|
290
|
+
- lessons/11-community-adapter.md
|
|
291
|
+
- lessons/12-rails-ecommerce-pressure.md
|
|
255
292
|
- lib/rubydb.rb
|
|
293
|
+
- lib/rubydb/accelerator.rb
|
|
294
|
+
- lib/rubydb/accelerator/client.rb
|
|
295
|
+
- lib/rubydb/accelerator/error.rb
|
|
296
|
+
- lib/rubydb/accelerator/manager.rb
|
|
256
297
|
- lib/rubydb/backup/archive.rb
|
|
257
298
|
- lib/rubydb/backup/backup.rb
|
|
258
299
|
- lib/rubydb/backup/incremental.rb
|
|
@@ -279,6 +320,7 @@ files:
|
|
|
279
320
|
- lib/rubydb/catalog/trigger.rb
|
|
280
321
|
- lib/rubydb/catalog/view.rb
|
|
281
322
|
- lib/rubydb/cli/application.rb
|
|
323
|
+
- lib/rubydb/cli/commands/accelerator.rb
|
|
282
324
|
- lib/rubydb/cli/commands/backup.rb
|
|
283
325
|
- lib/rubydb/cli/commands/branch.rb
|
|
284
326
|
- lib/rubydb/cli/commands/checkout.rb
|
|
@@ -345,7 +387,9 @@ files:
|
|
|
345
387
|
- lib/rubydb/errors/server_error.rb
|
|
346
388
|
- lib/rubydb/errors/storage_error.rb
|
|
347
389
|
- lib/rubydb/errors/transaction_error.rb
|
|
390
|
+
- lib/rubydb/execution/accelerator_dispatch.rb
|
|
348
391
|
- lib/rubydb/execution/aggregate_executor.rb
|
|
392
|
+
- lib/rubydb/execution/cost_model.rb
|
|
349
393
|
- lib/rubydb/execution/delete_executor.rb
|
|
350
394
|
- lib/rubydb/execution/distinct_executor.rb
|
|
351
395
|
- lib/rubydb/execution/executor.rb
|
|
@@ -354,7 +398,9 @@ files:
|
|
|
354
398
|
- lib/rubydb/execution/insert_executor.rb
|
|
355
399
|
- lib/rubydb/execution/join_executor.rb
|
|
356
400
|
- lib/rubydb/execution/limit_executor.rb
|
|
401
|
+
- lib/rubydb/execution/operator_selection.rb
|
|
357
402
|
- lib/rubydb/execution/optimizer.rb
|
|
403
|
+
- lib/rubydb/execution/physical_plan.rb
|
|
358
404
|
- lib/rubydb/execution/plan.rb
|
|
359
405
|
- lib/rubydb/execution/planner.rb
|
|
360
406
|
- lib/rubydb/execution/predicate.rb
|
|
@@ -502,6 +548,7 @@ files:
|
|
|
502
548
|
- lib/rubydb/storage/record.rb
|
|
503
549
|
- lib/rubydb/storage/row.rb
|
|
504
550
|
- lib/rubydb/storage/serializer.rb
|
|
551
|
+
- lib/rubydb/storage/snapshot_reader.rb
|
|
505
552
|
- lib/rubydb/storage/storage_layout.rb
|
|
506
553
|
- lib/rubydb/storage/storage_manager.rb
|
|
507
554
|
- lib/rubydb/storage/tuple.rb
|
|
@@ -547,6 +594,7 @@ files:
|
|
|
547
594
|
- packaging/systemd/rubydb.service
|
|
548
595
|
- rubydb.gemspec
|
|
549
596
|
- scripts/benchmark
|
|
597
|
+
- scripts/build_accelerator
|
|
550
598
|
- scripts/durability_drill
|
|
551
599
|
- scripts/format
|
|
552
600
|
- scripts/fuzz
|