[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"skill:01M6C4P0DK385QBG3B3S86TQV2":3,"skill-same:01M6C4P0DK385QBG3B3S86TQV2":93},{"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":26,"publishedAt":39,"linkOnly":40,"markdownContent":41,"markdownBody":42,"frontMatter":43,"refName":44,"commitSha":45,"skillDirectory":46,"forksCount":47,"repositoryHtmlUrl":48,"repositoryHomepageUrl":6,"ownerHtmlUrl":49,"ownerBlogUrl":50,"ownerDescription":51,"updatedAt":52,"install":53,"resources":66},"01M6C4P0DK385QBG3B3S86TQV2","react-testing",null,"USE WHEN writing, fixing or reviewing a React Testing Library test for a component, hook or context provider, even one small test, or when asked for an end-to-end journey inside a Vitest or React Testing Library suite; NOT WHEN changing the component itself (react), testing XState actors or @xstate\u002Freact (xstate), or writing a Playwright or Cypress test; covers renderHook, providers, async results, forms and false-pass anti-patterns, and declines end-to-end journeys with the testable slices.","mintuz\u002Fskills","mintuz","https:\u002F\u002Favatars.githubusercontent.com\u002Fu\u002F447031?v=4","01M6BVWJYSVR4XQC9AQCEMWQRG","Adam Bulmer","01M6C4DCXKNYZB281YB3PZDJJG",35,"MIT","https:\u002F\u002Fgithub.com\u002Fmintuz\u002Fskills\u002Fblob\u002Fmain\u002Fsrc\u002Fweb\u002Fskills\u002Freact-testing\u002FSKILL.md",[18,23],{"categoryNo":19,"categoryName":20,"taxonomyType":21,"taxonomyTypeDesc":22},"01JBSEEDCAT000000000000008","测试与质量","SCENARIO","使用场景",{"categoryNo":24,"categoryName":25,"taxonomyType":21,"taxonomyTypeDesc":22},"01JBSEEDCAT000000000000009","前端开发",[27,28,29,30,31,32,33,34,35,36,37,38],"testing","react testing","react","anti-patterns","hooks","e2e","library","testing library","components","Providers","context","react components","2026-11-10 10:12:30",false,"---\nname: react-testing\ndescription: \"USE WHEN writing, fixing or reviewing a React Testing Library test for a component, hook or context provider, even one small test, or when asked for an end-to-end journey inside a Vitest or React Testing Library suite; NOT WHEN changing the component itself (react), testing XState actors or @xstate\u002Freact (xstate), or writing a Playwright or Cypress test; covers renderHook, providers, async results, forms and false-pass anti-patterns, and declines end-to-end journeys with the testable slices.\"\n---\n\n# React Testing Library\n\nFor a page or widget not built with React, use the `frontend-testing` skill. For the TDD workflow, use the `tdd` skill.\n\n## Core rules\n\nTest behaviour through public APIs: props in, rendered DOM out (`principle-test-behavior-not-implementation`). For each assertion, name a plausible wrong implementation that would still pass. Write the assertion that fails on it.\n\n- Query by accessible role, label or visible text.\n- Add `{ name }` to `getByRole` only when the element has an accessible name. Content names a `button`, `link` or `heading`. `aria-label` or `aria-labelledby` names an element whose role accepts an author-supplied name. A plain `\u003Cli>` takes no name from its text, so query it by that text.\n- Assert the call count with `toHaveBeenCalledTimes` as well as the arguments. `toHaveBeenCalledWith` alone does not prove the number of calls.\n- Do not test component state or methods. Do not assert on a class name, test id or handler name when accessible output proves the same behaviour. Do not use shallow rendering.\n- Do not wrap `render()`, `userEvent` calls or async queries in `act()`. RTL wraps them.\n- Do not call `cleanup()` in a test file. RTL cleans up automatically when the runner exposes a global `afterEach`. In Vitest, that needs `globals: true` or one `afterEach(cleanup)` in a shared setup file. When the project keeps globals off, put that call in the setup file, remove `cleanup` from every test file and leave the config unchanged.\n- Render through a factory function in each test, not a shared `beforeEach` render.\n\n## Project libraries\n\nUse the runner, matchers and helpers the project already has. Do not add a testing dependency that nobody asked for (`principle-reuse-before-building`).\n\n- If `@testing-library\u002Fuser-event` is installed, create `userEvent.setup()` in each test. If not, use `fireEvent` and say that `user-event` models the interaction more closely.\n- If the setup registers jest-dom matchers, use them, such as `toBeInTheDocument()`. If not, assert absence with `toBeNull()` and text with `textContent`.\n- Before you write a network stub or custom render helper, use the project's existing one, such as a `stubApi` function, an MSW `server` or a `renderWithProviders` helper.\n\n## Scope\n\nRTL renders one component tree, in jsdom or a browser test runner. Keep every test inside that tree.\n\nA request crosses that boundary when it needs a real network, a real email or a redirect to a third-party site. A demand for several real browsers is a coverage matrix for that journey, not a separate boundary. For such a request:\n\n1. Say it is end-to-end work. Name each external system from the request that it crosses.\n2. Recommend a browser-driven tool by name, such as Playwright or Cypress, for the journey.\n3. Name each slice RTL can still cover with the network boundary mocked: its component and the behaviour to assert (`principle-state-the-scope`).\n\nDo not offer a test that fakes those external systems as an equivalent of the journey.\n\n## Test allocation\n\nPrefer integration tests over unit tests.\n\n| Level | What to test | How many | Tools |\n| --- | --- | --- | --- |\n| Unit | Pure functions that hold a decision, such as a permission rule, a complex calculation or a shared utility | Each rule outside a component | Vitest, no renderer |\n| Integration | Features, user flows, component interactions | Most tests | Vitest + Testing Library |\n| E2E | Critical user journeys | Few, critical paths only | Playwright or Cypress |\n\nTest a permission rule in a plain function without rendering React (`react` skill). Test a state machine as an actor (`xstate` skill). Keep those unit tests. Do not move their rule into a rendered test.\n\n## Asynchronous results\n\nA view that loads or updates asynchronously shows its result after the first render. To assert that a value is absent from that result:\n\n1. Await a positive assertion, such as `await screen.findByText(...)`.\n2. Then assert the absence with a `queryBy*` query and `not.toBeInTheDocument()`.\n\nAn earlier absence check passes while the view still shows its loading state, so it proves nothing. Reach the result with awaited Testing Library APIs, not a fixed delay or an `act()` around `render()`. Use fake timers only when a timer is the behaviour under test. Then pass `advanceTimers` to `userEvent.setup()` and advance the clock with the runner's timer API.\n\nWhen an `async` handler calls a callback, await the callback assertion, for example `await waitFor(() => expect(onSave).toHaveBeenCalledTimes(1))`.\n\nAssert a synchronous initial state, such as a collapsed panel, directly after `render()`.\n\n## Hooks and context\n\nUse `renderHook` for hook-only behaviour. Its `initialProps` and `rerender(props)` reach the hook callback only, never the `wrapper`. Use the `wrapper` option to mount a provider with fixed props. When the test calls a state-changing hook callback directly, such as `result.current.addItem()`, wrap that call in `act()`. It runs outside RTL's auto-wrapped helpers.\n\nWhen a provider prop must change, render a small consumer component with `render()`. Change the prop through that render result's `rerender()`. The rendered output is the public seam that the provider change must affect. Do not pass the new value through a mutable variable that the `wrapper` reads, or through a second mounted hook.\n\n## Missing facts\n\nWrite every assertion the supplied facts support, and keep that runnable test in the answer. When one expected outcome is undefined:\n\n1. Name the minimum contract in two parts: how the code signals the outcome (for example, a callback that rejects), and how a test can observe it (its role, its text or the callback it fires).\n2. Leave only that path as a `test.todo` that states what is needed.\n3. Continue the other work (`principle-never-block-on-the-human`).\n\nDo not invent copy, a role or a test id and assert it as though it was supplied. Do not delete the supported assertions because one path is undefined.\n\n## References\n\n| Reference | Read when |\n| --- | --- |\n| [components.md](references\u002Fcomponents.md) | Testing props to output, callbacks or conditional rendering |\n| [hooks.md](references\u002Fhooks.md) | Using `renderHook`, `result.current`, `act()` or `rerender()` |\n| [context.md](references\u002Fcontext.md) | Wrapping in providers or writing a custom render helper |\n| [forms.md](references\u002Fforms.md) | Testing inputs, submissions or validation |\n| [anti-patterns.md](references\u002Fanti-patterns.md) | Removing manual `act()`, manual `cleanup()`, `beforeEach` render, internals or shallow rendering |\n| [advanced.md](references\u002Fadvanced.md) | Testing loading states, error boundaries, portals or Suspense |\n\n## Done\n\n- `render()` and `renderHook()` come from `@testing-library\u002Freact`. No enzyme `shallow` or `mount`.\n- Every rule above holds in each returned test file and setup file.\n- An end-to-end request gets the named tool and slices. An undefined outcome stays a `test.todo`.\n","# React Testing Library\n\nFor a page or widget not built with React, use the `frontend-testing` skill. For the TDD workflow, use the `tdd` skill.\n\n## Core rules\n\nTest behaviour through public APIs: props in, rendered DOM out (`principle-test-behavior-not-implementation`). For each assertion, name a plausible wrong implementation that would still pass. Write the assertion that fails on it.\n\n- Query by accessible role, label or visible text.\n- Add `{ name }` to `getByRole` only when the element has an accessible name. Content names a `button`, `link` or `heading`. `aria-label` or `aria-labelledby` names an element whose role accepts an author-supplied name. A plain `\u003Cli>` takes no name from its text, so query it by that text.\n- Assert the call count with `toHaveBeenCalledTimes` as well as the arguments. `toHaveBeenCalledWith` alone does not prove the number of calls.\n- Do not test component state or methods. Do not assert on a class name, test id or handler name when accessible output proves the same behaviour. Do not use shallow rendering.\n- Do not wrap `render()`, `userEvent` calls or async queries in `act()`. RTL wraps them.\n- Do not call `cleanup()` in a test file. RTL cleans up automatically when the runner exposes a global `afterEach`. In Vitest, that needs `globals: true` or one `afterEach(cleanup)` in a shared setup file. When the project keeps globals off, put that call in the setup file, remove `cleanup` from every test file and leave the config unchanged.\n- Render through a factory function in each test, not a shared `beforeEach` render.\n\n## Project libraries\n\nUse the runner, matchers and helpers the project already has. Do not add a testing dependency that nobody asked for (`principle-reuse-before-building`).\n\n- If `@testing-library\u002Fuser-event` is installed, create `userEvent.setup()` in each test. If not, use `fireEvent` and say that `user-event` models the interaction more closely.\n- If the setup registers jest-dom matchers, use them, such as `toBeInTheDocument()`. If not, assert absence with `toBeNull()` and text with `textContent`.\n- Before you write a network stub or custom render helper, use the project's existing one, such as a `stubApi` function, an MSW `server` or a `renderWithProviders` helper.\n\n## Scope\n\nRTL renders one component tree, in jsdom or a browser test runner. Keep every test inside that tree.\n\nA request crosses that boundary when it needs a real network, a real email or a redirect to a third-party site. A demand for several real browsers is a coverage matrix for that journey, not a separate boundary. For such a request:\n\n1. Say it is end-to-end work. Name each external system from the request that it crosses.\n2. Recommend a browser-driven tool by name, such as Playwright or Cypress, for the journey.\n3. Name each slice RTL can still cover with the network boundary mocked: its component and the behaviour to assert (`principle-state-the-scope`).\n\nDo not offer a test that fakes those external systems as an equivalent of the journey.\n\n## Test allocation\n\nPrefer integration tests over unit tests.\n\n| Level | What to test | How many | Tools |\n| --- | --- | --- | --- |\n| Unit | Pure functions that hold a decision, such as a permission rule, a complex calculation or a shared utility | Each rule outside a component | Vitest, no renderer |\n| Integration | Features, user flows, component interactions | Most tests | Vitest + Testing Library |\n| E2E | Critical user journeys | Few, critical paths only | Playwright or Cypress |\n\nTest a permission rule in a plain function without rendering React (`react` skill). Test a state machine as an actor (`xstate` skill). Keep those unit tests. Do not move their rule into a rendered test.\n\n## Asynchronous results\n\nA view that loads or updates asynchronously shows its result after the first render. To assert that a value is absent from that result:\n\n1. Await a positive assertion, such as `await screen.findByText(...)`.\n2. Then assert the absence with a `queryBy*` query and `not.toBeInTheDocument()`.\n\nAn earlier absence check passes while the view still shows its loading state, so it proves nothing. Reach the result with awaited Testing Library APIs, not a fixed delay or an `act()` around `render()`. Use fake timers only when a timer is the behaviour under test. Then pass `advanceTimers` to `userEvent.setup()` and advance the clock with the runner's timer API.\n\nWhen an `async` handler calls a callback, await the callback assertion, for example `await waitFor(() => expect(onSave).toHaveBeenCalledTimes(1))`.\n\nAssert a synchronous initial state, such as a collapsed panel, directly after `render()`.\n\n## Hooks and context\n\nUse `renderHook` for hook-only behaviour. Its `initialProps` and `rerender(props)` reach the hook callback only, never the `wrapper`. Use the `wrapper` option to mount a provider with fixed props. When the test calls a state-changing hook callback directly, such as `result.current.addItem()`, wrap that call in `act()`. It runs outside RTL's auto-wrapped helpers.\n\nWhen a provider prop must change, render a small consumer component with `render()`. Change the prop through that render result's `rerender()`. The rendered output is the public seam that the provider change must affect. Do not pass the new value through a mutable variable that the `wrapper` reads, or through a second mounted hook.\n\n## Missing facts\n\nWrite every assertion the supplied facts support, and keep that runnable test in the answer. When one expected outcome is undefined:\n\n1. Name the minimum contract in two parts: how the code signals the outcome (for example, a callback that rejects), and how a test can observe it (its role, its text or the callback it fires).\n2. Leave only that path as a `test.todo` that states what is needed.\n3. Continue the other work (`principle-never-block-on-the-human`).\n\nDo not invent copy, a role or a test id and assert it as though it was supplied. Do not delete the supported assertions because one path is undefined.\n\n## References\n\n| Reference | Read when |\n| --- | --- |\n| [components.md](references\u002Fcomponents.md) | Testing props to output, callbacks or conditional rendering |\n| [hooks.md](references\u002Fhooks.md) | Using `renderHook`, `result.current`, `act()` or `rerender()` |\n| [context.md](references\u002Fcontext.md) | Wrapping in providers or writing a custom render helper |\n| [forms.md](references\u002Fforms.md) | Testing inputs, submissions or validation |\n| [anti-patterns.md](references\u002Fanti-patterns.md) | Removing manual `act()`, manual `cleanup()`, `beforeEach` render, internals or shallow rendering |\n| [advanced.md](references\u002Fadvanced.md) | Testing loading states, error boundaries, portals or Suspense |\n\n## Done\n\n- `render()` and `renderHook()` come from `@testing-library\u002Freact`. No enzyme `shallow` or `mount`.\n- Every rule above holds in each returned test file and setup file.\n- An end-to-end request gets the named tool and slices. An undefined outcome stays a `test.todo`.\n",{"name":5,"description":7},"main","0e0a9088ef87c2efb762c587ce6e949289321143","src\u002Fweb\u002Fskills\u002Freact-testing",7,"https:\u002F\u002Fgithub.com\u002Fmintuz\u002Fskills","https:\u002F\u002Fgithub.com\u002Fmintuz","http:\u002F\u002Fwww.mintuz.com","Working at @monzo, Previously worked at Moonpig, @booking and @bbc","2026-11-13 19:21:11",{"source":8,"skillName":5,"commands":54,"prompt":64,"zipAvailable":65},[55,58,61],{"tool":56,"command":57},"npx","npx skills add mintuz\u002Fskills --skill react-testing",{"tool":59,"command":60},"bunx","bunx skills add mintuz\u002Fskills --skill react-testing",{"tool":62,"command":63},"pnpm","pnpm dlx skills add mintuz\u002Fskills --skill react-testing","安装技能，技能地址：https:\u002F\u002Fgithub.com\u002Fmintuz\u002Fskills\u002Fblob\u002Fmain\u002Fsrc\u002Fweb\u002Fskills\u002Freact-testing\u002FSKILL.md",true,[67,73,77,81,85,89],{"path":68,"resourceType":69,"resourceTypeDesc":70,"sizeBytes":71,"sourceHtmlUrl":72},"references\u002Fadvanced.md","REFERENCE","参考文档",1306,"https:\u002F\u002Fgithub.com\u002Fmintuz\u002Fskills\u002Fblob\u002Fmain\u002Fsrc\u002Fweb\u002Fskills\u002Freact-testing\u002Freferences\u002Fadvanced.md",{"path":74,"resourceType":69,"resourceTypeDesc":70,"sizeBytes":75,"sourceHtmlUrl":76},"references\u002Fanti-patterns.md",2528,"https:\u002F\u002Fgithub.com\u002Fmintuz\u002Fskills\u002Fblob\u002Fmain\u002Fsrc\u002Fweb\u002Fskills\u002Freact-testing\u002Freferences\u002Fanti-patterns.md",{"path":78,"resourceType":69,"resourceTypeDesc":70,"sizeBytes":79,"sourceHtmlUrl":80},"references\u002Fcomponents.md",1551,"https:\u002F\u002Fgithub.com\u002Fmintuz\u002Fskills\u002Fblob\u002Fmain\u002Fsrc\u002Fweb\u002Fskills\u002Freact-testing\u002Freferences\u002Fcomponents.md",{"path":82,"resourceType":69,"resourceTypeDesc":70,"sizeBytes":83,"sourceHtmlUrl":84},"references\u002Fcontext.md",1168,"https:\u002F\u002Fgithub.com\u002Fmintuz\u002Fskills\u002Fblob\u002Fmain\u002Fsrc\u002Fweb\u002Fskills\u002Freact-testing\u002Freferences\u002Fcontext.md",{"path":86,"resourceType":69,"resourceTypeDesc":70,"sizeBytes":87,"sourceHtmlUrl":88},"references\u002Fforms.md",1584,"https:\u002F\u002Fgithub.com\u002Fmintuz\u002Fskills\u002Fblob\u002Fmain\u002Fsrc\u002Fweb\u002Fskills\u002Freact-testing\u002Freferences\u002Fforms.md",{"path":90,"resourceType":69,"resourceTypeDesc":70,"sizeBytes":91,"sourceHtmlUrl":92},"references\u002Fhooks.md",1206,"https:\u002F\u002Fgithub.com\u002Fmintuz\u002Fskills\u002Fblob\u002Fmain\u002Fsrc\u002Fweb\u002Fskills\u002Freact-testing\u002Freferences\u002Fhooks.md",[94,109,132,145,166,180],{"skillNo":95,"name":96,"nameZh":6,"description":97,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":98,"categories":99,"keywords":102,"publishedAt":39},"01M6C4PDGB6ZZWBS35N3DF7PZZ","xstate","WHEN React state changes in response to an external answer — async submit, in-flight or loading flags, retries, cancellation, polling, optimistic updates, stale responses — or to an interaction with an interruptible middle, such as a drag or a gesture; or WHEN building, reviewing, testing, or visualising XState 5 actors and @xstate\u002Freact integrations; NOT for a value one event sets completely, such as a text draft, a focus flag, or a plain open and closed toggle; models typed lifecycles and renders legal Mermaid stateDiagram-v2 charts.","https:\u002F\u002Fgithub.com\u002Fmintuz\u002Fskills\u002Fblob\u002Fmain\u002Fsrc\u002Fweb\u002Fskills\u002Fxstate\u002FSKILL.md",[100,101],{"categoryNo":19,"categoryName":20,"taxonomyType":21,"taxonomyTypeDesc":22},{"categoryNo":24,"categoryName":25,"taxonomyType":21,"taxonomyTypeDesc":22},[96,29,103,104,105,106,107,27,108],"text","state","integrations","Charts","mermaid","open",{"skillNo":110,"name":111,"nameZh":6,"description":112,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":113,"categories":114,"keywords":123,"publishedAt":39},"01M6C4PB6VVC2X19B63B7YNH0T","web-design","WHEN refining UI layout, typography, color, or polish; NOT code implementation; provides concise principles for intentional, legible design.","https:\u002F\u002Fgithub.com\u002Fmintuz\u002Fskills\u002Fblob\u002Fmain\u002Fsrc\u002Fweb\u002Fskills\u002Fweb-design\u002FSKILL.md",[115,120],{"categoryNo":116,"categoryName":117,"taxonomyType":118,"taxonomyTypeDesc":119},"01JBSEEDCAT000000000000032","设计师","PROFESSION","适用职业",{"categoryNo":121,"categoryName":122,"taxonomyType":21,"taxonomyTypeDesc":22},"01JBSEEDCAT000000000000015","视觉设计",[124,125,126,127,128,129,130,131],"web","design","web design","code implementation","polish","ui","typography","code",{"skillNo":133,"name":134,"nameZh":6,"description":135,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":136,"categories":137,"keywords":139,"publishedAt":39},"01M6C4P8D92GJDA49V7X1CZXEV","tailwind","USE WHEN writing, fixing or reviewing styling in a project that uses Tailwind CSS, even a one-class change or a request that does not name Tailwind: colours, focus rings, spacing, class names chosen by a prop, map or CVA variants, theme tokens and dark mode in the Tailwind stylesheet or tailwind.config, setup or upgrades (if unsure whether the project uses Tailwind, check package.json or the main stylesheet first); NOT WHEN writing plain CSS or Sass in a project without Tailwind; produces class names Tailwind can find, syntax for the installed major version, visible focus indicators, and no unrequested dependency or invented brand value.","https:\u002F\u002Fgithub.com\u002Fmintuz\u002Fskills\u002Fblob\u002Fmain\u002Fsrc\u002Fweb\u002Fskills\u002Ftailwind\u002FSKILL.md",[138],{"categoryNo":121,"categoryName":122,"taxonomyType":21,"taxonomyTypeDesc":22},[140,141,142,143,125,144],"Tailwind","libraries","component","css","design systems",{"skillNo":146,"name":147,"nameZh":6,"description":148,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":149,"categories":150,"keywords":154,"publishedAt":39},"01M6C4P5VWQ69Q32DA0634GDJY","refactoring","WHEN you need a plan to refactor, restructure, or clean up working code and the test result is known, either green or a recorded failing set; NOT for new feature delivery or any behavior change; reversible-baseline safety with prioritized improvements.","https:\u002F\u002Fgithub.com\u002Fmintuz\u002Fskills\u002Fblob\u002Fmain\u002Fsrc\u002Fweb\u002Fskills\u002Frefactoring\u002FSKILL.md",[151],{"categoryNo":152,"categoryName":153,"taxonomyType":21,"taxonomyTypeDesc":22},"01JBSEEDCAT000000000000007","代码审查",[147,155,156,157,158,159,160,161,162,131,163,164,165],"Safety","refactor","baseline","change","behavior","plan","SET","up","feature delivery","test","new feature",{"skillNo":167,"name":29,"nameZh":6,"description":168,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":169,"categories":170,"keywords":173,"publishedAt":39},"01M6C4P345APEFEX00J8T7QMXQ","USE WHEN changing the logic, data, props, state, Effects or rendered text of a React component, hook or page, even a one-line change; NOT WHEN the request is styling only (class names, Tailwind, CSS, dark mode, spacing, shadows) or tests only, or when it models submit, in-flight, loading, retry or failure states, even for a named React form (xstate covers that, including its React wiring); applies React 19 composition, state, Effect, structure, API and performance rules with only the project's installed libraries.","https:\u002F\u002Fgithub.com\u002Fmintuz\u002Fskills\u002Fblob\u002Fmain\u002Fsrc\u002Fweb\u002Fskills\u002Freact\u002FSKILL.md",[171,172],{"categoryNo":19,"categoryName":20,"taxonomyType":21,"taxonomyTypeDesc":22},{"categoryNo":24,"categoryName":25,"taxonomyType":21,"taxonomyTypeDesc":22},[29,174,143,140,175,27,31,131,35,176,38,104,164,177,178,179],"architecture","performance","api","state management","styling","management",{"skillNo":181,"name":182,"nameZh":6,"description":183,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":184,"categories":185,"keywords":188,"publishedAt":39},"01M6C4NY0FTYGTS7THKRAC20T3","frontend-testing","USE WHEN testing non-React UI (vanilla JavaScript or TypeScript DOM code, a web component, or a Vue, Svelte or Angular component) with DOM Testing Library in Vitest or Jest with jsdom: writing, fixing or reviewing a test, or a request to add an end-to-end journey or a layout check to that suite; NOT WHEN the code or project uses React or React Testing Library (use web:react-testing), for XState actors (web:xstate), or for Playwright, Cypress or screenshot-comparison work in a real browser; covers queries, accessible names, userEvent, async results, network stubs and assertions that pass for the wrong reason, and declines what jsdom cannot prove while offering the part that fits.","https:\u002F\u002Fgithub.com\u002Fmintuz\u002Fskills\u002Fblob\u002Fmain\u002Fsrc\u002Fweb\u002Fskills\u002Ffrontend-testing\u002FSKILL.md",[186,187],{"categoryNo":19,"categoryName":20,"taxonomyType":21,"taxonomyTypeDesc":22},{"categoryNo":24,"categoryName":25,"taxonomyType":21,"taxonomyTypeDesc":22},[27,189,190,191,192,193,159,33,34,129],"frontend testing","frontend","browser","first","regression"]