nuxt-bee-queue 1.0.0 → 1.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +172 -71
- package/dist/module.d.mts +1 -0
- package/dist/module.json +2 -2
- package/dist/module.mjs +7 -3
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -1,84 +1,185 @@
|
|
|
1
|
-
|
|
2
|
-
Get your module up and running quickly.
|
|
1
|
+
# Nuxt BeeQueue 🐝
|
|
3
2
|
|
|
4
|
-
|
|
5
|
-
- Name: My Module
|
|
6
|
-
- Package name: my-module
|
|
7
|
-
- Description: My new Nuxt module
|
|
8
|
-
-->
|
|
3
|
+
A powerful Nuxt module for handling background jobs using Redis and Bee-Queue. This module integrates seamlessly with Nuxt server routes and Nitro, allowing you to define, dispatch, and process jobs with ease.
|
|
9
4
|
|
|
10
|
-
|
|
5
|
+
## Features
|
|
11
6
|
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
7
|
+
- **Easy Job Definition**: Define jobs in server/jobs using a simple API.
|
|
8
|
+
- **Type Safety**: Full TypeScript support for job payloads and returns.
|
|
9
|
+
- **Flexible Execution**: Run workers inside the Nuxt process (dev) or as separate microservices.
|
|
10
|
+
- **Zero Configuration**: Auto-imports and sensible defaults.
|
|
16
11
|
|
|
17
|
-
|
|
12
|
+
## Installation
|
|
18
13
|
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
14
|
+
```bash
|
|
15
|
+
npm install nuxt-bee-queue
|
|
16
|
+
# or
|
|
17
|
+
yarn add nuxt-bee-queue
|
|
18
|
+
# or
|
|
19
|
+
pnpm add nuxt-bee-queue
|
|
20
|
+
```
|
|
22
21
|
|
|
23
|
-
|
|
22
|
+
Add the module to your `nuxt.config.ts`:
|
|
23
|
+
|
|
24
|
+
```typescript
|
|
25
|
+
export default defineNuxtConfig({
|
|
26
|
+
modules: ['nuxt-bee-queue'],
|
|
27
|
+
// Optional configuration
|
|
28
|
+
queue: {
|
|
29
|
+
redis: 'redis://localhost:6379',
|
|
30
|
+
infernalQueue: true, // in false in dev mode queue not run automatically (must run node --watch path)
|
|
31
|
+
}
|
|
32
|
+
})
|
|
33
|
+
```
|
|
34
|
+
|
|
35
|
+
## Usage
|
|
36
|
+
|
|
37
|
+
### 1. Defining a Job
|
|
38
|
+
|
|
39
|
+
Create a job file in your server directory. By convention, stick to `server/jobs/`. Example path: `server/jobs/user-create.ts`
|
|
40
|
+
|
|
41
|
+
> **Note**: The name of the file becomes the name of the queue.
|
|
42
|
+
|
|
43
|
+
You can use standard async/await or the callback style (done).
|
|
44
|
+
|
|
45
|
+
```typescript
|
|
46
|
+
// server/jobs/user-create.ts
|
|
47
|
+
import { db, schema } from 'hub:db' // Example using Nuxt Hub
|
|
48
|
+
|
|
49
|
+
interface JobPayload {
|
|
50
|
+
firstName: string
|
|
51
|
+
lastName: string
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
// Inferred return type for Type Safety
|
|
55
|
+
type JobReturn = Array<typeof schema.users.$inferSelect>
|
|
56
|
+
|
|
57
|
+
export default defineJob<JobPayload, JobReturn>({
|
|
58
|
+
// Option 1: Async/Await (Recommended)
|
|
59
|
+
process: async (job) => {
|
|
60
|
+
console.log(`Processing user: ${job.data.firstName}`)
|
|
61
|
+
|
|
62
|
+
const user = await db.insert(schema.users).values({
|
|
63
|
+
firstName: job.data.firstName,
|
|
64
|
+
lastName: job.data.lastName,
|
|
65
|
+
}).returning()
|
|
66
|
+
|
|
67
|
+
console.log('User Created!')
|
|
68
|
+
return user
|
|
69
|
+
},
|
|
70
|
+
|
|
71
|
+
// Option 2: Callback style
|
|
72
|
+
// process: (job, done) => {
|
|
73
|
+
// // do work...
|
|
74
|
+
// done(null, result)
|
|
75
|
+
// },
|
|
76
|
+
|
|
77
|
+
setting: {
|
|
78
|
+
sendEvents: false,
|
|
79
|
+
removeOnSuccess: true,
|
|
80
|
+
},
|
|
81
|
+
})
|
|
82
|
+
```
|
|
83
|
+
|
|
84
|
+
### 2. Dispatching a Job
|
|
85
|
+
|
|
86
|
+
You can dispatch jobs from your API routes or other server files using `useQueue`.
|
|
87
|
+
|
|
88
|
+
```typescript
|
|
89
|
+
// server/api/register.post.ts
|
|
90
|
+
export default defineEventHandler(async (event) => {
|
|
91
|
+
const body = await readBody(event)
|
|
24
92
|
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
- 🚠 Bar
|
|
28
|
-
- 🌲 Baz
|
|
93
|
+
// The name 'user-create' matches the filename in server/jobs/
|
|
94
|
+
const queue = useQueue('user-create')
|
|
29
95
|
|
|
30
|
-
|
|
96
|
+
const job = await queue.createJob({
|
|
97
|
+
firstName: body.firstName,
|
|
98
|
+
lastName: body.lastName
|
|
99
|
+
}).save()
|
|
31
100
|
|
|
32
|
-
|
|
101
|
+
return { jobId: job.id, status: 'queued' }
|
|
102
|
+
})
|
|
103
|
+
```
|
|
104
|
+
|
|
105
|
+
## Running Workers
|
|
106
|
+
|
|
107
|
+
### Development
|
|
108
|
+
|
|
109
|
+
You have two options during development:
|
|
110
|
+
|
|
111
|
+
1. **Integrated (Default)**: Do nothing. The queue workers will launch in the same process as your Nuxt/Nitro server.
|
|
112
|
+
|
|
113
|
+
2. **Separate Process**: If you want to isolate the worker logs or performance, you can run the worker separately.
|
|
114
|
+
|
|
115
|
+
Add the following to your `package.json` scripts:
|
|
116
|
+
|
|
117
|
+
**Node:**
|
|
118
|
+
```json
|
|
119
|
+
"scripts": {
|
|
120
|
+
"queue:dev": "node --watch .nuxt/dev/workers/index.mjs"
|
|
121
|
+
}
|
|
122
|
+
```
|
|
123
|
+
|
|
124
|
+
**Bun:**
|
|
125
|
+
```json
|
|
126
|
+
"scripts": {
|
|
127
|
+
"queue:dev": "bun --watch .nuxt/dev/workers/index.mjs"
|
|
128
|
+
}
|
|
129
|
+
```
|
|
130
|
+
|
|
131
|
+
**Deno:**
|
|
132
|
+
```json
|
|
133
|
+
"scripts": {
|
|
134
|
+
"queue:dev": "deno run --allow-all --watch .nuxt/dev/workers/index.mjs"
|
|
135
|
+
}
|
|
136
|
+
```
|
|
137
|
+
|
|
138
|
+
### Production
|
|
139
|
+
|
|
140
|
+
For production deployment, the workers are built into a separate entry point.
|
|
33
141
|
|
|
34
142
|
```bash
|
|
35
|
-
|
|
143
|
+
node .output/server/workers/index.mjs
|
|
36
144
|
```
|
|
37
145
|
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
[npm-downloads-href]: https://npm.chart.dev/my-module
|
|
79
|
-
|
|
80
|
-
[license-src]: https://img.shields.io/npm/l/my-module.svg?style=flat&colorA=020420&colorB=00DC82
|
|
81
|
-
[license-href]: https://npmjs.com/package/my-module
|
|
82
|
-
|
|
83
|
-
[nuxt-src]: https://img.shields.io/badge/Nuxt-020420?logo=nuxt
|
|
84
|
-
[nuxt-href]: https://nuxt.com
|
|
146
|
+
## Tips & Best Practices
|
|
147
|
+
|
|
148
|
+
### 1. Queue Instance Management
|
|
149
|
+
|
|
150
|
+
Every time you call `defineJob` or `useQueue('name')`, a BeeQueue client instance is created. **Rule**: Ensure you strictly use the filename (without extension) as the queue name when dispatching.
|
|
151
|
+
|
|
152
|
+
### 2. Optimization (Singleton Pattern)
|
|
153
|
+
|
|
154
|
+
For optimization purposes, every BeeQueue client is stored in memory as long as the server is running. Creating a new queue instance on every request is an anti-pattern.
|
|
155
|
+
|
|
156
|
+
We highly recommend creating a wrapper for your queues to reuse the client instance.
|
|
157
|
+
|
|
158
|
+
```typescript
|
|
159
|
+
// server/utils/queue.ts
|
|
160
|
+
export function useEmailQueue() {
|
|
161
|
+
// This reuses the existing client if strictly created before
|
|
162
|
+
return useQueue('email-sender', {
|
|
163
|
+
sendEvents: false
|
|
164
|
+
// ...other specific config
|
|
165
|
+
})
|
|
166
|
+
}
|
|
167
|
+
```
|
|
168
|
+
|
|
169
|
+
Usage in API:
|
|
170
|
+
|
|
171
|
+
```typescript
|
|
172
|
+
// server/api/send.ts
|
|
173
|
+
export default defineEventHandler(async () => {
|
|
174
|
+
// Uses the cached connection
|
|
175
|
+
await useEmailQueue().createJob({ email: '...' }).save()
|
|
176
|
+
})
|
|
177
|
+
```
|
|
178
|
+
|
|
179
|
+
## Credits
|
|
180
|
+
|
|
181
|
+
A special thanks to Aidan Hibbard and the [nuxt-processor](https://github.com/) repository. Parts of this module's architecture and logic were inspired by his work on queue processing in the Nuxt ecosystem.
|
|
182
|
+
|
|
183
|
+
## License
|
|
184
|
+
|
|
185
|
+
MIT
|
package/dist/module.d.mts
CHANGED
package/dist/module.json
CHANGED
package/dist/module.mjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { useNuxt, createResolver, defineNuxtModule, addServerTemplate, addTemplate, addServerImports } from '@nuxt/kit';
|
|
1
|
+
import { useNuxt, createResolver, defineNuxtModule, addServerTemplate, addTemplate, addServerImports, addServerPlugin } from '@nuxt/kit';
|
|
2
2
|
import { parse, relative } from 'node:path';
|
|
3
3
|
import fs from 'node:fs';
|
|
4
4
|
import fg from 'fast-glob';
|
|
@@ -20,11 +20,12 @@ const scanFolder = async (path) => {
|
|
|
20
20
|
const module$1 = defineNuxtModule({
|
|
21
21
|
meta: {
|
|
22
22
|
name: "nuxt-bee-queue",
|
|
23
|
-
configKey: "
|
|
23
|
+
configKey: "queue"
|
|
24
24
|
},
|
|
25
25
|
// Default configuration options of the Nuxt module
|
|
26
26
|
defaults: {
|
|
27
|
-
redis: "redis://localhost:6379"
|
|
27
|
+
redis: "redis://localhost:6379",
|
|
28
|
+
infernalQueue: true
|
|
28
29
|
},
|
|
29
30
|
async setup(options, nuxt) {
|
|
30
31
|
const resolver = createResolver(import.meta.url);
|
|
@@ -123,6 +124,9 @@ const module$1 = defineNuxtModule({
|
|
|
123
124
|
name: "useQueue",
|
|
124
125
|
from: resolver.resolve("./runtime/server/utils/useQueue")
|
|
125
126
|
}]);
|
|
127
|
+
if (options.infernalQueue && process.env.NODE_ENV == "development") {
|
|
128
|
+
addServerPlugin(resolver.resolve("./plugins/workerRunner"));
|
|
129
|
+
}
|
|
126
130
|
function createWorkersRollupPlugin() {
|
|
127
131
|
const VIRTUAL_ID = "\0nuxt-bee-queue-entry";
|
|
128
132
|
let virtualCode = "";
|