FrontendPrep
Menu
Topics
Questions
Guides
Challenges
Soon
typescriptEasy

TypeScript: any vs. unknown

Understand the differences between any and unknown in TypeScript. Learn when to use which, type assertion, type narrowing, and type safety best practices.

TypeScript: any vs. unknown

One of the most common introductory TypeScript interview questions is:

What is the difference between any and unknown in TypeScript? When should you choose one over the other?

Both types are used when we do not know the type of a value ahead of time (for example, when parsing third-party JSON API payloads). However, they interact with the TypeScript compiler in fundamentally different ways.


1. The Core Difference: Type Safety

The key difference lies in whether the compiler enforces type safety checks:

  • any is unsafe: It effectively disables the type checker. You can access any property, invoke it as a function, or assign it to any type without compile-time errors.
  • unknown is safe: It represents a value that could be anything, but you must perform type narrowing (type checks) or type assertion before you can perform any operations on it.
       any (Opt-out of checking)
       ┌────────────────────────┐
       │ value.foo();           │ ◄── Allowed (Unsafe: may crash at runtime)
       │ value.bar = 10;        │
       └────────────────────────┘
 
       unknown (Safe container)
       ┌────────────────────────┐
       │ value.foo();           │ ◄── Compile Error (Safe: compiler blocks access)
       │ if (typeof value ===   │
       │    'function') {       │
       │    value();            │ ◄── Allowed after narrowing!
       │ }                      │
       └────────────────────────┘

2. Comparing Behaviors in Code

A. Operations with any

let value: any;
 
value.trim();       // OK
value();            // OK
value.foo.bar = 10; // OK

At runtime, if value is a number, the first two calls will crash with a TypeError. The compiler will not warn you.

B. Operations with unknown

let value: unknown;
 
value.trim(); // ❌ Compile Error: Object is of type 'unknown'.
value();      // ❌ Compile Error: Object is of type 'unknown'.

To use an unknown value safely, you must narrow its type first.


3. How to Narrow unknown

There are three common ways to narrow a value of type unknown:

A. Using typeof checks

let value: unknown = "hello";
 
if (typeof value === "string") {
  console.log(value.toUpperCase()); // ✅ Allowed: TypeScript knows value is a string
}

B. Using instanceof checks

let value: unknown = new Date();
 
if (value instanceof Date) {
  console.log(value.getFullYear()); // ✅ Allowed: TypeScript knows value is a Date object
}

C. Using Type Assertion (as)

If you are certain of the type, you can assert it:

let value: unknown = getApiData();
const strValue = value as string;
console.log(strValue.trim()); // ✅ Allowed

4. Key Contrast Summary

Action / Capabilityanyunknown
Can assign any value to it?✅ Yes✅ Yes
Can assign it to another type?✅ Yes (except never)❌ No (only to any or unknown)
Can access arbitrary properties?✅ Yes❌ No
Can invoke as a function?✅ Yes❌ No
Forces type checking?❌ No✅ Yes

Key Takeaways

  • unknown Type: Use unknown by default when you don't know the incoming type (e.g., fetch request responses, dynamic input fields) to keep the codebase type-safe.
  • any Type: Avoid any unless migrating legacy JavaScript or writing complex generic libraries where type safety is managed via other assertions.
  • Top Type Behavior: Both any and unknown are top types (all values are assignable to them), but unknown cannot be assigned to anything else without narrowing.

Share this Resource

Help other developers level up by sharing this study guide.

More Technical Questions

Expand your mastery. Deep dive into other frontend interview challenges in this category.