(rawExpr *pgquery.Node)
| 1234 | } |
| 1235 | |
| 1236 | func (p PostgresParser) parseDefaultValue(rawExpr *pgquery.Node) (*parser.DefaultDefinition, error) { |
| 1237 | node, err := p.parseExpr(rawExpr) |
| 1238 | if err != nil { |
| 1239 | return nil, err |
| 1240 | } |
| 1241 | switch expr := node.(type) { |
| 1242 | case *parser.NullVal: |
| 1243 | return &parser.DefaultDefinition{ |
| 1244 | Expression: parser.DefaultExpression{ |
| 1245 | Expr: parser.NewValArg("null"), |
| 1246 | }, |
| 1247 | }, nil |
| 1248 | case *parser.SQLVal: |
| 1249 | return &parser.DefaultDefinition{ |
| 1250 | Expression: parser.DefaultExpression{ |
| 1251 | Expr: expr, |
| 1252 | }, |
| 1253 | }, nil |
| 1254 | case *parser.BoolVal: |
| 1255 | return &parser.DefaultDefinition{ |
| 1256 | Expression: parser.DefaultExpression{ |
| 1257 | Expr: parser.NewBoolSQLVal(bool(*expr)), |
| 1258 | }, |
| 1259 | }, nil |
| 1260 | case *parser.ArrayConstructor: |
| 1261 | return &parser.DefaultDefinition{ |
| 1262 | Expression: parser.DefaultExpression{ |
| 1263 | Expr: expr, |
| 1264 | }, |
| 1265 | }, nil |
| 1266 | case *parser.CastExpr: |
| 1267 | // Preserve CastExpr nodes in defaults (fix for incorrect normalization) |
| 1268 | // PostgreSQL stores defaults with explicit casts, so we should preserve them |
| 1269 | // Special case: Convert NullVal to SQLVal for consistency |
| 1270 | if nullVal, ok := expr.Expr.(*parser.NullVal); ok { |
| 1271 | _ = nullVal // Mark as used |
| 1272 | // Handle NULL::type casts by converting NullVal to SQLVal |
| 1273 | // PostgreSQL represents NULL as NullVal in pg_query AST but we use SQLVal |
| 1274 | // Preserve the cast by wrapping the SQLVal in a CastExpr |
| 1275 | // Use lowercase null to match the lexer's keyword normalization |
| 1276 | return &parser.DefaultDefinition{ |
| 1277 | Expression: parser.DefaultExpression{ |
| 1278 | Expr: &parser.CastExpr{ |
| 1279 | Expr: parser.NewValArg("null"), |
| 1280 | Type: expr.Type, |
| 1281 | }, |
| 1282 | }, |
| 1283 | }, nil |
| 1284 | } |
| 1285 | // For other CastExpr cases, check if the cast is semantically meaningful |
| 1286 | // Strip redundant casts like ::text, ::character varying on string literals |
| 1287 | // But preserve important casts like ::interval, ::bpchar, ::json, ::jsonb, ::integer[], and numeric casts |
| 1288 | if expr.Type != nil { |
| 1289 | typeStr := strings.ToLower(expr.Type.Type) |
| 1290 | // Check if this is a redundant cast that should be stripped |
| 1291 | if sqlVal, ok := expr.Expr.(*parser.SQLVal); ok && sqlVal.Type == parser.StrVal { |
| 1292 | switch typeStr { |
| 1293 | case "integer", "bigint", "smallint": |
no test coverage detected