首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如果mysql结果值是数组,而泛型T不是数组,那么可以在类型记录中删除它吗?

如果mysql结果值是数组,而泛型T不是数组,那么可以在类型记录中删除它吗?
EN

Stack Overflow用户
提问于 2022-02-02 08:28:35
回答 1查看 268关注 0票数 0
代码语言:javascript
复制
type User = {
  name: string
  email: string
}

这是我的密码

代码语言:javascript
复制
import type { PoolConnection, RowDataPacket, OkPacket } from "mysql2/promise";

type dbDefaults = RowDataPacket[] | RowDataPacket[][] | OkPacket | OkPacket[];
type dbQuery<T> = T & dbDefaults;

type FlattenIfArray<T> = T extends (infer R)[] ? R : T;

function isFlattenArray<T>(rows: any[]): rows is T[] {
  return rows.length < 1;
}

// eslint-disable-next-line consistent-return
export async function queryWrapper<T>(
  { query, values }: { query: string; values?: string[] },
  conn: PoolConnection
): Promise<T | undefined> {
  try {
    await conn.beginTransaction();
    const [rows, _] = await conn.query<dbQuery<T>>(query, values || undefined);
    await conn.commit();

    if (isFlattenArray<FlattenIfArray<T>>(rows)) {
      return rows;
    }

    return rows;
  } catch (error) {
    await conn.rollback();
  } finally {
    conn.release();
  }
}

Mysql代码只返回数组

User[]没有问题。但是在使用User时,我想删除这个安排。

所以我用了这段代码,但它不起作用。我该怎么办?

我补充了一些解释。

const result = queryWrapper<User>(query, values, conn)

当使用user时,它是这样出现的。

代码语言:javascript
复制
[
  {
   name: "user-name",
   email: "user@gmail.com"
  }
]

但我希望它像这样出来。

代码语言:javascript
复制
{
 name: "user-name",
 email: "user@gmail.com"
}
EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2022-02-11 00:13:04

我自己回答。

代码语言:javascript
复制
type dbDefaults =
  | RowDataPacket[]
  | RowDataPacket[][]
  | OkPacket
  | OkPacket[]
  | ResultSetHeader;

type Query = { query: string; values?: any[] };

type QueryFunction<T = any> = () => Promise<[T & dbDefaults, FieldPacket[]]>;

type AlwaysArray<T> = T extends (infer R)[] ? R[] : T[];
// eslint-disable-next-line consistent-return
export async function queryTransactionWrapper<T = any>(
  queries: QueryFunction[],
  conn: PoolConnection
): Promise<[AlwaysArray<T>, FieldPacket[]][] | undefined> {
  try {
    await conn.beginTransaction();
    // await conn.query("START TRANSACTION;");

    const executedQueries = await Promise.all(
      queries.map((query) => {
        return query();
      })
    );

    // await conn.query("COMMIT;");
    await conn.commit();
    return executedQueries;
  } catch (error) {
    logger.error(colors.blue(JSON.stringify(error)));
    await conn.rollback();
  } finally {
    conn.release();
  }
}

export function findOne({ query, values }: Query, conn: PoolConnection) {
  return function () {
    return conn.query<RowDataPacket[]>(query, values);
  };
}

export function find({ query, values }: Query, conn: PoolConnection) {
  return function () {
    return conn.query<RowDataPacket[]>(query, values);
  };
}

export function update({ query, values }: Query, conn: PoolConnection) {
  return function () {
    return conn.query<ResultSetHeader>(query, values);
  };
}

export function insert({ query, values }: Query, conn: PoolConnection) {
  return function () {
    return conn.query<OkPacket>(query, values);
  };
}

何时调用findOneUser

代码语言:javascript
复制
async findByEmail(email: string): Promise<IUser | undefined> {
    const conn = await this.mysql.getConnection();
    const query = `Select * FROM ${USER_TABLE} WHERE email=?`;

    const findUserQueryFunction = findOne({ query, values: [email] }, conn);

    const executedQueries = await queryTransactionWrapper<IUser>(
      [findUserQueryFunction],
      conn
    );
    if (!executedQueries) {
      throw new Error();
    }
    const [[rows]] = executedQueries;

    return rows[0];
  }

如果,则findByEmail返回行,否则返回行

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/70952470

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档