api-test skill
ApiTestCase kullanarak API Platform uç noktaları için CRUD, doğrulama, güvenlik ve çoklu kiracılı (multi-tenant) izolasyonu doğrulayan fonksiyonel testler yazar.
- GitHub yıldızları
- 29
- Dosyalar
- 1
- Son commit
- 22 Eki 2026
- Lisans
- —
- İzin verilen araçlar
- —
api-test skill ne işe yarar?
api-test bir agent skill'dir. ApiTestCase kullanarak API Platform uç noktaları için CRUD, doğrulama, güvenlik ve çoklu kiracılı (multi-tenant) izolasyonu doğrulayan fonksiyonel testler yazar.
Özet, skill'in SKILL.md dosyasından oluşturuldu.
api-test skilli hakkında
API Platform uç noktaları için fonksiyonel testler yazmak, bu SKILL'i kullanan geliştiriciler için temel görevdir. CRUD işlemleri, veri doğrulama, güvenlik protokolleri ve çoklu kiracılı izolasyonu doğrulayan test paketlerinin oluşturulmasını otomatikleştirir. Bir kullanıcı belirli bir API kaynağını test etmeye, mevcut fonksiyonel testleri düzeltmeye veya bir uç noktada bulunan hataları yeniden üretmeye ihtiyaç duyduğunda bir agent bu aracı yüklemelidir.
SKILL, kimlik doğrulama başlıklarını ayarlama veya veritabanı fixture'larını yönetme gibi karmaşık gereksinimleri ele alarak Symfony tabanlı uygulamalar için PHP kodu üretmek amacıyla ApiTestCase kullanır. Ayrıca ApiTestAssertionsTrait ve RefreshDatabase kullanarak Laravel ortamları için özel destek sağlar. İster Doctrine ORM ister MongoDB ile çalışıyor olun, araç kaynak bütünlüğünü ve düzgün şema yönetimini sağlamak için uygun dizinde yapılandırılmış test dosyaları üretir.
Bir agent bununla neler yapabilir
- 1CRUD işlemlerini doğrulayınBelirli bir kaynak için GET, POST, PATCH ve DELETE isteklerinin doğru çalıştığından emin olmak için fonksiyonel testler oluşturun.
- 2Veri kısıtlamalarını doğrulayınGeçersiz veri gönderildiğinde API'nin 422 durum kodu döndürüp döndürmediğini kontrol eden testler oluşturun.
- 3Çoklu kiracılı güvenliği uygulayınKullanıcıların farklı bir kuruluşa ait kaynaklara erişemeyeceğini veya bunları değiştiremeyeceğini onaylamak için testler geliştirin.
Skill'in SKILL.md dosyasından yazılmıştır. Her kullanım durumu oradaki bir alıntı ile kontrol edilir.
api-test skill nasıl kurulur
Her komut, skill klasörünü istemcinin skills dizinine kopyalar. Yüklemek için istemciyi yeniden başlatın veya yeni bir oturum başlatın.api-test skill'ini Eklenti uygulamasına kur
/plugin marketplace add api-platform/skillset /plugin install api-platform@api-platform-skillset
api-test skill'ini Claude Code uygulamasına kur
~/.claude/skills/api-test/SKILL.md
$ npx degit api-platform/skillset/skills/api-test ~/.claude/skills/api-testapi-test skill'ini Claude Code (project) uygulamasına kur
.claude/skills/api-test/SKILL.md
$ npx degit api-platform/skillset/skills/api-test .claude/skills/api-testapi-test skill'ini Codex uygulamasına kur
~/.agents/skills/api-test/SKILL.md
$ npx degit api-platform/skillset/skills/api-test ~/.agents/skills/api-testapi-test skill'ini Gemini CLI uygulamasına kur
~/.gemini/skills/api-test/SKILL.md
$ npx degit api-platform/skillset/skills/api-test ~/.gemini/skills/api-testapi-test skill'ini Claude.ai uygulamasına kur
npx degit api-platform/skillset/skills/api-test api-test && zip -r api-test.zip api-test # claude.ai → Customize → Skills → + → Create skill → Upload a skill → api-test.zip
SKILL.md
GitHub'da görüntüleTesting API Platform Endpoints
Use ApiPlatform\Symfony\Bundle\Test\ApiTestCase for functional API tests.
Base Test Class
Create a base class that handles database setup and authentication:
<?php
namespace App\Tests;
use ApiPlatform\Symfony\Bundle\Test\ApiTestCase as SymfonyApiTestCase;
use ApiPlatform\Symfony\Bundle\Test\Client;
class ApiTestCase extends SymfonyApiTestCase
{
protected function setUp(): void
{
parent::setUp();
// Reset database state for each test
$manager = static::getContainer()->get('doctrine')->getManager();
// For MongoDB: drop and recreate
// For ORM: use fixtures or transactions
}
/**
* Creates an authenticated client with test fixtures.
*/
public function createLoggedInClient(): Client
{
$manager = static::getContainer()->get('doctrine')->getManager();
// Create user, token, and required fixtures
$user = new User();
// ... set up user
$manager->persist($user);
$manager->flush();
// Return client with auth headers
return static::createClient([], [
'headers' => ['x-api-key' => 'test_token'],
]);
}
}
Basic CRUD Tests
class OrderTest extends ApiTestCase
{
public function testGetCollection(): void
{
$client = $this->createLoggedInClient();
$client->request('GET', '/orders');
$this->assertResponseIsSuccessful();
$this->assertResponseHeaderSame('content-type', 'application/ld+json; charset=utf-8');
}
public function testCreate(): void
{
$client = $this->createLoggedInClient();
$client->request('POST', '/orders', [
'headers' => ['Content-Type' => 'application/ld+json'],
'json' => ['name' => 'Test Order', 'total' => 99.99],
]);
$this->assertResponseStatusCodeSame(201);
$data = $client->getResponse()->toArray();
$this->assertSame('Test Order', $data['name']);
}
public function testUpdate(): void
{
$client = $this->createLoggedInClient();
// Create then update
$client->request('POST', '/orders', [
'headers' => ['Content-Type' => 'application/ld+json'],
'json' => ['name' => 'Original'],
]);
$order = $client->getResponse()->toArray();
$client->request('PATCH', '/orders/' . $order['id'], [
'headers' => ['Content-Type' => 'application/merge-patch+json'],
'json' => ['name' => 'Updated'],
]);
$this->assertResponseIsSuccessful();
$this->assertSame('Updated', $client->getResponse()->toArray()['name']);
}
public function testDelete(): void
{
$client = $this->createLoggedInClient();
// ... create resource first
$client->request('DELETE', '/orders/' . $id);
$this->assertResponseStatusCodeSame(204);
}
}
Testing Validation
public function testCreateWithInvalidData(): void
{
$client = $this->createLoggedInClient();
$client->request('POST', '/orders', [
'json' => ['email' => 'not-valid'],
]);
$this->assertResponseStatusCodeSame(422);
$this->assertJsonContains([
'violations' => [
['propertyPath' => 'email', 'message' => 'This value is not a valid email address.'],
],
]);
}
Testing Authentication
public function testRequiresAuthentication(): void
{
// No auth headers — use raw createClient
$client = static::createClient();
$client->request('GET', '/orders');
$this->assertResponseStatusCodeSame(401);
}
Multi-Tenant Isolation Tests
Test that users can only access their own resources:
public function testIsolationBetweenUsers(): void
{
$client1 = $this->createLoggedInClient(); // User 1, Org 1
$client2 = $this->createSecondUserClient(); // User 2, Org 2
// User 1 creates a resource
$client1->request('POST', '/accounts', [
'headers' => ['Content-Type' => 'application/ld+json'],
'json' => ['address' => 'user1@example.com', 'password' => 'Pass123!'],
]);
$account = $client1->getResponse()->toArray();
// User 2 cannot read it
$client2->request('GET', '/accounts/' . $account['id']);
$this->assertResponseStatusCodeSame(404);
// User 2 cannot update it
$client2->request('PATCH', '/accounts/' . $account['id'], [
'headers' => ['Content-Type' => 'application/merge-patch+json'],
'json' => ['isActive' => false],
]);
$this->assertResponseStatusCodeSame(404);
// User 2 cannot delete it
$client2->request('DELETE', '/accounts/' . $account['id']);
$this->assertResponseStatusCodeSame(404);
// Collections are isolated
$client2->request('GET', '/accounts');
$collection = $client2->getResponse()->toArray();
$ids = array_column($collection['member'], 'id');
$this->assertNotContains($account['id'], $ids);
}
Testing Filters
public function testFilterByStatus(): void
{
$client = $this->createLoggedInClient();
// ... create test data with different statuses
$client->request('GET', '/orders?isActive=true');
$this->assertResponseIsSuccessful();
$data = $client->getResponse()->toArray();
foreach ($data['member'] as $order) {
$this->assertTrue($order['isActive']);
}
}
Common Assertions
$this->assertResponseIsSuccessful();
$this->assertResponseStatusCodeSame(201);
$this->assertJsonContains(['name' => 'Expected']);
$this->assertMatchesResourceItemJsonSchema(Order::class);
$this->assertMatchesResourceCollectionJsonSchema(Order::class);
Resetting the Schema Between Tests (ORM)
For a clean database per test, drop and recreate the schema in setUp(). API
Platform's own suite uses an internal ApiPlatform\Tests\RecreateSchemaTrait —
that namespace is not autoloaded in your app, so copy the mechanism rather than
importing it:
use Doctrine\ORM\Tools\SchemaTool;
protected function setUp(): void
{
parent::setUp();
$manager = static::getContainer()->get('doctrine')->getManager();
$metadata = $manager->getMetadataFactory()->getAllMetadata();
$schemaTool = new SchemaTool($manager);
$schemaTool->dropDatabase();
$schemaTool->createSchema($metadata);
}
For MongoDB ODM, drop the collections via
$manager->getSchemaManager()->dropDocumentCollection(...) instead.
Test File Location
Place tests in tests/Functional/ following the naming convention {ResourceName}Test.php.
Laravel
Laravel uses its own HTTP test client (PHPUnit Tests\TestCase or Pest), not
ApiTestCase. API Platform ships ApiPlatform\Laravel\Test\ApiTestAssertionsTrait
(adds assertJsonContains(), assertArraySubset(), getIriFromResource()). Use
RefreshDatabase for isolation and model factories for fixtures (not Doctrine
SchemaTool/fixtures).
<?php
namespace Tests\Feature;
use ApiPlatform\Laravel\Test\ApiTestAssertionsTrait;
use App\Models\Book;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Tests\TestCase;
class BooksTest extends TestCase
{
use RefreshDatabase, ApiTestAssertionsTrait;
public function testCreate(): void
{
$response = $this->postJson('/api/books', ['isbn' => '0099740915', 'title' => 'X']);
$response->assertStatus(201);
$this->assertJsonContains(['title' => 'X'], $response->json());
$book = Book::factory()->create();
$this->getJson($this->getIriFromResource($book))->assertStatus(200);
}
}
Key deltas: request helpers are getJson/postJson/patchJson/deleteJson;
assertions are $response->assertStatus(...), $response->assertHeader(...),
$this->assertDatabaseMissing(...). assertJsonContains() takes the decoded body
($response->json()). Isolation/validation(422)/auth tests use the same status-code
assertions; auth uses Sanctum/actingAs(), not custom headers. Pest is the default
and wraps the same trait via uses(RefreshDatabase::class, ApiTestAssertionsTrait::class).
Bu becerideki dosyalar
1api-test skill soruları
api-test skill'ini Claude Code uygulamasına nasıl kurarım?
npx degit api-platform/skillset/skills/api-test ~/.claude/skills/api-test komutunu çalıştırın. Claude Code, skill'leri ~/.claude/skills (tüm projeler) veya .claude/skills (tek proje) konumundan yükler ve açıklaması görevle eşleştiğinde skill'i kullanır.
api-test skill'ini hangi istemciler kullanabilir?
Agent Skills biçimini okuyan her istemci: Claude Code, Codex, Gemini CLI ve claude.ai (ZIP olarak yükleyin). Skill içindeki betikler yalnızca istemcinin kod çalıştırmaya izin verdiği yerlerde çalışır.
Bu SKILL Laravel testlerini destekliyor mu?
Evet, ApiTestCase yerine ApiTestAssertionsTrait, RefreshDatabase ve model factory'lerini kullanarak Laravel için rehberlik sağlar.