How to get ID of last inserted row using denodb?

279 Views Asked by At

I am dealing with the work of DenoDb and trying to make the createCat function return the type Promise<CatModel>. What is the best way to do it? Here is my current code:

import { Model, Database, SQLite3Connector, DataTypes } from 'https://deno.land/x/denodb/mod.ts';

interface CatModel {
    id: bigint;
    name: string;
}

const connector = new SQLite3Connector({
  filepath: './db.sqlite',
});
const db = new Database(connector);

class CatSchema extends Model {
  static table = 'cats';
  static fields = {
      id: {
          type: DataTypes.BIG_INTEGER,
          primaryKey: true,
          autoIncrement: true,
      },
      name: {
          type: DataTypes.STRING,
      }
  };
}

db.link([CatSchema]);
await db.sync({ drop: true });

const createCat = async (name: string): Promise<CatSchema> => {
    return await CatSchema.create({
        name: name
    });
};

const dataCat = await createCat("Three");
console.log(dataCat);

await db.close();

Deno.exit(1);

I'm trying to make a function like this:

const createCat = async (name: string): Promise<CatModel>

How to convert Promise<CatSchema> to Promise<CatModel> correctly? I plan to hide the work with DenoDB in the CatsRepo class in the future and give only CatModel. Is this a good solution?

1

There are 1 best solutions below

2
jsejcksn On BEST ANSWER

Model.create returns an object which includes the id of the last inserted row as a number, and that property is called lastInsertId. Because denodb returns a number type, there's not much value in using bigint for the id of your CatModel, so you can just change it to number, then modify your function like this:

so-70550010.ts:

import {
  Database,
  DataTypes,
  Model,
  SQLite3Connector,
} from "https://deno.land/x/[email protected]/mod.ts";

class CatSchema extends Model {
  static table = "cats";
  static fields = {
    id: {
      type: DataTypes.BIG_INTEGER,
      primaryKey: true,
      autoIncrement: true,
    },
    name: {
      type: DataTypes.STRING,
    },
  };
}

interface CatModel {
  id: number;
  name: string;
}

async function createCat(name: string): Promise<CatModel> {
  const model = await CatSchema.create({ name });
  const id = model.lastInsertId as number;
  return { id, name };
}

async function main() {
  const connector = new SQLite3Connector({ filepath: ":memory:" });
  const db = new Database(connector);
  db.link([CatSchema]);
  await db.sync({ drop: true });

  for (const name of ["One", "Two", "Three"]) {
    const catModel = await createCat(name);
    console.log(catModel);
  }

  await db.close();
  await connector.close();
  Deno.exit();
}

if (import.meta.main) main();
$ deno run so-70550010.ts
{ id: 1, name: "One" }
{ id: 2, name: "Two" }
{ id: 3, name: "Three" }

If you want lower-level control while working with SQLite, I recommend https://deno.land/x/sqlite instead of denodb.