Skip to content
Open
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
4 changes: 4 additions & 0 deletions sqlglot/expressions/ddl.py
Original file line number Diff line number Diff line change
Expand Up @@ -245,6 +245,10 @@ class AlterColumn(Expression):
}


class ModifyColumn(Expression):
pass


class AlterIndex(Expression):
arg_types = {"this": True, "visible": True}

Expand Down
3 changes: 3 additions & 0 deletions sqlglot/generators/mysql.py
Original file line number Diff line number Diff line change
Expand Up @@ -718,6 +718,9 @@ def altercolumn_sql(self, expression: exp.AlterColumn) -> str:
this = self.sql(expression, "this")
return f"MODIFY COLUMN {this} {dtype}"

def modifycolumn_sql(self, expression: exp.ModifyColumn) -> str:
return f"MODIFY COLUMN {self.sql(expression, 'this')}"

def _prefixed_sql(self, prefix: str, expression: exp.Expr, arg: str) -> str:
sql = self.sql(expression, arg)
return f" {prefix} {sql}" if sql else ""
Expand Down
23 changes: 22 additions & 1 deletion sqlglot/parsers/mysql.py
Original file line number Diff line number Diff line change
Expand Up @@ -252,7 +252,7 @@ class MySQLParser(parser.Parser):

ALTER_PARSERS = {
**parser.Parser.ALTER_PARSERS,
"MODIFY": lambda self: self._parse_alter_table_alter(),
"MODIFY": lambda self: self._parse_alter_table_modify(),
"AUTO_INCREMENT": lambda self: self._parse_property_assignment(exp.AutoIncrementProperty),
}

Expand Down Expand Up @@ -315,6 +315,27 @@ def _parse_alter_drop_action(self) -> exp.Expr | None:
return self.expression(exp.DropPrimaryKey())
return super()._parse_alter_drop_action()

def _parse_alter_table_modify(self) -> exp.Expr | None:
self._match(TokenType.COLUMN)

column = self._parse_field(any_token=True)
if column is None:
return None

column_def = self._parse_column_def(column)
if not isinstance(column_def, exp.ColumnDef):
return None

if self._match_texts(("FIRST", "AFTER")):
keyword = self._prev.text.upper()
target = self._parse_column() if keyword == "AFTER" else None
column_def.set(
"position",
self.expression(exp.ColumnPosition(this=target, position=keyword)),
)

return self.expression(exp.ModifyColumn(this=column_def))

def _parse_generated_as_identity(
self,
) -> (
Expand Down
12 changes: 12 additions & 0 deletions tests/dialects/test_mysql.py
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,18 @@ def test_ddl(self):
self.validate_identity("ALTER TABLE t DROP PRIMARY KEY")
self.validate_identity("ALTER TABLE t DROP COLUMN c, DROP PRIMARY KEY, DROP INDEX `i`")
self.validate_identity("ALTER TABLE test_table MODIFY COLUMN test_column LONGTEXT")
self.validate_identity("ALTER TABLE t MODIFY COLUMN c INT NOT NULL")
self.validate_identity("ALTER TABLE t MODIFY COLUMN c INT DEFAULT 5")
self.validate_identity("ALTER TABLE t MODIFY COLUMN c INT NOT NULL DEFAULT 5")
self.validate_identity("ALTER TABLE t MODIFY COLUMN c VARCHAR(50) NOT NULL DEFAULT 'foo'")
self.validate_identity("ALTER TABLE t MODIFY COLUMN c INT COMMENT 'hi'")
self.validate_identity("ALTER TABLE t MODIFY COLUMN c INT FIRST")
self.validate_identity("ALTER TABLE t MODIFY COLUMN c INT AFTER d")
self.validate_identity("ALTER TABLE t MODIFY COLUMN c INT NOT NULL AFTER d")
self.validate_identity(
"ALTER TABLE t MODIFY c INT NOT NULL",
"ALTER TABLE t MODIFY COLUMN c INT NOT NULL",
)
self.validate_identity("ALTER TABLE t AUTO_INCREMENT=3000000000")
self.validate_identity("ALTER VIEW v AS SELECT a, b, c, d FROM foo")
self.validate_identity("ALTER VIEW v AS SELECT * FROM foo WHERE c > 100")
Expand Down
Loading