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

Docs: Partial Example Error from v3.5.1 #61

Closed
hookercookerman opened this issue Oct 4, 2019 · 2 comments · Fixed by #62
Closed

Docs: Partial Example Error from v3.5.1 #61

hookercookerman opened this issue Oct 4, 2019 · 2 comments · Fixed by #62

Comments

@hookercookerman
Copy link

hookercookerman commented Oct 4, 2019

Partial Example: error from 3.5.1

interface NodeConfig {
 		appName: string;
 		port: number;
 }

 class NodeAppBuilder {
 		private configuration: NodeConfig = {
 				appName: 'NodeApp',
 				port: 3000
 		};

 		config(config: Partial<NodeConfig>) {
 				type NodeConfigKey = keyof NodeConfig;

 				for (const key of Object.keys(config) as NodeConfigKey[]) {
 						const updateValue = config[key];

 						if (updateValue === undefined) {
 								continue;
 						}

 						this.configuration[key] = updateValue;
 				}

 				return this;
 		}
 }

 // `Partial<NodeConfig>`` allows us to provide only a part of the
 // NodeConfig interface.
 new NodeAppBuilder().config({appName: 'ToDoApp'});
Type 'string | number' is not assignable to type 'string & number'.
  Type 'string' is not assignable to type 'string & number'.
    Type 'string' is not assignable to type 'number'.

playground example

https://www.typescriptlang.org/play/?ts=3.3.3#code/JYOwLgpgTgZghgYwgAgHIHsAmEDC6QzADmyA3gLABQyycADnanALYQBcyAzmFKEQNxUaddFDAcQAV2YAjaIMoBfKlQQAbOJ05osEAIIMAQpOBrsUMkOR1eANziRkCfISKSoD4Pg4ZseAsTIALyW1DS0DEysHADkvvoMMQA0VsKi4sgAzAAMuVaKClbOAUQAFMWuHAAKcGLAcGoAPPH+rgB8AJSh4chgAJ50KC0uxADSEH3ByADWE+gwOn4jAiphNDCiyOX43DMTyPPIAPIyAFYQCGAAdLN9nNslXZqLuMvjfQDaALpdFGvhxV2kjomAcEAAag1JCgQhViB9bl9Cv8aMAFqVgaDIJC1NDgkEQpIQNhCCAIJhfqkek58GBQNCFNTkMpKFSaGAABbAThXOFuDx0-AIiZfKaYsE46FUllUqAQMDuEC9LmcRnMqgsoA

I would submit pull request but my typescript journey is just beginning; nut shell either typescript bug or from 3.5.1 strictness on this is tighter. But for me both types are string | number| so 🤷‍♂

@sindresorhus
Copy link
Owner

// @krnik

@ghost
Copy link

ghost commented Oct 4, 2019

Hi, I'll respond and try to fix the code on 7th Sept.

But, what's happening here is most likely caused by TypeScripts' 3.5 Fixes to unsound writes to indexed access types.

It's not really an access issue but assign issue. Since simply accessing the property by key works fine.
Any ideas why accessing and assigning gives different types?

  const x = this.configuration[key]; // string | number
  this.configuration[key] /* string & number */ = <value>; // TS 3.5
  this.configuration[key] /* never */ = <value>; // TS 3.6

Edit:
Related TS PR link

In a nut shell: indexed key assignment is more strict (sinze 3.5) and allows only writes that are certain to give correct result.

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 a pull request may close this issue.

2 participants