Skip to content

Commit e2cc923

Browse files
committed
Remove task array access
1 parent d708780 commit e2cc923

File tree

5 files changed

+87
-152
lines changed

5 files changed

+87
-152
lines changed

src/Contracts/Task.php

Lines changed: 21 additions & 55 deletions
Original file line numberDiff line numberDiff line change
@@ -16,12 +16,11 @@
1616
use Meilisearch\Contracts\TaskDetails\TaskCancelationDetails;
1717
use Meilisearch\Contracts\TaskDetails\TaskDeletionDetails;
1818

19-
final class Task implements \ArrayAccess
19+
final class Task
2020
{
2121
/**
2222
* @param non-negative-int $taskUid
2323
* @param non-empty-string|null $indexUid
24-
* @param array<mixed> $data Raw data
2524
*/
2625
public function __construct(
2726
private readonly int $taskUid,
@@ -36,7 +35,6 @@ public function __construct(
3635
private readonly ?int $batchUid = null,
3736
private readonly ?TaskDetails $details = null,
3837
private readonly ?TaskError $error = null,
39-
private readonly array $data = [],
4038
) {
4139
}
4240

@@ -106,38 +104,6 @@ public function getError(): ?TaskError
106104
return $this->error;
107105
}
108106

109-
/**
110-
* @return array<mixed>
111-
*/
112-
public function getData(): array
113-
{
114-
return $this->data;
115-
}
116-
117-
// @todo: deprecate
118-
public function offsetExists(mixed $offset): bool
119-
{
120-
return \array_key_exists($offset, $this->data);
121-
}
122-
123-
// @todo: deprecate
124-
public function offsetGet(mixed $offset): mixed
125-
{
126-
return $this->data[$offset] ?? null;
127-
}
128-
129-
// @todo: deprecate
130-
public function offsetSet(mixed $offset, mixed $value): void
131-
{
132-
throw new \LogicException(\sprintf('Setting data on "%s::%s" is not supported.', get_debug_type($this), $offset));
133-
}
134-
135-
// @todo: deprecate
136-
public function offsetUnset(mixed $offset): void
137-
{
138-
throw new \LogicException(\sprintf('Unsetting data on "%s::%s" is not supported.', get_debug_type($this), $offset));
139-
}
140-
141107
public function isFinished(): bool
142108
{
143109
return TaskStatus::Enqueued !== $this->status && TaskStatus::Processing !== $this->status;
@@ -151,47 +117,47 @@ public function isFinished(): bool
151117
* status: non-empty-string,
152118
* type: non-empty-string,
153119
* enqueuedAt: non-empty-string,
154-
* startedAt?: non-empty-string,
155-
* finishedAt?: non-empty-string,
156-
* duration?: non-empty-string,
120+
* startedAt?: non-empty-string|null,
121+
* finishedAt?: non-empty-string|null,
122+
* duration?: non-empty-string|null,
157123
* canceledBy?: int,
158124
* batchUid?: int,
159125
* details?: array<mixed>|null,
160-
* error?: array<mixed>|null,
161-
* data: array<mixed>
126+
* error?: array<mixed>|null
162127
* } $data
163128
*/
164129
public static function fromArray(array $data): Task
165130
{
131+
$details = $data['details'] ?? null;
132+
166133
return new self(
167134
$data['taskUid'] ?? $data['uid'],
168135
$data['indexUid'] ?? null,
169136
TaskStatus::from($data['status']),
170137
$type = TaskType::from($data['type']),
171138
new \DateTimeImmutable($data['enqueuedAt']),
172-
isset($data['startedAt']) ? new \DateTimeImmutable($data['startedAt']) : null,
173-
isset($data['finishedAt']) ? new \DateTimeImmutable($data['finishedAt']) : null,
139+
\array_key_exists('startedAt', $data) && null !== $data['startedAt'] ? new \DateTimeImmutable($data['startedAt']) : null,
140+
\array_key_exists('finishedAt', $data) && null !== $data['finishedAt'] ? new \DateTimeImmutable($data['finishedAt']) : null,
174141
$data['duration'] ?? null,
175142
$data['canceledBy'] ?? null,
176143
$data['batchUid'] ?? null,
177144
match ($type) {
178-
TaskType::IndexCreation => null !== $data['details'] ? IndexCreationDetails::fromArray($data['details']) : null,
179-
TaskType::IndexUpdate => null !== $data['details'] ? IndexUpdateDetails::fromArray($data['details']) : null,
180-
TaskType::IndexDeletion => null !== $data['details'] ? IndexDeletionDetails::fromArray($data['details']) : null,
181-
TaskType::IndexSwap => null !== $data['details'] ? IndexSwapDetails::fromArray($data['details']) : null,
182-
TaskType::DocumentAdditionOrUpdate => null !== $data['details'] ? DocumentAdditionOrUpdateDetails::fromArray($data['details']) : null,
183-
TaskType::DocumentDeletion => null !== $data['details'] ? DocumentDeletionDetails::fromArray($data['details']) : null,
184-
TaskType::DocumentEdition => null !== $data['details'] ? DocumentEditionDetails::fromArray($data['details']) : null,
185-
TaskType::SettingsUpdate => null !== $data['details'] ? SettingsUpdateDetails::fromArray($data['details']) : null,
186-
TaskType::DumpCreation => null !== $data['details'] ? DumpCreationDetails::fromArray($data['details']) : null,
187-
TaskType::TaskCancelation => null !== $data['details'] ? TaskCancelationDetails::fromArray($data['details']) : null,
188-
TaskType::TaskDeletion => null !== $data['details'] ? TaskDeletionDetails::fromArray($data['details']) : null,
145+
TaskType::IndexCreation => null !== $details ? IndexCreationDetails::fromArray($details) : null,
146+
TaskType::IndexUpdate => null !== $details ? IndexUpdateDetails::fromArray($details) : null,
147+
TaskType::IndexDeletion => null !== $details ? IndexDeletionDetails::fromArray($details) : null,
148+
TaskType::IndexSwap => null !== $details ? IndexSwapDetails::fromArray($details) : null,
149+
TaskType::DocumentAdditionOrUpdate => null !== $details ? DocumentAdditionOrUpdateDetails::fromArray($details) : null,
150+
TaskType::DocumentDeletion => null !== $details ? DocumentDeletionDetails::fromArray($details) : null,
151+
TaskType::DocumentEdition => null !== $details ? DocumentEditionDetails::fromArray($details) : null,
152+
TaskType::SettingsUpdate => null !== $details ? SettingsUpdateDetails::fromArray($details) : null,
153+
TaskType::DumpCreation => null !== $details ? DumpCreationDetails::fromArray($details) : null,
154+
TaskType::TaskCancelation => null !== $details ? TaskCancelationDetails::fromArray($details) : null,
155+
TaskType::TaskDeletion => null !== $details ? TaskDeletionDetails::fromArray($details) : null,
189156
// It’s intentional that SnapshotCreation tasks don’t have a details object
190157
// (no SnapshotCreationDetails exists and tests don’t exercise any details)
191158
TaskType::SnapshotCreation => null,
192159
},
193-
null !== $data['error'] ? TaskError::fromArray($data['error']) : null,
194-
$data,
160+
\array_key_exists('error', $data) && null !== $data['error'] ? TaskError::fromArray($data['error']) : null,
195161
);
196162
}
197163
}

src/Contracts/TaskDetails/DocumentAdditionOrUpdateDetails.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@
1515
final class DocumentAdditionOrUpdateDetails implements TaskDetails
1616
{
1717
/**
18-
* @param non-negative-int $receivedDocuments Number of documents received
18+
* @param non-negative-int $receivedDocuments Number of documents received.
1919
* @param non-negative-int|null $indexedDocuments Number of documents indexed. `null` while the task status is enqueued or processing.
2020
*/
2121
public function __construct(

tests/Contracts/TaskTest.php

Lines changed: 0 additions & 42 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,6 @@
1010
use Meilisearch\Contracts\TaskStatus;
1111
use Meilisearch\Contracts\TaskType;
1212
use PHPUnit\Framework\TestCase;
13-
use Tests\MockTask;
1413

1514
final class TaskTest extends TestCase
1615
{
@@ -34,13 +33,6 @@ public function testCreate(): void
3433
'invalid_request',
3534
'https://docs.meilisearch.com/errors#index_not_found',
3635
),
37-
data: [
38-
'taskUid' => 1,
39-
'indexUid' => 'documents',
40-
'status' => 'failed',
41-
'type' => 'index_creation',
42-
'enqueuedAt' => '2025-04-09T10:28:12.236789123Z',
43-
],
4436
);
4537

4638
self::assertSame(1, $task->getTaskUid());
@@ -60,20 +52,6 @@ public function testCreate(): void
6052
'invalid_request',
6153
'https://docs.meilisearch.com/errors#index_not_found',
6254
), $task->getError());
63-
self::assertSame([
64-
'taskUid' => 1,
65-
'indexUid' => 'documents',
66-
'status' => 'failed',
67-
'type' => 'index_creation',
68-
'enqueuedAt' => '2025-04-09T10:28:12.236789123Z',
69-
], $task->getData());
70-
71-
// Ensure the class supports array access retrocompatibility
72-
self::assertSame(1, $task->getTaskUid());
73-
self::assertSame('documents', $task['indexUid']);
74-
self::assertSame('failed', $task['status']);
75-
self::assertSame('index_creation', $task['type']);
76-
self::assertSame('2025-04-09T10:28:12.236789123Z', $task['enqueuedAt']);
7755
}
7856

7957
public function testCreateEnqueuedTask(): void
@@ -99,24 +77,4 @@ public function testCreateEnqueuedTask(): void
9977
self::assertNull($task->getDetails());
10078
self::assertNull($task->getError());
10179
}
102-
103-
public function testArraySetThrows(): void
104-
{
105-
$task = MockTask::create(TaskType::IndexCreation);
106-
107-
$this->expectException(\LogicException::class);
108-
$this->expectExceptionMessage('Setting data on "Meilisearch\Contracts\Task::type" is not supported.');
109-
110-
$task['type'] = TaskType::IndexDeletion;
111-
}
112-
113-
public function testArrayUnsetThrows(): void
114-
{
115-
$task = MockTask::create(TaskType::IndexCreation);
116-
117-
$this->expectException(\LogicException::class);
118-
$this->expectExceptionMessage('Unsetting data on "Meilisearch\Contracts\Task::type" is not supported.');
119-
120-
unset($task['type']);
121-
}
12280
}

tests/Endpoints/DocumentsTest.php

Lines changed: 29 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,8 @@
77
use Meilisearch\Contracts\DocumentsQuery;
88
use Meilisearch\Contracts\Http;
99
use Meilisearch\Contracts\Task;
10+
use Meilisearch\Contracts\TaskDetails\DocumentAdditionOrUpdateDetails;
11+
use Meilisearch\Contracts\TaskStatus;
1012
use Meilisearch\Contracts\TaskType;
1113
use Meilisearch\Endpoints\Indexes;
1214
use Meilisearch\Exceptions\ApiException;
@@ -74,11 +76,11 @@ public function testAddDocumentsCsv(): void
7476
fclose($fileCsv);
7577

7678
$task = $index->addDocumentsCsv($documentCsv);
79+
$completedTask = $index->waitForTask($task->getTaskUid());
7780

78-
$update = $index->waitForTask($task->getTaskUid());
79-
80-
self::assertSame('succeeded', $update['status']);
81-
self::assertNotSame(0, $update['details']['receivedDocuments']);
81+
self::assertSame(TaskStatus::Succeeded, $completedTask->getStatus());
82+
self::assertInstanceOf(DocumentAdditionOrUpdateDetails::class, $details = $completedTask->getDetails());
83+
self::assertNotSame(0, $details->receivedDocuments);
8284

8385
$response = $index->getDocuments();
8486
self::assertCount(20, $response);
@@ -91,11 +93,11 @@ public function testAddDocumentsCsvWithCustomSeparator(): void
9193
$csv = file_get_contents('./tests/datasets/songs-custom-separator.csv', true);
9294

9395
$task = $index->addDocumentsCsv($csv, null, '|');
96+
$completedTask = $index->waitForTask($task->getTaskUid());
9497

95-
$update = $index->waitForTask($task->getTaskUid());
96-
97-
self::assertSame('succeeded', $update['status']);
98-
self::assertSame(6, $update['details']['receivedDocuments']);
98+
self::assertSame(TaskStatus::Succeeded, $completedTask->getStatus());
99+
self::assertInstanceOf(DocumentAdditionOrUpdateDetails::class, $details = $completedTask->getDetails());
100+
self::assertSame(6, $details->receivedDocuments);
99101

100102
$documents = $index->getDocuments()->getResults();
101103
self::assertSame('Teenage Neon Jungle', $documents[4]['album']);
@@ -111,11 +113,11 @@ public function testAddDocumentsJson(): void
111113
fclose($fileJson);
112114

113115
$task = $index->addDocumentsJson($documentJson);
116+
$completedTask = $index->waitForTask($task->getTaskUid());
114117

115-
$update = $index->waitForTask($task->getTaskUid());
116-
117-
self::assertSame('succeeded', $update['status']);
118-
self::assertNotSame(0, $update['details']['receivedDocuments']);
118+
self::assertSame(TaskStatus::Succeeded, $completedTask->getStatus());
119+
self::assertInstanceOf(DocumentAdditionOrUpdateDetails::class, $details = $completedTask->getDetails());
120+
self::assertNotSame(0, $details->receivedDocuments);
119121

120122
$response = $index->getDocuments();
121123
self::assertCount(20, $response);
@@ -130,11 +132,11 @@ public function testAddDocumentsNdJson(): void
130132
fclose($fileNdJson);
131133

132134
$task = $index->addDocumentsNdjson($documentNdJson);
135+
$completedTask = $index->waitForTask($task->getTaskUid());
133136

134-
$update = $index->waitForTask($task->getTaskUid());
135-
136-
self::assertSame('succeeded', $update['status']);
137-
self::assertNotSame(0, $update['details']['receivedDocuments']);
137+
self::assertSame(TaskStatus::Succeeded, $completedTask->getStatus());
138+
self::assertInstanceOf(DocumentAdditionOrUpdateDetails::class, $details = $completedTask->getDetails());
139+
self::assertNotSame(0, $details->receivedDocuments);
138140

139141
$response = $index->getDocuments();
140142
self::assertCount(20, $response);
@@ -154,8 +156,10 @@ public function testCannotAddDocumentWhenJsonEncodingFails(): void
154156
public function testGetSingleDocumentWithIntegerDocumentId(): void
155157
{
156158
$index = $this->createEmptyIndex($this->safeIndexName('movies'));
159+
157160
$task = $index->addDocuments(self::DOCUMENTS);
158161
$index->waitForTask($task->getTaskUid());
162+
159163
$doc = $this->findDocumentWithId(self::DOCUMENTS, 4);
160164
$response = $index->getDocument($doc['id']);
161165

@@ -166,8 +170,10 @@ public function testGetSingleDocumentWithIntegerDocumentId(): void
166170
public function testGetSingleDocumentWithFields(): void
167171
{
168172
$index = $this->createEmptyIndex($this->safeIndexName('movies'));
173+
169174
$task = $index->addDocuments(self::DOCUMENTS);
170175
$index->waitForTask($task->getTaskUid());
176+
171177
$doc = $this->findDocumentWithId(self::DOCUMENTS, 4);
172178
$response = $index->getDocument($doc['id'], ['title']);
173179

@@ -178,8 +184,10 @@ public function testGetSingleDocumentWithFields(): void
178184
public function testGetSingleDocumentWithStringDocumentId(): void
179185
{
180186
$stringDocumentId = 'myUniqueId';
187+
181188
$index = $this->createEmptyIndex($this->safeIndexName('movies'));
182189
$task = $index->addDocuments([['id' => $stringDocumentId]]);
190+
183191
$index->waitForTask($task->getTaskUid());
184192
$response = $index->getDocument($stringDocumentId);
185193

@@ -189,8 +197,10 @@ public function testGetSingleDocumentWithStringDocumentId(): void
189197
public function testGetMultipleDocumentsByIds(): void
190198
{
191199
$index = $this->createEmptyIndex($this->safeIndexName('movies'));
200+
192201
$task = $index->addDocuments(self::DOCUMENTS);
193202
$index->waitForTask($task->getTaskUid());
203+
194204
$documentIds = [1, 2];
195205
$response = $index->getDocuments((new DocumentsQuery())->setIds($documentIds));
196206

@@ -203,8 +213,10 @@ public function testGetMultipleDocumentsByIds(): void
203213
public function testReplaceDocuments(): void
204214
{
205215
$index = $this->createEmptyIndex($this->safeIndexName('movies'));
216+
206217
$task = $index->addDocuments(self::DOCUMENTS);
207218
$index->waitForTask($task->getTaskUid());
219+
208220
$replacement = [
209221
'id' => 2,
210222
'title' => 'The Red And The Black',
@@ -916,7 +928,7 @@ public function testUpdateDocumentsNdjsonInBatches(): void
916928
self::assertSame('Ailitp', $response['artist']);
917929
}
918930

919-
private function findDocumentWithId($documents, $documentId)
931+
private function findDocumentWithId($documents, $documentId): ?array
920932
{
921933
foreach ($documents as $document) {
922934
if ($document['id'] === $documentId) {

0 commit comments

Comments
 (0)