Rules Hub
Coding Rules Library
Rule priority, scope & exceptions
Use this to align rules with the senior-level structure (P0/P1/P2, scope, exceptions/tradeoffs).
Reuse a singleton service instead of instantiating per call
Don't instantiate stateful services (clients, connections) inside loops or repeated calls — reuse a single shared/singleton instance to avoid memory churn and leaks.
Bad example
| 1 | for (const job of jobs) { |
| 2 | const client = new DbClient(config); // new connection every iteration |
| 3 | await client.write(job); |
| 4 | } |
Explanation (EN)
A new stateful client is created on every iteration. Each holds connections/buffers and relies on GC to clean up; under load this churns memory and can leak connections.
Objašnjenje (HR)
Novi stateful klijent se stvara u svakoj iteraciji. Svaki drži konekcije/buffere i oslanja se na GC za čišćenje; pod opterećenjem to troši memoriju i može curiti konekcije.
Good example
| 1 | class DbService { |
| 2 | private static instance: DbService; |
| 3 | static get(): DbService { |
| 4 | if (!DbService.instance) DbService.instance = new DbService(); |
| 5 | return DbService.instance; |
| 6 | } |
| 7 | } |
| 8 |
|
| 9 | const service = DbService.get(); |
| 10 | for (const job of jobs) { |
| 11 | await service.write(job); // reuse one client/connection |
| 12 | } |
Explanation (EN)
A single long-lived instance is reused across all iterations, so connections and state are shared and GC pressure stays low.
Objašnjenje (HR)
Jedna dugovječna instanca se ponovno koristi kroz sve iteracije, pa se konekcije i stanje dijele, a pritisak na GC ostaje nizak.
Exceptions / Tradeoffs (EN)
When each call genuinely needs isolated state (e.g. per-request transaction scope), a fresh instance is correct — but still pool/dispose the underlying connection. Balance against avoid-mutable-shared-state-in-singletons: reuse the singleton only when it is stateless; never park per-request data on it.
Iznimke / Tradeoffi (HR)
Kad svaki poziv stvarno treba izolirano stanje (npr. opseg transakcije po zahtjevu), nova instanca je ispravna — ali i dalje koristi pool ili oslobodi temeljnu konekciju.