Skip to content

Commit e9f858d

Browse files
fix: Enhance binary and varbinary introspection handling in MySQL dialect
1 parent d6bbf2c commit e9f858d

2 files changed

Lines changed: 26 additions & 5 deletions

File tree

drizzle-kit/src/dialects/mysql/grammar.ts

Lines changed: 22 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -358,7 +358,14 @@ export const Binary: SqlType = {
358358
defaultFromIntrospect: (value) => {
359359
// when you do `binary default 'text'` instead of `default ('text')`
360360
if (value.startsWith('0x')) {
361-
return `'${Buffer.from(value.slice(2), 'hex').toString('utf-8')}'`;
361+
if (typeof Buffer !== 'undefined') {
362+
return `'${Buffer.from(value.slice(2), 'hex').toString('utf-8')}'`;
363+
}
364+
const hex = value.slice(2);
365+
const matches = hex.match(/.{1,2}/g) ?? [];
366+
const bytes = new Uint8Array(matches.map((b) => parseInt(b, 16)));
367+
const decoded = new TextDecoder().decode(bytes);
368+
return `'${decoded}'`;
362369
}
363370
return value;
364371
},
@@ -369,7 +376,12 @@ export const Varbinary: SqlType = {
369376
is: (type) => /^(?:varbinary)(?:[\s(].*)?$/i.test(type),
370377
drizzleImport: () => 'varbinary',
371378
defaultFromDrizzle: (value) => {
372-
return `(0x${Buffer.from(value as string).toString('hex').toLowerCase()})`;
379+
if (typeof Buffer !== 'undefined') {
380+
return `(0x${Buffer.from(value as string).toString('hex').toLowerCase()})`;
381+
}
382+
const bytes = new TextEncoder().encode(value as string);
383+
const hex = Array.from(bytes).map((b) => b.toString(16).padStart(2, '0')).join('');
384+
return `(0x${hex})`;
373385
},
374386
defaultFromIntrospect: (value) => value,
375387
toTs: (type, value) => {
@@ -382,7 +394,14 @@ export const Varbinary: SqlType = {
382394
let trimmed = value.startsWith('(') ? value.substring(1, value.length - 1) : value;
383395
trimmed = trimChar(value, "'");
384396
if (trimmed.startsWith('0x')) {
385-
trimmed = Buffer.from(trimmed.slice(2), 'hex').toString('utf-8');
397+
if (typeof Buffer !== 'undefined') {
398+
trimmed = Buffer.from(trimmed.slice(2), 'hex').toString('utf-8');
399+
} else {
400+
const hex = trimmed.slice(2);
401+
const matches = hex.match(/.{1,2}/g) ?? [];
402+
const bytes = new Uint8Array(matches.map((b) => parseInt(b, 16)));
403+
trimmed = new TextDecoder().decode(bytes);
404+
}
386405
return { options, default: `"${trimmed.replaceAll('"', '\\"')}"` };
387406
} else {
388407
return { options, default: `sql\`${value}\`` };

drizzle-kit/tests/mysql/pull.test.ts

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ import { SQL, sql } from 'drizzle-orm';
33
import {
44
AnyMySqlColumn,
55
bigint,
6+
binary,
67
blob,
78
boolean,
89
char,
@@ -806,15 +807,16 @@ test('datetime #2', async () => {
806807
expect(sqlStatements).toStrictEqual([]);
807808
});
808809

809-
test('introspect varbinary', async () => {
810+
test('introspect varbinary and binary', async () => {
810811
const table1 = mysqlTable('table1', {
811812
col1: varbinary({ length: 16 }),
813+
col2: binary({ length: 16 }).default(''),
812814
});
813815

814816
const { sqlStatements } = await diffIntrospect(
815817
db,
816818
{ table1 },
817-
'varbinary',
819+
'varbinary-and-binary',
818820
);
819821

820822
expect(sqlStatements).toStrictEqual([]);

0 commit comments

Comments
 (0)