Skip to content

Members of re-exported namespace can be used as values but not types #35165

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

Closed
ultimatelostcause opened this issue Nov 18, 2019 · 3 comments
Closed
Labels
Question An issue which isn't directly actionable in code

Comments

@ultimatelostcause
Copy link

ultimatelostcause commented Nov 18, 2019

TypeScript Version: 3.8.0-dev.20191116

Search Terms:

  • export namespace
  • export merged namespace
  • export namespace type

Code

a.ts:

export namespace Foo {
   export class Bar {}
}

b.ts:

import {Foo as FooImpl} from './a.js'
export namespace Baz {
   export const Foo = FooImpl
}

Expected behavior:

import {Baz} from './b.js'
let x: Baz.Foo.Bar      // should compile without error

Actual behavior:

import {Baz} from './b.js'
let x: Baz.Foo.Bar      // Error: Namespace '".../b".Baz' has no exported member 'Foo'.
let y = new Baz.Foo.Bar // Ok

Playground Link:
I am unsure how to use TypeScript Playground to import custom modules.

Related Issues:

@ultimatelostcause
Copy link
Author

This is not surprising, since namespaces aren't types themselves, so can't be exported as types and therefore the nested types are lost.

import {Foo as FooImpl} from './a.js'
export namespace Baz {
   export const Foo = FooImpl
   //export type Foo = FooImpl  <-- can't do this, since namespaces aren't types
   //export namespace Foo = FooImpl  <-- can't do this, since namespaces can't be assigned
}

However, since the members can be accessed as values, they should also be accessible as types.

@RyanCavanaugh RyanCavanaugh added the Question An issue which isn't directly actionable in code label Nov 26, 2019
@RyanCavanaugh
Copy link
Member

You can use export import Foo = a.FooImpl with a qualified name (so use a top-level module import to a instead of destructring) if this is what you want to happen

@ultimatelostcause
Copy link
Author

Apologies, I was unaware of the export import syntax.

This most trivial change to b.ts to resolve this is:

import {Foo as FooImpl} from './a.js'
export namespace Baz {
   export import Foo = FooImpl
}

I note I was not able to find the export import syntax anywhere in the TypeScript documentation. Now I know what to look for, this appears to be a duplicate of issue 10058. I will close this and also update my Stack Overflow question with the answer.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Question An issue which isn't directly actionable in code
Projects
None yet
Development

No branches or pull requests

2 participants