-
-
Notifications
You must be signed in to change notification settings - Fork 8
Update react-dom peerDependencies to match react (17/18/19) #37
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: master
Are you sure you want to change the base?
Changes from all commits
3cce32f
280ce65
f8ed216
b3f06f7
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change | ||||||||||||||||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| @@ -1,6 +1,5 @@ | ||||||||||||||||||||||||||||||||
| import * as React from 'react' | ||||||||||||||||||||||||||||||||
| import ReactDOM from 'react-dom' | ||||||||||||||||||||||||||||||||
| import { Field } from 'react-final-form' | ||||||||||||||||||||||||||||||||
| import { Field, FieldRenderProps } from 'react-final-form' | ||||||||||||||||||||||||||||||||
| import { Html5ValidationFieldProps } from './types' | ||||||||||||||||||||||||||||||||
| import warning from './warning' | ||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||
|
|
@@ -24,6 +23,7 @@ | |||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||
| class Html5ValidationField extends React.Component<Html5ValidationFieldProps> { | ||||||||||||||||||||||||||||||||
| private input: WithValidity | null = null | ||||||||||||||||||||||||||||||||
| private fieldRef = React.createRef<any>() | ||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||
|
Comment on lines
+26
to
27
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🧩 Analysis chain🏁 Script executed: # First, locate and examine the Html5ValidationField.tsx file
find . -name "Html5ValidationField.tsx" -type fRepository: final-form/react-final-form-html5-validation Length of output: 118 🏁 Script executed: # Check the overall structure of the src directory
git ls-files | grep -E "^src/" | head -20Repository: final-form/react-final-form-html5-validation Length of output: 191 🏁 Script executed: # Check file size to determine how to read it
wc -l src/Html5ValidationField.tsxRepository: final-form/react-final-form-html5-validation Length of output: 120 🏁 Script executed: # Also check types.ts
wc -l src/types.tsRepository: final-form/react-final-form-html5-validation Length of output: 103 🏁 Script executed: cat -n src/Html5ValidationField.tsxRepository: final-form/react-final-form-html5-validation Length of output: 7178 🏁 Script executed: cat -n src/types.tsRepository: final-form/react-final-form-html5-validation Length of output: 1412 Forwarded ref type mismatch: assigns HTMLElement but exposes Html5ValidationField. The
This breaks TypeScript's contract for consumers. Callers will receive a DOM element but TypeScript will claim they have a component instance. Update all ref types to Proposed fix (this file)- private fieldRef = React.createRef<any>()
+ private fieldRef = React.createRef<HTMLElement>()
@@
-function Html5ValidationFieldWithRef(
+function Html5ValidationFieldWithRef(
props: Omit<Html5ValidationFieldProps, 'ref'>,
- ref: React.Ref<Html5ValidationField>
+ ref: React.Ref<HTMLElement>
): React.ReactElement {
@@
-const ForwardedHtml5ValidationField = React.forwardRef<
- Html5ValidationField,
+const ForwardedHtml5ValidationField = React.forwardRef<
+ HTMLElement,
Omit<Html5ValidationFieldProps, 'ref'>
>(Html5ValidationFieldWithRef)🧰 Tools🪛 GitHub Check: Lint[warning] 26-26: 🤖 Prompt for AI Agents |
||||||||||||||||||||||||||||||||
| static defaultProps = { | ||||||||||||||||||||||||||||||||
| badInput: 'Incorrect input', | ||||||||||||||||||||||||||||||||
|
|
@@ -42,7 +42,17 @@ | |||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||
| componentDidMount(): void { | ||||||||||||||||||||||||||||||||
| const root = ReactDOM.findDOMNode(this) | ||||||||||||||||||||||||||||||||
| this.findInput() | ||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||
| componentDidUpdate(): void { | ||||||||||||||||||||||||||||||||
| if (!this.input) { | ||||||||||||||||||||||||||||||||
| this.findInput() | ||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||
| private findInput = (): void => { | ||||||||||||||||||||||||||||||||
| const root = this.fieldRef.current | ||||||||||||||||||||||||||||||||
| if (root) { | ||||||||||||||||||||||||||||||||
| let input: WithValidity | null = null | ||||||||||||||||||||||||||||||||
| if (/input|textarea|select/.test(root.nodeName.toLowerCase())) { | ||||||||||||||||||||||||||||||||
|
|
@@ -120,6 +130,9 @@ | |||||||||||||||||||||||||||||||
| typeMismatch, | ||||||||||||||||||||||||||||||||
| valueMissing, | ||||||||||||||||||||||||||||||||
| innerRef, | ||||||||||||||||||||||||||||||||
| component, | ||||||||||||||||||||||||||||||||
| render, | ||||||||||||||||||||||||||||||||
| children, | ||||||||||||||||||||||||||||||||
| ...rest | ||||||||||||||||||||||||||||||||
| } = this.props | ||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||
|
|
@@ -137,11 +150,38 @@ | |||||||||||||||||||||||||||||||
| ...fieldProps | ||||||||||||||||||||||||||||||||
| } = rest | ||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||
| // Merge innerRef with fieldRef | ||||||||||||||||||||||||||||||||
| const mergedRef = (node: HTMLElement | null) => { | ||||||||||||||||||||||||||||||||
| (this.fieldRef as React.MutableRefObject<HTMLElement | null>).current = node | ||||||||||||||||||||||||||||||||
| if (typeof innerRef === 'function') { | ||||||||||||||||||||||||||||||||
| innerRef(node) | ||||||||||||||||||||||||||||||||
| } else if (innerRef) { | ||||||||||||||||||||||||||||||||
| (innerRef as React.MutableRefObject<HTMLElement | null>).current = node | ||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||
| // Wrap render function to inject ref | ||||||||||||||||||||||||||||||||
| const wrappedRender = (fieldProps: FieldRenderProps<any, HTMLElement>) => { | ||||||||||||||||||||||||||||||||
| // Call user's render/children function if provided | ||||||||||||||||||||||||||||||||
| const userRender = render || children | ||||||||||||||||||||||||||||||||
| if (userRender && typeof userRender === 'function') { | ||||||||||||||||||||||||||||||||
| const element = userRender(fieldProps) | ||||||||||||||||||||||||||||||||
| // Clone and inject ref | ||||||||||||||||||||||||||||||||
| return React.isValidElement(element) | ||||||||||||||||||||||||||||||||
| ? React.cloneElement(element, { ref: mergedRef } as any) | ||||||||||||||||||||||||||||||||
| : element | ||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||
| // Default: render input with ref | ||||||||||||||||||||||||||||||||
| return React.createElement(component || 'input', { | ||||||||||||||||||||||||||||||||
| ...fieldProps.input, | ||||||||||||||||||||||||||||||||
| ref: mergedRef | ||||||||||||||||||||||||||||||||
| }) | ||||||||||||||||||||||||||||||||
|
Comment on lines
+163
to
+178
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🧩 Analysis chain🏁 Script executed: # First, let's find and examine the Html5ValidationField.tsx file
find . -name "Html5ValidationField.tsx" -type fRepository: final-form/react-final-form-html5-validation Length of output: 118 🏁 Script executed: # Read the Html5ValidationField.tsx file to examine the code
wc -l ./src/Html5ValidationField.tsxRepository: final-form/react-final-form-html5-validation Length of output: 122 🏁 Script executed: # Read the entire file to understand the context
cat -n ./src/Html5ValidationField.tsxRepository: final-form/react-final-form-html5-validation Length of output: 7178 🏁 Script executed: # Let's check the types to understand FieldRenderProps better
find . -name "types.ts" -o -name "types.tsx" | head -5Repository: final-form/react-final-form-html5-validation Length of output: 321 🏁 Script executed: # Check the local types file
cat -n ./src/types.tsRepository: final-form/react-final-form-html5-validation Length of output: 1412 🏁 Script executed: # Let's check for test files related to Html5ValidationField
find . -path ./node_modules -prune -o -name "*.test.*" -o -name "*.spec.*" | grep -i "html5\|validation" | head -10Repository: final-form/react-final-form-html5-validation Length of output: 123 🏁 Script executed: # Read the test file to understand what tests are failing
cat -n ./src/Html5ValidationField.test.tsxRepository: final-form/react-final-form-html5-validation Length of output: 26470 🏁 Script executed: # Let's check what FieldRenderProps includes from react-final-form
find . -path ./node_modules/react-final-form -prune -o -type f -name "*.d.ts" -print | xargs grep -l "FieldRenderProps" 2>/dev/null | head -5Repository: final-form/react-final-form-html5-validation Length of output: 70 🏁 Script executed: # Check the react-final-form package for FieldRenderProps definition
find ./node_modules/react-final-form -name "*.d.ts" | head -10Repository: final-form/react-final-form-html5-validation Length of output: 154 🏁 Script executed: # Let's check the package.json to understand the react-final-form version
cat ./package.json | head -30Repository: final-form/react-final-form-html5-validation Length of output: 1488 🌐 Web query:
💡 Result: Here’s the TypeScript definition for export interface FieldInputProps<FieldValue = any, T extends HTMLElement = HTMLElement> {
name: string;
onBlur: (event?: React.FocusEvent<T>) => void;
onChange: (event: React.ChangeEvent<T> | any) => void;
onFocus: (event?: React.FocusEvent<T>) => void;
value: FieldValue;
checked?: boolean;
multiple?: boolean;
type?: string;
}
export interface FieldRenderProps<
FieldValue = any,
T extends HTMLElement = HTMLElement,
_FormValues = any
> {
input: FieldInputProps<FieldValue, T>;
meta: {
active?: boolean;
data?: Record<string, any>;
dirty?: boolean;
dirtySinceLastSubmit?: boolean;
error?: any;
initial?: any;
invalid?: boolean;
length?: number;
modified?: boolean;
modifiedSinceLastSubmit?: boolean;
pristine?: boolean;
submitError?: any;
submitFailed?: boolean;
submitSucceeded?: boolean;
submitting?: boolean;
touched?: boolean;
valid?: boolean;
validating?: boolean;
visited?: boolean;
};
}
Sources: [1] [2] 🏁 Script executed: # Let's verify that fieldProps from line 150 is indeed passed to the Field component
sed -n '181,186p' ./src/Html5ValidationField.tsxRepository: final-form/react-final-form-html5-validation Length of output: 220 🏁 Script executed: # Let me trace the issue more carefully - let's look at what FieldProps extends
web_search "react-final-form FieldProps interface definition"Repository: final-form/react-final-form-html5-validation Length of output: 138 🏁 Script executed: # Let me check if there's a way to pass attributes through Field to the wrapped render
grep -A 20 "interface FieldProps" ./src/types.tsRepository: final-form/react-final-form-html5-validation Length of output: 70 🏁 Script executed: # Let's understand the actual props flow better by checking how Field from react-final-form works
# First, let's see what the Html5ValidationFieldProps interface includes
cat -n ./src/types.tsRepository: final-form/react-final-form-html5-validation Length of output: 1412 🏁 Script executed: # Let me check if the tests are actually passing or failing currently
npm test 2>&1 | head -100Repository: final-form/react-final-form-html5-validation Length of output: 169 🏁 Script executed: # Let me trace through the logic more carefully by examining what happens with the props
# The key question is: when Field receives fieldProps from line 150, does it pass them through to wrappedRender?
# Let's create a simple analysis script
python3 << 'EOF'
# Trace the props flow
print("Props Flow Analysis:")
print("=" * 60)
print()
print("1. Html5ValidationField receives props (line 121-137):")
print(" - Destructures: validate, messages, innerRef, component, render, children")
print(" - Rest goes into: ...rest variable")
print()
print("2. Lines 140-151:")
print(" - Removes message keys from rest")
print(" - Remaining goes into: fieldProps")
print(" - fieldProps contains: name, data-testid, required, minLength, etc.")
print()
print("3. Line 181-185:")
print(" - Passes ...fieldProps to <Field> component")
print(" - Passes wrappedRender as children")
print()
print("4. Field component (from react-final-form):")
print(" - Receives fieldProps (name, data-testid, required, etc.)")
print(" - Calls wrappedRender(FieldRenderProps)")
print(" - FieldRenderProps = { input, meta }")
print()
print("5. wrappedRender (lines 164-179):")
print(" - Receives: FieldRenderProps = { input, meta }")
print(" - Does NOT have access to original custom attributes")
print(" - Line 176: Spreads only fieldProps.input")
print(" - RESULT: Custom attributes are LOST")
print()
print("ISSUE CONFIRMED:")
print("- Custom attributes (data-testid, required, minLength, etc.)")
print(" passed to Field on line 182 are not forwarded to the rendered element")
print("- They are only available on the DOM element if Field passes them,")
print(" which it typically doesn't for arbitrary attributes")
EOFRepository: final-form/react-final-form-html5-validation Length of output: 1293 Custom attributes are lost in the default render path. When To fix this, the original props passed to Html5ValidationField need to be accessible and forwarded within 🧰 Tools🪛 GitHub Check: Lint[warning] 171-171: [warning] 164-164: |
||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||
| return React.createElement(Field, { | ||||||||||||||||||||||||||||||||
| ...fieldProps, | ||||||||||||||||||||||||||||||||
| validate: this.validate, | ||||||||||||||||||||||||||||||||
| ref: innerRef as React.Ref<HTMLElement>, | ||||||||||||||||||||||||||||||||
| component: 'input' | ||||||||||||||||||||||||||||||||
| children: wrappedRender | ||||||||||||||||||||||||||||||||
| }) | ||||||||||||||||||||||||||||||||
|
Comment on lines
181
to
185
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🧩 Analysis chain🏁 Script executed: head -190 src/Html5ValidationField.tsx | tail -20Repository: final-form/react-final-form-html5-validation Length of output: 570 🏁 Script executed: sed -n '175,190p' src/Html5ValidationField.tsxRepository: final-form/react-final-form-html5-validation Length of output: 435 🏁 Script executed: find . -name "biome.json" -o -name ".biomerc*" -o -name "biome.jsonc" | head -5Repository: final-form/react-final-form-html5-validation Length of output: 100 🏁 Script executed: cat biome.json 2>/dev/null || cat biome.jsonc 2>/dev/null || echo "No Biome config found"Repository: final-form/react-final-form-html5-validation Length of output: 1871 🌐 Web query:
💡 Result: Biome’s Invalid (triggers rule) React.createElement("div", { children: "foo" });[1] Valid React.createElement("div", null, "foo");
// or
React.createElement("div", {}, "foo");(“children should be passed as additional arguments to JSX equivalent <div>foo</div>[1] If you truly need a prop named Biome lint error: pass children as the 3rd argument. Proposed fix- return React.createElement(Field, {
- ...fieldProps,
- validate: this.validate,
- children: wrappedRender
- })
+ return React.createElement(
+ Field,
+ {
+ ...fieldProps,
+ validate: this.validate
+ },
+ wrappedRender
+ )📝 Committable suggestion
Suggested change
🧰 Tools🪛 Biome (2.3.13)[error] 184-184: Avoid passing children using a prop The canonical way to pass children in React is to use additional arguments to React.createElement (lint/correctness/noChildrenProp) 🤖 Prompt for AI Agents |
||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||
Uh oh!
There was an error while loading. Please reload this page.