Files
Baradb/src/barabadb/query/ast.nim
T
dimgigov f7d4961125
CI / test (push) Has been cancelled
CI / verify (push) Has been cancelled
Clients CI / build-server (push) Has been cancelled
Clients CI / test-python (push) Has been cancelled
Clients CI / test-javascript (push) Has been cancelled
Clients CI / test-nim (push) Has been cancelled
Clients CI / test-rust (push) Has been cancelled
feat: Multi-tenant ERP support via session variables + RLS
- SET var = value / current_setting('var') for session-scoped variables
- current_user / current_role SQL keywords with auth bridge
- server.nim + httpserver.nim populate ExecutionContext.currentUser/currentRole
- RLS policies can reference current_setting('app.tenant_id') for tenant isolation
- Fixed evalExpr to propagate ctx recursively (fixes current_user in sub-expressions)
- Fixed GROUPING SETS execution (lowerSelect checks selGroupingSetsKind)
- Fixed FTS CREATE INDEX docId mismatch (hash of tableName.$key)
- Fixed all test suites to use isolated temp directories
- Added 5 multi-tenant tests (355 total, all green)
- Updated docs: PLAN_SQL_ADVANCED.md, baraql.md, changelog.md
2026-05-14 16:28:41 +03:00

557 lines
12 KiB
Nim

## BaraQL AST — Abstract Syntax Tree nodes
import ../core/types
type
NodeKind* = enum
# Statements
nkSelect
nkInsert
nkUpdate
nkDelete
nkMerge
nkCreateType
nkDropType
nkAlterType
nkCreateTable
nkDropTable
nkAlterTable
nkCreateIndex
nkDropIndex
nkBeginTxn
nkCommitTxn
nkRollbackTxn
nkExplainStmt
nkRecoverToTimestamp
nkCreateView
nkDropView
nkCreateTrigger
nkDropTrigger
nkCreateMigration
nkApplyMigration
nkMigrationStatus
nkMigrationUp
nkMigrationDown
nkMigrationDryRun
nkCreateUser
nkDropUser
nkCreatePolicy
nkDropPolicy
nkEnableRLS
nkDisableRLS
nkGrant
nkRevoke
nkSetVar
# Clauses
nkFrom
nkWhere
nkOrderBy
nkGroupBy
nkHaving
nkLimit
nkOffset
nkReturning
nkWith
# Expressions
nkBinOp
nkUnaryOp
nkJsonPath # column->'key' or column->>'key'
nkFuncCall
nkTypeCast
nkPath
nkIdent
nkIntLit
nkFloatLit
nkStringLit
nkBoolLit
nkNullLit
nkArrayLit
nkVectorLit
nkObjectLit
nkIfElse
nkCase
nkSubquery
nkExists
nkInExpr
nkBetweenExpr
nkLikeExpr
nkIsExpr
nkStar
nkPlaceholder
nkCurrentUser
nkCurrentRole
# Graph-specific
nkGraphTraversal
nkBfsQuery
nkDfsQuery
nkShortestPath
nkPatternMatch
# Vector-specific
nkVectorSimilar
nkVectorNearest
# Pivot
nkPivot
nkUnpivot
# Set operations
nkSetOp
# Join
nkJoin
# Type definitions / DDL
nkPropertyDef
nkLinkDef
nkIndexDef
nkColumnDef
nkConstraintDef
# Window functions
nkWindowExpr
nkOverClause
nkFrameSpec
nkFrameBoundary
# Top-level
nkStatementList
BinOpKind* = enum
bkAdd = "+"
bkSub = "-"
bkMul = "*"
bkDiv = "/"
bkMod = "%"
bkPow = "**"
bkFloorDiv = "//"
bkEq = "="
bkNotEq = "!="
bkLt = "<"
bkLtEq = "<="
bkGt = ">"
bkGtEq = ">="
bkAnd = "AND"
bkOr = "OR"
bkIn = "IN"
bkNotIn = "NOT IN"
bkLike = "LIKE"
bkILike = "ILIKE"
bkConcat = "++"
bkCoalesce = "??"
bkAssign = ":="
bkArrow = "=>"
bkJsonPath = "->"
bkJsonPathText = "->>"
bkFtsMatch = "@@"
bkDistance = "<->"
bkJsonContains = "@>"
bkJsonContainedBy = "<@"
bkJsonHasAny = "?|"
bkJsonHasAll = "?&"
UnaryOpKind* = enum
ukNeg = "-"
ukNot = "NOT"
ukIsNull = "IS NULL"
ukIsNotNull = "IS NOT NULL"
JoinKind* = enum
jkInner
jkLeft
jkRight
jkFull
jkCross
SetOpKind* = enum
sdkUnion
sdkIntersect
sdkExcept
GroupingSetsKind* = enum
gskNone
gskGroupingSets
gskRollup
gskCube
SortDir* = enum
sdAsc
sdDesc
Node* = ref object
line*: int
col*: int
exprAlias*: string
case kind*: NodeKind
of nkSelect:
selDistinct*: bool
selWith*: seq[(string, Node, bool)]
selResult*: seq[Node]
selFrom*: Node
selJoins*: seq[Node]
selWhere*: Node
selGroupBy*: seq[Node]
selGroupingSetsKind*: GroupingSetsKind
selGroupingSets*: seq[seq[Node]]
selHaving*: Node
selOrderBy*: seq[Node]
selLimit*: Node
selOffset*: Node
of nkInsert:
insTarget*: string
insFields*: seq[Node]
insValues*: seq[Node]
insReturning*: seq[Node]
insConflict*: Node
of nkUpdate:
updTarget*: string
updAlias*: string
updSet*: seq[Node]
updWhere*: Node
updReturning*: seq[Node]
of nkDelete:
delTarget*: string
delAlias*: string
delWhere*: Node
delReturning*: seq[Node]
of nkMerge:
mergeTarget*: string
mergeTargetAlias*: string
mergeSource*: Node
mergeSourceAlias*: string
mergeOn*: Node
mergeMatchedUpdate*: seq[Node] # SET assignments, empty if no UPDATE
mergeNotMatchedInsert*: seq[Node] # column list for INSERT
mergeNotMatchedValues*: seq[Node] # value expressions for INSERT
of nkCreateType:
ctName*: string
ctBases*: seq[string]
ctProperties*: seq[Node]
ctLinks*: seq[Node]
of nkDropType:
dtName*: string
of nkAlterType:
atName*: string
atOps*: seq[Node]
of nkCreateTable:
crtName*: string
crtColumns*: seq[Node]
crtConstraints*: seq[Node]
crtIfNotExists*: bool
of nkDropTable:
drtName*: string
drtIfExists*: bool
of nkAlterTable:
altName*: string
altOps*: seq[Node]
of nkColumnDef:
cdName*: string
cdType*: string
cdConstraints*: seq[Node]
of nkConstraintDef:
cstName*: string
cstType*: string
cstExpr*: Node
cstColumns*: seq[string]
cstRefTable*: string
cstRefColumns*: seq[string]
cstOnDelete*: string
cstOnUpdate*: string
cstCheck*: Node
cstDefault*: Node
of nkBeginTxn:
btxnMode*: string
of nkCommitTxn:
ctxnChain*: bool
of nkRollbackTxn:
rtxnChain*: bool
of nkExplainStmt:
expStmt*: Node
expAnalyze*: bool
of nkRecoverToTimestamp:
recoverTimestamp*: string
of nkCreateView:
cvName*: string
cvQuery*: Node
cvOrReplace*: bool
of nkDropView:
dvName*: string
dvIfExists*: bool
of nkCreateTrigger:
trigName*: string
trigTable*: string
trigTiming*: string # BEFORE, AFTER, INSTEAD OF
trigEvent*: string # INSERT, UPDATE, DELETE
trigAction*: Node # SQL statement to execute
of nkDropTrigger:
trigDropName*: string
trigDropIfExists*: bool
of nkCreateMigration:
cmName*: string
cmBody*: string # UP migration body (SQL string)
cmDownBody*: string # DOWN migration body (SQL string)
cmChecksum*: string # SHA256 of cmBody
cmAuthor*: string
cmTimestamp*: int64
of nkCreateUser:
cuName*: string
cuPassword*: string
cuSuperuser*: bool
of nkDropUser:
duName*: string
duIfExists*: bool
of nkCreatePolicy:
cpName*: string
cpTable*: string
cpCommand*: string # ALL, SELECT, INSERT, UPDATE, DELETE
cpUsing*: Node # USING expression
cpWithCheck*: Node # WITH CHECK expression
of nkDropPolicy:
dpName*: string
dpTable*: string
dpIfExists*: bool
of nkEnableRLS:
erlsTable*: string
of nkDisableRLS:
drlsTable*: string
of nkGrant:
grPrivilege*: string # SELECT, INSERT, UPDATE, DELETE, ALL
grTable*: string
grGrantee*: string # user, role, or PUBLIC
of nkRevoke:
rvPrivilege*: string
rvTable*: string
rvGrantee*: string
of nkSetVar:
svName*: string
svValue*: string
of nkApplyMigration:
amName*: string
of nkMigrationStatus:
discard # no fields needed
of nkMigrationUp:
muCount*: int # 0 = all, N = apply N pending migrations
of nkMigrationDown:
mdCount*: int # 0 = 1, N = rollback N migrations
of nkMigrationDryRun:
mdrName*: string # migration name to dry-run
of nkCreateIndex:
ciTarget*: string
ciName*: string
ciColumns*: seq[string]
ciExpr*: Node
ciKind*: IndexKind
of nkDropIndex:
diName*: string
of nkFrom:
fromTable*: string
fromAlias*: string
fromSubquery*: Node
of nkWhere:
whereExpr*: Node
of nkOrderBy:
orderByExpr*: Node
orderByDir*: SortDir
of nkGroupBy:
groupExprs*: seq[Node]
of nkHaving:
havingExpr*: Node
of nkLimit:
limitExpr*: Node
of nkOffset:
offsetExpr*: Node
of nkReturning:
retExprs*: seq[Node]
of nkWith:
withBindings*: seq[(string, Node, bool)]
of nkBinOp:
binOp*: BinOpKind
binLeft*: Node
binRight*: Node
of nkUnaryOp:
unOp*: UnaryOpKind
unOperand*: Node
of nkJsonPath:
jpLeft*: Node
jpKey*: string
jpAsText*: bool # true for ->>, false for ->
of nkFuncCall:
funcName*: string
funcArgs*: seq[Node]
funcFilter*: Node
of nkTypeCast:
castType*: string
castExpr*: Node
of nkPath:
pathParts*: seq[string]
of nkIdent:
identName*: string
of nkIntLit:
intVal*: int64
of nkFloatLit:
floatVal*: float64
of nkStringLit:
strVal*: string
of nkBoolLit:
boolVal*: bool
of nkNullLit:
discard
of nkArrayLit:
arrayElems*: seq[Node]
of nkVectorLit:
vecElems*: seq[Node]
of nkObjectLit:
objFields*: seq[(string, Node)]
of nkIfElse:
ifCond*: Node
ifThen*: Node
ifElse*: Node
of nkCase:
caseExpr*: Node
caseWhens*: seq[(Node, Node)]
caseElse*: Node
of nkSubquery:
subQuery*: Node
of nkExists:
existsExpr*: Node
of nkInExpr:
inLeft*: Node
inRight*: Node
of nkBetweenExpr:
betweenExpr*: Node
betweenLow*: Node
betweenHigh*: Node
of nkLikeExpr:
likeExpr*: Node
likePattern*: Node
likeCaseInsensitive*: bool
of nkIsExpr:
isExpr*: Node
isType*: string
isNegated*: bool
of nkGraphTraversal:
gtGraphName*: string
gtStart*: Node
gtEdge*: string
gtDirection*: string
gtEnd*: Node
gtMaxDepth*: int
gtReturnCols*: seq[string]
of nkBfsQuery:
bfsStart*: Node
bfsTarget*: Node
bfsEdge*: string
bfsMaxDepth*: int
bfsFilter*: Node
of nkDfsQuery:
dfsStart*: Node
dfsTarget*: Node
dfsEdge*: string
dfsMaxDepth*: int
dfsFilter*: Node
of nkShortestPath:
spStart*: Node
spEnd*: Node
spEdge*: string
spMaxDepth*: int
of nkPatternMatch:
pmPattern*: Node
pmWhere*: Node
of nkVectorSimilar:
vsField*: string
vsVector*: Node
vsLimit*: int
vsMetric*: string
of nkVectorNearest:
vnField*: string
vnVector*: Node
vnLimit*: int
vnMetric*: string
of nkPivot:
pivotSource*: Node
pivotAgg*: Node
pivotForCol*: string
pivotInValues*: seq[string]
of nkUnpivot:
unpivotSource*: Node
unpivotValueCol*: string
unpivotForCol*: string
unpivotInCols*: seq[string]
of nkJoin:
joinKind*: JoinKind
joinTarget*: Node
joinOn*: Node
joinAlias*: string
joinLateral*: bool
of nkSetOp:
setOpKind*: SetOpKind
setOpAll*: bool
setOpLeft*: Node
setOpRight*: Node
of nkStar:
discard
of nkPlaceholder:
discard
of nkCurrentUser:
discard
of nkCurrentRole:
discard
of nkPropertyDef:
pdName*: string
pdType*: string
pdRequired*: bool
pdDefault*: Node
pdComputed*: bool
pdExpr*: Node
of nkLinkDef:
ldName*: string
ldTarget*: string
ldCardinality*: Cardinality
ldRequired*: bool
of nkIndexDef:
idName*: string
idExpr*: Node
idKind*: IndexKind
of nkWindowExpr:
winFunc*: string
winArgs*: seq[Node]
winOver*: Node
of nkOverClause:
overPartition*: seq[Node]
overOrderBy*: seq[Node]
overFrame*: Node
of nkFrameSpec:
frameMode*: string # "ROWS" or "RANGE"
frameStartType*: string # "UNBOUNDED PRECEDING", "CURRENT ROW", "EXPR PRECEDING", "EXPR FOLLOWING"
frameStartExpr*: Node
frameEndType*: string
frameEndExpr*: Node
frameExclude*: string # "NO OTHERS", "CURRENT ROW", "GROUP", "TIES"
of nkFrameBoundary:
fbType*: string # "UNBOUNDED PRECEDING", "CURRENT ROW", "EXPR PRECEDING", "EXPR FOLLOWING", "UNBOUNDED FOLLOWING"
fbExpr*: Node
of nkStatementList:
stmts*: seq[Node]
proc newNode*(kind: NodeKind, line: int = 0, col: int = 0): Node =
result = Node(kind: kind, line: line, col: col)
case kind
of nkSelect: result.selResult = @[]
of nkInsert: result.insFields = @[]; result.insValues = @[]
of nkUpdate: result.updSet = @[]
of nkDelete: discard
of nkCreateTable: result.crtColumns = @[]; result.crtConstraints = @[]
of nkAlterTable: result.altOps = @[]
of nkColumnDef: result.cdConstraints = @[]
of nkConstraintDef: result.cstColumns = @[]; result.cstRefColumns = @[]
of nkWindowExpr: result.winArgs = @[]
of nkOverClause: result.overPartition = @[]; result.overOrderBy = @[]
of nkMerge:
result.mergeMatchedUpdate = @[]
result.mergeNotMatchedInsert = @[]
result.mergeNotMatchedValues = @[]
of nkStatementList: result.stmts = @[]
else: discard