Die folgende Abfrage gibt ein Postgres bigint
für die Spalte assigned_client_count
(Ergebnisse von COUNT(*)
.
Dies ist eine Zeichenfolge und keine Number
in den zurückgegebenen Ergebnissen.
{ __cid: '__cid40',
method: 'select',
options: undefined,
bindings: [ 1 ],
sql: 'select "id", "name", "fluid_account_id", "survey_fid", coalesce(assigned_client_count, 0) as assigned_client_count from (select "survey_id", count(*) as "assigned_client_count" from "client_surveys" group by "survey_id") as "t_counts" right join "fluid_surveys" on "t_counts"."survey_id" = "fluid_surveys"."id" where "fluid_account_id" = $1' }
[ { id: 6,
name: 'some name',
fluid_account_id: 1,
survey_fid: 69942,
assigned_client_count: '1' } ]
Dies ist also eine Node-Postgres-Entwurfsentscheidung und nicht wirklich eine, über die wir auch abstrahieren können:
https://github.com/brianc/node-postgres/pull/353
node-postgres macht seinen Typ-Parser verfügbar, sodass Sie seine Standardeinstellung für bigint jederzeit überschreiben und für alle Abfragen mit parseInt
ausführen können.
Das Problem hierbei ist, dass JS, wenn Sie tatsächlich große Ganzzahlen hatten, nicht nativ mit ihnen umgehen kann. Die Standardeinstellung ermöglicht volle Präzision und Sie können sich abmelden, wenn Sie sie nicht benötigen.
@ rhys-vdw http://mathjs.org/ ist eine Bibliothek, die mit Bignumbers umgehen kann, und es gibt noch viele weitere.
Prost. In diesem Fall wird nur null oder eins zurückgegeben, daher werde ich wahrscheinlich die Typ-Parser-Option untersuchen.
@ rhys-vdw, ich habe das gleiche Problem. Die Problemumgehung besteht darin, die folgenden 2 Zeilen über require('knex')
hinzuzufügen
var pg = require('pg')
pg.types.setTypeParser(20, 'text', parseInt)
Hallo Leute. Ich habe das gleiche Problem. Wir verwenden Bigint für einige eventuell große Tische.
Leider betrachte ich die @ Sidazhang- Lösung als Verschlechterung des Bigint zu int (eventueller Präzisionsverlust).
Schlagen Sie vor, Bigint lieber nicht zu verwenden, oder gibt es eine Problemumgehung, die die Präzision beibehält?
Eine, die mir in den Sinn kam, ist das Akzeptieren von Zeichenfolgen als Bigint-Darstellung, aber knex lehnt eine solche Abfrage an Tabellen mit konditionierenden Bigints mit Zeichenfolgen als Wert ab. Im Falle von Indizes muss ich keine mathematischen Operationen an der Zahl durchführen.
Error: invalid input syntax for integer: "{"1"}"
at Connection.Object.<anonymous>.Connection.parseE (D:\repos\ImgPoolWebApp\node_modules\pg\lib\connection.js:553:11)
at Connection.Object.<anonymous>.Connection.parseMessage (D:\repos\ImgPoolWebApp\node_modules\pg\lib\connection.js:378:19)
at Socket.<anonymous> (D:\repos\ImgPoolWebApp\node_modules\pg\lib\connection.js:119:22)
at emitOne (events.js:116:13)
at Socket.emit (events.js:211:7)
at addChunk (_stream_readable.js:263:12)
at readableAddChunk (_stream_readable.js:250:11)
at Socket.Readable.push (_stream_readable.js:208:10)
at TCP.onread (net.js:597:20), level=error
Wäre es irgendwie möglich zu akzeptieren, wo Bedingung mit Zeichenfolge, falls der linke Operand bigint ist?
query.where("bigintkey", "123456")
WHERE "bigintkey" = 123456
Die Gültigkeit des Wertes müsste von den Verbrauchern gehandhabt werden.
Im Moment müssen wir die Abfragen akzeptieren, die einen String zurückgeben, und unter Bedingungen => verlorene Genauigkeit in eine Zahl konvertieren.
Dies scheint mir ein API-Problem zu sein, unabhängig davon, ob die zugrunde liegende Bibliothek einige Einschränkungen auf Engine-Ebene aufweist.
Der letzte Ausweg wäre, dass wir Strings als Alternative zu bigint in db verwenden und einige UUids anstelle von automatisch inkrementierten Primärschlüsseln generieren.
@miroslavvojtus Ich habe einen Handler (für pg-Typen), der Bigints in Javascript-Zahlen konvertiert und einen Fehler auslöst, wenn der Wert zu groß ist, als dass die Zahl damit umgehen könnte. Wenn Ihre Werte kleiner als 53 Bit sind, verlieren Sie keine Genauigkeit.
Ich sehe nicht, was das Problem ist, das Sie tatsächlich dort haben. Wenn Sie Bigint mit voller Präzision verwenden möchten, können Sie diese als Zeichenfolgen auf der Javascript-Seite behalten.
Hilfreichster Kommentar
@ rhys-vdw, ich habe das gleiche Problem. Die Problemumgehung besteht darin, die folgenden 2 Zeilen über
require('knex')
hinzuzufügen