Skip to content

♻️ refactor(segments): convert SegmentSource to a function component - #4822

Open
riccio82 wants to merge 13 commits into
developfrom
refactor/hooks-segment-source
Open

riccio82 wants to merge 13 commits into
developfrom
refactor/hooks-segment-source

Conversation

@riccio82

@riccio82 riccio82 commented Sep 11, 2026

Copy link
Copy Markdown
Collaborator

Summary

Converts SegmentSource from a class to a function component — the last piece of the
segment editor still on class syntax. Behaviour is unchanged: it keeps its Flux listeners,
the DraftJS decorator pipeline and the split-mode flow.

The test suite is rewritten to drive the component through the DOM instead of an imperative
handle. The conversion had exposed ~27 internal methods via forwardRef/useImperativeHandle
purely so the class-era tests could keep calling them; no production caller ever passed a ref,
so that surface is gone.

Type

  • feat — new user-facing feature
  • fix — bug fix
  • refactor — restructure without behavior change
  • chore — build, deps, config, docs
  • perf — performance improvement
  • test — test coverage

Changes

File Change
public/js/components/segments/SegmentSource.js Class → function component: class fields become refs, setState becomes useState, lifecycle becomes effects. Destructures the segment prop and renames the context-derived one to contextSegment to resolve the collision. Five pure helpers extracted to module scope. No forwardRef/useImperativeHandle — the tag decorator's props are built once, so they read current data through latestRef/methodsRef, which is what this.context/this.state gave the class for free.
public/js/components/segments/SegmentSource.test.js Rewritten as black-box tests driven by real DOM events. The TagEntity double mirrors the real onClickBound, so clicking a rendered tag exercises the selection-dependent paths (options toolbar, AI assistant, split points) without a ref. Tests asserting internal state with no user-visible outcome removed.
.eslintrc.js Adds SegmentSource.js to the existing override banning class components in migrated files.
public/img/icons/*.js fill-rule/clip-rulefillRule/clipRule, silencing invalid-DOM-attribute warnings surfaced by the new tests.

Testing

  • vendor/bin/phpunit --exclude-group=ExternalServices --no-coverage passes
  • ./vendor/bin/phpstan passes (0 errors, with baseline)
  • Manual testing performed (describe below)
  • New tests added for changed behavior
  • Regression tests added for bug fixes

yarn test — 427 suites / 4384 tests green. SegmentSource.test.js is 57 tests and
SegmentSource.js sits at 88.2% lines, above the 80% floor for
public/js/components/segments/.

Manual testing in the CAT tool caught the regression noted below, which is now covered by
tests. No PHP is touched, so phpunit and phpstan do not apply.

AI Disclosure

  • No AI tools were used in this PR
  • AI tools were used — name the agent/tool below

Claude Code (Sonnet 5, Opus 5)

Notes

Part of the split of #4768 (wave 2, step 08 of 14) — see #4814 for the full merge-order plan.
Independent of step 09 (Editarea + SegmentTarget); both are only gated on step 07 (TagEntity),
already merged.

One regression was introduced and fixed within this PR: extracting getUpdatedSegmentInfo
into a pure function moved it inside the useRef initializer that builds the tag decorator,
freezing its inputs at first render, so a tag missing from the target stopped turning red in
the source. Fixed in 71cd271 with regression tests. Net behaviour against develop is
unchanged.

Ports SegmentSource from the class-to-hooks migration branch, and
extends the eslint class-component ratchet to this file (scoped to
just SegmentSource.js, since Editarea/SegmentTarget in the same
directory aren't migrated yet).

Destructures the single `segment` prop in the signature. Renames the
render-scope `const {segment} = context` to `contextSegment` to avoid
a collision — the component already tracked these as two distinct
values elsewhere (liveRef.current.segment vs liveRef.current.contextSegment),
this just extends that existing naming to the one spot that didn't use it.
@github-actions

Copy link
Copy Markdown

🧪 Test-Guard Report

✅ PASS — All changed source files have adequate test coverage.

Coverage Analysis: ❌ FAIL

No changed source files found in coverage report (threshold: 80%)

📋 1 files: 1 ✅ pass
File Verdict Reason
public/js/components/segments/SegmentSource.js ✅ pass in coverage report, but no executable lines changed

Test File Matching: ✅ PASS

File matching: 1 pass

📋 1 files: 1 ✅ pass
File Verdict Reason
public/js/components/segments/SegmentSource.js ✅ pass Test file modified in PR: public/js/components/segments/SegmentSource.test.js

Per-File Evaluation: ✅ PASS

All files resolved by deterministic shortcuts.

📋 1 files: 1 ⏭️ skip
File Verdict Reason
public/js/components/segments/SegmentSource.js ⏭️ skip shortcut → in coverage report, but no executable lines changed

Result: ✅ PASS

Replaces the 58-method instanceRef/methodsAssignedRef ceremony (needed
only so the old Enzyme-style tests could inspect the instance) with
plain per-render closures for everything except the handful of
functions that genuinely need a stable identity: the three Flux store
listeners (registered once, matched by reference) and the two methods
tests spy on. Those five share one methodsRef, assigned exactly once,
reading current data through a small latestRef mirror instead of the
original all-encompassing liveRef.

getSearchParams and isValidPhraseToAiAssistant are pure functions of
their arguments, so they're now module-level exports, testable
directly with no rendering.

Rewrites the test file's ~40 ref.current.state.X / direct-method-call
assertions to match: real DOM-observable triggers where jsdom allows
it, a handful of small explicitly-documented test-only accessors
where it doesn't (the same jsdom contentEditable/Selection limitation
the original tests already worked around). All 70 tests still pass,
same coverage.
@github-actions

Copy link
Copy Markdown

🧪 Test-Guard Report

✅ PASS — All changed source files have adequate test coverage.

Coverage Analysis: ❌ FAIL

No changed source files found in coverage report (threshold: 80%)

📋 1 files: 1 ✅ pass
File Verdict Reason
public/js/components/segments/SegmentSource.js ✅ pass in coverage report, but no executable lines changed

Test File Matching: ✅ PASS

File matching: 1 pass

📋 1 files: 1 ✅ pass
File Verdict Reason
public/js/components/segments/SegmentSource.js ✅ pass Test file modified in PR: public/js/components/segments/SegmentSource.test.js

Per-File Evaluation: ✅ PASS

All files resolved by deterministic shortcuts.

📋 1 files: 1 ⏭️ skip
File Verdict Reason
public/js/components/segments/SegmentSource.js ⏭️ skip shortcut → in coverage report, but no executable lines changed

Result: ✅ PASS

@github-actions

Copy link
Copy Markdown

🧪 Test-Guard Report

✅ PASS — All changed source files have adequate test coverage.

Coverage Analysis: ❌ FAIL

No changed source files found in coverage report (threshold: 80%)

📋 5 files: 4 ❌ fail, 1 ✅ pass
File Verdict Reason
public/img/icons/EyeOff.js ❌ fail not in coverage report
public/img/icons/EyeOn.js ❌ fail not in coverage report
public/img/icons/IconSplit.js ❌ fail not in coverage report
public/img/icons/social/Github.js ❌ fail not in coverage report
public/js/components/segments/SegmentSource.js ✅ pass in coverage report, but no executable lines changed

Test File Matching: ❌ FAIL

File matching: 1 pass, 4 fail

📋 5 files: 4 ❌ fail, 1 ✅ pass
File Verdict Reason
public/img/icons/EyeOff.js ❌ fail No matching test file found
public/img/icons/EyeOn.js ❌ fail No matching test file found
public/img/icons/IconSplit.js ❌ fail No matching test file found
public/img/icons/social/Github.js ❌ fail No matching test file found
public/js/components/segments/SegmentSource.js ✅ pass Test file modified in PR: public/js/components/segments/SegmentSource.test.js

Per-File Evaluation: ✅ PASS

Evaluated 5 files: 4 via AI (1 batch), 1 via shortcuts.

📋 5 files: 4 ✅ pass, 1 ⏭️ skip
File Verdict Reason
public/js/components/segments/SegmentSource.js ⏭️ skip shortcut → in coverage report, but no executable lines changed
public/img/icons/EyeOff.js ✅ pass Changes are purely syntactic refactoring of attribute naming to React standards.
public/img/icons/EyeOn.js ✅ pass Changes are purely syntactic refactoring of attribute naming to React standards.
public/img/icons/IconSplit.js ✅ pass Changes are purely syntactic refactoring of attribute naming to React standards.
public/img/icons/social/Github.js ✅ pass Changes are purely syntactic refactoring of attribute naming to React standards.

Result: ✅ PASS

Removes editAreaClasses/unlockedForCopy state — both were write-only
in the class component too, never read in render() or anywhere else,
only ever assigned via setState.

Converts endSplitMode and refreshTagMap from permanently-stable
useRef-wrapped functions to plain per-render closures (via useCallback,
depending only on what they actually read), each registered through
its own useEffect that re-subscribes to the matching SegmentStore
event whenever its dependencies change. setTaggedSource stays
permanently stable: its SET_SEGMENT_TAGGED listener is intentionally
never removed on cleanup (a pre-existing bug preserved verbatim), so
re-registering it on every dependency change would turn that one
leaked listener into one leaked per change instead.

getSelectedWords similarly becomes a plain closure; the two tests
that relied on jest.spyOn(ref.current, 'getSelectedWords') surviving
a re-render now mock DraftMatecatUtils.getSelectedTextWithoutEntities
instead — more robust, since it no longer depends on the spied
instance's identity at all. helpAiAssistant keeps its stable identity:
one test asserts its own invocation count across four rapid keyup
events, each of which triggers a re-render via its own
setIsShowingOptionsToolbar call.

latestRef shrinks accordingly (down to what setTaggedSource and
helpAiAssistant's delayed setTimeout still read). Net effect: useRef
calls 18 → 16, and the two remaining store-listener-driven functions
now follow an idiomatic register/cleanup pattern instead of a
permanent-registration-plus-live-mirror one.
@github-actions

Copy link
Copy Markdown

🧪 Test-Guard Report

✅ PASS — All changed source files have adequate test coverage.

Coverage Analysis: ❌ FAIL

No changed source files found in coverage report (threshold: 80%)

📋 5 files: 4 ❌ fail, 1 ✅ pass
File Verdict Reason
public/img/icons/EyeOff.js ❌ fail not in coverage report
public/img/icons/EyeOn.js ❌ fail not in coverage report
public/img/icons/IconSplit.js ❌ fail not in coverage report
public/img/icons/social/Github.js ❌ fail not in coverage report
public/js/components/segments/SegmentSource.js ✅ pass in coverage report, but no executable lines changed

Test File Matching: ❌ FAIL

File matching: 1 pass, 4 fail

📋 5 files: 4 ❌ fail, 1 ✅ pass
File Verdict Reason
public/img/icons/EyeOff.js ❌ fail No matching test file found
public/img/icons/EyeOn.js ❌ fail No matching test file found
public/img/icons/IconSplit.js ❌ fail No matching test file found
public/img/icons/social/Github.js ❌ fail No matching test file found
public/js/components/segments/SegmentSource.js ✅ pass Test file modified in PR: public/js/components/segments/SegmentSource.test.js

Per-File Evaluation: ✅ PASS

Evaluated 5 files: 4 via AI (1 batch), 1 via shortcuts.

📋 5 files: 4 ✅ pass, 1 ⏭️ skip
File Verdict Reason
public/js/components/segments/SegmentSource.js ⏭️ skip shortcut → in coverage report, but no executable lines changed
public/img/icons/EyeOff.js ✅ pass Change involves minor JSX attribute normalization, which is functionally equivalent to existing implementation.
public/img/icons/EyeOn.js ✅ pass Change involves minor JSX attribute normalization, which is functionally equivalent to existing implementation.
public/img/icons/IconSplit.js ✅ pass Change involves minor JSX attribute normalization, which is functionally equivalent to existing implementation.
public/img/icons/social/Github.js ✅ pass Change involves minor JSX attribute normalization, which is functionally equivalent to existing implementation.

Result: ✅ PASS

@github-actions

Copy link
Copy Markdown

🧪 Test-Guard Report

✅ PASS — All changed source files have adequate test coverage.

Coverage Analysis: ❌ FAIL

No changed source files found in coverage report (threshold: 80%)

📋 5 files: 4 ❌ fail, 1 ✅ pass
File Verdict Reason
public/img/icons/EyeOff.js ❌ fail not in coverage report
public/img/icons/EyeOn.js ❌ fail not in coverage report
public/img/icons/IconSplit.js ❌ fail not in coverage report
public/img/icons/social/Github.js ❌ fail not in coverage report
public/js/components/segments/SegmentSource.js ✅ pass in coverage report, but no executable lines changed

Test File Matching: ❌ FAIL

File matching: 1 pass, 4 fail

📋 5 files: 4 ❌ fail, 1 ✅ pass
File Verdict Reason
public/img/icons/EyeOff.js ❌ fail No matching test file found
public/img/icons/EyeOn.js ❌ fail No matching test file found
public/img/icons/IconSplit.js ❌ fail No matching test file found
public/img/icons/social/Github.js ❌ fail No matching test file found
public/js/components/segments/SegmentSource.js ✅ pass Test file modified in PR: public/js/components/segments/SegmentSource.test.js

Per-File Evaluation: ✅ PASS

Evaluated 5 files: 4 via AI (1 batch), 1 via shortcuts.

📋 5 files: 4 ✅ pass, 1 ⏭️ skip
File Verdict Reason
public/js/components/segments/SegmentSource.js ⏭️ skip shortcut → in coverage report, but no executable lines changed
public/img/icons/EyeOff.js ✅ pass This is a trivial syntax correction to React property naming conventions, requiring no functional tests.
public/img/icons/EyeOn.js ✅ pass This is a trivial syntax correction to React property naming conventions, requiring no functional tests.
public/img/icons/IconSplit.js ✅ pass This is a trivial syntax correction to React property naming conventions, requiring no functional tests.
public/img/icons/social/Github.js ✅ pass This is a trivial syntax correction to React property naming conventions, requiring no functional tests.

Result: ✅ PASS

@github-actions

Copy link
Copy Markdown

🧪 Test-Guard Report

✅ PASS — All changed source files have adequate test coverage.

Coverage Analysis: ❌ FAIL

No changed source files found in coverage report (threshold: 80%)

📋 5 files: 4 ❌ fail, 1 ✅ pass
File Verdict Reason
public/img/icons/EyeOff.js ❌ fail not in coverage report
public/img/icons/EyeOn.js ❌ fail not in coverage report
public/img/icons/IconSplit.js ❌ fail not in coverage report
public/img/icons/social/Github.js ❌ fail not in coverage report
public/js/components/segments/SegmentSource.js ✅ pass in coverage report, but no executable lines changed

Test File Matching: ❌ FAIL

File matching: 1 pass, 4 fail

📋 5 files: 4 ❌ fail, 1 ✅ pass
File Verdict Reason
public/img/icons/EyeOff.js ❌ fail No matching test file found
public/img/icons/EyeOn.js ❌ fail No matching test file found
public/img/icons/IconSplit.js ❌ fail No matching test file found
public/img/icons/social/Github.js ❌ fail No matching test file found
public/js/components/segments/SegmentSource.js ✅ pass Test file modified in PR: public/js/components/segments/SegmentSource.test.js

Per-File Evaluation: ✅ PASS

AI analysis failed (Error code: 503 - [{'error': {'code': 503, 'message': 'This model is currently experiencing high demand. Spikes in demand are usually temporary. Please try again later.', 'status': 'UNAVAILABLE'}}]) — shortcuts resolved; remaining files deferred to L1+L2.

📋 5 files: 5 ⏭️ skip
File Verdict Reason
public/js/components/segments/SegmentSource.js ⏭️ skip shortcut → in coverage report, but no executable lines changed
public/img/icons/EyeOff.js ⏭️ skip AI analysis unavailable — deferred to Layer 2
public/img/icons/EyeOn.js ⏭️ skip AI analysis unavailable — deferred to Layer 2
public/img/icons/IconSplit.js ⏭️ skip AI analysis unavailable — deferred to Layer 2
public/img/icons/social/Github.js ⏭️ skip AI analysis unavailable — deferred to Layer 2

Result: ✅ PASS

@github-actions

Copy link
Copy Markdown

🧪 Test-Guard Report

✅ PASS — All changed source files have adequate test coverage.

Coverage Analysis: ❌ FAIL

No changed source files found in coverage report (threshold: 80%)

📋 5 files: 4 ❌ fail, 1 ✅ pass
File Verdict Reason
public/img/icons/EyeOff.js ❌ fail not in coverage report
public/img/icons/EyeOn.js ❌ fail not in coverage report
public/img/icons/IconSplit.js ❌ fail not in coverage report
public/img/icons/social/Github.js ❌ fail not in coverage report
public/js/components/segments/SegmentSource.js ✅ pass in coverage report, but no executable lines changed

Test File Matching: ❌ FAIL

File matching: 1 pass, 4 fail

📋 5 files: 4 ❌ fail, 1 ✅ pass
File Verdict Reason
public/img/icons/EyeOff.js ❌ fail No matching test file found
public/img/icons/EyeOn.js ❌ fail No matching test file found
public/img/icons/IconSplit.js ❌ fail No matching test file found
public/img/icons/social/Github.js ❌ fail No matching test file found
public/js/components/segments/SegmentSource.js ✅ pass Test file modified in PR: public/js/components/segments/SegmentSource.test.js

Per-File Evaluation: ✅ PASS

Evaluated 5 files: 4 via AI (1 batch), 1 via shortcuts.

📋 5 files: 4 ✅ pass, 1 ⏭️ skip
File Verdict Reason
public/js/components/segments/SegmentSource.js ⏭️ skip shortcut → in coverage report, but no executable lines changed
public/img/icons/EyeOff.js ✅ pass Refactoring attribute naming to valid React JSX syntax does not change visual behavior.
public/img/icons/EyeOn.js ✅ pass Refactoring attribute naming to valid React JSX syntax does not change visual behavior.
public/img/icons/IconSplit.js ✅ pass Refactoring attribute naming to valid React JSX syntax does not change visual behavior.
public/img/icons/social/Github.js ✅ pass Refactoring attribute naming to valid React JSX syntax does not change visual behavior.

Result: ✅ PASS

@github-actions

Copy link
Copy Markdown

🧪 Test-Guard Report

✅ PASS — All changed source files have adequate test coverage.

Coverage Analysis: ❌ FAIL

No changed source files found in coverage report (threshold: 80%)

📋 5 files: 4 ❌ fail, 1 ✅ pass
File Verdict Reason
public/img/icons/EyeOff.js ❌ fail not in coverage report
public/img/icons/EyeOn.js ❌ fail not in coverage report
public/img/icons/IconSplit.js ❌ fail not in coverage report
public/img/icons/social/Github.js ❌ fail not in coverage report
public/js/components/segments/SegmentSource.js ✅ pass in coverage report, but no executable lines changed

Test File Matching: ❌ FAIL

File matching: 1 pass, 4 fail

📋 5 files: 4 ❌ fail, 1 ✅ pass
File Verdict Reason
public/img/icons/EyeOff.js ❌ fail No matching test file found
public/img/icons/EyeOn.js ❌ fail No matching test file found
public/img/icons/IconSplit.js ❌ fail No matching test file found
public/img/icons/social/Github.js ❌ fail No matching test file found
public/js/components/segments/SegmentSource.js ✅ pass Test file modified in PR: public/js/components/segments/SegmentSource.test.js

Per-File Evaluation: ✅ PASS

AI analysis failed (Error code: 503 - [{'error': {'code': 503, 'message': 'This model is currently experiencing high demand. Spikes in demand are usually temporary. Please try again later.', 'status': 'UNAVAILABLE'}}]) — shortcuts resolved; remaining files deferred to L1+L2.

📋 5 files: 5 ⏭️ skip
File Verdict Reason
public/js/components/segments/SegmentSource.js ⏭️ skip shortcut → in coverage report, but no executable lines changed
public/img/icons/EyeOff.js ⏭️ skip AI analysis unavailable — deferred to Layer 2
public/img/icons/EyeOn.js ⏭️ skip AI analysis unavailable — deferred to Layer 2
public/img/icons/IconSplit.js ⏭️ skip AI analysis unavailable — deferred to Layer 2
public/img/icons/social/Github.js ⏭️ skip AI analysis unavailable — deferred to Layer 2

Result: ✅ PASS

… through the DOM

SegmentWrapper renders SegmentSource without a ref, so the forwardRef wrapper, the
useImperativeHandle surface and its 27 exposed methods existed only to let the tests reach
internals. Remove them, along with the stable-assignment guard, the test-only editor accessor
and the useReducer that backed a ref forceUpdate.

methodsRef stays at three entries (checkDecorators, updateSourceInStore, getSelectedWords),
which the call sites frozen relative to render still read to avoid stale closures. Dropping
the ref also leaves setSource, setEditorStateBeforeSplit and disableDecorator unreferenced.

Tests move to black-box DOM interaction. The TagEntity double now mirrors the real
onClickBound, calling back with the entity's own offsets and name, so clicking a tag makes the
component force a non-collapsed selection the same way it does in the browser. That reaches
the options toolbar, the AI assistant debounce, glossary prefill and split-point removal
without a ref. Tests asserting internal state with no user-visible outcome are removed.
@github-actions

Copy link
Copy Markdown

🧪 Test-Guard Report

✅ PASS — All changed source files have adequate test coverage.

Coverage Analysis: ❌ FAIL

No changed source files found in coverage report (threshold: 80%)

📋 5 files: 4 ❌ fail, 1 ✅ pass
File Verdict Reason
public/img/icons/EyeOff.js ❌ fail not in coverage report
public/img/icons/EyeOn.js ❌ fail not in coverage report
public/img/icons/IconSplit.js ❌ fail not in coverage report
public/img/icons/social/Github.js ❌ fail not in coverage report
public/js/components/segments/SegmentSource.js ✅ pass in coverage report, but no executable lines changed

Test File Matching: ❌ FAIL

File matching: 1 pass, 4 fail

📋 5 files: 4 ❌ fail, 1 ✅ pass
File Verdict Reason
public/img/icons/EyeOff.js ❌ fail No matching test file found
public/img/icons/EyeOn.js ❌ fail No matching test file found
public/img/icons/IconSplit.js ❌ fail No matching test file found
public/img/icons/social/Github.js ❌ fail No matching test file found
public/js/components/segments/SegmentSource.js ✅ pass Test file modified in PR: public/js/components/segments/SegmentSource.test.js

Per-File Evaluation: ✅ PASS

AI analysis failed (Error code: 503 - [{'error': {'code': 503, 'message': 'This model is currently experiencing high demand. Spikes in demand are usually temporary. Please try again later.', 'status': 'UNAVAILABLE'}}]) — shortcuts resolved; remaining files deferred to L1+L2.

📋 5 files: 5 ⏭️ skip
File Verdict Reason
public/js/components/segments/SegmentSource.js ⏭️ skip shortcut → in coverage report, but no executable lines changed
public/img/icons/EyeOff.js ⏭️ skip AI analysis unavailable — deferred to Layer 2
public/img/icons/EyeOn.js ⏭️ skip AI analysis unavailable — deferred to Layer 2
public/img/icons/IconSplit.js ⏭️ skip AI analysis unavailable — deferred to Layer 2
public/img/icons/social/Github.js ⏭️ skip AI analysis unavailable — deferred to Layer 2

Result: ✅ PASS

The tag decorator is built once and kept in a ref, so its props are frozen relative to render.
6bf1f4b changed getUpdatedSegmentInfo from a stable function reading the live ref into an
arrow capturing contextSegment/tagRange/editorState, freezing them at the first render. TagEntity
re-renders itself off EDIT_AREA_CHANGED and calls that prop to pick its warning styling, so a tag
that only enters missingTagsInTarget after mount never turned red.

Read contextSegment, tagRange, editorState and segment through latestRef, and route onClick
through methodsRef, restoring what this.context/this.state gave the class version. onClick was
stale the same way, forcing selection against a first-render editorState.
@github-actions

Copy link
Copy Markdown

🧪 Test-Guard Report

✅ PASS — All changed source files have adequate test coverage.

Coverage Analysis: ❌ FAIL

No changed source files found in coverage report (threshold: 80%)

📋 5 files: 4 ❌ fail, 1 ✅ pass
File Verdict Reason
public/img/icons/EyeOff.js ❌ fail not in coverage report
public/img/icons/EyeOn.js ❌ fail not in coverage report
public/img/icons/IconSplit.js ❌ fail not in coverage report
public/img/icons/social/Github.js ❌ fail not in coverage report
public/js/components/segments/SegmentSource.js ✅ pass in coverage report, but no executable lines changed

Test File Matching: ❌ FAIL

File matching: 1 pass, 4 fail

📋 5 files: 4 ❌ fail, 1 ✅ pass
File Verdict Reason
public/img/icons/EyeOff.js ❌ fail No matching test file found
public/img/icons/EyeOn.js ❌ fail No matching test file found
public/img/icons/IconSplit.js ❌ fail No matching test file found
public/img/icons/social/Github.js ❌ fail No matching test file found
public/js/components/segments/SegmentSource.js ✅ pass Test file modified in PR: public/js/components/segments/SegmentSource.test.js

Per-File Evaluation: ✅ PASS

Evaluated 5 files: 4 via AI (1 batch), 1 via shortcuts.

📋 5 files: 4 ✅ pass, 1 ⏭️ skip
File Verdict Reason
public/js/components/segments/SegmentSource.js ⏭️ skip shortcut → in coverage report, but no executable lines changed
public/img/icons/EyeOff.js ✅ pass This is a non-functional syntax refactor (SVG attribute normalization) and requires no testing.
public/img/icons/EyeOn.js ✅ pass This is a non-functional syntax refactor (SVG attribute normalization) and requires no testing.
public/img/icons/IconSplit.js ✅ pass This is a non-functional syntax refactor (SVG attribute normalization) and requires no testing.
public/img/icons/social/Github.js ✅ pass This is a non-functional syntax refactor (SVG attribute normalization) and requires no testing.

Result: ✅ PASS

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant