[typescript] error TS2339: Property 'x' does not exist on type 'Y'

I don't understand why this code generates TypeScript error. (It's not the original code and is a bit derived, so please ignore the non-sense in the example):

interface Images {
  [key:string]: string;
}

function getMainImageUrl(images: Images): string {
  return images.main;
}

I'm getting error (using TypeScript 1.7.5):

error TS2339: Property 'main' does not exist on type 'Images'.

Of course I could get rid of the error when writing:

return images["main"];

I'd prefer not using string to access the property. What can I do?

This question is related to typescript

The answer is


The correct fix is to add the property in the type definition as explained by @Nitzan Tomer. But also you can just define property as any, if you want to write code almost as in JavaScript:

arr.filter((item:any) => {
    return item.isSelected == true;
}

The correct fix is to add the property in the type definition as explained in @Nitzan Tomer's answer. If that's not an option though:

(Hacky) Workaround 1

You can assign the object to a constant of type any, then call the 'non-existing' property.

const newObj: any = oldObj;
return newObj.someProperty;

You can also cast it as any:

return (oldObj as any).someProperty;

This fails to provide any type safety though, which is the point of TypeScript.


(Hacky) Workaround 2

Another thing you may consider, if you're unable to modify the original type, is extending the type like so:

interface NewType extends OldType {
  someProperty: string;
}

Now you can cast your variable as this NewType instead of any. Still not ideal but less permissive than any, giving you more type safety.

return (oldObj as NewType).someProperty;

I'm no expert in Typescript, but I think the main problem is the way of accessing data. Seeing how you described your Images interface, you can define any key as a String.

When accessing a property, the "dot" syntax (images.main) supposes, I think, that it already exists. I had such problems without Typescript, in "vanilla" Javascript, where I tried to access data as:

return json.property[0].index

where index was a variable. But it interpreted index, resulting in a:

cannot find property "index" of json.property[0]

And I had to find a workaround using your syntax:

return json.property[0][index]

It may be your only option there. But, once again, I'm no Typescript expert, if anyone knows a better solution / explaination about what happens, feel free to correct me.


Starting with TypeScript 2.2 using dot notation to access indexed properties is allowed. You won't get error TS2339 on your example.

See Dotted property for types with string index signatures in TypeScript 2.2 release note.


I was getting this error on Vue 3. It was because defineComponent must be imported like this:

<script lang="ts">
import { defineComponent } from "vue";

export default defineComponent({
    name: "HelloWorld",
    props: {
        msg: String,
    },
    created() {
        this.testF();
    },
    methods: {
        testF() {
            console.log("testF");
        },
    },
});
</script>