@@ -3574,10 +3574,82 @@ func (p *Parser) parseColumnDefinition() (*ast.ColumnDefinition, error) {
35743574 indexDef := & ast.IndexDefinition {
35753575 IndexType : & ast.IndexType {},
35763576 }
3577- // Parse index name
3578- if p .curTok .Type == TokenIdent {
3577+ // Parse index name (skip if it's CLUSTERED/NONCLUSTERED)
3578+ idxUpper := strings .ToUpper (p .curTok .Literal )
3579+ if p .curTok .Type == TokenIdent && idxUpper != "CLUSTERED" && idxUpper != "NONCLUSTERED" && p .curTok .Type != TokenLParen {
35793580 indexDef .Name = p .parseIdentifier ()
35803581 }
3582+ // Parse optional CLUSTERED/NONCLUSTERED
3583+ if strings .ToUpper (p .curTok .Literal ) == "CLUSTERED" {
3584+ indexDef .IndexType .IndexTypeKind = "Clustered"
3585+ p .nextToken ()
3586+ } else if strings .ToUpper (p .curTok .Literal ) == "NONCLUSTERED" {
3587+ indexDef .IndexType .IndexTypeKind = "NonClustered"
3588+ p .nextToken ()
3589+ }
3590+ // Parse optional column list: (col1 [ASC|DESC], ...)
3591+ if p .curTok .Type == TokenLParen {
3592+ p .nextToken () // consume (
3593+ for p .curTok .Type != TokenRParen && p .curTok .Type != TokenEOF {
3594+ colWithSort := & ast.ColumnWithSortOrder {
3595+ SortOrder : ast .SortOrderNotSpecified ,
3596+ }
3597+ // Parse column name
3598+ colRef := & ast.ColumnReferenceExpression {
3599+ ColumnType : "Regular" ,
3600+ MultiPartIdentifier : & ast.MultiPartIdentifier {
3601+ Identifiers : []* ast.Identifier {p .parseIdentifier ()},
3602+ },
3603+ }
3604+ colRef .MultiPartIdentifier .Count = len (colRef .MultiPartIdentifier .Identifiers )
3605+ colWithSort .Column = colRef
3606+
3607+ // Parse optional ASC/DESC
3608+ if strings .ToUpper (p .curTok .Literal ) == "ASC" {
3609+ colWithSort .SortOrder = ast .SortOrderAscending
3610+ p .nextToken ()
3611+ } else if strings .ToUpper (p .curTok .Literal ) == "DESC" {
3612+ colWithSort .SortOrder = ast .SortOrderDescending
3613+ p .nextToken ()
3614+ }
3615+ indexDef .Columns = append (indexDef .Columns , colWithSort )
3616+
3617+ if p .curTok .Type == TokenComma {
3618+ p .nextToken ()
3619+ } else {
3620+ break
3621+ }
3622+ }
3623+ if p .curTok .Type == TokenRParen {
3624+ p .nextToken () // consume )
3625+ }
3626+ }
3627+ // Parse optional INCLUDE clause
3628+ if strings .ToUpper (p .curTok .Literal ) == "INCLUDE" {
3629+ p .nextToken () // consume INCLUDE
3630+ if p .curTok .Type == TokenLParen {
3631+ p .nextToken () // consume (
3632+ for p .curTok .Type != TokenRParen && p .curTok .Type != TokenEOF {
3633+ colRef := & ast.ColumnReferenceExpression {
3634+ ColumnType : "Regular" ,
3635+ MultiPartIdentifier : & ast.MultiPartIdentifier {
3636+ Identifiers : []* ast.Identifier {p .parseIdentifier ()},
3637+ },
3638+ }
3639+ colRef .MultiPartIdentifier .Count = len (colRef .MultiPartIdentifier .Identifiers )
3640+ indexDef .IncludeColumns = append (indexDef .IncludeColumns , colRef )
3641+
3642+ if p .curTok .Type == TokenComma {
3643+ p .nextToken ()
3644+ } else {
3645+ break
3646+ }
3647+ }
3648+ if p .curTok .Type == TokenRParen {
3649+ p .nextToken () // consume )
3650+ }
3651+ }
3652+ }
35813653 col .Index = indexDef
35823654 } else if upperLit == "SPARSE" {
35833655 p .nextToken () // consume SPARSE
0 commit comments