PHPLIB-1859 Add Psalm array shapes for search and vector search index definitions#1899
PHPLIB-1859 Add Psalm array shapes for search and vector search index definitions#1899GromNaN wants to merge 5 commits into
Conversation
… definitions Adds typed `@psalm-type` shapes to `Collection` for all search index structures (`SearchIndexDefinitionShape`, `VectorSearchIndexDefinitionShape`, and their subtypes), including `storedSource` support in both. Renames `OperationType` to `OperationShape` for consistency. Adds Psalm type tests in `tests/Type/`.
There was a problem hiding this comment.
Pull request overview
Adds Psalm array-shape aliases for Atlas Search and Atlas Vector Search index definitions and wires those shapes into Collection APIs and the internal SearchIndexInput model, with a new Psalm-only type test file to validate documentation examples.
Changes:
- Introduces
@psalm-typealiases insrc/Collection.phpfor search/vector index definitions (includingstoredSource) and uses them increateSearchIndex()/createSearchIndexes()/updateSearchIndex()phpdocs. - Renames the BulkWrite operation psalm alias from
OperationTypetoOperationShapeand updates dependent annotations. - Adds
tests/Type/SearchIndexShapes.phpand includestests/Typein Psalm config so these shape examples are type-checked.
Reviewed changes
Copilot reviewed 6 out of 6 changed files in this pull request and generated 2 comments.
Show a summary per file
| File | Description |
|---|---|
| tests/Type/SearchIndexShapes.php | Adds Psalm-only type checks using documentation-style examples for search/vector index definitions. |
| src/Operation/BulkWrite.php | Renames the psalm alias for bulk write operations to OperationShape and updates related annotations. |
| src/Model/SearchIndexInput.php | Switches the input model to reference the imported SearchIndexShape alias. |
| src/Collection.php | Defines search/vector index shape aliases and updates related method annotations/usages. |
| psalm.xml.dist | Adds tests/Type/ to Psalm’s analyzed project files. |
Comments suppressed due to low confidence (1)
src/Model/SearchIndexInput.php:52
- The constructor validates
$index['definition']withis_document, which allows both arrays and objects, but the new@param SearchIndexShapedepends onSearchIndexShapecurrently restrictingdefinitionto array shapes only. This will cause Psalm to reject valid object definitions. Align the imported shape (or override with a@psalm-paramhere) sodefinitioncan be an object as well.
* @psalm-import-type SearchIndexShape from Collection
*/
final class SearchIndexInput implements Serializable
{
/**
* @param SearchIndexShape $index Search index specification
* @throws InvalidArgumentException
*/
public function __construct(private array $index)
{
if (! isset($index['definition'])) {
throw new InvalidArgumentException('Required "definition" document is missing from search index specification');
}
if (! is_document($index['definition'])) {
throw InvalidArgumentException::expectedDocumentType('"definition" option', $index['definition']);
Codecov Report✅ All modified and coverable lines are covered by tests. Additional details and impacted files@@ Coverage Diff @@
## v2.x #1899 +/- ##
============================================
- Coverage 87.74% 87.72% -0.02%
- Complexity 3319 3328 +9
============================================
Files 451 454 +3
Lines 6632 6657 +25
============================================
+ Hits 5819 5840 +21
- Misses 813 817 +4
Flags with carried forward coverage won't be shown. Click here to find out more. ☔ View full report in Codecov by Sentry. |
…remove redundant array from updateSearchIndex param
| /** @phpstan-import-type OperationType from BulkWrite */ | ||
| /** | ||
| * @psalm-import-type OperationShape from BulkWrite | ||
| * @psalm-type SearchIndexFieldShape = array{ |
There was a problem hiding this comment.
I put this shapes in the Collection class because that's where they are used. And the SearchIndexInput class is internal, so it can't expose a psalm type.
There was a problem hiding this comment.
Interesting. Is this a limitation from psalm/phpstan?
| * | ||
| * @psalm-type Document = object|array | ||
| * @psalm-type OperationType = array{deleteMany: array{0: Document, 1?: array}}|array{deleteOne: array{0: Document, 1?: array}}|array{insertOne: array{0: Document}}|array{replaceOne: array{0: Document, 1: Document, 2?: array}}|array{updateMany: array{0: Document, 1: Document, 2?: array}}|array{updateOne: array{0: Document, 1: Document, 2?: array}} | ||
| * @psalm-type OperationShape = array{deleteMany: array{0: Document, 1?: array}}|array{deleteOne: array{0: Document, 1?: array}}|array{insertOne: array{0: Document}}|array{replaceOne: array{0: Document, 1: Document, 2?: array}}|array{updateMany: array{0: Document, 1: Document, 2?: array}}|array{updateOne: array{0: Document, 1: Document, 2?: array}} |
There was a problem hiding this comment.
This shape can be improved using the query operators once we generate array shapes for the agg builder.
…IndexDefinitionShape mappings
alcaeus
left a comment
There was a problem hiding this comment.
LGTM; good to merge once CI is alive again.
| * This file is not executed by PHPUnit; it is only checked by Psalm to verify | ||
| * that the OperationShape defined in BulkWrite is accepted by Collection::bulkWrite. |
There was a problem hiding this comment.
Interesting strategy, I like it!
Adds typed
@psalm-typeshapes toCollectionfor all search and vector search index structures, includingstoredSourcesupport inVectorSearchIndexDefinitionShape(PHPLIB-1859) andSearchIndexDefinitionShape.The shapes are adapted from laravel-mongodb, which defines equivalent PHPStan types.
OperationType→OperationShapeinBulkWritefor naming consistencySearchIndexFieldShape,SearchIndexCharFilterShape,SearchIndexTokenFilterShape,SearchIndexAnalyzerShape,SearchIndexStoredSourceShape,SearchIndexSynonymShape,SearchIndexDefinitionShape,VectorSearchIndexFieldShape,VectorSearchIndexDefinitionShape,SearchIndexShape@paramoncreateSearchIndex,createSearchIndexes,updateSearchIndexSearchIndexInputimportsSearchIndexShapefromCollectionvia@psalm-import-typetests/Type/SearchIndexShapes.phpandtests/Type/BulkWriteShapes.phpwith Psalm type tests based on documentation examplestests/Type/topsalm.xml.dist