Skip to content

bindings/ruby: fix tuple float comparison on Ruby 3.3 and later - #14507

Merged
ploxiln merged 1 commit into
apple:mainfrom
0z5a:fix/ruby-tuple-compare-floats
Nov 11, 2026
Merged

ploxiln merged 1 commit into
apple:mainfrom
0z5a:fix/ruby-tuple-compare-floats

Conversation

@0z5a

@0z5a 0z5a commented Nov 11, 2026

Copy link
Copy Markdown
Contributor

Problem

Fixes #14505.

On Ruby 3.3 and later, FDB::Tuple.compare raises ArgumentError: unknown pack directive '>' in '>G' as soon as it compares two doubles, and FDB::Tuple::SingleFloat#<=> raises the same for '>g'. FDB::Tuple._compare_floats packs its arguments with ">G" / ">g". > is not valid in front of g/G; older Rubies ignored it with a warning, and Ruby 3.3 turned unknown pack directives into an error.

Found by reading bindings/ruby/lib/fdbtuple.rb with an AI assistant (Claude Code, claude-fable-5-2) and reproduced with the Ruby binding tester on Ruby 3.4.7: the api test stops in TUPLE_SORT.

Solution

Use "G" / "g". Both are big-endian already, so the bytes are the same as before on Rubies that ignored the >.

The scripted binding test gets a TUPLE_SORT of tuples with doubles, SingleFloats and nested 0.0 / -0.0. It had no TUPLE_SORT so far, which is why scripted passes for Ruby on main even on Ruby 3.4.

Testing

Run against a single-process cluster from the 8.0.0 release binaries, binding sources from this branch, x86_64 Linux:

  • ./bindingtester.py ruby --test-name scripted on Ruby 3.4.7: fails on main once the new TUPLE_SORT block is added (ArgumentError), passes with the fix.
  • ./bindingtester.py ruby --test-name api --num-ops 1000 --seed 12345 on Ruby 3.4.7: fails on main, passes with the fix.
  • ./bindingtester.py python --test-name scripted and --test-name api --num-ops 1000 --seed 12345: pass with the new block.
  • A small script calling FDB::Tuple.compare and SingleFloat#<=> (in the issue) gives the expected results on Ruby 3.2.9, 3.3.10 and 3.4.7 with the fix; on main it raises on 3.3.10 and 3.4.7 and warns on 3.2.9.
  • black 22.8.0 and flake8 5.0.4 on bindings/bindingtester/tests/scripted.py: clean.

Not run: the CMake build, ctest, Joshua, and the Java, Go, Flow and Swift binding testers. The new scripted block also runs for those testers; if that is a concern, the block can be dropped, since the existing api test already covers the failure.

AI disclosure: Claude Code, model claude-fable-5-2; AI was used to find the bug, write the reproducer, the fix and the test, run the tests listed above, and write the first draft of this description; AI-generated code: bindings/ruby/lib/fdbtuple.rb lines 311-312 and the TUPLE_SORT block in bindings/bindingtester/tests/scripted.py.

🤖 Generated with Claude Code

FDB::Tuple._compare_floats packed its arguments with the format
strings ">g" and ">G". ">" is only a modifier for the integer
directives; in front of "g"/"G" it is an unknown directive. Older
Rubies ignored it (with a warning under -w), but since Ruby 3.3
Array#pack raises ArgumentError for unknown directives. As a result
FDB::Tuple.compare raised for any pair of tuples that reached a float
or double comparison, and so did FDB::Tuple::SingleFloat#<=>.

"g" and "G" are already big-endian, so drop the ">". The packed bytes
are the same as before on Rubies that ignored it.

Add a TUPLE_SORT of tuples containing floats and doubles to the
scripted binding test, which until now did not sort tuples at all.

Co-Authored-By: Claude Fable 5.2 <[email protected]>
Signed-off-by: Dezhen Lu <[email protected]>
@ploxiln ploxiln closed this Nov 11, 2026
@ploxiln ploxiln reopened this Nov 11, 2026
@foundationdb-ci

Copy link
Copy Markdown
Contributor

Result of foundationdb-pr-macos-m1 on macOS

  • Commit ID: f773c04
  • Duration 0:25:37
  • Result: ✅ SUCCEEDED
  • Error: N/A
  • Build Log terminal output (available for 30 days)
  • Build Workspace zip file of the working directory (available for 30 days)

@foundationdb-ci

Copy link
Copy Markdown
Contributor

Result of foundationdb-pr-clang-ide on Linux RHEL 9

  • Commit ID: f773c04
  • Duration 0:30:26
  • Result: ✅ SUCCEEDED
  • Error: N/A
  • Build Log terminal output (available for 30 days)
  • Build Workspace zip file of the working directory (available for 30 days)

@foundationdb-ci

Copy link
Copy Markdown
Contributor

Result of foundationdb-pr-clang-arm on Linux RHEL 9

  • Commit ID: f773c04
  • Duration 0:47:47
  • Result: ✅ SUCCEEDED
  • Error: N/A
  • Build Log terminal output (available for 30 days)
  • Build Workspace zip file of the working directory (available for 30 days)

@foundationdb-ci

Copy link
Copy Markdown
Contributor

Result of foundationdb-pr-clang on Linux RHEL 9

  • Commit ID: f773c04
  • Duration 0:54:27
  • Result: ✅ SUCCEEDED
  • Error: N/A
  • Build Log terminal output (available for 30 days)
  • Build Workspace zip file of the working directory (available for 30 days)

@foundationdb-ci

Copy link
Copy Markdown
Contributor

Result of foundationdb-pr on Linux RHEL 9

  • Commit ID: f773c04
  • Duration 0:59:37
  • Result: ✅ SUCCEEDED
  • Error: N/A
  • Build Log terminal output (available for 30 days)
  • Build Workspace zip file of the working directory (available for 30 days)

@foundationdb-ci

Copy link
Copy Markdown
Contributor

Result of foundationdb-pr-macos on macOS

  • Commit ID: f773c04
  • Duration 1:02:55
  • Result: ✅ SUCCEEDED
  • Error: N/A
  • Build Log terminal output (available for 30 days)
  • Build Workspace zip file of the working directory (available for 30 days)

@foundationdb-ci

Copy link
Copy Markdown
Contributor

Result of foundationdb-pr-cluster-tests on Linux RHEL 9

  • Commit ID: f773c04
  • Duration 1:49:42
  • Result: ✅ SUCCEEDED
  • Error: N/A
  • Build Log terminal output (available for 30 days)
  • Build Workspace zip file of the working directory (available for 30 days)
  • Cluster Test Logs zip file of the test logs (available for 30 days)

@ploxiln
ploxiln merged commit 5ca2747 into apple:main Nov 11, 2026
12 of 15 checks passed
ploxiln pushed a commit that referenced this pull request Nov 13, 2026
FDB::Tuple._compare_floats packed its arguments with the format
strings ">g" and ">G". ">" is only a modifier for the integer
directives; in front of "g"/"G" it is an unknown directive. Older
Rubies ignored it (with a warning under -w), but since Ruby 3.3
Array#pack raises ArgumentError for unknown directives. As a result
FDB::Tuple.compare raised for any pair of tuples that reached a float
or double comparison, and so did FDB::Tuple::SingleFloat#<=>.

"g" and "G" are already big-endian, so drop the ">". The packed bytes
are the same as before on Rubies that ignored it.

Add a TUPLE_SORT of tuples containing floats and doubles to the
scripted binding test, which until now did not sort tuples at all.

Signed-off-by: Dezhen Lu <[email protected]>
Co-authored-by: Claude Fable 5.2 <[email protected]>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Ruby binding: FDB::Tuple.compare and SingleFloat#<=> raise ArgumentError on Ruby 3.3+

3 participants