drizzle-team / drizzle-team/drizzle-orm
[Enhancement]: Allow different input/output types on customType
- Dominant language
- TypeScript
- Stars
- 35.8k
- Forks
- 1.6k
- Avg merge
- 2d 7h
- Merged PRs (30d)
- 4
Description
### What version of `drizzle-orm` are you using?
0.29.1
### What version of `drizzle-kit` are you using?
_No response_
### Describe the Bug
In the following code, when you insert, you should be able to input both `Vector` and `number[]`
```ts
export const customVector = customType<{
data: Vector|number[];
driverData: string;
config: { dimensions: number };
}>({
dataType(config) {
if (!config) {
return `vector(1536)`;
}
return `vector(${config.dimensions})`;
},
toDriver(value: Vector | number[]): string {
return toSql(value);
},
fromDriver(value: string): Vector {
return fromSql(value);
},
});
function fromSql(value: string) {
return new Vector(
value
.substring(1, value.length - 1)
.split(",")
.map((v) => parseFloat(v))
);
}
function toSql(value: Vector | number[]) {
return JSON.stringify(value);
}
```
Both of these work:
```ts
await db.insert(schema.myTable).values({ id: "1", embedding: [1, 2, 3] });
await db.insert(schema.myTable).values({ id: "1", embedding: new Vector([1, 2, 3]) });
```
This is great, however, given the fromDriver ALWAYS returns a vector, it should be able to correctly infer that it's a `Vector` type.
However, when querying the database, it returns as `Vector | number[]`
```ts
const myEmbeddingQuery = await db.select({ embedding: schema.myTable.embedding }).from(schema.myTable);
// ^? const myEmbeddingQuery: { embedding: Vector | number[];}[]
```
It seems to simply use the `data: Vector | number[];` type from the `customType`, however I've looked in the codebase and it should be able to infer the type based on the `fromDriver`.
https://github.com/drizzle-team/drizzle-orm/blob/0a4e3b265ce121675e7baa14f3a39669ea387e6d/drizzle-orm/src/pg-core/columns/custom.ts#L60-L83
### Expected behavior
Custom types should be able to have different input/output types.
Being able to transform data at the ORM-level would be such a powerful ability, in ensuring that data is always the format that you want it to be, without having to transform on every query.
### Environment & setup
_No response_
Contributor guide
Assessment
This issue has not been assessed yet.