> ## Documentation Index
> Fetch the complete documentation index at: https://pulian.mintlify.site/llms.txt
> Use this file to discover all available pages before exploring further.

# @hile/ioredis

> Create Redis clients manually or as Hile services with lifecycle cleanup.

# @hile/ioredis

Create Redis clients manually or as Hile services with lifecycle cleanup.

## Choose This Package When

| User asks for    | Use             | Also read                                                  |
| ---------------- | --------------- | ---------------------------------------------------------- |
| Connect to Redis | `@hile/ioredis` | `packages/core-lifecycle.md`, `packages/infrastructure.md` |

## Use When

Use these packages when an app needs managed startup, singleton resources, dependency ordering, environment-file loading, graceful shutdown, logs, Redis, or SQL database connections.

## Do Not Use When

* Do not use `loadService()` at module top level.
* Do not use `auto_load_packages` for file paths. It accepts package names only.
* Do not use the default `@hile/ioredis` or `@hile/typeorm` services when one app needs multiple Redis or database connections; define separate services with separate keys.

## Install

```bash theme={null}
pnpm add @hile/core @hile/logger @hile/ioredis @hile/typeorm
pnpm add -D @hile/cli
```

## Imports

```ts theme={null}
import { defineService, loadService, container } from '@hile/core'
import { createLogger } from '@hile/logger'
import redisService, { createRedis } from '@hile/ioredis'
import typeormService, { createDataSource, transaction } from '@hile/typeorm'
```

## Copy-Paste Example

```ts theme={null}
// src/services/http.boot.ts
import { defineService } from '@hile/core'
import { Http } from '@hile/http'

export default defineService('http', async (shutdown) => {
  const http = new Http({ port: Number(process.env.HTTP_PORT ?? 3000) })
  await http.load(new URL('../controllers', import.meta.url).pathname)
  const close = await http.listen()
  shutdown(close)
  return http
})
```

Run:

```bash theme={null}
hile start --dev --env-file .env
```

## More Examples

Use `package.json` auto-load for integration services that default-export a Hile service:

```json theme={null}
{
  "type": "module",
  "scripts": {
    "dev": "hile start --dev --env-file .env",
    "start": "hile start --env-file .env.prod"
  },
  "hile": {
    "auto_load_packages": ["@hile/logger", "@hile/ioredis", "@hile/typeorm"]
  }
}
```

Inside another service, load dependencies:

```ts theme={null}
import { defineService, loadService } from '@hile/core'
import redisService from '@hile/ioredis'
import typeormService from '@hile/typeorm'

export default defineService('user.service', async () => {
  const [redis, ds] = await Promise.all([
    loadService(redisService),
    loadService(typeormService),
  ])
  return { redis, ds }
})
```

## Runtime And Lifecycle Notes

* `defineService(key, fn)` registers a service factory and does not execute it.
* `loadService(service)` executes the factory on first call and returns the cached value afterwards.
* The `shutdown` callback registers teardown functions; they run in LIFO order.
* The container tracks dependencies when service factories call `loadService()`.
* `container.shutdown()` triggers registered teardowns.
* `@hile/bootstrap` loads env files first, sets `NODE_ENV`, imports auto-load packages, scans boot files, and installs exit hooks.
* `@hile/logger.createLogger()` returns `{ logger, teardown }`.
* `@hile/ioredis.createRedis()` waits for `connect`.
* `@hile/typeorm.createDataSource()` initializes a TypeORM `DataSource`.

## Anti-Patterns

* Reusing one service key for unrelated factories.
* Missing `shutdown()` callbacks for network connections or servers.
* Assuming TypeORM env config fills entities automatically when `TYPEORM_ENTITIES` is not set.
* Calling `transaction()` and manually committing; the helper commits or rolls back internally.

## Verification Checklist

* Boot files default-export `defineService(...)`.
* Long-lived resources register teardown callbacks.
* `auto_load_packages` contains package names, not local files.
* `hile start --dev` can find `src/**/*.boot.ts`.
* Production build emits `dist/**/*.boot.js`.

## Related Recipes

### Redis Cache With Singleflight

## Complete Example

```ts theme={null}
import { loadService } from '@hile/core'
import redisService from '@hile/ioredis'
import { Cache, defineCache, RedisCache } from '@hile/cache'

const userProfileCache = defineCache(
  'user:{id:string}:profile',
  async ({ id }) => {
    const profile = await loadProfileFromDatabase(id)
    if (!profile) return new Cache(undefined)
    return new Cache(profile).setExpire(300)
  },
  {
    singleflight: { ttl: 10_000, wait: 10_000 },
    stale: { ttl: 60 },
    negative: { ttl: 30 },
    tags: (params, data) => data ? [`user:${params.id}`] : [],
  },
)

const redis = await loadService(redisService)
const cache = new RedisCache('app:', redis)
const userProfiles = await cache.loadCache(userProfileCache)

const profile = await userProfiles.read({ id: 'u1' })
await userProfiles.remove({ id: 'u1' })
await cache.removeTag('user:u1')
```

## Package-Local AI Guide

This package also ships `AI.md` in npm so agents can read accurate examples after installation.
