Open autsada opened 3 years ago
Hi autsada,
For now, UUID fields are not auto-generated indeed.
I just found that Deno has a uuid
helper in the standard library, so here's how you can do it:
import { v4 } from "https://deno.land/std@0.84.0/uuid/mod.ts";
class User extends Model {
static table = 'users';
static timestamps = true;
static fields = {
id: {
type: DataTypes.UUID,
primaryKey: true,
},
};
static defaults = {
id: () => v4.generate(),
// id: v4.generate, should work as well
};
}
Let me know if this works for you.
Keep in touch
Hi eveningkid,
I will test it, thank you for your help.
Cheers,
Hi eveningkid,
I have tested it, and it has to be
static defaults = {
id: v4.generate()
};
But it will work for the first time only, after I tried to add the second one it failed. Here is the error I got.
PostgresError: duplicate key value violates unique constraint "id"
at parseError (error.ts:106:10)
at Connection._processError (connection.ts:434:19)
at Connection._simpleQuery (connection.ts:298:20)
at async Connection.query (connection.ts:546:16)
at async Client.query (client.ts:25:12)
at async PostgresConnector.query (postgres-connector.ts:63:22)
at async Database.query (database.ts:227:21)
at async Function._runQuery (model.ts:217:21)
at async Function.create (model.ts:417:21)
at async addProduct (admin.ts:102:21)
For now, I solved this by adding the v4 generate function directly to the database.
Cheers,
I have tested it, and it has to be
static defaults = { id: v4.generate() };
Doing so sets the default value as the immediate return value of generate()
which is a constant string. In his example @eveningkid gave a function:
static defaults = { id: () => v4.generate(), // id: v4.generate, should work as well };
Hey,
I think @juliendargelos said it well, this should work!
Hope the problem has been solved on your end.
Have a great day :)
I feel like I might have won an award for the weirdest bug I have ever see, consider the following user model:
export class User extends Model {
static table = "users";
static timestamps = true;
static fields = {
id: { primaryKey: true, type: DataTypes.UUID },
provider: DataTypes.STRING,
providerUserId: DataTypes.STRING,
displayName: DataTypes.STRING,
email: DataTypes.STRING,
};
static defaults = {
id: v4.generate,
};
}
On running I get a TS error:
Uncaught (in promise) PostgresError: invalid input syntax for type uuid: "function generate() {
const rnds = crypto.getRandomValues(new Uint8Array(16));
rnds[6] = (rnds[6] & 0x0f) | 0x40;
rnds[8] = (rnds[8] & 0x3f) | 0x80;
return bytesToUuid(rnds);
}"
If I flip the ID type to DataTypes.STRING
- it boots up fine, but then when a row is added to the DB the ID is
function generate() {
const rnds = crypto.getRandomValues(new Uint8Array(16));
rnds[6] = (rnds[6] & 0x0f) | 0x40;
rnds[8] = (rnds[8] & 0x3f) | 0x80;
return bytesToUuid(rnds);
}
It's evaling the string of the function....?
Like literally in the ID column...
Hey Darren,
Thanks a lot for sharing all the details :)
Could you please show me how you're creating an instance of that user? I think I might have an idea.
This seems related to #198.
Let's see how we can fix this once and for all!
Hey @eveningkid
const user = await User.create({
provider: "google",
providerUserId: userInfo.providerUserId,
displayName: userInfo.displayName,
email: userInfo.emails[0],
});
I have added on id: v4.generate()
for the short term!
@eveningkid
const user = new User();
user.provider = "google";
user.providerUserId = userInfo.providerUserId;
user.displayName = userInfo.displayName;
user.email = userInfo.emails[0];
await user.save();
Works! I still get errors from Typescript if i set the id in the model with id: { primaryKey: true, type: DataTypes.UUID }
the error is:
error: Uncaught (in promise) PostgresError: invalid input syntax for type uuid: "() => v4.generate()"
return new PostgresError(errorFields);
^
at parseError (https://deno.land/x/postgres@v0.4.6/error.ts:106:10)
at Connection._processError (https://deno.land/x/postgres@v0.4.6/connection.ts:434:19)
at Connection._simpleQuery (https://deno.land/x/postgres@v0.4.6/connection.ts:298:20)
at async Connection.query (https://deno.land/x/postgres@v0.4.6/connection.ts:546:16)
at async Client.query (https://deno.land/x/postgres@v0.4.6/client.ts:25:12)
at async PostgresConnector.query (https://deno.land/x/denodb@v1.0.33/lib/connectors/postgres-connector.ts:63:22)
at async Database.query (https://deno.land/x/denodb@v1.0.33/lib/database.ts:239:21)
at async Function.createTable (https://deno.land/x/denodb@v1.0.33/lib/model.ts:172:5)
at async Database.sync (https://deno.land/x/denodb@v1.0.33/lib/database.ts:209:7)
at async file:///Users/darren/Workspace/Deno/toto/database.ts:38:1
but no error if I set it to string.
Hey Darren,
We discussed this issue on #198 and @stillalivx implemented the fix in #248 :)
The issue should go away using 1.0.37
.
Thanks again for reporting this issue and have a great day!
id: v4.generate
with DataTypes.String
(id is uuid) works while DataTypes.UUID
throws error with 1.0.37
error: Uncaught (in promise) PostgresError: invalid input syntax for type uuid: "function generate() {
const rnds = crypto.getRandomValues(new Uint8Array(16));
rnds[6] = (rnds[6] & 0x0f) | 0x40;
rnds[8] = (rnds[8] & 0x3f) | 0x80;
return bytesToUuid(rnds);
}"
return new PostgresError(parseWarning(msg));
^
at parseError (https://deno.land/x/postgres@v0.11.2/connection/warning.ts:48:10)
at Connection.processError (https://deno.land/x/postgres@v0.11.2/connection/connection.ts:689:19)
at Connection._simpleQuery (https://deno.land/x/postgres@v0.11.2/connection/connection.ts:550:20)
at async Connection.query (https://deno.land/x/postgres@v0.11.2/connection/connection.ts:795:16)
at async PostgresConnector.query (https://raw.githubusercontent.com/eveningkid/denodb/master/lib/connectors/postgres-connector.ts:63:22)
at async Database.query (https://raw.githubusercontent.com/eveningkid/denodb/master/lib/database.ts:240:21)
at async Function.createTable (https://raw.githubusercontent.com/eveningkid/denodb/master/lib/model.ts:172:5)
at async Database.sync (https://raw.githubusercontent.com/eveningkid/denodb/master/lib/database.ts:210:7)
at async file:///home/mb/my/career/deno/denodb/demo/users-demo-oak-graphql-server/src/models.ts:24:1
Watcher Process finished! Restarting on file change...
@borsemayur2 would you mind sharing the full model file that throws an error (with DataTypes.UUID
)?
This indeed seems abnormal...
@eveningkid Here's the file: models.ts
Is there an update here? What is the best way to generate a random uuid as a default? Seems like v4.generate
is deprecated.
Is there an update here? What is the best way to generate a random uuid as a default? Seems like
v4.generate
is deprecated.
crypto.randomUUID()
Hi,
I have one issue that would like to ask here.
If I set the id to INTEGER it will be auto-generated, but if I use UUID it's not. This is my model.
Do I miss anything to have this auto-generated?