[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"skill:01M6X662G3CEV5AP0BPF4DFKZ2":3,"skill-same:01M6X662G3CEV5AP0BPF4DFKZ2":94},{"skillNo":4,"name":5,"nameZh":6,"description":7,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":16,"categories":17,"keywords":34,"publishedAt":55,"linkOnly":56,"markdownContent":57,"markdownBody":58,"frontMatter":59,"refName":65,"commitSha":66,"skillDirectory":67,"forksCount":68,"repositoryHtmlUrl":69,"repositoryHomepageUrl":70,"ownerHtmlUrl":71,"ownerBlogUrl":70,"ownerDescription":72,"updatedAt":73,"install":74,"resources":87},"01M6X662G3CEV5AP0BPF4DFKZ2","api-testing",null,"Use when writing API endpoint tests — integration tests, contract validation, response assertions, mocked external services — even when the user says 'test this route' without naming API testing.","event4u-app\u002Fagent-config","event4u-app","https:\u002F\u002Favatars.githubusercontent.com\u002Fu\u002F199339632?v=4","01M6X5TWBNCQCE1VDKT4E9KF7N","event4u.app","01M6X5TWF4HRM266RG2Q5VVH1X",19,"MIT","https:\u002F\u002Fgithub.com\u002Fevent4u-app\u002Fagent-config\u002Fblob\u002Fmain\u002Fsrc\u002Fskills\u002Fapi-testing\u002FSKILL.md",[18,23,26,31],{"categoryNo":19,"categoryName":20,"taxonomyType":21,"taxonomyTypeDesc":22},"01JBSEEDCAT000000000000008","测试与质量","SCENARIO","使用场景",{"categoryNo":24,"categoryName":25,"taxonomyType":21,"taxonomyTypeDesc":22},"01JBSEEDCAT000000000000010","后端与接口",{"categoryNo":27,"categoryName":28,"taxonomyType":29,"taxonomyTypeDesc":30},"01JBSEEDCAT000000000000030","开发工程师","PROFESSION","适用职业",{"categoryNo":32,"categoryName":33,"taxonomyType":29,"taxonomyTypeDesc":30},"01JBSEEDCAT000000000000037","律师与法务",[35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54],"api","testing","api testing","use","when","assertions","naming","tests","contract","route","base","api endpoint","quality","endpoint","services","integration","validation","integration tests","test","writing","2026-11-10 10:12:30",false,"---\nmodel_tier: medium\nname: api-testing\ndescription: \"Use when writing API endpoint tests — integration tests, contract validation, response assertions, mocked external services — even when the user says 'test this route' without naming API testing.\"\ndomain: quality\nworkspaces:\n  - engineering\npacks:\n  - engineering-base\n---\n\n# api-testing\n\n## When to use\n\nUse this skill when writing or reviewing API endpoint tests — integration tests,\ncontract validation, response structure checks, or external service mocking.\n\n## Procedure: Write API tests\n\n1. **Understand the endpoint** — Read the controller, form request, and existing tests. Understand expected behavior, edge cases, and auth requirements before writing anything.\n2. **Set up test data** — Use seeders (preferred) or factories. Mock external services with `Http::fake()`.\n3. **Enumerate test cases** — Run the [`test-case-discovery`](..\u002Ftest-case-discovery\u002FSKILL.md) funnel first; cover success, validation errors, authorization failures, and edge cases — floor per behavior: 1 happy + 1 boundary + 1 error (+1 abuse case; on data-returning endpoints the three `broken-access-control` negative tests are mandatory).\n4. **Assert response** — Check status code, JSON structure, data values. Use `assertJsonStructure()`.\n5. **Verify** — Run the test. Must pass. Check no flaky assertions (no time-dependent, no random ordering).\n\n### Example\n\n```php\ndescribe('GET \u002Fapi\u002Fv1\u002Fprojects', function () {\n    it('returns paginated projects for authenticated user', function () {\n        $user = loginAsTestUser();\n\n        $response = $this->getJson('\u002Fapi\u002Fv1\u002Fprojects');\n\n        $response->assertOk()\n            ->assertJsonStructure([\n                'data' => [['id', 'title', 'status']],\n                'meta' => ['current_page', 'per_page', 'total'],\n            ]);\n    });\n\n    it('returns 401 for unauthenticated request', function () {\n        $this->getJson('\u002Fapi\u002Fv1\u002Fprojects')\n            ->assertUnauthorized();\n    });\n\n    it('returns 403 when user lacks permission', function () {\n        loginAsRestrictedUser();\n\n        $this->getJson('\u002Fapi\u002Fv1\u002Fprojects')\n            ->assertForbidden();\n    });\n});\n```\n\n## Test categories\n\n### Happy path\n\nTest the expected success scenario with valid input:\n\n```php\nit('creates a project', function () {\n    loginAsTestUser();\n\n    $this->postJson('\u002Fapi\u002Fv1\u002Fprojects', [\n        'title' => 'New Project',\n        'customer_id' => $customerId,\n    ])\n        ->assertCreated()\n        ->assertJsonPath('data.title', 'New Project');\n\n    $this->assertDatabaseHas('projects', ['title' => 'New Project']);\n});\n```\n\n### Validation\n\nTest that invalid input is rejected with correct error messages:\n\n```php\nit('rejects project without title', function () {\n    loginAsTestUser();\n\n    $this->postJson('\u002Fapi\u002Fv1\u002Fprojects', [\n        'customer_id' => $customerId,\n    ])\n        ->assertUnprocessable()\n        ->assertJsonValidationErrors(['title']);\n});\n```\n\n### Authorization\n\nTest that unauthorized access is blocked:\n\n```php\nit('prevents non-owner from updating project', function () {\n    $otherUser = loginAsOtherUser();\n\n    $this->putJson(\"\u002Fapi\u002Fv1\u002Fprojects\u002F{$project->id}\", [\n        'title' => 'Hijacked',\n    ])\n        ->assertForbidden();\n});\n```\n\n### Edge cases\n\nTest boundary conditions:\n\n```php\nit('handles empty collection', function () {\n    loginAsTestUser();\n\n    $this->getJson('\u002Fapi\u002Fv1\u002Fprojects')\n        ->assertOk()\n        ->assertJsonCount(0, 'data');\n});\n\nit('paginates large result sets', function () {\n    loginAsTestUser();\n\n    $this->getJson('\u002Fapi\u002Fv1\u002Fprojects?per_page=5')\n        ->assertOk()\n        ->assertJsonPath('meta.per_page', 5);\n});\n```\n\n## Response contract validation\n\n### Assert JSON structure\n\n```php\n\u002F\u002F Verify response shape (keys exist)\n$response->assertJsonStructure([\n    'data' => ['id', 'title', 'status', 'created_at'],\n]);\n\n\u002F\u002F Verify exact values\n$response->assertJsonPath('data.status', 'active');\n\n\u002F\u002F Verify collection count\n$response->assertJsonCount(3, 'data');\n```\n\n### Assert response types\n\n```php\n\u002F\u002F When strict typing matters\n$data = $response->json('data');\nexpect($data['id'])->toBeInt();\nexpect($data['title'])->toBeString();\nexpect($data['total'])->toBeString(); \u002F\u002F Money as string, not float\n```\n\n### Filter noisy responses\n\nWhen a failing test dumps the full JSON body, narrow the diagnosis with `jq` or `grep`\ninstead of scrolling the whole payload:\n\n```bash\n# Extract only the failing assertion path\necho \"$RESPONSE_JSON\" | jq '.data.status, .errors'\n\n# Targeted log scan\nrg --json 'API call failed' storage\u002Flogs\u002Flaravel.log | jq -r '.data.lines.text'\n```\n\n## External service mocking\n\n```php\nit('handles external API failure gracefully', function () {\n    Http::fake([\n        'external-api.com\u002F*' => Http::response(null, 500),\n    ]);\n\n    loginAsTestUser();\n\n    $this->postJson('\u002Fapi\u002Fv1\u002Fsync')\n        ->assertStatus(502)\n        ->assertJsonPath('message', 'External service unavailable');\n});\n```\n\n## Test checklist per endpoint\n\n| Category | Tests needed |\n|---|---|\n| **Auth** | Unauthenticated (401), unauthorized (403) |\n| **Validation** | Missing fields, wrong types, boundary values |\n| **Happy path** | Success with valid input, correct status code |\n| **Response** | JSON structure, field types, pagination meta |\n| **Side effects** | Database changes, events dispatched, jobs queued |\n| **Edge cases** | Empty results, large payloads, concurrent access |\n\n## Bridge to UI verification\n\nAPI tests cover the contract layer. When an endpoint feeds a UI surface (Livewire component, Blade-rendered page, SPA route), complement the API test with a thin UI probe: a `livewire test` for wired components, or a Playwright spec \u002F browser `screenshot` for the rendered shell. Never assume the UI works just because the API test is green.\n\n## Output format\n\n1. Test file in the project’s test framework (Pest, Jest, pytest) covering happy path, validation, auth, and edge cases\n2. Test names as readable sentences describing expected behavior\n3. Mocked external services where applicable\n\n## Auto-trigger keywords\n\n- API test\n- endpoint test\n- integration test\n- response validation\n- contract testing\n\n## Gotcha\n\n- Don't test framework internals (e.g., \"does Laravel return 422 on validation error\") — test YOUR validation rules.\n- Always seed test data explicitly — don't rely on data from other tests (parallel execution).\n- Mock external APIs with `Http::fake()` — never hit real services in tests.\n- The model forgets to assert response structure, only checking status codes — always check both.\n\n## Do NOT\n\n- Do not hardcode IDs or timestamps — use factories or seeders.\n- Do not skip auth tests — always test both authenticated and unauthenticated.\n- Do not assert entire JSON responses — assert only meaningful fields.\n- Do not use `Http::fake()` without also testing the real integration path.\n\n## Anti-bruteforce — diagnose before retry\n\nWhen a test fails, do not retry blindly with tweaked assertions until something passes. Diagnose the root cause first: print the actual response shape once, compare it to the contract, then write a targeted fix. Trial-and-error retries hide real regressions.\n\n## Clarification guard — ambiguous contract → ask\n\nIf the endpoint contract is ambiguous (unclear status code, optional fields, error envelope shape), do not assume. Ask the user or check the OpenAPI spec \u002F route definition before writing assertions — never guess the response shape from the route name.\n\n## The HTTP-assertion idiom, per ecosystem\n\nThe examples above are Laravel's. The *shape* they teach — assert the status,\nthen the body contract, then the side effect, and keep one behavior per test —\ntransfers unchanged; the API does not. Resolve the runner with\n`resolve_toolchain` and read its `ecosystems`:\n\n| `ecosystems` | Request + assertion surface |\n|---|---|\n| `php` | `$this->getJson(...)` \u002F `assertStatus` \u002F `assertJsonPath` |\n| `js` | `supertest` or the framework's own test client, with `expect(res.status)` |\n| `python` | `httpx.AsyncClient` \u002F framework `TestClient`; `assert res.status_code` |\n| `go` | `httptest.NewServer` + `net\u002Fhttp`, or the router's own `ServeHTTP` |\n\nWhatever the surface, the negative tests are not optional: unauthenticated,\nnot-owner and cross-tenant each get their own case, per `broken-access-control`.\n","# api-testing\n\n## When to use\n\nUse this skill when writing or reviewing API endpoint tests — integration tests,\ncontract validation, response structure checks, or external service mocking.\n\n## Procedure: Write API tests\n\n1. **Understand the endpoint** — Read the controller, form request, and existing tests. Understand expected behavior, edge cases, and auth requirements before writing anything.\n2. **Set up test data** — Use seeders (preferred) or factories. Mock external services with `Http::fake()`.\n3. **Enumerate test cases** — Run the [`test-case-discovery`](..\u002Ftest-case-discovery\u002FSKILL.md) funnel first; cover success, validation errors, authorization failures, and edge cases — floor per behavior: 1 happy + 1 boundary + 1 error (+1 abuse case; on data-returning endpoints the three `broken-access-control` negative tests are mandatory).\n4. **Assert response** — Check status code, JSON structure, data values. Use `assertJsonStructure()`.\n5. **Verify** — Run the test. Must pass. Check no flaky assertions (no time-dependent, no random ordering).\n\n### Example\n\n```php\ndescribe('GET \u002Fapi\u002Fv1\u002Fprojects', function () {\n    it('returns paginated projects for authenticated user', function () {\n        $user = loginAsTestUser();\n\n        $response = $this->getJson('\u002Fapi\u002Fv1\u002Fprojects');\n\n        $response->assertOk()\n            ->assertJsonStructure([\n                'data' => [['id', 'title', 'status']],\n                'meta' => ['current_page', 'per_page', 'total'],\n            ]);\n    });\n\n    it('returns 401 for unauthenticated request', function () {\n        $this->getJson('\u002Fapi\u002Fv1\u002Fprojects')\n            ->assertUnauthorized();\n    });\n\n    it('returns 403 when user lacks permission', function () {\n        loginAsRestrictedUser();\n\n        $this->getJson('\u002Fapi\u002Fv1\u002Fprojects')\n            ->assertForbidden();\n    });\n});\n```\n\n## Test categories\n\n### Happy path\n\nTest the expected success scenario with valid input:\n\n```php\nit('creates a project', function () {\n    loginAsTestUser();\n\n    $this->postJson('\u002Fapi\u002Fv1\u002Fprojects', [\n        'title' => 'New Project',\n        'customer_id' => $customerId,\n    ])\n        ->assertCreated()\n        ->assertJsonPath('data.title', 'New Project');\n\n    $this->assertDatabaseHas('projects', ['title' => 'New Project']);\n});\n```\n\n### Validation\n\nTest that invalid input is rejected with correct error messages:\n\n```php\nit('rejects project without title', function () {\n    loginAsTestUser();\n\n    $this->postJson('\u002Fapi\u002Fv1\u002Fprojects', [\n        'customer_id' => $customerId,\n    ])\n        ->assertUnprocessable()\n        ->assertJsonValidationErrors(['title']);\n});\n```\n\n### Authorization\n\nTest that unauthorized access is blocked:\n\n```php\nit('prevents non-owner from updating project', function () {\n    $otherUser = loginAsOtherUser();\n\n    $this->putJson(\"\u002Fapi\u002Fv1\u002Fprojects\u002F{$project->id}\", [\n        'title' => 'Hijacked',\n    ])\n        ->assertForbidden();\n});\n```\n\n### Edge cases\n\nTest boundary conditions:\n\n```php\nit('handles empty collection', function () {\n    loginAsTestUser();\n\n    $this->getJson('\u002Fapi\u002Fv1\u002Fprojects')\n        ->assertOk()\n        ->assertJsonCount(0, 'data');\n});\n\nit('paginates large result sets', function () {\n    loginAsTestUser();\n\n    $this->getJson('\u002Fapi\u002Fv1\u002Fprojects?per_page=5')\n        ->assertOk()\n        ->assertJsonPath('meta.per_page', 5);\n});\n```\n\n## Response contract validation\n\n### Assert JSON structure\n\n```php\n\u002F\u002F Verify response shape (keys exist)\n$response->assertJsonStructure([\n    'data' => ['id', 'title', 'status', 'created_at'],\n]);\n\n\u002F\u002F Verify exact values\n$response->assertJsonPath('data.status', 'active');\n\n\u002F\u002F Verify collection count\n$response->assertJsonCount(3, 'data');\n```\n\n### Assert response types\n\n```php\n\u002F\u002F When strict typing matters\n$data = $response->json('data');\nexpect($data['id'])->toBeInt();\nexpect($data['title'])->toBeString();\nexpect($data['total'])->toBeString(); \u002F\u002F Money as string, not float\n```\n\n### Filter noisy responses\n\nWhen a failing test dumps the full JSON body, narrow the diagnosis with `jq` or `grep`\ninstead of scrolling the whole payload:\n\n```bash\n# Extract only the failing assertion path\necho \"$RESPONSE_JSON\" | jq '.data.status, .errors'\n\n# Targeted log scan\nrg --json 'API call failed' storage\u002Flogs\u002Flaravel.log | jq -r '.data.lines.text'\n```\n\n## External service mocking\n\n```php\nit('handles external API failure gracefully', function () {\n    Http::fake([\n        'external-api.com\u002F*' => Http::response(null, 500),\n    ]);\n\n    loginAsTestUser();\n\n    $this->postJson('\u002Fapi\u002Fv1\u002Fsync')\n        ->assertStatus(502)\n        ->assertJsonPath('message', 'External service unavailable');\n});\n```\n\n## Test checklist per endpoint\n\n| Category | Tests needed |\n|---|---|\n| **Auth** | Unauthenticated (401), unauthorized (403) |\n| **Validation** | Missing fields, wrong types, boundary values |\n| **Happy path** | Success with valid input, correct status code |\n| **Response** | JSON structure, field types, pagination meta |\n| **Side effects** | Database changes, events dispatched, jobs queued |\n| **Edge cases** | Empty results, large payloads, concurrent access |\n\n## Bridge to UI verification\n\nAPI tests cover the contract layer. When an endpoint feeds a UI surface (Livewire component, Blade-rendered page, SPA route), complement the API test with a thin UI probe: a `livewire test` for wired components, or a Playwright spec \u002F browser `screenshot` for the rendered shell. Never assume the UI works just because the API test is green.\n\n## Output format\n\n1. Test file in the project’s test framework (Pest, Jest, pytest) covering happy path, validation, auth, and edge cases\n2. Test names as readable sentences describing expected behavior\n3. Mocked external services where applicable\n\n## Auto-trigger keywords\n\n- API test\n- endpoint test\n- integration test\n- response validation\n- contract testing\n\n## Gotcha\n\n- Don't test framework internals (e.g., \"does Laravel return 422 on validation error\") — test YOUR validation rules.\n- Always seed test data explicitly — don't rely on data from other tests (parallel execution).\n- Mock external APIs with `Http::fake()` — never hit real services in tests.\n- The model forgets to assert response structure, only checking status codes — always check both.\n\n## Do NOT\n\n- Do not hardcode IDs or timestamps — use factories or seeders.\n- Do not skip auth tests — always test both authenticated and unauthenticated.\n- Do not assert entire JSON responses — assert only meaningful fields.\n- Do not use `Http::fake()` without also testing the real integration path.\n\n## Anti-bruteforce — diagnose before retry\n\nWhen a test fails, do not retry blindly with tweaked assertions until something passes. Diagnose the root cause first: print the actual response shape once, compare it to the contract, then write a targeted fix. Trial-and-error retries hide real regressions.\n\n## Clarification guard — ambiguous contract → ask\n\nIf the endpoint contract is ambiguous (unclear status code, optional fields, error envelope shape), do not assume. Ask the user or check the OpenAPI spec \u002F route definition before writing assertions — never guess the response shape from the route name.\n\n## The HTTP-assertion idiom, per ecosystem\n\nThe examples above are Laravel's. The *shape* they teach — assert the status,\nthen the body contract, then the side effect, and keep one behavior per test —\ntransfers unchanged; the API does not. Resolve the runner with\n`resolve_toolchain` and read its `ecosystems`:\n\n| `ecosystems` | Request + assertion surface |\n|---|---|\n| `php` | `$this->getJson(...)` \u002F `assertStatus` \u002F `assertJsonPath` |\n| `js` | `supertest` or the framework's own test client, with `expect(res.status)` |\n| `python` | `httpx.AsyncClient` \u002F framework `TestClient`; `assert res.status_code` |\n| `go` | `httptest.NewServer` + `net\u002Fhttp`, or the router's own `ServeHTTP` |\n\nWhatever the surface, the negative tests are not optional: unauthenticated,\nnot-owner and cross-tenant each get their own case, per `broken-access-control`.\n",{"name":5,"packs":60,"domain":47,"model_tier":62,"workspaces":63,"description":7},[61],"engineering-base","medium",[64],"engineering","main","12bd765ce1d800501d45dfb8232102793af01290","src\u002Fskills\u002Fapi-testing",1,"https:\u002F\u002Fgithub.com\u002Fevent4u-app\u002Fagent-config","https:\u002F\u002Fevent4u.app","https:\u002F\u002Fgithub.com\u002Fevent4u-app","Your events in your hand","2026-11-11 06:19:40",{"source":8,"skillName":5,"commands":75,"prompt":85,"zipAvailable":86},[76,79,82],{"tool":77,"command":78},"npx","npx skills add event4u-app\u002Fagent-config --skill api-testing",{"tool":80,"command":81},"bunx","bunx skills add event4u-app\u002Fagent-config --skill api-testing",{"tool":83,"command":84},"pnpm","pnpm dlx skills add event4u-app\u002Fagent-config --skill api-testing","安装技能，技能地址：https:\u002F\u002Fgithub.com\u002Fevent4u-app\u002Fagent-config\u002Fblob\u002Fmain\u002Fsrc\u002Fskills\u002Fapi-testing\u002FSKILL.md",true,[88],{"path":89,"resourceType":90,"resourceTypeDesc":91,"sizeBytes":92,"sourceHtmlUrl":93},"evals\u002Ftriggers.json","REFERENCE","参考文档",2828,"https:\u002F\u002Fgithub.com\u002Fevent4u-app\u002Fagent-config\u002Fblob\u002Fmain\u002Fsrc\u002Fskills\u002Fapi-testing\u002Fevals\u002Ftriggers.json",[95,111,124,136,148,158],{"skillNo":96,"name":97,"nameZh":6,"description":98,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":99,"categories":100,"keywords":104,"publishedAt":55},"01M6X84PK96XBPENXH66JCTSD1","unknown-key-fixture","Declares a key the schema does not know.","https:\u002F\u002Fgithub.com\u002Fevent4u-app\u002Fagent-config\u002Fblob\u002Fmain\u002Ftests\u002Fscripts\u002Ffixtures\u002Fbody-portable\u002Funknown-key\u002FSKILL.md",[101],{"categoryNo":102,"categoryName":103,"taxonomyType":21,"taxonomyTypeDesc":22},"01JBSEEDCAT000000000000023","Skill与智能体开发",[105,106,107,108,109,110],"unknown key fixture","Unknown key","fixture","unknown","schema","package",{"skillNo":112,"name":113,"nameZh":6,"description":114,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":115,"categories":116,"keywords":118,"publishedAt":55},"01M6X84HW7NAHZ7GZMQ9RXK1XJ","portable-fixture","Declares only semantics the MCP-lite carrier transports whole.","https:\u002F\u002Fgithub.com\u002Fevent4u-app\u002Fagent-config\u002Fblob\u002Fmain\u002Ftests\u002Fscripts\u002Ffixtures\u002Fbody-portable\u002Fportable\u002FSKILL.md",[117],{"categoryNo":102,"categoryName":103,"taxonomyType":21,"taxonomyTypeDesc":22},[107,119,120,121,122,110,123],"portable","portable fixture","engineer","only","MCP",{"skillNo":125,"name":126,"nameZh":6,"description":127,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":128,"categories":129,"keywords":131,"publishedAt":55},"01M6X84F29FE0RGGZ1ZTFGZTX2","non-portable-fixture","Declares a runtime semantic the carrier drops.","https:\u002F\u002Fgithub.com\u002Fevent4u-app\u002Fagent-config\u002Fblob\u002Fmain\u002Ftests\u002Fscripts\u002Ffixtures\u002Fbody-portable\u002Fnon-portable\u002FSKILL.md",[130],{"categoryNo":102,"categoryName":103,"taxonomyType":21,"taxonomyTypeDesc":22},[120,132,119,107,133,134,135,110],"non portable fixture","semantic","high","runtime",{"skillNo":137,"name":138,"nameZh":6,"description":139,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":140,"categories":141,"keywords":143,"publishedAt":55},"01M6X848F706PT9MDCX75JKJ6B","candidate-zero-width","A candidate whose prose carries an invisible joiner.","https:\u002F\u002Fgithub.com\u002Fevent4u-app\u002Fagent-config\u002Fblob\u002Fmain\u002Ftests\u002Ffixtures\u002Fskill-scout-candidates\u002Fzero-width-injection\u002FSKILL.md",[142],{"categoryNo":102,"categoryName":103,"taxonomyType":21,"taxonomyTypeDesc":22},[144,145,146,147],"candidate zero width","candidate","ZeRO","prose",{"skillNo":149,"name":150,"nameZh":6,"description":151,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":152,"categories":153,"keywords":155,"publishedAt":55},"01M6X841SSC2T31VDF41SA6DG1","candidate-disclosure-suppression","A candidate whose prose tells the agent to withhold from the user.","https:\u002F\u002Fgithub.com\u002Fevent4u-app\u002Fagent-config\u002Fblob\u002Fmain\u002Ftests\u002Ffixtures\u002Fskill-scout-candidates\u002Fdisclosure-suppression\u002FSKILL.md",[154],{"categoryNo":102,"categoryName":103,"taxonomyType":21,"taxonomyTypeDesc":22},[156,145,147,157],"candidate disclosure suppression","user",{"skillNo":159,"name":160,"nameZh":6,"description":161,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":162,"categories":163,"keywords":165,"publishedAt":55},"01M6X83TFS5AGPBPVTQNWP0BB3","candidate-dangerous-frontmatter","A candidate claiming an unscoped tool grant and a permission bypass.","https:\u002F\u002Fgithub.com\u002Fevent4u-app\u002Fagent-config\u002Fblob\u002Fmain\u002Ftests\u002Ffixtures\u002Fskill-scout-candidates\u002Fdangerous-frontmatter\u002FSKILL.md",[164],{"categoryNo":102,"categoryName":103,"taxonomyType":21,"taxonomyTypeDesc":22},[166,145,167,168,169,170],"candidate dangerous frontmatter","frontmatter","shell","permission","tool"]