Skip to content

How to properly fail factory.create ? #273

Open

Description

@silverbucket

From the documentation it seems that you should not handle exceptions during .createPool() but instead during .aquire(). However if the factory.create() function fails, it continues to retry. I've tried both throwing an exception and rejecting the promise and I'm unable to get any controlled failure path from the operation.

const genericPool = require('generic-pool');
const pool = genericPool.createPool({
  create: () => {
    console.log('create called');
    return new Promise((resolve, reject) => {
      console.log('rejecting promise');
      throw new Error('connection problem');
      //reject('connection problem');
    });
  },
  destroy: () => {
    return new Promise((resolve, reject) => { resolve(); });
  }
}, { max: 2 });

console.log("acquire");
pool.acquire().then((client) => {
  console.log("success");
}, (err) => {
  console.log("controlled failure 1");
}).catch((err) => {
  console.log("controlled failure 2");
});

In the above example, aquire is never reached, and I get an endless loop of 'create called' and 'rejecting promise'. The behaviour is the same if I reject or throw.

...
create called
rejecting promise
create called
rejecting promise
create called
rejecting promise
create called
rejecting promise
^C

How can I reliably handle, for example, connection errors to a database, if the user provides incorrect config? Currently either I get a timeout unhandled exception from the DB library, or a hang/endless loop.

Activity

  1. martin-randall-tanium commented on Dec 20, 2021

    @martin-randall-tanium

    Potential fix and workaround: #221

  2. silverbucket commented on Aug 21, 2022

    @silverbucket
    Author

    @Kikobeats @sandfox any update on this issue? It continues to be a source of debugging trouble, with any connection error silently causing an endless loop.

  3. alanwu4321 commented on Oct 12, 2022

    @alanwu4321

    Can we use this to prevent the issue #175 (comment)

  4. MattCollyer commented on Aug 8, 2025

    @MattCollyer

    Hello from 2025 👋🏼

    I recently ran into this issue. It was horrible. With just some bad credentials it turned my nice generic pool into an infinite loop of death. I started ripping out the library and told myself that this was a fatal flaw. What good is it to be able to listen/ log these events, but not catch or stop this loop of death from happening?

    Enter a discovery :
    The snowflake SDK uses this library under the hood. Surely a company like snowflake would have encountered this issue??

    And yes, they have ! This is their workaround to this.

    And it worked for me as well.
    Is it a hack? 100%
    If you're using TS you'll have to put some casting in there to access the private var...

    I still think this needs its own fix in the lib, but if you're in deep (like snowflake and myself) this hack will do the trick!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions