# autocontainer

> `autocontainer` is an [IoC](https://en.wikipedia.org/wiki/Inversion_of_control) container and [DI](https://en.wikipedia.org/wiki/Dependency_injection) framework for TypeScript that relies on a custom transformer pass to be able to use type information at

Latest version **0.1.3** (published 2022-10-04) · 0 weekly downloads

## Install

```sh
npm install autocontainer
pnpm add autocontainer
yarn add autocontainer
bun add autocontainer
```

## Health

**Score 15/100 (F)** — status: abandoned.

Positive: esm support; no vulnerabilities.

Warnings: low downloads; no types; low quality score; pre 1.0.

Negative: abandoned; low maintenance score.

## Facts

| | |
|---|---|
| Version | 0.1.3 |
| Published | 2022-10-04 |
| First published | 2022-10-04 |
| Weekly downloads | 0 |
| TypeScript types | none |
| Module format | ESM |
| Dependencies | 0 |
| Unpacked size | 60.3 KB |
| Known vulnerabilities | 0 |
| Install scripts | no |
| Maintainers | emilniklas |

## Links

- npm: https://www.npmjs.com/package/autocontainer
- npm.io page: https://npm.io/package/autocontainer

## Recent versions

- 0.1.3 (latest) — 2022-10-04
- 0.1.2 — 2022-10-04
- 0.1.1 — 2022-10-04
- 0.1.0 — 2022-10-04

## README

# `autocontainer`

`autocontainer` is an [IoC](https://en.wikipedia.org/wiki/Inversion_of_control) container and
[DI](https://en.wikipedia.org/wiki/Dependency_injection) framework for TypeScript that relies
on a custom transformer pass to be able to use type information at runtime.

Because of the reliance on a custom transformer, it is required that the user uses
[`ttypescript`](https://github.com/cevek/ttypescript/tree/master) replacement executables instead
of the native TypeScript `tsc`/`tsserver` executables.

## Configuration

```json
{
  "compilerOptions": {
    "plugins": [
      { "transform": "autocontainer/dist/transformer.js" }
    ]
  }
}
```

## Usage

Let's start with some vanilla TypeScript declarations.

```typescript
import { Database } from "some-database-library";

// A perfectly normal TypeScript interface
interface UserRepository {
  getUsers(): AsyncIterable<User>;
}

// A class dependent on the interface
class UserController {
  readonly #repo: UserRepository;
  // ...
}

// An implementation of the interface using a third-party class
class DatabaseUserRepository implements UserRepository {
  readonly #database: Database;
  // ...
}
```

Given the above code, here's how we can use `autocontainer` to resolve the dependency graph.

First, we create an instance of the container:

```typescript
import { Container } from "autocontainer";

const container = Container.create();
```

We can provide implementations for arbitrary types. Here we're providing a singleton binding,
meaning the same instance will be reused anytime someone injects the type.

```typescript
import { Database } from "some-database-library";
container.provide<Database>(
  () => new Database("db://connection-string"),
  { singleton: true },
);
```

We can make a binding from an abstract type to a concrete one, by using the `bind` method.

```typescript
container.bind<UserRepository, DatabaseUserRepository>();
```

Now, we can use the `make` method to create an instance of `UserController`, which recursively
makes instances of all the dependencies of that class.

```typescript
const controller = container.make<UserController>();
```

Note how, as long as TypeScript knows the type argument provided to `make`, the transformer
is able to generate the correct code. So, thanks to the flow analysis of the TypeScript
compiler, we're sometimes able to omit the type argument. Here's an example.

```typescript
async function startServer(controller: UserController) {
  // ...
}

await startServer(container.make());
```

---
_Source: https://npm.io/package/autocontainer · Machine-readable twin of the npm.io package page. Health data is recomputed on every publish._
