Skip to content

Commit bad1829

Browse files
kyleconroyclaude
andcommitted
Add ALTER TABLE REBUILD index options support
- Add ONLINE option with WAIT_AT_LOW_PRIORITY support - Add DATA_COMPRESSION with ON PARTITIONS support - Add PAD_INDEX and FILLFACTOR options - Support COLUMNSTORE and COLUMNSTORE_ARCHIVE compression levels Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
1 parent c4759e0 commit bad1829

3 files changed

Lines changed: 150 additions & 2 deletions

File tree

parser/parse_ddl.go

Lines changed: 148 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10457,6 +10457,154 @@ func (p *Parser) parseAlterTableRebuildStatement(tableName *ast.SchemaObjectName
1045710457
OptionState: state,
1045810458
}
1045910459
stmt.IndexOptions = append(stmt.IndexOptions, opt)
10460+
case "PAD_INDEX":
10461+
stateUpper := strings.ToUpper(p.curTok.Literal)
10462+
state := "On"
10463+
if stateUpper == "OFF" {
10464+
state = "Off"
10465+
}
10466+
p.nextToken()
10467+
opt := &ast.IndexStateOption{
10468+
OptionKind: "PadIndex",
10469+
OptionState: state,
10470+
}
10471+
stmt.IndexOptions = append(stmt.IndexOptions, opt)
10472+
case "FILLFACTOR":
10473+
opt := &ast.IndexExpressionOption{
10474+
OptionKind: "FillFactor",
10475+
Expression: &ast.IntegerLiteral{
10476+
LiteralType: "Integer",
10477+
Value: p.curTok.Literal,
10478+
},
10479+
}
10480+
stmt.IndexOptions = append(stmt.IndexOptions, opt)
10481+
p.nextToken()
10482+
case "ONLINE":
10483+
stateUpper := strings.ToUpper(p.curTok.Literal)
10484+
state := "On"
10485+
if stateUpper == "OFF" {
10486+
state = "Off"
10487+
}
10488+
p.nextToken()
10489+
opt := &ast.OnlineIndexOption{
10490+
OptionKind: "Online",
10491+
OptionState: state,
10492+
}
10493+
// Check for (WAIT_AT_LOW_PRIORITY ...)
10494+
if p.curTok.Type == TokenLParen {
10495+
p.nextToken() // consume (
10496+
if strings.ToUpper(p.curTok.Literal) == "WAIT_AT_LOW_PRIORITY" {
10497+
p.nextToken() // consume WAIT_AT_LOW_PRIORITY
10498+
if p.curTok.Type == TokenLParen {
10499+
p.nextToken() // consume (
10500+
lwOpt := &ast.OnlineIndexLowPriorityLockWaitOption{}
10501+
for p.curTok.Type != TokenRParen && p.curTok.Type != TokenEOF {
10502+
lwOptName := strings.ToUpper(p.curTok.Literal)
10503+
p.nextToken()
10504+
if p.curTok.Type == TokenEquals {
10505+
p.nextToken()
10506+
}
10507+
if lwOptName == "MAX_DURATION" {
10508+
maxDurOpt := &ast.LowPriorityLockWaitMaxDurationOption{
10509+
OptionKind: "MaxDuration",
10510+
MaxDuration: &ast.IntegerLiteral{LiteralType: "Integer", Value: p.curTok.Literal},
10511+
}
10512+
p.nextToken()
10513+
// Check for MINUTES
10514+
if strings.ToUpper(p.curTok.Literal) == "MINUTES" {
10515+
maxDurOpt.Unit = "Minutes"
10516+
p.nextToken()
10517+
}
10518+
lwOpt.Options = append(lwOpt.Options, maxDurOpt)
10519+
} else if lwOptName == "ABORT_AFTER_WAIT" {
10520+
abortVal := strings.ToUpper(p.curTok.Literal)
10521+
var abortAfterWait string
10522+
switch abortVal {
10523+
case "NONE":
10524+
abortAfterWait = "None"
10525+
case "SELF":
10526+
abortAfterWait = "Self"
10527+
case "BLOCKERS":
10528+
abortAfterWait = "Blockers"
10529+
default:
10530+
abortAfterWait = abortVal
10531+
}
10532+
p.nextToken()
10533+
lwOpt.Options = append(lwOpt.Options, &ast.LowPriorityLockWaitAbortAfterWaitOption{
10534+
OptionKind: "AbortAfterWait",
10535+
AbortAfterWait: abortAfterWait,
10536+
})
10537+
}
10538+
if p.curTok.Type == TokenComma {
10539+
p.nextToken()
10540+
}
10541+
}
10542+
if p.curTok.Type == TokenRParen {
10543+
p.nextToken() // consume inner )
10544+
}
10545+
opt.LowPriorityLockWaitOption = lwOpt
10546+
}
10547+
}
10548+
if p.curTok.Type == TokenRParen {
10549+
p.nextToken() // consume outer )
10550+
}
10551+
}
10552+
stmt.IndexOptions = append(stmt.IndexOptions, opt)
10553+
case "DATA_COMPRESSION":
10554+
compLevel := strings.ToUpper(p.curTok.Literal)
10555+
var compressionLevel string
10556+
switch compLevel {
10557+
case "NONE":
10558+
compressionLevel = "None"
10559+
case "ROW":
10560+
compressionLevel = "Row"
10561+
case "PAGE":
10562+
compressionLevel = "Page"
10563+
case "COLUMNSTORE":
10564+
compressionLevel = "ColumnStore"
10565+
case "COLUMNSTORE_ARCHIVE":
10566+
compressionLevel = "ColumnStoreArchive"
10567+
default:
10568+
compressionLevel = compLevel
10569+
}
10570+
p.nextToken()
10571+
opt := &ast.DataCompressionOption{
10572+
OptionKind: "DataCompression",
10573+
CompressionLevel: compressionLevel,
10574+
}
10575+
// Check for ON PARTITIONS (...)
10576+
if p.curTok.Type == TokenOn {
10577+
p.nextToken() // consume ON
10578+
if strings.ToUpper(p.curTok.Literal) == "PARTITIONS" {
10579+
p.nextToken() // consume PARTITIONS
10580+
if p.curTok.Type == TokenLParen {
10581+
p.nextToken() // consume (
10582+
for p.curTok.Type != TokenRParen && p.curTok.Type != TokenEOF {
10583+
pr := &ast.CompressionPartitionRange{}
10584+
if p.curTok.Type == TokenNumber {
10585+
pr.From = &ast.IntegerLiteral{LiteralType: "Integer", Value: p.curTok.Literal}
10586+
p.nextToken()
10587+
}
10588+
// Check for TO range
10589+
if strings.ToUpper(p.curTok.Literal) == "TO" {
10590+
p.nextToken() // consume TO
10591+
if p.curTok.Type == TokenNumber {
10592+
pr.To = &ast.IntegerLiteral{LiteralType: "Integer", Value: p.curTok.Literal}
10593+
p.nextToken()
10594+
}
10595+
}
10596+
opt.PartitionRanges = append(opt.PartitionRanges, pr)
10597+
if p.curTok.Type == TokenComma {
10598+
p.nextToken()
10599+
}
10600+
}
10601+
if p.curTok.Type == TokenRParen {
10602+
p.nextToken() // consume )
10603+
}
10604+
}
10605+
}
10606+
}
10607+
stmt.IndexOptions = append(stmt.IndexOptions, opt)
1046010608
default:
1046110609
// Skip unknown options
1046210610
p.nextToken()
Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
{"todo": true}
1+
{}
Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
{"todo": true}
1+
{}

0 commit comments

Comments
 (0)