How to fix Cannot use namespace 'X' as a type in TypeScript

TypeScriptINTERMEDIATEMEDIUMUpdated Dec 8, 2025· 143 views

This error occurs when you try to use a namespace as a type annotation instead of as a value. Namespaces are organizational containers, not type definitions. The fix involves using 'typeof' keyword or refactoring to use interfaces/types directly.

Quick fix

Fixes TS2709

namespace Shapes {
  export interface Circle {
    radius: number;
  }
  export interface Square {
    side: number;
  }
}
  1. Identify what type you need from the namespace
  2. Use typeof keyword for namespace values
  3. Refactor to use interfaces or types directly
  4. Fix module declaration conflicts
typescript — error
namespace Shapes {
export interface Circle {
radius: number;
}
export interface Square {
side: number;
}
}
Cannot use namespace 'X' as a type

What this error means

In TypeScript, namespaces and types serve different purposes. A namespace is a organizational container that groups related code, while a type or interface defines the structure of data. TypeScript distinguishes between the namespace itself (a value) and the types contained within it. When you try to use a namespace name directly as a type annotation, TypeScript can't determine what you mean because a namespace is not a type—it's a collection of values and types. This error typically occurs in three scenarios: 1. Using the namespace name directly as a type instead of accessing a type within it 2. Mixing module declarations with imports inconsistently 3. Importing namespace modules and trying to use the namespace as a type The compiler error code is TS2709.

Typical symptoms

  • Compiler error 'TS2709: Cannot use namespace X as a type' appears on specific lines
  • The error points to a variable declaration, function parameter, or type annotation
  • The problematic line attempts to use a namespace name in a type position
  • Code compiles and runs fine if you use the namespace as a value but fails as a type
  • The issue appears immediately after importing a namespace with 'import * as'
  • Conditional type checks or generic constraints fail with this error

Common causes

  1. Using a namespace name directly in a type position instead of its exported type member (most common)
  2. Accidentally importing a module as a namespace then trying to use it as a type
  3. Inconsistent module declaration patterns mixing 'declare module' with regular imports
  4. Attempting to use 'typeof' on a namespace that exports only type members
  5. Type definitions file (.d.ts) accidentally declaring a namespace when it should be a module
  6. Package types export a namespace but your code expects it to be a type directly

How to fix "Cannot use namespace 'X' as a type"

1Identify what type you need from the namespace

First, understand the structure of the namespace you're using. If you have a namespace with exported members, you need to access the specific type, not the namespace itself.

Common namespace structure:

typescript
namespace Shapes {
  export interface Circle {
    radius: number;
  }
  export interface Square {
    side: number;
  }
}

When using this, you cannot do:

typescript
let shape: Shapes;  // ERROR: Cannot use namespace 'Shapes' as a type

Instead, access the specific type within it:

typescript
let circle: Shapes.Circle;  // CORRECT
2Use typeof keyword for namespace values

If you want to capture the type of a namespace itself (not an exported type within it), use the 'typeof' operator:

typescript
import * as Vector3 from './Vector3'

// Instead of:
type Vec = Vector3;  // ERROR

// Use typeof:
type Vec = typeof Vector3;

This creates a type that represents the shape of the namespace object itself, including all its exported members.

3Refactor to use interfaces or types directly

Instead of relying on namespaces for type grouping, use ES6 modules with explicit exports:

Before (namespace approach - problematic):

typescript
namespace Car {
  export interface Props {
    color: string;
    wheels: number;
  }
}

// This fails:
type CarType = Car;  // ERROR: Cannot use namespace as a type

After (module approach - recommended):

typescript
// car.ts
export interface CarProps {
  color: string;
  wheels: number;
}

// usage.ts
import type { CarProps } from './car'

type Car = CarProps;  // CORRECT
4Fix module declaration conflicts

If you have a 'declare module' statement conflicting with an import, remove the unnecessary declaration:

Problematic code:

typescript
declare module 'mylib';  // Declares a namespace

import { MyInterface } from 'mylib';  // Imports from same module

type Result = MyInterface;  // This can cause confusion

Solution:
Remove the 'declare module' line if you're already importing from the module. Use one approach or the other, not both:

typescript
// Keep only this:
import { MyInterface } from 'mylib';

type Result = MyInterface;  // Now works correctly
5Use namespace member access notation

If you must work with existing namespaces, access the types within them using dot notation:

typescript
namespace Database {
  export interface Connection {
    host: string;
    port: number;
  }

  export class ConnectionPool {
    // implementation
  }
}

// Correct ways to use it:
let conn: Database.Connection;  // Access the interface
let pool = new Database.ConnectionPool();  // Access the class

// Incorrect:
let x: Database;  // ERROR: Cannot use namespace as a type

Advanced notes

### Why Namespaces Are Problematic

TypeScript namespaces are an older pattern for code organization. They predate ES6 modules and were useful when modules weren't standardized. However, modern TypeScript and JavaScript use ES6 module syntax, which provides better clarity.

Mixing namespaces with modules creates ambiguity:

typescript
// Namespace declares a value container
namespace Utils {
  export const helper = () => {}
}

// But Utils is also a value, not just a type
// So: type X = Utils; is ambiguous

The recommended pattern today is:

typescript
// Export types and values separately
export interface Config {
  // type definition
}

export const createConfig = () => ({})  // value

### Barrel Exports

If you organize code with barrel exports (index.ts files), you can avoid namespace issues:

typescript
// api/index.ts (barrel file)
export * from './types';
export * from './client';
export * from './middleware';

// Usage:
import type { Request } from './api';  // Clear type import
import { createClient } from './api';   // Clear value import

### TypeScript Compiler Strict Mode

The --strict compiler flag makes namespace issues more apparent. If you see this error with strict mode enabled, it's almost always because of ambiguous namespace usage.

### Type-Only Imports (TypeScript 3.8+)

Use type-only imports to be explicit:

typescript
// Instead of:
import { Something } from './module';

// Use type-only imports for types:
import type { Something } from './module';

// This prevents namespace ambiguity issues

Frequently asked questions

What does "TS2709" mean?
In TypeScript, namespaces and types serve different purposes. A namespace is a organizational container that groups related code, while a type or interface defines the structure of data. TypeScript distinguishes between the namespace itself (a value) and the types contained within it.
How do I fix "TS2709"?
This error occurs when you try to use a namespace as a type annotation instead of as a value. Namespaces are organizational containers, not type definitions. The fix involves using 'typeof' keyword or refactoring to use interfaces/types directly.
What causes "TS2709"?
Using a namespace name directly in a type position instead of its exported type member (most common) Accidentally importing a module as a namespace then trying to use it as a type Inconsistent module declaration patterns mixing 'declare module' with regular imports
Is the "TS2709" error serious?
It is a medium-severity error — more of a blocker than a risk. The steps above resolve it.

Official resources & further reading