diff --git a/README.md b/README.md index e8d127d..b0cc51d 100644 --- a/README.md +++ b/README.md @@ -152,6 +152,38 @@ $value = '{ "string": "value", "array": [1, 2, 3] }'; assert($value === ['string' => 'value', 'array' => [1, 2, 3]]); ``` +#### UuidFilter::filter + +This filter verifies a given string is a valid universally unique identifier. + +The second parameter can be set to `true` to allow null values through without an error. + +The third parameter can be set to `true` to allow [Nil UUIDs](https://datatracker.ietf.org/doc/html/rfc4122#section-4.1.7) values through without an error. + +The fourth parameter determines which UUID version the value will be validated against. By default, the filter will succeed if the values matches version 1, 2, 3, 4, 5, 6, or 7 + +```php +// Filtering an UUID string +$value = '1a42403c-a29d-11ef-b864-0242ac120002'; +$filtered = \TraderInteractive\Filter\UuidFilter::filter($value); +assert($value === $filtered); + +// Filtering null values +$value = null; +$filtered = \TraderInteractive\Filter\UuidFilter::filter($value, true); +assert(null === $filtered); + +// Filtering a nil UUID +$value = '00000000-0000-0000-0000-000000000000'; +$filtered = \TraderInteractive\Filter\UuidFilter::filter($value, false, true); +assert($value === $filtered); + +// Filtering for only UUID v4 +$value = '1a42403c-a29d-41ef-b864-0242ac120002'; +$filtered = \TraderInteractive\Filter\UuidFilter::filter($value, false, false, [4]); +assert($value === $filtered); +``` + #### XmlFilter::filter This filter ensures the given string is valid XML. diff --git a/src/Filter/UuidFilter.php b/src/Filter/UuidFilter.php new file mode 100644 index 0000000..3180a6b --- /dev/null +++ b/src/Filter/UuidFilter.php @@ -0,0 +1,121 @@ + + */ +final class UuidFilterTest extends TestCase +{ + /** + * @var string + * @internal + */ + const UUID_V1 = '1a42403c-a29d-11ef-b864-0242ac120002'; + + /** + * @var string + * @internal + */ + const UUID_V4 = 'cc468b36-0b9d-4c93-b8e9-d5e949331ffb'; + + /** + * @var string + * @internal + */ + const UUID_V7 = '01932b4a-af2b-7093-af59-2fb2044d13d8'; + + /** + * @test + * @covers ::filter + */ + public function filterUuidV1() + { + $this->assertSame(self::UUID_V1, UuidFilter::filter(self::UUID_V1)); + } + + /** + * @test + * @covers ::filter + */ + public function filterUuidV4() + { + $this->assertSame(self::UUID_V4, UuidFilter::filter(self::UUID_V4)); + } + + /** + * @test + * @covers ::filter + */ + public function filterUuidV7() + { + $this->assertSame(self::UUID_V7, UuidFilter::filter(self::UUID_V7)); + } + + /** + * @test + * @covers ::filter + */ + public function filterNullAllowedNullIsTrue() + { + $this->assertNull(UuidFilter::filter(null, true)); + } + + /** + * @test + * @covers ::filter + */ + public function filterNullAllowedNullIsFalse() + { + $this->expectException(FilterException::class); + UuidFilter::filter(null, false); + } + + /** + * @test + * @covers ::filter + */ + public function filterWithInvalidVersionSpecified() + { + $this->expectException(InvalidArgumentException::class); + $this->expectExceptionMessage(sprintf(UuidFilter::UNSUPPORTED_VERSION_ERROR_FORMAT, 0)); + UuidFilter::filter(self::UUID_V7, false, false, [0]); + } + + /** + * @test + * @covers ::filter + */ + public function filterValueDoesNotMatchGivenVersions() + { + $this->expectException(FilterException::class); + $this->expectExceptionMessage( + sprintf( + UuidFilter::FILTER_ERROR_FORMAT, + self::UUID_V4, + implode(', ', [1,7]) + ) + ); + UuidFilter::filter(self::UUID_V4, false, false, [1,7]); + } + + /** + * @test + * @covers ::filter + */ + public function filterNilUuid() + { + $value = UuidFilter::NIL_UUID; + $this->assertSame($value, UuidFilter::filter($value, false, true)); + } + + /** + * @test + * @covers ::filter + */ + public function filterNilUuidNilNotAllowed() + { + $value = UuidFilter::NIL_UUID; + $this->expectException(FilterException::class); + $this->expectExceptionMessage(sprintf(UuidFilter::NIL_NOT_ALLOWED_ERROR_FORMAT, $value)); + UuidFilter::filter($value, false, false); + } +}