{"record":{"id":"7c488311e3f4f585","repo":"micro/go-micro","slug":"model-postgres-create-table-w","errorCode":null,"errorMessage":"model/postgres: create table: %w","messagePattern":"model/postgres: create table: %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"model/postgres/postgres.go","lineNumber":64,"sourceCode":"\n\td.mu.Lock()\n\td.schemas[schema.Table] = schema\n\td.types[t] = schema\n\td.mu.Unlock()\n\n\tvar cols []string\n\tfor _, f := range schema.Fields {\n\t\tcolType := goTypeToPostgres(f.Type)\n\t\tcol := fmt.Sprintf(\"%s %s\", quoteIdent(f.Column), colType)\n\t\tif f.IsKey {\n\t\t\tcol += \" PRIMARY KEY\"\n\t\t}\n\t\tcols = append(cols, col)\n\t}\n\n\tquery := fmt.Sprintf(\"CREATE TABLE IF NOT EXISTS %s (%s)\", quoteIdent(schema.Table), strings.Join(cols, \", \"))\n\tif _, err := d.db.Exec(query); err != nil {\n\t\treturn fmt.Errorf(\"model/postgres: create table: %w\", err)\n\t}\n\n\tfor _, f := range schema.Fields {\n\t\tif f.Index && !f.IsKey {\n\t\t\tidx := fmt.Sprintf(\"CREATE INDEX IF NOT EXISTS %s ON %s (%s)\",\n\t\t\t\tquoteIdent(\"idx_\"+schema.Table+\"_\"+f.Column),\n\t\t\t\tquoteIdent(schema.Table),\n\t\t\t\tquoteIdent(f.Column))\n\t\t\tif _, err := d.db.Exec(idx); err != nil {\n\t\t\t\treturn fmt.Errorf(\"model/postgres: create index: %w\", err)\n\t\t\t}\n\t\t}\n\t}\n\n\treturn nil\n}\n\nfunc (d *postgresModel) schema(v interface{}) (*model.Schema, error) {","sourceCodeStart":46,"sourceCodeEnd":82,"githubUrl":"https://github.com/micro/go-micro/blob/24529f140421a11a33b6999ab7944f2021cfd69c/model/postgres/postgres.go#L46-L82","documentation":"Register ensures the schema's table exists by running CREATE TABLE IF NOT EXISTS with columns derived from schema.Fields. If the database rejects that DDL statement, the error is wrapped as \"model/postgres: create table\" preserving the underlying pq/pgx error.","triggerScenarios":"Calling postgresModel.Register (or New/postgres model setup that auto-registers) when the CREATE TABLE fails: invalid table/column names, reserved SQL keywords used unquoted, insufficient privileges, or the database being unreachable.","commonSituations":"App user lacking CREATE privilege on the schema, table name colliding with reserved words, read-only replicas or restricted production credentials, or connecting to a database where another system owns the migration.","solutions":["Read the wrapped cause (%w) for the real Postgres error — it names the exact problem (permission, syntax, connection).","Grant the connecting role CREATE privilege on the schema, or run DDL with a migration user.","Fix table/column identifiers in the model schema; quote reserved words (the driver's quoteIdent usually handles this).","Verify connectivity (DSN, network, DB up) with psql before starting the app.","Prefer an external migration tool and make Register tolerant if the table is managed elsewhere."],"exampleFix":"// before\ndb, _ := NewPostgresModel(dburl) // auto Register fails on readonly role\n\n// after\n-- grant once as superuser\nGRANT CREATE ON SCHEMA public TO app_user;\n// then\nif err := store.Register(ctx, &User{}); err != nil {\n    log.Fatalf(\"schema setup failed: %v\", err)\n}","handlingStrategy":"try-catch","validationCode":"// before Register: check privileges and connectivity\nvar hasCreate bool\nif err := db.QueryRow(\n    \"SELECT has_schema_privilege(current_user, 'public', 'CREATE')\",\n).Scan(&hasCreate); err != nil {\n    return err\n}\nif !hasCreate {\n    return errors.New(\"db role lacks CREATE privilege on schema public\")\n}","typeGuard":null,"tryCatchPattern":"if err := store.Register(ctx, &User{}); err != nil {\n    var pgErr *pgconn.PgError\n    if errors.As(err, &pgErr) {\n        log.Printf(\"create table failed [%s]: %s\", pgErr.Code, pgErr.Message)\n    }\n    return fmt.Errorf(\"schema bootstrap: %w\", err)\n}","preventionTips":["Run migrations with a role that has CREATE privilege; use a restricted role at runtime.","Ping the database and verify DSN before starting schema bootstrap.","Keep table/column identifiers lowercase snake_case to avoid quoting/reserved-word issues.","Manage DDL with a migration tool and keep the model schema in sync with it."],"tags":["postgres","database","ddl","schema"],"backgroundTag":"database-migration-failed","analyzedSha":"24529f140421a11a33b6999ab7944f2021cfd69c","analyzedAt":"2026-09-01T02:52:24.923Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-08T05:18:18.240Z"}