Last updated: Jan 24, 2023
Reading timeยท4 min
If you got the error when using React.js, click on the second subheading.
The error "Property 'X' does not exist on type 'EventTarget'" occurs when we
try to access a property that doesn't exist on the EventTarget
interface.
To solve the error, use a type assertion to type the element correctly before accessing the property.
This is the index.html
file for the example.
<!DOCTYPE html> <html> <head> <meta charset="UTF-8" /> </head> <body> <input id="first_name" type="text" name="first_name" value="Initial Value" /> <script src="./src/index.ts"></script> </body> </html>
And here is an example of how the error occurs in the index.ts
file.
const input = document.getElementById('first_name'); // โ๏ธ Property 'value' does not exist on type 'EventTarget'.ts(2339) function handleEvent(event: Event) { console.log(event.target?.value); } input?.addEventListener('input', handleEvent);
The reason we got the error is that the EventTarget
interface doesn't contain a
value
property.
The EventTarget
interface contains only a few properties like
addEventListener
, removeEventListener
and dispatchEvent
.
To solve the error, use a type assertion to type the element as
HTMLInputElement
.
const input = document.getElementById('first_name'); function handleEvent(event: Event) { const target = event.target as HTMLInputElement; console.log(target.value); } input?.addEventListener('input', handleEvent);
We assigned the event.target
property to a target
variable and typed it as
an HTMLInputElement
so we can access its value
property.
The EventTarget
interface doesn't contain a value
property, so we typed the
target
property as an HTMLInputElement
instead.
HTML***Element
. Once you start typing HTML..
, your IDE should be able to help you with autocomplete.Some commonly used types are: HTMLInputElement
, HTMLButtonElement
,
HTMLAnchorElement
, HTMLImageElement
, HTMLTextAreaElement
,
HTMLSelectElement
, etc.
You could also use the type assertion inline.
const input = document.getElementById('first_name'); function handleEvent(event: Event) { const result = (event.target as HTMLInputElement).value; console.log(result); } input?.addEventListener('input', handleEvent);
Type assertions are used when we have information about the type of a value that TypeScript can't know about.
target
variable stores anHTMLInputElement
and not to worry about it.Notice that we used the optional chaining (?.) operator in the example.
input?.addEventListener('input', event => {})
The optional chaining (?.) operator
short-circuits and returns undefined
if the value to the left is nullish
(null
or undefined
).
The document.getElementById method
returns null
if an element with the supplied if
is not found, so we have to
make sure the element exists before accessing any properties.
The same can be achieved by using a simple if
statement that serves as a type
guard.
const input = document.getElementById('first_name'); function handleEvent(event: Event) { const target = event.target as HTMLInputElement; console.log(target.value); } // ๐๏ธ input has type HTMLElement or null here if (input) { // ๐๏ธ input has type HTMLElement here input.addEventListener('input', handleEvent); }
Once we enter the if
block, TypeScript knows that the input
variable stores
an HTMLElement and not a null
value.
You can also define the event handler function inline and pass it as the second
argument to the addEventListener()
method.
const input = document.getElementById('first_name'); input?.addEventListener('input', event => { const target = event.target as HTMLInputElement; console.log(target.value); });
When we write the event handler function inline, we don't have to type the
event
parameter as Event
because TypeScript is able to infer its type.
I've also written a detailed guide on how to get the value of an input element in TS.
The React.js error "Property 'value' does not exist on type EventTarget" occurs when the type of the event parameter is incorrect.
To solve the error, type the event as React.ChangeEvent<HTMLInputElement>
. You
can then access the value as event.target.value
.
Here is an example of how the error occurs.
function App() { // ๐๏ธ incorrect event type const handleChange = (event: Event) => { console.log(event.target?.value); }; return ( <div> {/* โ๏ธ Property 'value' does not exist on type 'EventTarget'. */} <input onChange={handleChange} type="text" id="message" /> </div> ); } export default App;
To solve the error, we have to type the event
parameter as:
React.ChangeEvent<HTMLInputElement>
for an input element.React.ChangeEvent<HTMLTextAreaElement>
for a textarea
element.function App() { // โ correct event type const handleChange = ( event: React.ChangeEvent<HTMLInputElement>, ) => { console.log(event.target.value); }; return ( <div> <input onChange={handleChange} type="text" id="message" /> </div> ); } export default App;
The ChangeEvent
type in React has a target
property that refers to the
element on which the event is dispatched.
You can find out what the type of an event is by writing the event handler
inline and hovering over the event
parameter in the function.
function App() { // ๐๏ธ event is written inline return ( <div> <input onChange={e => console.log(e.target.value)} type="text" id="message" /> </div> ); } export default App;
The screenshot shows that when we hover over the e
variable in the inline
event handler, we get the correct type for the event.
TypeScript is always going to be able to infer the event
type on an inline
event handler because you have the type definitions for React installed.
# ๐๏ธ with NPM npm install --save-dev @types/react @types/react-dom # ---------------------------------------------- # ๐๏ธ with YARN yarn add @types/react @types/react-dom --dev
The code sample installs the typings for react
and react-dom
.
You can learn more about the related topics by checking out the following tutorials: