Skip to content

Fix DBR::Misc::DBI::Compat dying on read-only row buffers#18

Merged
riccardo-perotti merged 1 commit into
masterfrom
rp.ROP-9213.fix-shim-error
May 18, 2026
Merged

Fix DBR::Misc::DBI::Compat dying on read-only row buffers#18
riccardo-perotti merged 1 commit into
masterfrom
rp.ROP-9213.fix-shim-error

Conversation

@riccardo-perotti

@riccardo-perotti riccardo-perotti commented May 18, 2026

Copy link
Copy Markdown

Summary

  • lib/DBR/Misc/DBI/Compat.pm: fetchrow_arrayref and the array-slice path of fetchall_arrayref now return a freshly allocated arrayref instead of reassigning into @$row. Hash-slice paths are unchanged — hash slot assignment replaces the SV and is safe regardless of source AV flags.
  • t/rt_rop9213.t (new): standalone regression test that mocks DBI::st to hand back row arrayrefs whose AV is flagged SvREADONLY, reproducing the production error on master and passing with the fix.

Background

After #17 merged, services using the new shim started dying with:

Modification of a read-only value attempted at /service/main/perl-DBR/lib/DBR/Misc/DBI/Compat.pm line 19

Line 19 was @$row = map { defined $_ ? "$_" : $_ } @$row;. DBD::mysql's fetchrow_arrayref returns a reused internal row buffer whose AV itself is flagged SvREADONLY (not the individual scalars — verified empirically: Internals::SvREADONLY(@arr, 1) triggers the same croak on @$arr = ..., while flagging the elements does not). Building a fresh arrayref sidesteps the issue entirely.

The same pattern existed at line 48 in fetchall_arrayref's array-slice branch — fixed the same way.

Test plan

  • prove -l t/rt_rop9213.t passes with fix, fails on master with the exact production error
  • Run full perl-DBR suite in the perl-base-image-v2 container to confirm no regressions — 29 files / 537 tests / PASS
  • Redeploy a service that was hitting the error and confirm it no longer dies

Jira ticket

https://gudtech.atlassian.net/browse/ROP-9213

🤖 Generated with Claude Code

DBD::mysql returns a reused internal row arrayref whose AV is flagged
SvREADONLY, so `@$row = map { ... } @$row` in fetchrow_arrayref and
fetchall_arrayref died with "Modification of a read-only value
attempted at .../Compat.pm line 19".

Build a fresh arrayref in both paths instead of reassigning in place.
Hash-slice paths are unchanged: hash slot assignment replaces the SV
and is safe regardless of the source AV's flags.

Adds rt_rop9213.t — a standalone regression test that mocks DBI::st
to hand back SvREADONLY row AVs; it reproduces the production error
on master and passes with the fix.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@riccardo-perotti riccardo-perotti merged commit 78dd35d into master May 18, 2026
1 check passed
@riccardo-perotti riccardo-perotti deleted the rp.ROP-9213.fix-shim-error branch May 18, 2026 18:08
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.

1 participant