apache/beam · critical

no database provided!

Error message

no database provided!

What it means

spannerio.Read panics when the database argument is an empty string. A table read always needs a fully qualified Cloud Spanner database path, and a missing one is treated as an immediate construction-time error before any query is built.

Source

Thrown at sdks/go/pkg/beam/io/spannerio/read.go:47

	"google.golang.org/api/iterator"
)

// spannerTag is the struct tag key used to identify Spanner field names.
const (
	spannerTag = "spanner"
)

func init() {
	register.DoFn3x1[context.Context, []byte, func(beam.X), error]((*queryFn)(nil))
	register.Emitter1[beam.X]()
}

// Read reads all rows from the given spanner table. It returns a PCollection<t> for a given type T.
// T must be a struct with exported fields that have the "spanner" tag. If the
// table has more rows than t, then Read is implicitly a projection.
func Read(s beam.Scope, db string, table string, t reflect.Type) beam.PCollection {
	if db == "" {
		panic("no database provided!")
	}

	cols := strings.Join(structx.InferFieldNames(t, spannerTag), ",")

	return query(s, db, fmt.Sprintf("SELECT %v from %v", cols, table), t, newQueryOptions())
}

// Query executes a spanner query. It returns a PCollection<t> for a given type T. T must be a struct with exported
// fields that have the "spanner" tag. By default, the transform uses spanners partitioned read ability to split
// the results into bundles.
// If the underlying query is not root-partitionable you can disable batching via UseBatching.
func Query(s beam.Scope, db string, q string, t reflect.Type, options ...QueryOptionFn) beam.PCollection {
	queryOptions := newQueryOptions(options...)

	if db == "" {
		panic("no database provided!")
	}

View on GitHub (pinned to 12126d8942)

Solutions

  1. Pass the full path projects/<proj>/instances/<inst>/databases/<db>.
  2. Validate db != "" before calling spannerio.Read and fail with a clear error.
  3. Check the flag/env/config source that supplies the database identifier.

Example fix

// before
spannerio.Read(s, os.Getenv("DB"), "users", reflect.TypeOf(User{})) // env unset
// after
db := os.Getenv("DB")
if db == "" {
    log.Fatal("spanner database must be set (projects/p/instances/i/databases/d)")
}
spannerio.Read(s, db, "users", reflect.TypeOf(User{}))
Defensive patterns

Strategy: validation

Validate before calling

if db == "" {
    return errors.New("spanner database path is required for spannerio.Read")
}

Try / catch

defer func() {
    if r := recover(); r != nil {
        if s, ok := r.(string); ok && s == "no database provided!" {
            // handle
        } else { panic(r) }
    }
}()

Prevention

When it happens

Trigger: Calling spannerio.Read(s, "", table, t) — typically when the db comes from a flag/env/config that was never set.

Common situations: Unset SPANNER_DATABASE env var; empty flag default; config file missing the database key; code refactor dropping the parameter.

Understand the failure class

Background: "missing required argument" and "the following required arguments were not provided": what required-argument errors mean and how to fix them — this error's family across 20 libraries.

Related errors


AI-assisted analysis of apache/beam@12126d8942 (2026-09-13). Data as JSON: /api/errors/ffdd1d2bcc3bfaeb. Report an issue: GitHub.