Changes for version v1.0.8 - 2026-09-08

  • SECURITY
    • An authorisation bypass was corrected using a cache key controlled by the user (CWE-639). This instance was detected by CPANsec. There were two different defects that together allowed one user's query to be fulfilled by other user's (or another database's) stored results.
      • The first of these issues is _generate_cache_key (ResultSet.pm) which reduced the cache key to primary key fields every time primary key was present in search condition ignoring all other conditions. Because of this, a search like search({ id => $id, owner => $user }) was saved as { id => $id }, so that in the future query with the same id regardless of who the owner is, could return the result from this cache. Actually the condition was applied correctly to the database but the cache key merged different queries in the cache. The cache key is generated now using the full search condition.
      • The CHI cache was created using global => 1 by _build_default_cache (Async.pm). As a result, all the instances of CHI::Driver::Memory in the given process are present in the same store. Because the cache key does not include connection identity, two Schemas that are connected to different databases have the possibility to read/write the entries of the cache of each other. The cache is isolated per connection now: global => 0, but, because each connection owns its own cache object, there is no need to add any connection identity to the key.
      • Because of this, it is impossible to guarantee that the cache key for Row::update's invalidation-by-primary-key would match the (now condition-aware) cache entry that has to be invalidated.
    • Added regression tests to t/148-caching.t reproducing both the predicate-collapse and the cross-connection cache leakage, and confirming the fix.

Documentation

Modules

Non-blocking, multi-worker asynchronous wrapper for DBIx::Class
Base class for DBIx::Class::Async exceptions
Exception for column names that are ambiguous across joined tables
Translate raw DBIx::Class errors into typed exception objects
Exception for absent required columns on insert
Exception for undeclared relationship names used in queries
Exception for operations on un-inserted row objects
Exception for relationship name passed where a column was expected
Non-blocking resultset proxy with Future-based execution
Asynchronous pagination handling for Async ResultSets
Asynchronous operations on a single ResultSource column
Asynchronous Row object representing a single database record.
Non-blocking, worker-pool based Proxy for DBIx::Class::Schema
Normalise -ident clauses in ResultSet select attributes
Storage Layer for DBIx::Class::Async
DBI-based async storage backend for DBIx::Class::Async
Asynchronous cursor for DBIx::Class ResultSets using Futures