microsoft / microsoft/TypeScript

[ Feature Request ] - FileSystem<T>

Open
#42,046 10 comments 10 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

Awaiting More Feedback Suggestion
Dominant language
Go
Stars
111k
Forks
14.3k
Avg merge
2d 4h
Merged PRs (30d)
132

Description

Suggestion

FileSystem type

Works with alot of simplicity

  • If it hits a folder adds it into the 'object' type and its children as traversable keys
  • If it hits a file thats a module it adds whatever its typeof import("..") type would be.
  • Recursive

Similar behavior to import(".....") type.
Usage: FileSystem<"../static">

FileSystem<"./api"> on this folder structure would produce the following object type which also shows how it would handle index.ts

- api 
     -users
         - by-id.ts
         - all.ts
         - index.ts
     -posts
        - all.ts
type Result = {
    users: {
        by-id: typeof import("./api/users/by-id");
        all: typeof import("./api/users/all");
    } & typeof import("./api/users"),
    posts: {
        all: typeof import("./api/posts/all");
    }
}

Use Cases and Examples

1: Every use case where previously people had alot of types or classes floating around and then had a single place where they imported all those types/classes into a union just to support typescript can now just use a folder to store those things in conjunction with FileSystem

// people using ORM's can avoid having a 'single' source where all their classes are imported in favor of just using a folder.
await database.user(123);

// folder strcuture
// tables
       user.ts     {default: class UsersTable {  getUsers() { return [] }}}  // contains following module

type ORM = {
    [K in keyof FileSystem<"../tables">]: FileSystem<"../tables">][K]["default"]
}

declare const database: ORM ;
database.users.getUsers();

2: Really strong support for image paths, and removing files in refactors that are referenced by string path.

 // (note: requires augmentation of JSX types);
<img src={"/static/dolphin.png"}/> // error dolphin.png isn't loaded in the file system.

3: Support for string based routing in applications and protection against routing refactors at a type-level.

 // (note: requires augmentation of JSX types);
<a href={"/home/name"}/>

// currently people do something like this just to have 'route refactorability' which bloats bundle size.
const Routes = {
     Home: {
         name: "/home/name"
     }
} as const

// can now do this..
- screens
      - home
              - name.ts // React page

4: Statically typed readFileSync for people using it to access their file system

const readFileSystem = (path: keyof FileSystem<".">): string=> fs.readFileSync(path);

5: Statically typed API handling

(pseudo code)
// before
const response = await api<typeof import("/api/user")>("/api/user")
// after
const response = await api.user(1);
// implementation
const api = new Proxy<FileSystem<"../../../api">>(...);
  • Many more use cases (File system based redux, file system based statically typed ExpressJS etc)

Precedence: When people look at the implementation in the standard library they will notice FileSystem doesn't have a implementation in the same way you can "peek definition" for types like Exclude and Omit, however there already is precedence for type-level helpers that work as a 'compiler flag' (I.E ThisType<T>);

Also utilizes a lot of things that already exist like typeof import("..") functionality.

Previous issue:
https://github.com/microsoft/TypeScript/issues/41550

Further important notes:

  • People are going to want to type things with the 'flattened' keys of a FileSytem in various formats which will easily be possible to use it in conjunction with existing mapped types and new string literal types.
  • People are going to want to use FileSystem to represent things that are FileSystem'Like which again is easily possible with mapped/string literal
  • People are going to want to use FileSystem to represent transformations that could happen at build time which is again possible with mapped/string literal types.

Checklist

My suggestion meets these guidelines:

  • This wouldn't be a breaking change in existing TypeScript/JavaScript code
  • This wouldn't change the runtime behavior of existing JavaScript code
  • This could be implemented without emitting different JS based on the types of the expressions
  • This isn't a runtime feature (e.g. library functionality, non-ECMAScript syntax with JavaScript output, etc.)
  • This feature would agree with the rest of TypeScript's Design Goals.

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Begin with the prior issue #41550 and the proposed FileSystem examples in this issue. Establish the design and compiler behavior needed for recursive folder and module typing, then validate that the stated use cases type-check as intended; completion depends on an accepted design rather than a localized edit.

Written by the indexing model from the issue text.

Assessment

Tech stack
typescript
Domain
compilers
Issue type
Feature
Difficulty
5/5
Estimated time
Over a week
Activity status
Stale
Clarity
Needs clarification
Newbie friendliness
25/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.