Closed brianc closed 7 years ago
Thank you so much for the feedback and review! I'm not quite done w/ this branch yet - code's still a bit dirty...but have quite a bit of client work in the next few days so I'll take me a bit of time to get to this. But know I'm grateful & I'll be back within a day or two! :dancer:
I did notice that promise support is still a bit second class. In that -- promisified apis would be able to perform much better than the scheme currently used.
@calebboyd - using callbacks internally in this module is so we can support pg>=5.x
instead of pg@7
which is when all the APIs for pg
are fully promisified. What do you mean by that exactly - could you elaborate?
Mostly I think that it would be best to stick with one API or the other. My reasoning is that: accepting a custom Promise at this level would cut into performance.
For example, Bluebird.promisify
, will rewrite the function (emit new code) in order to maintain low overhead when allocating new Promise
s -- and then uses an internal implementation. Node's require('util').promisify
will use a native deferred api. Each of which would behave much faster than creating the new Promise
and deferred mechanism being used. As a plus, plain callbacks for waiters in this internal queue will always be the quicker solution of the two.
In general sticking with callbacks here will allow people who use promises (I'm one) to do so with the lowest overhead, which is a plus for the library that proxies queries.
I guess that wasn't super clear. I don't have anything that would stop me from using this (I could promisify it anyways to avoid the issue). But Maybe the removal of this.Promise
such that promisify
is encouraged instead. As that is generally blessed now (in node core)
I'll take a look at hard look at the code once I finish it to ensure it's not doing unnecessary work wrt allocating promises. It should only allocate a promise if you don't supply a callback: if you use a callback it will never even allocate any promises so you don't have to be concerned about any performance as some folks who use callbacks tend to be. π
As far as Bluebird.promsify
versus the ability to accept a callback or return a promise (the api that this lib is going for) - I'd be pretty surprised if Bluebird.promsify
generates any noticeable performance gains over what's going on in this code, but I'll investigate that to see...and like you said if someone prefers that approach nothing is stopping them from doing that as well in their own code on top of the pool. π
The goal is to support both promises and callbacks in a transparent way versus requiring someone run Bluebird.promsify
or something similar on the pool, at least for the time being: supply a callback & callbacks will be used. Don't & you'll get a promise back. π
Thanks again for the feedback & comments. They're very helpful! π
Thank you for entertaining them. I'm very grateful for your work on these tools π¨
This contains a massive number of internal changes. However, the external API remains very close to the same.
The breaking changes are:
max
andidleTimeoutMillis
new
keywordI attempted to upgrade to node-pool@3.x, but it weirdly no longer supports returning an error when a client fails to connect. Instead it tries to reconnect the client in a tight loop and makes the error non-actionable. I was unable to find a good way to hook into this behavior and override it. Furthermore it has a lot of additional bells and whistles for priority queuing, min levels, auto-connection, and other behavior pg and pg-pool have never used. Initially I was distraught at the thought of implementing the pooling behavior here, but it turns out it wasn't very much code & all the tests still pass!
After this I spent some time going through and writing tests for many of the open issues to verify they no longer happen. I also added support for the long requested
connectionTimeoutMillis
- now supplyingconnectionTimeoutMillis
as a millisecond value will cause the pool to return an error on yourconnect
call if a connection could not be established within the configured time. By default there is no timeout.Known fixes:
pg>=5.0
is apeerDependency
. closes #45.ending
property which will allow you to inspect when the pool is in the process of shutting down. closes #58idleTimeoutMillis
of 0 disables idle timeout. closes #64