Skip to content
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

Typescript interfaces do not guarantee that properties required by interfaces are gettable or settable #25650

Closed
jasonbaker opened this issue Jul 13, 2018 · 4 comments
Labels
Duplicate An existing issue was already created

Comments

@jasonbaker
Copy link

TypeScript Version: 3.0.0-dev.201xxxxx

Search Terms:
typescript interface getter setter

Code

interface Blah {
  a: string;
}

class SettableBlah implements Blah{
  // No error for not having a getter
  set a(val: string) {
  }
}

class GettableBlah implements Blah{
  // No error for not having a setter
  get a() {
    return 'a';
  }
}

const s: Blah = new SettableBlah();
// No error for SettableBlah not having a getter
s.a;

const g: Blah = new GettableBlah();
// No error for GettableBlah not having a setter
g.a = 'a';

Expected behavior:

My expectation is that if an interface specifies a property a, it is read-write. If that interface specifies readonly a, that property should be readonly. However typescript appears to guarantee neither readability nor writability (only that the property is either readable or writable). So I would expect this code to not compile for a couple of reasons:

  1. SettableBlah does not have a getter for a
  2. GettableBlah does not have a setter and the field is not marked readonly.

Actual behavior:

The code compiles and breaks at runtime for reasons that might be difficult for the programmer to track down.

Playground Link: http://www.typescriptlang.org/play/#src=interface%20Blah%20%7B%0D%0A%20%20a%3A%20string%3B%0D%0A%7D%0D%0A%0D%0Aclass%20SettableBlah%20implements%20Blah%7B%0D%0A%20%20%2F%2F%20No%20error%20for%20not%20having%20a%20getter%0D%0A%20%20set%20a(val%3A%20string)%20%7B%0D%0A%20%20%7D%0D%0A%7D%0D%0A%0D%0Aclass%20GettableBlah%20implements%20Blah%7B%0D%0A%20%20%2F%2F%20No%20error%20for%20not%20having%20a%20setter%0D%0A%20%20get%20a()%20%7B%0D%0A%20%20%20%20return%20'a'%3B%0D%0A%20%20%7D%0D%0A%7D%0D%0A%0D%0Aconst%20s%3A%20Blah%20%3D%20new%20SettableBlah()%3B%0D%0A%2F%2F%20No%20error%20for%20SettableBlah%20not%20having%20a%20getter%0D%0As.a%3B%0D%0A%0D%0Aconst%20g%3A%20Blah%20%3D%20new%20GettableBlah()%3B%0D%0A%2F%2F%20No%20error%20for%20GettableBlah%20not%20having%20a%20setter%0D%0Ag.a%20%3D%20'a'%3B

Related Issues:

This is related to #11596. This bug references behavior that allows a write-only property (which is specified to be unsupported in 11596) to be treated as read-write behavior by the compiler.

@jasonbaker jasonbaker changed the title Typescript interfaces do not guarantee that properties are gettable or settable Typescript interfaces do not guarantee that properties required by interfaces are gettable or settable Jul 13, 2018
@mhegazy mhegazy added the Duplicate An existing issue was already created label Jul 13, 2018
@mhegazy
Copy link
Contributor

mhegazy commented Jul 13, 2018

#11481 tracks the issue.

I could see us erroring on set-only class implementation since the getter type is undefined.

@jasonbaker
Copy link
Author

Does this mean that there's no way the compiler can guarantee that a field that is not marked readonly has both a getter and a setter?

@mhegazy
Copy link
Contributor

mhegazy commented Jul 18, 2018

An interface is a contract. if the contract has a non-readonly property, it means you can assign to it, and you can read its value (nothing in the contract says that they both have to be the same).

A get-only property can still be written to. so that satisfies the contract. A set-only property can still be read from, but it has the value undefined at runtime. so the compiler should flag this as a violation of the contract, and it is not doing this today.

@typescript-bot
Copy link
Collaborator

Automatically closing this issue for housekeeping purposes. The issue labels indicate that it is unactionable at the moment or has already been addressed.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Duplicate An existing issue was already created
Projects
None yet
Development

No branches or pull requests

3 participants