Skip to content

feat: Redis distributed locking for concurrent payroll runs + correlation ID logging - #1131

Merged
Wilfred007 merged 2 commits into
Gildado:mainfrom
Williams-1604:feat/redis-lock-correlation-logging-1027-1028
Jul 31, 2026
Merged

feat: Redis distributed locking for concurrent payroll runs + correlation ID logging#1131
Wilfred007 merged 2 commits into
Gildado:mainfrom
Williams-1604:feat/redis-lock-correlation-logging-1027-1028

Conversation

@Williams-1604

Copy link
Copy Markdown
Contributor

Summary

  • Redis distributed locking (RedisLockService) prevents two payroll runs for the same organisation executing concurrently across horizontally-scaled worker instances. Uses SET NX PX for atomic acquisition, a Lua script for safe token-matched release, and a background renewal interval to keep long-running runs from expiring the lock mid-flight.
  • Correlation ID propagation (correlationContext.ts) adds a per-operation x-correlation-id to every Winston log entry via AsyncLocalStorage — the same mechanism as the existing request-ID middleware. PayrollQueueService stamps a correlation ID onto each enqueued job (inheriting the HTTP caller's ID when available), and the payroll worker restores it at job start so all async log lines share a single traceable token.

Changed files

File Change
backend/src/services/redisLockService.ts New — RedisLockService with acquire() / withLock() / auto-renewal
backend/src/utils/correlationContext.ts New — AsyncLocalStorage correlation ID context
backend/src/utils/logger.ts Inject x-correlation-id into every log entry
backend/src/services/payrollQueueService.ts Propagate correlation ID into job payload
backend/src/workers/payrollWorker.ts Acquire org-scoped lock; restore correlation context per job
backend/src/services/__tests__/redisLockService.test.ts 9 tests covering acquire, retry, release, withLock, no-Redis fallback
backend/src/utils/__tests__/correlationContext.test.ts 10 tests covering context propagation, nesting, async, header constant

Closes #1027
Closes #1028
Closes #1029
Closes #1032

…ging

Closes Gildado#1027 — add RedisLockService (SET NX / Lua unlock / auto-renewal)
and integrate it into the payroll worker so only one payroll run per
organisation can execute concurrently across horizontally-scaled instances.
The worker concurrency setting is also relaxed to 5 now that the per-org
lock provides the safety guarantee.

Closes Gildado#1028 — add correlationContext (AsyncLocalStorage) that injects a
x-correlation-id into every Winston log entry, matching the pattern already
used by the request-ID middleware.  PayrollQueueService propagates the
caller's correlation ID into job data; the worker restores it at the start
of each job so the entire async chain shares a single traceable ID.

Closes Gildado#1029
Closes Gildado#1032
@drips-wave

drips-wave Bot commented Jul 28, 2026

Copy link
Copy Markdown

@Williams-1604 Great news! 🎉 Based on an automated assessment of this PR, the linked Wave issue(s) no longer count against your application limits.

You can now already apply to more issues while waiting for a review of this PR. Keep up the great work! 🚀

Learn more about application limits

@Wilfred007
Wilfred007 merged commit 84f6e4c into Gildado:main Jul 31, 2026
1 of 4 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

2 participants