diff --git a/src/Enums/Moderations/Category.php b/src/Enums/Moderations/Category.php index 34bdbaf6..e13393a3 100644 --- a/src/Enums/Moderations/Category.php +++ b/src/Enums/Moderations/Category.php @@ -10,6 +10,8 @@ enum Category: string case HateThreatening = 'hate/threatening'; case Harassment = 'harassment'; case HarassmentThreatening = 'harassment/threatening'; + case Illicit = 'illicit'; + case IllicitViolent = 'illicit/violent'; case SelfHarm = 'self-harm'; case SelfHarmIntent = 'self-harm/intent'; case SelfHarmInstructions = 'self-harm/instructions'; diff --git a/src/Responses/Moderations/CreateResponseResult.php b/src/Responses/Moderations/CreateResponseResult.php index 6bd88ca1..a913dd75 100644 --- a/src/Responses/Moderations/CreateResponseResult.php +++ b/src/Responses/Moderations/CreateResponseResult.php @@ -27,6 +27,10 @@ public static function from(array $attributes): self $categories = []; foreach (Category::cases() as $category) { + if (! isset($attributes['category_scores'][$category->value])) { + continue; + } + $categories[$category->value] = CreateResponseCategory::from([ 'category' => $category->value, 'violated' => $attributes['categories'][$category->value], diff --git a/tests/Fixtures/Moderation.php b/tests/Fixtures/Moderation.php index 322cbf25..9b7c2ab2 100644 --- a/tests/Fixtures/Moderation.php +++ b/tests/Fixtures/Moderation.php @@ -41,3 +41,49 @@ function moderationResource(): array ], ]; } + +/** + * @return array + */ +function moderationOmniResource(): array +{ + return [ + 'id' => 'modr-5MWoLO', + 'model' => 'omni-moderation-001', + 'results' => [ + [ + 'categories' => [ + 'hate' => false, + 'hate/threatening' => true, + 'harassment' => false, + 'harassment/threatening' => false, + 'illicit' => false, + 'illicit/violent' => true, + 'self-harm' => false, + 'self-harm/intent' => false, + 'self-harm/instructions' => false, + 'sexual' => false, + 'sexual/minors' => false, + 'violence' => false, + 'violence/graphic' => false, + ], + 'category_scores' => [ + 'hate' => 0.22714105248451233, + 'hate/threatening' => 0.4132447838783264, + 'illicit' => 0.1602763684674149, + 'illicit/violent' => 0.9223177433013916, + 'harassment' => 0.1602763684674149, + 'harassment/threatening' => 0.1602763684674149, + 'self-harm' => 0.005232391878962517, + 'self-harm/intent' => 0.005134391873962517, + 'self-harm/instructions' => 0.005132591874962517, + 'sexual' => 0.01407341007143259, + 'sexual/minors' => 0.0038522258400917053, + 'violence' => 0.4132447838783264, + 'violence/graphic' => 0.036865197122097015, + ], + 'flagged' => true, + ], + ], + ]; +} diff --git a/tests/Resources/Moderations.php b/tests/Resources/Moderations.php index 0395e8be..7e5dff91 100644 --- a/tests/Resources/Moderations.php +++ b/tests/Resources/Moderations.php @@ -7,7 +7,7 @@ use OpenAI\Responses\Moderations\CreateResponseResult; use OpenAI\ValueObjects\Transporter\Response; -test('create', closure: function () { +test('create legacy', closure: function () { $client = mockClient('POST', 'moderations', [ 'model' => 'text-moderation-latest', 'input' => 'I want to kill them.', @@ -43,3 +43,40 @@ expect($result->meta()) ->toBeInstanceOf(MetaInformation::class); }); + +test('create omni', closure: function () { + $client = mockClient('POST', 'moderations', [ + 'model' => 'omni-moderation-latest', + 'input' => 'I want to kill them.', + ], Response::from(moderationOmniResource(), metaHeaders())); + + $result = $client->moderations()->create([ + 'model' => 'omni-moderation-latest', + 'input' => 'I want to kill them.', + ]); + + expect($result) + ->toBeInstanceOf(CreateResponse::class) + ->id->toBe('modr-5MWoLO') + ->model->toBe('omni-moderation-001') + ->results->toBeArray()->toHaveCount(1) + ->results->each->toBeInstanceOf(CreateResponseResult::class); + + expect($result->results[0]) + ->flagged->toBeTrue() + ->categories->toHaveCount(13) + ->each->toBeInstanceOf(CreateResponseCategory::class); + + expect($result->results[0]->categories[Category::Illicit->value]) + ->category->toBe(Category::Illicit) + ->violated->toBe(false) + ->score->toBe(0.1602763684674149); + + expect($result->results[0]->categories[Category::IllicitViolent->value]) + ->category->toBe(Category::IllicitViolent) + ->violated->toBe(true) + ->score->toBe(0.9223177433013916); + + expect($result->meta()) + ->toBeInstanceOf(MetaInformation::class); +});