gofr-dev/gofr · error

%w: %s: %w

Error message

%w: %s: %w

What it means

This wrapped error is produced by surrealMigrator.checkAndCreateMigrationTable when one of the queries that creates the SurrealDB migration table fails. The format `%w: %s: %w` embeds the sentinel errExecuteQuery, the exact failing query text, and the underlying driver error, so the full message reads like 'failed to execute migration query: <query>: <driver error>'. It means the migration table could not be created and migrations cannot proceed.

Source

Thrown at pkg/gofr/migration/surreal_db.go:73

)

func getMigrationTableQueries() []string {
	return []string{
		"DEFINE TABLE IF NOT EXISTS gofr_migrations SCHEMAFULL;",
		"DEFINE FIELD IF NOT EXISTS id ON gofr_migrations TYPE string;",
		"DEFINE FIELD IF NOT EXISTS version ON gofr_migrations TYPE number;",
		"DEFINE FIELD IF NOT EXISTS method ON gofr_migrations TYPE string;",
		"DEFINE FIELD IF NOT EXISTS start_time ON gofr_migrations TYPE datetime;",
		"DEFINE FIELD IF NOT EXISTS duration ON gofr_migrations TYPE number;",
		"DEFINE INDEX IF NOT EXISTS version_method ON gofr_migrations COLUMNS version, method UNIQUE;",
	}
}

func (s surrealMigrator) checkAndCreateMigrationTable(c *container.Container) error {
	// Create migration table directly
	for _, q := range getMigrationTableQueries() {
		if _, err := s.SurrealDB.Query(context.Background(), q, nil); err != nil {
			return fmt.Errorf("%w: %s: %w", errExecuteQuery, q, err)
		}
	}

	return s.migrator.checkAndCreateMigrationTable(c)
}

// surrealVersionToInt64 converts the `version` field returned by SurrealDB into an int64.
// The SurrealDB driver decodes a `number` column into different Go types depending on the
// stored value and driver version (e.g. int or int64 or uint64 or float64 over CBOR
// responses), so we handle each numeric type explicitly. Unknown/absent values default to 0.
func surrealVersionToInt64(v any) int64 {
	switch n := v.(type) {
	case int64:
		return n
	case int:
		return int64(n)
	case uint64:
		if n > math.MaxInt64 {

View on GitHub (pinned to 187eb24962)

Solutions

  1. Read the innermost wrapped error in the message chain — it names the actual SurrealDB failure (auth, permission, syntax).
  2. Run the failing query (printed in the error) manually in a SurrealDB shell to reproduce and debug.
  3. Grant the configured SurrealDB user permission to create tables in the target namespace/database.
  4. Confirm SurrealDB server version compatibility with the GoFr driver queries.

Example fix

// before: user without define-table permission
DEFINE USER app PASSWORD '...' ROLES EDITOR;
// after: grant permissions allowing table creation
DEFINE USER app PASSWORD '...' ROLES OWNER;
Defensive patterns

Strategy: try-catch

Validate before calling

// validate permissions by attempting a harmless query first
if _, err := db.Query(ctx, "RETURN 1", nil); err != nil {
	return fmt.Errorf("surrealdb not ready: %w", err)
}

Type guard

func isSetupErr(err error) bool {
	return errors.Is(err, errExecuteQuery)
}

Try / catch

err := migrator.checkAndCreateMigrationTable(c)
if err != nil {
	// message chain: sentinel : query : driver error — parse innermost first
	log.Printf("setup failed: %v", err)
	return err
}

Prevention

When it happens

Trigger: Running GoFr migrations with a SurrealDB datasource where s.SurrealDB.Query(context.Background(), q, nil) errors for any query in getMigrationTableQueries() — bad connection, insufficient permissions, unsupported syntax.

Common situations: SurrealDB user lacks permission to define tables; SurrealDB running an older version that rejects the query syntax; endpoint misconfigured so connection drops mid-query.

Related errors


AI-assisted analysis of gofr-dev/gofr@187eb24962 (2026-09-01). Data as JSON: /api/errors/80c407145d41af1e. Report an issue: GitHub.