Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
50 changes: 50 additions & 0 deletions src/queryKinds/ddl/table/Alter.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
import { describe, expect, it } from "vitest";
import AlterTableQuery from "./Alter.js";
import Column from "../../../queryUtils/Column.js";


describe('Alter Table Query', () => {
it('should create a basic ALTER TABLE query to add a column', () => {
const query = new AlterTableQuery('users')
.addColumnsToAdd(Column('id', 'INT').primaryKey().notNull())
.build();

expect(query).toEqual([
'ALTER TABLE "users" ADD COLUMN id INT;',
'ALTER TABLE "users" ALTER COLUMN id SET NOT NULL;',
'ALTER TABLE "users" ADD CONSTRAINT id_pkey PRIMARY KEY (id);',
]);
});

it('should allow to set table name later', () => {
const query = new AlterTableQuery()
.table('products')
.addColumnsToAdd([
Column('product_id', 'INT').primaryKey().notNull(),
])
.build();

expect(query).toEqual([
'ALTER TABLE "products" ADD COLUMN product_id INT;',
'ALTER TABLE "products" ALTER COLUMN product_id SET NOT NULL;',
'ALTER TABLE "products" ADD CONSTRAINT product_id_pkey PRIMARY KEY (product_id);',
]);
});

it('should allow to set columns to add', () => {
const query = new AlterTableQuery('orders')
.setColumnsToAdd([
Column('order_id', 'INT').primaryKey().notNull(),
Column('order_date', 'DATE').notNull(),
])
.build();

expect(query).toEqual([
'ALTER TABLE "orders" ADD COLUMN order_id INT;',
'ALTER TABLE "orders" ALTER COLUMN order_id SET NOT NULL;',
'ALTER TABLE "orders" ADD CONSTRAINT order_id_pkey PRIMARY KEY (order_id);',
'ALTER TABLE "orders" ADD COLUMN order_date DATE;',
'ALTER TABLE "orders" ALTER COLUMN order_date SET NOT NULL;',
]);
});
});
8 changes: 2 additions & 6 deletions src/queryKinds/ddl/table/Alter.ts
Original file line number Diff line number Diff line change
Expand Up @@ -199,13 +199,9 @@ export default class AlterTableQuery extends TableQueryDefinition {
* @returns The SQL string representation of the ALTER TABLE query.
* @throws Error if the query has not been built yet.
*/
public toSQL(): string | string[] {
public toSQL(): string[] {
if (this.builtQuery) this.build();
if (!this.builtQuery)
throw new Error(
"No built query available. Please build the query first.",
);
return this.builtQuery;
return this.builtQuery as string[];
}

/**
Expand Down
65 changes: 65 additions & 0 deletions src/queryKinds/ddl/table/Create.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ import { describe, expect, it } from "vitest";
import CreateTableQuery from "./Create.js";
import Column from "../../../queryUtils/Column.js";
import { Decimal, Varchar } from "../../../types/ColumnTypes.js";
import QueryKind from "../../../types/QueryKind.js";


describe('Create Table Query', () => {
Expand Down Expand Up @@ -101,4 +102,68 @@ describe('Create Table Query', () => {
const query = new CreateTableQuery('empty_table');
expect(() => query.build()).toThrow('No columns defined for the table.');
});

it('should reset the query state', () => {
const query = new CreateTableQuery('temp_table')
.ifNotExists()
.addColumns([
Column('id', 'INT').primaryKey().notNull()
]);

query.reset();

expect(() => query.build()).toThrow('Table name is not set.');
});

it('should return toSQL correctly', () => {
const query = new CreateTableQuery('logs')
.addColumns(Column('id', 'INT').primaryKey().notNull())
.addColumns(Column('message', Varchar(255)).notNull());

expect(query.toSQL()).toBe(
'CREATE TABLE "logs" (\n id INT PRIMARY KEY,\n message VARCHAR(255) NOT NULL\n);'
);
});

it('should be able to handle setting columns', () => {
const query = new CreateTableQuery('employees')
.setColumns([
Column('id', 'INT').primaryKey().notNull(),
Column('first_name', Varchar(50)).notNull(),
Column('last_name', Varchar(50)).notNull()
]);

expect(query.build()).toBe(
'CREATE TABLE "employees" (\n id INT PRIMARY KEY,\n first_name VARCHAR(50) NOT NULL,\n last_name VARCHAR(50) NOT NULL\n);'
);
});

it('should be able to return its columns array', () => {
const columns = [
Column('id', 'INT').primaryKey().notNull(),
Column('username', Varchar(50)).notNull()
];
const query = new CreateTableQuery('accounts')
.setColumns(columns);

expect(query.columns).toEqual(columns);
});

it('should be able to set the table name later', () => {
const query = new CreateTableQuery()
.table('departments')
.addColumns([
Column('id', 'INT').primaryKey().notNull(),
Column('dept_name', Varchar(100)).notNull()
]);

expect(query.build()).toBe(
'CREATE TABLE "departments" (\n id INT PRIMARY KEY,\n dept_name VARCHAR(100) NOT NULL\n);'
);
});

it('should return its kind', () => {
const query = new CreateTableQuery('audit');
expect(query.kind).toBe(QueryKind.CREATE_TABLE);
});
});
7 changes: 4 additions & 3 deletions src/queryKinds/ddl/table/Create.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ export default class CreateTableQuery extends TableQueryDefinition {
this.tableName = tableName
? SqlEscaper.escapeTableName(tableName, this.flavor)
: "";
this.tableColumns = columns ?? [];
this.tableColumns = columns;
}

/**
Expand Down Expand Up @@ -98,7 +98,7 @@ export default class CreateTableQuery extends TableQueryDefinition {
this.tableName = "";
this.tableColumns = [];
this.builtQuery = null;
this.ifNotExistsFlag = false;
this.resetIfNotExists();
return this;
}

Expand All @@ -107,7 +107,8 @@ export default class CreateTableQuery extends TableQueryDefinition {
* @returns The SQL string representation of the CREATE TABLE query.
*/
public toSQL(): string {
return this.build();
if(!this.builtQuery) this.build();
return this.builtQuery as string;
}

/**
Expand Down
48 changes: 48 additions & 0 deletions src/queryKinds/ddl/table/Drop.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
import { describe, expect, it } from "vitest";
import DropTableQuery from "./Drop.js";
import QueryKind from "../../../types/QueryKind.js";

describe('Drop Table Query', () => {
it('should create a basic DROP TABLE query', () => {
const query = new DropTableQuery('users').build();
expect(query).toBe('DROP TABLE "users";');
});

it('should be able to set table name later', () => {
const query = new DropTableQuery().table('products').build();
expect(query).toBe('DROP TABLE "products";');
});

it('should throw if table name is not provided', () => {
const query = new DropTableQuery();
expect(() => query.build()).toThrow('Table name is required to build DROP TABLE query.');
});

it('should create a DROP TABLE query with IF EXISTS', () => {
const query = new DropTableQuery('users').ifExists().build();
expect(query).toBe('DROP TABLE IF EXISTS "users";');
});

it('should clone the DropTableQuery instance', () => {
const original = new DropTableQuery('orders').ifExists();
const cloned = original.clone();
expect(cloned).not.toBe(original);
expect(cloned.build()).toBe(original.build());
});

it('should reset the DropTableQuery instance', () => {
const query = new DropTableQuery('customers').ifExists();
query.reset();
expect(() => query.build()).toThrow('Table name is required to build DROP TABLE query.');
});

it('should return the correct SQL string representation', () => {
const query = new DropTableQuery('employees').ifExists();
expect(query.toSQL()).toBe('DROP TABLE IF EXISTS "employees";');
});

it('should return kind as DROP_TABLE', () => {
const query = new DropTableQuery('departments');
expect(query.kind).toBe(QueryKind.DROP_TABLE);
});
});
13 changes: 10 additions & 3 deletions src/queryKinds/ddl/table/Drop.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,11 @@ export default class DropTableQuery extends TableQueryDefinition {
: "";
}

public ifExists(): this {
this.ifNotExistsFlag = true;
return this;
}

/**
* Builds the DROP TABLE SQL query string.
* @param _deepAnalysis - Optional boolean to indicate if deep analysis is required (default is false).
Expand All @@ -39,7 +44,8 @@ export default class DropTableQuery extends TableQueryDefinition {
* @returns A new DropTableQuery instance with the same properties as the current instance.
*/
public clone(): DropTableQuery {
const cloned = new DropTableQuery(this.tableName);
const cloned = new DropTableQuery();
cloned.tableName = this.tableName;
cloned.flavor = this.flavor;
cloned.ifNotExistsFlag = this.ifNotExistsFlag;
return cloned;
Expand All @@ -53,7 +59,7 @@ export default class DropTableQuery extends TableQueryDefinition {
public reset(): this {
this.tableName = "";
this.builtQuery = null;
this.ifNotExistsFlag = false;
this.resetIfNotExists();
return this;
}

Expand All @@ -62,7 +68,8 @@ export default class DropTableQuery extends TableQueryDefinition {
* @returns The SQL string representation of the DROP TABLE query.
*/
public toSQL(): string {
return this.build();
if(!this.builtQuery) this.build();
return this.builtQuery as string;
}

/** Getter for the kind of query. */
Expand Down