diff --git a/.travis.yml b/.travis.yml
index 40f6484b..9eff19d2 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -26,6 +26,7 @@ before_script:
script:
- if [[ $TEST_COVERAGE == 'true' ]]; then php -dzend_extension=xdebug.so ./vendor/bin/phpunit --exclude-group=ignore --coverage-text --coverage-clover ./build/logs/clover.xml; else ./vendor/bin/phpunit --exclude-group=ignore; fi
+- ./vendor/bin/psalm
- if [[ $EXECUTE_CS_CHECK == 'true' ]]; then ./vendor/bin/php-cs-fixer fix -v --diff --dry-run; fi
after_success:
diff --git a/composer.json b/composer.json
index d281698a..eaeb8ed3 100644
--- a/composer.json
+++ b/composer.json
@@ -19,16 +19,16 @@
"require": {
"php": "^7.4",
"ext-json": "*",
- "ramsey/uuid": "^3.8"
+ "ramsey/uuid": "^3.9.3"
},
"require-dev": {
- "amphp/amp": "^2.1.2",
- "doctrine/instantiator": "^1.1",
- "php-coveralls/php-coveralls": "^2.1",
- "phpspec/prophecy": "^1.7.2",
- "phpunit/phpunit": "^8.2.2",
- "prooph/php-cs-fixer-config": "^0.3",
- "sebastian/object-enumerator": "^3.0.3"
+ "amphp/amp": "^2.4.4",
+ "doctrine/instantiator": "^1.3",
+ "php-coveralls/php-coveralls": "^2.2",
+ "phpspec/prophecy": "^1.10.3",
+ "phpunit/phpunit": "^9.1",
+ "prooph/php-cs-fixer-config": "^0.3.1",
+ "vimeo/psalm": "^3.11.2"
},
"autoload": {
"psr-4": {
diff --git a/psalm.xml b/psalm.xml
new file mode 100644
index 00000000..d0e0cce1
--- /dev/null
+++ b/psalm.xml
@@ -0,0 +1,16 @@
+
+
+
+
+
+
+
+
+
diff --git a/src/AllEventsSlice.php b/src/AllEventsSlice.php
index 06948921..4c3c7dbd 100644
--- a/src/AllEventsSlice.php
+++ b/src/AllEventsSlice.php
@@ -18,17 +18,14 @@ class AllEventsSlice
private ReadDirection $readDirection;
private Position $fromPosition;
private Position $nextPosition;
- /** @var ResolvedEvent[] */
+ /** @var list */
private array $events;
private bool $isEndOfStream;
/**
* @internal
*
- * @param ReadDirection $readDirection
- * @param Position $fromPosition
- * @param Position $nextPosition
- * @param ResolvedEvent[] $events
+ * @param list $events
*/
public function __construct(
ReadDirection $readDirection,
@@ -58,7 +55,7 @@ public function nextPosition(): Position
return $this->nextPosition;
}
- /** @return ResolvedEvent[] */
+ /** @return list */
public function events(): array
{
return $this->events;
diff --git a/src/Async/CatchUpSubscriptionDropped.php b/src/Async/CatchUpSubscriptionDropped.php
deleted file mode 100644
index 1bd42765..00000000
--- a/src/Async/CatchUpSubscriptionDropped.php
+++ /dev/null
@@ -1,26 +0,0 @@
-
- * (c) 2015-2020 Sascha-Oliver Prolic
- *
- * For the full copyright and license information, please view the LICENSE
- * file that was distributed with this source code.
- */
-
-declare(strict_types=1);
-
-namespace Prooph\EventStore\Async;
-
-use Prooph\EventStore\SubscriptionDropReason;
-use Throwable;
-
-interface CatchUpSubscriptionDropped
-{
- public function __invoke(
- EventStoreCatchUpSubscription $subscription,
- SubscriptionDropReason $reason,
- ?Throwable $exception = null
- ): void;
-}
diff --git a/src/Async/EventAppearedOnCatchupSubscription.php b/src/Async/EventAppearedOnCatchupSubscription.php
deleted file mode 100644
index a5753034..00000000
--- a/src/Async/EventAppearedOnCatchupSubscription.php
+++ /dev/null
@@ -1,25 +0,0 @@
-
- * (c) 2015-2020 Sascha-Oliver Prolic
- *
- * For the full copyright and license information, please view the LICENSE
- * file that was distributed with this source code.
- */
-
-declare(strict_types=1);
-
-namespace Prooph\EventStore\Async;
-
-use Amp\Promise;
-use Prooph\EventStore\ResolvedEvent;
-
-interface EventAppearedOnCatchupSubscription
-{
- public function __invoke(
- EventStoreCatchUpSubscription $subscription,
- ResolvedEvent $resolvedEvent
- ): Promise;
-}
diff --git a/src/Async/EventAppearedOnPersistentSubscription.php b/src/Async/EventAppearedOnPersistentSubscription.php
deleted file mode 100644
index 309d3250..00000000
--- a/src/Async/EventAppearedOnPersistentSubscription.php
+++ /dev/null
@@ -1,26 +0,0 @@
-
- * (c) 2015-2020 Sascha-Oliver Prolic
- *
- * For the full copyright and license information, please view the LICENSE
- * file that was distributed with this source code.
- */
-
-declare(strict_types=1);
-
-namespace Prooph\EventStore\Async;
-
-use Amp\Promise;
-use Prooph\EventStore\ResolvedEvent;
-
-interface EventAppearedOnPersistentSubscription
-{
- public function __invoke(
- EventStorePersistentSubscription $subscription,
- ResolvedEvent $resolvedEvent,
- ?int $retryCount = null
- ): Promise;
-}
diff --git a/src/Async/EventAppearedOnSubscription.php b/src/Async/EventAppearedOnSubscription.php
deleted file mode 100644
index 3ba98db4..00000000
--- a/src/Async/EventAppearedOnSubscription.php
+++ /dev/null
@@ -1,26 +0,0 @@
-
- * (c) 2015-2020 Sascha-Oliver Prolic
- *
- * For the full copyright and license information, please view the LICENSE
- * file that was distributed with this source code.
- */
-
-declare(strict_types=1);
-
-namespace Prooph\EventStore\Async;
-
-use Amp\Promise;
-use Prooph\EventStore\EventStoreSubscription;
-use Prooph\EventStore\ResolvedEvent;
-
-interface EventAppearedOnSubscription
-{
- public function __invoke(
- EventStoreSubscription $subscription,
- ResolvedEvent $resolvedEvent
- ): Promise;
-}
diff --git a/src/Async/EventStoreCatchUpSubscription.php b/src/Async/EventStoreCatchUpSubscription.php
index 9909365f..ecd58b6d 100644
--- a/src/Async/EventStoreCatchUpSubscription.php
+++ b/src/Async/EventStoreCatchUpSubscription.php
@@ -14,7 +14,6 @@
namespace Prooph\EventStore\Async;
use Amp\Promise;
-use Throwable;
interface EventStoreCatchUpSubscription
{
diff --git a/src/Async/EventStoreConnection.php b/src/Async/EventStoreConnection.php
index b96688df..dfd1a6f3 100644
--- a/src/Async/EventStoreConnection.php
+++ b/src/Async/EventStoreConnection.php
@@ -29,13 +29,15 @@
use Prooph\EventStore\PersistentSubscriptionSettings;
use Prooph\EventStore\Position;
use Prooph\EventStore\RawStreamMetadataResult;
+use Prooph\EventStore\ResolvedEvent;
use Prooph\EventStore\StreamEventsSlice;
use Prooph\EventStore\StreamMetadata;
use Prooph\EventStore\StreamMetadataResult;
-use Prooph\EventStore\SubscriptionDropped;
+use Prooph\EventStore\SubscriptionDropReason;
use Prooph\EventStore\SystemSettings;
use Prooph\EventStore\UserCredentials;
use Prooph\EventStore\WriteResult;
+use Throwable;
interface EventStoreConnection
{
@@ -54,10 +56,7 @@ public function deleteStreamAsync(
): Promise;
/**
- * @param string $stream
- * @param int $expectedVersion
- * @param EventData[] $events
- * @param UserCredentials|null $userCredentials
+ * @param list $events
* @return Promise
*/
public function appendToStreamAsync(
@@ -68,10 +67,7 @@ public function appendToStreamAsync(
): Promise;
/**
- * @param string $stream
- * @param int $expectedVersion
- * @param EventData[] $events
- * @param UserCredentials|null $userCredentials
+ * @param list $events
* @return Promise
*/
public function conditionalAppendToStreamAsync(
@@ -184,74 +180,106 @@ public function deletePersistentSubscriptionAsync(
): Promise;
/**
+ * @param Closure(EventStoreSubscription, ResolvedEvent): Promise $eventAppeared
+ * @param null|Closure(EventStoreSubscription, SubscriptionDropReason, ?Throwable): void $subscriptionDropped
+ * @param null|UserCredentials $userCredentials
* @return Promise
*/
public function subscribeToStreamAsync(
string $stream,
bool $resolveLinkTos,
- EventAppearedOnSubscription $eventAppeared,
- ?SubscriptionDropped $subscriptionDropped = null,
+ Closure $eventAppeared,
+ ?Closure $subscriptionDropped = null,
?UserCredentials $userCredentials = null
): Promise;
/**
+ * @param Closure(EventStoreCatchUpSubscription, ResolvedEvent): Promise $eventAppeared
+ * @param null|Closure(EventStoreCatchUpSubscription): void $liveProcessingStarted
+ * @param null|Closure(EventStoreCatchUpSubscription, SubscriptionDropReason, ?Throwable): void $subscriptionDropped
* @return Promise
*/
public function subscribeToStreamFromAsync(
string $stream,
?int $lastCheckpoint,
?CatchUpSubscriptionSettings $settings,
- EventAppearedOnCatchupSubscription $eventAppeared,
- ?LiveProcessingStartedOnCatchUpSubscription $liveProcessingStarted = null,
- ?CatchUpSubscriptionDropped $subscriptionDropped = null,
+ Closure $eventAppeared,
+ ?Closure $liveProcessingStarted = null,
+ ?Closure $subscriptionDropped = null,
?UserCredentials $userCredentials = null
): Promise;
/**
+ * @param Closure(EventStoreSubscription, ResolvedEvent): Promise $eventAppeared
+ * @param null|Closure(EventStoreSubscription, SubscriptionDropReason, ?Throwable): void $subscriptionDropped
* @return Promise
*/
public function subscribeToAllAsync(
bool $resolveLinkTos,
- EventAppearedOnSubscription $eventAppeared,
- ?SubscriptionDropped $subscriptionDropped = null,
+ Closure $eventAppeared,
+ ?Closure $subscriptionDropped = null,
?UserCredentials $userCredentials = null
): Promise;
/**
+ * @param Closure(EventStoreCatchUpSubscription, ResolvedEvent): Promise $eventAppeared
+ * @param null|Closure(EventStoreCatchUpSubscription): void $liveProcessingStarted
+ * @param null|Closure(EventStoreCatchUpSubscription, SubscriptionDropReason, ?Throwable): void $subscriptionDropped
* @return Promise
*/
public function subscribeToAllFromAsync(
?Position $lastCheckpoint,
?CatchUpSubscriptionSettings $settings,
- EventAppearedOnCatchupSubscription $eventAppeared,
- ?LiveProcessingStartedOnCatchUpSubscription $liveProcessingStarted = null,
- ?CatchUpSubscriptionDropped $subscriptionDropped = null,
+ Closure $eventAppeared,
+ ?Closure $liveProcessingStarted = null,
+ ?Closure $subscriptionDropped = null,
?UserCredentials $userCredentials = null
): Promise;
/**
+ * @param Closure(EventStorePersistentSubscription, ResolvedEvent, ?int): Promise $eventAppeared
+ * @param null|Closure(EventStorePersistentSubscription, SubscriptionDropReason, ?Throwable): void $subscriptionDropped
+ *
* @return Promise
*/
public function connectToPersistentSubscriptionAsync(
string $stream,
string $groupName,
- EventAppearedOnPersistentSubscription $eventAppeared,
- ?PersistentSubscriptionDropped $subscriptionDropped = null,
+ Closure $eventAppeared,
+ ?Closure $subscriptionDropped = null,
int $bufferSize = 10,
bool $autoAck = true,
?UserCredentials $userCredentials = null
): Promise;
+ /**
+ * @param Closure(ClientConnectionEventArgs): void $handler
+ */
public function onConnected(Closure $handler): ListenerHandler;
+ /**
+ * @param Closure(ClientConnectionEventArgs): void $handler
+ */
public function onDisconnected(Closure $handler): ListenerHandler;
+ /**
+ * @param Closure(ClientReconnectingEventArgs): void $handler
+ */
public function onReconnecting(Closure $handler): ListenerHandler;
+ /**
+ * @param Closure(ClientClosedEventArgs): void $handler
+ */
public function onClosed(Closure $handler): ListenerHandler;
+ /**
+ * @param Closure(ClientErrorEventArgs): void $handler
+ */
public function onErrorOccurred(Closure $handler): ListenerHandler;
+ /**
+ * @param Closure(ClientAuthenticationFailedEventArgs): void $handler
+ */
public function onAuthenticationFailed(Closure $handler): ListenerHandler;
public function detach(ListenerHandler $handler): void;
diff --git a/src/Async/EventStorePersistentSubscription.php b/src/Async/EventStorePersistentSubscription.php
index 241b80b7..f05b3291 100644
--- a/src/Async/EventStorePersistentSubscription.php
+++ b/src/Async/EventStorePersistentSubscription.php
@@ -25,10 +25,6 @@ interface EventStorePersistentSubscription
/**
* Acknowledge that a message have completed processing (this will tell the server it has been processed)
* Note: There is no need to ack a message if you have Auto Ack enabled
- *
- * @param ResolvedEvent $event
- *
- * @return void
*/
public function acknowledge(ResolvedEvent $event): void;
@@ -36,19 +32,13 @@ public function acknowledge(ResolvedEvent $event): void;
* Acknowledge that a message have completed processing (this will tell the server it has been processed)
* Note: There is no need to ack a message if you have Auto Ack enabled
*
- * @param ResolvedEvent[] $events
- *
- * @return void
+ * @param list $events
*/
public function acknowledgeMultiple(array $events): void;
/**
* Acknowledge that a message have completed processing (this will tell the server it has been processed)
* Note: There is no need to ack a message if you have Auto Ack enabled
- *
- * @param EventId $eventId
- *
- * @return void
*/
public function acknowledgeEventId(EventId $eventId): void;
@@ -56,9 +46,7 @@ public function acknowledgeEventId(EventId $eventId): void;
* Acknowledge that a message have completed processing (this will tell the server it has been processed)
* Note: There is no need to ack a message if you have Auto Ack enabled
*
- * @param EventId[] $eventIds
- *
- * @return void
+ * @param list $eventIds
*/
public function acknowledgeMultipleEventIds(array $eventIds): void;
@@ -74,9 +62,7 @@ public function fail(
/**
* Mark n messages that have failed processing. The server will take action based upon the action parameter
*
- * @param ResolvedEvent[] $events
- * @param PersistentSubscriptionNakEventAction $action
- * @param string $reason
+ * @param list $events
*/
public function failMultiple(
array $events,
@@ -96,9 +82,7 @@ public function failEventId(
/**
* Mark n messages that have failed processing. The server will take action based upon the action parameter
*
- * @param EventId[] $eventIds
- * @param PersistentSubscriptionNakEventAction $action
- * @param string $reason
+ * @param list $eventIds
*/
public function failMultipleEventIds(
array $eventIds,
diff --git a/src/Async/EventStoreTransaction.php b/src/Async/EventStoreTransaction.php
index 617c8ccf..794c9d03 100644
--- a/src/Async/EventStoreTransaction.php
+++ b/src/Async/EventStoreTransaction.php
@@ -59,7 +59,7 @@ public function commitAsync(): Promise
}
/**
- * @param EventData[] $events
+ * @param list $events
*
* @return Promise
*/
diff --git a/src/Async/Internal/EventStoreTransactionConnection.php b/src/Async/Internal/EventStoreTransactionConnection.php
index 491f46dd..42103ed7 100644
--- a/src/Async/Internal/EventStoreTransactionConnection.php
+++ b/src/Async/Internal/EventStoreTransactionConnection.php
@@ -21,6 +21,7 @@
/** @internal */
interface EventStoreTransactionConnection
{
+ /** @return Promise */
public function transactionalWriteAsync(
EventStoreTransaction $transaction,
array $events,
diff --git a/src/Async/LiveProcessingStartedOnCatchUpSubscription.php b/src/Async/LiveProcessingStartedOnCatchUpSubscription.php
deleted file mode 100644
index c2a1087a..00000000
--- a/src/Async/LiveProcessingStartedOnCatchUpSubscription.php
+++ /dev/null
@@ -1,19 +0,0 @@
-
- * (c) 2015-2020 Sascha-Oliver Prolic
- *
- * For the full copyright and license information, please view the LICENSE
- * file that was distributed with this source code.
- */
-
-declare(strict_types=1);
-
-namespace Prooph\EventStore\Async;
-
-interface LiveProcessingStartedOnCatchUpSubscription
-{
- public function __invoke(EventStoreCatchUpSubscription $subscription): void;
-}
diff --git a/src/Async/PersistentSubscriptionDropped.php b/src/Async/PersistentSubscriptionDropped.php
deleted file mode 100644
index bc88d62a..00000000
--- a/src/Async/PersistentSubscriptionDropped.php
+++ /dev/null
@@ -1,26 +0,0 @@
-
- * (c) 2015-2020 Sascha-Oliver Prolic
- *
- * For the full copyright and license information, please view the LICENSE
- * file that was distributed with this source code.
- */
-
-declare(strict_types=1);
-
-namespace Prooph\EventStore\Async;
-
-use Prooph\EventStore\SubscriptionDropReason;
-use Throwable;
-
-interface PersistentSubscriptionDropped
-{
- public function __invoke(
- EventStorePersistentSubscription $subscription,
- SubscriptionDropReason $reason,
- ?Throwable $exception = null
- ): void;
-}
diff --git a/src/Async/PersistentSubscriptions/PersistentSubscriptionsManager.php b/src/Async/PersistentSubscriptions/PersistentSubscriptionsManager.php
index 3c8a46cf..f825ab6e 100644
--- a/src/Async/PersistentSubscriptions/PersistentSubscriptionsManager.php
+++ b/src/Async/PersistentSubscriptions/PersistentSubscriptionsManager.php
@@ -32,6 +32,6 @@ public function replayParkedMessages(
?UserCredentials $userCredentials = null
): Promise;
- /** @return Promise */
+ /** @return Promise> */
public function list(?string $stream = null, ?UserCredentials $userCredentials = null): Promise;
}
diff --git a/src/Async/Projections/ProjectionsManager.php b/src/Async/Projections/ProjectionsManager.php
index 97879684..ebd1009a 100644
--- a/src/Async/Projections/ProjectionsManager.php
+++ b/src/Async/Projections/ProjectionsManager.php
@@ -67,21 +67,21 @@ public function createContinuousAsync(
/**
* Asynchronously lists all projections
*
- * @return Promise
+ * @return Promise>
*/
public function listAllAsync(?UserCredentials $userCredentials = null): Promise;
/**
* Asynchronously lists all one-time projections
*
- * @return Promise
+ * @return Promise>
*/
public function listOneTimeAsync(?UserCredentials $userCredentials = null): Promise;
/**
* Asynchronously lists this status of all continuous projections
*
- * @return Promise
+ * @return Promise>
*/
public function listContinuousAsync(?UserCredentials $userCredentials = null): Promise;
diff --git a/src/Async/Projections/QueryManager.php b/src/Async/Projections/QueryManager.php
index 0b18de3f..4e6be341 100644
--- a/src/Async/Projections/QueryManager.php
+++ b/src/Async/Projections/QueryManager.php
@@ -25,13 +25,6 @@ interface QueryManager
*
* returns String of JSON containing query result
*
- * @param string $name A name for the query
- * @param string $query The source code for the query
- * @param int $initialPollingDelay Initial time to wait between polling for projection status
- * @param int $maximumPollingDelay Maximum time to wait between polling for projection status
- * @param string $type The type to use, defaults to JS
- * @param UserCredentials|null $userCredentials Credentials for a user with permission to create a query
- *
* @return Promise
*/
public function executeAsync(
diff --git a/src/Async/UserManagement/UsersManager.php b/src/Async/UserManagement/UsersManager.php
index b48bbdf7..be449933 100644
--- a/src/Async/UserManagement/UsersManager.php
+++ b/src/Async/UserManagement/UsersManager.php
@@ -20,14 +20,16 @@
interface UsersManager
{
+ /** @return Promise */
public function enableAsync(string $login, ?UserCredentials $userCredentials = null): Promise;
+ /** @return Promise */
public function disableAsync(string $login, ?UserCredentials $userCredentials = null): Promise;
/** @throws UserCommandFailed */
public function deleteUserAsync(string $login, ?UserCredentials $userCredentials = null): Promise;
- /** @return Promise */
+ /** @return Promise> */
public function listAllAsync(?UserCredentials $userCredentials = null): Promise;
/** @return Promise */
@@ -37,12 +39,8 @@ public function getCurrentUserAsync(?UserCredentials $userCredentials = null): P
public function getUserAsync(string $login, ?UserCredentials $userCredentials = null): Promise;
/**
- * @param string $login
- * @param string $fullName
- * @param string[] $groups
- * @param string $password
- * @param UserCredentials|null $userCredentials
- * @return Promise
+ * @param list $groups
+ * @return Promise
*/
public function createUserAsync(
string $login,
@@ -53,11 +51,8 @@ public function createUserAsync(
): Promise;
/**
- * @param string $login
- * @param string $fullName
- * @param string[] $groups
- * @param UserCredentials|null $userCredentials
- * @return Promise
+ * @param list $groups
+ * @return Promise
*/
public function updateUserAsync(
string $login,
@@ -66,6 +61,7 @@ public function updateUserAsync(
?UserCredentials $userCredentials = null
): Promise;
+ /** @return Promise */
public function changePasswordAsync(
string $login,
string $oldPassword,
@@ -73,6 +69,7 @@ public function changePasswordAsync(
?UserCredentials $userCredentials = null
): Promise;
+ /** @return Promise */
public function resetPasswordAsync(
string $login,
string $newPassword,
diff --git a/src/CatchUpSubscriptionDropped.php b/src/CatchUpSubscriptionDropped.php
deleted file mode 100644
index a43dc165..00000000
--- a/src/CatchUpSubscriptionDropped.php
+++ /dev/null
@@ -1,25 +0,0 @@
-
- * (c) 2015-2020 Sascha-Oliver Prolic
- *
- * For the full copyright and license information, please view the LICENSE
- * file that was distributed with this source code.
- */
-
-declare(strict_types=1);
-
-namespace Prooph\EventStore;
-
-use Throwable;
-
-interface CatchUpSubscriptionDropped
-{
- public function __invoke(
- EventStoreCatchUpSubscription $subscription,
- SubscriptionDropReason $reason,
- ?Throwable $exception = null
- ): void;
-}
diff --git a/src/ConditionalWriteResult.php b/src/ConditionalWriteResult.php
index 9a4b85d6..71d8f65c 100644
--- a/src/ConditionalWriteResult.php
+++ b/src/ConditionalWriteResult.php
@@ -15,25 +15,23 @@
use Prooph\EventStore\Exception\InvalidArgumentException;
+/** @psam-immutable */
class ConditionalWriteResult
{
private ConditionalWriteStatus $status;
private ?int $nextExpectedVersion;
private ?Position $logPosition;
- private function __construct()
+ private function __construct(ConditionalWriteStatus $status, ?int $nextExpectedVersion, ?Position $logPosition)
{
+ $this->status = $status;
+ $this->nextExpectedVersion = $nextExpectedVersion;
+ $this->logPosition = $logPosition;
}
public static function success(int $nextExpectedVersion, Position $logPosition): ConditionalWriteResult
{
- $self = new self();
-
- $self->status = ConditionalWriteStatus::succeeded();
- $self->nextExpectedVersion = $nextExpectedVersion;
- $self->logPosition = $logPosition;
-
- return $self;
+ return new self(ConditionalWriteStatus::succeeded(), $nextExpectedVersion, $logPosition);
}
public static function fail(ConditionalWriteStatus $status): ConditionalWriteResult
@@ -42,22 +40,22 @@ public static function fail(ConditionalWriteStatus $status): ConditionalWriteRes
throw new InvalidArgumentException('For successful write pass next expected version and log position');
}
- $self = new self();
- $self->status = $status;
-
- return $self;
+ return new self($status, null, null);
}
+ /** @psalm-pure */
public function status(): ConditionalWriteStatus
{
return $this->status;
}
+ /** @psalm-pure */
public function nextExpectedVersion(): ?int
{
return $this->nextExpectedVersion;
}
+ /** @psalm-pure */
public function logPosition(): ?Position
{
return $this->logPosition;
diff --git a/src/ConditionalWriteStatus.php b/src/ConditionalWriteStatus.php
index 311e0ff5..b611eaa0 100644
--- a/src/ConditionalWriteStatus.php
+++ b/src/ConditionalWriteStatus.php
@@ -15,6 +15,7 @@
use Prooph\EventStore\Exception\InvalidArgumentException;
+/** @psalm-immutable */
class ConditionalWriteStatus
{
public const OPTIONS = [
@@ -57,35 +58,39 @@ public static function byName(string $value): self
throw new InvalidArgumentException('Unknown enum name given');
}
- return self::{$value}();
+ return new self($value);
}
- public static function byValue($value): self
+ public static function byValue(int $value): self
{
foreach (self::OPTIONS as $name => $v) {
if ($v === $value) {
- return self::{$name}();
+ return new self($name);
}
}
throw new InvalidArgumentException('Unknown enum value given');
}
+ /** @psalm-pure */
public function equals(ConditionalWriteStatus $other): bool
{
return \get_class($this) === \get_class($other) && $this->name === $other->name;
}
+ /** @psalm-pure */
public function name(): string
{
return $this->name;
}
- public function value()
+ /** @psalm-pure */
+ public function value(): int
{
return $this->value;
}
+ /** @psalm-pure */
public function __toString(): string
{
return $this->name;
diff --git a/src/EventAppearedOnCatchupSubscription.php b/src/EventAppearedOnCatchupSubscription.php
deleted file mode 100644
index 6912eab5..00000000
--- a/src/EventAppearedOnCatchupSubscription.php
+++ /dev/null
@@ -1,22 +0,0 @@
-
- * (c) 2015-2020 Sascha-Oliver Prolic
- *
- * For the full copyright and license information, please view the LICENSE
- * file that was distributed with this source code.
- */
-
-declare(strict_types=1);
-
-namespace Prooph\EventStore;
-
-interface EventAppearedOnCatchupSubscription
-{
- public function __invoke(
- EventStoreCatchUpSubscription $subscription,
- ResolvedEvent $resolvedEvent
- ): void;
-}
diff --git a/src/EventAppearedOnPersistentSubscription.php b/src/EventAppearedOnPersistentSubscription.php
deleted file mode 100644
index b6d4d65b..00000000
--- a/src/EventAppearedOnPersistentSubscription.php
+++ /dev/null
@@ -1,23 +0,0 @@
-
- * (c) 2015-2020 Sascha-Oliver Prolic
- *
- * For the full copyright and license information, please view the LICENSE
- * file that was distributed with this source code.
- */
-
-declare(strict_types=1);
-
-namespace Prooph\EventStore;
-
-interface EventAppearedOnPersistentSubscription
-{
- public function __invoke(
- EventStorePersistentSubscription $subscription,
- ResolvedEvent $resolvedEvent,
- ?int $retryCount = null
- ): void;
-}
diff --git a/src/EventAppearedOnSubscription.php b/src/EventAppearedOnSubscription.php
deleted file mode 100644
index c85f75a9..00000000
--- a/src/EventAppearedOnSubscription.php
+++ /dev/null
@@ -1,22 +0,0 @@
-
- * (c) 2015-2020 Sascha-Oliver Prolic
- *
- * For the full copyright and license information, please view the LICENSE
- * file that was distributed with this source code.
- */
-
-declare(strict_types=1);
-
-namespace Prooph\EventStore;
-
-interface EventAppearedOnSubscription
-{
- public function __invoke(
- EventStoreSubscription $subscription,
- ResolvedEvent $resolvedEvent
- ): void;
-}
diff --git a/src/EventId.php b/src/EventId.php
index aa0adf71..11f9b1b9 100644
--- a/src/EventId.php
+++ b/src/EventId.php
@@ -16,6 +16,7 @@
use Prooph\EventStore\Util\Guid;
use Ramsey\Uuid\UuidInterface;
+/** @psalm-immutable */
class EventId
{
private UuidInterface $uuid;
@@ -37,26 +38,35 @@ public static function fromBinary(string $bytes): EventId
private function __construct(UuidInterface $eventId)
{
+ /** @psalm-suppress ImpurePropertyAssignment */
$this->uuid = $eventId;
}
+ /** @psalm-pure */
public function toString(): string
{
+ /** @psalm-suppress ImpureMethodCall */
return $this->uuid->toString();
}
+ /** @psalm-pure */
public function toBinary(): string
{
+ /** @psalm-suppress ImpureMethodCall */
return $this->uuid->getBytes();
}
+ /** @psalm-pure */
public function __toString(): string
{
+ /** @psalm-suppress ImpureMethodCall */
return $this->uuid->toString();
}
+ /** @psalm-pure */
public function equals(EventId $other): bool
{
+ /** @psalm-suppress ImpureMethodCall */
return $this->uuid->equals($other->uuid);
}
}
diff --git a/src/EventReadStatus.php b/src/EventReadStatus.php
index 1439dbc2..f4247f6e 100644
--- a/src/EventReadStatus.php
+++ b/src/EventReadStatus.php
@@ -15,6 +15,7 @@
use Prooph\EventStore\Exception\InvalidArgumentException;
+/** @psalm-immutable */
class EventReadStatus
{
public const OPTIONS = [
@@ -64,35 +65,39 @@ public static function byName(string $value): self
throw new InvalidArgumentException('Unknown enum name given');
}
- return self::{$value}();
+ return new self($value);
}
- public static function byValue($value): self
+ public static function byValue(int $value): self
{
foreach (self::OPTIONS as $name => $v) {
if ($v === $value) {
- return self::{$name}();
+ return new self($name);
}
}
throw new InvalidArgumentException('Unknown enum value given');
}
+ /** @psalm-pure */
public function equals(EventReadStatus $other): bool
{
return static::class === \get_class($other) && $this->name === $other->name;
}
+ /** @psalm-pure */
public function name(): string
{
return $this->name;
}
- public function value()
+ /** @psalm-pure */
+ public function value(): int
{
return $this->value;
}
+ /** @psalm-pure */
public function __toString(): string
{
return $this->name;
diff --git a/src/EventStoreCatchUpSubscription.php b/src/EventStoreCatchUpSubscription.php
index 6ad827fb..c0c548c5 100644
--- a/src/EventStoreCatchUpSubscription.php
+++ b/src/EventStoreCatchUpSubscription.php
@@ -13,8 +13,6 @@
namespace Prooph\EventStore;
-use Throwable;
-
interface EventStoreCatchUpSubscription
{
public function isSubscribedToAll(): bool;
diff --git a/src/EventStoreConnection.php b/src/EventStoreConnection.php
index b0c5c516..46f59a09 100644
--- a/src/EventStoreConnection.php
+++ b/src/EventStoreConnection.php
@@ -13,9 +13,11 @@
namespace Prooph\EventStore;
+use Closure;
use Prooph\EventStore\Internal\PersistentSubscriptionCreateResult;
use Prooph\EventStore\Internal\PersistentSubscriptionDeleteResult;
use Prooph\EventStore\Internal\PersistentSubscriptionUpdateResult;
+use Throwable;
interface EventStoreConnection
{
@@ -27,10 +29,7 @@ public function deleteStream(
): DeleteResult;
/**
- * @param string $stream
- * @param int $expectedVersion
- * @param EventData[] $events
- * @param UserCredentials|null $userCredentials
+ * @param list $events
*
* @return WriteResult
*/
@@ -136,45 +135,67 @@ public function deletePersistentSubscription(
?UserCredentials $userCredentials = null
): PersistentSubscriptionDeleteResult;
+ /**
+ * @param Closure(EventStoreSubscription, ResolvedEvent): void $eventAppeared
+ * @param null|Closure(EventStoreSubscription, SubscriptionDropReason, ?Throwable): void $subscriptionDropped
+ */
public function subscribeToStream(
string $stream,
bool $resolveLinkTos,
- EventAppearedOnSubscription $eventAppeared,
- ?SubscriptionDropped $subscriptionDropped = null,
+ Closure $eventAppeared,
+ ?Closure $subscriptionDropped = null,
?UserCredentials $userCredentials = null
): EventStoreSubscription;
+ /**
+ * @param Closure(EventStoreCatchUpSubscription, ResolvedEvent): void $eventAppeared
+ * @param null|Closure(EventStoreCatchUpSubscription): void $liveProcessingStarted
+ * @param null|Closure(EventStoreCatchUpSubscription, SubscriptionDropReason, ?Throwable): void $subscriptionDropped
+ */
public function subscribeToStreamFrom(
string $stream,
?int $lastCheckpoint,
?CatchUpSubscriptionSettings $settings,
- EventAppearedOnCatchupSubscription $eventAppeared,
- ?LiveProcessingStartedOnCatchUpSubscription $liveProcessingStarted = null,
- ?CatchUpSubscriptionDropped $subscriptionDropped = null,
+ Closure $eventAppeared,
+ ?Closure $liveProcessingStarted = null,
+ ?Closure $subscriptionDropped = null,
?UserCredentials $userCredentials = null
): EventStoreStreamCatchUpSubscription;
+ /**
+ * @param Closure(EventStoreSubscription, ResolvedEvent): void $eventAppeared
+ * @param Closure(EventStoreSubscription, SubscriptionDropReason, ?Throwable): void $subscriptionDropped
+ */
public function subscribeToAll(
bool $resolveLinkTos,
- EventAppearedOnSubscription $eventAppeared,
- ?SubscriptionDropped $subscriptionDropped = null,
+ Closure $eventAppeared,
+ ?Closure $subscriptionDropped = null,
?UserCredentials $userCredentials = null
): EventStoreSubscription;
+ /**
+ * @param Closure(EventStoreCatchUpSubscription, ResolvedEvent): void $eventAppeared
+ * @param null|Closure(EventStoreCatchUpSubscription): void $liveProcessingStarted
+ * @param null|Closure(EventStoreCatchUpSubscription, SubscriptionDropReason, ?Throwable): void $subscriptionDropped
+ */
public function subscribeToAllFrom(
?Position $lastCheckpoint,
?CatchUpSubscriptionSettings $settings,
- EventAppearedOnCatchupSubscription $eventAppeared,
- ?LiveProcessingStartedOnCatchUpSubscription $liveProcessingStarted = null,
- ?CatchUpSubscriptionDropped $subscriptionDropped = null,
+ Closure $eventAppeared,
+ ?Closure $liveProcessingStarted = null,
+ ?Closure $subscriptionDropped = null,
?UserCredentials $userCredentials = null
): EventStoreAllCatchUpSubscription;
+ /**
+ * @param Closure(EventStorePersistentSubscription, ResolvedEvent, ?int): void $eventAppeared
+ * @param null|Closure(EventStorePersistentSubscription, SubscriptionDropReason, ?Throwable): void $subscriptionDropped
+ */
public function connectToPersistentSubscription(
string $stream,
string $groupName,
- EventAppearedOnPersistentSubscription $eventAppeared,
- ?PersistentSubscriptionDropped $subscriptionDropped = null,
+ Closure $eventAppeared,
+ ?Closure $subscriptionDropped = null,
int $bufferSize = 10,
bool $autoAck = true,
?UserCredentials $userCredentials = null
diff --git a/src/EventStorePersistentSubscription.php b/src/EventStorePersistentSubscription.php
index f853d412..ab98c0b5 100644
--- a/src/EventStorePersistentSubscription.php
+++ b/src/EventStorePersistentSubscription.php
@@ -31,7 +31,7 @@ public function acknowledge(ResolvedEvent $event): void;
* Acknowledge that a message have completed processing (this will tell the server it has been processed)
* Note: There is no need to ack a message if you have Auto Ack enabled
*
- * @param ResolvedEvent[] $events
+ * @param list $events
*/
public function acknowledgeMultiple(array $events): void;
@@ -45,7 +45,7 @@ public function acknowledgeEventId(EventId $eventId): void;
* Acknowledge that a message have completed processing (this will tell the server it has been processed)
* Note: There is no need to ack a message if you have Auto Ack enabled
*
- * @param EventId[] $eventIds
+ * @param list $eventIds
*/
public function acknowledgeMultipleEventIds(array $eventIds): void;
@@ -61,9 +61,7 @@ public function fail(
/**
* Mark n messages that have failed processing. The server will take action based upon the action parameter
*
- * @param ResolvedEvent[] $events
- * @param PersistentSubscriptionNakEventAction $action
- * @param string $reason
+ * @param list $events
*/
public function failMultiple(
array $events,
@@ -83,9 +81,7 @@ public function failEventId(
/**
* Mark n messages that have failed processing. The server will take action based upon the action parameter
*
- * @param EventId[] $eventIds
- * @param PersistentSubscriptionNakEventAction $action
- * @param string $reason
+ * @param list $eventIds
*/
public function failMultipleEventIds(
array $eventIds,
diff --git a/src/EventStoreTransaction.php b/src/EventStoreTransaction.php
index 30324b6a..fcc671da 100644
--- a/src/EventStoreTransaction.php
+++ b/src/EventStoreTransaction.php
@@ -52,7 +52,7 @@ public function commit(): WriteResult
}
/**
- * @param EventData[] $events
+ * @param list $events
*/
public function write(array $events = []): void
{
diff --git a/src/Exception/WrongExpectedVersion.php b/src/Exception/WrongExpectedVersion.php
index ab9dc433..e72d2ad4 100644
--- a/src/Exception/WrongExpectedVersion.php
+++ b/src/Exception/WrongExpectedVersion.php
@@ -30,7 +30,7 @@ public static function with(
$message,
$stream,
$expectedVersion,
- $currentVersion
+ (string) $currentVersion
));
}
}
diff --git a/src/Internal/ConnectToPersistentSubscriptions.php b/src/Internal/ConnectToPersistentSubscriptions.php
index 2d4c7a73..1729a19a 100644
--- a/src/Internal/ConnectToPersistentSubscriptions.php
+++ b/src/Internal/ConnectToPersistentSubscriptions.php
@@ -19,13 +19,11 @@
/** @internal */
interface ConnectToPersistentSubscriptions
{
- /** @param EventId[] $eventIds */
+ /** @param list $eventIds */
public function notifyEventsProcessed(array $eventIds): void;
/**
- * @param EventId[] $eventIds
- * @param PersistentSubscriptionNakEventAction $action
- * @param string $reason
+ * @param list $eventIds
*/
public function notifyEventsFailed(
array $eventIds,
diff --git a/src/Internal/PersistentEventStoreSubscription.php b/src/Internal/PersistentEventStoreSubscription.php
index 65a8d2ce..f5d9e15d 100644
--- a/src/Internal/PersistentEventStoreSubscription.php
+++ b/src/Internal/PersistentEventStoreSubscription.php
@@ -42,16 +42,14 @@ public function unsubscribe(): void
$this->subscriptionOperation->unsubscribe();
}
- /** @param EventId[] $eventIds */
+ /** @param list $eventIds */
public function notifyEventsProcessed(array $eventIds): void
{
$this->subscriptionOperation->notifyEventsProcessed($eventIds);
}
/**
- * @param EventId[] $eventIds
- * @param PersistentSubscriptionNakEventAction $action
- * @param string $reason
+ * @param list $eventIds
*/
public function notifyEventsFailed(
array $eventIds,
diff --git a/src/Internal/PersistentSubscriptionCreateStatus.php b/src/Internal/PersistentSubscriptionCreateStatus.php
index 34023eda..1e6ef957 100644
--- a/src/Internal/PersistentSubscriptionCreateStatus.php
+++ b/src/Internal/PersistentSubscriptionCreateStatus.php
@@ -15,7 +15,10 @@
use Prooph\EventStore\Exception\InvalidArgumentException;
-/** @internal */
+/**
+ * @internal
+ * @psalm-immutable
+ */
class PersistentSubscriptionCreateStatus
{
public const OPTIONS = [
@@ -58,35 +61,39 @@ public static function byName(string $value): self
throw new InvalidArgumentException('Unknown enum name given');
}
- return self::{$value}();
+ return new self($value);
}
- public static function byValue($value): self
+ public static function byValue(int $value): self
{
foreach (self::OPTIONS as $name => $v) {
if ($v === $value) {
- return self::{$name}();
+ return new self($name);
}
}
throw new InvalidArgumentException('Unknown enum value given');
}
+ /** @psalm-pure */
public function equals(PersistentSubscriptionCreateStatus $other): bool
{
return \get_class($this) === \get_class($other) && $this->name === $other->name;
}
+ /** @psalm-pure */
public function name(): string
{
return $this->name;
}
- public function value()
+ /** @psalm-pure */
+ public function value(): int
{
return $this->value;
}
+ /** @psalm-pure */
public function __toString(): string
{
return $this->name;
diff --git a/src/Internal/PersistentSubscriptionDeleteStatus.php b/src/Internal/PersistentSubscriptionDeleteStatus.php
index 07be5563..0e14fd70 100644
--- a/src/Internal/PersistentSubscriptionDeleteStatus.php
+++ b/src/Internal/PersistentSubscriptionDeleteStatus.php
@@ -15,7 +15,10 @@
use Prooph\EventStore\Exception\InvalidArgumentException;
-/** @internal */
+/**
+ * @internal
+ * @psalm-immutable
+ */
class PersistentSubscriptionDeleteStatus
{
public const OPTIONS = [
@@ -51,35 +54,39 @@ public static function byName(string $value): self
throw new InvalidArgumentException('Unknown enum name given');
}
- return self::{$value}();
+ return new self($value);
}
- public static function byValue($value): self
+ public static function byValue(int $value): self
{
foreach (self::OPTIONS as $name => $v) {
if ($v === $value) {
- return self::{$name}();
+ return new self($name);
}
}
throw new InvalidArgumentException('Unknown enum value given');
}
+ /** @psalm-pure */
public function equals(PersistentSubscriptionDeleteStatus $other): bool
{
return \get_class($this) === \get_class($other) && $this->name === $other->name;
}
+ /** @psalm-pure */
public function name(): string
{
return $this->name;
}
- public function value()
+ /** @psalm-pure */
+ public function value(): int
{
return $this->value;
}
+ /** @psalm-pure */
public function __toString(): string
{
return $this->name;
diff --git a/src/Internal/PersistentSubscriptionUpdateStatus.php b/src/Internal/PersistentSubscriptionUpdateStatus.php
index 5d2eae26..e067e373 100644
--- a/src/Internal/PersistentSubscriptionUpdateStatus.php
+++ b/src/Internal/PersistentSubscriptionUpdateStatus.php
@@ -15,7 +15,10 @@
use Prooph\EventStore\Exception\InvalidArgumentException;
-/** @internal */
+/**
+ * @internal
+ * @psalm-immutable
+ */
class PersistentSubscriptionUpdateStatus
{
public const OPTIONS = [
@@ -58,35 +61,39 @@ public static function byName(string $value): self
throw new InvalidArgumentException('Unknown enum name given');
}
- return self::{$value}();
+ return new self($value);
}
- public static function byValue($value): self
+ public static function byValue(int $value): self
{
foreach (self::OPTIONS as $name => $v) {
if ($v === $value) {
- return self::{$name}();
+ return new self($name);
}
}
throw new InvalidArgumentException('Unknown enum value given');
}
+ /** @psalm-pure */
public function equals(PersistentSubscriptionUpdateStatus $other): bool
{
return \get_class($this) === \get_class($other) && $this->name === $other->name;
}
+ /** @psalm-pure */
public function name(): string
{
return $this->name;
}
- public function value()
+ /** @psalm-pure */
+ public function value(): int
{
return $this->value;
}
+ /** @psalm-pure */
public function __toString(): string
{
return $this->name;
diff --git a/src/LiveProcessingStartedOnCatchUpSubscription.php b/src/LiveProcessingStartedOnCatchUpSubscription.php
deleted file mode 100644
index e60aa76d..00000000
--- a/src/LiveProcessingStartedOnCatchUpSubscription.php
+++ /dev/null
@@ -1,19 +0,0 @@
-
- * (c) 2015-2020 Sascha-Oliver Prolic
- *
- * For the full copyright and license information, please view the LICENSE
- * file that was distributed with this source code.
- */
-
-declare(strict_types=1);
-
-namespace Prooph\EventStore;
-
-interface LiveProcessingStartedOnCatchUpSubscription
-{
- public function __invoke(EventStoreCatchUpSubscription $subscription): void;
-}
diff --git a/src/PersistentSubscriptionDropped.php b/src/PersistentSubscriptionDropped.php
deleted file mode 100644
index 7aa810d0..00000000
--- a/src/PersistentSubscriptionDropped.php
+++ /dev/null
@@ -1,25 +0,0 @@
-
- * (c) 2015-2020 Sascha-Oliver Prolic
- *
- * For the full copyright and license information, please view the LICENSE
- * file that was distributed with this source code.
- */
-
-declare(strict_types=1);
-
-namespace Prooph\EventStore;
-
-use Throwable;
-
-interface PersistentSubscriptionDropped
-{
- public function __invoke(
- EventStorePersistentSubscription $subscription,
- SubscriptionDropReason $reason,
- ?Throwable $exception = null
- ): void;
-}
diff --git a/src/PersistentSubscriptionNakEventAction.php b/src/PersistentSubscriptionNakEventAction.php
index da48df2a..59b9f0d5 100644
--- a/src/PersistentSubscriptionNakEventAction.php
+++ b/src/PersistentSubscriptionNakEventAction.php
@@ -15,6 +15,7 @@
use Prooph\EventStore\Exception\InvalidArgumentException;
+/** @psalm-immutable */
class PersistentSubscriptionNakEventAction
{
public const OPTIONS = [
@@ -76,35 +77,39 @@ public static function byName(string $value): self
throw new InvalidArgumentException('Unknown enum name given');
}
- return self::{$value}();
+ return new self($value);
}
- public static function byValue($value): self
+ public static function byValue(int $value): self
{
foreach (self::OPTIONS as $name => $v) {
if ($v === $value) {
- return self::{$name}();
+ return new self($name);
}
}
throw new InvalidArgumentException('Unknown enum value given');
}
+ /** @psalm-pure */
public function equals(PersistentSubscriptionNakEventAction $other): bool
{
return \get_class($this) === \get_class($other) && $this->name === $other->name;
}
+ /** @psalm-pure */
public function name(): string
{
return $this->name;
}
- public function value()
+ /** @psalm-pure */
+ public function value(): int
{
return $this->value;
}
+ /** @psalm-pure */
public function __toString(): string
{
return $this->name;
diff --git a/src/PersistentSubscriptions/PersistentSubscriptionConfigDetails.php b/src/PersistentSubscriptions/PersistentSubscriptionConfigDetails.php
index d312e850..a24b046c 100644
--- a/src/PersistentSubscriptions/PersistentSubscriptionConfigDetails.php
+++ b/src/PersistentSubscriptions/PersistentSubscriptionConfigDetails.php
@@ -13,7 +13,10 @@
namespace Prooph\EventStore\PersistentSubscriptions;
-/** @internal */
+/**
+ * @internal
+ * @psalm-immutable
+ */
final class PersistentSubscriptionConfigDetails
{
private bool $resolveLinktos;
@@ -31,97 +34,140 @@ final class PersistentSubscriptionConfigDetails
private string $namedConsumerStrategy;
private bool $preferRoundRobin;
- private function __construct()
- {
- }
-
+ private function __construct(
+ bool $resolveLinktos,
+ int $startFrom,
+ int $messageTimeoutMilliseconds,
+ bool $extraStatistics,
+ int $maxRetryCount,
+ int $liveBufferSize,
+ int $bufferSize,
+ int $readBatchSize,
+ int $checkPointAfterMilliseconds,
+ int $minCheckPointCount,
+ int $maxCheckPointCount,
+ int $maxSubscriberCount,
+ string $namedConsumerStrategy,
+ bool $preferRoundRobin
+ ) {
+ $this->resolveLinktos = $resolveLinktos;
+ $this->startFrom = $startFrom;
+ $this->messageTimeoutMilliseconds = $messageTimeoutMilliseconds;
+ $this->extraStatistics = $extraStatistics;
+ $this->maxRetryCount = $maxRetryCount;
+ $this->liveBufferSize = $liveBufferSize;
+ $this->bufferSize = $bufferSize;
+ $this->readBatchSize = $readBatchSize;
+ $this->checkPointAfterMilliseconds = $checkPointAfterMilliseconds;
+ $this->minCheckPointCount = $minCheckPointCount;
+ $this->maxCheckPointCount = $maxCheckPointCount;
+ $this->maxSubscriberCount = $maxSubscriberCount;
+ $this->namedConsumerStrategy = $namedConsumerStrategy;
+ $this->preferRoundRobin = $preferRoundRobin;
+ }
+
+ /**
+ * @param array $data
+ */
public static function fromArray(array $data): self
{
- $details = new self();
-
- $details->resolveLinktos = $data['resolveLinktos'];
- $details->startFrom = $data['startFrom'];
- $details->messageTimeoutMilliseconds = $data['messageTimeoutMilliseconds'];
- $details->extraStatistics = $data['extraStatistics'];
- $details->maxRetryCount = $data['maxRetryCount'];
- $details->liveBufferSize = $data['liveBufferSize'];
- $details->bufferSize = $data['bufferSize'];
- $details->readBatchSize = $data['readBatchSize'];
- $details->checkPointAfterMilliseconds = $data['checkPointAfterMilliseconds'];
- $details->minCheckPointCount = $data['minCheckPointCount'];
- $details->maxCheckPointCount = $data['maxCheckPointCount'];
- $details->maxSubscriberCount = $data['maxSubscriberCount'];
- $details->namedConsumerStrategy = $data['namedConsumerStrategy'];
- $details->preferRoundRobin = $data['preferRoundRobin'];
-
- return $details;
- }
-
+ return new self(
+ (bool) $data['resolveLinktos'],
+ (int) $data['startFrom'],
+ (int) $data['messageTimeoutMilliseconds'],
+ (bool) $data['extraStatistics'],
+ (int) $data['maxRetryCount'],
+ (int) $data['liveBufferSize'],
+ (int) $data['bufferSize'],
+ (int) $data['readBatchSize'],
+ (int) $data['checkPointAfterMilliseconds'],
+ (int) $data['minCheckPointCount'],
+ (int) $data['maxCheckPointCount'],
+ (int) $data['maxSubscriberCount'],
+ (string) $data['namedConsumerStrategy'],
+ (bool) $data['preferRoundRobin']
+ );
+ }
+
+ /** @psalm-pure */
public function resolveLinktos(): bool
{
return $this->resolveLinktos;
}
+ /** @psalm-pure */
public function startFrom(): int
{
return $this->startFrom;
}
+ /** @psalm-pure */
public function messageTimeoutMilliseconds(): int
{
return $this->messageTimeoutMilliseconds;
}
+ /** @psalm-pure */
public function extraStatistics(): bool
{
return $this->extraStatistics;
}
+ /** @psalm-pure */
public function maxRetryCount(): int
{
return $this->maxRetryCount;
}
+ /** @psalm-pure */
public function liveBufferSize(): int
{
return $this->liveBufferSize;
}
+ /** @psalm-pure */
public function bufferSize(): int
{
return $this->bufferSize;
}
+ /** @psalm-pure */
public function readBatchSize(): int
{
return $this->readBatchSize;
}
+ /** @psalm-pure */
public function checkPointAfterMilliseconds(): int
{
return $this->checkPointAfterMilliseconds;
}
+ /** @psalm-pure */
public function minCheckPointCount(): int
{
return $this->minCheckPointCount;
}
+ /** @psalm-pure */
public function maxCheckPointCount(): int
{
return $this->maxCheckPointCount;
}
+ /** @psalm-pure */
public function maxSubscriberCount(): int
{
return $this->maxSubscriberCount;
}
+ /** @psalm-pure */
public function namedConsumerStrategy(): string
{
return $this->namedConsumerStrategy;
}
+ /** @psalm-pure */
public function preferRoundRobin(): bool
{
return $this->preferRoundRobin;
diff --git a/src/PersistentSubscriptions/PersistentSubscriptionConnectionDetails.php b/src/PersistentSubscriptions/PersistentSubscriptionConnectionDetails.php
index 7ab94408..6bda2279 100644
--- a/src/PersistentSubscriptions/PersistentSubscriptionConnectionDetails.php
+++ b/src/PersistentSubscriptions/PersistentSubscriptionConnectionDetails.php
@@ -13,7 +13,10 @@
namespace Prooph\EventStore\PersistentSubscriptions;
-/** @internal */
+/**
+ * @internal
+ * @psalm-immutable
+ */
final class PersistentSubscriptionConnectionDetails
{
private string $from;
@@ -24,55 +27,78 @@ final class PersistentSubscriptionConnectionDetails
private int $availableSlots;
private int $inFlightMessages;
- private function __construct()
- {
+ private function __construct(
+ string $from,
+ string $username,
+ float $averageItemsPerSecond,
+ int $totalItemsProcessed,
+ int $countSinceLastMeasurement,
+ int $availableSlots,
+ int $inFlightMessages
+ ) {
+ $this->from = $from;
+ $this->username = $username;
+ $this->averageItemsPerSecond = $averageItemsPerSecond;
+ $this->totalItemsProcessed = $totalItemsProcessed;
+ $this->countSinceLastMeasurement = $countSinceLastMeasurement;
+ $this->availableSlots = $availableSlots;
+ $this->inFlightMessages = $inFlightMessages;
}
+ /**
+ * @param array $data
+ * @psalm-pure
+ */
public static function fromArray(array $data): self
{
- $details = new self();
-
- $details->from = $data['from'];
- $details->username = $data['username'];
- $details->averageItemsPerSecond = $data['averageItemsPerSecond'];
- $details->totalItemsProcessed = $data['totalItemsProcessed'];
- $details->countSinceLastMeasurement = $data['countSinceLastMeasurement'];
- $details->availableSlots = $data['availableSlots'];
- $details->inFlightMessages = $data['inFlightMessages'];
-
- return $details;
+ return new self(
+ (string) $data['from'],
+ (string) $data['username'],
+ (float) $data['averageItemsPerSecond'],
+ (int) $data['totalItemsProcessed'],
+ (int) $data['countSinceLastMeasurement'],
+ (int) $data['availableSlots'],
+ (int) $data['inFlightMessages'],
+ );
}
+ /** @psalm-pure */
public function from(): string
{
return $this->from;
}
+ /** @psalm-pure */
public function username(): string
{
return $this->username;
}
+ /** @psalm-pure */
public function averageItemsPerSecond(): float
{
return $this->averageItemsPerSecond;
}
+ /** @psalm-pure */
public function totalItemsProcessed(): int
{
return $this->totalItemsProcessed;
}
+ /** @psalm-pure */
public function countSinceLastMeasurement(): int
{
return $this->countSinceLastMeasurement;
}
+ /** @psalm-pure */
public function availableSlots(): int
{
return $this->availableSlots;
}
+ /** @psalm-pure */
public function inFlightMessages(): int
{
return $this->inFlightMessages;
diff --git a/src/PersistentSubscriptions/PersistentSubscriptionDetails.php b/src/PersistentSubscriptions/PersistentSubscriptionDetails.php
index e1c1d877..91886f7a 100644
--- a/src/PersistentSubscriptions/PersistentSubscriptionDetails.php
+++ b/src/PersistentSubscriptions/PersistentSubscriptionDetails.php
@@ -13,15 +13,16 @@
namespace Prooph\EventStore\PersistentSubscriptions;
+/** @psalm-immutable */
final class PersistentSubscriptionDetails
{
/**
*
* Only populated when retrieved via PersistentSubscriptionsManager::describe() method.
*/
- private PersistentSubscriptionConfigDetails $config;
+ private ?PersistentSubscriptionConfigDetails $config;
/**
- * @var PersistentSubscriptionConfigDetails[]
+ * @var list
*
* Only populated when retrieved via PersistentSubscriptionsManager::describe() method.
*/
@@ -42,124 +43,186 @@ final class PersistentSubscriptionDetails
private string $parkedMessageUri;
private string $getMessagesUri;
- private function __construct()
- {
+ /**
+ * @param list $connections
+ */
+ private function __construct(
+ ?PersistentSubscriptionConfigDetails $config,
+ array $connections,
+ string $eventStreamId,
+ string $groupName,
+ string $status,
+ float $averageItemsPerSecond,
+ int $totalItemsProcessed,
+ int $countSinceLastMeasurement,
+ int $lastProcessedEventNumber,
+ int $lastKnownEventNumber,
+ int $readBufferCount,
+ int $liveBufferCount,
+ int $retryBufferCount,
+ int $totalInFlightMessages,
+ int $connectionCount,
+ string $parkedMessageUri,
+ string $getMessagesUri
+ ) {
+ $this->config = $config;
+ $this->connections = $connections;
+ $this->eventStreamId = $eventStreamId;
+ $this->groupName = $groupName;
+ $this->status = $status;
+ $this->averageItemsPerSecond = $averageItemsPerSecond;
+ $this->totalItemsProcessed = $totalItemsProcessed;
+ $this->countSinceLastMeasurement = $countSinceLastMeasurement;
+ $this->lastProcessedEventNumber = $lastProcessedEventNumber;
+ $this->lastKnownEventNumber = $lastKnownEventNumber;
+ $this->readBufferCount = $readBufferCount;
+ $this->liveBufferCount = $liveBufferCount;
+ $this->retryBufferCount = $retryBufferCount;
+ $this->totalInFlightMessages = $totalInFlightMessages;
+ $this->connectionCount = $connectionCount;
+ $this->parkedMessageUri = $parkedMessageUri;
+ $this->getMessagesUri = $getMessagesUri;
}
public static function fromArray(array $data): self
{
- $details = new self();
+ $config = null;
if (isset($data['config'])) {
- $details->config = PersistentSubscriptionConfigDetails::fromArray($data['config']);
+ /** @var array $data['config'] */
+ $config = PersistentSubscriptionConfigDetails::fromArray($data['config']);
}
+ $connections = [];
+
if (isset($data['connections'])) {
+ /** @var array $connection */
foreach ($data['connections'] as $connection) {
- $details->connections[] = PersistentSubscriptionConnectionDetails::fromArray($connection);
+ $connections[] = PersistentSubscriptionConnectionDetails::fromArray($connection);
}
}
- $details->eventStreamId = $data['eventStreamId'];
- $details->groupName = $data['groupName'];
- $details->status = $data['status'];
- $details->averageItemsPerSecond = $data['averageItemsPerSecond'];
- $details->totalItemsProcessed = $data['totalItemsProcessed'];
- $details->countSinceLastMeasurement = $data['countSinceLastMeasurement'] ?? 0;
- $details->lastProcessedEventNumber = $data['lastProcessedEventNumber'];
- $details->lastKnownEventNumber = $data['lastKnownEventNumber'];
- $details->readBufferCount = $data['readBufferCount'] ?? 0;
- $details->liveBufferCount = $data['liveBufferCount'] ?? 0;
- $details->retryBufferCount = $data['retryBufferCount'] ?? 0;
- $details->totalInFlightMessages = $data['totalInFlightMessages'];
- $details->parkedMessageUri = $data['parkedMessageUri'];
- $details->getMessagesUri = $data['getMessagesUri'];
- $details->connectionCount = $data['connectionCount'] ?? 0;
-
- return $details;
- }
-
- public function config(): PersistentSubscriptionConfigDetails
+ return new self(
+ $config,
+ $connections,
+ (string) $data['eventStreamId'],
+ (string) $data['groupName'],
+ (string) $data['status'],
+ (float) $data['averageItemsPerSecond'],
+ (int) $data['totalItemsProcessed'],
+ (int) ($data['countSinceLastMeasurement'] ?? 0),
+ (int) $data['lastProcessedEventNumber'],
+ (int) $data['lastKnownEventNumber'],
+ (int) ($data['readBufferCount'] ?? 0),
+ (int) ($data['liveBufferCount'] ?? 0),
+ (int) ($data['retryBufferCount'] ?? 0),
+ (int) $data['totalInFlightMessages'],
+ (int) ($data['connectionCount'] ?? 0),
+ (string) $data['parkedMessageUri'],
+ (string) $data['getMessagesUri']
+ );
+ }
+
+ /** @psalm-pure */
+ public function config(): ?PersistentSubscriptionConfigDetails
{
return $this->config;
}
- /** @return PersistentSubscriptionConfigDetails[] */
+ /**
+ * @return list
+ * @psalm-pure
+ */
public function connections(): array
{
return $this->connections;
}
+ /** @psalm-pure */
public function eventStreamId(): string
{
return $this->eventStreamId;
}
+ /** @psalm-pure */
public function groupName(): string
{
return $this->groupName;
}
+ /** @psalm-pure */
public function status(): string
{
return $this->status;
}
+ /** @psalm-pure */
public function averageItemsPerSecond(): float
{
return $this->averageItemsPerSecond;
}
+ /** @psalm-pure */
public function totalItemsProcessed(): int
{
return $this->totalItemsProcessed;
}
+ /** @psalm-pure */
public function countSinceLastMeasurement(): int
{
return $this->countSinceLastMeasurement;
}
+ /** @psalm-pure */
public function lastProcessedEventNumber(): int
{
return $this->lastProcessedEventNumber;
}
+ /** @psalm-pure */
public function lastKnownEventNumber(): int
{
return $this->lastKnownEventNumber;
}
+ /** @psalm-pure */
public function readBufferCount(): int
{
return $this->readBufferCount;
}
+ /** @psalm-pure */
public function liveBufferCount(): int
{
return $this->liveBufferCount;
}
+ /** @psalm-pure */
public function retryBufferCount(): int
{
return $this->retryBufferCount;
}
+ /** @psalm-pure */
public function totalInFlightMessages(): int
{
return $this->totalInFlightMessages;
}
+ /** @psalm-pure */
public function connectionCount(): int
{
return $this->connectionCount;
}
+ /** @psalm-pure */
public function parkedMessageUri(): string
{
return $this->parkedMessageUri;
}
+ /** @psalm-pure */
public function getMessagesUri(): string
{
return $this->getMessagesUri;
diff --git a/src/PersistentSubscriptions/PersistentSubscriptionsManager.php b/src/PersistentSubscriptions/PersistentSubscriptionsManager.php
index 4ecbf3f4..2071d811 100644
--- a/src/PersistentSubscriptions/PersistentSubscriptionsManager.php
+++ b/src/PersistentSubscriptions/PersistentSubscriptionsManager.php
@@ -30,9 +30,7 @@ public function replayParkedMessages(
): void;
/**
- * @param null|string $stream
- * @param null|UserCredentials $userCredentials
- * @return PersistentSubscriptionDetails[]
+ * @return list
*/
public function list(?string $stream = null, ?UserCredentials $userCredentials = null): array;
}
diff --git a/src/Position.php b/src/Position.php
index 4fbf87b0..33e5b14c 100644
--- a/src/Position.php
+++ b/src/Position.php
@@ -17,6 +17,8 @@
/**
* Transaction File Position
+ *
+ * @psalm-immutable
*/
class Position
{
@@ -62,49 +64,58 @@ public static function parse(string $string): Position
return new Position($commitPosition, $preparePosition);
}
+ /** @psalm-pure */
public function commitPosition(): int
{
return $this->commitPosition;
}
+ /** @psalm-pure */
public function preparePosition(): int
{
return $this->preparePosition;
}
+ /** @psalm-pure */
public function asString(): string
{
return \substr('000000000000000' . \dechex($this->commitPosition), -16)
. \substr('000000000000000' . \dechex($this->preparePosition), -16);
}
+ /** @psalm-pure */
public function __toString(): string
{
return 'C:' . $this->commitPosition . '/P:' . $this->preparePosition;
}
+ /** @psalm-pure */
public function equals(Position $other): bool
{
return $this->commitPosition === $other->commitPosition && $this->preparePosition === $other->preparePosition;
}
+ /** @psalm-pure */
public function greater(Position $other): bool
{
return $this->commitPosition > $other->commitPosition
|| ($this->commitPosition === $other->commitPosition && $this->preparePosition > $other->preparePosition);
}
+ /** @psalm-pure */
public function smaller(Position $other): bool
{
return $this->commitPosition < $other->commitPosition
|| ($this->commitPosition === $other->commitPosition && $this->preparePosition < $other->preparePosition);
}
+ /** @psalm-pure */
public function greaterOrEquals(Position $other): bool
{
return $this->greater($other) || $this->equals($other);
}
+ /** @psalm-pure */
public function smallerOrEquals(Position $other): bool
{
return $this->smaller($other) || $this->equals($other);
diff --git a/src/Projections/ProjectionDetails.php b/src/Projections/ProjectionDetails.php
index b3ef0b4e..2f997a45 100644
--- a/src/Projections/ProjectionDetails.php
+++ b/src/Projections/ProjectionDetails.php
@@ -13,6 +13,7 @@
namespace Prooph\EventStore\Projections;
+/** @psalm-immutable */
final class ProjectionDetails
{
private int $coreProcessingTime;
@@ -95,126 +96,151 @@ public function __construct(
$this->writePendingEventsAfterCheckpoint = $writePendingEventsAfterCheckpoint;
}
+ /** @psalm-pure */
public function coreProcessingTime(): int
{
return $this->coreProcessingTime;
}
+ /** @psalm-pure */
public function version(): int
{
return $this->version;
}
+ /** @psalm-pure */
public function epoch(): int
{
return $this->epoch;
}
+ /** @psalm-pure */
public function effectiveName(): string
{
return $this->effectiveName;
}
+ /** @psalm-pure */
public function writesInProgress(): int
{
return $this->writesInProgress;
}
+ /** @psalm-pure */
public function readsInProgress(): int
{
return $this->readsInProgress;
}
+ /** @psalm-pure */
public function partitionsCached(): int
{
return $this->partitionsCached;
}
+ /** @psalm-pure */
public function status(): string
{
return $this->status;
}
+ /** @psalm-pure */
public function stateReason(): ?string
{
return $this->stateReason;
}
+ /** @psalm-pure */
public function name(): string
{
return $this->name;
}
+ /** @psalm-pure */
public function mode(): string
{
return $this->mode;
}
+ /** @psalm-pure */
public function position(): string
{
return $this->position;
}
+ /** @psalm-pure */
public function progress(): float
{
return $this->progress;
}
+ /** @psalm-pure */
public function lastCheckpoint(): ?string
{
return $this->lastCheckpoint;
}
+ /** @psalm-pure */
public function eventsProcessedAfterRestart(): int
{
return $this->eventsProcessedAfterRestart;
}
+ /** @psalm-pure */
public function statusUrl(): string
{
return $this->statusUrl;
}
+ /** @psalm-pure */
public function stateUrl(): string
{
return $this->stateUrl;
}
+ /** @psalm-pure */
public function resultUrl(): string
{
return $this->resultUrl;
}
+ /** @psalm-pure */
public function queryUrl(): string
{
return $this->queryUrl;
}
+ /** @psalm-pure */
public function enableCommandUrl(): string
{
return $this->enableCommandUrl;
}
+ /** @psalm-pure */
public function disableCommandUrl(): string
{
return $this->disableCommandUrl;
}
+ /** @psalm-pure */
public function checkpointStatus(): ?string
{
return $this->checkpointStatus;
}
+ /** @psalm-pure */
public function bufferedEvents(): int
{
return $this->bufferedEvents;
}
+ /** @psalm-pure */
public function writePendingEventsBeforeCheckpoint(): int
{
return $this->writePendingEventsBeforeCheckpoint;
}
+ /** @psalm-pure */
public function writePendingEventsAfterCheckpoint(): int
{
return $this->writePendingEventsAfterCheckpoint;
diff --git a/src/Projections/ProjectionsManager.php b/src/Projections/ProjectionsManager.php
index 3ef0ed95..d42c6381 100644
--- a/src/Projections/ProjectionsManager.php
+++ b/src/Projections/ProjectionsManager.php
@@ -65,21 +65,21 @@ public function createContinuous(
/**
* Synchronously lists all projections
*
- * @return ProjectionDetails[]
+ * @return list
*/
public function listAll(?UserCredentials $userCredentials = null): array;
/**
* Synchronously lists all one-time projections
*
- * @return ProjectionDetails[]
+ * @return list
*/
public function listOneTime(?UserCredentials $userCredentials = null): array;
/**
* Synchronously lists this status of all continuous projections
*
- * @return ProjectionDetails[]
+ * @return list
*/
public function listContinuous(?UserCredentials $userCredentials = null): array;
diff --git a/src/Projections/QueryManager.php b/src/Projections/QueryManager.php
index b27b943f..6cf65ab5 100644
--- a/src/Projections/QueryManager.php
+++ b/src/Projections/QueryManager.php
@@ -23,15 +23,6 @@ interface QueryManager
* Creates a new transient projection and polls its status until it is Completed
*
* returns String of JSON containing query result
- *
- * @param string $name A name for the query
- * @param string $query The source code for the query
- * @param int $initialPollingDelay Initial time to wait between polling for projection status
- * @param int $maximumPollingDelay Maximum time to wait between polling for projection status
- * @param string $type The type to use, defaults to JS
- * @param UserCredentials|null $userCredentials Credentials for a user with permission to create a query
- *
- * @return string
*/
public function execute(
string $name,
diff --git a/src/ReadDirection.php b/src/ReadDirection.php
index e767057a..7383117e 100644
--- a/src/ReadDirection.php
+++ b/src/ReadDirection.php
@@ -15,6 +15,7 @@
use Prooph\EventStore\Exception\InvalidArgumentException;
+/** @psalm-immutable */
class ReadDirection
{
public const OPTIONS = [
@@ -50,14 +51,14 @@ public static function byName(string $value): self
throw new InvalidArgumentException('Unknown enum name given');
}
- return self::{$value}();
+ return new self($value);
}
- public static function byValue($value): self
+ public static function byValue(int $value): self
{
foreach (self::OPTIONS as $name => $v) {
if ($v === $value) {
- return self::{$name}();
+ return new self($name);
}
}
@@ -69,16 +70,19 @@ public function equals(ReadDirection $other): bool
return \get_class($this) === \get_class($other) && $this->name === $other->name;
}
+ /** @psalm-pure */
public function name(): string
{
return $this->name;
}
- public function value()
+ /** @psalm-pure */
+ public function value(): int
{
return $this->value;
}
+ /** @psalm-pure */
public function __toString(): string
{
return $this->name;
diff --git a/src/RecordedEvent.php b/src/RecordedEvent.php
index 202a3cb8..08d5d31d 100644
--- a/src/RecordedEvent.php
+++ b/src/RecordedEvent.php
@@ -15,6 +15,7 @@
use DateTimeImmutable;
+/** @psalm-immutable */
class RecordedEvent
{
protected string $eventStreamId;
@@ -47,41 +48,49 @@ public function __construct(
$this->created = $created;
}
+ /** @psalm-pure */
public function eventStreamId(): string
{
return $this->eventStreamId;
}
+ /** @psalm-pure */
public function eventNumber(): int
{
return $this->eventNumber;
}
+ /** @psalm-pure */
public function eventId(): EventId
{
return $this->eventId;
}
+ /** @psalm-pure */
public function eventType(): string
{
return $this->eventType;
}
+ /** @psalm-pure */
public function isJson(): bool
{
return $this->isJson;
}
+ /** @psalm-pure */
public function data(): string
{
return $this->data;
}
+ /** @psalm-pure */
public function metadata(): string
{
return $this->metadata;
}
+ /** @psalm-pure */
public function created(): DateTimeImmutable
{
return $this->created;
diff --git a/src/ResolvedEvent.php b/src/ResolvedEvent.php
index a503b40e..dbfd4c89 100644
--- a/src/ResolvedEvent.php
+++ b/src/ResolvedEvent.php
@@ -17,6 +17,8 @@
/**
* A structure representing a single event or a resolved link event.
+ *
+ * @psalm-immutable
*/
class ResolvedEvent implements InternalResolvedEvent
{
@@ -53,38 +55,45 @@ public function __construct(?RecordedEvent $event, ?RecordedEvent $link, ?Positi
$this->originalPosition = $originalPosition;
}
+ /** @psalm-pure */
public function event(): ?RecordedEvent
{
return $this->event;
}
+ /** @psalm-pure */
public function link(): ?RecordedEvent
{
return $this->link;
}
+ /** @psalm-pure */
public function originalEvent(): ?RecordedEvent
{
return $this->originalEvent;
}
+ /** @psalm-pure */
public function isResolved(): bool
{
return $this->isResolved;
}
+ /** @psalm-pure */
public function originalPosition(): ?Position
{
return $this->originalPosition;
}
+ /** @psalm-pure */
public function originalStreamName(): string
{
- return $this->originalEvent->eventStreamId();
+ return null !== $this->originalEvent ? $this->originalEvent->eventStreamId() : '';
}
+ /** @psalm-pure */
public function originalEventNumber(): int
{
- return $this->originalEvent->eventNumber();
+ return null !== $this->originalEvent ? $this->originalEvent->eventNumber() : 0;
}
}
diff --git a/src/SliceReadStatus.php b/src/SliceReadStatus.php
index e80a095b..3089d2a7 100644
--- a/src/SliceReadStatus.php
+++ b/src/SliceReadStatus.php
@@ -15,6 +15,7 @@
use Prooph\EventStore\Exception\InvalidArgumentException;
+/** @psalm-immutable */
class SliceReadStatus
{
public const OPTIONS = [
@@ -57,14 +58,14 @@ public static function byName(string $value): self
throw new InvalidArgumentException('Unknown enum name given');
}
- return self::{$value}();
+ return new self($value);
}
- public static function byValue($value): self
+ public static function byValue(int $value): self
{
foreach (self::OPTIONS as $name => $v) {
if ($v === $value) {
- return self::{$name}();
+ return new self($name);
}
}
@@ -76,16 +77,19 @@ public function equals(SliceReadStatus $other): bool
return \get_class($this) === \get_class($other) && $this->name === $other->name;
}
+ /** @psalm-pure */
public function name(): string
{
return $this->name;
}
- public function value()
+ /** @psalm-pure */
+ public function value(): int
{
return $this->value;
}
+ /** @psalm-pure */
public function __toString(): string
{
return $this->name;
diff --git a/src/StreamAcl.php b/src/StreamAcl.php
index 13e6f661..be996741 100644
--- a/src/StreamAcl.php
+++ b/src/StreamAcl.php
@@ -14,36 +14,42 @@
namespace Prooph\EventStore;
use Prooph\EventStore\Common\SystemMetadata;
-use Prooph\EventStore\Exception\InvalidArgumentException;
class StreamAcl
{
/**
* Roles and users permitted to read the stream
- * @var string[]
+ * @var list
*/
private array $readRoles;
/**
* Roles and users permitted to write to the stream
- * @var string[]
+ * @var list
*/
private array $writeRoles;
/**
* Roles and users permitted to delete the stream
- * @var string[]
+ * @var list
*/
private array $deleteRoles;
/**
* Roles and users permitted to read stream metadata
- * @var string[]
+ * @var list
*/
private array $metaReadRoles;
/**
* Roles and users permitted to write stream metadata
- * @var string[]
+ * @var list
*/
private array $metaWriteRoles;
+ /**
+ * @param list $readRoles
+ * @param list $writeRoles
+ * @param list $deleteRoles
+ * @param list $metaReadRoles
+ * @param list $metaWriteRoles
+ */
public function __construct(
array $readRoles = [],
array $writeRoles = [],
@@ -51,20 +57,6 @@ public function __construct(
array $metaReadRoles = [],
array $metaWriteRoles = []
) {
- $check = function (array $data): void {
- foreach ($data as $value) {
- if (! \is_string($value)) {
- throw new InvalidArgumentException('Invalid roles given, expected an array of strings');
- }
- }
- };
-
- $check($readRoles);
- $check($writeRoles);
- $check($deleteRoles);
- $check($metaReadRoles);
- $check($metaWriteRoles);
-
$this->readRoles = $readRoles;
$this->writeRoles = $writeRoles;
$this->deleteRoles = $deleteRoles;
@@ -73,7 +65,7 @@ public function __construct(
}
/**
- * @return string[]
+ * @return list
*/
public function readRoles(): array
{
@@ -81,7 +73,7 @@ public function readRoles(): array
}
/**
- * @return string[]
+ * @return list
*/
public function writeRoles(): array
{
@@ -89,7 +81,7 @@ public function writeRoles(): array
}
/**
- * @return string[]
+ * @return list
*/
public function deleteRoles(): array
{
@@ -97,7 +89,7 @@ public function deleteRoles(): array
}
/**
- * @return string[]
+ * @return list
*/
public function metaReadRoles(): array
{
@@ -105,7 +97,7 @@ public function metaReadRoles(): array
}
/**
- * @return string[]
+ * @return list
*/
public function metaWriteRoles(): array
{
@@ -139,6 +131,9 @@ public function toArray(): array
return $data;
}
+ /**
+ * @param array> $data
+ */
public static function fromArray(array $data): StreamAcl
{
return new self(
@@ -150,6 +145,14 @@ public static function fromArray(array $data): StreamAcl
);
}
+ /**
+ * @return list|string|null
+ *
+ * @psalm-pure
+ * @psalm-suppress MixedInferredReturnType
+ * @psalm-suppress MixedReturnStatement
+ * @psalm-suppress MixedReturnTypeCoercion
+ */
private function exportRoles(?array $roles)
{
if (null === $roles
diff --git a/src/StreamEventsSlice.php b/src/StreamEventsSlice.php
index 071fd15a..15ca6c34 100644
--- a/src/StreamEventsSlice.php
+++ b/src/StreamEventsSlice.php
@@ -13,19 +13,24 @@
namespace Prooph\EventStore;
+/** @psalm-immutable */
class StreamEventsSlice
{
private SliceReadStatus $status;
private string $stream;
private int $fromEventNumber;
private ReadDirection $readDirection;
- /** @var ResolvedEvent[] */
+ /** @var list */
private array $events;
private int $nextEventNumber;
private int $lastEventNumber;
private bool $isEndOfStream;
- /** @internal */
+ /**
+ * @internal
+ *
+ * @param list $events
+ */
public function __construct(
SliceReadStatus $status,
string $stream,
@@ -46,44 +51,53 @@ public function __construct(
$this->isEndOfStream = $isEndOfStream;
}
+ /** @psalm-pure */
public function status(): SliceReadStatus
{
return $this->status;
}
+ /** @psalm-pure */
public function stream(): string
{
return $this->stream;
}
+ /** @psalm-pure */
public function fromEventNumber(): int
{
return $this->fromEventNumber;
}
+ /** @psalm-pure */
public function readDirection(): ReadDirection
{
return $this->readDirection;
}
/**
- * @return ResolvedEvent[]
+ * @return list
+ *
+ * @psalm-pure
*/
public function events(): array
{
return $this->events;
}
+ /** @psalm-pure */
public function nextEventNumber(): int
{
return $this->nextEventNumber;
}
+ /** @psalm-pure */
public function lastEventNumber(): int
{
return $this->lastEventNumber;
}
+ /** @psalm-pure */
public function isEndOfStream(): bool
{
return $this->isEndOfStream;
diff --git a/src/StreamMetadata.php b/src/StreamMetadata.php
index 382c5223..3dc9142e 100644
--- a/src/StreamMetadata.php
+++ b/src/StreamMetadata.php
@@ -44,9 +44,13 @@ class StreamMetadata implements JsonSerializable
private ?StreamAcl $acl;
/**
* key => value pairs of custom metadata
+ * @var array
*/
private array $customMetadata;
+ /**
+ * @param array $customMetadata
+ */
public function __construct(
?int $maxCount = null,
?int $maxAge = null,
@@ -71,12 +75,6 @@ public function __construct(
throw new InvalidArgumentException('Cache control should be positive value');
}
- foreach ($customMetadata as $key => $value) {
- if (! \is_string($key)) {
- throw new InvalidArgumentException('CustomMetadata key must be a string');
- }
- }
-
$this->maxCount = $maxCount;
$this->maxAge = $maxAge;
$this->truncateBefore = $truncateBefore;
@@ -116,7 +114,7 @@ public function acl(): ?StreamAcl
}
/**
- * @return array
+ * @return array
*/
public function customMetadata(): array
{
@@ -124,7 +122,6 @@ public function customMetadata(): array
}
/**
- * @param string $key
* @return mixed
*/
public function getValue(string $key)
@@ -164,6 +161,7 @@ public function jsonSerialize(): object
}
}
+ /** @psalm-suppress MixedAssignment */
foreach ($this->customMetadata as $key => $value) {
$object->{$key} = $value;
}
@@ -171,6 +169,11 @@ public function jsonSerialize(): object
return $object;
}
+ /**
+ * @psalm-suppress PossiblyInvalidArgument
+ * @psalm-suppress MixedArgument
+ * @psalm-suppress MixedAssignment
+ */
public static function createFromArray(array $data): StreamMetadata
{
$internals = [
@@ -186,6 +189,7 @@ public static function createFromArray(array $data): StreamMetadata
if (\in_array($key, $internals, true)) {
$params[$key] = $value;
} elseif ($key === SystemMetadata::ACL) {
+ /** @var array> $value */
$params[SystemMetadata::ACL] = StreamAcl::fromArray($value);
} else {
$params['customMetadata'][$key] = $value;
diff --git a/src/StreamMetadataBuilder.php b/src/StreamMetadataBuilder.php
index 520893d2..a6a0c2bf 100644
--- a/src/StreamMetadataBuilder.php
+++ b/src/StreamMetadataBuilder.php
@@ -21,13 +21,27 @@ class StreamMetadataBuilder
private ?int $maxAge;
private ?int $truncateBefore;
private ?int $cacheControl;
+ /** @var list */
private array $aclRead;
+ /** @var list */
private array $aclWrite;
+ /** @var list */
private array $aclDelete;
+ /** @var list */
private array $aclMetaRead;
+ /** @var list */
private array $aclMetaWrite;
+ /** @var array */
private array $customMetadata;
+ /**
+ * @param list $aclRead
+ * @param list $aclWrite
+ * @param list $aclDelete
+ * @param list $aclMetaRead
+ * @param list $aclMetaWrite
+ * @param array $customMetadata
+ */
public function __construct(
?int $maxCount = null,
?int $maxAge = null,
@@ -54,11 +68,11 @@ public function __construct(
public function build(): StreamMetadata
{
- $acl = null === $this->aclRead
- && null === $this->aclWrite
- && null === $this->aclDelete
- && null === $this->aclMetaRead
- && null === $this->aclMetaWrite
+ $acl = empty($this->aclRead)
+ && empty($this->aclWrite)
+ && empty($this->aclDelete)
+ && empty($this->aclMetaRead)
+ && empty($this->aclMetaWrite)
? null
: new StreamAcl($this->aclRead, $this->aclWrite, $this->aclDelete, $this->aclMetaRead, $this->aclMetaWrite);
@@ -160,6 +174,9 @@ public function setMetadataWriteRoles(string ...$metaWriteRoles): StreamMetadata
return $this;
}
+ /**
+ * @param mixed $value
+ */
public function setCustomProperty(string $key, $value): StreamMetadataBuilder
{
$this->customMetadata[$key] = $value;
diff --git a/src/SubscriptionDropReason.php b/src/SubscriptionDropReason.php
index 41030b64..44069fb8 100644
--- a/src/SubscriptionDropReason.php
+++ b/src/SubscriptionDropReason.php
@@ -15,6 +15,7 @@
use Prooph\EventStore\Exception\InvalidArgumentException;
+/** @psalm-immutable */
class SubscriptionDropReason
{
public const OPTIONS = [
@@ -127,35 +128,39 @@ public static function byName(string $value): self
throw new InvalidArgumentException('Unknown enum name given');
}
- return self::{$value}();
+ return new self($value);
}
- public static function byValue($value): self
+ public static function byValue(int $value): self
{
foreach (self::OPTIONS as $name => $v) {
if ($v === $value) {
- return self::{$name}();
+ return new self($name);
}
}
throw new InvalidArgumentException('Unknown enum value given');
}
+ /** @psalm-pure */
public function equals(SubscriptionDropReason $other): bool
{
return \get_class($this) === \get_class($other) && $this->name === $other->name;
}
+ /** @psalm-pure */
public function name(): string
{
return $this->name;
}
- public function value()
+ /** @psalm-pure */
+ public function value(): int
{
return $this->value;
}
+ /** @psalm-pure */
public function __toString(): string
{
return $this->name;
diff --git a/src/SubscriptionDropped.php b/src/SubscriptionDropped.php
deleted file mode 100644
index 623aafa4..00000000
--- a/src/SubscriptionDropped.php
+++ /dev/null
@@ -1,25 +0,0 @@
-
- * (c) 2015-2020 Sascha-Oliver Prolic
- *
- * For the full copyright and license information, please view the LICENSE
- * file that was distributed with this source code.
- */
-
-declare(strict_types=1);
-
-namespace Prooph\EventStore;
-
-use Throwable;
-
-interface SubscriptionDropped
-{
- public function __invoke(
- EventStoreSubscription $subscription,
- SubscriptionDropReason $reason,
- ?Throwable $exception = null
- ): void;
-}
diff --git a/src/SystemSettings.php b/src/SystemSettings.php
index de2fc134..faa542ae 100644
--- a/src/SystemSettings.php
+++ b/src/SystemSettings.php
@@ -82,6 +82,7 @@ public function jsonSerialize(): object
public static function createFromArray(array $data): SystemSettings
{
+ /** @var array>> $data */
return new self(
isset($data[SystemMetadata::USER_STREAM_ACL])
? StreamAcl::fromArray($data[SystemMetadata::USER_STREAM_ACL])
diff --git a/src/Transport/Http/EndpointExtensions.php b/src/Transport/Http/EndpointExtensions.php
index ba83ed99..4368946e 100644
--- a/src/Transport/Http/EndpointExtensions.php
+++ b/src/Transport/Http/EndpointExtensions.php
@@ -38,7 +38,7 @@ public static function formatStringToHttpUrl(
EndPoint $endPoint,
string $schema,
string $formatString,
- ...$args
+ string ...$args
): string {
return self::createHttpUrl(
$schema,
diff --git a/src/UserManagement/RelLink.php b/src/UserManagement/RelLink.php
index 6659f1ab..62100903 100644
--- a/src/UserManagement/RelLink.php
+++ b/src/UserManagement/RelLink.php
@@ -13,6 +13,9 @@
namespace Prooph\EventStore\UserManagement;
+/**
+ * @psalm-immutable
+ */
class RelLink
{
private string $href;
@@ -24,11 +27,13 @@ public function __construct(string $href, string $rel)
$this->rel = $rel;
}
+ /** @psalm-pure */
public function href(): string
{
return $this->href;
}
+ /** @psalm-pure */
public function rel(): string
{
return $this->rel;
diff --git a/src/UserManagement/UserCreationInformation.php b/src/UserManagement/UserCreationInformation.php
index dd8d67a3..385e9d54 100644
--- a/src/UserManagement/UserCreationInformation.php
+++ b/src/UserManagement/UserCreationInformation.php
@@ -20,10 +20,13 @@ final class UserCreationInformation implements JsonSerializable
{
private string $loginName;
private string $fullName;
- /** @var string[] */
+ /** @var list */
private array $groups;
private string $password;
+ /**
+ * @param list $groups
+ */
public function __construct(string $loginName, string $fullName, array $groups, string $password)
{
$this->loginName = $loginName;
diff --git a/src/UserManagement/UserDetails.php b/src/UserManagement/UserDetails.php
index 73af7dec..fe4a5244 100644
--- a/src/UserManagement/UserDetails.php
+++ b/src/UserManagement/UserDetails.php
@@ -17,79 +17,112 @@
use Prooph\EventStore\Exception\RuntimeException;
use Prooph\EventStore\Util\DateTime;
-/** @internal */
+/** @psalm-immutable */
final class UserDetails
{
private string $loginName;
private string $fullName;
- /** @var string[] */
+ /** @var list */
private array $groups = [];
private ?DateTimeImmutable $dateLastUpdated = null;
private bool $disabled;
- /** @var RelLink[] */
+ /** @var list */
private array $links = [];
- private function __construct()
+ /**
+ * @param list $groups
+ * @param list $links
+ */
+ private function __construct(
+ string $loginName,
+ string $fullName,
+ array $groups,
+ ?DateTimeImmutable $dateLastUpdated,
+ bool $disabled,
+ array $links)
{
+ $this->loginName = $loginName;
+ $this->fullName = $fullName;
+ $this->groups = $groups;
+ $this->dateLastUpdated = $dateLastUpdated;
+ $this->disabled = $disabled;
+ $this->links = $links;
}
+ /** @internal */
public static function fromArray(array $data): self
{
- $details = new self();
-
- $details->loginName = $data['loginName'];
- $details->fullName = $data['fullName'];
- $details->groups = $data['groups'];
- $details->disabled = $data['disabled'];
-
- $details->dateLastUpdated = isset($data['dateLastUpdated'])
- ? DateTime::create($data['dateLastUpdated'])
+ $dateLastUpdated = isset($data['dateLastUpdated'])
+ ? DateTime::create((string) $data['dateLastUpdated'])
: null;
$links = [];
+
if (isset($data['links'])) {
+ /** @var list> $data['links'] */
foreach ($data['links'] as $link) {
- $links[] = new RelLink($link['href'], $link['rel']);
+ $links[] = new RelLink((string) $link['href'], (string) $link['rel']);
}
}
- $details->links = $links;
- return $details;
+ /** @var list $data['groups'] */
+
+ return new self(
+ (string) $data['loginName'],
+ (string) $data['fullName'],
+ $data['groups'],
+ $dateLastUpdated,
+ (bool) $data['disabled'],
+ $links
+ );
}
+ /** @psalm-pure */
public function loginName(): string
{
return $this->loginName;
}
+ /** @psalm-pure */
public function fullName(): string
{
return $this->fullName;
}
- /** @return string[] */
+ /**
+ * @return list
+ * @psalm-pure
+ */
public function groups(): array
{
return $this->groups;
}
+ /** @psalm-pure */
public function dateLastUpdated(): ?DateTimeImmutable
{
return $this->dateLastUpdated;
}
+ /** @psalm-pure */
public function disabled(): bool
{
return $this->disabled;
}
- /** @return RelLink[] */
+ /**
+ * @return list
+ * @psalm-pure
+ */
public function links(): array
{
return $this->links;
}
- /** @throws RuntimeException if rel not found */
+ /**
+ * @throws RuntimeException if rel not found
+ * @psalm-pure
+ */
public function getRelLink(string $rel): string
{
$rel = \strtolower($rel);
diff --git a/src/UserManagement/UserUpdateInformation.php b/src/UserManagement/UserUpdateInformation.php
index 55dc9370..dff0aa12 100644
--- a/src/UserManagement/UserUpdateInformation.php
+++ b/src/UserManagement/UserUpdateInformation.php
@@ -16,13 +16,20 @@
use JsonSerializable;
use stdClass;
-/** @internal */
+/**
+ * @internal
+ */
class UserUpdateInformation implements JsonSerializable
{
private string $fullName;
- /** @var string[] */
+ /** @var list */
private array $groups;
+ /**
+ * @param list $groups
+ *
+ * @psalm-pure
+ */
public function __construct(string $fullName, array $groups)
{
$this->fullName = $fullName;
diff --git a/src/UserManagement/UsersManager.php b/src/UserManagement/UsersManager.php
index dd60af6f..e3773132 100644
--- a/src/UserManagement/UsersManager.php
+++ b/src/UserManagement/UsersManager.php
@@ -25,7 +25,7 @@ public function disable(string $login, ?UserCredentials $userCredentials = null)
/** @throws UserCommandFailed */
public function deleteUser(string $login, ?UserCredentials $userCredentials = null): void;
- /** @return UserDetails[] */
+ /** @return list */
public function listAll(?UserCredentials $userCredentials = null): array;
public function getCurrentUser(?UserCredentials $userCredentials = null): UserDetails;
@@ -33,13 +33,7 @@ public function getCurrentUser(?UserCredentials $userCredentials = null): UserDe
public function getUser(string $login, ?UserCredentials $userCredentials = null): UserDetails;
/**
- * @param string $login
- * @param string $fullName
- * @param string[] $groups
- * @param string $password
- * @param UserCredentials|null $userCredentials
- *
- * @return void
+ * @param list $groups
*/
public function createUser(
string $login,
@@ -50,12 +44,7 @@ public function createUser(
): void;
/**
- * @param string $login
- * @param string $fullName
- * @param string[] $groups
- * @param UserCredentials|null $userCredentials
- *
- * @return void
+ * @param list $groups
*/
public function updateUser(
string $login,
diff --git a/src/Util/DateTime.php b/src/Util/DateTime.php
index b0b93aff..32a73b03 100644
--- a/src/Util/DateTime.php
+++ b/src/Util/DateTime.php
@@ -24,6 +24,7 @@ public static function utcNow(): DateTimeImmutable
return new DateTimeImmutable('now', new DateTimeZone('UTC'));
}
+ /** @psalm-pure */
public static function create(string $dateTimeString): DateTimeImmutable
{
$dateTime = DateTimeImmutable::createFromFormat(
@@ -44,6 +45,7 @@ public static function create(string $dateTimeString): DateTimeImmutable
return $dateTime;
}
+ /** @psalm-pure */
public static function format(DateTimeImmutable $dateTime): string
{
return $dateTime->format('Y-m-d\TH:i:s.uP');
diff --git a/src/Util/Json.php b/src/Util/Json.php
index c75de026..f735db8e 100644
--- a/src/Util/Json.php
+++ b/src/Util/Json.php
@@ -17,7 +17,6 @@ class Json
{
/**
* @param mixed $value
- * @return string
*/
public static function encode($value): string
{
@@ -27,7 +26,6 @@ public static function encode($value): string
}
/**
- * @param string $json
* @return mixed
*/
public static function decode(string $json)