Skip to content

Commit 9434270

Browse files
authored
Merge pull request #2847 from dolthub/daylon/context-accepts-db
Context collections accept a database
2 parents 6ae7b7d + 2937c29 commit 9434270

39 files changed

Lines changed: 147 additions & 117 deletions

core/context.go

Lines changed: 91 additions & 66 deletions
Original file line numberDiff line numberDiff line change
@@ -38,14 +38,13 @@ import (
3838
// and may be refreshed at any point, including during the middle of a query. Callers should not assume that
3939
// data stored in contextValues is persisted, and other types of data should not be added to contextValues.
4040
type contextValues struct {
41-
seqs map[string]*sequences.Collection
42-
// TODO: all these collection fields need to be mapped by database name as seqs above
43-
types *typecollection.TypeCollection
44-
funcs *functions.Collection
45-
procs *procedures.Collection
46-
trigs *triggers.Collection
47-
exts *extensions.Collection
48-
casts *casts.Collection
41+
seqs map[string]*sequences.Collection
42+
types map[string]*typecollection.TypeCollection
43+
funcs map[string]*functions.Collection
44+
procs map[string]*procedures.Collection
45+
trigs map[string]*triggers.Collection
46+
exts map[string]*extensions.Collection
47+
casts map[string]*casts.Collection
4948

5049
pgCatalogCache any
5150
runner sql.StatementRunner
@@ -292,72 +291,75 @@ func GetExtensionsCollectionFromContext(ctx *sql.Context, database string) (*ext
292291
if err != nil {
293292
return nil, err
294293
}
295-
_, root, err := getRootFromContextForDatabase(ctx, database)
296-
if err != nil {
297-
return nil, err
298-
}
299294
if cv.exts == nil {
300-
cv.exts, err = extensions.LoadExtensions(ctx, root)
295+
cv.exts = make(map[string]*extensions.Collection)
296+
}
297+
if len(database) == 0 {
298+
database = ctx.GetCurrentDatabase()
299+
}
300+
if cv.exts[database] == nil {
301+
_, root, err := getRootFromContextForDatabase(ctx, database)
301302
if err != nil {
302303
return nil, err
303304
}
304-
} else if cv.exts.DiffersFrom(ctx, root) {
305-
cv.exts, err = extensions.LoadExtensions(ctx, root)
305+
cv.exts[database], err = extensions.LoadExtensions(ctx, root)
306306
if err != nil {
307307
return nil, err
308308
}
309309
}
310-
return cv.exts, nil
310+
return cv.exts[database], nil
311311
}
312312

313313
// GetFunctionsCollectionFromContext returns the functions collection from the given context. Will always return a
314314
// collection if no error is returned.
315-
func GetFunctionsCollectionFromContext(ctx *sql.Context) (*functions.Collection, error) {
315+
func GetFunctionsCollectionFromContext(ctx *sql.Context, database string) (*functions.Collection, error) {
316316
cv, err := getContextValues(ctx)
317317
if err != nil {
318318
return nil, err
319319
}
320-
_, root, err := GetRootFromContext(ctx)
321-
if err != nil {
322-
return nil, err
323-
}
324320
if cv.funcs == nil {
325-
cv.funcs, err = functions.LoadFunctions(ctx, root)
321+
cv.funcs = make(map[string]*functions.Collection)
322+
}
323+
if len(database) == 0 {
324+
database = ctx.GetCurrentDatabase()
325+
}
326+
if cv.funcs[database] == nil {
327+
_, root, err := getRootFromContextForDatabase(ctx, database)
326328
if err != nil {
327329
return nil, err
328330
}
329-
} else if cv.funcs.DiffersFrom(ctx, root) {
330-
cv.funcs, err = functions.LoadFunctions(ctx, root)
331+
cv.funcs[database], err = functions.LoadFunctions(ctx, root)
331332
if err != nil {
332333
return nil, err
333334
}
334335
}
335-
return cv.funcs, nil
336+
return cv.funcs[database], nil
336337
}
337338

338339
// GetProceduresCollectionFromContext returns the procedures collection from the given context. Will always return a
339340
// collection if no error is returned.
340-
func GetProceduresCollectionFromContext(ctx *sql.Context) (*procedures.Collection, error) {
341+
func GetProceduresCollectionFromContext(ctx *sql.Context, database string) (*procedures.Collection, error) {
341342
cv, err := getContextValues(ctx)
342343
if err != nil {
343344
return nil, err
344345
}
345-
_, root, err := GetRootFromContext(ctx)
346-
if err != nil {
347-
return nil, err
348-
}
349346
if cv.procs == nil {
350-
cv.procs, err = procedures.LoadProcedures(ctx, root)
347+
cv.procs = make(map[string]*procedures.Collection)
348+
}
349+
if len(database) == 0 {
350+
database = ctx.GetCurrentDatabase()
351+
}
352+
if cv.procs[database] == nil {
353+
_, root, err := getRootFromContextForDatabase(ctx, database)
351354
if err != nil {
352355
return nil, err
353356
}
354-
} else if cv.procs.DiffersFrom(ctx, root) {
355-
cv.procs, err = procedures.LoadProcedures(ctx, root)
357+
cv.procs[database], err = procedures.LoadProcedures(ctx, root)
356358
if err != nil {
357359
return nil, err
358360
}
359361
}
360-
return cv.procs, nil
362+
return cv.procs[database], nil
361363
}
362364

363365
// GetSequencesCollectionFromContext returns the given sequence collection from the context for the database
@@ -371,6 +373,9 @@ func GetSequencesCollectionFromContext(ctx *sql.Context, database string) (*sequ
371373
if cv.seqs == nil {
372374
cv.seqs = make(map[string]*sequences.Collection)
373375
}
376+
if len(database) == 0 {
377+
database = ctx.GetCurrentDatabase()
378+
}
374379
if cv.seqs[database] == nil {
375380
_, root, err := getRootFromContextForDatabase(ctx, database)
376381
if err != nil {
@@ -391,62 +396,75 @@ func GetTriggersCollectionFromContext(ctx *sql.Context, database string) (*trigg
391396
if err != nil {
392397
return nil, err
393398
}
394-
_, root, err := getRootFromContextForDatabase(ctx, database)
395-
if err != nil {
396-
return nil, err
397-
}
398399
if cv.trigs == nil {
399-
cv.trigs, err = triggers.LoadTriggers(ctx, root)
400+
cv.trigs = make(map[string]*triggers.Collection)
401+
}
402+
if len(database) == 0 {
403+
database = ctx.GetCurrentDatabase()
404+
}
405+
if cv.trigs[database] == nil {
406+
_, root, err := getRootFromContextForDatabase(ctx, database)
400407
if err != nil {
401408
return nil, err
402409
}
403-
} else if cv.trigs.DiffersFrom(ctx, root) {
404-
cv.trigs, err = triggers.LoadTriggers(ctx, root)
410+
cv.trigs[database], err = triggers.LoadTriggers(ctx, root)
405411
if err != nil {
406412
return nil, err
407413
}
408414
}
409-
return cv.trigs, nil
415+
return cv.trigs[database], nil
410416
}
411417

412418
// GetTypesCollectionFromContext returns the given type collection from the context.
413419
// Will always return a collection if no error is returned.
414-
func GetTypesCollectionFromContext(ctx *sql.Context) (*typecollection.TypeCollection, error) {
420+
func GetTypesCollectionFromContext(ctx *sql.Context, database string) (*typecollection.TypeCollection, error) {
415421
cv, err := getContextValues(ctx)
416422
if err != nil {
417423
return nil, err
418424
}
419425
if cv.types == nil {
420-
_, root, err := GetRootFromContext(ctx)
426+
cv.types = make(map[string]*typecollection.TypeCollection)
427+
}
428+
if len(database) == 0 {
429+
database = ctx.GetCurrentDatabase()
430+
}
431+
if cv.types[database] == nil {
432+
_, root, err := getRootFromContextForDatabase(ctx, database)
421433
if err != nil {
422434
return nil, err
423435
}
424-
cv.types, err = typecollection.LoadTypes(ctx, root)
436+
cv.types[database], err = typecollection.LoadTypes(ctx, root)
425437
if err != nil {
426438
return nil, err
427439
}
428440
}
429-
return cv.types, nil
441+
return cv.types[database], nil
430442
}
431443

432444
// GetCastsCollectionFromContext returns the given casts collection from the context.
433445
// Will always return a collection if no error is returned.
434-
func GetCastsCollectionFromContext(ctx *sql.Context) (*casts.Collection, error) {
446+
func GetCastsCollectionFromContext(ctx *sql.Context, database string) (*casts.Collection, error) {
435447
cv, err := getContextValues(ctx)
436448
if err != nil {
437449
return nil, err
438450
}
439451
if cv.casts == nil {
440-
_, root, err := GetRootFromContext(ctx)
452+
cv.casts = make(map[string]*casts.Collection)
453+
}
454+
if len(database) == 0 {
455+
database = ctx.GetCurrentDatabase()
456+
}
457+
if cv.casts[database] == nil {
458+
_, root, err := getRootFromContextForDatabase(ctx, database)
441459
if err != nil {
442460
return nil, err
443461
}
444-
cv.casts, err = casts.LoadCasts(ctx, root)
462+
cv.casts[database], err = casts.LoadCasts(ctx, root)
445463
if err != nil {
446464
return nil, err
447465
}
448466
}
449-
return cv.casts, nil
467+
return cv.casts[database], nil
450468
}
451469

452470
// CloseContextRootFinalizer finalizes any changes persisted within the context by writing them to the working root.
@@ -490,52 +508,59 @@ func updateSessionRootForDatabase(ctx *sql.Context, db string, cv *contextValues
490508
delete(cv.seqs, db)
491509
}
492510

493-
if cv.funcs != nil && cv.funcs.DiffersFrom(ctx, root) {
494-
retRoot, err := cv.funcs.UpdateRoot(ctx, newRoot)
511+
if cv.funcs != nil && cv.funcs[db] != nil && cv.funcs[db].DiffersFrom(ctx, root) {
512+
retRoot, err := cv.funcs[db].UpdateRoot(ctx, newRoot)
495513
if err != nil {
496514
return err
497515
}
498516
newRoot = retRoot.(*RootValue)
499-
cv.funcs = nil
517+
delete(cv.funcs, db)
500518
}
501519

502-
if cv.procs != nil && cv.procs.DiffersFrom(ctx, root) {
503-
retRoot, err := cv.procs.UpdateRoot(ctx, newRoot)
520+
if cv.procs != nil && cv.procs[db] != nil && cv.procs[db].DiffersFrom(ctx, root) {
521+
retRoot, err := cv.procs[db].UpdateRoot(ctx, newRoot)
504522
if err != nil {
505523
return err
506524
}
507525
newRoot = retRoot.(*RootValue)
508-
cv.procs = nil
526+
delete(cv.procs, db)
509527
}
510528

511-
if cv.trigs != nil && cv.trigs.DiffersFrom(ctx, root) {
512-
retRoot, err := cv.trigs.UpdateRoot(ctx, newRoot)
529+
if cv.trigs != nil && cv.trigs[db] != nil && cv.trigs[db].DiffersFrom(ctx, root) {
530+
retRoot, err := cv.trigs[db].UpdateRoot(ctx, newRoot)
513531
if err != nil {
514532
return err
515533
}
516534
newRoot = retRoot.(*RootValue)
517-
cv.trigs = nil
535+
delete(cv.trigs, db)
518536
}
519537

520-
if cv.exts != nil && cv.exts.DiffersFrom(ctx, root) {
521-
retRoot, err := cv.exts.UpdateRoot(ctx, newRoot)
538+
if cv.exts != nil && cv.exts[db] != nil && cv.exts[db].DiffersFrom(ctx, root) {
539+
retRoot, err := cv.exts[db].UpdateRoot(ctx, newRoot)
522540
if err != nil {
523541
return err
524542
}
525543
newRoot = retRoot.(*RootValue)
526-
cv.exts = nil
544+
delete(cv.exts, db)
527545
}
528546

529-
if cv.types != nil {
530-
retRoot, err := cv.types.UpdateRoot(ctx, newRoot)
547+
if cv.types != nil && cv.types[db] != nil {
548+
retRoot, err := cv.types[db].UpdateRoot(ctx, newRoot)
531549
if err != nil {
532550
return err
533551
}
534552
newRoot = retRoot.(*RootValue)
535-
cv.types = nil
553+
delete(cv.types, db)
536554
}
537555

538-
// TODO: need to be able to persist cv.casts without an empty collection updating the root (no value != empty value)
556+
if cv.casts != nil && cv.casts[db] != nil && cv.casts[db].DiffersFrom(ctx, root) {
557+
retRoot, err := cv.casts[db].UpdateRoot(ctx, newRoot)
558+
if err != nil {
559+
return err
560+
}
561+
newRoot = retRoot.(*RootValue)
562+
delete(cv.casts, db)
563+
}
539564

540565
// Setting the session working root doesn't do a check to see if anything actually changed or not before marking that
541566
// branch state dirty, and dolt only allows a single dirty working set per commit. So it's important here to only

core/init.go

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -37,11 +37,11 @@ func Init() {
3737
id.RegisterListener(sequenceIDListener{}, id.Section_Table)
3838
typecollection.GetSqlTableFromContext = GetSqlTableFromContext
3939
typecollection.GetSchemaName = GetSchemaName
40-
pgtypes.GetTypesCollectionFromContext = func(ctx *sql.Context) (pgtypes.TypeCollection, error) {
41-
return GetTypesCollectionFromContext(ctx)
40+
pgtypes.GetTypesCollectionFromContext = func(ctx *sql.Context, database string) (pgtypes.TypeCollection, error) {
41+
return GetTypesCollectionFromContext(ctx, database)
4242
}
4343
pgtypes.GetAssignmentCast = func(ctx *sql.Context, sourceType *pgtypes.DoltgresType, targetType *pgtypes.DoltgresType) (pgtypes.Cast, error) {
44-
castsColl, err := GetCastsCollectionFromContext(ctx)
44+
castsColl, err := GetCastsCollectionFromContext(ctx, "")
4545
if err != nil {
4646
return nil, err
4747
}

server/analyzer/foreign_key.go

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,8 @@ func validateForeignKeyDefinition(ctx *sql.Context, fkDef sql.ForeignKeyConstrai
3232
var castsColl *casts.Collection
3333
if len(fkDef.Columns) > 0 {
3434
var err error
35-
castsColl, err = core.GetCastsCollectionFromContext(ctx)
35+
// TODO: which database is this supposed to use?
36+
castsColl, err = core.GetCastsCollectionFromContext(ctx, "")
3637
if err != nil {
3738
return err
3839
}

server/analyzer/resolve_routine_defaults.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -36,11 +36,11 @@ import (
3636
func ResolveProcedureDefaults(ctx *sql.Context, a *analyzer.Analyzer, node sql.Node, scope *plan.Scope, selector analyzer.RuleSelector, qFlags *sql.QueryFlags) (sql.Node, transform.TreeIdentity, error) {
3737
switch n := node.(type) {
3838
case *pgnodes.Call:
39-
procCollection, err := core.GetProceduresCollectionFromContext(ctx)
39+
procCollection, err := core.GetProceduresCollectionFromContext(ctx, "")
4040
if err != nil {
4141
return nil, transform.SameTree, err
4242
}
43-
typesCollection, err := core.GetTypesCollectionFromContext(ctx)
43+
typesCollection, err := core.GetTypesCollectionFromContext(ctx, "")
4444
if err != nil {
4545
return nil, transform.SameTree, err
4646
}

server/analyzer/resolve_type.go

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -259,7 +259,11 @@ func resolveType(ctx *sql.Context, db sql.Database, typ *pgtypes.DoltgresType) (
259259
if typ.IsResolvedType() {
260260
return typ, nil
261261
}
262-
typs, err := core.GetTypesCollectionFromContext(ctx)
262+
var dbname string
263+
if db != nil {
264+
dbname = db.Name()
265+
}
266+
typs, err := core.GetTypesCollectionFromContext(ctx, dbname)
263267
if err != nil {
264268
return nil, err
265269
}

server/doltgres_handler.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -304,7 +304,7 @@ func (h *DoltgresHandler) convertBindParameters(ctx *sql.Context, types []uint32
304304
if err != nil {
305305
return nil, err
306306
}
307-
typeColl, err := core.GetTypesCollectionFromContext(ctx)
307+
typeColl, err := core.GetTypesCollectionFromContext(ctx, "")
308308
if err != nil {
309309
return nil, err
310310
}

server/expression/array.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -66,7 +66,7 @@ func (array *Array) Children() []sql.Expression {
6666
func (array *Array) Eval(ctx *sql.Context, row sql.Row) (any, error) {
6767
resultTyp := array.coercedType.ArrayBaseType()
6868
values := make([]any, len(array.children))
69-
castsColl, err := core.GetCastsCollectionFromContext(ctx)
69+
castsColl, err := core.GetCastsCollectionFromContext(ctx, "")
7070
if err != nil {
7171
return nil, err
7272
}
@@ -192,7 +192,7 @@ func (array *Array) getTargetType(ctx *sql.Context, children ...sql.Expression)
192192
if schemaName == "" {
193193
schemaName, _ = core.GetCurrentSchema(ctx)
194194
}
195-
if typeColl, tcErr := core.GetTypesCollectionFromContext(ctx); tcErr == nil && typeColl != nil {
195+
if typeColl, tcErr := core.GetTypesCollectionFromContext(ctx, ""); tcErr == nil && typeColl != nil {
196196
if resolved, rErr := typeColl.GetType(ctx, id.NewType(schemaName, targetType.ID.TypeName())); rErr == nil && resolved != nil {
197197
targetType = resolved
198198
}

server/expression/assignment_cast.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,7 @@ func (ac *AssignmentCast) Eval(ctx *sql.Context, row sql.Row) (any, error) {
5353
if err != nil || val == nil {
5454
return val, err
5555
}
56-
castsColl, err := core.GetCastsCollectionFromContext(ctx)
56+
castsColl, err := core.GetCastsCollectionFromContext(ctx, "")
5757
if err != nil {
5858
return nil, err
5959
}

server/expression/column_access.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -141,7 +141,7 @@ func (expr *ColumnAccess) WithChildren(ctx *sql.Context, children ...sql.Express
141141
return nil, errors.New("column access is only valid for Doltgres types")
142142
}
143143
if !doltgresType.IsResolvedType() {
144-
typeColl, err := core.GetTypesCollectionFromContext(ctx)
144+
typeColl, err := core.GetTypesCollectionFromContext(ctx, "")
145145
if err != nil {
146146
return nil, err
147147
}

0 commit comments

Comments
 (0)