github carthage-software/mago 1.58.0
Mago 1.58.0

latest releases: 1.58.2, 1.58.1
4 hours ago

Mago 1.58.0 adds opt-in dead-catch checks, a prefer-self rule, and extension throw-type providers, cuts analysis overhead, and fixes type narrowing and PHP formatting.

Note

Support Mago

Does your company use Mago? Please consider sponsoring its development so we can keep fixing bugs and shipping releases.

Sponsor Mago ❤️

✨ Features

Analyzer

  • Dead catches: adds opt-in checks for catches with no known matching throws. (#2503, #2525, 18315f6)
  • Enum throws: avoids ValueError for known-valid BackedEnum::from() arguments. (#2544, #2565, 5bcf444)

Linter

  • Prefer self: adds an opt-in rule to replace references to the enclosing class with self. (#2528, aba4df1)
  • Extension rules: accepts enabled, level, and exclude settings under [linter.rules]. (#2530, f2b479c)

🐛 Bug Fixes

Analyzer

  • Named arguments: honors class-level @no-named-arguments tags. (#2514, a33b014)
  • Mixed array keys: reports mixed-array-index for keys whose type is mixed. (#2522, 4b19550)
  • Nullsafe guards: narrows receivers through guards and falsy ?? fallbacks. (#2515, #2563, 83a0bfd, 891c463)
  • Do-while loops: preserves initial types when by-reference calls update loop variables. (#2523, b6a24d9)
  • Diagnostics: clarifies class resolution, member access, and type-check messages. (#2541, 43f0a1a)
  • Redundant nullsafe calls: reports unnecessary ?-> on method calls. (#2547, ba38156)
  • Iterable guards: narrows iterable values to Traversable after type checks. (#2550, dd17cfb)
  • Match assignments: preserves subject types and evaluates assignment subjects once. (8a19e98)
  • Shape unions: removes shapes with required keys after a failed key-existence check. (#2557, 5ffc5d2)
  • Nested array guards: keeps required keys when narrowing nested shapes. (#2577, 221fd63)
  • Type switches: narrows variables in get_class() and gettype() switch cases. (#2558, eba91e1)
  • Callable guards: fixes narrowing of callable objects and strings in type checks. (#2552, #2560, 0e1d212, abea0ad)
  • Conditional assignments: keeps assignments scoped to each analysis pass. (#2561, 64a2323)
  • Short-circuit assignments: tracks reassignment and narrowing across logical chains. (#2571, #2562, c8358f1, 001666b)
  • Array membership: fixes strict checks and unsafe narrowing after negated in_array(). (#2573, #2574, d5ca2a6, c16337a)
  • Known array keys: resolves literal keys in isset() and empty() guards. (#2575, #2585, 9671d89, f8f46a6)
  • Numeric-string keys: normalizes integer-like string keys in array guards. (#2578, d7dae70)
  • Loose null checks: preserves falsy strings when comparing nullable strings with null. (#2579, ff5df16)
  • Negated isset: does not treat nullable keys as missing after a failed check. (#2554, #2576, fb8de05)
  • Switch transfers: preserves nested breaks, continues, and finally control flow. (#2569, #2570, b6e8259)
  • Empty foreach loops: skips unreachable loop bodies for known empty arrays. (#2572, 6bdf6c6)
  • Switch coverage: detects impossible cases and unreachable defaults. (#2553, 204f678)

Codex

  • Large unions: expands types beyond 64 members without leaving unresolved references. (#2518, 51f2762)
  • Traversable templates: keeps caller templates instead of widening them to their bounds. (#2520, 735d59d)
  • Class strings: handles leading backslashes when comparing literal class names. (#2533, 1a28236)
  • Iterable arguments: rejects excess generic arguments on iterable types. (#2543, 1c3eba0)
  • Mixed array keys: treats explicit mixed key types as array-key. (#2545, c4d7f9a)

PHPDoc

  • Array shorthand: accepts spaces between a type and its [] suffix. (#2546, 00c150d)

Formatter

  • Preserved breaks: keeps argument-list and binary-expression layouts stable across passes. (#2524, e665c18)
  • Instanceof calls: preserves required parentheses around calls used as class expressions. (#2584, 7562fff)
  • Clone chains: keeps parentheses so member chains clone the intended object. (#2588, 4681219)
  • Dynamic classes: preserves required parentheses in new (self::MAP[$key])() and related forms. (#2587, 0c7c2b5)

Linter

  • Deprecated casts: shows the cast as written in the source. (7823faf)

Parser

  • Incomplete code: recovers unfinished control heads without misleading lint reports. (81367b8)

Prelude

  • Class interfaces: drops false from class_implements() results for object inputs. (#2513, f7af709)
  • Class-name maps: gives SPL class inspection helpers associative return types. (#2531, 5ea84ce)
  • SoapVar: makes the typeName constructor argument optional. (#2519, 245ee75)
  • Class checks: accepts mixed inputs for is_a() and is_subclass_of(). (#2549, bfe814f)

Composer

  • Download progress: limits progress updates to once per second. (#2521, f721198)

📖 Documentation

Analyzer

  • Dead-catch settings: documents opt-in checks in English, French, and Chinese. (#2525, 18315f6)

Extensions

  • Rule settings: documents configuration for extension linter rules. (#2530, f2b479c)
  • Throw providers: adds PHP SDK examples and reference entries. (#2527, #2542, 53611ac)

🏗️ Internal

Analyzer

  • Condition checks: cuts clause copies, redundant interning, and repeated lookups. (6451560, 28fc0f0)

Codex

  • Codebase setup: parallelizes population and bounds integer-mask expansion. (26aa86d, ccbd052)

CLI

  • Embedded prelude: compresses prelude data and encodes each shared word once. (7be3117)
  • Shutdown: skips allocator teardown after flushing command output. (b85d25e)

Database

  • Loading: cuts serial pipeline work and line-table allocations. (f8531a2, fa3a5c9)
  • Path matching: adds opt-in Git-ignore handling and shared directory matching APIs. (7e72b4a)

Reporting

  • Parallel output: streams rendered issues in order. (8036e42)

Parser

  • Parsing work: skips detached whitespace and needless control-flow walks. (b142e5f)

Word

  • String interning: uses parking_lot mutexes for shared string tables. (cd49bc3)

Names

  • Deprecation metadata: records the deprecation version of ResolvedNames::all(). (#2564, c15c158)

🧩 Extension Protocol

Analyzer

  • MANA 2.1: adds function, method, and expression throw-type providers. (#2527, #2542, 53611ac)

Update the PHP SDK to 1.58.0 when upgrading Mago. Custom analyzer workers must use MANA 2.1; MANA 2.0 workers are not compatible. The linter protocol is unchanged.

🙏 Thank You

Contributors

Thank you to everyone who contributed to this release:

Issue Reporters

Thank you to everyone who reported issues that shaped this release:

Full Changelog: 1.57.0...1.58.0

Don't miss a new mago release

NewReleases is sending notifications on new releases.