fix(sqlite): emit inline foreign keys, bare-name default schema, direct exec
SQLite can't ALTER TABLE ADD CONSTRAINT, so foreign keys are now written as inline FOREIGN KEY clauses in CREATE TABLE instead of commented-out ALTER statements. The default schema (public/main) now produces bare table names instead of a "public_" prefix; other schemas are still prefixed to avoid collisions. Also adds direct-to-file execution: the sqlite writer can now apply generated DDL straight to a .db file via Metadata["connection_string"], wired into `relspec merge --output-conn`.
This commit is contained in:
@@ -40,10 +40,22 @@ func NewTemplateExecutor(opts *writers.WriterOptions) (*TemplateExecutor, error)
|
||||
|
||||
// TableTemplateData contains data for table template
|
||||
type TableTemplateData struct {
|
||||
Schema string
|
||||
Name string
|
||||
Columns []*models.Column
|
||||
PrimaryKey *models.Constraint
|
||||
Schema string
|
||||
Name string
|
||||
Columns []*models.Column
|
||||
PrimaryKey *models.Constraint
|
||||
ForeignKeys []ForeignKeyTemplateData
|
||||
}
|
||||
|
||||
// ForeignKeyTemplateData contains data for an inline FOREIGN KEY clause
|
||||
type ForeignKeyTemplateData struct {
|
||||
Name string
|
||||
Columns []string
|
||||
ForeignSchema string
|
||||
ForeignTable string
|
||||
ForeignColumns []string
|
||||
OnDelete string
|
||||
OnUpdate string
|
||||
}
|
||||
|
||||
// IndexTemplateData contains data for index template
|
||||
@@ -120,16 +132,6 @@ func (te *TemplateExecutor) ExecuteCreateCheckConstraint(data ConstraintTemplate
|
||||
return buf.String(), nil
|
||||
}
|
||||
|
||||
// ExecuteCreateForeignKey executes the create foreign key template
|
||||
func (te *TemplateExecutor) ExecuteCreateForeignKey(data ConstraintTemplateData) (string, error) {
|
||||
var buf bytes.Buffer
|
||||
err := te.templates.ExecuteTemplate(&buf, "create_foreign_key.tmpl", data)
|
||||
if err != nil {
|
||||
return "", fmt.Errorf("failed to execute create_foreign_key template: %w", err)
|
||||
}
|
||||
return buf.String(), nil
|
||||
}
|
||||
|
||||
// Helper functions to build template data from models
|
||||
|
||||
// BuildTableTemplateData builds TableTemplateData from a models.Table
|
||||
@@ -162,11 +164,35 @@ func BuildTableTemplateData(schema string, table *models.Table) TableTemplateDat
|
||||
}
|
||||
}
|
||||
|
||||
// Collect foreign keys for inline FOREIGN KEY clauses
|
||||
var fks []ForeignKeyTemplateData
|
||||
for _, constraint := range sortConstraints(table.Constraints) {
|
||||
if constraint.Type != models.ForeignKeyConstraint {
|
||||
continue
|
||||
}
|
||||
|
||||
refSchema := tableSchemaName(constraint.ReferencedSchema)
|
||||
if refSchema == "" {
|
||||
refSchema = schema
|
||||
}
|
||||
|
||||
fks = append(fks, ForeignKeyTemplateData{
|
||||
Name: constraint.Name,
|
||||
Columns: constraint.Columns,
|
||||
ForeignSchema: refSchema,
|
||||
ForeignTable: constraint.ReferencedTable,
|
||||
ForeignColumns: constraint.ReferencedColumns,
|
||||
OnDelete: constraint.OnDelete,
|
||||
OnUpdate: constraint.OnUpdate,
|
||||
})
|
||||
}
|
||||
|
||||
return TableTemplateData{
|
||||
Schema: schema,
|
||||
Name: table.Name,
|
||||
Columns: columns,
|
||||
PrimaryKey: pk,
|
||||
Schema: schema,
|
||||
Name: table.Name,
|
||||
Columns: columns,
|
||||
PrimaryKey: pk,
|
||||
ForeignKeys: fks,
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user