psalm icon indicating copy to clipboard operation
psalm copied to clipboard

AssertionError from simple array assignment

Open scribblemaniac opened this issue 3 months ago • 2 comments

Analyzing the following PHP code causes Psalm (6.13.1 and the latest git commit 37282530e0c780519d2cd0187ba8461d1dd9cacc) to crash for me when installed with composer, but not with the official Docker container:

<?php
$conditions = ['A' => 'B'];
$conditions[]['C'] = [];
Psalm output with --debug
JIT acceleration: ON

JIT compilation in progress... Done.

Process plugin adjustments...
Target PHP version: 8.4 (inferred from current PHP version).


Scanning files...

Initializing plugins...
Registering autoloaded files
 /var/www/html/vendor/autoload.php
 /var/www/html/vendor/composer/autoload_real.php
 /var/www/html/vendor/composer/ClassLoader.php
 /var/www/html/vendor/composer/autoload_static.php
 /var/www/html/vendor/amphp/amp/src/functions.php
 /var/www/html/vendor/amphp/amp/src/Future/functions.php
 /var/www/html/vendor/amphp/amp/src/Internal/functions.php
 /var/www/html/vendor/amphp/serialization/src/functions.php
 /var/www/html/vendor/amphp/sync/src/functions.php
 /var/www/html/vendor/amphp/byte-stream/src/functions.php
 /var/www/html/vendor/amphp/byte-stream/src/Internal/functions.php
 /var/www/html/vendor/symfony/polyfill-mbstring/bootstrap.php
 /var/www/html/vendor/symfony/polyfill-mbstring/bootstrap80.php
 /var/www/html/vendor/amphp/process/src/functions.php
 /var/www/html/vendor/symfony/deprecation-contracts/function.php
 /var/www/html/vendor/symfony/polyfill-ctype/bootstrap.php
 /var/www/html/vendor/symfony/polyfill-ctype/bootstrap80.php
 /var/www/html/vendor/daverandom/libdns/src/functions.php
 /var/www/html/vendor/amphp/dns/src/functions.php
 /var/www/html/vendor/symfony/polyfill-intl-grapheme/bootstrap.php
 /var/www/html/vendor/symfony/polyfill-intl-grapheme/bootstrap80.php
 /var/www/html/vendor/symfony/polyfill-intl-normalizer/bootstrap.php
 /var/www/html/vendor/symfony/polyfill-intl-normalizer/bootstrap80.php
 /var/www/html/vendor/amphp/socket/src/functions.php
 /var/www/html/vendor/amphp/socket/src/Internal/functions.php
 /var/www/html/vendor/amphp/socket/src/SocketAddress/functions.php
 /var/www/html/vendor/symfony/string/Resources/functions.php
 /var/www/html/vendor/amphp/parallel/src/Context/functions.php
 /var/www/html/vendor/amphp/parallel/src/Context/Internal/functions.php
 /var/www/html/vendor/amphp/parallel/src/Ipc/functions.php
 /var/www/html/vendor/amphp/parallel/src/Worker/functions.php
 /var/www/html/vendor/symfony/polyfill-php84/bootstrap.php
 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/VersionUtils.php
 /var/www/html/vendor/composer/InstalledVersions.php
 /var/www/html/vendor/composer/installed.php
 /var/www/html/vendor/composer/autoload_files.php
Using reflection to get metadata for RuntimeException
Using reflection to get metadata for Closure
Using reflection to get metadata for InvalidArgumentException
Using composer to locate file for Amp\Future
Using composer to locate file for Amp\Internal\FutureState
Using reflection to get metadata for Throwable
Using composer to locate file for Revolt\EventLoop
Using composer to locate file for Amp\Cancellation
Using composer to locate file for Amp\CancelledException
Using composer to locate file for Revolt\EventLoop\UnsupportedFeatureException
Using reflection to get metadata for ReflectionFunction
Using reflection to get metadata for WeakReference
Using reflection to get metadata for Error
Using composer to locate file for Amp\CompositeLengthException
Using composer to locate file for Amp\CompositeException
Using reflection to get metadata for ValueError
Using reflection to get metadata for Countable
Using composer to locate file for Amp\Sync\Semaphore
Using composer to locate file for Revolt\EventLoop\FiberLocal
Using reflection to get metadata for WeakMap
Using composer to locate file for Amp\Sync\Channel
Using composer to locate file for Amp\Pipeline\Queue
Using composer to locate file for Amp\Sync\Internal\ConcurrentIteratorChannel
Using composer to locate file for Amp\ByteStream\ReadableStream
Using composer to locate file for Amp\ByteStream\WritableStream
Using composer to locate file for Amp\ByteStream\BufferException
Using composer to locate file for Amp\ByteStream\ReadableResourceStream
Using composer to locate file for Amp\ByteStream\WritableResourceStream
Using reflection to get metadata for Traversable
Using reflection to get metadata for JsonException
Using composer to locate file for Symfony\Polyfill\Mbstring\Mbstring
Using composer to locate file for Symfony\Polyfill\Ctype\Ctype
Using composer to locate file for Amp\Dns\DnsResolver
Using composer to locate file for Amp\Dns\Rfc1035StubDnsResolver
Using composer to locate file for Amp\Dns\DnsException
Using composer to locate file for Amp\Dns\InvalidNameException
Using composer to locate file for Symfony\Polyfill\Intl\Grapheme\Grapheme
Using composer to locate file for Symfony\Polyfill\Intl\Normalizer\Normalizer
Using composer to locate file for Amp\Socket\SocketAddress
Using composer to locate file for Amp\Socket\BindContext
Using composer to locate file for Amp\Socket\ResourceServerSocket
Using composer to locate file for Amp\Socket\SocketException
Using composer to locate file for Amp\Socket\ResourceSocket
Using composer to locate file for Amp\Socket\ResourceServerSocketFactory
Using composer to locate file for Amp\Socket\InternetAddress
Using composer to locate file for Amp\Socket\ResourceUdpSocket
Using composer to locate file for Amp\Socket\SocketConnector
Using composer to locate file for Amp\Socket\RetrySocketConnector
Using composer to locate file for Amp\Socket\DnsSocketConnector
Using composer to locate file for Amp\Socket\ConnectContext
Using composer to locate file for Amp\Socket\Socket
Using composer to locate file for Amp\Socket\ConnectException
Using composer to locate file for Amp\Socket\TlsException
Using composer to locate file for Amp\Socket\ClientTlsContext
Using composer to locate file for League\Uri\UriString
Using reflection to get metadata for Exception
Using composer to locate file for Amp\NullCancellation
Using composer to locate file for Amp\Socket\UnixAddress
Using reflection to locate file for Symfony\Component\String\u
Using composer to locate file for Symfony\Component\String\UnicodeString
Using reflection to locate file for Symfony\Component\String\b
Using composer to locate file for Symfony\Component\String\ByteString
Using reflection to locate file for Symfony\Component\String\s
Using composer to locate file for Symfony\Component\String\AbstractString
Using composer to locate file for Amp\Parallel\Context\Context
Using composer to locate file for Amp\Parallel\Context\ContextFactory
Using composer to locate file for Amp\Parallel\Context\DefaultContextFactory
Using composer to locate file for Amp\ByteStream\StreamChannel
Using reflection to get metadata for TypeError
Using reflection to get metadata for ParseError
Using composer to locate file for Amp\Parallel\Context\Internal\ContextChannel
Using composer to locate file for Amp\Parallel\Context\Internal\ExitSuccess
Using composer to locate file for Amp\Parallel\Context\Internal\ExitFailure
Using composer to locate file for Amp\Serialization\SerializationException
Using composer to locate file for Amp\Parallel\Ipc\SocketIpcHub
Using composer to locate file for Amp\Parallel\Worker\WorkerPool
Using composer to locate file for Amp\Parallel\Worker\ContextWorkerPool
Using composer to locate file for Amp\Parallel\Worker\Task
Using composer to locate file for Amp\Parallel\Worker\Execution
Using composer to locate file for Amp\Parallel\Worker\Worker
Using composer to locate file for Amp\Parallel\Worker\WorkerFactory
Using composer to locate file for Amp\Parallel\Worker\ContextWorkerFactory
Using composer to locate file for Symfony\Polyfill\Php84\Php84
Using reflection to get metadata for Phar
Using reflection to get metadata for OutOfBoundsException
Using composer to locate file for Composer\Semver\VersionParser
Using reflection to get metadata for ReflectionClass
Using reflection to get metadata for ReflectionExtension
Using reflection to get metadata for ReflectionParameter
Using reflection to get metadata for ReflectionType
Using reflection to get metadata for ReflectionAttribute
Using reflection to get metadata for Iterator
Using reflection to get metadata for SplFileInfo
Using reflection to get metadata for SplFileObject
Using reflection to get metadata for DirectoryIterator
Using reflection to get metadata for FilesystemIterator
Using reflection to get metadata for RecursiveIterator
Using reflection to get metadata for RecursiveDirectoryIterator
Using reflection to get metadata for PharData
Using reflection to get metadata for PharFileInfo
Using composer to locate file for Amp\ForbidCloning
Using composer to locate file for Amp\ForbidSerialization
Using composer to locate file for Revolt\EventLoop\Driver
Using composer to locate file for Revolt\EventLoop\InvalidCallbackError
Using composer to locate file for Revolt\EventLoop\CallbackType
Using composer to locate file for Revolt\EventLoop\Suspension
Using composer to locate file for Amp\Sync\Lock
Using reflection to get metadata for Fiber
Using composer to locate file for Amp\Closable
Using composer to locate file for Amp\Sync\ChannelException
Using composer to locate file for Amp\Pipeline\Internal\QueueState
Using composer to locate file for Amp\Pipeline\Pipeline
Using composer to locate file for Amp\Pipeline\ConcurrentIterator
Using composer to locate file for Amp\Pipeline\DisposedException
Using composer to locate file for Amp\DeferredFuture
Using composer to locate file for Amp\ByteStream\PendingReadError
Using composer to locate file for Amp\ByteStream\StreamException
Using composer to locate file for Amp\ByteStream\ClosedException
Using composer to locate file for Amp\ByteStream\ReadableStreamIteratorAggregate
Using composer to locate file for Amp\ByteStream\ResourceStream
Using reflection to get metadata for IteratorAggregate
Using reflection to get metadata for SplQueue
Using composer to locate file for Amp\Dns\MissingDnsRecordException
Using composer to locate file for Amp\Dns\DnsRecord
Using composer to locate file for Amp\Dns\DnsConfigLoader
Using composer to locate file for LibDNS\Records\QuestionFactory
Using composer to locate file for Amp\Dns\DnsConfig
Using composer to locate file for Amp\Cache\Cache
Using composer to locate file for Amp\Dns\Internal\Socket
Using composer to locate file for Amp\Dns\BlockingFallbackDnsResolver
Using composer to locate file for Amp\Dns\DnsConfigException
Using composer to locate file for LibDNS\Records\Question
Using composer to locate file for LibDNS\Messages\Message
Using composer to locate file for Normalizer
Using reflection to get metadata for Stringable
Using composer to locate file for Amp\Socket\SocketAddressType
Using composer to locate file for Amp\Socket\ServerTlsContext
Using composer to locate file for Amp\Socket\ServerSocket
Using composer to locate file for Amp\Socket\PendingAcceptError
Using composer to locate file for Amp\Socket\TlsState
Using composer to locate file for Amp\Socket\TlsInfo
Using composer to locate file for Amp\Socket\ServerSocketFactory
Using composer to locate file for Amp\Socket\InternetAddressVersion
Using composer to locate file for Amp\Socket\UdpSocket
Using composer to locate file for Amp\Socket\Certificate
Using composer to locate file for League\Uri\Exceptions\SyntaxError
Using composer to locate file for League\Uri\Exceptions\MissingFeature
Using composer to locate file for League\Uri\Exceptions\ConversionFailed
Using composer to locate file for Symfony\Component\String\AbstractUnicodeString
Using composer to locate file for Symfony\Component\String\CodePointString
Using reflection to get metadata for JsonSerializable
Using composer to locate file for Symfony\Component\String\TruncateMode
Using composer to locate file for Amp\Parallel\Context\ContextException
Using composer to locate file for Amp\Parallel\Ipc\IpcHub
Using composer to locate file for Amp\ByteStream\Internal\ChannelParser
Using composer to locate file for Amp\Sync\Mutex
Using composer to locate file for Amp\Serialization\Serializer
Using composer to locate file for Amp\Parallel\Context\Internal\ExitResult
Using composer to locate file for Amp\Parallel\Context\ContextPanicError
Using composer to locate file for Amp\Cache\LocalCache
Using composer to locate file for Amp\Parallel\Context\StatusError
Using composer to locate file for Amp\Parallel\Worker\LimitedWorkerPool
Using reflection to get metadata for SplObjectStorage
Using composer to locate file for Amp\DeferredCancellation
Using composer to locate file for Amp\Parallel\Worker\WorkerException
Using reflection to get metadata for UnexpectedValueException
Using composer to locate file for Composer\Semver\Constraint\ConstraintInterface
Using reflection to get metadata for ReflectionMethod
Using reflection to get metadata for ReflectionProperty
Using reflection to get metadata for ReflectionClassConstant
Using reflection to get metadata for ReflectionFunctionAbstract
Using reflection to get metadata for UnitEnum
Using composer to locate file for Amp\Pipeline\Internal\IntermediateOperation
Using composer to locate file for LibDNS\Records\ResourceTypes
Using composer to locate file for LibDNS\Records\ResourceQTypes
Using composer to locate file for Amp\Cache\CacheException
Using reflection to get metadata for ArrayObject
Using composer to locate file for LibDNS\Messages\MessageFactory
Using composer to locate file for LibDNS\Records\Record
Using composer to locate file for LibDNS\Records\Types\TypeFactory
Using composer to locate file for LibDNS\Records\RecordCollection
Using composer to locate file for LibDNS\Messages\MessageOpCodes
Using composer to locate file for LibDNS\Messages\MessageResponseCodes
Using composer to locate file for LibDNS\Records\RecordCollectionFactory
Using reflection to get metadata for RangeException
Using composer to locate file for Kelunik\Certificate\Certificate
Using composer to locate file for Amp\Socket\PendingReceiveError
Using composer to locate file for League\Uri\Contracts\UriException
Using composer to locate file for League\Uri\Idna\Result
Using reflection to locate file for Transliterator
Using composer to locate file for Amp\Parser\Parser
Using reflection to get metadata for Generator
Using composer to locate file for Amp\Parallel\Context\Internal\ContextException
Using composer to locate file for Amp\Internal\Cancellable
Using composer to locate file for Composer\Semver\Constraint\Constraint
Using composer to locate file for Composer\Semver\Constraint\Bound
Using reflection to get metadata for PropertyHookType
Using reflection to get metadata for ArrayIterator
Using composer to locate file for LibDNS\Enumeration
Using composer to locate file for LibDNS\Records\Types\DomainName
Using composer to locate file for LibDNS\Records\ResourceClasses
Using composer to locate file for LibDNS\Records\Types\Anything
Using composer to locate file for LibDNS\Records\Types\BitMap
Using composer to locate file for LibDNS\Records\Types\Char
Using composer to locate file for LibDNS\Records\Types\CharacterString
Using composer to locate file for LibDNS\Records\Types\IPv4Address
Using composer to locate file for LibDNS\Records\Types\IPv6Address
Using composer to locate file for LibDNS\Records\Types\Long
Using composer to locate file for LibDNS\Records\Types\Short
Using composer to locate file for League\Uri\Idna\Error
Using composer to locate file for Amp\Parser\InvalidDelimiterError
Using composer to locate file for LibDNS\Records\Types\Type
Using reflection to get metadata for UnderflowException
Using reflection to get metadata for OverflowException
Using reflection to get metadata for BackedEnum
Finished registering autoloaded files
Visiting autoload files took 0.116s
Checking /var/www/html/Example.php
ClassLikeStorage is populating
Have populated ComposerAutoloaderInitbfac7131d4887929ae4726e353d496f3
Have populated Composer\Autoload\ClassLoader
Have populated Composer\Autoload\ComposerStaticInitbfac7131d4887929ae4726e353d496f3
Have populated Psalm\Internal\VersionUtils
Have populated Composer\InstalledVersions
Have populated Exception
Have populated RuntimeException
Have populated Stringable
Have populated Throwable
Have populated Closure
Have populated LogicException
Have populated InvalidArgumentException
Have populated ReflectionFunctionAbstract
Have populated ReflectionFunction
Have populated Reflector
Have populated WeakReference
Have populated Error
Have populated ValueError
Have populated Countable
Have populated WeakMap
Have populated ArrayAccess
Have populated IteratorAggregate
Have populated Traversable
Have populated JsonException
Have populated TypeError
Have populated CompileError
Have populated ParseError
Have populated SplFileInfo
Have populated DirectoryIterator
Have populated FilesystemIterator
Have populated RecursiveDirectoryIterator
Have populated Phar
Have populated SeekableIterator
Have populated Iterator
Have populated RecursiveIterator
Have populated OutOfBoundsException
Have populated Amp\ForbidCloning
Have populated Amp\ForbidSerialization
Have populated Amp\Future
Have populated Amp\Internal\FutureState
Have populated Revolt\EventLoop
Have populated Amp\Cancellation
Have populated Amp\CancelledException
Have populated Revolt\EventLoop\UnsupportedFeatureException
Have populated Amp\CompositeLengthException
Have populated Amp\CompositeException
Have populated Amp\Sync\Semaphore
Have populated Revolt\EventLoop\FiberLocal
Have populated Amp\Closable
Have populated Amp\Sync\Channel
Have populated Amp\Pipeline\Queue
Have populated Amp\Sync\Internal\ConcurrentIteratorChannel
Have populated Amp\ByteStream\ReadableStream
Have populated Amp\ByteStream\WritableStream
Have populated Amp\ByteStream\StreamException
Have populated Amp\ByteStream\BufferException
Have populated Amp\ByteStream\ReadableStreamIteratorAggregate
Have populated Amp\ByteStream\ResourceStream
Have populated Amp\ByteStream\ReadableResourceStream
Have populated Amp\ByteStream\WritableResourceStream
Have populated Symfony\Polyfill\Mbstring\Mbstring
Have populated Symfony\Polyfill\Ctype\Ctype
Have populated Amp\Dns\DnsResolver
Have populated Amp\Dns\Rfc1035StubDnsResolver
Have populated Amp\Dns\DnsException
Have populated Amp\Dns\InvalidNameException
Have populated Symfony\Polyfill\Intl\Grapheme\Grapheme
Have populated Symfony\Polyfill\Intl\Normalizer\Normalizer
Have populated Amp\Socket\SocketAddress
Have populated Amp\Socket\BindContext
Have populated Amp\Socket\ServerSocket
Have populated Amp\Socket\ResourceServerSocket
Have populated Amp\Socket\SocketException
Have populated Amp\Socket\Socket
Have populated Amp\Socket\ResourceSocket
Have populated Amp\Socket\ServerSocketFactory
Have populated Amp\Socket\ResourceServerSocketFactory
Have populated Amp\Socket\InternetAddress
Have populated Amp\Socket\UdpSocket
Have populated Amp\Socket\ResourceUdpSocket
Have populated Amp\Socket\SocketConnector
Have populated Amp\Socket\RetrySocketConnector
Have populated Amp\Socket\DnsSocketConnector
Have populated Amp\Socket\ConnectContext
Have populated Amp\Socket\ConnectException
Have populated Amp\Socket\TlsException
Have populated Amp\Socket\ClientTlsContext
Have populated League\Uri\UriString
Have populated Amp\NullCancellation
Have populated Amp\Socket\UnixAddress
Have populated JsonSerializable
Have populated Symfony\Component\String\AbstractString
Have populated Symfony\Component\String\AbstractUnicodeString
Have populated Symfony\Component\String\UnicodeString
Have populated Symfony\Component\String\ByteString
Have populated Amp\Parallel\Context\Context
Have populated Amp\Parallel\Context\ContextFactory
Have populated Amp\Parallel\Context\DefaultContextFactory
Have populated Amp\ByteStream\StreamChannel
Have populated Amp\Parallel\Context\Internal\ContextChannel
Have populated Amp\Parallel\Context\Internal\ExitResult
Have populated Amp\Parallel\Context\Internal\ExitSuccess
Have populated Amp\Parallel\Context\Internal\ExitFailure
Have populated Amp\Serialization\SerializationException
Have populated Amp\Parallel\Ipc\IpcHub
Have populated Amp\Parallel\Ipc\SocketIpcHub
Have populated Amp\Parallel\Worker\Worker
Have populated Amp\Parallel\Worker\WorkerPool
Have populated Amp\Parallel\Worker\LimitedWorkerPool
Have populated Amp\Parallel\Worker\ContextWorkerPool
Have populated Amp\Parallel\Worker\Task
Have populated Amp\Parallel\Worker\Execution
Have populated Amp\Parallel\Worker\WorkerFactory
Have populated Amp\Parallel\Worker\ContextWorkerFactory
Have populated Symfony\Polyfill\Php84\Php84
Have populated Composer\Semver\VersionParser
Have populated ReflectionClass
Have populated ReflectionExtension
Have populated ReflectionParameter
Have populated ReflectionType
Have populated ReflectionAttribute
Have populated SplFileObject
Have populated PharData
Have populated PharFileInfo
Have populated Fiber
Have populated SplDoublyLinkedList
Have populated SplQueue
Have populated Serializable
Have populated SplObjectStorage
Have populated UnexpectedValueException
Have populated Revolt\EventLoop\Driver
Have populated Revolt\EventLoop\InvalidCallbackError
Have populated UnitEnum
Have populated Revolt\EventLoop\CallbackType
Have populated Revolt\EventLoop\Suspension
Have populated Amp\Sync\Lock
Have populated Amp\Sync\ChannelException
Have populated Amp\Pipeline\Internal\QueueState
Have populated Amp\Pipeline\Pipeline
Have populated Amp\Pipeline\ConcurrentIterator
Have populated Amp\Pipeline\DisposedException
Have populated Amp\DeferredFuture
Have populated Amp\ByteStream\PendingReadError
Have populated Amp\ByteStream\ClosedException
Have populated Amp\Dns\MissingDnsRecordException
Have populated Amp\Dns\DnsRecord
Have populated Amp\Dns\DnsConfigLoader
Have populated LibDNS\Records\QuestionFactory
Have populated Amp\Dns\DnsConfig
Have populated Amp\Cache\Cache
Have populated Amp\Dns\Internal\Socket
Have populated Amp\Dns\BlockingFallbackDnsResolver
Have populated Amp\Dns\DnsConfigException
Have populated LibDNS\Records\Record
Have populated LibDNS\Records\Question
Have populated LibDNS\Messages\Message
Have populated Normalizer
Have populated Amp\Socket\SocketAddressType
Have populated Amp\Socket\ServerTlsContext
Have populated Amp\Socket\PendingAcceptError
Have populated Amp\Socket\TlsState
Have populated Amp\Socket\TlsInfo
Have populated Amp\Socket\InternetAddressVersion
Have populated Amp\Socket\Certificate
Have populated League\Uri\Contracts\UriException
Have populated League\Uri\Exceptions\SyntaxError
Have populated League\Uri\Exceptions\MissingFeature
Have populated League\Uri\Exceptions\ConversionFailed
Have populated Symfony\Component\String\CodePointString
Have populated Symfony\Component\String\TruncateMode
Have populated Amp\Parallel\Context\ContextException
Have populated Amp\Parser\Parser
Have populated Amp\ByteStream\Internal\ChannelParser
Have populated Amp\Sync\Mutex
Have populated Amp\Serialization\Serializer
Have populated Amp\Parallel\Context\Internal\ContextException
Have populated Amp\Parallel\Context\ContextPanicError
Have populated Amp\Cache\LocalCache
Have populated Amp\Parallel\Context\StatusError
Have populated Amp\DeferredCancellation
Have populated Amp\Parallel\Worker\WorkerException
Have populated Composer\Semver\Constraint\ConstraintInterface
Have populated ReflectionMethod
Have populated ReflectionProperty
Have populated ReflectionClassConstant
Have populated ArrayObject
Have populated RangeException
Have populated Generator
Have populated Amp\Pipeline\Internal\IntermediateOperation
Have populated LibDNS\Enumeration
Have populated LibDNS\Records\ResourceTypes
Have populated LibDNS\Records\ResourceQTypes
Have populated Amp\Cache\CacheException
Have populated LibDNS\Messages\MessageFactory
Have populated LibDNS\Records\Types\TypeFactory
Have populated LibDNS\Records\RecordCollection
Have populated LibDNS\Messages\MessageOpCodes
Have populated LibDNS\Messages\MessageResponseCodes
Have populated LibDNS\Records\RecordCollectionFactory
Have populated Kelunik\Certificate\Certificate
Have populated Amp\Socket\PendingReceiveError
Have populated League\Uri\Idna\Result
Have populated Amp\Internal\Cancellable
Have populated Composer\Semver\Constraint\Constraint
Have populated Composer\Semver\Constraint\Bound
Have populated PropertyHookType
Have populated BackedEnum
Have populated ArrayIterator
Have populated LibDNS\Records\Types\Type
Have populated LibDNS\Records\Types\DomainName
Have populated LibDNS\Records\ResourceClasses
Have populated LibDNS\Records\Types\Anything
Have populated LibDNS\Records\Types\BitMap
Have populated LibDNS\Records\Types\Char
Have populated LibDNS\Records\Types\CharacterString
Have populated LibDNS\Records\Types\IPv4Address
Have populated LibDNS\Records\Types\IPv6Address
Have populated LibDNS\Records\Types\Long
Have populated LibDNS\Records\Types\Short
Have populated League\Uri\Idna\Error
Have populated Amp\Parser\InvalidDelimiterError
Have populated UnderflowException
Have populated OverflowException
ClassLikeStorage is populated
FileStorage is populating
FileStorage is populated
Registering stub files
Parsing /var/www/html/vendor/vimeo/psalm/stubs/CoreGenericFunctions.phpstub because we cannot use cache
Deep scanning /var/www/html/vendor/vimeo/psalm/stubs/CoreGenericFunctions.phpstub
Parsing /var/www/html/vendor/vimeo/psalm/stubs/CoreGenericClasses.phpstub because we cannot use cache
Deep scanning /var/www/html/vendor/vimeo/psalm/stubs/CoreGenericClasses.phpstub
Parsing /var/www/html/vendor/vimeo/psalm/stubs/CoreGenericIterators.phpstub because we cannot use cache
Deep scanning /var/www/html/vendor/vimeo/psalm/stubs/CoreGenericIterators.phpstub
Parsing /var/www/html/vendor/vimeo/psalm/stubs/CoreImmutableClasses.phpstub because we cannot use cache
Deep scanning /var/www/html/vendor/vimeo/psalm/stubs/CoreImmutableClasses.phpstub
Parsing /var/www/html/vendor/vimeo/psalm/stubs/Reflection.phpstub because we cannot use cache
Deep scanning /var/www/html/vendor/vimeo/psalm/stubs/Reflection.phpstub
Parsing /var/www/html/vendor/vimeo/psalm/stubs/SPL.phpstub because we cannot use cache
Deep scanning /var/www/html/vendor/vimeo/psalm/stubs/SPL.phpstub
Parsing /var/www/html/vendor/vimeo/psalm/stubs/CoreGenericAttributes.phpstub because we cannot use cache
Deep scanning /var/www/html/vendor/vimeo/psalm/stubs/CoreGenericAttributes.phpstub
Parsing /var/www/html/vendor/vimeo/psalm/stubs/Php74.phpstub because we cannot use cache
Deep scanning /var/www/html/vendor/vimeo/psalm/stubs/Php74.phpstub
Parsing /var/www/html/vendor/vimeo/psalm/stubs/Php80.phpstub because we cannot use cache
Deep scanning /var/www/html/vendor/vimeo/psalm/stubs/Php80.phpstub
Parsing /var/www/html/vendor/vimeo/psalm/stubs/Php81.phpstub because we cannot use cache
Deep scanning /var/www/html/vendor/vimeo/psalm/stubs/Php81.phpstub
Parsing /var/www/html/vendor/vimeo/psalm/stubs/Php82.phpstub because we cannot use cache
Deep scanning /var/www/html/vendor/vimeo/psalm/stubs/Php82.phpstub
Parsing /var/www/html/vendor/vimeo/psalm/stubs/Php84.phpstub because we cannot use cache
Deep scanning /var/www/html/vendor/vimeo/psalm/stubs/Php84.phpstub
Parsing /var/www/html/vendor/vimeo/psalm/stubs/extensions/random.phpstub because we cannot use cache
Deep scanning /var/www/html/vendor/vimeo/psalm/stubs/extensions/random.phpstub
Using reflection to get metadata for DateTimeInterface
Using reflection to get metadata for DateTime
Using reflection to get metadata for Reflector
Using reflection to get metadata for ReflectionException
ClassLikeStorage is populating
Have populated Traversable
Have populated ArrayAccess
Have populated IteratorAggregate
Have populated WeakMap
Have populated SplFileInfo
Have populated Iterator
Have populated SeekableIterator
Have populated DirectoryIterator
Have populated FilesystemIterator
Have populated RecursiveIterator
Have populated RecursiveDirectoryIterator
Have populated Phar
Have populated Amp\ByteStream\ReadableStream
Have populated Amp\ByteStream\ReadableResourceStream
Have populated Amp\Socket\Socket
Have populated Amp\Socket\ResourceSocket
Have populated SplFileObject
Have populated PharData
Have populated Serializable
Have populated SplDoublyLinkedList
Have populated SplQueue
Have populated SplObjectStorage
Have populated Amp\Pipeline\Internal\QueueState
Have populated Amp\Pipeline\Pipeline
Have populated Amp\Pipeline\ConcurrentIterator
Have populated Amp\Cache\LocalCache
Have populated ArrayObject
Have populated Generator
Have populated LibDNS\Records\RecordCollection
Have populated ArrayIterator
Have populated WeakReference
Have populated mysqli
Have populated SQLite3
Have populated ReturnTypeWillChange
Have populated DateInterval
Have populated OuterIterator
Have populated IteratorIterator
Have populated AppendIterator
Have populated FilterIterator
Have populated CachingIterator
Have populated CallbackFilterIterator
Have populated EmptyIterator
Have populated GlobIterator
Have populated InfiniteIterator
Have populated LimitIterator
Have populated NoRewindIterator
Have populated MultipleIterator
Have populated RecursiveFilterIterator
Have populated ParentIterator
Have populated RecursiveArrayIterator
Have populated RecursiveCachingIterator
Have populated RecursiveCallbackFilterIterator
Have populated RecursiveIteratorIterator
Have populated RegexIterator
Have populated RecursiveRegexIterator
Have populated RecursiveTreeIterator
Have populated DateTimeInterface
Have populated DateTimeImmutable
Have populated DateTimeZone
Have populated DatePeriod
Have populated Throwable
Have populated Exception
Have populated RuntimeException
Have populated LogicException
Have populated InvalidArgumentException
Have populated Error
Have populated ValueError
Have populated JsonException
Have populated TypeError
Have populated CompileError
Have populated ParseError
Have populated OutOfBoundsException
Have populated Amp\CancelledException
Have populated Revolt\EventLoop\UnsupportedFeatureException
Have populated Amp\CompositeLengthException
Have populated Amp\CompositeException
Have populated Amp\ByteStream\StreamException
Have populated Amp\ByteStream\BufferException
Have populated Amp\Dns\DnsException
Have populated Amp\Dns\InvalidNameException
Have populated Amp\Socket\SocketException
Have populated Amp\Socket\ConnectException
Have populated Amp\Socket\TlsException
Have populated Amp\Serialization\SerializationException
Have populated UnexpectedValueException
Have populated Revolt\EventLoop\InvalidCallbackError
Have populated Amp\Sync\ChannelException
Have populated Amp\Pipeline\DisposedException
Have populated Amp\ByteStream\PendingReadError
Have populated Amp\ByteStream\ClosedException
Have populated Amp\Dns\MissingDnsRecordException
Have populated Amp\Dns\DnsConfigException
Have populated Amp\Socket\PendingAcceptError
Have populated League\Uri\Contracts\UriException
Have populated League\Uri\Exceptions\SyntaxError
Have populated League\Uri\Exceptions\MissingFeature
Have populated League\Uri\Exceptions\ConversionFailed
Have populated Amp\Parallel\Context\ContextException
Have populated Amp\Parallel\Context\ContextPanicError
Have populated Amp\Parallel\Context\StatusError
Have populated Amp\Parallel\Worker\WorkerException
Have populated RangeException
Have populated Amp\Cache\CacheException
Have populated Amp\Socket\PendingReceiveError
Have populated Amp\Parser\InvalidDelimiterError
Have populated UnderflowException
Have populated OverflowException
Have populated ReflectionClass
Have populated ReflectionFunctionAbstract
Have populated ReflectionFunction
Have populated ReflectionMethod
Have populated ReflectionProperty
Have populated ReflectionClassConstant
Have populated ReflectionParameter
Have populated ReflectionType
Have populated ReflectionNamedType
Have populated SplFixedArray
Have populated SplStack
Have populated SplHeap
Have populated SplMaxHeap
Have populated SplMinHeap
Have populated SplPriorityQueue
Have populated AllowDynamicProperties
Have populated Override
Have populated SensitiveParameter
Have populated Deprecated
Have populated Stringable
Have populated Amp\Socket\SocketAddress
Have populated Amp\Socket\InternetAddress
Have populated Amp\Socket\UnixAddress
Have populated Symfony\Component\String\AbstractString
Have populated Symfony\Component\String\AbstractUnicodeString
Have populated Symfony\Component\String\UnicodeString
Have populated Symfony\Component\String\ByteString
Have populated ReflectionExtension
Have populated ReflectionAttribute
Have populated PharFileInfo
Have populated Symfony\Component\String\CodePointString
Have populated Kelunik\Certificate\Certificate
Have populated Composer\Semver\Constraint\Constraint
Have populated Composer\Semver\Constraint\Bound
Have populated LibDNS\Records\Types\Type
Have populated LibDNS\Records\Types\DomainName
Have populated LibDNS\Records\Types\Anything
Have populated LibDNS\Records\Types\BitMap
Have populated LibDNS\Records\Types\Char
Have populated LibDNS\Records\Types\CharacterString
Have populated LibDNS\Records\Types\IPv4Address
Have populated LibDNS\Records\Types\IPv6Address
Have populated LibDNS\Records\Types\Long
Have populated LibDNS\Records\Types\Short
Have populated Attribute
Have populated ReflectionUnionType
Have populated UnhandledMatchError
Have populated CurlHandle
Have populated CurlMultiHandle
Have populated CurlShareHandle
Have populated UnitEnum
Have populated Revolt\EventLoop\CallbackType
Have populated Amp\Socket\SocketAddressType
Have populated Amp\Socket\TlsState
Have populated Amp\Socket\InternetAddressVersion
Have populated Symfony\Component\String\TruncateMode
Have populated PropertyHookType
Have populated BackedEnum
Have populated League\Uri\Idna\Error
Have populated ReflectionEnum
Have populated ReflectionEnumUnitCase
Have populated ReflectionEnumBackedCase
Have populated ReflectionIntersectionType
Have populated FTP\Connection
Have populated IMAP\Connection
Have populated LDAP\Connection
Have populated LDAP\Result
Have populated LDAP\ResultEntry
Have populated PgSql\Connection
Have populated PgSql\Result
Have populated PgSql\Lob
Have populated PSpell\Config
Have populated PSpell\Dictionary
Have populated SensitiveParameterValue
Have populated Random\Engine
Have populated Random\Engine\Mt19937
Have populated Random\Engine\PcgOneseq128XslRr64
Have populated Random\Engine\Xoshiro256StarStar
Have populated Random\CryptoSafeEngine
Have populated Random\Engine\Secure
Have populated Random\Randomizer
Have populated Random\RandomError
Have populated Random\BrokenRandomEngineError
Have populated Random\RandomException
Have populated DateTime
Have populated ReflectionException
ClassLikeStorage is populated
FileStorage is populating
FileStorage is populated
Finished registering stub files

Analyzing files...
Analyzing /var/www/html/Example.php
Uncaught AssertionError: assert(count($array_atomic_type) > 0) in /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Analyzer/Statements/Expression/Assignment/ArrayAssignmentAnalyzer.php:639
Stack trace:
#0 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Analyzer/Statements/Expression/Assignment/ArrayAssignmentAnalyzer.php(639): assert(false, 'assert(count($a...')
#1 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Analyzer/Statements/Expression/Assignment/ArrayAssignmentAnalyzer.php(207): Psalm\Internal\Analyzer\Statements\Expression\Assignment\ArrayAssignmentAnalyzer::updateArrayAssignmentChildType(Object(Psalm\Internal\Analyzer\StatementsAnalyzer), Object(Psalm\Codebase), NULL, Object(Psalm\Context), Object(Psalm\Type\Union), Object(Psalm\Type\Union), false, '$conditions')
#2 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Analyzer/Statements/Expression/Assignment/ArrayAssignmentAnalyzer.php(75): Psalm\Internal\Analyzer\Statements\Expression\Assignment\ArrayAssignmentAnalyzer::updateArrayType(Object(Psalm\Internal\Analyzer\StatementsAnalyzer), Object(PhpParser\Node\Expr\ArrayDimFetch), Object(PhpParser\Node\Expr\Array_), Object(Psalm\Type\Union), Object(Psalm\Context))
#3 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Analyzer/Statements/Expression/AssignmentAnalyzer.php(558): Psalm\Internal\Analyzer\Statements\Expression\Assignment\ArrayAssignmentAnalyzer::analyze(Object(Psalm\Internal\Analyzer\StatementsAnalyzer), Object(PhpParser\Node\Expr\ArrayDimFetch), Object(Psalm\Context), Object(PhpParser\Node\Expr\Array_), Object(Psalm\Type\Union))
#4 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Analyzer/Statements/Expression/AssignmentAnalyzer.php(443): Psalm\Internal\Analyzer\Statements\Expression\AssignmentAnalyzer::analyzeAssignment(Object(PhpParser\Node\Expr\ArrayDimFetch), Object(Psalm\Internal\Analyzer\StatementsAnalyzer), Object(Psalm\Codebase), Object(PhpParser\Node\Expr\Array_), Object(Psalm\Type\Union), NULL, Object(Psalm\Context), NULL, NULL, Array, Array)
#5 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Analyzer/Statements/ExpressionAnalyzer.php(499): Psalm\Internal\Analyzer\Statements\Expression\AssignmentAnalyzer::analyze(Object(Psalm\Internal\Analyzer\StatementsAnalyzer), Object(PhpParser\Node\Expr\ArrayDimFetch), Object(PhpParser\Node\Expr\Array_), Object(Psalm\Type\Union), Object(Psalm\Context), NULL, Array, NULL)
#6 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Analyzer/Statements/ExpressionAnalyzer.php(205): Psalm\Internal\Analyzer\Statements\ExpressionAnalyzer::analyzeAssignment(Object(Psalm\Internal\Analyzer\StatementsAnalyzer), Object(PhpParser\Node\Expr\Assign), Object(Psalm\Context), Object(PhpParser\Node\Stmt\Expression))
#7 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Analyzer/Statements/ExpressionAnalyzer.php(92): Psalm\Internal\Analyzer\Statements\ExpressionAnalyzer::handleExpression(Object(Psalm\Internal\Analyzer\StatementsAnalyzer), Object(PhpParser\Node\Expr\Assign), Object(Psalm\Context), false, Object(Psalm\Context), Object(PhpParser\Node\Stmt\Expression), NULL, false)
#8 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Analyzer/StatementsAnalyzer.php(563): Psalm\Internal\Analyzer\Statements\ExpressionAnalyzer::analyze(Object(Psalm\Internal\Analyzer\StatementsAnalyzer), Object(PhpParser\Node\Expr\Assign), Object(Psalm\Context), false, Object(Psalm\Context), Object(PhpParser\Node\Stmt\Expression))
#9 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Analyzer/StatementsAnalyzer.php(193): Psalm\Internal\Analyzer\StatementsAnalyzer::analyzeStatement(Object(Psalm\Internal\Analyzer\StatementsAnalyzer), Object(PhpParser\Node\Stmt\Expression), Object(Psalm\Context), Object(Psalm\Context))
#10 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Analyzer/FunctionLikeAnalyzer.php(508): Psalm\Internal\Analyzer\StatementsAnalyzer->analyze(Array, Object(Psalm\Context), Object(Psalm\Context), true)
#11 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Analyzer/FunctionAnalyzer.php(99): Psalm\Internal\Analyzer\FunctionLikeAnalyzer->analyze(Object(Psalm\Context), Object(Psalm\Internal\Provider\NodeDataProvider), Object(Psalm\Context))
#12 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Analyzer/StatementsAnalyzer.php(561): Psalm\Internal\Analyzer\FunctionAnalyzer::analyzeStatement(Object(Psalm\Internal\Analyzer\StatementsAnalyzer), Object(PhpParser\Node\Stmt\Function_), Object(Psalm\Context))
#13 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Analyzer/StatementsAnalyzer.php(193): Psalm\Internal\Analyzer\StatementsAnalyzer::analyzeStatement(Object(Psalm\Internal\Analyzer\StatementsAnalyzer), Object(PhpParser\Node\Stmt\Function_), Object(Psalm\Context), NULL)
#14 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Analyzer/FileAnalyzer.php(174): Psalm\Internal\Analyzer\StatementsAnalyzer->analyze(Array, Object(Psalm\Context), NULL, true)
#15 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Codebase/Analyzer.php(1486): Psalm\Internal\Analyzer\FileAnalyzer->analyze()
#16 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Codebase/Analyzer.php(438): Psalm\Internal\Codebase\Analyzer::analysisWorker(Object(Psalm\Config), Object(Psalm\Progress\DebugProgress), '/var/www/html/E...')
#17 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Codebase/Analyzer.php(246): Psalm\Internal\Codebase\Analyzer->doAnalysis(Object(Psalm\Internal\Analyzer\ProjectAnalyzer), 1)
#18 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Analyzer/ProjectAnalyzer.php(974): Psalm\Internal\Codebase\Analyzer->analyzeFiles(Object(Psalm\Internal\Analyzer\ProjectAnalyzer), 1, false, false)
#19 /var/www/html/vendor/vimeo/psalm/src/Psalm/Internal/Cli/Psalm.php(402): Psalm\Internal\Analyzer\ProjectAnalyzer->checkPaths(Array)
#20 /var/www/html/vendor/vimeo/psalm/psalm(9): Psalm\Internal\Cli\Psalm::run(Array)
#21 /var/www/html/vendor/bin/psalm(119): include('/var/www/html/v...')
#22 {main}
(Psalm 6.13.1@1e3b7f0a8ab32b23197b91107adc0a7ed8a05b51 crashed due to an uncaught Throwable)

Since this seems to depend somewhat on the environment, here is a standalone Docker image that can reliably reproduce the issue:

FROM php:8.4.12-cli

# Install Composer
ADD https://github.com/mlocati/docker-php-extension-installer/releases/latest/download/install-php-extensions /usr/local/bin/
RUN chmod +x /usr/local/bin/install-php-extensions && \
  install-php-extensions @composer

# Install psalm
WORKDIR /var/www/html
RUN composer require --dev vimeo/psalm:6.13.1 # or vimeo/psalm:6.x-dev@dev

# Create example file to analyze
RUN echo -e "<?php\n\$conditions = ['A' => 'B'];\n\$conditions[]['C'] = [];" > Example.php

# Initialize psalm and analyze example file when container is run
ENTRYPOINT ["/var/www/html/vendor/bin/psalm", "--init"]

Just build and run this and it should produce the same error.

scribblemaniac avatar Sep 16 '25 06:09 scribblemaniac

Hey @scribblemaniac, can you reproduce the issue on https://psalm.dev? These will be used as phpunit tests when implementing the feature or fixing this bug.

psalm-github-bot[bot] avatar Sep 16 '25 06:09 psalm-github-bot[bot]

The provided code also runs fine on psalm.dev.

scribblemaniac avatar Sep 16 '25 06:09 scribblemaniac