From dee11a626cb8e7ff045ac9413dcd8a92e72f5863 Mon Sep 17 00:00:00 2001
From: jeffjiang <guokeno0@gmail.com>
Date: Tue, 14 Feb 2017 09:06:13 -0800
Subject: [PATCH] spanner: add generated code (#19)

---
 .../database/v1/spanner_database_admin.pb.go  |  920 ++++++++++++
 .../instance/v1/spanner_instance_admin.pb.go  | 1281 +++++++++++++++++
 googleapis/spanner/v1/keys.pb.go              |  438 ++++++
 googleapis/spanner/v1/mutation.pb.go          |  346 +++++
 googleapis/spanner/v1/query_plan.pb.go        |  285 ++++
 googleapis/spanner/v1/result_set.pb.go        |  310 ++++
 googleapis/spanner/v1/spanner.pb.go           | 1217 ++++++++++++++++
 googleapis/spanner/v1/transaction.pb.go       |  830 +++++++++++
 googleapis/spanner/v1/type.pb.go              |  216 +++
 9 files changed, 5843 insertions(+)
 create mode 100644 googleapis/spanner/admin/database/v1/spanner_database_admin.pb.go
 create mode 100644 googleapis/spanner/admin/instance/v1/spanner_instance_admin.pb.go
 create mode 100644 googleapis/spanner/v1/keys.pb.go
 create mode 100644 googleapis/spanner/v1/mutation.pb.go
 create mode 100644 googleapis/spanner/v1/query_plan.pb.go
 create mode 100644 googleapis/spanner/v1/result_set.pb.go
 create mode 100644 googleapis/spanner/v1/spanner.pb.go
 create mode 100644 googleapis/spanner/v1/transaction.pb.go
 create mode 100644 googleapis/spanner/v1/type.pb.go

diff --git a/googleapis/spanner/admin/database/v1/spanner_database_admin.pb.go b/googleapis/spanner/admin/database/v1/spanner_database_admin.pb.go
new file mode 100644
index 00000000..8112d788
--- /dev/null
+++ b/googleapis/spanner/admin/database/v1/spanner_database_admin.pb.go
@@ -0,0 +1,920 @@
+// Code generated by protoc-gen-go.
+// source: google/spanner/admin/database/v1/spanner_database_admin.proto
+// DO NOT EDIT!
+
+/*
+Package database is a generated protocol buffer package.
+
+It is generated from these files:
+	google/spanner/admin/database/v1/spanner_database_admin.proto
+
+It has these top-level messages:
+	Database
+	ListDatabasesRequest
+	ListDatabasesResponse
+	CreateDatabaseRequest
+	CreateDatabaseMetadata
+	GetDatabaseRequest
+	UpdateDatabaseDdlRequest
+	UpdateDatabaseDdlMetadata
+	DropDatabaseRequest
+	GetDatabaseDdlRequest
+	GetDatabaseDdlResponse
+*/
+package database
+
+import proto "github.com/golang/protobuf/proto"
+import fmt "fmt"
+import math "math"
+import _ "google.golang.org/genproto/googleapis/api/annotations"
+import _ "google.golang.org/genproto/googleapis/api/serviceconfig"
+import google_iam_v11 "google.golang.org/genproto/googleapis/iam/v1"
+import google_iam_v1 "google.golang.org/genproto/googleapis/iam/v1"
+import google_longrunning "google.golang.org/genproto/googleapis/longrunning"
+import google_protobuf2 "github.com/golang/protobuf/ptypes/empty"
+import google_protobuf3 "github.com/golang/protobuf/ptypes/timestamp"
+
+import (
+	context "golang.org/x/net/context"
+	grpc "google.golang.org/grpc"
+)
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ = proto.Marshal
+var _ = fmt.Errorf
+var _ = math.Inf
+
+// This is a compile-time assertion to ensure that this generated file
+// is compatible with the proto package it is being compiled against.
+// A compilation error at this line likely means your copy of the
+// proto package needs to be updated.
+const _ = proto.ProtoPackageIsVersion2 // please upgrade the proto package
+
+// Indicates the current state of the database.
+type Database_State int32
+
+const (
+	// Not specified.
+	Database_STATE_UNSPECIFIED Database_State = 0
+	// The database is still being created. Operations on the database may fail
+	// with `FAILED_PRECONDITION` in this state.
+	Database_CREATING Database_State = 1
+	// The database is fully created and ready for use.
+	Database_READY Database_State = 2
+)
+
+var Database_State_name = map[int32]string{
+	0: "STATE_UNSPECIFIED",
+	1: "CREATING",
+	2: "READY",
+}
+var Database_State_value = map[string]int32{
+	"STATE_UNSPECIFIED": 0,
+	"CREATING":          1,
+	"READY":             2,
+}
+
+func (x Database_State) String() string {
+	return proto.EnumName(Database_State_name, int32(x))
+}
+func (Database_State) EnumDescriptor() ([]byte, []int) { return fileDescriptor0, []int{0, 0} }
+
+// A Cloud Spanner database.
+type Database struct {
+	// Required. The name of the database. Values are of the form
+	// `projects/<project>/instances/<instance>/databases/<database>`,
+	// where `<database>` is as specified in the `CREATE DATABASE`
+	// statement. This name can be passed to other API methods to
+	// identify the database.
+	Name string `protobuf:"bytes,1,opt,name=name" json:"name,omitempty"`
+	// Output only. The current database state.
+	State Database_State `protobuf:"varint,2,opt,name=state,enum=google.spanner.admin.database.v1.Database_State" json:"state,omitempty"`
+}
+
+func (m *Database) Reset()                    { *m = Database{} }
+func (m *Database) String() string            { return proto.CompactTextString(m) }
+func (*Database) ProtoMessage()               {}
+func (*Database) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{0} }
+
+func (m *Database) GetName() string {
+	if m != nil {
+		return m.Name
+	}
+	return ""
+}
+
+func (m *Database) GetState() Database_State {
+	if m != nil {
+		return m.State
+	}
+	return Database_STATE_UNSPECIFIED
+}
+
+// The request for [ListDatabases][google.spanner.admin.database.v1.DatabaseAdmin.ListDatabases].
+type ListDatabasesRequest struct {
+	// Required. The instance whose databases should be listed.
+	// Values are of the form `projects/<project>/instances/<instance>`.
+	Parent string `protobuf:"bytes,1,opt,name=parent" json:"parent,omitempty"`
+	// Number of databases to be returned in the response. If 0 or less,
+	// defaults to the server's maximum allowed page size.
+	PageSize int32 `protobuf:"varint,3,opt,name=page_size,json=pageSize" json:"page_size,omitempty"`
+	// If non-empty, `page_token` should contain a
+	// [next_page_token][google.spanner.admin.database.v1.ListDatabasesResponse.next_page_token] from a
+	// previous [ListDatabasesResponse][google.spanner.admin.database.v1.ListDatabasesResponse].
+	PageToken string `protobuf:"bytes,4,opt,name=page_token,json=pageToken" json:"page_token,omitempty"`
+}
+
+func (m *ListDatabasesRequest) Reset()                    { *m = ListDatabasesRequest{} }
+func (m *ListDatabasesRequest) String() string            { return proto.CompactTextString(m) }
+func (*ListDatabasesRequest) ProtoMessage()               {}
+func (*ListDatabasesRequest) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{1} }
+
+func (m *ListDatabasesRequest) GetParent() string {
+	if m != nil {
+		return m.Parent
+	}
+	return ""
+}
+
+func (m *ListDatabasesRequest) GetPageSize() int32 {
+	if m != nil {
+		return m.PageSize
+	}
+	return 0
+}
+
+func (m *ListDatabasesRequest) GetPageToken() string {
+	if m != nil {
+		return m.PageToken
+	}
+	return ""
+}
+
+// The response for [ListDatabases][google.spanner.admin.database.v1.DatabaseAdmin.ListDatabases].
+type ListDatabasesResponse struct {
+	// Databases that matched the request.
+	Databases []*Database `protobuf:"bytes,1,rep,name=databases" json:"databases,omitempty"`
+	// `next_page_token` can be sent in a subsequent
+	// [ListDatabases][google.spanner.admin.database.v1.DatabaseAdmin.ListDatabases] call to fetch more
+	// of the matching databases.
+	NextPageToken string `protobuf:"bytes,2,opt,name=next_page_token,json=nextPageToken" json:"next_page_token,omitempty"`
+}
+
+func (m *ListDatabasesResponse) Reset()                    { *m = ListDatabasesResponse{} }
+func (m *ListDatabasesResponse) String() string            { return proto.CompactTextString(m) }
+func (*ListDatabasesResponse) ProtoMessage()               {}
+func (*ListDatabasesResponse) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{2} }
+
+func (m *ListDatabasesResponse) GetDatabases() []*Database {
+	if m != nil {
+		return m.Databases
+	}
+	return nil
+}
+
+func (m *ListDatabasesResponse) GetNextPageToken() string {
+	if m != nil {
+		return m.NextPageToken
+	}
+	return ""
+}
+
+// The request for [CreateDatabase][google.spanner.admin.database.v1.DatabaseAdmin.CreateDatabase].
+type CreateDatabaseRequest struct {
+	// Required. The name of the instance that will serve the new database.
+	// Values are of the form `projects/<project>/instances/<instance>`.
+	Parent string `protobuf:"bytes,1,opt,name=parent" json:"parent,omitempty"`
+	// Required. A `CREATE DATABASE` statement, which specifies the ID of the
+	// new database.  The database ID must conform to the regular expression
+	// `[a-z][a-z0-9_\-]*[a-z0-9]` and be between 2 and 30 characters in length.
+	CreateStatement string `protobuf:"bytes,2,opt,name=create_statement,json=createStatement" json:"create_statement,omitempty"`
+	// An optional list of DDL statements to run inside the newly created
+	// database. Statements can create tables, indexes, etc. These
+	// statements execute atomically with the creation of the database:
+	// if there is an error in any statement, the database is not created.
+	ExtraStatements []string `protobuf:"bytes,3,rep,name=extra_statements,json=extraStatements" json:"extra_statements,omitempty"`
+}
+
+func (m *CreateDatabaseRequest) Reset()                    { *m = CreateDatabaseRequest{} }
+func (m *CreateDatabaseRequest) String() string            { return proto.CompactTextString(m) }
+func (*CreateDatabaseRequest) ProtoMessage()               {}
+func (*CreateDatabaseRequest) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{3} }
+
+func (m *CreateDatabaseRequest) GetParent() string {
+	if m != nil {
+		return m.Parent
+	}
+	return ""
+}
+
+func (m *CreateDatabaseRequest) GetCreateStatement() string {
+	if m != nil {
+		return m.CreateStatement
+	}
+	return ""
+}
+
+func (m *CreateDatabaseRequest) GetExtraStatements() []string {
+	if m != nil {
+		return m.ExtraStatements
+	}
+	return nil
+}
+
+// Metadata type for the operation returned by
+// [CreateDatabase][google.spanner.admin.database.v1.DatabaseAdmin.CreateDatabase].
+type CreateDatabaseMetadata struct {
+	// The database being created.
+	Database string `protobuf:"bytes,1,opt,name=database" json:"database,omitempty"`
+}
+
+func (m *CreateDatabaseMetadata) Reset()                    { *m = CreateDatabaseMetadata{} }
+func (m *CreateDatabaseMetadata) String() string            { return proto.CompactTextString(m) }
+func (*CreateDatabaseMetadata) ProtoMessage()               {}
+func (*CreateDatabaseMetadata) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{4} }
+
+func (m *CreateDatabaseMetadata) GetDatabase() string {
+	if m != nil {
+		return m.Database
+	}
+	return ""
+}
+
+// The request for [GetDatabase][google.spanner.admin.database.v1.DatabaseAdmin.GetDatabase].
+type GetDatabaseRequest struct {
+	// Required. The name of the requested database. Values are of the form
+	// `projects/<project>/instances/<instance>/databases/<database>`.
+	Name string `protobuf:"bytes,1,opt,name=name" json:"name,omitempty"`
+}
+
+func (m *GetDatabaseRequest) Reset()                    { *m = GetDatabaseRequest{} }
+func (m *GetDatabaseRequest) String() string            { return proto.CompactTextString(m) }
+func (*GetDatabaseRequest) ProtoMessage()               {}
+func (*GetDatabaseRequest) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{5} }
+
+func (m *GetDatabaseRequest) GetName() string {
+	if m != nil {
+		return m.Name
+	}
+	return ""
+}
+
+// Enqueues the given DDL statements to be applied, in order but not
+// necessarily all at once, to the database schema at some point (or
+// points) in the future. The server checks that the statements
+// are executable (syntactically valid, name tables that exist, etc.)
+// before enqueueing them, but they may still fail upon
+// later execution (e.g., if a statement from another batch of
+// statements is applied first and it conflicts in some way, or if
+// there is some data-related problem like a `NULL` value in a column to
+// which `NOT NULL` would be added). If a statement fails, all
+// subsequent statements in the batch are automatically cancelled.
+//
+// Each batch of statements is assigned a name which can be used with
+// the [Operations][google.longrunning.Operations] API to monitor
+// progress. See the
+// [operation_id][google.spanner.admin.database.v1.UpdateDatabaseDdlRequest.operation_id] field for more
+// details.
+type UpdateDatabaseDdlRequest struct {
+	// Required. The database to update.
+	Database string `protobuf:"bytes,1,opt,name=database" json:"database,omitempty"`
+	// DDL statements to be applied to the database.
+	Statements []string `protobuf:"bytes,2,rep,name=statements" json:"statements,omitempty"`
+	// If empty, the new update request is assigned an
+	// automatically-generated operation ID. Otherwise, `operation_id`
+	// is used to construct the name of the resulting
+	// [Operation][google.longrunning.Operation].
+	//
+	// Specifying an explicit operation ID simplifies determining
+	// whether the statements were executed in the event that the
+	// [UpdateDatabaseDdl][google.spanner.admin.database.v1.DatabaseAdmin.UpdateDatabaseDdl] call is replayed,
+	// or the return value is otherwise lost: the [database][google.spanner.admin.database.v1.UpdateDatabaseDdlRequest.database] and
+	// `operation_id` fields can be combined to form the
+	// [name][google.longrunning.Operation.name] of the resulting
+	// [longrunning.Operation][google.longrunning.Operation]: `<database>/operations/<operation_id>`.
+	//
+	// `operation_id` should be unique within the database, and must be
+	// a valid identifier: `[a-zA-Z][a-zA-Z0-9_]*`. Note that
+	// automatically-generated operation IDs always begin with an
+	// underscore. If the named operation already exists,
+	// [UpdateDatabaseDdl][google.spanner.admin.database.v1.DatabaseAdmin.UpdateDatabaseDdl] returns
+	// `ALREADY_EXISTS`.
+	OperationId string `protobuf:"bytes,3,opt,name=operation_id,json=operationId" json:"operation_id,omitempty"`
+}
+
+func (m *UpdateDatabaseDdlRequest) Reset()                    { *m = UpdateDatabaseDdlRequest{} }
+func (m *UpdateDatabaseDdlRequest) String() string            { return proto.CompactTextString(m) }
+func (*UpdateDatabaseDdlRequest) ProtoMessage()               {}
+func (*UpdateDatabaseDdlRequest) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{6} }
+
+func (m *UpdateDatabaseDdlRequest) GetDatabase() string {
+	if m != nil {
+		return m.Database
+	}
+	return ""
+}
+
+func (m *UpdateDatabaseDdlRequest) GetStatements() []string {
+	if m != nil {
+		return m.Statements
+	}
+	return nil
+}
+
+func (m *UpdateDatabaseDdlRequest) GetOperationId() string {
+	if m != nil {
+		return m.OperationId
+	}
+	return ""
+}
+
+// Metadata type for the operation returned by
+// [UpdateDatabaseDdl][google.spanner.admin.database.v1.DatabaseAdmin.UpdateDatabaseDdl].
+type UpdateDatabaseDdlMetadata struct {
+	// The database being modified.
+	Database string `protobuf:"bytes,1,opt,name=database" json:"database,omitempty"`
+	// For an update this list contains all the statements. For an
+	// individual statement, this list contains only that statement.
+	Statements []string `protobuf:"bytes,2,rep,name=statements" json:"statements,omitempty"`
+	// Reports the commit timestamps of all statements that have
+	// succeeded so far, where `commit_timestamps[i]` is the commit
+	// timestamp for the statement `statements[i]`.
+	CommitTimestamps []*google_protobuf3.Timestamp `protobuf:"bytes,3,rep,name=commit_timestamps,json=commitTimestamps" json:"commit_timestamps,omitempty"`
+}
+
+func (m *UpdateDatabaseDdlMetadata) Reset()                    { *m = UpdateDatabaseDdlMetadata{} }
+func (m *UpdateDatabaseDdlMetadata) String() string            { return proto.CompactTextString(m) }
+func (*UpdateDatabaseDdlMetadata) ProtoMessage()               {}
+func (*UpdateDatabaseDdlMetadata) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{7} }
+
+func (m *UpdateDatabaseDdlMetadata) GetDatabase() string {
+	if m != nil {
+		return m.Database
+	}
+	return ""
+}
+
+func (m *UpdateDatabaseDdlMetadata) GetStatements() []string {
+	if m != nil {
+		return m.Statements
+	}
+	return nil
+}
+
+func (m *UpdateDatabaseDdlMetadata) GetCommitTimestamps() []*google_protobuf3.Timestamp {
+	if m != nil {
+		return m.CommitTimestamps
+	}
+	return nil
+}
+
+// The request for [DropDatabase][google.spanner.admin.database.v1.DatabaseAdmin.DropDatabase].
+type DropDatabaseRequest struct {
+	// Required. The database to be dropped.
+	Database string `protobuf:"bytes,1,opt,name=database" json:"database,omitempty"`
+}
+
+func (m *DropDatabaseRequest) Reset()                    { *m = DropDatabaseRequest{} }
+func (m *DropDatabaseRequest) String() string            { return proto.CompactTextString(m) }
+func (*DropDatabaseRequest) ProtoMessage()               {}
+func (*DropDatabaseRequest) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{8} }
+
+func (m *DropDatabaseRequest) GetDatabase() string {
+	if m != nil {
+		return m.Database
+	}
+	return ""
+}
+
+// The request for [GetDatabaseDdl][google.spanner.admin.database.v1.DatabaseAdmin.GetDatabaseDdl].
+type GetDatabaseDdlRequest struct {
+	// Required. The database whose schema we wish to get.
+	Database string `protobuf:"bytes,1,opt,name=database" json:"database,omitempty"`
+}
+
+func (m *GetDatabaseDdlRequest) Reset()                    { *m = GetDatabaseDdlRequest{} }
+func (m *GetDatabaseDdlRequest) String() string            { return proto.CompactTextString(m) }
+func (*GetDatabaseDdlRequest) ProtoMessage()               {}
+func (*GetDatabaseDdlRequest) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{9} }
+
+func (m *GetDatabaseDdlRequest) GetDatabase() string {
+	if m != nil {
+		return m.Database
+	}
+	return ""
+}
+
+// The response for [GetDatabaseDdl][google.spanner.admin.database.v1.DatabaseAdmin.GetDatabaseDdl].
+type GetDatabaseDdlResponse struct {
+	// A list of formatted DDL statements defining the schema of the database
+	// specified in the request.
+	Statements []string `protobuf:"bytes,1,rep,name=statements" json:"statements,omitempty"`
+}
+
+func (m *GetDatabaseDdlResponse) Reset()                    { *m = GetDatabaseDdlResponse{} }
+func (m *GetDatabaseDdlResponse) String() string            { return proto.CompactTextString(m) }
+func (*GetDatabaseDdlResponse) ProtoMessage()               {}
+func (*GetDatabaseDdlResponse) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{10} }
+
+func (m *GetDatabaseDdlResponse) GetStatements() []string {
+	if m != nil {
+		return m.Statements
+	}
+	return nil
+}
+
+func init() {
+	proto.RegisterType((*Database)(nil), "google.spanner.admin.database.v1.Database")
+	proto.RegisterType((*ListDatabasesRequest)(nil), "google.spanner.admin.database.v1.ListDatabasesRequest")
+	proto.RegisterType((*ListDatabasesResponse)(nil), "google.spanner.admin.database.v1.ListDatabasesResponse")
+	proto.RegisterType((*CreateDatabaseRequest)(nil), "google.spanner.admin.database.v1.CreateDatabaseRequest")
+	proto.RegisterType((*CreateDatabaseMetadata)(nil), "google.spanner.admin.database.v1.CreateDatabaseMetadata")
+	proto.RegisterType((*GetDatabaseRequest)(nil), "google.spanner.admin.database.v1.GetDatabaseRequest")
+	proto.RegisterType((*UpdateDatabaseDdlRequest)(nil), "google.spanner.admin.database.v1.UpdateDatabaseDdlRequest")
+	proto.RegisterType((*UpdateDatabaseDdlMetadata)(nil), "google.spanner.admin.database.v1.UpdateDatabaseDdlMetadata")
+	proto.RegisterType((*DropDatabaseRequest)(nil), "google.spanner.admin.database.v1.DropDatabaseRequest")
+	proto.RegisterType((*GetDatabaseDdlRequest)(nil), "google.spanner.admin.database.v1.GetDatabaseDdlRequest")
+	proto.RegisterType((*GetDatabaseDdlResponse)(nil), "google.spanner.admin.database.v1.GetDatabaseDdlResponse")
+	proto.RegisterEnum("google.spanner.admin.database.v1.Database_State", Database_State_name, Database_State_value)
+}
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ context.Context
+var _ grpc.ClientConn
+
+// This is a compile-time assertion to ensure that this generated file
+// is compatible with the grpc package it is being compiled against.
+const _ = grpc.SupportPackageIsVersion4
+
+// Client API for DatabaseAdmin service
+
+type DatabaseAdminClient interface {
+	// Lists Cloud Spanner databases.
+	ListDatabases(ctx context.Context, in *ListDatabasesRequest, opts ...grpc.CallOption) (*ListDatabasesResponse, error)
+	// Creates a new Cloud Spanner database and starts to prepare it for serving.
+	// The returned [long-running operation][google.longrunning.Operation] will
+	// have a name of the format `<database_name>/operations/<operation_id>` and
+	// can be used to track preparation of the database. The
+	// [metadata][google.longrunning.Operation.metadata] field type is
+	// [CreateDatabaseMetadata][google.spanner.admin.database.v1.CreateDatabaseMetadata]. The
+	// [response][google.longrunning.Operation.response] field type is
+	// [Database][google.spanner.admin.database.v1.Database], if successful.
+	CreateDatabase(ctx context.Context, in *CreateDatabaseRequest, opts ...grpc.CallOption) (*google_longrunning.Operation, error)
+	// Gets the state of a Cloud Spanner database.
+	GetDatabase(ctx context.Context, in *GetDatabaseRequest, opts ...grpc.CallOption) (*Database, error)
+	// Updates the schema of a Cloud Spanner database by
+	// creating/altering/dropping tables, columns, indexes, etc. The returned
+	// [long-running operation][google.longrunning.Operation] will have a name of
+	// the format `<database_name>/operations/<operation_id>` and can be used to
+	// track execution of the schema change(s). The
+	// [metadata][google.longrunning.Operation.metadata] field type is
+	// [UpdateDatabaseDdlMetadata][google.spanner.admin.database.v1.UpdateDatabaseDdlMetadata].  The operation has no response.
+	UpdateDatabaseDdl(ctx context.Context, in *UpdateDatabaseDdlRequest, opts ...grpc.CallOption) (*google_longrunning.Operation, error)
+	// Drops (aka deletes) a Cloud Spanner database.
+	DropDatabase(ctx context.Context, in *DropDatabaseRequest, opts ...grpc.CallOption) (*google_protobuf2.Empty, error)
+	// Returns the schema of a Cloud Spanner database as a list of formatted
+	// DDL statements. This method does not show pending schema updates, those may
+	// be queried using the [Operations][google.longrunning.Operations] API.
+	GetDatabaseDdl(ctx context.Context, in *GetDatabaseDdlRequest, opts ...grpc.CallOption) (*GetDatabaseDdlResponse, error)
+	// Sets the access control policy on a database resource. Replaces any
+	// existing policy.
+	//
+	// Authorization requires `spanner.databases.setIamPolicy` permission on
+	// [resource][google.iam.v1.SetIamPolicyRequest.resource].
+	SetIamPolicy(ctx context.Context, in *google_iam_v11.SetIamPolicyRequest, opts ...grpc.CallOption) (*google_iam_v1.Policy, error)
+	// Gets the access control policy for a database resource. Returns an empty
+	// policy if a database exists but does not have a policy set.
+	//
+	// Authorization requires `spanner.databases.getIamPolicy` permission on
+	// [resource][google.iam.v1.GetIamPolicyRequest.resource].
+	GetIamPolicy(ctx context.Context, in *google_iam_v11.GetIamPolicyRequest, opts ...grpc.CallOption) (*google_iam_v1.Policy, error)
+	// Returns permissions that the caller has on the specified database resource.
+	//
+	// Attempting this RPC on a non-existent Cloud Spanner database will result in
+	// a NOT_FOUND error if the user has `spanner.databases.list` permission on
+	// the containing Cloud Spanner instance. Otherwise returns an empty set of
+	// permissions.
+	TestIamPermissions(ctx context.Context, in *google_iam_v11.TestIamPermissionsRequest, opts ...grpc.CallOption) (*google_iam_v11.TestIamPermissionsResponse, error)
+}
+
+type databaseAdminClient struct {
+	cc *grpc.ClientConn
+}
+
+func NewDatabaseAdminClient(cc *grpc.ClientConn) DatabaseAdminClient {
+	return &databaseAdminClient{cc}
+}
+
+func (c *databaseAdminClient) ListDatabases(ctx context.Context, in *ListDatabasesRequest, opts ...grpc.CallOption) (*ListDatabasesResponse, error) {
+	out := new(ListDatabasesResponse)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.database.v1.DatabaseAdmin/ListDatabases", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *databaseAdminClient) CreateDatabase(ctx context.Context, in *CreateDatabaseRequest, opts ...grpc.CallOption) (*google_longrunning.Operation, error) {
+	out := new(google_longrunning.Operation)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.database.v1.DatabaseAdmin/CreateDatabase", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *databaseAdminClient) GetDatabase(ctx context.Context, in *GetDatabaseRequest, opts ...grpc.CallOption) (*Database, error) {
+	out := new(Database)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.database.v1.DatabaseAdmin/GetDatabase", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *databaseAdminClient) UpdateDatabaseDdl(ctx context.Context, in *UpdateDatabaseDdlRequest, opts ...grpc.CallOption) (*google_longrunning.Operation, error) {
+	out := new(google_longrunning.Operation)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.database.v1.DatabaseAdmin/UpdateDatabaseDdl", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *databaseAdminClient) DropDatabase(ctx context.Context, in *DropDatabaseRequest, opts ...grpc.CallOption) (*google_protobuf2.Empty, error) {
+	out := new(google_protobuf2.Empty)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.database.v1.DatabaseAdmin/DropDatabase", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *databaseAdminClient) GetDatabaseDdl(ctx context.Context, in *GetDatabaseDdlRequest, opts ...grpc.CallOption) (*GetDatabaseDdlResponse, error) {
+	out := new(GetDatabaseDdlResponse)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.database.v1.DatabaseAdmin/GetDatabaseDdl", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *databaseAdminClient) SetIamPolicy(ctx context.Context, in *google_iam_v11.SetIamPolicyRequest, opts ...grpc.CallOption) (*google_iam_v1.Policy, error) {
+	out := new(google_iam_v1.Policy)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.database.v1.DatabaseAdmin/SetIamPolicy", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *databaseAdminClient) GetIamPolicy(ctx context.Context, in *google_iam_v11.GetIamPolicyRequest, opts ...grpc.CallOption) (*google_iam_v1.Policy, error) {
+	out := new(google_iam_v1.Policy)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.database.v1.DatabaseAdmin/GetIamPolicy", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *databaseAdminClient) TestIamPermissions(ctx context.Context, in *google_iam_v11.TestIamPermissionsRequest, opts ...grpc.CallOption) (*google_iam_v11.TestIamPermissionsResponse, error) {
+	out := new(google_iam_v11.TestIamPermissionsResponse)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.database.v1.DatabaseAdmin/TestIamPermissions", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+// Server API for DatabaseAdmin service
+
+type DatabaseAdminServer interface {
+	// Lists Cloud Spanner databases.
+	ListDatabases(context.Context, *ListDatabasesRequest) (*ListDatabasesResponse, error)
+	// Creates a new Cloud Spanner database and starts to prepare it for serving.
+	// The returned [long-running operation][google.longrunning.Operation] will
+	// have a name of the format `<database_name>/operations/<operation_id>` and
+	// can be used to track preparation of the database. The
+	// [metadata][google.longrunning.Operation.metadata] field type is
+	// [CreateDatabaseMetadata][google.spanner.admin.database.v1.CreateDatabaseMetadata]. The
+	// [response][google.longrunning.Operation.response] field type is
+	// [Database][google.spanner.admin.database.v1.Database], if successful.
+	CreateDatabase(context.Context, *CreateDatabaseRequest) (*google_longrunning.Operation, error)
+	// Gets the state of a Cloud Spanner database.
+	GetDatabase(context.Context, *GetDatabaseRequest) (*Database, error)
+	// Updates the schema of a Cloud Spanner database by
+	// creating/altering/dropping tables, columns, indexes, etc. The returned
+	// [long-running operation][google.longrunning.Operation] will have a name of
+	// the format `<database_name>/operations/<operation_id>` and can be used to
+	// track execution of the schema change(s). The
+	// [metadata][google.longrunning.Operation.metadata] field type is
+	// [UpdateDatabaseDdlMetadata][google.spanner.admin.database.v1.UpdateDatabaseDdlMetadata].  The operation has no response.
+	UpdateDatabaseDdl(context.Context, *UpdateDatabaseDdlRequest) (*google_longrunning.Operation, error)
+	// Drops (aka deletes) a Cloud Spanner database.
+	DropDatabase(context.Context, *DropDatabaseRequest) (*google_protobuf2.Empty, error)
+	// Returns the schema of a Cloud Spanner database as a list of formatted
+	// DDL statements. This method does not show pending schema updates, those may
+	// be queried using the [Operations][google.longrunning.Operations] API.
+	GetDatabaseDdl(context.Context, *GetDatabaseDdlRequest) (*GetDatabaseDdlResponse, error)
+	// Sets the access control policy on a database resource. Replaces any
+	// existing policy.
+	//
+	// Authorization requires `spanner.databases.setIamPolicy` permission on
+	// [resource][google.iam.v1.SetIamPolicyRequest.resource].
+	SetIamPolicy(context.Context, *google_iam_v11.SetIamPolicyRequest) (*google_iam_v1.Policy, error)
+	// Gets the access control policy for a database resource. Returns an empty
+	// policy if a database exists but does not have a policy set.
+	//
+	// Authorization requires `spanner.databases.getIamPolicy` permission on
+	// [resource][google.iam.v1.GetIamPolicyRequest.resource].
+	GetIamPolicy(context.Context, *google_iam_v11.GetIamPolicyRequest) (*google_iam_v1.Policy, error)
+	// Returns permissions that the caller has on the specified database resource.
+	//
+	// Attempting this RPC on a non-existent Cloud Spanner database will result in
+	// a NOT_FOUND error if the user has `spanner.databases.list` permission on
+	// the containing Cloud Spanner instance. Otherwise returns an empty set of
+	// permissions.
+	TestIamPermissions(context.Context, *google_iam_v11.TestIamPermissionsRequest) (*google_iam_v11.TestIamPermissionsResponse, error)
+}
+
+func RegisterDatabaseAdminServer(s *grpc.Server, srv DatabaseAdminServer) {
+	s.RegisterService(&_DatabaseAdmin_serviceDesc, srv)
+}
+
+func _DatabaseAdmin_ListDatabases_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(ListDatabasesRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(DatabaseAdminServer).ListDatabases(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.database.v1.DatabaseAdmin/ListDatabases",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(DatabaseAdminServer).ListDatabases(ctx, req.(*ListDatabasesRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _DatabaseAdmin_CreateDatabase_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(CreateDatabaseRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(DatabaseAdminServer).CreateDatabase(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.database.v1.DatabaseAdmin/CreateDatabase",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(DatabaseAdminServer).CreateDatabase(ctx, req.(*CreateDatabaseRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _DatabaseAdmin_GetDatabase_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(GetDatabaseRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(DatabaseAdminServer).GetDatabase(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.database.v1.DatabaseAdmin/GetDatabase",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(DatabaseAdminServer).GetDatabase(ctx, req.(*GetDatabaseRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _DatabaseAdmin_UpdateDatabaseDdl_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(UpdateDatabaseDdlRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(DatabaseAdminServer).UpdateDatabaseDdl(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.database.v1.DatabaseAdmin/UpdateDatabaseDdl",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(DatabaseAdminServer).UpdateDatabaseDdl(ctx, req.(*UpdateDatabaseDdlRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _DatabaseAdmin_DropDatabase_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(DropDatabaseRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(DatabaseAdminServer).DropDatabase(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.database.v1.DatabaseAdmin/DropDatabase",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(DatabaseAdminServer).DropDatabase(ctx, req.(*DropDatabaseRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _DatabaseAdmin_GetDatabaseDdl_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(GetDatabaseDdlRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(DatabaseAdminServer).GetDatabaseDdl(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.database.v1.DatabaseAdmin/GetDatabaseDdl",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(DatabaseAdminServer).GetDatabaseDdl(ctx, req.(*GetDatabaseDdlRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _DatabaseAdmin_SetIamPolicy_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(google_iam_v11.SetIamPolicyRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(DatabaseAdminServer).SetIamPolicy(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.database.v1.DatabaseAdmin/SetIamPolicy",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(DatabaseAdminServer).SetIamPolicy(ctx, req.(*google_iam_v11.SetIamPolicyRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _DatabaseAdmin_GetIamPolicy_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(google_iam_v11.GetIamPolicyRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(DatabaseAdminServer).GetIamPolicy(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.database.v1.DatabaseAdmin/GetIamPolicy",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(DatabaseAdminServer).GetIamPolicy(ctx, req.(*google_iam_v11.GetIamPolicyRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _DatabaseAdmin_TestIamPermissions_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(google_iam_v11.TestIamPermissionsRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(DatabaseAdminServer).TestIamPermissions(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.database.v1.DatabaseAdmin/TestIamPermissions",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(DatabaseAdminServer).TestIamPermissions(ctx, req.(*google_iam_v11.TestIamPermissionsRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+var _DatabaseAdmin_serviceDesc = grpc.ServiceDesc{
+	ServiceName: "google.spanner.admin.database.v1.DatabaseAdmin",
+	HandlerType: (*DatabaseAdminServer)(nil),
+	Methods: []grpc.MethodDesc{
+		{
+			MethodName: "ListDatabases",
+			Handler:    _DatabaseAdmin_ListDatabases_Handler,
+		},
+		{
+			MethodName: "CreateDatabase",
+			Handler:    _DatabaseAdmin_CreateDatabase_Handler,
+		},
+		{
+			MethodName: "GetDatabase",
+			Handler:    _DatabaseAdmin_GetDatabase_Handler,
+		},
+		{
+			MethodName: "UpdateDatabaseDdl",
+			Handler:    _DatabaseAdmin_UpdateDatabaseDdl_Handler,
+		},
+		{
+			MethodName: "DropDatabase",
+			Handler:    _DatabaseAdmin_DropDatabase_Handler,
+		},
+		{
+			MethodName: "GetDatabaseDdl",
+			Handler:    _DatabaseAdmin_GetDatabaseDdl_Handler,
+		},
+		{
+			MethodName: "SetIamPolicy",
+			Handler:    _DatabaseAdmin_SetIamPolicy_Handler,
+		},
+		{
+			MethodName: "GetIamPolicy",
+			Handler:    _DatabaseAdmin_GetIamPolicy_Handler,
+		},
+		{
+			MethodName: "TestIamPermissions",
+			Handler:    _DatabaseAdmin_TestIamPermissions_Handler,
+		},
+	},
+	Streams:  []grpc.StreamDesc{},
+	Metadata: "google/spanner/admin/database/v1/spanner_database_admin.proto",
+}
+
+func init() {
+	proto.RegisterFile("google/spanner/admin/database/v1/spanner_database_admin.proto", fileDescriptor0)
+}
+
+var fileDescriptor0 = []byte{
+	// 999 bytes of a gzipped FileDescriptorProto
+	0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xbc, 0x96, 0xcf, 0x6f, 0x1b, 0x45,
+	0x14, 0xc7, 0x99, 0xa4, 0xa9, 0xe2, 0x17, 0x27, 0x75, 0x06, 0x1c, 0xb9, 0x5b, 0x5a, 0xcc, 0x82,
+	0x90, 0x6b, 0x89, 0x5d, 0xe2, 0x34, 0x24, 0x18, 0x05, 0x91, 0xc6, 0xae, 0x6b, 0x09, 0x5a, 0xcb,
+	0x76, 0x0f, 0x70, 0xb1, 0x26, 0xf6, 0xb0, 0x6c, 0xf1, 0xce, 0x2e, 0x3b, 0xe3, 0xaa, 0x2d, 0xea,
+	0x05, 0x89, 0x03, 0x07, 0x4e, 0x80, 0xc4, 0x0d, 0xc4, 0x81, 0x33, 0x37, 0x24, 0x8e, 0xfc, 0x0b,
+	0xfc, 0x0b, 0xfc, 0x21, 0x68, 0x66, 0x77, 0x9c, 0xf5, 0x3a, 0x89, 0xd7, 0x1c, 0xb8, 0x79, 0xdf,
+	0x8f, 0x79, 0x9f, 0xf7, 0xf6, 0x7d, 0xc7, 0x0b, 0x47, 0x8e, 0xef, 0x3b, 0x63, 0x6a, 0xf3, 0x80,
+	0x30, 0x46, 0x43, 0x9b, 0x8c, 0x3c, 0x97, 0xd9, 0x23, 0x22, 0xc8, 0x29, 0xe1, 0xd4, 0x7e, 0xb2,
+	0xab, 0x3d, 0x03, 0x6d, 0x1b, 0xa8, 0x10, 0x2b, 0x08, 0x7d, 0xe1, 0xe3, 0x72, 0x94, 0x6e, 0xc5,
+	0x41, 0x56, 0xe4, 0xd3, 0xa1, 0xd6, 0x93, 0x5d, 0xe3, 0xd5, 0xb8, 0x00, 0x09, 0x5c, 0x9b, 0x30,
+	0xe6, 0x0b, 0x22, 0x5c, 0x9f, 0xf1, 0x28, 0xdf, 0x28, 0x26, 0xbd, 0x13, 0xf1, 0x79, 0x6c, 0xbe,
+	0x15, 0x9b, 0x5d, 0xe2, 0x49, 0x04, 0x97, 0x78, 0x83, 0xc0, 0x1f, 0xbb, 0xc3, 0x67, 0xb1, 0xdf,
+	0x98, 0xf5, 0xcf, 0xf8, 0xde, 0x88, 0x7d, 0x63, 0x9f, 0x39, 0xe1, 0x84, 0x31, 0x97, 0x39, 0xb6,
+	0x1f, 0xd0, 0x70, 0xa6, 0xee, 0x8d, 0x38, 0x48, 0x3d, 0x9d, 0x4e, 0x3e, 0xb3, 0xa9, 0x17, 0x08,
+	0x7d, 0xc2, 0x6b, 0x69, 0xa7, 0x70, 0x3d, 0xca, 0x05, 0xf1, 0x82, 0x28, 0xc0, 0xfc, 0x19, 0xc1,
+	0x7a, 0x23, 0xee, 0x11, 0x63, 0xb8, 0xc2, 0x88, 0x47, 0x4b, 0xa8, 0x8c, 0x2a, 0xb9, 0xae, 0xfa,
+	0x8d, 0xef, 0xc1, 0x1a, 0x17, 0x44, 0xd0, 0xd2, 0x4a, 0x19, 0x55, 0xb6, 0x6a, 0xef, 0x58, 0x8b,
+	0xc6, 0x64, 0xe9, 0xe3, 0xac, 0x9e, 0xcc, 0xeb, 0x46, 0xe9, 0xe6, 0x01, 0xac, 0xa9, 0x67, 0x5c,
+	0x84, 0xed, 0x5e, 0xff, 0xb8, 0xdf, 0x1c, 0x3c, 0x7a, 0xd0, 0xeb, 0x34, 0x4f, 0xda, 0xf7, 0xda,
+	0xcd, 0x46, 0xe1, 0x25, 0x9c, 0x87, 0xf5, 0x93, 0x6e, 0xf3, 0xb8, 0xdf, 0x7e, 0xd0, 0x2a, 0x20,
+	0x9c, 0x83, 0xb5, 0x6e, 0xf3, 0xb8, 0xf1, 0x49, 0x61, 0xc5, 0x7c, 0x0c, 0xaf, 0x7c, 0xe4, 0x72,
+	0xa1, 0x4f, 0xe5, 0x5d, 0xfa, 0xe5, 0x84, 0x72, 0x81, 0x77, 0xe0, 0x6a, 0x40, 0x42, 0xca, 0x44,
+	0x8c, 0x1b, 0x3f, 0xe1, 0x1b, 0x90, 0x0b, 0x88, 0x43, 0x07, 0xdc, 0x7d, 0x4e, 0x4b, 0xab, 0x65,
+	0x54, 0x59, 0xeb, 0xae, 0x4b, 0x43, 0xcf, 0x7d, 0x4e, 0xf1, 0x4d, 0x00, 0xe5, 0x14, 0xfe, 0x17,
+	0x94, 0x95, 0xae, 0xa8, 0x44, 0x15, 0xde, 0x97, 0x06, 0xf3, 0x5b, 0x04, 0xc5, 0x54, 0x31, 0x1e,
+	0xf8, 0x8c, 0x53, 0x7c, 0x1f, 0x72, 0xba, 0x47, 0x5e, 0x42, 0xe5, 0xd5, 0xca, 0x46, 0xad, 0x9a,
+	0x7d, 0x14, 0xdd, 0xb3, 0x64, 0xfc, 0x16, 0x5c, 0x63, 0xf4, 0xa9, 0x18, 0x24, 0x38, 0x56, 0x14,
+	0xc7, 0xa6, 0x34, 0x77, 0xa6, 0x2c, 0xdf, 0x20, 0x28, 0x9e, 0x84, 0x94, 0x08, 0x3a, 0x3d, 0x65,
+	0x41, 0xe7, 0xb7, 0xa1, 0x30, 0x54, 0x09, 0x03, 0x35, 0x72, 0x4f, 0x46, 0x44, 0x47, 0x5f, 0x8b,
+	0xec, 0x3d, 0x6d, 0x96, 0xa1, 0xf4, 0xa9, 0x08, 0xc9, 0x59, 0x24, 0x2f, 0xad, 0x96, 0x57, 0x65,
+	0xa8, 0xb2, 0x4f, 0x23, 0xb9, 0x79, 0x07, 0x76, 0x66, 0x31, 0x3e, 0xa6, 0x82, 0xc8, 0x76, 0xb0,
+	0x01, 0xeb, 0xba, 0xad, 0x98, 0x64, 0xfa, 0x6c, 0x56, 0x00, 0xb7, 0xa8, 0x48, 0x93, 0x9f, 0xb3,
+	0x60, 0xe6, 0x33, 0x28, 0x3d, 0x0a, 0x46, 0x89, 0xf3, 0x1b, 0xa3, 0xb1, 0x8e, 0xbf, 0xa4, 0x02,
+	0xbe, 0x05, 0x90, 0x80, 0x5f, 0x51, 0xf0, 0x09, 0x0b, 0x7e, 0x1d, 0xf2, 0x53, 0xad, 0x0c, 0xdc,
+	0x91, 0x5a, 0x85, 0x5c, 0x77, 0x63, 0x6a, 0x6b, 0x8f, 0xcc, 0x5f, 0x10, 0x5c, 0x9f, 0xab, 0x9d,
+	0xa5, 0xbd, 0x85, 0xc5, 0x5b, 0xb0, 0x3d, 0xf4, 0x3d, 0xcf, 0x15, 0x83, 0xa9, 0xe0, 0xa2, 0x01,
+	0x6f, 0xd4, 0x0c, 0xbd, 0x36, 0x5a, 0x93, 0x56, 0x5f, 0x87, 0x74, 0x0b, 0x51, 0xd2, 0xd4, 0xc0,
+	0xcd, 0x5d, 0x78, 0xb9, 0x11, 0xfa, 0x41, 0x7a, 0x90, 0x97, 0x8d, 0x7e, 0x0f, 0x8a, 0x89, 0xd1,
+	0x67, 0x9b, 0xa6, 0x79, 0x08, 0x3b, 0xe9, 0xa4, 0x78, 0xf3, 0x67, 0x5b, 0x45, 0xe9, 0x56, 0x6b,
+	0x3f, 0xe6, 0x61, 0x53, 0xe7, 0x1d, 0x4b, 0x05, 0xe0, 0x3f, 0x10, 0x6c, 0xce, 0xa8, 0x08, 0xbf,
+	0xbb, 0x58, 0x2a, 0xe7, 0x69, 0xdc, 0x38, 0x58, 0x3a, 0x2f, 0x82, 0x36, 0xf7, 0xbf, 0xfe, 0xfb,
+	0x9f, 0xef, 0x57, 0x6c, 0xfc, 0xb6, 0xbc, 0x53, 0xbf, 0x8a, 0xf4, 0x71, 0x14, 0x84, 0xfe, 0x63,
+	0x3a, 0x14, 0xdc, 0xae, 0xda, 0x2e, 0xe3, 0x82, 0xb0, 0x21, 0xe5, 0x76, 0xf5, 0x85, 0x7d, 0xa6,
+	0xcd, 0x5f, 0x11, 0x6c, 0xcd, 0x2e, 0x3b, 0xce, 0x80, 0x70, 0xae, 0x4a, 0x8d, 0x9b, 0x3a, 0x31,
+	0x71, 0x7b, 0x5b, 0x0f, 0xf5, 0xf6, 0x99, 0x87, 0x8a, 0xb0, 0x66, 0x2e, 0x47, 0x58, 0x47, 0x55,
+	0xfc, 0x1b, 0x82, 0x8d, 0xc4, 0xbb, 0xc2, 0x77, 0x16, 0x13, 0xce, 0x4b, 0xd1, 0x58, 0xe2, 0xf6,
+	0x4a, 0x4d, 0x53, 0xaa, 0xf6, 0x02, 0xd2, 0x33, 0x50, 0xbb, 0xfa, 0x02, 0xff, 0x8e, 0x60, 0x7b,
+	0x4e, 0x5e, 0xb8, 0xbe, 0xb8, 0xf0, 0x45, 0xf7, 0xc1, 0xa2, 0x99, 0x7e, 0xa8, 0x38, 0xeb, 0xb5,
+	0x7d, 0xc5, 0xa9, 0x4f, 0xcc, 0xc2, 0x6a, 0x8f, 0x46, 0x63, 0x39, 0xdb, 0x9f, 0x10, 0xe4, 0x93,
+	0x7a, 0xc3, 0xfb, 0x19, 0xc6, 0x34, 0xaf, 0x4f, 0x63, 0x67, 0x4e, 0xe4, 0x4d, 0xf9, 0xaf, 0x6c,
+	0xbe, 0xa7, 0x08, 0xf7, 0xaa, 0xbb, 0x4b, 0x13, 0xe2, 0xbf, 0x10, 0x6c, 0xcd, 0x4a, 0x34, 0xcb,
+	0x6e, 0x9e, 0x7b, 0x13, 0x18, 0x87, 0xcb, 0x27, 0xc6, 0xc2, 0x3a, 0x52, 0x0d, 0x1c, 0xe0, 0xff,
+	0x36, 0x62, 0xfc, 0x03, 0x82, 0x7c, 0x8f, 0x8a, 0x36, 0xf1, 0x3a, 0xea, 0x43, 0x07, 0x9b, 0x9a,
+	0xc4, 0x25, 0x9e, 0x2c, 0x9b, 0x74, 0x6a, 0xda, 0x62, 0x2a, 0x26, 0xf2, 0x9a, 0x6d, 0x85, 0x72,
+	0x62, 0x7e, 0xa0, 0x50, 0x42, 0xca, 0xfd, 0x49, 0x38, 0xcc, 0x84, 0x52, 0xe7, 0x89, 0x2a, 0xf2,
+	0xb5, 0x4b, 0xac, 0xd6, 0x65, 0x58, 0xad, 0xff, 0x05, 0xcb, 0x49, 0x61, 0xfd, 0x89, 0x00, 0xf7,
+	0x29, 0x57, 0x46, 0x1a, 0x7a, 0x2e, 0xe7, 0xf2, 0xbb, 0x0f, 0x57, 0x52, 0x85, 0xe7, 0x43, 0x34,
+	0xe2, 0xed, 0x0c, 0x91, 0xf1, 0x8b, 0x7d, 0xa8, 0xb0, 0xdb, 0x66, 0x63, 0x79, 0x6c, 0x31, 0x77,
+	0x6a, 0x1d, 0x55, 0xef, 0x7e, 0x87, 0xe0, 0xcd, 0xa1, 0xef, 0x2d, 0xdc, 0xb4, 0xbb, 0xd7, 0x7b,
+	0x91, 0x6b, 0xe6, 0x4f, 0xa4, 0x23, 0x75, 0xd3, 0x41, 0x9f, 0xde, 0x8f, 0xd3, 0x1d, 0x7f, 0x4c,
+	0x98, 0x63, 0xf9, 0xa1, 0x63, 0x3b, 0x94, 0x29, 0x55, 0xd9, 0x91, 0x8b, 0x04, 0x2e, 0xbf, 0xf8,
+	0x9b, 0xff, 0x7d, 0xfd, 0xfb, 0xf4, 0xaa, 0x4a, 0xda, 0xfb, 0x37, 0x00, 0x00, 0xff, 0xff, 0x46,
+	0x3d, 0xa5, 0xd9, 0x27, 0x0c, 0x00, 0x00,
+}
diff --git a/googleapis/spanner/admin/instance/v1/spanner_instance_admin.pb.go b/googleapis/spanner/admin/instance/v1/spanner_instance_admin.pb.go
new file mode 100644
index 00000000..15f812d1
--- /dev/null
+++ b/googleapis/spanner/admin/instance/v1/spanner_instance_admin.pb.go
@@ -0,0 +1,1281 @@
+// Code generated by protoc-gen-go.
+// source: google/spanner/admin/instance/v1/spanner_instance_admin.proto
+// DO NOT EDIT!
+
+/*
+Package instance is a generated protocol buffer package.
+
+It is generated from these files:
+	google/spanner/admin/instance/v1/spanner_instance_admin.proto
+
+It has these top-level messages:
+	InstanceConfig
+	Instance
+	ListInstanceConfigsRequest
+	ListInstanceConfigsResponse
+	GetInstanceConfigRequest
+	GetInstanceRequest
+	CreateInstanceRequest
+	ListInstancesRequest
+	ListInstancesResponse
+	UpdateInstanceRequest
+	DeleteInstanceRequest
+	CreateInstanceMetadata
+	UpdateInstanceMetadata
+*/
+package instance
+
+import proto "github.com/golang/protobuf/proto"
+import fmt "fmt"
+import math "math"
+import _ "google.golang.org/genproto/googleapis/api/annotations"
+import _ "google.golang.org/genproto/googleapis/api/serviceconfig"
+import google_iam_v11 "google.golang.org/genproto/googleapis/iam/v1"
+import google_iam_v1 "google.golang.org/genproto/googleapis/iam/v1"
+import google_longrunning "google.golang.org/genproto/googleapis/longrunning"
+import google_protobuf2 "github.com/golang/protobuf/ptypes/empty"
+import google_protobuf3 "google.golang.org/genproto/protobuf/field_mask"
+import google_protobuf4 "github.com/golang/protobuf/ptypes/timestamp"
+
+import (
+	context "golang.org/x/net/context"
+	grpc "google.golang.org/grpc"
+)
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ = proto.Marshal
+var _ = fmt.Errorf
+var _ = math.Inf
+
+// This is a compile-time assertion to ensure that this generated file
+// is compatible with the proto package it is being compiled against.
+// A compilation error at this line likely means your copy of the
+// proto package needs to be updated.
+const _ = proto.ProtoPackageIsVersion2 // please upgrade the proto package
+
+// Indicates the current state of the instance.
+type Instance_State int32
+
+const (
+	// Not specified.
+	Instance_STATE_UNSPECIFIED Instance_State = 0
+	// The instance is still being created. Resources may not be
+	// available yet, and operations such as database creation may not
+	// work.
+	Instance_CREATING Instance_State = 1
+	// The instance is fully created and ready to do work such as
+	// creating databases.
+	Instance_READY Instance_State = 2
+)
+
+var Instance_State_name = map[int32]string{
+	0: "STATE_UNSPECIFIED",
+	1: "CREATING",
+	2: "READY",
+}
+var Instance_State_value = map[string]int32{
+	"STATE_UNSPECIFIED": 0,
+	"CREATING":          1,
+	"READY":             2,
+}
+
+func (x Instance_State) String() string {
+	return proto.EnumName(Instance_State_name, int32(x))
+}
+func (Instance_State) EnumDescriptor() ([]byte, []int) { return fileDescriptor0, []int{1, 0} }
+
+// A possible configuration for a Cloud Spanner instance. Configurations
+// define the geographic placement of nodes and their replication.
+type InstanceConfig struct {
+	// A unique identifier for the instance configuration.  Values
+	// are of the form
+	// `projects/<project>/instanceConfigs/[a-z][-a-z0-9]*`
+	Name string `protobuf:"bytes,1,opt,name=name" json:"name,omitempty"`
+	// The name of this instance configuration as it appears in UIs.
+	DisplayName string `protobuf:"bytes,2,opt,name=display_name,json=displayName" json:"display_name,omitempty"`
+}
+
+func (m *InstanceConfig) Reset()                    { *m = InstanceConfig{} }
+func (m *InstanceConfig) String() string            { return proto.CompactTextString(m) }
+func (*InstanceConfig) ProtoMessage()               {}
+func (*InstanceConfig) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{0} }
+
+func (m *InstanceConfig) GetName() string {
+	if m != nil {
+		return m.Name
+	}
+	return ""
+}
+
+func (m *InstanceConfig) GetDisplayName() string {
+	if m != nil {
+		return m.DisplayName
+	}
+	return ""
+}
+
+// An isolated set of Cloud Spanner resources on which databases can be hosted.
+type Instance struct {
+	// Required. A unique identifier for the instance, which cannot be changed
+	// after the instance is created. Values are of the form
+	// `projects/<project>/instances/[a-z][-a-z0-9]*[a-z0-9]`. The final
+	// segment of the name must be between 6 and 30 characters in length.
+	Name string `protobuf:"bytes,1,opt,name=name" json:"name,omitempty"`
+	// Required. The name of the instance's configuration. Values are of the form
+	// `projects/<project>/instanceConfigs/<configuration>`. See
+	// also [InstanceConfig][google.spanner.admin.instance.v1.InstanceConfig] and
+	// [ListInstanceConfigs][google.spanner.admin.instance.v1.InstanceAdmin.ListInstanceConfigs].
+	Config string `protobuf:"bytes,2,opt,name=config" json:"config,omitempty"`
+	// Required. The descriptive name for this instance as it appears in UIs.
+	// Must be unique per project and between 4 and 30 characters in length.
+	DisplayName string `protobuf:"bytes,3,opt,name=display_name,json=displayName" json:"display_name,omitempty"`
+	// Required. The number of nodes allocated to this instance.
+	NodeCount int32 `protobuf:"varint,5,opt,name=node_count,json=nodeCount" json:"node_count,omitempty"`
+	// Output only. The current instance state. For
+	// [CreateInstance][google.spanner.admin.instance.v1.InstanceAdmin.CreateInstance], the state must be
+	// either omitted or set to `CREATING`. For
+	// [UpdateInstance][google.spanner.admin.instance.v1.InstanceAdmin.UpdateInstance], the state must be
+	// either omitted or set to `READY`.
+	State Instance_State `protobuf:"varint,6,opt,name=state,enum=google.spanner.admin.instance.v1.Instance_State" json:"state,omitempty"`
+	// Cloud Labels are a flexible and lightweight mechanism for organizing cloud
+	// resources into groups that reflect a customer's organizational needs and
+	// deployment strategies. Cloud Labels can be used to filter collections of
+	// resources. They can be used to control how resource metrics are aggregated.
+	// And they can be used as arguments to policy management rules (e.g. route,
+	// firewall, load balancing, etc.).
+	//
+	//  * Label keys must be between 1 and 63 characters long and must conform to
+	//    the following regular expression: `[a-z]([-a-z0-9]*[a-z0-9])?`.
+	//  * Label values must be between 0 and 63 characters long and must conform
+	//    to the regular expression `([a-z]([-a-z0-9]*[a-z0-9])?)?`.
+	//  * No more than 64 labels can be associated with a given resource.
+	//
+	// See https://goo.gl/xmQnxf for more information on and examples of labels.
+	//
+	// If you plan to use labels in your own code, please note that additional
+	// characters may be allowed in the future. And so you are advised to use an
+	// internal label representation, such as JSON, which doesn't rely upon
+	// specific characters being disallowed.  For example, representing labels
+	// as the string:  name + "_" + value  would prove problematic if we were to
+	// allow "_" in a future release.
+	Labels map[string]string `protobuf:"bytes,7,rep,name=labels" json:"labels,omitempty" protobuf_key:"bytes,1,opt,name=key" protobuf_val:"bytes,2,opt,name=value"`
+}
+
+func (m *Instance) Reset()                    { *m = Instance{} }
+func (m *Instance) String() string            { return proto.CompactTextString(m) }
+func (*Instance) ProtoMessage()               {}
+func (*Instance) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{1} }
+
+func (m *Instance) GetName() string {
+	if m != nil {
+		return m.Name
+	}
+	return ""
+}
+
+func (m *Instance) GetConfig() string {
+	if m != nil {
+		return m.Config
+	}
+	return ""
+}
+
+func (m *Instance) GetDisplayName() string {
+	if m != nil {
+		return m.DisplayName
+	}
+	return ""
+}
+
+func (m *Instance) GetNodeCount() int32 {
+	if m != nil {
+		return m.NodeCount
+	}
+	return 0
+}
+
+func (m *Instance) GetState() Instance_State {
+	if m != nil {
+		return m.State
+	}
+	return Instance_STATE_UNSPECIFIED
+}
+
+func (m *Instance) GetLabels() map[string]string {
+	if m != nil {
+		return m.Labels
+	}
+	return nil
+}
+
+// The request for [ListInstanceConfigs][google.spanner.admin.instance.v1.InstanceAdmin.ListInstanceConfigs].
+type ListInstanceConfigsRequest struct {
+	// Required. The name of the project for which a list of supported instance
+	// configurations is requested. Values are of the form
+	// `projects/<project>`.
+	Parent string `protobuf:"bytes,1,opt,name=parent" json:"parent,omitempty"`
+	// Number of instance configurations to be returned in the response. If 0 or
+	// less, defaults to the server's maximum allowed page size.
+	PageSize int32 `protobuf:"varint,2,opt,name=page_size,json=pageSize" json:"page_size,omitempty"`
+	// If non-empty, `page_token` should contain a
+	// [next_page_token][google.spanner.admin.instance.v1.ListInstanceConfigsResponse.next_page_token]
+	// from a previous [ListInstanceConfigsResponse][google.spanner.admin.instance.v1.ListInstanceConfigsResponse].
+	PageToken string `protobuf:"bytes,3,opt,name=page_token,json=pageToken" json:"page_token,omitempty"`
+}
+
+func (m *ListInstanceConfigsRequest) Reset()                    { *m = ListInstanceConfigsRequest{} }
+func (m *ListInstanceConfigsRequest) String() string            { return proto.CompactTextString(m) }
+func (*ListInstanceConfigsRequest) ProtoMessage()               {}
+func (*ListInstanceConfigsRequest) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{2} }
+
+func (m *ListInstanceConfigsRequest) GetParent() string {
+	if m != nil {
+		return m.Parent
+	}
+	return ""
+}
+
+func (m *ListInstanceConfigsRequest) GetPageSize() int32 {
+	if m != nil {
+		return m.PageSize
+	}
+	return 0
+}
+
+func (m *ListInstanceConfigsRequest) GetPageToken() string {
+	if m != nil {
+		return m.PageToken
+	}
+	return ""
+}
+
+// The response for [ListInstanceConfigs][google.spanner.admin.instance.v1.InstanceAdmin.ListInstanceConfigs].
+type ListInstanceConfigsResponse struct {
+	// The list of requested instance configurations.
+	InstanceConfigs []*InstanceConfig `protobuf:"bytes,1,rep,name=instance_configs,json=instanceConfigs" json:"instance_configs,omitempty"`
+	// `next_page_token` can be sent in a subsequent
+	// [ListInstanceConfigs][google.spanner.admin.instance.v1.InstanceAdmin.ListInstanceConfigs] call to
+	// fetch more of the matching instance configurations.
+	NextPageToken string `protobuf:"bytes,2,opt,name=next_page_token,json=nextPageToken" json:"next_page_token,omitempty"`
+}
+
+func (m *ListInstanceConfigsResponse) Reset()                    { *m = ListInstanceConfigsResponse{} }
+func (m *ListInstanceConfigsResponse) String() string            { return proto.CompactTextString(m) }
+func (*ListInstanceConfigsResponse) ProtoMessage()               {}
+func (*ListInstanceConfigsResponse) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{3} }
+
+func (m *ListInstanceConfigsResponse) GetInstanceConfigs() []*InstanceConfig {
+	if m != nil {
+		return m.InstanceConfigs
+	}
+	return nil
+}
+
+func (m *ListInstanceConfigsResponse) GetNextPageToken() string {
+	if m != nil {
+		return m.NextPageToken
+	}
+	return ""
+}
+
+// The request for
+// [GetInstanceConfigRequest][google.spanner.admin.instance.v1.InstanceAdmin.GetInstanceConfig].
+type GetInstanceConfigRequest struct {
+	// Required. The name of the requested instance configuration. Values are of
+	// the form `projects/<project>/instanceConfigs/<config>`.
+	Name string `protobuf:"bytes,1,opt,name=name" json:"name,omitempty"`
+}
+
+func (m *GetInstanceConfigRequest) Reset()                    { *m = GetInstanceConfigRequest{} }
+func (m *GetInstanceConfigRequest) String() string            { return proto.CompactTextString(m) }
+func (*GetInstanceConfigRequest) ProtoMessage()               {}
+func (*GetInstanceConfigRequest) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{4} }
+
+func (m *GetInstanceConfigRequest) GetName() string {
+	if m != nil {
+		return m.Name
+	}
+	return ""
+}
+
+// The request for [GetInstance][google.spanner.admin.instance.v1.InstanceAdmin.GetInstance].
+type GetInstanceRequest struct {
+	// Required. The name of the requested instance. Values are of the form
+	// `projects/<project>/instances/<instance>`.
+	Name string `protobuf:"bytes,1,opt,name=name" json:"name,omitempty"`
+}
+
+func (m *GetInstanceRequest) Reset()                    { *m = GetInstanceRequest{} }
+func (m *GetInstanceRequest) String() string            { return proto.CompactTextString(m) }
+func (*GetInstanceRequest) ProtoMessage()               {}
+func (*GetInstanceRequest) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{5} }
+
+func (m *GetInstanceRequest) GetName() string {
+	if m != nil {
+		return m.Name
+	}
+	return ""
+}
+
+// The request for [CreateInstance][google.spanner.admin.instance.v1.InstanceAdmin.CreateInstance].
+type CreateInstanceRequest struct {
+	// Required. The name of the project in which to create the instance. Values
+	// are of the form `projects/<project>`.
+	Parent string `protobuf:"bytes,1,opt,name=parent" json:"parent,omitempty"`
+	// Required. The ID of the instance to create.  Valid identifiers are of the
+	// form `[a-z][-a-z0-9]*[a-z0-9]` and must be between 6 and 30 characters in
+	// length.
+	InstanceId string `protobuf:"bytes,2,opt,name=instance_id,json=instanceId" json:"instance_id,omitempty"`
+	// Required. The instance to create.  The name may be omitted, but if
+	// specified must be `<parent>/instances/<instance_id>`.
+	Instance *Instance `protobuf:"bytes,3,opt,name=instance" json:"instance,omitempty"`
+}
+
+func (m *CreateInstanceRequest) Reset()                    { *m = CreateInstanceRequest{} }
+func (m *CreateInstanceRequest) String() string            { return proto.CompactTextString(m) }
+func (*CreateInstanceRequest) ProtoMessage()               {}
+func (*CreateInstanceRequest) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{6} }
+
+func (m *CreateInstanceRequest) GetParent() string {
+	if m != nil {
+		return m.Parent
+	}
+	return ""
+}
+
+func (m *CreateInstanceRequest) GetInstanceId() string {
+	if m != nil {
+		return m.InstanceId
+	}
+	return ""
+}
+
+func (m *CreateInstanceRequest) GetInstance() *Instance {
+	if m != nil {
+		return m.Instance
+	}
+	return nil
+}
+
+// The request for [ListInstances][google.spanner.admin.instance.v1.InstanceAdmin.ListInstances].
+type ListInstancesRequest struct {
+	// Required. The name of the project for which a list of instances is
+	// requested. Values are of the form `projects/<project>`.
+	Parent string `protobuf:"bytes,1,opt,name=parent" json:"parent,omitempty"`
+	// Number of instances to be returned in the response. If 0 or less, defaults
+	// to the server's maximum allowed page size.
+	PageSize int32 `protobuf:"varint,2,opt,name=page_size,json=pageSize" json:"page_size,omitempty"`
+	// If non-empty, `page_token` should contain a
+	// [next_page_token][google.spanner.admin.instance.v1.ListInstancesResponse.next_page_token] from a
+	// previous [ListInstancesResponse][google.spanner.admin.instance.v1.ListInstancesResponse].
+	PageToken string `protobuf:"bytes,3,opt,name=page_token,json=pageToken" json:"page_token,omitempty"`
+	// An expression for filtering the results of the request. Filter rules are
+	// case insensitive. The fields eligible for filtering are:
+	//
+	//   * name
+	//   * display_name
+	//   * labels.key where key is the name of a label
+	//
+	// Some examples of using filters are:
+	//
+	//   * name:* --> The instance has a name.
+	//   * name:Howl --> The instance's name contains the string "howl".
+	//   * name:HOWL --> Equivalent to above.
+	//   * NAME:howl --> Equivalent to above.
+	//   * labels.env:* --> The instance has the label "env".
+	//   * labels.env:dev --> The instance has the label "env" and the value of
+	//                        the label contains the string "dev".
+	//   * name:howl labels.env:dev --> The instance's name contains "howl" and
+	//                                  it has the label "env" with its value
+	//                                  containing "dev".
+	Filter string `protobuf:"bytes,4,opt,name=filter" json:"filter,omitempty"`
+}
+
+func (m *ListInstancesRequest) Reset()                    { *m = ListInstancesRequest{} }
+func (m *ListInstancesRequest) String() string            { return proto.CompactTextString(m) }
+func (*ListInstancesRequest) ProtoMessage()               {}
+func (*ListInstancesRequest) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{7} }
+
+func (m *ListInstancesRequest) GetParent() string {
+	if m != nil {
+		return m.Parent
+	}
+	return ""
+}
+
+func (m *ListInstancesRequest) GetPageSize() int32 {
+	if m != nil {
+		return m.PageSize
+	}
+	return 0
+}
+
+func (m *ListInstancesRequest) GetPageToken() string {
+	if m != nil {
+		return m.PageToken
+	}
+	return ""
+}
+
+func (m *ListInstancesRequest) GetFilter() string {
+	if m != nil {
+		return m.Filter
+	}
+	return ""
+}
+
+// The response for [ListInstances][google.spanner.admin.instance.v1.InstanceAdmin.ListInstances].
+type ListInstancesResponse struct {
+	// The list of requested instances.
+	Instances []*Instance `protobuf:"bytes,1,rep,name=instances" json:"instances,omitempty"`
+	// `next_page_token` can be sent in a subsequent
+	// [ListInstances][google.spanner.admin.instance.v1.InstanceAdmin.ListInstances] call to fetch more
+	// of the matching instances.
+	NextPageToken string `protobuf:"bytes,2,opt,name=next_page_token,json=nextPageToken" json:"next_page_token,omitempty"`
+}
+
+func (m *ListInstancesResponse) Reset()                    { *m = ListInstancesResponse{} }
+func (m *ListInstancesResponse) String() string            { return proto.CompactTextString(m) }
+func (*ListInstancesResponse) ProtoMessage()               {}
+func (*ListInstancesResponse) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{8} }
+
+func (m *ListInstancesResponse) GetInstances() []*Instance {
+	if m != nil {
+		return m.Instances
+	}
+	return nil
+}
+
+func (m *ListInstancesResponse) GetNextPageToken() string {
+	if m != nil {
+		return m.NextPageToken
+	}
+	return ""
+}
+
+// The request for [UpdateInstance][google.spanner.admin.instance.v1.InstanceAdmin.UpdateInstance].
+type UpdateInstanceRequest struct {
+	// Required. The instance to update, which must always include the instance
+	// name.  Otherwise, only fields mentioned in [][google.spanner.admin.instance.v1.UpdateInstanceRequest.field_mask] need be included.
+	Instance *Instance `protobuf:"bytes,1,opt,name=instance" json:"instance,omitempty"`
+	// Required. A mask specifying which fields in [][google.spanner.admin.instance.v1.UpdateInstanceRequest.instance] should be updated.
+	// The field mask must always be specified; this prevents any future fields in
+	// [][google.spanner.admin.instance.v1.Instance] from being erased accidentally by clients that do not know
+	// about them.
+	FieldMask *google_protobuf3.FieldMask `protobuf:"bytes,2,opt,name=field_mask,json=fieldMask" json:"field_mask,omitempty"`
+}
+
+func (m *UpdateInstanceRequest) Reset()                    { *m = UpdateInstanceRequest{} }
+func (m *UpdateInstanceRequest) String() string            { return proto.CompactTextString(m) }
+func (*UpdateInstanceRequest) ProtoMessage()               {}
+func (*UpdateInstanceRequest) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{9} }
+
+func (m *UpdateInstanceRequest) GetInstance() *Instance {
+	if m != nil {
+		return m.Instance
+	}
+	return nil
+}
+
+func (m *UpdateInstanceRequest) GetFieldMask() *google_protobuf3.FieldMask {
+	if m != nil {
+		return m.FieldMask
+	}
+	return nil
+}
+
+// The request for [DeleteInstance][google.spanner.admin.instance.v1.InstanceAdmin.DeleteInstance].
+type DeleteInstanceRequest struct {
+	// Required. The name of the instance to be deleted. Values are of the form
+	// `projects/<project>/instances/<instance>`
+	Name string `protobuf:"bytes,1,opt,name=name" json:"name,omitempty"`
+}
+
+func (m *DeleteInstanceRequest) Reset()                    { *m = DeleteInstanceRequest{} }
+func (m *DeleteInstanceRequest) String() string            { return proto.CompactTextString(m) }
+func (*DeleteInstanceRequest) ProtoMessage()               {}
+func (*DeleteInstanceRequest) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{10} }
+
+func (m *DeleteInstanceRequest) GetName() string {
+	if m != nil {
+		return m.Name
+	}
+	return ""
+}
+
+// Metadata type for the operation returned by
+// [CreateInstance][google.spanner.admin.instance.v1.InstanceAdmin.CreateInstance].
+type CreateInstanceMetadata struct {
+	// The instance being created.
+	Instance *Instance `protobuf:"bytes,1,opt,name=instance" json:"instance,omitempty"`
+	// The time at which the
+	// [CreateInstance][google.spanner.admin.instance.v1.InstanceAdmin.CreateInstance] request was
+	// received.
+	StartTime *google_protobuf4.Timestamp `protobuf:"bytes,2,opt,name=start_time,json=startTime" json:"start_time,omitempty"`
+	// The time at which this operation was cancelled. If set, this operation is
+	// in the process of undoing itself (which is guaranteed to succeed) and
+	// cannot be cancelled again.
+	CancelTime *google_protobuf4.Timestamp `protobuf:"bytes,3,opt,name=cancel_time,json=cancelTime" json:"cancel_time,omitempty"`
+	// The time at which this operation failed or was completed successfully.
+	EndTime *google_protobuf4.Timestamp `protobuf:"bytes,4,opt,name=end_time,json=endTime" json:"end_time,omitempty"`
+}
+
+func (m *CreateInstanceMetadata) Reset()                    { *m = CreateInstanceMetadata{} }
+func (m *CreateInstanceMetadata) String() string            { return proto.CompactTextString(m) }
+func (*CreateInstanceMetadata) ProtoMessage()               {}
+func (*CreateInstanceMetadata) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{11} }
+
+func (m *CreateInstanceMetadata) GetInstance() *Instance {
+	if m != nil {
+		return m.Instance
+	}
+	return nil
+}
+
+func (m *CreateInstanceMetadata) GetStartTime() *google_protobuf4.Timestamp {
+	if m != nil {
+		return m.StartTime
+	}
+	return nil
+}
+
+func (m *CreateInstanceMetadata) GetCancelTime() *google_protobuf4.Timestamp {
+	if m != nil {
+		return m.CancelTime
+	}
+	return nil
+}
+
+func (m *CreateInstanceMetadata) GetEndTime() *google_protobuf4.Timestamp {
+	if m != nil {
+		return m.EndTime
+	}
+	return nil
+}
+
+// Metadata type for the operation returned by
+// [UpdateInstance][google.spanner.admin.instance.v1.InstanceAdmin.UpdateInstance].
+type UpdateInstanceMetadata struct {
+	// The desired end state of the update.
+	Instance *Instance `protobuf:"bytes,1,opt,name=instance" json:"instance,omitempty"`
+	// The time at which [UpdateInstance][google.spanner.admin.instance.v1.InstanceAdmin.UpdateInstance]
+	// request was received.
+	StartTime *google_protobuf4.Timestamp `protobuf:"bytes,2,opt,name=start_time,json=startTime" json:"start_time,omitempty"`
+	// The time at which this operation was cancelled. If set, this operation is
+	// in the process of undoing itself (which is guaranteed to succeed) and
+	// cannot be cancelled again.
+	CancelTime *google_protobuf4.Timestamp `protobuf:"bytes,3,opt,name=cancel_time,json=cancelTime" json:"cancel_time,omitempty"`
+	// The time at which this operation failed or was completed successfully.
+	EndTime *google_protobuf4.Timestamp `protobuf:"bytes,4,opt,name=end_time,json=endTime" json:"end_time,omitempty"`
+}
+
+func (m *UpdateInstanceMetadata) Reset()                    { *m = UpdateInstanceMetadata{} }
+func (m *UpdateInstanceMetadata) String() string            { return proto.CompactTextString(m) }
+func (*UpdateInstanceMetadata) ProtoMessage()               {}
+func (*UpdateInstanceMetadata) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{12} }
+
+func (m *UpdateInstanceMetadata) GetInstance() *Instance {
+	if m != nil {
+		return m.Instance
+	}
+	return nil
+}
+
+func (m *UpdateInstanceMetadata) GetStartTime() *google_protobuf4.Timestamp {
+	if m != nil {
+		return m.StartTime
+	}
+	return nil
+}
+
+func (m *UpdateInstanceMetadata) GetCancelTime() *google_protobuf4.Timestamp {
+	if m != nil {
+		return m.CancelTime
+	}
+	return nil
+}
+
+func (m *UpdateInstanceMetadata) GetEndTime() *google_protobuf4.Timestamp {
+	if m != nil {
+		return m.EndTime
+	}
+	return nil
+}
+
+func init() {
+	proto.RegisterType((*InstanceConfig)(nil), "google.spanner.admin.instance.v1.InstanceConfig")
+	proto.RegisterType((*Instance)(nil), "google.spanner.admin.instance.v1.Instance")
+	proto.RegisterType((*ListInstanceConfigsRequest)(nil), "google.spanner.admin.instance.v1.ListInstanceConfigsRequest")
+	proto.RegisterType((*ListInstanceConfigsResponse)(nil), "google.spanner.admin.instance.v1.ListInstanceConfigsResponse")
+	proto.RegisterType((*GetInstanceConfigRequest)(nil), "google.spanner.admin.instance.v1.GetInstanceConfigRequest")
+	proto.RegisterType((*GetInstanceRequest)(nil), "google.spanner.admin.instance.v1.GetInstanceRequest")
+	proto.RegisterType((*CreateInstanceRequest)(nil), "google.spanner.admin.instance.v1.CreateInstanceRequest")
+	proto.RegisterType((*ListInstancesRequest)(nil), "google.spanner.admin.instance.v1.ListInstancesRequest")
+	proto.RegisterType((*ListInstancesResponse)(nil), "google.spanner.admin.instance.v1.ListInstancesResponse")
+	proto.RegisterType((*UpdateInstanceRequest)(nil), "google.spanner.admin.instance.v1.UpdateInstanceRequest")
+	proto.RegisterType((*DeleteInstanceRequest)(nil), "google.spanner.admin.instance.v1.DeleteInstanceRequest")
+	proto.RegisterType((*CreateInstanceMetadata)(nil), "google.spanner.admin.instance.v1.CreateInstanceMetadata")
+	proto.RegisterType((*UpdateInstanceMetadata)(nil), "google.spanner.admin.instance.v1.UpdateInstanceMetadata")
+	proto.RegisterEnum("google.spanner.admin.instance.v1.Instance_State", Instance_State_name, Instance_State_value)
+}
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ context.Context
+var _ grpc.ClientConn
+
+// This is a compile-time assertion to ensure that this generated file
+// is compatible with the grpc package it is being compiled against.
+const _ = grpc.SupportPackageIsVersion4
+
+// Client API for InstanceAdmin service
+
+type InstanceAdminClient interface {
+	// Lists the supported instance configurations for a given project.
+	ListInstanceConfigs(ctx context.Context, in *ListInstanceConfigsRequest, opts ...grpc.CallOption) (*ListInstanceConfigsResponse, error)
+	// Gets information about a particular instance configuration.
+	GetInstanceConfig(ctx context.Context, in *GetInstanceConfigRequest, opts ...grpc.CallOption) (*InstanceConfig, error)
+	// Lists all instances in the given project.
+	ListInstances(ctx context.Context, in *ListInstancesRequest, opts ...grpc.CallOption) (*ListInstancesResponse, error)
+	// Gets information about a particular instance.
+	GetInstance(ctx context.Context, in *GetInstanceRequest, opts ...grpc.CallOption) (*Instance, error)
+	// Creates an instance and begins preparing it to begin serving. The
+	// returned [long-running operation][google.longrunning.Operation]
+	// can be used to track the progress of preparing the new
+	// instance. The instance name is assigned by the caller. If the
+	// named instance already exists, `CreateInstance` returns
+	// `ALREADY_EXISTS`.
+	//
+	// Immediately upon completion of this request:
+	//
+	//   * The instance is readable via the API, with all requested attributes
+	//     but no allocated resources. Its state is `CREATING`.
+	//
+	// Until completion of the returned operation:
+	//
+	//   * Cancelling the operation renders the instance immediately unreadable
+	//     via the API.
+	//   * The instance can be deleted.
+	//   * All other attempts to modify the instance are rejected.
+	//
+	// Upon completion of the returned operation:
+	//
+	//   * Billing for all successfully-allocated resources begins (some types
+	//     may have lower than the requested levels).
+	//   * Databases can be created in the instance.
+	//   * The instance's allocated resource levels are readable via the API.
+	//   * The instance's state becomes `READY`.
+	//
+	// The returned [long-running operation][google.longrunning.Operation] will
+	// have a name of the format `<instance_name>/operations/<operation_id>` and
+	// can be used to track creation of the instance.  The
+	// [metadata][google.longrunning.Operation.metadata] field type is
+	// [CreateInstanceMetadata][google.spanner.admin.instance.v1.CreateInstanceMetadata].
+	// The [response][google.longrunning.Operation.response] field type is
+	// [Instance][google.spanner.admin.instance.v1.Instance], if successful.
+	CreateInstance(ctx context.Context, in *CreateInstanceRequest, opts ...grpc.CallOption) (*google_longrunning.Operation, error)
+	// Updates an instance, and begins allocating or releasing resources
+	// as requested. The returned [long-running
+	// operation][google.longrunning.Operation] can be used to track the
+	// progress of updating the instance. If the named instance does not
+	// exist, returns `NOT_FOUND`.
+	//
+	// Immediately upon completion of this request:
+	//
+	//   * For resource types for which a decrease in the instance's allocation
+	//     has been requested, billing is based on the newly-requested level.
+	//
+	// Until completion of the returned operation:
+	//
+	//   * Cancelling the operation sets its metadata's
+	//     [cancel_time][google.spanner.admin.instance.v1.UpdateInstanceMetadata.cancel_time], and begins
+	//     restoring resources to their pre-request values. The operation
+	//     is guaranteed to succeed at undoing all resource changes,
+	//     after which point it terminates with a `CANCELLED` status.
+	//   * All other attempts to modify the instance are rejected.
+	//   * Reading the instance via the API continues to give the pre-request
+	//     resource levels.
+	//
+	// Upon completion of the returned operation:
+	//
+	//   * Billing begins for all successfully-allocated resources (some types
+	//     may have lower than the requested levels).
+	//   * All newly-reserved resources are available for serving the instance's
+	//     tables.
+	//   * The instance's new resource levels are readable via the API.
+	//
+	// The returned [long-running operation][google.longrunning.Operation] will
+	// have a name of the format `<instance_name>/operations/<operation_id>` and
+	// can be used to track the instance modification.  The
+	// [metadata][google.longrunning.Operation.metadata] field type is
+	// [UpdateInstanceMetadata][google.spanner.admin.instance.v1.UpdateInstanceMetadata].
+	// The [response][google.longrunning.Operation.response] field type is
+	// [Instance][google.spanner.admin.instance.v1.Instance], if successful.
+	//
+	// Authorization requires `spanner.instances.update` permission on
+	// resource [name][google.spanner.admin.instance.v1.Instance.name].
+	UpdateInstance(ctx context.Context, in *UpdateInstanceRequest, opts ...grpc.CallOption) (*google_longrunning.Operation, error)
+	// Deletes an instance.
+	//
+	// Immediately upon completion of the request:
+	//
+	//   * Billing ceases for all of the instance's reserved resources.
+	//
+	// Soon afterward:
+	//
+	//   * The instance and *all of its databases* immediately and
+	//     irrevocably disappear from the API. All data in the databases
+	//     is permanently deleted.
+	DeleteInstance(ctx context.Context, in *DeleteInstanceRequest, opts ...grpc.CallOption) (*google_protobuf2.Empty, error)
+	// Sets the access control policy on an instance resource. Replaces any
+	// existing policy.
+	//
+	// Authorization requires `spanner.instances.setIamPolicy` on
+	// [resource][google.iam.v1.SetIamPolicyRequest.resource].
+	SetIamPolicy(ctx context.Context, in *google_iam_v11.SetIamPolicyRequest, opts ...grpc.CallOption) (*google_iam_v1.Policy, error)
+	// Gets the access control policy for an instance resource. Returns an empty
+	// policy if an instance exists but does not have a policy set.
+	//
+	// Authorization requires `spanner.instances.getIamPolicy` on
+	// [resource][google.iam.v1.GetIamPolicyRequest.resource].
+	GetIamPolicy(ctx context.Context, in *google_iam_v11.GetIamPolicyRequest, opts ...grpc.CallOption) (*google_iam_v1.Policy, error)
+	// Returns permissions that the caller has on the specified instance resource.
+	//
+	// Attempting this RPC on a non-existent Cloud Spanner instance resource will
+	// result in a NOT_FOUND error if the user has `spanner.instances.list`
+	// permission on the containing Google Cloud Project. Otherwise returns an
+	// empty set of permissions.
+	TestIamPermissions(ctx context.Context, in *google_iam_v11.TestIamPermissionsRequest, opts ...grpc.CallOption) (*google_iam_v11.TestIamPermissionsResponse, error)
+}
+
+type instanceAdminClient struct {
+	cc *grpc.ClientConn
+}
+
+func NewInstanceAdminClient(cc *grpc.ClientConn) InstanceAdminClient {
+	return &instanceAdminClient{cc}
+}
+
+func (c *instanceAdminClient) ListInstanceConfigs(ctx context.Context, in *ListInstanceConfigsRequest, opts ...grpc.CallOption) (*ListInstanceConfigsResponse, error) {
+	out := new(ListInstanceConfigsResponse)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.instance.v1.InstanceAdmin/ListInstanceConfigs", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *instanceAdminClient) GetInstanceConfig(ctx context.Context, in *GetInstanceConfigRequest, opts ...grpc.CallOption) (*InstanceConfig, error) {
+	out := new(InstanceConfig)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.instance.v1.InstanceAdmin/GetInstanceConfig", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *instanceAdminClient) ListInstances(ctx context.Context, in *ListInstancesRequest, opts ...grpc.CallOption) (*ListInstancesResponse, error) {
+	out := new(ListInstancesResponse)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.instance.v1.InstanceAdmin/ListInstances", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *instanceAdminClient) GetInstance(ctx context.Context, in *GetInstanceRequest, opts ...grpc.CallOption) (*Instance, error) {
+	out := new(Instance)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.instance.v1.InstanceAdmin/GetInstance", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *instanceAdminClient) CreateInstance(ctx context.Context, in *CreateInstanceRequest, opts ...grpc.CallOption) (*google_longrunning.Operation, error) {
+	out := new(google_longrunning.Operation)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.instance.v1.InstanceAdmin/CreateInstance", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *instanceAdminClient) UpdateInstance(ctx context.Context, in *UpdateInstanceRequest, opts ...grpc.CallOption) (*google_longrunning.Operation, error) {
+	out := new(google_longrunning.Operation)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.instance.v1.InstanceAdmin/UpdateInstance", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *instanceAdminClient) DeleteInstance(ctx context.Context, in *DeleteInstanceRequest, opts ...grpc.CallOption) (*google_protobuf2.Empty, error) {
+	out := new(google_protobuf2.Empty)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.instance.v1.InstanceAdmin/DeleteInstance", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *instanceAdminClient) SetIamPolicy(ctx context.Context, in *google_iam_v11.SetIamPolicyRequest, opts ...grpc.CallOption) (*google_iam_v1.Policy, error) {
+	out := new(google_iam_v1.Policy)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.instance.v1.InstanceAdmin/SetIamPolicy", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *instanceAdminClient) GetIamPolicy(ctx context.Context, in *google_iam_v11.GetIamPolicyRequest, opts ...grpc.CallOption) (*google_iam_v1.Policy, error) {
+	out := new(google_iam_v1.Policy)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.instance.v1.InstanceAdmin/GetIamPolicy", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *instanceAdminClient) TestIamPermissions(ctx context.Context, in *google_iam_v11.TestIamPermissionsRequest, opts ...grpc.CallOption) (*google_iam_v11.TestIamPermissionsResponse, error) {
+	out := new(google_iam_v11.TestIamPermissionsResponse)
+	err := grpc.Invoke(ctx, "/google.spanner.admin.instance.v1.InstanceAdmin/TestIamPermissions", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+// Server API for InstanceAdmin service
+
+type InstanceAdminServer interface {
+	// Lists the supported instance configurations for a given project.
+	ListInstanceConfigs(context.Context, *ListInstanceConfigsRequest) (*ListInstanceConfigsResponse, error)
+	// Gets information about a particular instance configuration.
+	GetInstanceConfig(context.Context, *GetInstanceConfigRequest) (*InstanceConfig, error)
+	// Lists all instances in the given project.
+	ListInstances(context.Context, *ListInstancesRequest) (*ListInstancesResponse, error)
+	// Gets information about a particular instance.
+	GetInstance(context.Context, *GetInstanceRequest) (*Instance, error)
+	// Creates an instance and begins preparing it to begin serving. The
+	// returned [long-running operation][google.longrunning.Operation]
+	// can be used to track the progress of preparing the new
+	// instance. The instance name is assigned by the caller. If the
+	// named instance already exists, `CreateInstance` returns
+	// `ALREADY_EXISTS`.
+	//
+	// Immediately upon completion of this request:
+	//
+	//   * The instance is readable via the API, with all requested attributes
+	//     but no allocated resources. Its state is `CREATING`.
+	//
+	// Until completion of the returned operation:
+	//
+	//   * Cancelling the operation renders the instance immediately unreadable
+	//     via the API.
+	//   * The instance can be deleted.
+	//   * All other attempts to modify the instance are rejected.
+	//
+	// Upon completion of the returned operation:
+	//
+	//   * Billing for all successfully-allocated resources begins (some types
+	//     may have lower than the requested levels).
+	//   * Databases can be created in the instance.
+	//   * The instance's allocated resource levels are readable via the API.
+	//   * The instance's state becomes `READY`.
+	//
+	// The returned [long-running operation][google.longrunning.Operation] will
+	// have a name of the format `<instance_name>/operations/<operation_id>` and
+	// can be used to track creation of the instance.  The
+	// [metadata][google.longrunning.Operation.metadata] field type is
+	// [CreateInstanceMetadata][google.spanner.admin.instance.v1.CreateInstanceMetadata].
+	// The [response][google.longrunning.Operation.response] field type is
+	// [Instance][google.spanner.admin.instance.v1.Instance], if successful.
+	CreateInstance(context.Context, *CreateInstanceRequest) (*google_longrunning.Operation, error)
+	// Updates an instance, and begins allocating or releasing resources
+	// as requested. The returned [long-running
+	// operation][google.longrunning.Operation] can be used to track the
+	// progress of updating the instance. If the named instance does not
+	// exist, returns `NOT_FOUND`.
+	//
+	// Immediately upon completion of this request:
+	//
+	//   * For resource types for which a decrease in the instance's allocation
+	//     has been requested, billing is based on the newly-requested level.
+	//
+	// Until completion of the returned operation:
+	//
+	//   * Cancelling the operation sets its metadata's
+	//     [cancel_time][google.spanner.admin.instance.v1.UpdateInstanceMetadata.cancel_time], and begins
+	//     restoring resources to their pre-request values. The operation
+	//     is guaranteed to succeed at undoing all resource changes,
+	//     after which point it terminates with a `CANCELLED` status.
+	//   * All other attempts to modify the instance are rejected.
+	//   * Reading the instance via the API continues to give the pre-request
+	//     resource levels.
+	//
+	// Upon completion of the returned operation:
+	//
+	//   * Billing begins for all successfully-allocated resources (some types
+	//     may have lower than the requested levels).
+	//   * All newly-reserved resources are available for serving the instance's
+	//     tables.
+	//   * The instance's new resource levels are readable via the API.
+	//
+	// The returned [long-running operation][google.longrunning.Operation] will
+	// have a name of the format `<instance_name>/operations/<operation_id>` and
+	// can be used to track the instance modification.  The
+	// [metadata][google.longrunning.Operation.metadata] field type is
+	// [UpdateInstanceMetadata][google.spanner.admin.instance.v1.UpdateInstanceMetadata].
+	// The [response][google.longrunning.Operation.response] field type is
+	// [Instance][google.spanner.admin.instance.v1.Instance], if successful.
+	//
+	// Authorization requires `spanner.instances.update` permission on
+	// resource [name][google.spanner.admin.instance.v1.Instance.name].
+	UpdateInstance(context.Context, *UpdateInstanceRequest) (*google_longrunning.Operation, error)
+	// Deletes an instance.
+	//
+	// Immediately upon completion of the request:
+	//
+	//   * Billing ceases for all of the instance's reserved resources.
+	//
+	// Soon afterward:
+	//
+	//   * The instance and *all of its databases* immediately and
+	//     irrevocably disappear from the API. All data in the databases
+	//     is permanently deleted.
+	DeleteInstance(context.Context, *DeleteInstanceRequest) (*google_protobuf2.Empty, error)
+	// Sets the access control policy on an instance resource. Replaces any
+	// existing policy.
+	//
+	// Authorization requires `spanner.instances.setIamPolicy` on
+	// [resource][google.iam.v1.SetIamPolicyRequest.resource].
+	SetIamPolicy(context.Context, *google_iam_v11.SetIamPolicyRequest) (*google_iam_v1.Policy, error)
+	// Gets the access control policy for an instance resource. Returns an empty
+	// policy if an instance exists but does not have a policy set.
+	//
+	// Authorization requires `spanner.instances.getIamPolicy` on
+	// [resource][google.iam.v1.GetIamPolicyRequest.resource].
+	GetIamPolicy(context.Context, *google_iam_v11.GetIamPolicyRequest) (*google_iam_v1.Policy, error)
+	// Returns permissions that the caller has on the specified instance resource.
+	//
+	// Attempting this RPC on a non-existent Cloud Spanner instance resource will
+	// result in a NOT_FOUND error if the user has `spanner.instances.list`
+	// permission on the containing Google Cloud Project. Otherwise returns an
+	// empty set of permissions.
+	TestIamPermissions(context.Context, *google_iam_v11.TestIamPermissionsRequest) (*google_iam_v11.TestIamPermissionsResponse, error)
+}
+
+func RegisterInstanceAdminServer(s *grpc.Server, srv InstanceAdminServer) {
+	s.RegisterService(&_InstanceAdmin_serviceDesc, srv)
+}
+
+func _InstanceAdmin_ListInstanceConfigs_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(ListInstanceConfigsRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(InstanceAdminServer).ListInstanceConfigs(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.instance.v1.InstanceAdmin/ListInstanceConfigs",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(InstanceAdminServer).ListInstanceConfigs(ctx, req.(*ListInstanceConfigsRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _InstanceAdmin_GetInstanceConfig_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(GetInstanceConfigRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(InstanceAdminServer).GetInstanceConfig(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.instance.v1.InstanceAdmin/GetInstanceConfig",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(InstanceAdminServer).GetInstanceConfig(ctx, req.(*GetInstanceConfigRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _InstanceAdmin_ListInstances_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(ListInstancesRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(InstanceAdminServer).ListInstances(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.instance.v1.InstanceAdmin/ListInstances",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(InstanceAdminServer).ListInstances(ctx, req.(*ListInstancesRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _InstanceAdmin_GetInstance_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(GetInstanceRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(InstanceAdminServer).GetInstance(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.instance.v1.InstanceAdmin/GetInstance",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(InstanceAdminServer).GetInstance(ctx, req.(*GetInstanceRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _InstanceAdmin_CreateInstance_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(CreateInstanceRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(InstanceAdminServer).CreateInstance(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.instance.v1.InstanceAdmin/CreateInstance",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(InstanceAdminServer).CreateInstance(ctx, req.(*CreateInstanceRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _InstanceAdmin_UpdateInstance_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(UpdateInstanceRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(InstanceAdminServer).UpdateInstance(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.instance.v1.InstanceAdmin/UpdateInstance",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(InstanceAdminServer).UpdateInstance(ctx, req.(*UpdateInstanceRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _InstanceAdmin_DeleteInstance_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(DeleteInstanceRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(InstanceAdminServer).DeleteInstance(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.instance.v1.InstanceAdmin/DeleteInstance",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(InstanceAdminServer).DeleteInstance(ctx, req.(*DeleteInstanceRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _InstanceAdmin_SetIamPolicy_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(google_iam_v11.SetIamPolicyRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(InstanceAdminServer).SetIamPolicy(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.instance.v1.InstanceAdmin/SetIamPolicy",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(InstanceAdminServer).SetIamPolicy(ctx, req.(*google_iam_v11.SetIamPolicyRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _InstanceAdmin_GetIamPolicy_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(google_iam_v11.GetIamPolicyRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(InstanceAdminServer).GetIamPolicy(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.instance.v1.InstanceAdmin/GetIamPolicy",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(InstanceAdminServer).GetIamPolicy(ctx, req.(*google_iam_v11.GetIamPolicyRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _InstanceAdmin_TestIamPermissions_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(google_iam_v11.TestIamPermissionsRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(InstanceAdminServer).TestIamPermissions(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.admin.instance.v1.InstanceAdmin/TestIamPermissions",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(InstanceAdminServer).TestIamPermissions(ctx, req.(*google_iam_v11.TestIamPermissionsRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+var _InstanceAdmin_serviceDesc = grpc.ServiceDesc{
+	ServiceName: "google.spanner.admin.instance.v1.InstanceAdmin",
+	HandlerType: (*InstanceAdminServer)(nil),
+	Methods: []grpc.MethodDesc{
+		{
+			MethodName: "ListInstanceConfigs",
+			Handler:    _InstanceAdmin_ListInstanceConfigs_Handler,
+		},
+		{
+			MethodName: "GetInstanceConfig",
+			Handler:    _InstanceAdmin_GetInstanceConfig_Handler,
+		},
+		{
+			MethodName: "ListInstances",
+			Handler:    _InstanceAdmin_ListInstances_Handler,
+		},
+		{
+			MethodName: "GetInstance",
+			Handler:    _InstanceAdmin_GetInstance_Handler,
+		},
+		{
+			MethodName: "CreateInstance",
+			Handler:    _InstanceAdmin_CreateInstance_Handler,
+		},
+		{
+			MethodName: "UpdateInstance",
+			Handler:    _InstanceAdmin_UpdateInstance_Handler,
+		},
+		{
+			MethodName: "DeleteInstance",
+			Handler:    _InstanceAdmin_DeleteInstance_Handler,
+		},
+		{
+			MethodName: "SetIamPolicy",
+			Handler:    _InstanceAdmin_SetIamPolicy_Handler,
+		},
+		{
+			MethodName: "GetIamPolicy",
+			Handler:    _InstanceAdmin_GetIamPolicy_Handler,
+		},
+		{
+			MethodName: "TestIamPermissions",
+			Handler:    _InstanceAdmin_TestIamPermissions_Handler,
+		},
+	},
+	Streams:  []grpc.StreamDesc{},
+	Metadata: "google/spanner/admin/instance/v1/spanner_instance_admin.proto",
+}
+
+func init() {
+	proto.RegisterFile("google/spanner/admin/instance/v1/spanner_instance_admin.proto", fileDescriptor0)
+}
+
+var fileDescriptor0 = []byte{
+	// 1176 bytes of a gzipped FileDescriptorProto
+	0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xe4, 0x57, 0xcf, 0x6f, 0x1b, 0xc5,
+	0x17, 0xff, 0x4e, 0x52, 0xa7, 0xf1, 0x73, 0x9a, 0xa6, 0xf3, 0xad, 0x23, 0xe3, 0x50, 0xea, 0x6e,
+	0x51, 0x71, 0x0c, 0xf2, 0x52, 0x43, 0x9b, 0x36, 0x25, 0x87, 0xd4, 0x71, 0x52, 0x4b, 0x6d, 0x88,
+	0xd6, 0xee, 0x01, 0x38, 0x58, 0x13, 0x7b, 0x62, 0x96, 0xec, 0xce, 0x2e, 0x3b, 0xe3, 0x88, 0x14,
+	0xf5, 0x52, 0x71, 0x00, 0x09, 0xc4, 0x01, 0x09, 0xa1, 0x5e, 0x90, 0xb8, 0x22, 0x71, 0xe0, 0x5f,
+	0xe0, 0x4f, 0xe0, 0x5f, 0x40, 0xfc, 0x1d, 0x68, 0x66, 0x77, 0x5c, 0xef, 0xda, 0x8e, 0xed, 0x8a,
+	0x9e, 0xb8, 0xed, 0xbc, 0x9f, 0x9f, 0xf9, 0xbc, 0xb7, 0xef, 0xed, 0xc2, 0x56, 0xd7, 0xf3, 0xba,
+	0x0e, 0x35, 0xb9, 0x4f, 0x18, 0xa3, 0x81, 0x49, 0x3a, 0xae, 0xcd, 0x4c, 0x9b, 0x71, 0x41, 0x58,
+	0x9b, 0x9a, 0x27, 0x37, 0xb5, 0xa6, 0xa5, 0x65, 0x2d, 0x65, 0x52, 0xf6, 0x03, 0x4f, 0x78, 0xb8,
+	0x10, 0xba, 0x97, 0x23, 0xa3, 0x72, 0xa8, 0xd3, 0xa6, 0xe5, 0x93, 0x9b, 0xf9, 0xd7, 0xa3, 0x04,
+	0xc4, 0xb7, 0x4d, 0xc2, 0x98, 0x27, 0x88, 0xb0, 0x3d, 0xc6, 0x43, 0xff, 0x7c, 0x76, 0x50, 0xdb,
+	0x13, 0x9f, 0x46, 0xe2, 0x37, 0x22, 0xb1, 0x4d, 0x5c, 0x09, 0xc1, 0x26, 0x6e, 0xcb, 0xf7, 0x1c,
+	0xbb, 0x7d, 0x1a, 0xe9, 0xf3, 0x71, 0x7d, 0x4c, 0x77, 0x3d, 0xd2, 0x39, 0x1e, 0xeb, 0x06, 0x3d,
+	0xc6, 0x6c, 0xd6, 0x35, 0x3d, 0x9f, 0x06, 0xb1, 0xbc, 0x6b, 0x91, 0x91, 0x3a, 0x1d, 0xf6, 0x8e,
+	0x4c, 0xea, 0xfa, 0x42, 0x47, 0x28, 0x24, 0x95, 0x47, 0x36, 0x75, 0x3a, 0x2d, 0x97, 0xf0, 0xe3,
+	0xc8, 0xe2, 0x6a, 0xd2, 0x42, 0xd8, 0x2e, 0xe5, 0x82, 0xb8, 0x7e, 0x68, 0x60, 0xec, 0xc1, 0x72,
+	0x3d, 0x22, 0xa1, 0xea, 0xb1, 0x23, 0xbb, 0x8b, 0x31, 0x9c, 0x63, 0xc4, 0xa5, 0x39, 0x54, 0x40,
+	0xc5, 0xb4, 0xa5, 0x9e, 0xf1, 0x35, 0x58, 0xea, 0xd8, 0xdc, 0x77, 0xc8, 0x69, 0x4b, 0xe9, 0xe6,
+	0x94, 0x2e, 0x13, 0xc9, 0xf6, 0x89, 0x4b, 0x8d, 0xaf, 0xe6, 0x61, 0x51, 0x47, 0x1a, 0x19, 0x63,
+	0x15, 0x16, 0xda, 0x2a, 0x43, 0xe4, 0x1d, 0x9d, 0x86, 0x62, 0xcf, 0x0f, 0xc5, 0xc6, 0x57, 0x00,
+	0x98, 0xd7, 0xa1, 0xad, 0xb6, 0xd7, 0x63, 0x22, 0x97, 0x2a, 0xa0, 0x62, 0xca, 0x4a, 0x4b, 0x49,
+	0x55, 0x0a, 0xf0, 0x2e, 0xa4, 0xb8, 0x20, 0x82, 0xe6, 0x16, 0x0a, 0xa8, 0xb8, 0x5c, 0x79, 0xb7,
+	0x3c, 0xa9, 0xd6, 0x65, 0x0d, 0xb4, 0xdc, 0x90, 0x7e, 0x56, 0xe8, 0x8e, 0xf7, 0x61, 0xc1, 0x21,
+	0x87, 0xd4, 0xe1, 0xb9, 0xf3, 0x85, 0xf9, 0x62, 0xa6, 0x72, 0x7b, 0x86, 0x40, 0x0f, 0x95, 0x63,
+	0x8d, 0x89, 0xe0, 0xd4, 0x8a, 0xa2, 0xe4, 0xef, 0x42, 0x66, 0x40, 0x8c, 0x57, 0x60, 0xfe, 0x98,
+	0x9e, 0x46, 0x9c, 0xc8, 0x47, 0x7c, 0x19, 0x52, 0x27, 0xc4, 0xe9, 0x69, 0x3e, 0xc3, 0xc3, 0xe6,
+	0xdc, 0x1d, 0x64, 0x6c, 0x40, 0x4a, 0x41, 0xc3, 0x59, 0xb8, 0xd4, 0x68, 0x6e, 0x37, 0x6b, 0xad,
+	0xc7, 0xfb, 0x8d, 0x83, 0x5a, 0xb5, 0xbe, 0x5b, 0xaf, 0xed, 0xac, 0xfc, 0x0f, 0x2f, 0xc1, 0x62,
+	0xd5, 0xaa, 0x6d, 0x37, 0xeb, 0xfb, 0x7b, 0x2b, 0x08, 0xa7, 0x21, 0x65, 0xd5, 0xb6, 0x77, 0x3e,
+	0x5a, 0x99, 0x33, 0x7c, 0xc8, 0x3f, 0xb4, 0xb9, 0x88, 0xd7, 0x94, 0x5b, 0xf4, 0xf3, 0x1e, 0xe5,
+	0x42, 0xd6, 0xc0, 0x27, 0x01, 0x65, 0x22, 0x42, 0x11, 0x9d, 0xf0, 0x1a, 0xa4, 0x7d, 0xd2, 0xa5,
+	0x2d, 0x6e, 0x3f, 0x09, 0xc1, 0xa4, 0xac, 0x45, 0x29, 0x68, 0xd8, 0x4f, 0x14, 0xfb, 0x4a, 0x29,
+	0xbc, 0x63, 0xca, 0xa2, 0xf2, 0x28, 0xf3, 0xa6, 0x14, 0x18, 0xbf, 0x20, 0x58, 0x1b, 0x99, 0x92,
+	0xfb, 0x1e, 0xe3, 0x14, 0x7f, 0x02, 0x2b, 0xfd, 0x37, 0x32, 0x2c, 0x39, 0xcf, 0x21, 0xc5, 0xef,
+	0x0c, 0x85, 0x0a, 0x83, 0x5a, 0x17, 0xed, 0x78, 0x12, 0x7c, 0x03, 0x2e, 0x32, 0xfa, 0x85, 0x68,
+	0x0d, 0x00, 0x0c, 0xb9, 0xbc, 0x20, 0xc5, 0x07, 0x7d, 0x90, 0x65, 0xc8, 0xed, 0xd1, 0x04, 0x44,
+	0x4d, 0xca, 0x88, 0x66, 0x35, 0x8a, 0x80, 0x07, 0xec, 0xcf, 0xb2, 0xfc, 0x09, 0x41, 0xb6, 0x1a,
+	0x50, 0x22, 0x68, 0xd2, 0x7a, 0x1c, 0xd9, 0x57, 0x21, 0xd3, 0x27, 0xc4, 0xee, 0x44, 0x78, 0x41,
+	0x8b, 0xea, 0x1d, 0xbc, 0x0b, 0x8b, 0xfa, 0xa4, 0xe8, 0xce, 0x54, 0x4a, 0xd3, 0x33, 0x65, 0xf5,
+	0x7d, 0x8d, 0x67, 0x08, 0x2e, 0x0f, 0x56, 0xe6, 0x55, 0xb6, 0x81, 0x8c, 0x79, 0x64, 0x3b, 0x82,
+	0x06, 0xb9, 0x73, 0x61, 0xcc, 0xf0, 0x64, 0x7c, 0x83, 0x20, 0x9b, 0x00, 0x11, 0x35, 0xc6, 0x03,
+	0x48, 0x6b, 0xa8, 0xba, 0x23, 0x66, 0xb9, 0xe7, 0x0b, 0xe7, 0xa9, 0xbb, 0xe0, 0x39, 0x82, 0xec,
+	0x63, 0xbf, 0x33, 0xa2, 0x56, 0x83, 0x94, 0xa3, 0x97, 0xa7, 0x1c, 0xdf, 0x05, 0x78, 0x31, 0x83,
+	0x15, 0x88, 0x4c, 0x25, 0xaf, 0x23, 0xe9, 0x21, 0x5c, 0xde, 0x95, 0x26, 0x8f, 0x08, 0x3f, 0xb6,
+	0xd2, 0x47, 0xfa, 0xd1, 0x78, 0x1b, 0xb2, 0x3b, 0xd4, 0xa1, 0xc3, 0xd8, 0x46, 0x75, 0xdd, 0xf7,
+	0x73, 0xb0, 0x1a, 0xef, 0xba, 0x47, 0x54, 0x90, 0x0e, 0x11, 0xe4, 0xdf, 0xbc, 0x0a, 0x17, 0x24,
+	0x10, 0x2d, 0xb9, 0x32, 0xc6, 0x5e, 0xa5, 0xa9, 0xf7, 0x89, 0x95, 0x56, 0xd6, 0xf2, 0x8c, 0xef,
+	0x41, 0xa6, 0x2d, 0x63, 0x38, 0xa1, 0xef, 0xfc, 0x44, 0x5f, 0x08, 0xcd, 0x95, 0xf3, 0x2d, 0x58,
+	0xa4, 0xac, 0x13, 0x7a, 0x9e, 0x9b, 0xe8, 0x79, 0x9e, 0xb2, 0x8e, 0x3c, 0x29, 0x46, 0xe2, 0xb5,
+	0xfd, 0x8f, 0x33, 0x52, 0xf9, 0x7b, 0x09, 0x2e, 0xe8, 0x5b, 0x6c, 0xcb, 0xfb, 0xe1, 0x3f, 0x10,
+	0xfc, 0x7f, 0xc4, 0xa8, 0xc6, 0x1f, 0x4c, 0xa6, 0x63, 0xfc, 0x52, 0xc9, 0x6f, 0xbd, 0xa4, 0x77,
+	0x38, 0x06, 0x0c, 0xf3, 0xd9, 0x9f, 0x7f, 0xfd, 0x30, 0xb7, 0x8e, 0xdf, 0x92, 0x1f, 0x48, 0x5f,
+	0x86, 0x93, 0x68, 0xcb, 0x0f, 0xbc, 0xcf, 0x68, 0x5b, 0x70, 0xb3, 0xf4, 0xd4, 0x4c, 0xce, 0xfc,
+	0xdf, 0x11, 0x5c, 0x1a, 0x1a, 0xe6, 0x78, 0x73, 0x32, 0x8a, 0x71, 0x1b, 0x20, 0x3f, 0xf3, 0x22,
+	0x4a, 0x80, 0x96, 0xaf, 0xe4, 0x00, 0xe4, 0x24, 0x62, 0xb3, 0xf4, 0x14, 0xff, 0x8a, 0xe0, 0x42,
+	0x6c, 0x0c, 0xe2, 0xdb, 0xb3, 0xd1, 0xd6, 0xa7, 0x7b, 0x63, 0x66, 0xbf, 0x88, 0xe8, 0x75, 0x85,
+	0xf9, 0x3a, 0xbe, 0x36, 0x89, 0x68, 0x8e, 0x9f, 0x23, 0xc8, 0x0c, 0xb0, 0x85, 0xdf, 0x9f, 0x89,
+	0x5c, 0x8d, 0x74, 0x86, 0xb7, 0x2c, 0x01, 0x6e, 0x1c, 0xa1, 0x8a, 0xca, 0x1f, 0x11, 0x2c, 0xc7,
+	0x67, 0x1f, 0x9e, 0x82, 0x93, 0x91, 0x3b, 0x3a, 0x7f, 0x45, 0x3b, 0x0e, 0x7c, 0x84, 0x97, 0x3f,
+	0xd4, 0x1f, 0xe1, 0xc6, 0x3b, 0x0a, 0xd5, 0x0d, 0x63, 0x32, 0x65, 0x9b, 0xa8, 0x84, 0x7f, 0x46,
+	0xb0, 0x1c, 0x1f, 0x41, 0xd3, 0x00, 0x1b, 0xb9, 0x90, 0x26, 0x01, 0xbb, 0xa5, 0x80, 0x99, 0x95,
+	0x92, 0x02, 0xd6, 0x0f, 0x77, 0x16, 0x6f, 0x12, 0xe1, 0xb7, 0x08, 0x96, 0xe3, 0x4b, 0x66, 0x1a,
+	0x84, 0x23, 0xd7, 0x52, 0x7e, 0x75, 0x68, 0x06, 0xd5, 0xe4, 0xaf, 0x89, 0xae, 0x64, 0x69, 0x8a,
+	0x4a, 0x7e, 0x8d, 0x60, 0xa9, 0x41, 0x45, 0x9d, 0xb8, 0x07, 0xea, 0xc7, 0x08, 0x1b, 0x3a, 0xa6,
+	0x4d, 0x5c, 0x99, 0x79, 0x50, 0xa9, 0xf3, 0x66, 0x13, 0x36, 0xa1, 0xd6, 0xd8, 0x52, 0x69, 0x37,
+	0x8c, 0x8a, 0x4a, 0x1b, 0x50, 0xee, 0xf5, 0x82, 0xf6, 0x78, 0x32, 0xf8, 0x40, 0x64, 0xc9, 0x8c,
+	0x84, 0xb2, 0x77, 0x16, 0x94, 0xbd, 0x57, 0x06, 0xa5, 0x9b, 0x80, 0xf2, 0x1b, 0x02, 0xdc, 0xa4,
+	0x5c, 0x09, 0x69, 0xe0, 0xda, 0x9c, 0xcb, 0xff, 0x41, 0x5c, 0x4c, 0x24, 0x1b, 0x36, 0xd1, 0xb0,
+	0xd6, 0xa7, 0xb0, 0x8c, 0x66, 0x42, 0x55, 0x41, 0xdd, 0x32, 0xee, 0x4c, 0x07, 0x55, 0x0c, 0x45,
+	0xda, 0x44, 0xa5, 0xfb, 0xdf, 0x21, 0x78, 0xb3, 0xed, 0xb9, 0x13, 0x1b, 0xe9, 0xfe, 0x6b, 0x8d,
+	0x50, 0x15, 0xdb, 0x4a, 0x07, 0xb2, 0x7d, 0x0e, 0xd0, 0xc7, 0x0f, 0x22, 0xf7, 0xae, 0xe7, 0x10,
+	0xd6, 0x2d, 0x7b, 0x41, 0xd7, 0xec, 0x52, 0xa6, 0x9a, 0xcb, 0x0c, 0x55, 0xc4, 0xb7, 0xf9, 0xf8,
+	0xff, 0xff, 0x7b, 0xfa, 0xf9, 0x70, 0x41, 0x39, 0xbd, 0xf7, 0x4f, 0x00, 0x00, 0x00, 0xff, 0xff,
+	0x22, 0x58, 0xb5, 0xfa, 0x33, 0x10, 0x00, 0x00,
+}
diff --git a/googleapis/spanner/v1/keys.pb.go b/googleapis/spanner/v1/keys.pb.go
new file mode 100644
index 00000000..8544b317
--- /dev/null
+++ b/googleapis/spanner/v1/keys.pb.go
@@ -0,0 +1,438 @@
+// Code generated by protoc-gen-go.
+// source: google/spanner/v1/keys.proto
+// DO NOT EDIT!
+
+/*
+Package spanner is a generated protocol buffer package.
+
+It is generated from these files:
+	google/spanner/v1/keys.proto
+	google/spanner/v1/mutation.proto
+	google/spanner/v1/query_plan.proto
+	google/spanner/v1/result_set.proto
+	google/spanner/v1/spanner.proto
+	google/spanner/v1/transaction.proto
+	google/spanner/v1/type.proto
+
+It has these top-level messages:
+	KeyRange
+	KeySet
+	Mutation
+	PlanNode
+	QueryPlan
+	ResultSet
+	PartialResultSet
+	ResultSetMetadata
+	ResultSetStats
+	CreateSessionRequest
+	Session
+	GetSessionRequest
+	DeleteSessionRequest
+	ExecuteSqlRequest
+	ReadRequest
+	BeginTransactionRequest
+	CommitRequest
+	CommitResponse
+	RollbackRequest
+	TransactionOptions
+	Transaction
+	TransactionSelector
+	Type
+	StructType
+*/
+package spanner
+
+import proto "github.com/golang/protobuf/proto"
+import fmt "fmt"
+import math "math"
+import _ "google.golang.org/genproto/googleapis/api/annotations"
+import google_protobuf1 "github.com/golang/protobuf/ptypes/struct"
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ = proto.Marshal
+var _ = fmt.Errorf
+var _ = math.Inf
+
+// This is a compile-time assertion to ensure that this generated file
+// is compatible with the proto package it is being compiled against.
+// A compilation error at this line likely means your copy of the
+// proto package needs to be updated.
+const _ = proto.ProtoPackageIsVersion2 // please upgrade the proto package
+
+// KeyRange represents a range of rows in a table or index.
+//
+// A range has a start key and an end key. These keys can be open or
+// closed, indicating if the range includes rows with that key.
+//
+// Keys are represented by lists, where the ith value in the list
+// corresponds to the ith component of the table or index primary key.
+// Individual values are encoded as described [here][google.spanner.v1.TypeCode].
+//
+// For example, consider the following table definition:
+//
+//     CREATE TABLE UserEvents (
+//       UserName STRING(MAX),
+//       EventDate STRING(10)
+//     ) PRIMARY KEY(UserName, EventDate);
+//
+// The following keys name rows in this table:
+//
+//     ["Bob", "2014-09-23"]
+//     ["Alfred", "2015-06-12"]
+//
+// Since the `UserEvents` table's `PRIMARY KEY` clause names two
+// columns, each `UserEvents` key has two elements; the first is the
+// `UserName`, and the second is the `EventDate`.
+//
+// Key ranges with multiple components are interpreted
+// lexicographically by component using the table or index key's declared
+// sort order. For example, the following range returns all events for
+// user `"Bob"` that occurred in the year 2015:
+//
+//     "start_closed": ["Bob", "2015-01-01"]
+//     "end_closed": ["Bob", "2015-12-31"]
+//
+// Start and end keys can omit trailing key components. This affects the
+// inclusion and exclusion of rows that exactly match the provided key
+// components: if the key is closed, then rows that exactly match the
+// provided components are included; if the key is open, then rows
+// that exactly match are not included.
+//
+// For example, the following range includes all events for `"Bob"` that
+// occurred during and after the year 2000:
+//
+//     "start_closed": ["Bob", "2000-01-01"]
+//     "end_closed": ["Bob"]
+//
+// The next example retrieves all events for `"Bob"`:
+//
+//     "start_closed": ["Bob"]
+//     "end_closed": ["Bob"]
+//
+// To retrieve events before the year 2000:
+//
+//     "start_closed": ["Bob"]
+//     "end_open": ["Bob", "2000-01-01"]
+//
+// The following range includes all rows in the table:
+//
+//     "start_closed": []
+//     "end_closed": []
+//
+// This range returns all users whose `UserName` begins with any
+// character from A to C:
+//
+//     "start_closed": ["A"]
+//     "end_open": ["D"]
+//
+// This range returns all users whose `UserName` begins with B:
+//
+//     "start_closed": ["B"]
+//     "end_open": ["C"]
+//
+// Key ranges honor column sort order. For example, suppose a table is
+// defined as follows:
+//
+//     CREATE TABLE DescendingSortedTable {
+//       Key INT64,
+//       ...
+//     ) PRIMARY KEY(Key DESC);
+//
+// The following range retrieves all rows with key values between 1
+// and 100 inclusive:
+//
+//     "start_closed": ["100"]
+//     "end_closed": ["1"]
+//
+// Note that 100 is passed as the start, and 1 is passed as the end,
+// because `Key` is a descending column in the schema.
+type KeyRange struct {
+	// The start key must be provided. It can be either closed or open.
+	//
+	// Types that are valid to be assigned to StartKeyType:
+	//	*KeyRange_StartClosed
+	//	*KeyRange_StartOpen
+	StartKeyType isKeyRange_StartKeyType `protobuf_oneof:"start_key_type"`
+	// The end key must be provided. It can be either closed or open.
+	//
+	// Types that are valid to be assigned to EndKeyType:
+	//	*KeyRange_EndClosed
+	//	*KeyRange_EndOpen
+	EndKeyType isKeyRange_EndKeyType `protobuf_oneof:"end_key_type"`
+}
+
+func (m *KeyRange) Reset()                    { *m = KeyRange{} }
+func (m *KeyRange) String() string            { return proto.CompactTextString(m) }
+func (*KeyRange) ProtoMessage()               {}
+func (*KeyRange) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{0} }
+
+type isKeyRange_StartKeyType interface {
+	isKeyRange_StartKeyType()
+}
+type isKeyRange_EndKeyType interface {
+	isKeyRange_EndKeyType()
+}
+
+type KeyRange_StartClosed struct {
+	StartClosed *google_protobuf1.ListValue `protobuf:"bytes,1,opt,name=start_closed,json=startClosed,oneof"`
+}
+type KeyRange_StartOpen struct {
+	StartOpen *google_protobuf1.ListValue `protobuf:"bytes,2,opt,name=start_open,json=startOpen,oneof"`
+}
+type KeyRange_EndClosed struct {
+	EndClosed *google_protobuf1.ListValue `protobuf:"bytes,3,opt,name=end_closed,json=endClosed,oneof"`
+}
+type KeyRange_EndOpen struct {
+	EndOpen *google_protobuf1.ListValue `protobuf:"bytes,4,opt,name=end_open,json=endOpen,oneof"`
+}
+
+func (*KeyRange_StartClosed) isKeyRange_StartKeyType() {}
+func (*KeyRange_StartOpen) isKeyRange_StartKeyType()   {}
+func (*KeyRange_EndClosed) isKeyRange_EndKeyType()     {}
+func (*KeyRange_EndOpen) isKeyRange_EndKeyType()       {}
+
+func (m *KeyRange) GetStartKeyType() isKeyRange_StartKeyType {
+	if m != nil {
+		return m.StartKeyType
+	}
+	return nil
+}
+func (m *KeyRange) GetEndKeyType() isKeyRange_EndKeyType {
+	if m != nil {
+		return m.EndKeyType
+	}
+	return nil
+}
+
+func (m *KeyRange) GetStartClosed() *google_protobuf1.ListValue {
+	if x, ok := m.GetStartKeyType().(*KeyRange_StartClosed); ok {
+		return x.StartClosed
+	}
+	return nil
+}
+
+func (m *KeyRange) GetStartOpen() *google_protobuf1.ListValue {
+	if x, ok := m.GetStartKeyType().(*KeyRange_StartOpen); ok {
+		return x.StartOpen
+	}
+	return nil
+}
+
+func (m *KeyRange) GetEndClosed() *google_protobuf1.ListValue {
+	if x, ok := m.GetEndKeyType().(*KeyRange_EndClosed); ok {
+		return x.EndClosed
+	}
+	return nil
+}
+
+func (m *KeyRange) GetEndOpen() *google_protobuf1.ListValue {
+	if x, ok := m.GetEndKeyType().(*KeyRange_EndOpen); ok {
+		return x.EndOpen
+	}
+	return nil
+}
+
+// XXX_OneofFuncs is for the internal use of the proto package.
+func (*KeyRange) XXX_OneofFuncs() (func(msg proto.Message, b *proto.Buffer) error, func(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error), func(msg proto.Message) (n int), []interface{}) {
+	return _KeyRange_OneofMarshaler, _KeyRange_OneofUnmarshaler, _KeyRange_OneofSizer, []interface{}{
+		(*KeyRange_StartClosed)(nil),
+		(*KeyRange_StartOpen)(nil),
+		(*KeyRange_EndClosed)(nil),
+		(*KeyRange_EndOpen)(nil),
+	}
+}
+
+func _KeyRange_OneofMarshaler(msg proto.Message, b *proto.Buffer) error {
+	m := msg.(*KeyRange)
+	// start_key_type
+	switch x := m.StartKeyType.(type) {
+	case *KeyRange_StartClosed:
+		b.EncodeVarint(1<<3 | proto.WireBytes)
+		if err := b.EncodeMessage(x.StartClosed); err != nil {
+			return err
+		}
+	case *KeyRange_StartOpen:
+		b.EncodeVarint(2<<3 | proto.WireBytes)
+		if err := b.EncodeMessage(x.StartOpen); err != nil {
+			return err
+		}
+	case nil:
+	default:
+		return fmt.Errorf("KeyRange.StartKeyType has unexpected type %T", x)
+	}
+	// end_key_type
+	switch x := m.EndKeyType.(type) {
+	case *KeyRange_EndClosed:
+		b.EncodeVarint(3<<3 | proto.WireBytes)
+		if err := b.EncodeMessage(x.EndClosed); err != nil {
+			return err
+		}
+	case *KeyRange_EndOpen:
+		b.EncodeVarint(4<<3 | proto.WireBytes)
+		if err := b.EncodeMessage(x.EndOpen); err != nil {
+			return err
+		}
+	case nil:
+	default:
+		return fmt.Errorf("KeyRange.EndKeyType has unexpected type %T", x)
+	}
+	return nil
+}
+
+func _KeyRange_OneofUnmarshaler(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error) {
+	m := msg.(*KeyRange)
+	switch tag {
+	case 1: // start_key_type.start_closed
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		msg := new(google_protobuf1.ListValue)
+		err := b.DecodeMessage(msg)
+		m.StartKeyType = &KeyRange_StartClosed{msg}
+		return true, err
+	case 2: // start_key_type.start_open
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		msg := new(google_protobuf1.ListValue)
+		err := b.DecodeMessage(msg)
+		m.StartKeyType = &KeyRange_StartOpen{msg}
+		return true, err
+	case 3: // end_key_type.end_closed
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		msg := new(google_protobuf1.ListValue)
+		err := b.DecodeMessage(msg)
+		m.EndKeyType = &KeyRange_EndClosed{msg}
+		return true, err
+	case 4: // end_key_type.end_open
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		msg := new(google_protobuf1.ListValue)
+		err := b.DecodeMessage(msg)
+		m.EndKeyType = &KeyRange_EndOpen{msg}
+		return true, err
+	default:
+		return false, nil
+	}
+}
+
+func _KeyRange_OneofSizer(msg proto.Message) (n int) {
+	m := msg.(*KeyRange)
+	// start_key_type
+	switch x := m.StartKeyType.(type) {
+	case *KeyRange_StartClosed:
+		s := proto.Size(x.StartClosed)
+		n += proto.SizeVarint(1<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(s))
+		n += s
+	case *KeyRange_StartOpen:
+		s := proto.Size(x.StartOpen)
+		n += proto.SizeVarint(2<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(s))
+		n += s
+	case nil:
+	default:
+		panic(fmt.Sprintf("proto: unexpected type %T in oneof", x))
+	}
+	// end_key_type
+	switch x := m.EndKeyType.(type) {
+	case *KeyRange_EndClosed:
+		s := proto.Size(x.EndClosed)
+		n += proto.SizeVarint(3<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(s))
+		n += s
+	case *KeyRange_EndOpen:
+		s := proto.Size(x.EndOpen)
+		n += proto.SizeVarint(4<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(s))
+		n += s
+	case nil:
+	default:
+		panic(fmt.Sprintf("proto: unexpected type %T in oneof", x))
+	}
+	return n
+}
+
+// `KeySet` defines a collection of Cloud Spanner keys and/or key ranges. All
+// the keys are expected to be in the same table or index. The keys need
+// not be sorted in any particular way.
+//
+// If the same key is specified multiple times in the set (for example
+// if two ranges, two keys, or a key and a range overlap), Cloud Spanner
+// behaves as if the key were only specified once.
+type KeySet struct {
+	// A list of specific keys. Entries in `keys` should have exactly as
+	// many elements as there are columns in the primary or index key
+	// with which this `KeySet` is used.  Individual key values are
+	// encoded as described [here][google.spanner.v1.TypeCode].
+	Keys []*google_protobuf1.ListValue `protobuf:"bytes,1,rep,name=keys" json:"keys,omitempty"`
+	// A list of key ranges. See [KeyRange][google.spanner.v1.KeyRange] for more information about
+	// key range specifications.
+	Ranges []*KeyRange `protobuf:"bytes,2,rep,name=ranges" json:"ranges,omitempty"`
+	// For convenience `all` can be set to `true` to indicate that this
+	// `KeySet` matches all keys in the table or index. Note that any keys
+	// specified in `keys` or `ranges` are only yielded once.
+	All bool `protobuf:"varint,3,opt,name=all" json:"all,omitempty"`
+}
+
+func (m *KeySet) Reset()                    { *m = KeySet{} }
+func (m *KeySet) String() string            { return proto.CompactTextString(m) }
+func (*KeySet) ProtoMessage()               {}
+func (*KeySet) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{1} }
+
+func (m *KeySet) GetKeys() []*google_protobuf1.ListValue {
+	if m != nil {
+		return m.Keys
+	}
+	return nil
+}
+
+func (m *KeySet) GetRanges() []*KeyRange {
+	if m != nil {
+		return m.Ranges
+	}
+	return nil
+}
+
+func (m *KeySet) GetAll() bool {
+	if m != nil {
+		return m.All
+	}
+	return false
+}
+
+func init() {
+	proto.RegisterType((*KeyRange)(nil), "google.spanner.v1.KeyRange")
+	proto.RegisterType((*KeySet)(nil), "google.spanner.v1.KeySet")
+}
+
+func init() { proto.RegisterFile("google/spanner/v1/keys.proto", fileDescriptor0) }
+
+var fileDescriptor0 = []byte{
+	// 338 bytes of a gzipped FileDescriptorProto
+	0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x8c, 0x92, 0xc1, 0x4b, 0xc3, 0x30,
+	0x14, 0xc6, 0xed, 0x36, 0xe6, 0x96, 0x8d, 0x31, 0x0b, 0x42, 0x99, 0x1e, 0xc6, 0x4e, 0x9e, 0x12,
+	0xe6, 0x0e, 0x0a, 0x3b, 0x08, 0xf5, 0x22, 0x4c, 0x70, 0x54, 0xf0, 0xe0, 0xc1, 0x91, 0xad, 0xcf,
+	0x50, 0x56, 0x5f, 0x42, 0x93, 0x0d, 0x7a, 0xf2, 0x5f, 0xf1, 0x4f, 0x95, 0xa4, 0xa9, 0x08, 0x03,
+	0xdd, 0x2d, 0x8f, 0xef, 0xfb, 0xbd, 0xef, 0xf5, 0xbd, 0x92, 0x4b, 0x21, 0xa5, 0xc8, 0x81, 0x69,
+	0xc5, 0x11, 0xa1, 0x60, 0xfb, 0x29, 0xdb, 0x42, 0xa9, 0xa9, 0x2a, 0xa4, 0x91, 0xe1, 0x59, 0xa5,
+	0x52, 0xaf, 0xd2, 0xfd, 0x74, 0x54, 0x03, 0x5c, 0x65, 0x8c, 0x23, 0x4a, 0xc3, 0x4d, 0x26, 0xd1,
+	0x03, 0x3f, 0xaa, 0xab, 0xd6, 0xbb, 0x77, 0xa6, 0x4d, 0xb1, 0xdb, 0x98, 0x4a, 0x9d, 0x7c, 0x35,
+	0x48, 0x67, 0x01, 0x65, 0xc2, 0x51, 0x40, 0x78, 0x47, 0xfa, 0xda, 0xf0, 0xc2, 0xac, 0x36, 0xb9,
+	0xd4, 0x90, 0x46, 0xc1, 0x38, 0xb8, 0xea, 0x5d, 0x8f, 0xa8, 0x8f, 0xac, 0x3b, 0xd0, 0xc7, 0x4c,
+	0x9b, 0x17, 0x9e, 0xef, 0xe0, 0xe1, 0x24, 0xe9, 0x39, 0xe2, 0xde, 0x01, 0xe1, 0x9c, 0x90, 0xaa,
+	0x81, 0x54, 0x80, 0x51, 0xe3, 0x08, 0xbc, 0xeb, 0xfc, 0x4f, 0x0a, 0xd0, 0xc2, 0x80, 0x69, 0x9d,
+	0xdd, 0xfc, 0x17, 0x0e, 0x92, 0x2e, 0x60, 0xea, 0x93, 0x6f, 0x48, 0xc7, 0xc2, 0x2e, 0xb7, 0x75,
+	0x04, 0x7a, 0x0a, 0x98, 0xda, 0xd4, 0x78, 0x48, 0x06, 0xd5, 0xc8, 0x5b, 0x28, 0x57, 0xa6, 0x54,
+	0x10, 0x0f, 0x48, 0xdf, 0xb6, 0xaa, 0xeb, 0xc9, 0x27, 0x69, 0x2f, 0xa0, 0x7c, 0x06, 0x13, 0x52,
+	0xd2, 0xb2, 0x97, 0x88, 0x82, 0x71, 0xf3, 0xef, 0x80, 0xc4, 0xf9, 0xc2, 0x19, 0x69, 0x17, 0x76,
+	0xb1, 0x3a, 0x6a, 0x38, 0xe2, 0x82, 0x1e, 0x1c, 0x8f, 0xd6, 0xcb, 0x4f, 0xbc, 0x35, 0x1c, 0x92,
+	0x26, 0xcf, 0x73, 0xf7, 0xfd, 0x9d, 0xc4, 0x3e, 0xe3, 0x37, 0x72, 0xbe, 0x91, 0x1f, 0x87, 0x6c,
+	0xdc, 0x5d, 0x40, 0xa9, 0x97, 0x36, 0x7d, 0x19, 0xbc, 0xde, 0x7a, 0x5d, 0xc8, 0x9c, 0xa3, 0xa0,
+	0xb2, 0x10, 0x4c, 0x00, 0xba, 0xd9, 0x58, 0x25, 0x71, 0x95, 0xe9, 0x5f, 0x7f, 0xd5, 0xdc, 0x3f,
+	0xd7, 0x6d, 0x67, 0x9a, 0x7d, 0x07, 0x00, 0x00, 0xff, 0xff, 0x83, 0x58, 0x82, 0xb7, 0x79, 0x02,
+	0x00, 0x00,
+}
diff --git a/googleapis/spanner/v1/mutation.pb.go b/googleapis/spanner/v1/mutation.pb.go
new file mode 100644
index 00000000..0147934c
--- /dev/null
+++ b/googleapis/spanner/v1/mutation.pb.go
@@ -0,0 +1,346 @@
+// Code generated by protoc-gen-go.
+// source: google/spanner/v1/mutation.proto
+// DO NOT EDIT!
+
+package spanner
+
+import proto "github.com/golang/protobuf/proto"
+import fmt "fmt"
+import math "math"
+import _ "google.golang.org/genproto/googleapis/api/annotations"
+import google_protobuf1 "github.com/golang/protobuf/ptypes/struct"
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ = proto.Marshal
+var _ = fmt.Errorf
+var _ = math.Inf
+
+// A modification to one or more Cloud Spanner rows.  Mutations can be
+// applied to a Cloud Spanner database by sending them in a
+// [Commit][google.spanner.v1.Spanner.Commit] call.
+type Mutation struct {
+	// Required. The operation to perform.
+	//
+	// Types that are valid to be assigned to Operation:
+	//	*Mutation_Insert
+	//	*Mutation_Update
+	//	*Mutation_InsertOrUpdate
+	//	*Mutation_Replace
+	//	*Mutation_Delete_
+	Operation isMutation_Operation `protobuf_oneof:"operation"`
+}
+
+func (m *Mutation) Reset()                    { *m = Mutation{} }
+func (m *Mutation) String() string            { return proto.CompactTextString(m) }
+func (*Mutation) ProtoMessage()               {}
+func (*Mutation) Descriptor() ([]byte, []int) { return fileDescriptor1, []int{0} }
+
+type isMutation_Operation interface {
+	isMutation_Operation()
+}
+
+type Mutation_Insert struct {
+	Insert *Mutation_Write `protobuf:"bytes,1,opt,name=insert,oneof"`
+}
+type Mutation_Update struct {
+	Update *Mutation_Write `protobuf:"bytes,2,opt,name=update,oneof"`
+}
+type Mutation_InsertOrUpdate struct {
+	InsertOrUpdate *Mutation_Write `protobuf:"bytes,3,opt,name=insert_or_update,json=insertOrUpdate,oneof"`
+}
+type Mutation_Replace struct {
+	Replace *Mutation_Write `protobuf:"bytes,4,opt,name=replace,oneof"`
+}
+type Mutation_Delete_ struct {
+	Delete *Mutation_Delete `protobuf:"bytes,5,opt,name=delete,oneof"`
+}
+
+func (*Mutation_Insert) isMutation_Operation()         {}
+func (*Mutation_Update) isMutation_Operation()         {}
+func (*Mutation_InsertOrUpdate) isMutation_Operation() {}
+func (*Mutation_Replace) isMutation_Operation()        {}
+func (*Mutation_Delete_) isMutation_Operation()        {}
+
+func (m *Mutation) GetOperation() isMutation_Operation {
+	if m != nil {
+		return m.Operation
+	}
+	return nil
+}
+
+func (m *Mutation) GetInsert() *Mutation_Write {
+	if x, ok := m.GetOperation().(*Mutation_Insert); ok {
+		return x.Insert
+	}
+	return nil
+}
+
+func (m *Mutation) GetUpdate() *Mutation_Write {
+	if x, ok := m.GetOperation().(*Mutation_Update); ok {
+		return x.Update
+	}
+	return nil
+}
+
+func (m *Mutation) GetInsertOrUpdate() *Mutation_Write {
+	if x, ok := m.GetOperation().(*Mutation_InsertOrUpdate); ok {
+		return x.InsertOrUpdate
+	}
+	return nil
+}
+
+func (m *Mutation) GetReplace() *Mutation_Write {
+	if x, ok := m.GetOperation().(*Mutation_Replace); ok {
+		return x.Replace
+	}
+	return nil
+}
+
+func (m *Mutation) GetDelete() *Mutation_Delete {
+	if x, ok := m.GetOperation().(*Mutation_Delete_); ok {
+		return x.Delete
+	}
+	return nil
+}
+
+// XXX_OneofFuncs is for the internal use of the proto package.
+func (*Mutation) XXX_OneofFuncs() (func(msg proto.Message, b *proto.Buffer) error, func(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error), func(msg proto.Message) (n int), []interface{}) {
+	return _Mutation_OneofMarshaler, _Mutation_OneofUnmarshaler, _Mutation_OneofSizer, []interface{}{
+		(*Mutation_Insert)(nil),
+		(*Mutation_Update)(nil),
+		(*Mutation_InsertOrUpdate)(nil),
+		(*Mutation_Replace)(nil),
+		(*Mutation_Delete_)(nil),
+	}
+}
+
+func _Mutation_OneofMarshaler(msg proto.Message, b *proto.Buffer) error {
+	m := msg.(*Mutation)
+	// operation
+	switch x := m.Operation.(type) {
+	case *Mutation_Insert:
+		b.EncodeVarint(1<<3 | proto.WireBytes)
+		if err := b.EncodeMessage(x.Insert); err != nil {
+			return err
+		}
+	case *Mutation_Update:
+		b.EncodeVarint(2<<3 | proto.WireBytes)
+		if err := b.EncodeMessage(x.Update); err != nil {
+			return err
+		}
+	case *Mutation_InsertOrUpdate:
+		b.EncodeVarint(3<<3 | proto.WireBytes)
+		if err := b.EncodeMessage(x.InsertOrUpdate); err != nil {
+			return err
+		}
+	case *Mutation_Replace:
+		b.EncodeVarint(4<<3 | proto.WireBytes)
+		if err := b.EncodeMessage(x.Replace); err != nil {
+			return err
+		}
+	case *Mutation_Delete_:
+		b.EncodeVarint(5<<3 | proto.WireBytes)
+		if err := b.EncodeMessage(x.Delete); err != nil {
+			return err
+		}
+	case nil:
+	default:
+		return fmt.Errorf("Mutation.Operation has unexpected type %T", x)
+	}
+	return nil
+}
+
+func _Mutation_OneofUnmarshaler(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error) {
+	m := msg.(*Mutation)
+	switch tag {
+	case 1: // operation.insert
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		msg := new(Mutation_Write)
+		err := b.DecodeMessage(msg)
+		m.Operation = &Mutation_Insert{msg}
+		return true, err
+	case 2: // operation.update
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		msg := new(Mutation_Write)
+		err := b.DecodeMessage(msg)
+		m.Operation = &Mutation_Update{msg}
+		return true, err
+	case 3: // operation.insert_or_update
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		msg := new(Mutation_Write)
+		err := b.DecodeMessage(msg)
+		m.Operation = &Mutation_InsertOrUpdate{msg}
+		return true, err
+	case 4: // operation.replace
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		msg := new(Mutation_Write)
+		err := b.DecodeMessage(msg)
+		m.Operation = &Mutation_Replace{msg}
+		return true, err
+	case 5: // operation.delete
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		msg := new(Mutation_Delete)
+		err := b.DecodeMessage(msg)
+		m.Operation = &Mutation_Delete_{msg}
+		return true, err
+	default:
+		return false, nil
+	}
+}
+
+func _Mutation_OneofSizer(msg proto.Message) (n int) {
+	m := msg.(*Mutation)
+	// operation
+	switch x := m.Operation.(type) {
+	case *Mutation_Insert:
+		s := proto.Size(x.Insert)
+		n += proto.SizeVarint(1<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(s))
+		n += s
+	case *Mutation_Update:
+		s := proto.Size(x.Update)
+		n += proto.SizeVarint(2<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(s))
+		n += s
+	case *Mutation_InsertOrUpdate:
+		s := proto.Size(x.InsertOrUpdate)
+		n += proto.SizeVarint(3<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(s))
+		n += s
+	case *Mutation_Replace:
+		s := proto.Size(x.Replace)
+		n += proto.SizeVarint(4<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(s))
+		n += s
+	case *Mutation_Delete_:
+		s := proto.Size(x.Delete)
+		n += proto.SizeVarint(5<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(s))
+		n += s
+	case nil:
+	default:
+		panic(fmt.Sprintf("proto: unexpected type %T in oneof", x))
+	}
+	return n
+}
+
+// Arguments to [insert][google.spanner.v1.Mutation.insert], [update][google.spanner.v1.Mutation.update], [insert_or_update][google.spanner.v1.Mutation.insert_or_update], and
+// [replace][google.spanner.v1.Mutation.replace] operations.
+type Mutation_Write struct {
+	// Required. The table whose rows will be written.
+	Table string `protobuf:"bytes,1,opt,name=table" json:"table,omitempty"`
+	// The names of the columns in [table][google.spanner.v1.Mutation.Write.table] to be written.
+	//
+	// The list of columns must contain enough columns to allow
+	// Cloud Spanner to derive values for all primary key columns in the
+	// row(s) to be modified.
+	Columns []string `protobuf:"bytes,2,rep,name=columns" json:"columns,omitempty"`
+	// The values to be written. `values` can contain more than one
+	// list of values. If it does, then multiple rows are written, one
+	// for each entry in `values`. Each list in `values` must have
+	// exactly as many entries as there are entries in [columns][google.spanner.v1.Mutation.Write.columns]
+	// above. Sending multiple lists is equivalent to sending multiple
+	// `Mutation`s, each containing one `values` entry and repeating
+	// [table][google.spanner.v1.Mutation.Write.table] and [columns][google.spanner.v1.Mutation.Write.columns]. Individual values in each list are
+	// encoded as described [here][google.spanner.v1.TypeCode].
+	Values []*google_protobuf1.ListValue `protobuf:"bytes,3,rep,name=values" json:"values,omitempty"`
+}
+
+func (m *Mutation_Write) Reset()                    { *m = Mutation_Write{} }
+func (m *Mutation_Write) String() string            { return proto.CompactTextString(m) }
+func (*Mutation_Write) ProtoMessage()               {}
+func (*Mutation_Write) Descriptor() ([]byte, []int) { return fileDescriptor1, []int{0, 0} }
+
+func (m *Mutation_Write) GetTable() string {
+	if m != nil {
+		return m.Table
+	}
+	return ""
+}
+
+func (m *Mutation_Write) GetColumns() []string {
+	if m != nil {
+		return m.Columns
+	}
+	return nil
+}
+
+func (m *Mutation_Write) GetValues() []*google_protobuf1.ListValue {
+	if m != nil {
+		return m.Values
+	}
+	return nil
+}
+
+// Arguments to [delete][google.spanner.v1.Mutation.delete] operations.
+type Mutation_Delete struct {
+	// Required. The table whose rows will be deleted.
+	Table string `protobuf:"bytes,1,opt,name=table" json:"table,omitempty"`
+	// Required. The primary keys of the rows within [table][google.spanner.v1.Mutation.Delete.table] to delete.
+	KeySet *KeySet `protobuf:"bytes,2,opt,name=key_set,json=keySet" json:"key_set,omitempty"`
+}
+
+func (m *Mutation_Delete) Reset()                    { *m = Mutation_Delete{} }
+func (m *Mutation_Delete) String() string            { return proto.CompactTextString(m) }
+func (*Mutation_Delete) ProtoMessage()               {}
+func (*Mutation_Delete) Descriptor() ([]byte, []int) { return fileDescriptor1, []int{0, 1} }
+
+func (m *Mutation_Delete) GetTable() string {
+	if m != nil {
+		return m.Table
+	}
+	return ""
+}
+
+func (m *Mutation_Delete) GetKeySet() *KeySet {
+	if m != nil {
+		return m.KeySet
+	}
+	return nil
+}
+
+func init() {
+	proto.RegisterType((*Mutation)(nil), "google.spanner.v1.Mutation")
+	proto.RegisterType((*Mutation_Write)(nil), "google.spanner.v1.Mutation.Write")
+	proto.RegisterType((*Mutation_Delete)(nil), "google.spanner.v1.Mutation.Delete")
+}
+
+func init() { proto.RegisterFile("google/spanner/v1/mutation.proto", fileDescriptor1) }
+
+var fileDescriptor1 = []byte{
+	// 382 bytes of a gzipped FileDescriptorProto
+	0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x94, 0x92, 0xd1, 0x4b, 0xeb, 0x30,
+	0x14, 0xc6, 0xef, 0xd6, 0xad, 0xbb, 0xcb, 0xb8, 0x17, 0x2d, 0x0a, 0xb5, 0xf8, 0x50, 0xf7, 0xb4,
+	0xa7, 0x94, 0xd5, 0x17, 0x61, 0xfa, 0x32, 0x7c, 0x10, 0x74, 0x38, 0x2a, 0x2a, 0xf8, 0x32, 0xd2,
+	0xee, 0x58, 0x4a, 0xbb, 0xa4, 0x24, 0xe9, 0x60, 0xff, 0x8c, 0x7f, 0xab, 0x34, 0x49, 0x65, 0x38,
+	0x95, 0xf9, 0xd4, 0x1e, 0xce, 0xf7, 0xfb, 0xce, 0x77, 0x92, 0x20, 0x3f, 0x65, 0x2c, 0x2d, 0x20,
+	0x10, 0x25, 0xa1, 0x14, 0x78, 0xb0, 0x1e, 0x07, 0xab, 0x4a, 0x12, 0x99, 0x31, 0x8a, 0x4b, 0xce,
+	0x24, 0x73, 0x0e, 0xb5, 0x02, 0x1b, 0x05, 0x5e, 0x8f, 0xbd, 0x53, 0x03, 0x91, 0x32, 0x0b, 0x08,
+	0xa5, 0x4c, 0xeb, 0x85, 0x06, 0x3e, 0xba, 0xaa, 0x8a, 0xab, 0xd7, 0x40, 0x48, 0x5e, 0x25, 0xf2,
+	0x53, 0x77, 0x6b, 0x60, 0x0e, 0x1b, 0xc3, 0x0e, 0xdf, 0x3a, 0xe8, 0xef, 0xcc, 0xcc, 0x77, 0x26,
+	0xc8, 0xce, 0xa8, 0x00, 0x2e, 0xdd, 0x96, 0xdf, 0x1a, 0x0d, 0xc2, 0x33, 0xbc, 0x13, 0x05, 0x37,
+	0x62, 0xfc, 0xcc, 0x33, 0x09, 0x37, 0x7f, 0x22, 0x83, 0xd4, 0x70, 0x55, 0x2e, 0x89, 0x04, 0xb7,
+	0xfd, 0x0b, 0x58, 0x23, 0xce, 0x0c, 0x1d, 0x68, 0x9b, 0x05, 0xe3, 0x0b, 0x63, 0x63, 0xed, 0x6f,
+	0xf3, 0x5f, 0xc3, 0xf7, 0xfc, 0x51, 0xdb, 0x5d, 0xa1, 0x1e, 0x87, 0xb2, 0x20, 0x09, 0xb8, 0x9d,
+	0xfd, 0x5d, 0x1a, 0xc6, 0xb9, 0x44, 0xf6, 0x12, 0x0a, 0x90, 0xe0, 0x76, 0x15, 0x3d, 0xfc, 0x89,
+	0xbe, 0x56, 0xca, 0x7a, 0x17, 0xcd, 0x78, 0x39, 0xea, 0x2a, 0x47, 0xe7, 0x08, 0x75, 0x25, 0x89,
+	0x0b, 0x50, 0xa7, 0xd9, 0x8f, 0x74, 0xe1, 0xb8, 0xa8, 0x97, 0xb0, 0xa2, 0x5a, 0x51, 0xe1, 0xb6,
+	0x7d, 0x6b, 0xd4, 0x8f, 0x9a, 0xd2, 0x09, 0x91, 0xbd, 0x26, 0x45, 0x05, 0xc2, 0xb5, 0x7c, 0x6b,
+	0x34, 0x08, 0xbd, 0x66, 0x6c, 0x73, 0xb1, 0xf8, 0x2e, 0x13, 0xf2, 0xa9, 0x96, 0x44, 0x46, 0xe9,
+	0x45, 0xc8, 0xd6, 0x01, 0xbe, 0x99, 0x16, 0xa2, 0x5e, 0x0e, 0x9b, 0x85, 0x00, 0x69, 0xae, 0xe5,
+	0xe4, 0x8b, 0x5d, 0x6e, 0x61, 0xf3, 0x00, 0x32, 0xb2, 0x73, 0xf5, 0x9d, 0x0e, 0x50, 0x9f, 0x95,
+	0xc0, 0xd5, 0x7a, 0xd3, 0x18, 0x1d, 0x27, 0x6c, 0xb5, 0x0b, 0x4d, 0xff, 0x35, 0x27, 0x30, 0xaf,
+	0xd3, 0xcd, 0x5b, 0x2f, 0x17, 0x46, 0x93, 0xb2, 0x82, 0xd0, 0x14, 0x33, 0x9e, 0x06, 0x29, 0x50,
+	0x95, 0x3d, 0xd0, 0x2d, 0x52, 0x66, 0x62, 0xeb, 0x1d, 0x4e, 0xcc, 0x6f, 0x6c, 0x2b, 0xd1, 0xf9,
+	0x7b, 0x00, 0x00, 0x00, 0xff, 0xff, 0xfc, 0x7c, 0xdc, 0xc0, 0x1c, 0x03, 0x00, 0x00,
+}
diff --git a/googleapis/spanner/v1/query_plan.pb.go b/googleapis/spanner/v1/query_plan.pb.go
new file mode 100644
index 00000000..98e7f832
--- /dev/null
+++ b/googleapis/spanner/v1/query_plan.pb.go
@@ -0,0 +1,285 @@
+// Code generated by protoc-gen-go.
+// source: google/spanner/v1/query_plan.proto
+// DO NOT EDIT!
+
+package spanner
+
+import proto "github.com/golang/protobuf/proto"
+import fmt "fmt"
+import math "math"
+import _ "google.golang.org/genproto/googleapis/api/annotations"
+import google_protobuf1 "github.com/golang/protobuf/ptypes/struct"
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ = proto.Marshal
+var _ = fmt.Errorf
+var _ = math.Inf
+
+// The kind of [PlanNode][google.spanner.v1.PlanNode]. Distinguishes between the two different kinds of
+// nodes that can appear in a query plan.
+type PlanNode_Kind int32
+
+const (
+	// Not specified.
+	PlanNode_KIND_UNSPECIFIED PlanNode_Kind = 0
+	// Denotes a Relational operator node in the expression tree. Relational
+	// operators represent iterative processing of rows during query execution.
+	// For example, a `TableScan` operation that reads rows from a table.
+	PlanNode_RELATIONAL PlanNode_Kind = 1
+	// Denotes a Scalar node in the expression tree. Scalar nodes represent
+	// non-iterable entities in the query plan. For example, constants or
+	// arithmetic operators appearing inside predicate expressions or references
+	// to column names.
+	PlanNode_SCALAR PlanNode_Kind = 2
+)
+
+var PlanNode_Kind_name = map[int32]string{
+	0: "KIND_UNSPECIFIED",
+	1: "RELATIONAL",
+	2: "SCALAR",
+}
+var PlanNode_Kind_value = map[string]int32{
+	"KIND_UNSPECIFIED": 0,
+	"RELATIONAL":       1,
+	"SCALAR":           2,
+}
+
+func (x PlanNode_Kind) String() string {
+	return proto.EnumName(PlanNode_Kind_name, int32(x))
+}
+func (PlanNode_Kind) EnumDescriptor() ([]byte, []int) { return fileDescriptor2, []int{0, 0} }
+
+// Node information for nodes appearing in a [QueryPlan.plan_nodes][google.spanner.v1.QueryPlan.plan_nodes].
+type PlanNode struct {
+	// The `PlanNode`'s index in [node list][google.spanner.v1.QueryPlan.plan_nodes].
+	Index int32 `protobuf:"varint,1,opt,name=index" json:"index,omitempty"`
+	// Used to determine the type of node. May be needed for visualizing
+	// different kinds of nodes differently. For example, If the node is a
+	// [SCALAR][google.spanner.v1.PlanNode.Kind.SCALAR] node, it will have a condensed representation
+	// which can be used to directly embed a description of the node in its
+	// parent.
+	Kind PlanNode_Kind `protobuf:"varint,2,opt,name=kind,enum=google.spanner.v1.PlanNode_Kind" json:"kind,omitempty"`
+	// The display name for the node.
+	DisplayName string `protobuf:"bytes,3,opt,name=display_name,json=displayName" json:"display_name,omitempty"`
+	// List of child node `index`es and their relationship to this parent.
+	ChildLinks []*PlanNode_ChildLink `protobuf:"bytes,4,rep,name=child_links,json=childLinks" json:"child_links,omitempty"`
+	// Condensed representation for [SCALAR][google.spanner.v1.PlanNode.Kind.SCALAR] nodes.
+	ShortRepresentation *PlanNode_ShortRepresentation `protobuf:"bytes,5,opt,name=short_representation,json=shortRepresentation" json:"short_representation,omitempty"`
+	// Attributes relevant to the node contained in a group of key-value pairs.
+	// For example, a Parameter Reference node could have the following
+	// information in its metadata:
+	//
+	//     {
+	//       "parameter_reference": "param1",
+	//       "parameter_type": "array"
+	//     }
+	Metadata *google_protobuf1.Struct `protobuf:"bytes,6,opt,name=metadata" json:"metadata,omitempty"`
+	// The execution statistics associated with the node, contained in a group of
+	// key-value pairs. Only present if the plan was returned as a result of a
+	// profile query. For example, number of executions, number of rows/time per
+	// execution etc.
+	ExecutionStats *google_protobuf1.Struct `protobuf:"bytes,7,opt,name=execution_stats,json=executionStats" json:"execution_stats,omitempty"`
+}
+
+func (m *PlanNode) Reset()                    { *m = PlanNode{} }
+func (m *PlanNode) String() string            { return proto.CompactTextString(m) }
+func (*PlanNode) ProtoMessage()               {}
+func (*PlanNode) Descriptor() ([]byte, []int) { return fileDescriptor2, []int{0} }
+
+func (m *PlanNode) GetIndex() int32 {
+	if m != nil {
+		return m.Index
+	}
+	return 0
+}
+
+func (m *PlanNode) GetKind() PlanNode_Kind {
+	if m != nil {
+		return m.Kind
+	}
+	return PlanNode_KIND_UNSPECIFIED
+}
+
+func (m *PlanNode) GetDisplayName() string {
+	if m != nil {
+		return m.DisplayName
+	}
+	return ""
+}
+
+func (m *PlanNode) GetChildLinks() []*PlanNode_ChildLink {
+	if m != nil {
+		return m.ChildLinks
+	}
+	return nil
+}
+
+func (m *PlanNode) GetShortRepresentation() *PlanNode_ShortRepresentation {
+	if m != nil {
+		return m.ShortRepresentation
+	}
+	return nil
+}
+
+func (m *PlanNode) GetMetadata() *google_protobuf1.Struct {
+	if m != nil {
+		return m.Metadata
+	}
+	return nil
+}
+
+func (m *PlanNode) GetExecutionStats() *google_protobuf1.Struct {
+	if m != nil {
+		return m.ExecutionStats
+	}
+	return nil
+}
+
+// Metadata associated with a parent-child relationship appearing in a
+// [PlanNode][google.spanner.v1.PlanNode].
+type PlanNode_ChildLink struct {
+	// The node to which the link points.
+	ChildIndex int32 `protobuf:"varint,1,opt,name=child_index,json=childIndex" json:"child_index,omitempty"`
+	// The type of the link. For example, in Hash Joins this could be used to
+	// distinguish between the build child and the probe child, or in the case
+	// of the child being an output variable, to represent the tag associated
+	// with the output variable.
+	Type string `protobuf:"bytes,2,opt,name=type" json:"type,omitempty"`
+	// Only present if the child node is [SCALAR][google.spanner.v1.PlanNode.Kind.SCALAR] and corresponds
+	// to an output variable of the parent node. The field carries the name of
+	// the output variable.
+	// For example, a `TableScan` operator that reads rows from a table will
+	// have child links to the `SCALAR` nodes representing the output variables
+	// created for each column that is read by the operator. The corresponding
+	// `variable` fields will be set to the variable names assigned to the
+	// columns.
+	Variable string `protobuf:"bytes,3,opt,name=variable" json:"variable,omitempty"`
+}
+
+func (m *PlanNode_ChildLink) Reset()                    { *m = PlanNode_ChildLink{} }
+func (m *PlanNode_ChildLink) String() string            { return proto.CompactTextString(m) }
+func (*PlanNode_ChildLink) ProtoMessage()               {}
+func (*PlanNode_ChildLink) Descriptor() ([]byte, []int) { return fileDescriptor2, []int{0, 0} }
+
+func (m *PlanNode_ChildLink) GetChildIndex() int32 {
+	if m != nil {
+		return m.ChildIndex
+	}
+	return 0
+}
+
+func (m *PlanNode_ChildLink) GetType() string {
+	if m != nil {
+		return m.Type
+	}
+	return ""
+}
+
+func (m *PlanNode_ChildLink) GetVariable() string {
+	if m != nil {
+		return m.Variable
+	}
+	return ""
+}
+
+// Condensed representation of a node and its subtree. Only present for
+// `SCALAR` [PlanNode(s)][google.spanner.v1.PlanNode].
+type PlanNode_ShortRepresentation struct {
+	// A string representation of the expression subtree rooted at this node.
+	Description string `protobuf:"bytes,1,opt,name=description" json:"description,omitempty"`
+	// A mapping of (subquery variable name) -> (subquery node id) for cases
+	// where the `description` string of this node references a `SCALAR`
+	// subquery contained in the expression subtree rooted at this node. The
+	// referenced `SCALAR` subquery may not necessarily be a direct child of
+	// this node.
+	Subqueries map[string]int32 `protobuf:"bytes,2,rep,name=subqueries" json:"subqueries,omitempty" protobuf_key:"bytes,1,opt,name=key" protobuf_val:"varint,2,opt,name=value"`
+}
+
+func (m *PlanNode_ShortRepresentation) Reset()                    { *m = PlanNode_ShortRepresentation{} }
+func (m *PlanNode_ShortRepresentation) String() string            { return proto.CompactTextString(m) }
+func (*PlanNode_ShortRepresentation) ProtoMessage()               {}
+func (*PlanNode_ShortRepresentation) Descriptor() ([]byte, []int) { return fileDescriptor2, []int{0, 1} }
+
+func (m *PlanNode_ShortRepresentation) GetDescription() string {
+	if m != nil {
+		return m.Description
+	}
+	return ""
+}
+
+func (m *PlanNode_ShortRepresentation) GetSubqueries() map[string]int32 {
+	if m != nil {
+		return m.Subqueries
+	}
+	return nil
+}
+
+// Contains an ordered list of nodes appearing in the query plan.
+type QueryPlan struct {
+	// The nodes in the query plan. Plan nodes are returned in pre-order starting
+	// with the plan root. Each [PlanNode][google.spanner.v1.PlanNode]'s `id` corresponds to its index in
+	// `plan_nodes`.
+	PlanNodes []*PlanNode `protobuf:"bytes,1,rep,name=plan_nodes,json=planNodes" json:"plan_nodes,omitempty"`
+}
+
+func (m *QueryPlan) Reset()                    { *m = QueryPlan{} }
+func (m *QueryPlan) String() string            { return proto.CompactTextString(m) }
+func (*QueryPlan) ProtoMessage()               {}
+func (*QueryPlan) Descriptor() ([]byte, []int) { return fileDescriptor2, []int{1} }
+
+func (m *QueryPlan) GetPlanNodes() []*PlanNode {
+	if m != nil {
+		return m.PlanNodes
+	}
+	return nil
+}
+
+func init() {
+	proto.RegisterType((*PlanNode)(nil), "google.spanner.v1.PlanNode")
+	proto.RegisterType((*PlanNode_ChildLink)(nil), "google.spanner.v1.PlanNode.ChildLink")
+	proto.RegisterType((*PlanNode_ShortRepresentation)(nil), "google.spanner.v1.PlanNode.ShortRepresentation")
+	proto.RegisterType((*QueryPlan)(nil), "google.spanner.v1.QueryPlan")
+	proto.RegisterEnum("google.spanner.v1.PlanNode_Kind", PlanNode_Kind_name, PlanNode_Kind_value)
+}
+
+func init() { proto.RegisterFile("google/spanner/v1/query_plan.proto", fileDescriptor2) }
+
+var fileDescriptor2 = []byte{
+	// 570 bytes of a gzipped FileDescriptorProto
+	0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x94, 0x54, 0xdd, 0x6e, 0xd3, 0x4c,
+	0x10, 0xfd, 0x9c, 0x26, 0xf9, 0x9a, 0x09, 0x4a, 0xc3, 0xb6, 0x08, 0x2b, 0x20, 0x61, 0x22, 0x21,
+	0xe5, 0xca, 0x56, 0x5b, 0x2e, 0xaa, 0x22, 0x04, 0x69, 0x9b, 0xa2, 0xa8, 0x51, 0x08, 0x1b, 0xb8,
+	0x41, 0x48, 0xd6, 0xc6, 0x5e, 0xdc, 0x55, 0x9c, 0x5d, 0xe3, 0x5d, 0x47, 0xcd, 0x4b, 0xf0, 0x7a,
+	0xbc, 0x0e, 0xda, 0xf5, 0x0f, 0x85, 0xa0, 0x48, 0xdc, 0xcd, 0xec, 0x9c, 0x39, 0x9a, 0x39, 0x67,
+	0x6c, 0xe8, 0x47, 0x42, 0x44, 0x31, 0xf5, 0x64, 0x42, 0x38, 0xa7, 0xa9, 0xb7, 0x3e, 0xf6, 0xbe,
+	0x65, 0x34, 0xdd, 0xf8, 0x49, 0x4c, 0xb8, 0x9b, 0xa4, 0x42, 0x09, 0xf4, 0x30, 0xc7, 0xb8, 0x05,
+	0xc6, 0x5d, 0x1f, 0xf7, 0x9e, 0x16, 0x6d, 0x24, 0x61, 0x1e, 0xe1, 0x5c, 0x28, 0xa2, 0x98, 0xe0,
+	0x32, 0x6f, 0xa8, 0xaa, 0x26, 0x5b, 0x64, 0x5f, 0x3d, 0xa9, 0xd2, 0x2c, 0x50, 0x79, 0xb5, 0xff,
+	0xbd, 0x09, 0xfb, 0xb3, 0x98, 0xf0, 0xa9, 0x08, 0x29, 0x3a, 0x82, 0x06, 0xe3, 0x21, 0xbd, 0xb3,
+	0x2d, 0xc7, 0x1a, 0x34, 0x70, 0x9e, 0xa0, 0x97, 0x50, 0x5f, 0x32, 0x1e, 0xda, 0x35, 0xc7, 0x1a,
+	0x74, 0x4e, 0x1c, 0x77, 0x6b, 0x00, 0xb7, 0x24, 0x70, 0x6f, 0x18, 0x0f, 0xb1, 0x41, 0xa3, 0xe7,
+	0xf0, 0x20, 0x64, 0x32, 0x89, 0xc9, 0xc6, 0xe7, 0x64, 0x45, 0xed, 0x3d, 0xc7, 0x1a, 0xb4, 0x70,
+	0xbb, 0x78, 0x9b, 0x92, 0x15, 0x45, 0xd7, 0xd0, 0x0e, 0x6e, 0x59, 0x1c, 0xfa, 0x31, 0xe3, 0x4b,
+	0x69, 0xd7, 0x9d, 0xbd, 0x41, 0xfb, 0xe4, 0xc5, 0x2e, 0xfe, 0x4b, 0x0d, 0x9f, 0x30, 0xbe, 0xc4,
+	0x10, 0x94, 0xa1, 0x44, 0x0b, 0x38, 0x92, 0xb7, 0x22, 0x55, 0x7e, 0x4a, 0x93, 0x94, 0x4a, 0xca,
+	0x73, 0x01, 0xec, 0x86, 0x63, 0x0d, 0xda, 0x27, 0xde, 0x2e, 0xc2, 0xb9, 0xee, 0xc3, 0xbf, 0xb5,
+	0xe1, 0x43, 0xb9, 0xfd, 0x88, 0x4e, 0x61, 0x7f, 0x45, 0x15, 0x09, 0x89, 0x22, 0x76, 0xd3, 0xf0,
+	0x3e, 0x2e, 0x79, 0x4b, 0x61, 0xdd, 0xb9, 0x11, 0x16, 0x57, 0x40, 0xf4, 0x16, 0x0e, 0xe8, 0x1d,
+	0x0d, 0x32, 0xcd, 0xe0, 0x4b, 0x45, 0x94, 0xb4, 0xff, 0xdf, 0xdd, 0xdb, 0xa9, 0xf0, 0x73, 0x0d,
+	0xef, 0x7d, 0x81, 0x56, 0xb5, 0x33, 0x7a, 0x56, 0xea, 0x75, 0xdf, 0xa4, 0x5c, 0x88, 0xb1, 0x71,
+	0x0a, 0x41, 0x5d, 0x6d, 0x12, 0x6a, 0x9c, 0x6a, 0x61, 0x13, 0xa3, 0x1e, 0xec, 0xaf, 0x49, 0xca,
+	0xc8, 0x22, 0x2e, 0x3d, 0xa8, 0xf2, 0xde, 0x0f, 0x0b, 0x0e, 0xff, 0xa2, 0x00, 0x72, 0xa0, 0x1d,
+	0x52, 0x19, 0xa4, 0x2c, 0x31, 0x3a, 0x5a, 0x85, 0x75, 0xbf, 0x9e, 0x90, 0x0f, 0x20, 0xb3, 0x85,
+	0x3e, 0x4e, 0x46, 0xa5, 0x5d, 0x33, 0xce, 0xbd, 0xf9, 0x47, 0xa1, 0xdd, 0x79, 0xc5, 0x30, 0xe2,
+	0x2a, 0xdd, 0xe0, 0x7b, 0x94, 0xbd, 0xd7, 0x70, 0xf0, 0x47, 0x19, 0x75, 0x61, 0x6f, 0x49, 0x37,
+	0xc5, 0x34, 0x3a, 0xd4, 0xf7, 0xba, 0x26, 0x71, 0x96, 0x2f, 0xdc, 0xc0, 0x79, 0x72, 0x5e, 0x3b,
+	0xb3, 0xfa, 0x67, 0x50, 0xd7, 0xb7, 0x88, 0x8e, 0xa0, 0x7b, 0x33, 0x9e, 0x5e, 0xf9, 0x9f, 0xa6,
+	0xf3, 0xd9, 0xe8, 0x72, 0x7c, 0x3d, 0x1e, 0x5d, 0x75, 0xff, 0x43, 0x1d, 0x00, 0x3c, 0x9a, 0x0c,
+	0x3f, 0x8e, 0xdf, 0x4f, 0x87, 0x93, 0xae, 0x85, 0x00, 0x9a, 0xf3, 0xcb, 0xe1, 0x64, 0x88, 0xbb,
+	0xb5, 0xfe, 0x3b, 0x68, 0x7d, 0xd0, 0xdf, 0x9c, 0x9e, 0x1c, 0x9d, 0x03, 0xe8, 0x4f, 0xcf, 0xe7,
+	0x22, 0xa4, 0xd2, 0xb6, 0xcc, 0x9a, 0x4f, 0x76, 0xac, 0x89, 0x5b, 0x49, 0x11, 0xc9, 0x8b, 0x00,
+	0x1e, 0x05, 0x62, 0xb5, 0x0d, 0xbe, 0xe8, 0x54, 0xfc, 0x33, 0xed, 0xfe, 0xcc, 0xfa, 0x7c, 0x56,
+	0x80, 0x22, 0x11, 0x13, 0x1e, 0xb9, 0x22, 0x8d, 0xbc, 0x88, 0x72, 0x73, 0x1b, 0x5e, 0x5e, 0x22,
+	0x09, 0x93, 0xf7, 0x7e, 0x0b, 0xaf, 0x8a, 0x70, 0xd1, 0x34, 0xa0, 0xd3, 0x9f, 0x01, 0x00, 0x00,
+	0xff, 0xff, 0x31, 0xcf, 0x6d, 0x19, 0x3a, 0x04, 0x00, 0x00,
+}
diff --git a/googleapis/spanner/v1/result_set.pb.go b/googleapis/spanner/v1/result_set.pb.go
new file mode 100644
index 00000000..c93717dc
--- /dev/null
+++ b/googleapis/spanner/v1/result_set.pb.go
@@ -0,0 +1,310 @@
+// Code generated by protoc-gen-go.
+// source: google/spanner/v1/result_set.proto
+// DO NOT EDIT!
+
+package spanner
+
+import proto "github.com/golang/protobuf/proto"
+import fmt "fmt"
+import math "math"
+import _ "google.golang.org/genproto/googleapis/api/annotations"
+import google_protobuf1 "github.com/golang/protobuf/ptypes/struct"
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ = proto.Marshal
+var _ = fmt.Errorf
+var _ = math.Inf
+
+// Results from [Read][google.spanner.v1.Spanner.Read] or
+// [ExecuteSql][google.spanner.v1.Spanner.ExecuteSql].
+type ResultSet struct {
+	// Metadata about the result set, such as row type information.
+	Metadata *ResultSetMetadata `protobuf:"bytes,1,opt,name=metadata" json:"metadata,omitempty"`
+	// Each element in `rows` is a row whose format is defined by
+	// [metadata.row_type][google.spanner.v1.ResultSetMetadata.row_type]. The ith element
+	// in each row matches the ith field in
+	// [metadata.row_type][google.spanner.v1.ResultSetMetadata.row_type]. Elements are
+	// encoded based on type as described
+	// [here][google.spanner.v1.TypeCode].
+	Rows []*google_protobuf1.ListValue `protobuf:"bytes,2,rep,name=rows" json:"rows,omitempty"`
+	// Query plan and execution statistics for the query that produced this
+	// result set. These can be requested by setting
+	// [ExecuteSqlRequest.query_mode][google.spanner.v1.ExecuteSqlRequest.query_mode].
+	Stats *ResultSetStats `protobuf:"bytes,3,opt,name=stats" json:"stats,omitempty"`
+}
+
+func (m *ResultSet) Reset()                    { *m = ResultSet{} }
+func (m *ResultSet) String() string            { return proto.CompactTextString(m) }
+func (*ResultSet) ProtoMessage()               {}
+func (*ResultSet) Descriptor() ([]byte, []int) { return fileDescriptor3, []int{0} }
+
+func (m *ResultSet) GetMetadata() *ResultSetMetadata {
+	if m != nil {
+		return m.Metadata
+	}
+	return nil
+}
+
+func (m *ResultSet) GetRows() []*google_protobuf1.ListValue {
+	if m != nil {
+		return m.Rows
+	}
+	return nil
+}
+
+func (m *ResultSet) GetStats() *ResultSetStats {
+	if m != nil {
+		return m.Stats
+	}
+	return nil
+}
+
+// Partial results from a streaming read or SQL query. Streaming reads and
+// SQL queries better tolerate large result sets, large rows, and large
+// values, but are a little trickier to consume.
+type PartialResultSet struct {
+	// Metadata about the result set, such as row type information.
+	// Only present in the first response.
+	Metadata *ResultSetMetadata `protobuf:"bytes,1,opt,name=metadata" json:"metadata,omitempty"`
+	// A streamed result set consists of a stream of values, which might
+	// be split into many `PartialResultSet` messages to accommodate
+	// large rows and/or large values. Every N complete values defines a
+	// row, where N is equal to the number of entries in
+	// [metadata.row_type.fields][google.spanner.v1.StructType.fields].
+	//
+	// Most values are encoded based on type as described
+	// [here][google.spanner.v1.TypeCode].
+	//
+	// It is possible that the last value in values is "chunked",
+	// meaning that the rest of the value is sent in subsequent
+	// `PartialResultSet`(s). This is denoted by the [chunked_value][google.spanner.v1.PartialResultSet.chunked_value]
+	// field. Two or more chunked values can be merged to form a
+	// complete value as follows:
+	//
+	//   * `bool/number/null`: cannot be chunked
+	//   * `string`: concatenate the strings
+	//   * `list`: concatenate the lists. If the last element in a list is a
+	//     `string`, `list`, or `object`, merge it with the first element in
+	//     the next list by applying these rules recursively.
+	//   * `object`: concatenate the (field name, field value) pairs. If a
+	//     field name is duplicated, then apply these rules recursively
+	//     to merge the field values.
+	//
+	// Some examples of merging:
+	//
+	//     # Strings are concatenated.
+	//     "foo", "bar" => "foobar"
+	//
+	//     # Lists of non-strings are concatenated.
+	//     [2, 3], [4] => [2, 3, 4]
+	//
+	//     # Lists are concatenated, but the last and first elements are merged
+	//     # because they are strings.
+	//     ["a", "b"], ["c", "d"] => ["a", "bc", "d"]
+	//
+	//     # Lists are concatenated, but the last and first elements are merged
+	//     # because they are lists. Recursively, the last and first elements
+	//     # of the inner lists are merged because they are strings.
+	//     ["a", ["b", "c"]], [["d"], "e"] => ["a", ["b", "cd"], "e"]
+	//
+	//     # Non-overlapping object fields are combined.
+	//     {"a": "1"}, {"b": "2"} => {"a": "1", "b": 2"}
+	//
+	//     # Overlapping object fields are merged.
+	//     {"a": "1"}, {"a": "2"} => {"a": "12"}
+	//
+	//     # Examples of merging objects containing lists of strings.
+	//     {"a": ["1"]}, {"a": ["2"]} => {"a": ["12"]}
+	//
+	// For a more complete example, suppose a streaming SQL query is
+	// yielding a result set whose rows contain a single string
+	// field. The following `PartialResultSet`s might be yielded:
+	//
+	//     {
+	//       "metadata": { ... }
+	//       "values": ["Hello", "W"]
+	//       "chunked_value": true
+	//       "resume_token": "Af65..."
+	//     }
+	//     {
+	//       "values": ["orl"]
+	//       "chunked_value": true
+	//       "resume_token": "Bqp2..."
+	//     }
+	//     {
+	//       "values": ["d"]
+	//       "resume_token": "Zx1B..."
+	//     }
+	//
+	// This sequence of `PartialResultSet`s encodes two rows, one
+	// containing the field value `"Hello"`, and a second containing the
+	// field value `"World" = "W" + "orl" + "d"`.
+	Values []*google_protobuf1.Value `protobuf:"bytes,2,rep,name=values" json:"values,omitempty"`
+	// If true, then the final value in [values][google.spanner.v1.PartialResultSet.values] is chunked, and must
+	// be combined with more values from subsequent `PartialResultSet`s
+	// to obtain a complete field value.
+	ChunkedValue bool `protobuf:"varint,3,opt,name=chunked_value,json=chunkedValue" json:"chunked_value,omitempty"`
+	// Streaming calls might be interrupted for a variety of reasons, such
+	// as TCP connection loss. If this occurs, the stream of results can
+	// be resumed by re-sending the original request and including
+	// `resume_token`. Note that executing any other transaction in the
+	// same session invalidates the token.
+	ResumeToken []byte `protobuf:"bytes,4,opt,name=resume_token,json=resumeToken,proto3" json:"resume_token,omitempty"`
+	// Query plan and execution statistics for the query that produced this
+	// streaming result set. These can be requested by setting
+	// [ExecuteSqlRequest.query_mode][google.spanner.v1.ExecuteSqlRequest.query_mode] and are sent
+	// only once with the last response in the stream.
+	Stats *ResultSetStats `protobuf:"bytes,5,opt,name=stats" json:"stats,omitempty"`
+}
+
+func (m *PartialResultSet) Reset()                    { *m = PartialResultSet{} }
+func (m *PartialResultSet) String() string            { return proto.CompactTextString(m) }
+func (*PartialResultSet) ProtoMessage()               {}
+func (*PartialResultSet) Descriptor() ([]byte, []int) { return fileDescriptor3, []int{1} }
+
+func (m *PartialResultSet) GetMetadata() *ResultSetMetadata {
+	if m != nil {
+		return m.Metadata
+	}
+	return nil
+}
+
+func (m *PartialResultSet) GetValues() []*google_protobuf1.Value {
+	if m != nil {
+		return m.Values
+	}
+	return nil
+}
+
+func (m *PartialResultSet) GetChunkedValue() bool {
+	if m != nil {
+		return m.ChunkedValue
+	}
+	return false
+}
+
+func (m *PartialResultSet) GetResumeToken() []byte {
+	if m != nil {
+		return m.ResumeToken
+	}
+	return nil
+}
+
+func (m *PartialResultSet) GetStats() *ResultSetStats {
+	if m != nil {
+		return m.Stats
+	}
+	return nil
+}
+
+// Metadata about a [ResultSet][google.spanner.v1.ResultSet] or [PartialResultSet][google.spanner.v1.PartialResultSet].
+type ResultSetMetadata struct {
+	// Indicates the field names and types for the rows in the result
+	// set.  For example, a SQL query like `"SELECT UserId, UserName FROM
+	// Users"` could return a `row_type` value like:
+	//
+	//     "fields": [
+	//       { "name": "UserId", "type": { "code": "INT64" } },
+	//       { "name": "UserName", "type": { "code": "STRING" } },
+	//     ]
+	RowType *StructType `protobuf:"bytes,1,opt,name=row_type,json=rowType" json:"row_type,omitempty"`
+	// If the read or SQL query began a transaction as a side-effect, the
+	// information about the new transaction is yielded here.
+	Transaction *Transaction `protobuf:"bytes,2,opt,name=transaction" json:"transaction,omitempty"`
+}
+
+func (m *ResultSetMetadata) Reset()                    { *m = ResultSetMetadata{} }
+func (m *ResultSetMetadata) String() string            { return proto.CompactTextString(m) }
+func (*ResultSetMetadata) ProtoMessage()               {}
+func (*ResultSetMetadata) Descriptor() ([]byte, []int) { return fileDescriptor3, []int{2} }
+
+func (m *ResultSetMetadata) GetRowType() *StructType {
+	if m != nil {
+		return m.RowType
+	}
+	return nil
+}
+
+func (m *ResultSetMetadata) GetTransaction() *Transaction {
+	if m != nil {
+		return m.Transaction
+	}
+	return nil
+}
+
+// Additional statistics about a [ResultSet][google.spanner.v1.ResultSet] or [PartialResultSet][google.spanner.v1.PartialResultSet].
+type ResultSetStats struct {
+	// [QueryPlan][google.spanner.v1.QueryPlan] for the query associated with this result.
+	QueryPlan *QueryPlan `protobuf:"bytes,1,opt,name=query_plan,json=queryPlan" json:"query_plan,omitempty"`
+	// Aggregated statistics from the execution of the query. Only present when
+	// the query is profiled. For example, a query could return the statistics as
+	// follows:
+	//
+	//     {
+	//       "rows_returned": "3",
+	//       "elapsed_time": "1.22 secs",
+	//       "cpu_time": "1.19 secs"
+	//     }
+	QueryStats *google_protobuf1.Struct `protobuf:"bytes,2,opt,name=query_stats,json=queryStats" json:"query_stats,omitempty"`
+}
+
+func (m *ResultSetStats) Reset()                    { *m = ResultSetStats{} }
+func (m *ResultSetStats) String() string            { return proto.CompactTextString(m) }
+func (*ResultSetStats) ProtoMessage()               {}
+func (*ResultSetStats) Descriptor() ([]byte, []int) { return fileDescriptor3, []int{3} }
+
+func (m *ResultSetStats) GetQueryPlan() *QueryPlan {
+	if m != nil {
+		return m.QueryPlan
+	}
+	return nil
+}
+
+func (m *ResultSetStats) GetQueryStats() *google_protobuf1.Struct {
+	if m != nil {
+		return m.QueryStats
+	}
+	return nil
+}
+
+func init() {
+	proto.RegisterType((*ResultSet)(nil), "google.spanner.v1.ResultSet")
+	proto.RegisterType((*PartialResultSet)(nil), "google.spanner.v1.PartialResultSet")
+	proto.RegisterType((*ResultSetMetadata)(nil), "google.spanner.v1.ResultSetMetadata")
+	proto.RegisterType((*ResultSetStats)(nil), "google.spanner.v1.ResultSetStats")
+}
+
+func init() { proto.RegisterFile("google/spanner/v1/result_set.proto", fileDescriptor3) }
+
+var fileDescriptor3 = []byte{
+	// 463 bytes of a gzipped FileDescriptorProto
+	0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xac, 0x93, 0x4d, 0x6f, 0xd3, 0x40,
+	0x10, 0x86, 0xe5, 0xf4, 0x83, 0x74, 0x1c, 0x10, 0x5d, 0x09, 0xb0, 0xa2, 0x82, 0xd2, 0x94, 0x43,
+	0x4e, 0xb6, 0x5a, 0x0e, 0x44, 0xea, 0xa5, 0xea, 0x19, 0xa4, 0xb0, 0x89, 0x38, 0x70, 0xb1, 0xa6,
+	0xee, 0x62, 0xac, 0x3a, 0xbb, 0xce, 0xee, 0x3a, 0x51, 0x7e, 0x00, 0xe2, 0xc8, 0xbf, 0xe1, 0xf7,
+	0xa1, 0xfd, 0xc8, 0x07, 0xd8, 0x42, 0x42, 0xea, 0x6d, 0xb3, 0xfb, 0xbc, 0xf3, 0xce, 0x3b, 0x9e,
+	0xc0, 0x30, 0x17, 0x22, 0x2f, 0x59, 0xa2, 0x2a, 0xe4, 0x9c, 0xc9, 0x64, 0x79, 0x99, 0x48, 0xa6,
+	0xea, 0x52, 0xa7, 0x8a, 0xe9, 0xb8, 0x92, 0x42, 0x0b, 0x72, 0xea, 0x98, 0xd8, 0x33, 0xf1, 0xf2,
+	0xb2, 0x7f, 0xe6, 0x65, 0x58, 0x15, 0x09, 0x72, 0x2e, 0x34, 0xea, 0x42, 0x70, 0xe5, 0x04, 0xdb,
+	0x57, 0xfb, 0xeb, 0xae, 0xfe, 0x9a, 0x28, 0x2d, 0xeb, 0xcc, 0x97, 0xeb, 0xb7, 0x58, 0x2e, 0x6a,
+	0x26, 0xd7, 0x69, 0x55, 0x22, 0xf7, 0xcc, 0x45, 0x93, 0xd1, 0x12, 0xb9, 0xc2, 0xcc, 0xf8, 0xfc,
+	0x65, 0xb3, 0x0f, 0xad, 0x2b, 0xe6, 0x5e, 0x87, 0xbf, 0x02, 0x38, 0xa1, 0x36, 0xca, 0x94, 0x69,
+	0x72, 0x03, 0xdd, 0x39, 0xd3, 0x78, 0x8f, 0x1a, 0xa3, 0x60, 0x10, 0x8c, 0xc2, 0xab, 0xb7, 0x71,
+	0x23, 0x56, 0xbc, 0xe5, 0x3f, 0x7a, 0x96, 0x6e, 0x55, 0x24, 0x86, 0x43, 0x29, 0x56, 0x2a, 0xea,
+	0x0c, 0x0e, 0x46, 0xe1, 0x55, 0x7f, 0xa3, 0xde, 0x64, 0x8c, 0x3f, 0x14, 0x4a, 0x7f, 0xc6, 0xb2,
+	0x66, 0xd4, 0x72, 0xe4, 0x3d, 0x1c, 0x29, 0x8d, 0x5a, 0x45, 0x07, 0xd6, 0xee, 0xfc, 0x5f, 0x76,
+	0x53, 0x03, 0x52, 0xc7, 0x0f, 0xbf, 0x77, 0xe0, 0xf9, 0x04, 0xa5, 0x2e, 0xb0, 0x7c, 0xdc, 0xfe,
+	0x8f, 0x97, 0xa6, 0xbd, 0x4d, 0x82, 0x97, 0x8d, 0x04, 0xae, 0x7b, 0x4f, 0x91, 0x0b, 0x78, 0x9a,
+	0x7d, 0xab, 0xf9, 0x03, 0xbb, 0x4f, 0xed, 0x8d, 0xcd, 0xd1, 0xa5, 0x3d, 0x7f, 0x69, 0x61, 0x72,
+	0x0e, 0x3d, 0xb3, 0x2e, 0x73, 0x96, 0x6a, 0xf1, 0xc0, 0x78, 0x74, 0x38, 0x08, 0x46, 0x3d, 0x1a,
+	0xba, 0xbb, 0x99, 0xb9, 0xda, 0xcd, 0xe1, 0xe8, 0x3f, 0xe7, 0xf0, 0x33, 0x80, 0xd3, 0x46, 0x20,
+	0x32, 0x86, 0xae, 0x14, 0xab, 0xd4, 0x7c, 0x68, 0x3f, 0x88, 0xd7, 0x2d, 0x15, 0xa7, 0x76, 0xe1,
+	0x66, 0xeb, 0x8a, 0xd1, 0x27, 0x52, 0xac, 0xcc, 0x81, 0xdc, 0x40, 0xb8, 0xb7, 0x43, 0x51, 0xc7,
+	0x8a, 0xdf, 0xb4, 0x88, 0x67, 0x3b, 0x8a, 0xee, 0x4b, 0x86, 0x3f, 0x02, 0x78, 0xf6, 0x67, 0xaf,
+	0xe4, 0x1a, 0x60, 0xb7, 0xbc, 0xbe, 0xa1, 0xb3, 0x96, 0x9a, 0x9f, 0x0c, 0x34, 0x29, 0x91, 0xd3,
+	0x93, 0xc5, 0xe6, 0x48, 0xc6, 0x10, 0x3a, 0xb1, 0x1b, 0x90, 0xeb, 0xe8, 0x55, 0xe3, 0xbb, 0xb8,
+	0x30, 0xd4, 0x19, 0x59, 0xdb, 0xdb, 0x0c, 0x5e, 0x64, 0x62, 0xde, 0xf4, 0xb9, 0xdd, 0xf5, 0x37,
+	0x31, 0xf2, 0x49, 0xf0, 0x65, 0xec, 0xa1, 0x5c, 0x94, 0xc8, 0xf3, 0x58, 0xc8, 0x3c, 0xc9, 0x19,
+	0xb7, 0xc5, 0x13, 0xf7, 0x84, 0x55, 0xa1, 0xf6, 0xfe, 0x44, 0xd7, 0xfe, 0x78, 0x77, 0x6c, 0xa1,
+	0x77, 0xbf, 0x03, 0x00, 0x00, 0xff, 0xff, 0x5f, 0xa5, 0x95, 0xcc, 0x24, 0x04, 0x00, 0x00,
+}
diff --git a/googleapis/spanner/v1/spanner.pb.go b/googleapis/spanner/v1/spanner.pb.go
new file mode 100644
index 00000000..e08f1603
--- /dev/null
+++ b/googleapis/spanner/v1/spanner.pb.go
@@ -0,0 +1,1217 @@
+// Code generated by protoc-gen-go.
+// source: google/spanner/v1/spanner.proto
+// DO NOT EDIT!
+
+package spanner
+
+import proto "github.com/golang/protobuf/proto"
+import fmt "fmt"
+import math "math"
+import _ "google.golang.org/genproto/googleapis/api/annotations"
+import _ "google.golang.org/genproto/googleapis/api/serviceconfig"
+import google_protobuf4 "github.com/golang/protobuf/ptypes/empty"
+import google_protobuf1 "github.com/golang/protobuf/ptypes/struct"
+import google_protobuf3 "github.com/golang/protobuf/ptypes/timestamp"
+
+import (
+	context "golang.org/x/net/context"
+	grpc "google.golang.org/grpc"
+)
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ = proto.Marshal
+var _ = fmt.Errorf
+var _ = math.Inf
+
+// Mode in which the query must be processed.
+type ExecuteSqlRequest_QueryMode int32
+
+const (
+	// The default mode where only the query result, without any information
+	// about the query plan is returned.
+	ExecuteSqlRequest_NORMAL ExecuteSqlRequest_QueryMode = 0
+	// This mode returns only the query plan, without any result rows or
+	// execution statistics information.
+	ExecuteSqlRequest_PLAN ExecuteSqlRequest_QueryMode = 1
+	// This mode returns both the query plan and the execution statistics along
+	// with the result rows.
+	ExecuteSqlRequest_PROFILE ExecuteSqlRequest_QueryMode = 2
+)
+
+var ExecuteSqlRequest_QueryMode_name = map[int32]string{
+	0: "NORMAL",
+	1: "PLAN",
+	2: "PROFILE",
+}
+var ExecuteSqlRequest_QueryMode_value = map[string]int32{
+	"NORMAL":  0,
+	"PLAN":    1,
+	"PROFILE": 2,
+}
+
+func (x ExecuteSqlRequest_QueryMode) String() string {
+	return proto.EnumName(ExecuteSqlRequest_QueryMode_name, int32(x))
+}
+func (ExecuteSqlRequest_QueryMode) EnumDescriptor() ([]byte, []int) {
+	return fileDescriptor4, []int{4, 0}
+}
+
+// The request for [CreateSession][google.spanner.v1.Spanner.CreateSession].
+type CreateSessionRequest struct {
+	// Required. The database in which the new session is created.
+	Database string `protobuf:"bytes,1,opt,name=database" json:"database,omitempty"`
+}
+
+func (m *CreateSessionRequest) Reset()                    { *m = CreateSessionRequest{} }
+func (m *CreateSessionRequest) String() string            { return proto.CompactTextString(m) }
+func (*CreateSessionRequest) ProtoMessage()               {}
+func (*CreateSessionRequest) Descriptor() ([]byte, []int) { return fileDescriptor4, []int{0} }
+
+func (m *CreateSessionRequest) GetDatabase() string {
+	if m != nil {
+		return m.Database
+	}
+	return ""
+}
+
+// A session in the Cloud Spanner API.
+type Session struct {
+	// Required. The name of the session.
+	Name string `protobuf:"bytes,1,opt,name=name" json:"name,omitempty"`
+}
+
+func (m *Session) Reset()                    { *m = Session{} }
+func (m *Session) String() string            { return proto.CompactTextString(m) }
+func (*Session) ProtoMessage()               {}
+func (*Session) Descriptor() ([]byte, []int) { return fileDescriptor4, []int{1} }
+
+func (m *Session) GetName() string {
+	if m != nil {
+		return m.Name
+	}
+	return ""
+}
+
+// The request for [GetSession][google.spanner.v1.Spanner.GetSession].
+type GetSessionRequest struct {
+	// Required. The name of the session to retrieve.
+	Name string `protobuf:"bytes,1,opt,name=name" json:"name,omitempty"`
+}
+
+func (m *GetSessionRequest) Reset()                    { *m = GetSessionRequest{} }
+func (m *GetSessionRequest) String() string            { return proto.CompactTextString(m) }
+func (*GetSessionRequest) ProtoMessage()               {}
+func (*GetSessionRequest) Descriptor() ([]byte, []int) { return fileDescriptor4, []int{2} }
+
+func (m *GetSessionRequest) GetName() string {
+	if m != nil {
+		return m.Name
+	}
+	return ""
+}
+
+// The request for [DeleteSession][google.spanner.v1.Spanner.DeleteSession].
+type DeleteSessionRequest struct {
+	// Required. The name of the session to delete.
+	Name string `protobuf:"bytes,1,opt,name=name" json:"name,omitempty"`
+}
+
+func (m *DeleteSessionRequest) Reset()                    { *m = DeleteSessionRequest{} }
+func (m *DeleteSessionRequest) String() string            { return proto.CompactTextString(m) }
+func (*DeleteSessionRequest) ProtoMessage()               {}
+func (*DeleteSessionRequest) Descriptor() ([]byte, []int) { return fileDescriptor4, []int{3} }
+
+func (m *DeleteSessionRequest) GetName() string {
+	if m != nil {
+		return m.Name
+	}
+	return ""
+}
+
+// The request for [ExecuteSql][google.spanner.v1.Spanner.ExecuteSql] and
+// [ExecuteStreamingSql][google.spanner.v1.Spanner.ExecuteStreamingSql].
+type ExecuteSqlRequest struct {
+	// Required. The session in which the SQL query should be performed.
+	Session string `protobuf:"bytes,1,opt,name=session" json:"session,omitempty"`
+	// The transaction to use. If none is provided, the default is a
+	// temporary read-only transaction with strong concurrency.
+	Transaction *TransactionSelector `protobuf:"bytes,2,opt,name=transaction" json:"transaction,omitempty"`
+	// Required. The SQL query string.
+	Sql string `protobuf:"bytes,3,opt,name=sql" json:"sql,omitempty"`
+	// The SQL query string can contain parameter placeholders. A parameter
+	// placeholder consists of `'@'` followed by the parameter
+	// name. Parameter names consist of any combination of letters,
+	// numbers, and underscores.
+	//
+	// Parameters can appear anywhere that a literal value is expected.  The same
+	// parameter name can be used more than once, for example:
+	//   `"WHERE id > @msg_id AND id < @msg_id + 100"`
+	//
+	// It is an error to execute an SQL query with unbound parameters.
+	//
+	// Parameter values are specified using `params`, which is a JSON
+	// object whose keys are parameter names, and whose values are the
+	// corresponding parameter values.
+	Params *google_protobuf1.Struct `protobuf:"bytes,4,opt,name=params" json:"params,omitempty"`
+	// It is not always possible for Cloud Spanner to infer the right SQL type
+	// from a JSON value.  For example, values of type `BYTES` and values
+	// of type `STRING` both appear in [params][google.spanner.v1.ExecuteSqlRequest.params] as JSON strings.
+	//
+	// In these cases, `param_types` can be used to specify the exact
+	// SQL type for some or all of the SQL query parameters. See the
+	// definition of [Type][google.spanner.v1.Type] for more information
+	// about SQL types.
+	ParamTypes map[string]*Type `protobuf:"bytes,5,rep,name=param_types,json=paramTypes" json:"param_types,omitempty" protobuf_key:"bytes,1,opt,name=key" protobuf_val:"bytes,2,opt,name=value"`
+	// If this request is resuming a previously interrupted SQL query
+	// execution, `resume_token` should be copied from the last
+	// [PartialResultSet][google.spanner.v1.PartialResultSet] yielded before the interruption. Doing this
+	// enables the new SQL query execution to resume where the last one left
+	// off. The rest of the request parameters must exactly match the
+	// request that yielded this token.
+	ResumeToken []byte `protobuf:"bytes,6,opt,name=resume_token,json=resumeToken,proto3" json:"resume_token,omitempty"`
+	// Used to control the amount of debugging information returned in
+	// [ResultSetStats][google.spanner.v1.ResultSetStats].
+	QueryMode ExecuteSqlRequest_QueryMode `protobuf:"varint,7,opt,name=query_mode,json=queryMode,enum=google.spanner.v1.ExecuteSqlRequest_QueryMode" json:"query_mode,omitempty"`
+}
+
+func (m *ExecuteSqlRequest) Reset()                    { *m = ExecuteSqlRequest{} }
+func (m *ExecuteSqlRequest) String() string            { return proto.CompactTextString(m) }
+func (*ExecuteSqlRequest) ProtoMessage()               {}
+func (*ExecuteSqlRequest) Descriptor() ([]byte, []int) { return fileDescriptor4, []int{4} }
+
+func (m *ExecuteSqlRequest) GetSession() string {
+	if m != nil {
+		return m.Session
+	}
+	return ""
+}
+
+func (m *ExecuteSqlRequest) GetTransaction() *TransactionSelector {
+	if m != nil {
+		return m.Transaction
+	}
+	return nil
+}
+
+func (m *ExecuteSqlRequest) GetSql() string {
+	if m != nil {
+		return m.Sql
+	}
+	return ""
+}
+
+func (m *ExecuteSqlRequest) GetParams() *google_protobuf1.Struct {
+	if m != nil {
+		return m.Params
+	}
+	return nil
+}
+
+func (m *ExecuteSqlRequest) GetParamTypes() map[string]*Type {
+	if m != nil {
+		return m.ParamTypes
+	}
+	return nil
+}
+
+func (m *ExecuteSqlRequest) GetResumeToken() []byte {
+	if m != nil {
+		return m.ResumeToken
+	}
+	return nil
+}
+
+func (m *ExecuteSqlRequest) GetQueryMode() ExecuteSqlRequest_QueryMode {
+	if m != nil {
+		return m.QueryMode
+	}
+	return ExecuteSqlRequest_NORMAL
+}
+
+// The request for [Read][google.spanner.v1.Spanner.Read] and
+// [StreamingRead][google.spanner.v1.Spanner.StreamingRead].
+type ReadRequest struct {
+	// Required. The session in which the read should be performed.
+	Session string `protobuf:"bytes,1,opt,name=session" json:"session,omitempty"`
+	// The transaction to use. If none is provided, the default is a
+	// temporary read-only transaction with strong concurrency.
+	Transaction *TransactionSelector `protobuf:"bytes,2,opt,name=transaction" json:"transaction,omitempty"`
+	// Required. The name of the table in the database to be read.
+	Table string `protobuf:"bytes,3,opt,name=table" json:"table,omitempty"`
+	// If non-empty, the name of an index on [table][google.spanner.v1.ReadRequest.table]. This index is
+	// used instead of the table primary key when interpreting [key_set][google.spanner.v1.ReadRequest.key_set]
+	// and sorting result rows. See [key_set][google.spanner.v1.ReadRequest.key_set] for further information.
+	Index string `protobuf:"bytes,4,opt,name=index" json:"index,omitempty"`
+	// The columns of [table][google.spanner.v1.ReadRequest.table] to be returned for each row matching
+	// this request.
+	Columns []string `protobuf:"bytes,5,rep,name=columns" json:"columns,omitempty"`
+	// Required. `key_set` identifies the rows to be yielded. `key_set` names the
+	// primary keys of the rows in [table][google.spanner.v1.ReadRequest.table] to be yielded, unless [index][google.spanner.v1.ReadRequest.index]
+	// is present. If [index][google.spanner.v1.ReadRequest.index] is present, then [key_set][google.spanner.v1.ReadRequest.key_set] instead names
+	// index keys in [index][google.spanner.v1.ReadRequest.index].
+	//
+	// Rows are yielded in table primary key order (if [index][google.spanner.v1.ReadRequest.index] is empty)
+	// or index key order (if [index][google.spanner.v1.ReadRequest.index] is non-empty).
+	//
+	// It is not an error for the `key_set` to name rows that do not
+	// exist in the database. Read yields nothing for nonexistent rows.
+	KeySet *KeySet `protobuf:"bytes,6,opt,name=key_set,json=keySet" json:"key_set,omitempty"`
+	// If greater than zero, only the first `limit` rows are yielded. If `limit`
+	// is zero, the default is no limit.
+	Limit int64 `protobuf:"varint,8,opt,name=limit" json:"limit,omitempty"`
+	// If this request is resuming a previously interrupted read,
+	// `resume_token` should be copied from the last
+	// [PartialResultSet][google.spanner.v1.PartialResultSet] yielded before the interruption. Doing this
+	// enables the new read to resume where the last read left off. The
+	// rest of the request parameters must exactly match the request
+	// that yielded this token.
+	ResumeToken []byte `protobuf:"bytes,9,opt,name=resume_token,json=resumeToken,proto3" json:"resume_token,omitempty"`
+}
+
+func (m *ReadRequest) Reset()                    { *m = ReadRequest{} }
+func (m *ReadRequest) String() string            { return proto.CompactTextString(m) }
+func (*ReadRequest) ProtoMessage()               {}
+func (*ReadRequest) Descriptor() ([]byte, []int) { return fileDescriptor4, []int{5} }
+
+func (m *ReadRequest) GetSession() string {
+	if m != nil {
+		return m.Session
+	}
+	return ""
+}
+
+func (m *ReadRequest) GetTransaction() *TransactionSelector {
+	if m != nil {
+		return m.Transaction
+	}
+	return nil
+}
+
+func (m *ReadRequest) GetTable() string {
+	if m != nil {
+		return m.Table
+	}
+	return ""
+}
+
+func (m *ReadRequest) GetIndex() string {
+	if m != nil {
+		return m.Index
+	}
+	return ""
+}
+
+func (m *ReadRequest) GetColumns() []string {
+	if m != nil {
+		return m.Columns
+	}
+	return nil
+}
+
+func (m *ReadRequest) GetKeySet() *KeySet {
+	if m != nil {
+		return m.KeySet
+	}
+	return nil
+}
+
+func (m *ReadRequest) GetLimit() int64 {
+	if m != nil {
+		return m.Limit
+	}
+	return 0
+}
+
+func (m *ReadRequest) GetResumeToken() []byte {
+	if m != nil {
+		return m.ResumeToken
+	}
+	return nil
+}
+
+// The request for [BeginTransaction][google.spanner.v1.Spanner.BeginTransaction].
+type BeginTransactionRequest struct {
+	// Required. The session in which the transaction runs.
+	Session string `protobuf:"bytes,1,opt,name=session" json:"session,omitempty"`
+	// Required. Options for the new transaction.
+	Options *TransactionOptions `protobuf:"bytes,2,opt,name=options" json:"options,omitempty"`
+}
+
+func (m *BeginTransactionRequest) Reset()                    { *m = BeginTransactionRequest{} }
+func (m *BeginTransactionRequest) String() string            { return proto.CompactTextString(m) }
+func (*BeginTransactionRequest) ProtoMessage()               {}
+func (*BeginTransactionRequest) Descriptor() ([]byte, []int) { return fileDescriptor4, []int{6} }
+
+func (m *BeginTransactionRequest) GetSession() string {
+	if m != nil {
+		return m.Session
+	}
+	return ""
+}
+
+func (m *BeginTransactionRequest) GetOptions() *TransactionOptions {
+	if m != nil {
+		return m.Options
+	}
+	return nil
+}
+
+// The request for [Commit][google.spanner.v1.Spanner.Commit].
+type CommitRequest struct {
+	// Required. The session in which the transaction to be committed is running.
+	Session string `protobuf:"bytes,1,opt,name=session" json:"session,omitempty"`
+	// Required. The transaction in which to commit.
+	//
+	// Types that are valid to be assigned to Transaction:
+	//	*CommitRequest_TransactionId
+	//	*CommitRequest_SingleUseTransaction
+	Transaction isCommitRequest_Transaction `protobuf_oneof:"transaction"`
+	// The mutations to be executed when this transaction commits. All
+	// mutations are applied atomically, in the order they appear in
+	// this list.
+	Mutations []*Mutation `protobuf:"bytes,4,rep,name=mutations" json:"mutations,omitempty"`
+}
+
+func (m *CommitRequest) Reset()                    { *m = CommitRequest{} }
+func (m *CommitRequest) String() string            { return proto.CompactTextString(m) }
+func (*CommitRequest) ProtoMessage()               {}
+func (*CommitRequest) Descriptor() ([]byte, []int) { return fileDescriptor4, []int{7} }
+
+type isCommitRequest_Transaction interface {
+	isCommitRequest_Transaction()
+}
+
+type CommitRequest_TransactionId struct {
+	TransactionId []byte `protobuf:"bytes,2,opt,name=transaction_id,json=transactionId,proto3,oneof"`
+}
+type CommitRequest_SingleUseTransaction struct {
+	SingleUseTransaction *TransactionOptions `protobuf:"bytes,3,opt,name=single_use_transaction,json=singleUseTransaction,oneof"`
+}
+
+func (*CommitRequest_TransactionId) isCommitRequest_Transaction()        {}
+func (*CommitRequest_SingleUseTransaction) isCommitRequest_Transaction() {}
+
+func (m *CommitRequest) GetTransaction() isCommitRequest_Transaction {
+	if m != nil {
+		return m.Transaction
+	}
+	return nil
+}
+
+func (m *CommitRequest) GetSession() string {
+	if m != nil {
+		return m.Session
+	}
+	return ""
+}
+
+func (m *CommitRequest) GetTransactionId() []byte {
+	if x, ok := m.GetTransaction().(*CommitRequest_TransactionId); ok {
+		return x.TransactionId
+	}
+	return nil
+}
+
+func (m *CommitRequest) GetSingleUseTransaction() *TransactionOptions {
+	if x, ok := m.GetTransaction().(*CommitRequest_SingleUseTransaction); ok {
+		return x.SingleUseTransaction
+	}
+	return nil
+}
+
+func (m *CommitRequest) GetMutations() []*Mutation {
+	if m != nil {
+		return m.Mutations
+	}
+	return nil
+}
+
+// XXX_OneofFuncs is for the internal use of the proto package.
+func (*CommitRequest) XXX_OneofFuncs() (func(msg proto.Message, b *proto.Buffer) error, func(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error), func(msg proto.Message) (n int), []interface{}) {
+	return _CommitRequest_OneofMarshaler, _CommitRequest_OneofUnmarshaler, _CommitRequest_OneofSizer, []interface{}{
+		(*CommitRequest_TransactionId)(nil),
+		(*CommitRequest_SingleUseTransaction)(nil),
+	}
+}
+
+func _CommitRequest_OneofMarshaler(msg proto.Message, b *proto.Buffer) error {
+	m := msg.(*CommitRequest)
+	// transaction
+	switch x := m.Transaction.(type) {
+	case *CommitRequest_TransactionId:
+		b.EncodeVarint(2<<3 | proto.WireBytes)
+		b.EncodeRawBytes(x.TransactionId)
+	case *CommitRequest_SingleUseTransaction:
+		b.EncodeVarint(3<<3 | proto.WireBytes)
+		if err := b.EncodeMessage(x.SingleUseTransaction); err != nil {
+			return err
+		}
+	case nil:
+	default:
+		return fmt.Errorf("CommitRequest.Transaction has unexpected type %T", x)
+	}
+	return nil
+}
+
+func _CommitRequest_OneofUnmarshaler(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error) {
+	m := msg.(*CommitRequest)
+	switch tag {
+	case 2: // transaction.transaction_id
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		x, err := b.DecodeRawBytes(true)
+		m.Transaction = &CommitRequest_TransactionId{x}
+		return true, err
+	case 3: // transaction.single_use_transaction
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		msg := new(TransactionOptions)
+		err := b.DecodeMessage(msg)
+		m.Transaction = &CommitRequest_SingleUseTransaction{msg}
+		return true, err
+	default:
+		return false, nil
+	}
+}
+
+func _CommitRequest_OneofSizer(msg proto.Message) (n int) {
+	m := msg.(*CommitRequest)
+	// transaction
+	switch x := m.Transaction.(type) {
+	case *CommitRequest_TransactionId:
+		n += proto.SizeVarint(2<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(len(x.TransactionId)))
+		n += len(x.TransactionId)
+	case *CommitRequest_SingleUseTransaction:
+		s := proto.Size(x.SingleUseTransaction)
+		n += proto.SizeVarint(3<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(s))
+		n += s
+	case nil:
+	default:
+		panic(fmt.Sprintf("proto: unexpected type %T in oneof", x))
+	}
+	return n
+}
+
+// The response for [Commit][google.spanner.v1.Spanner.Commit].
+type CommitResponse struct {
+	// The Cloud Spanner timestamp at which the transaction committed.
+	CommitTimestamp *google_protobuf3.Timestamp `protobuf:"bytes,1,opt,name=commit_timestamp,json=commitTimestamp" json:"commit_timestamp,omitempty"`
+}
+
+func (m *CommitResponse) Reset()                    { *m = CommitResponse{} }
+func (m *CommitResponse) String() string            { return proto.CompactTextString(m) }
+func (*CommitResponse) ProtoMessage()               {}
+func (*CommitResponse) Descriptor() ([]byte, []int) { return fileDescriptor4, []int{8} }
+
+func (m *CommitResponse) GetCommitTimestamp() *google_protobuf3.Timestamp {
+	if m != nil {
+		return m.CommitTimestamp
+	}
+	return nil
+}
+
+// The request for [Rollback][google.spanner.v1.Spanner.Rollback].
+type RollbackRequest struct {
+	// Required. The session in which the transaction to roll back is running.
+	Session string `protobuf:"bytes,1,opt,name=session" json:"session,omitempty"`
+	// Required. The transaction to roll back.
+	TransactionId []byte `protobuf:"bytes,2,opt,name=transaction_id,json=transactionId,proto3" json:"transaction_id,omitempty"`
+}
+
+func (m *RollbackRequest) Reset()                    { *m = RollbackRequest{} }
+func (m *RollbackRequest) String() string            { return proto.CompactTextString(m) }
+func (*RollbackRequest) ProtoMessage()               {}
+func (*RollbackRequest) Descriptor() ([]byte, []int) { return fileDescriptor4, []int{9} }
+
+func (m *RollbackRequest) GetSession() string {
+	if m != nil {
+		return m.Session
+	}
+	return ""
+}
+
+func (m *RollbackRequest) GetTransactionId() []byte {
+	if m != nil {
+		return m.TransactionId
+	}
+	return nil
+}
+
+func init() {
+	proto.RegisterType((*CreateSessionRequest)(nil), "google.spanner.v1.CreateSessionRequest")
+	proto.RegisterType((*Session)(nil), "google.spanner.v1.Session")
+	proto.RegisterType((*GetSessionRequest)(nil), "google.spanner.v1.GetSessionRequest")
+	proto.RegisterType((*DeleteSessionRequest)(nil), "google.spanner.v1.DeleteSessionRequest")
+	proto.RegisterType((*ExecuteSqlRequest)(nil), "google.spanner.v1.ExecuteSqlRequest")
+	proto.RegisterType((*ReadRequest)(nil), "google.spanner.v1.ReadRequest")
+	proto.RegisterType((*BeginTransactionRequest)(nil), "google.spanner.v1.BeginTransactionRequest")
+	proto.RegisterType((*CommitRequest)(nil), "google.spanner.v1.CommitRequest")
+	proto.RegisterType((*CommitResponse)(nil), "google.spanner.v1.CommitResponse")
+	proto.RegisterType((*RollbackRequest)(nil), "google.spanner.v1.RollbackRequest")
+	proto.RegisterEnum("google.spanner.v1.ExecuteSqlRequest_QueryMode", ExecuteSqlRequest_QueryMode_name, ExecuteSqlRequest_QueryMode_value)
+}
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ context.Context
+var _ grpc.ClientConn
+
+// This is a compile-time assertion to ensure that this generated file
+// is compatible with the grpc package it is being compiled against.
+const _ = grpc.SupportPackageIsVersion4
+
+// Client API for Spanner service
+
+type SpannerClient interface {
+	// Creates a new session. A session can be used to perform
+	// transactions that read and/or modify data in a Cloud Spanner database.
+	// Sessions are meant to be reused for many consecutive
+	// transactions.
+	//
+	// Sessions can only execute one transaction at a time. To execute
+	// multiple concurrent read-write/write-only transactions, create
+	// multiple sessions. Note that standalone reads and queries use a
+	// transaction internally, and count toward the one transaction
+	// limit.
+	//
+	// Cloud Spanner limits the number of sessions that can exist at any given
+	// time; thus, it is a good idea to delete idle and/or unneeded sessions.
+	// Aside from explicit deletes, Cloud Spanner can delete sessions for
+	// which no operations are sent for more than an hour, or due to
+	// internal errors. If a session is deleted, requests to it
+	// return `NOT_FOUND`.
+	//
+	// Idle sessions can be kept alive by sending a trivial SQL query
+	// periodically, e.g., `"SELECT 1"`.
+	CreateSession(ctx context.Context, in *CreateSessionRequest, opts ...grpc.CallOption) (*Session, error)
+	// Gets a session. Returns `NOT_FOUND` if the session does not exist.
+	// This is mainly useful for determining whether a session is still
+	// alive.
+	GetSession(ctx context.Context, in *GetSessionRequest, opts ...grpc.CallOption) (*Session, error)
+	// Ends a session, releasing server resources associated with it.
+	DeleteSession(ctx context.Context, in *DeleteSessionRequest, opts ...grpc.CallOption) (*google_protobuf4.Empty, error)
+	// Executes an SQL query, returning all rows in a single reply. This
+	// method cannot be used to return a result set larger than 10 MiB;
+	// if the query yields more data than that, the query fails with
+	// a `FAILED_PRECONDITION` error.
+	//
+	// Queries inside read-write transactions might return `ABORTED`. If
+	// this occurs, the application should restart the transaction from
+	// the beginning. See [Transaction][google.spanner.v1.Transaction] for more details.
+	//
+	// Larger result sets can be fetched in streaming fashion by calling
+	// [ExecuteStreamingSql][google.spanner.v1.Spanner.ExecuteStreamingSql] instead.
+	ExecuteSql(ctx context.Context, in *ExecuteSqlRequest, opts ...grpc.CallOption) (*ResultSet, error)
+	// Like [ExecuteSql][google.spanner.v1.Spanner.ExecuteSql], except returns the result
+	// set as a stream. Unlike [ExecuteSql][google.spanner.v1.Spanner.ExecuteSql], there
+	// is no limit on the size of the returned result set. However, no
+	// individual row in the result set can exceed 100 MiB, and no
+	// column value can exceed 10 MiB.
+	ExecuteStreamingSql(ctx context.Context, in *ExecuteSqlRequest, opts ...grpc.CallOption) (Spanner_ExecuteStreamingSqlClient, error)
+	// Reads rows from the database using key lookups and scans, as a
+	// simple key/value style alternative to
+	// [ExecuteSql][google.spanner.v1.Spanner.ExecuteSql].  This method cannot be used to
+	// return a result set larger than 10 MiB; if the read matches more
+	// data than that, the read fails with a `FAILED_PRECONDITION`
+	// error.
+	//
+	// Reads inside read-write transactions might return `ABORTED`. If
+	// this occurs, the application should restart the transaction from
+	// the beginning. See [Transaction][google.spanner.v1.Transaction] for more details.
+	//
+	// Larger result sets can be yielded in streaming fashion by calling
+	// [StreamingRead][google.spanner.v1.Spanner.StreamingRead] instead.
+	Read(ctx context.Context, in *ReadRequest, opts ...grpc.CallOption) (*ResultSet, error)
+	// Like [Read][google.spanner.v1.Spanner.Read], except returns the result set as a
+	// stream. Unlike [Read][google.spanner.v1.Spanner.Read], there is no limit on the
+	// size of the returned result set. However, no individual row in
+	// the result set can exceed 100 MiB, and no column value can exceed
+	// 10 MiB.
+	StreamingRead(ctx context.Context, in *ReadRequest, opts ...grpc.CallOption) (Spanner_StreamingReadClient, error)
+	// Begins a new transaction. This step can often be skipped:
+	// [Read][google.spanner.v1.Spanner.Read], [ExecuteSql][google.spanner.v1.Spanner.ExecuteSql] and
+	// [Commit][google.spanner.v1.Spanner.Commit] can begin a new transaction as a
+	// side-effect.
+	BeginTransaction(ctx context.Context, in *BeginTransactionRequest, opts ...grpc.CallOption) (*Transaction, error)
+	// Commits a transaction. The request includes the mutations to be
+	// applied to rows in the database.
+	//
+	// `Commit` might return an `ABORTED` error. This can occur at any time;
+	// commonly, the cause is conflicts with concurrent
+	// transactions. However, it can also happen for a variety of other
+	// reasons. If `Commit` returns `ABORTED`, the caller should re-attempt
+	// the transaction from the beginning, re-using the same session.
+	Commit(ctx context.Context, in *CommitRequest, opts ...grpc.CallOption) (*CommitResponse, error)
+	// Rolls back a transaction, releasing any locks it holds. It is a good
+	// idea to call this for any transaction that includes one or more
+	// [Read][google.spanner.v1.Spanner.Read] or [ExecuteSql][google.spanner.v1.Spanner.ExecuteSql] requests and
+	// ultimately decides not to commit.
+	//
+	// `Rollback` returns `OK` if it successfully aborts the transaction, the
+	// transaction was already aborted, or the transaction is not
+	// found. `Rollback` never returns `ABORTED`.
+	Rollback(ctx context.Context, in *RollbackRequest, opts ...grpc.CallOption) (*google_protobuf4.Empty, error)
+}
+
+type spannerClient struct {
+	cc *grpc.ClientConn
+}
+
+func NewSpannerClient(cc *grpc.ClientConn) SpannerClient {
+	return &spannerClient{cc}
+}
+
+func (c *spannerClient) CreateSession(ctx context.Context, in *CreateSessionRequest, opts ...grpc.CallOption) (*Session, error) {
+	out := new(Session)
+	err := grpc.Invoke(ctx, "/google.spanner.v1.Spanner/CreateSession", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *spannerClient) GetSession(ctx context.Context, in *GetSessionRequest, opts ...grpc.CallOption) (*Session, error) {
+	out := new(Session)
+	err := grpc.Invoke(ctx, "/google.spanner.v1.Spanner/GetSession", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *spannerClient) DeleteSession(ctx context.Context, in *DeleteSessionRequest, opts ...grpc.CallOption) (*google_protobuf4.Empty, error) {
+	out := new(google_protobuf4.Empty)
+	err := grpc.Invoke(ctx, "/google.spanner.v1.Spanner/DeleteSession", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *spannerClient) ExecuteSql(ctx context.Context, in *ExecuteSqlRequest, opts ...grpc.CallOption) (*ResultSet, error) {
+	out := new(ResultSet)
+	err := grpc.Invoke(ctx, "/google.spanner.v1.Spanner/ExecuteSql", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *spannerClient) ExecuteStreamingSql(ctx context.Context, in *ExecuteSqlRequest, opts ...grpc.CallOption) (Spanner_ExecuteStreamingSqlClient, error) {
+	stream, err := grpc.NewClientStream(ctx, &_Spanner_serviceDesc.Streams[0], c.cc, "/google.spanner.v1.Spanner/ExecuteStreamingSql", opts...)
+	if err != nil {
+		return nil, err
+	}
+	x := &spannerExecuteStreamingSqlClient{stream}
+	if err := x.ClientStream.SendMsg(in); err != nil {
+		return nil, err
+	}
+	if err := x.ClientStream.CloseSend(); err != nil {
+		return nil, err
+	}
+	return x, nil
+}
+
+type Spanner_ExecuteStreamingSqlClient interface {
+	Recv() (*PartialResultSet, error)
+	grpc.ClientStream
+}
+
+type spannerExecuteStreamingSqlClient struct {
+	grpc.ClientStream
+}
+
+func (x *spannerExecuteStreamingSqlClient) Recv() (*PartialResultSet, error) {
+	m := new(PartialResultSet)
+	if err := x.ClientStream.RecvMsg(m); err != nil {
+		return nil, err
+	}
+	return m, nil
+}
+
+func (c *spannerClient) Read(ctx context.Context, in *ReadRequest, opts ...grpc.CallOption) (*ResultSet, error) {
+	out := new(ResultSet)
+	err := grpc.Invoke(ctx, "/google.spanner.v1.Spanner/Read", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *spannerClient) StreamingRead(ctx context.Context, in *ReadRequest, opts ...grpc.CallOption) (Spanner_StreamingReadClient, error) {
+	stream, err := grpc.NewClientStream(ctx, &_Spanner_serviceDesc.Streams[1], c.cc, "/google.spanner.v1.Spanner/StreamingRead", opts...)
+	if err != nil {
+		return nil, err
+	}
+	x := &spannerStreamingReadClient{stream}
+	if err := x.ClientStream.SendMsg(in); err != nil {
+		return nil, err
+	}
+	if err := x.ClientStream.CloseSend(); err != nil {
+		return nil, err
+	}
+	return x, nil
+}
+
+type Spanner_StreamingReadClient interface {
+	Recv() (*PartialResultSet, error)
+	grpc.ClientStream
+}
+
+type spannerStreamingReadClient struct {
+	grpc.ClientStream
+}
+
+func (x *spannerStreamingReadClient) Recv() (*PartialResultSet, error) {
+	m := new(PartialResultSet)
+	if err := x.ClientStream.RecvMsg(m); err != nil {
+		return nil, err
+	}
+	return m, nil
+}
+
+func (c *spannerClient) BeginTransaction(ctx context.Context, in *BeginTransactionRequest, opts ...grpc.CallOption) (*Transaction, error) {
+	out := new(Transaction)
+	err := grpc.Invoke(ctx, "/google.spanner.v1.Spanner/BeginTransaction", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *spannerClient) Commit(ctx context.Context, in *CommitRequest, opts ...grpc.CallOption) (*CommitResponse, error) {
+	out := new(CommitResponse)
+	err := grpc.Invoke(ctx, "/google.spanner.v1.Spanner/Commit", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+func (c *spannerClient) Rollback(ctx context.Context, in *RollbackRequest, opts ...grpc.CallOption) (*google_protobuf4.Empty, error) {
+	out := new(google_protobuf4.Empty)
+	err := grpc.Invoke(ctx, "/google.spanner.v1.Spanner/Rollback", in, out, c.cc, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return out, nil
+}
+
+// Server API for Spanner service
+
+type SpannerServer interface {
+	// Creates a new session. A session can be used to perform
+	// transactions that read and/or modify data in a Cloud Spanner database.
+	// Sessions are meant to be reused for many consecutive
+	// transactions.
+	//
+	// Sessions can only execute one transaction at a time. To execute
+	// multiple concurrent read-write/write-only transactions, create
+	// multiple sessions. Note that standalone reads and queries use a
+	// transaction internally, and count toward the one transaction
+	// limit.
+	//
+	// Cloud Spanner limits the number of sessions that can exist at any given
+	// time; thus, it is a good idea to delete idle and/or unneeded sessions.
+	// Aside from explicit deletes, Cloud Spanner can delete sessions for
+	// which no operations are sent for more than an hour, or due to
+	// internal errors. If a session is deleted, requests to it
+	// return `NOT_FOUND`.
+	//
+	// Idle sessions can be kept alive by sending a trivial SQL query
+	// periodically, e.g., `"SELECT 1"`.
+	CreateSession(context.Context, *CreateSessionRequest) (*Session, error)
+	// Gets a session. Returns `NOT_FOUND` if the session does not exist.
+	// This is mainly useful for determining whether a session is still
+	// alive.
+	GetSession(context.Context, *GetSessionRequest) (*Session, error)
+	// Ends a session, releasing server resources associated with it.
+	DeleteSession(context.Context, *DeleteSessionRequest) (*google_protobuf4.Empty, error)
+	// Executes an SQL query, returning all rows in a single reply. This
+	// method cannot be used to return a result set larger than 10 MiB;
+	// if the query yields more data than that, the query fails with
+	// a `FAILED_PRECONDITION` error.
+	//
+	// Queries inside read-write transactions might return `ABORTED`. If
+	// this occurs, the application should restart the transaction from
+	// the beginning. See [Transaction][google.spanner.v1.Transaction] for more details.
+	//
+	// Larger result sets can be fetched in streaming fashion by calling
+	// [ExecuteStreamingSql][google.spanner.v1.Spanner.ExecuteStreamingSql] instead.
+	ExecuteSql(context.Context, *ExecuteSqlRequest) (*ResultSet, error)
+	// Like [ExecuteSql][google.spanner.v1.Spanner.ExecuteSql], except returns the result
+	// set as a stream. Unlike [ExecuteSql][google.spanner.v1.Spanner.ExecuteSql], there
+	// is no limit on the size of the returned result set. However, no
+	// individual row in the result set can exceed 100 MiB, and no
+	// column value can exceed 10 MiB.
+	ExecuteStreamingSql(*ExecuteSqlRequest, Spanner_ExecuteStreamingSqlServer) error
+	// Reads rows from the database using key lookups and scans, as a
+	// simple key/value style alternative to
+	// [ExecuteSql][google.spanner.v1.Spanner.ExecuteSql].  This method cannot be used to
+	// return a result set larger than 10 MiB; if the read matches more
+	// data than that, the read fails with a `FAILED_PRECONDITION`
+	// error.
+	//
+	// Reads inside read-write transactions might return `ABORTED`. If
+	// this occurs, the application should restart the transaction from
+	// the beginning. See [Transaction][google.spanner.v1.Transaction] for more details.
+	//
+	// Larger result sets can be yielded in streaming fashion by calling
+	// [StreamingRead][google.spanner.v1.Spanner.StreamingRead] instead.
+	Read(context.Context, *ReadRequest) (*ResultSet, error)
+	// Like [Read][google.spanner.v1.Spanner.Read], except returns the result set as a
+	// stream. Unlike [Read][google.spanner.v1.Spanner.Read], there is no limit on the
+	// size of the returned result set. However, no individual row in
+	// the result set can exceed 100 MiB, and no column value can exceed
+	// 10 MiB.
+	StreamingRead(*ReadRequest, Spanner_StreamingReadServer) error
+	// Begins a new transaction. This step can often be skipped:
+	// [Read][google.spanner.v1.Spanner.Read], [ExecuteSql][google.spanner.v1.Spanner.ExecuteSql] and
+	// [Commit][google.spanner.v1.Spanner.Commit] can begin a new transaction as a
+	// side-effect.
+	BeginTransaction(context.Context, *BeginTransactionRequest) (*Transaction, error)
+	// Commits a transaction. The request includes the mutations to be
+	// applied to rows in the database.
+	//
+	// `Commit` might return an `ABORTED` error. This can occur at any time;
+	// commonly, the cause is conflicts with concurrent
+	// transactions. However, it can also happen for a variety of other
+	// reasons. If `Commit` returns `ABORTED`, the caller should re-attempt
+	// the transaction from the beginning, re-using the same session.
+	Commit(context.Context, *CommitRequest) (*CommitResponse, error)
+	// Rolls back a transaction, releasing any locks it holds. It is a good
+	// idea to call this for any transaction that includes one or more
+	// [Read][google.spanner.v1.Spanner.Read] or [ExecuteSql][google.spanner.v1.Spanner.ExecuteSql] requests and
+	// ultimately decides not to commit.
+	//
+	// `Rollback` returns `OK` if it successfully aborts the transaction, the
+	// transaction was already aborted, or the transaction is not
+	// found. `Rollback` never returns `ABORTED`.
+	Rollback(context.Context, *RollbackRequest) (*google_protobuf4.Empty, error)
+}
+
+func RegisterSpannerServer(s *grpc.Server, srv SpannerServer) {
+	s.RegisterService(&_Spanner_serviceDesc, srv)
+}
+
+func _Spanner_CreateSession_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(CreateSessionRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(SpannerServer).CreateSession(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.v1.Spanner/CreateSession",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(SpannerServer).CreateSession(ctx, req.(*CreateSessionRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _Spanner_GetSession_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(GetSessionRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(SpannerServer).GetSession(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.v1.Spanner/GetSession",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(SpannerServer).GetSession(ctx, req.(*GetSessionRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _Spanner_DeleteSession_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(DeleteSessionRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(SpannerServer).DeleteSession(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.v1.Spanner/DeleteSession",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(SpannerServer).DeleteSession(ctx, req.(*DeleteSessionRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _Spanner_ExecuteSql_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(ExecuteSqlRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(SpannerServer).ExecuteSql(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.v1.Spanner/ExecuteSql",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(SpannerServer).ExecuteSql(ctx, req.(*ExecuteSqlRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _Spanner_ExecuteStreamingSql_Handler(srv interface{}, stream grpc.ServerStream) error {
+	m := new(ExecuteSqlRequest)
+	if err := stream.RecvMsg(m); err != nil {
+		return err
+	}
+	return srv.(SpannerServer).ExecuteStreamingSql(m, &spannerExecuteStreamingSqlServer{stream})
+}
+
+type Spanner_ExecuteStreamingSqlServer interface {
+	Send(*PartialResultSet) error
+	grpc.ServerStream
+}
+
+type spannerExecuteStreamingSqlServer struct {
+	grpc.ServerStream
+}
+
+func (x *spannerExecuteStreamingSqlServer) Send(m *PartialResultSet) error {
+	return x.ServerStream.SendMsg(m)
+}
+
+func _Spanner_Read_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(ReadRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(SpannerServer).Read(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.v1.Spanner/Read",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(SpannerServer).Read(ctx, req.(*ReadRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _Spanner_StreamingRead_Handler(srv interface{}, stream grpc.ServerStream) error {
+	m := new(ReadRequest)
+	if err := stream.RecvMsg(m); err != nil {
+		return err
+	}
+	return srv.(SpannerServer).StreamingRead(m, &spannerStreamingReadServer{stream})
+}
+
+type Spanner_StreamingReadServer interface {
+	Send(*PartialResultSet) error
+	grpc.ServerStream
+}
+
+type spannerStreamingReadServer struct {
+	grpc.ServerStream
+}
+
+func (x *spannerStreamingReadServer) Send(m *PartialResultSet) error {
+	return x.ServerStream.SendMsg(m)
+}
+
+func _Spanner_BeginTransaction_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(BeginTransactionRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(SpannerServer).BeginTransaction(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.v1.Spanner/BeginTransaction",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(SpannerServer).BeginTransaction(ctx, req.(*BeginTransactionRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _Spanner_Commit_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(CommitRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(SpannerServer).Commit(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.v1.Spanner/Commit",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(SpannerServer).Commit(ctx, req.(*CommitRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+func _Spanner_Rollback_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+	in := new(RollbackRequest)
+	if err := dec(in); err != nil {
+		return nil, err
+	}
+	if interceptor == nil {
+		return srv.(SpannerServer).Rollback(ctx, in)
+	}
+	info := &grpc.UnaryServerInfo{
+		Server:     srv,
+		FullMethod: "/google.spanner.v1.Spanner/Rollback",
+	}
+	handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+		return srv.(SpannerServer).Rollback(ctx, req.(*RollbackRequest))
+	}
+	return interceptor(ctx, in, info, handler)
+}
+
+var _Spanner_serviceDesc = grpc.ServiceDesc{
+	ServiceName: "google.spanner.v1.Spanner",
+	HandlerType: (*SpannerServer)(nil),
+	Methods: []grpc.MethodDesc{
+		{
+			MethodName: "CreateSession",
+			Handler:    _Spanner_CreateSession_Handler,
+		},
+		{
+			MethodName: "GetSession",
+			Handler:    _Spanner_GetSession_Handler,
+		},
+		{
+			MethodName: "DeleteSession",
+			Handler:    _Spanner_DeleteSession_Handler,
+		},
+		{
+			MethodName: "ExecuteSql",
+			Handler:    _Spanner_ExecuteSql_Handler,
+		},
+		{
+			MethodName: "Read",
+			Handler:    _Spanner_Read_Handler,
+		},
+		{
+			MethodName: "BeginTransaction",
+			Handler:    _Spanner_BeginTransaction_Handler,
+		},
+		{
+			MethodName: "Commit",
+			Handler:    _Spanner_Commit_Handler,
+		},
+		{
+			MethodName: "Rollback",
+			Handler:    _Spanner_Rollback_Handler,
+		},
+	},
+	Streams: []grpc.StreamDesc{
+		{
+			StreamName:    "ExecuteStreamingSql",
+			Handler:       _Spanner_ExecuteStreamingSql_Handler,
+			ServerStreams: true,
+		},
+		{
+			StreamName:    "StreamingRead",
+			Handler:       _Spanner_StreamingRead_Handler,
+			ServerStreams: true,
+		},
+	},
+	Metadata: "google/spanner/v1/spanner.proto",
+}
+
+func init() { proto.RegisterFile("google/spanner/v1/spanner.proto", fileDescriptor4) }
+
+var fileDescriptor4 = []byte{
+	// 1188 bytes of a gzipped FileDescriptorProto
+	0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xbc, 0x97, 0x4d, 0x6f, 0x1b, 0x45,
+	0x18, 0xc7, 0xbb, 0x49, 0x6a, 0xc7, 0x8f, 0x93, 0xc6, 0x19, 0xd2, 0xc6, 0xb8, 0xa1, 0x75, 0xb7,
+	0x94, 0x58, 0x96, 0xf0, 0x52, 0xc3, 0x21, 0x18, 0x10, 0xad, 0x5b, 0xb7, 0x89, 0xf2, 0xe6, 0xac,
+	0x5d, 0x2a, 0x55, 0x42, 0xd6, 0xd8, 0x7e, 0x30, 0x8b, 0xf7, 0x2d, 0x3b, 0xe3, 0xa8, 0x16, 0xea,
+	0x85, 0x2b, 0x17, 0x5e, 0x0e, 0x70, 0xe0, 0x06, 0x47, 0xee, 0xdc, 0xf8, 0x12, 0x7c, 0x05, 0x2e,
+	0x7c, 0x06, 0x2e, 0x68, 0x66, 0x77, 0x9d, 0x8d, 0x77, 0x9b, 0xa4, 0x04, 0x71, 0xca, 0xbc, 0xfc,
+	0x67, 0x9e, 0xdf, 0xfc, 0xe7, 0xd9, 0x79, 0x1c, 0xb8, 0x39, 0x70, 0x9c, 0x81, 0x89, 0x1a, 0x73,
+	0xa9, 0x6d, 0xa3, 0xa7, 0x1d, 0xdd, 0x0d, 0x9b, 0x15, 0xd7, 0x73, 0xb8, 0x43, 0x96, 0x7d, 0x41,
+	0x25, 0x1c, 0x3d, 0xba, 0x5b, 0x58, 0x0b, 0xd6, 0x50, 0xd7, 0xd0, 0xa8, 0x6d, 0x3b, 0x9c, 0x72,
+	0xc3, 0xb1, 0x99, 0xbf, 0xa0, 0x70, 0x35, 0x3a, 0x3b, 0xe2, 0x9f, 0x07, 0xc3, 0xd7, 0x83, 0x61,
+	0xd9, 0xeb, 0x8e, 0x3e, 0xd3, 0xd0, 0x72, 0xf9, 0x38, 0x98, 0x5c, 0x9b, 0x9e, 0x64, 0xdc, 0x1b,
+	0xf5, 0x78, 0x30, 0x7b, 0x73, 0x7a, 0x96, 0x1b, 0x16, 0x32, 0x4e, 0x2d, 0x77, 0x6a, 0x79, 0xe4,
+	0x10, 0x43, 0x1c, 0x87, 0x40, 0xc5, 0xf8, 0xac, 0x35, 0xf2, 0x99, 0x03, 0x85, 0x1a, 0x57, 0x1c,
+	0x8e, 0xd0, 0x1b, 0x77, 0x5c, 0x93, 0x9e, 0xa2, 0xf1, 0x90, 0x8d, 0x4c, 0xde, 0x61, 0x18, 0x82,
+	0xde, 0x8e, 0x6b, 0xb8, 0x47, 0x6d, 0x46, 0x7b, 0x91, 0x60, 0x09, 0xb0, 0x7c, 0xec, 0xa2, 0x3f,
+	0xab, 0x56, 0x61, 0xe5, 0x81, 0x87, 0x94, 0x63, 0x0b, 0x19, 0x33, 0x1c, 0x5b, 0xc7, 0xc3, 0x11,
+	0x32, 0x4e, 0x0a, 0x30, 0xdf, 0xa7, 0x9c, 0x76, 0x29, 0xc3, 0xbc, 0x52, 0x54, 0x4a, 0x19, 0x7d,
+	0xd2, 0x57, 0xdf, 0x80, 0x74, 0xa0, 0x26, 0x04, 0xe6, 0x6c, 0x6a, 0x85, 0x12, 0xd9, 0x56, 0xd7,
+	0x61, 0xf9, 0x31, 0xf2, 0xa9, 0xfd, 0x92, 0x84, 0x65, 0x58, 0x79, 0x88, 0x26, 0xc6, 0x62, 0x27,
+	0x69, 0xbf, 0x9e, 0x83, 0xe5, 0xc6, 0x73, 0xec, 0x8d, 0x38, 0xb6, 0x0e, 0xcd, 0x50, 0x99, 0x87,
+	0x34, 0xf3, 0xd7, 0x06, 0xe2, 0xb0, 0x4b, 0x36, 0x21, 0x1b, 0xb1, 0x22, 0x3f, 0x53, 0x54, 0x4a,
+	0xd9, 0xea, 0x5b, 0x95, 0x58, 0x72, 0x55, 0xda, 0xc7, 0xaa, 0x16, 0x9a, 0xd8, 0xe3, 0x8e, 0xa7,
+	0x47, 0x97, 0x92, 0x1c, 0xcc, 0xb2, 0x43, 0x33, 0x3f, 0x2b, 0xf7, 0x17, 0x4d, 0xa2, 0x41, 0xca,
+	0xa5, 0x1e, 0xb5, 0x58, 0x7e, 0x4e, 0x6e, 0xbb, 0x1a, 0x6e, 0x1b, 0x26, 0x4c, 0xa5, 0x25, 0xd3,
+	0x49, 0x0f, 0x64, 0xe4, 0x09, 0x64, 0x65, 0xab, 0x23, 0x8c, 0x67, 0xf9, 0xcb, 0xc5, 0xd9, 0x52,
+	0xb6, 0xfa, 0x5e, 0x02, 0x4c, 0xec, 0x84, 0x95, 0xa6, 0x58, 0xd7, 0x16, 0xcb, 0x1a, 0x36, 0xf7,
+	0xc6, 0x3a, 0xb8, 0x93, 0x01, 0x72, 0x0b, 0x16, 0x44, 0x4a, 0x58, 0xd8, 0xe1, 0xce, 0x10, 0xed,
+	0x7c, 0xaa, 0xa8, 0x94, 0x16, 0xf4, 0xac, 0x3f, 0xd6, 0x16, 0x43, 0x64, 0x17, 0xc0, 0xcf, 0x2c,
+	0xcb, 0xe9, 0x63, 0x3e, 0x5d, 0x54, 0x4a, 0x57, 0xaa, 0x95, 0x73, 0x05, 0x3e, 0x10, 0xcb, 0x76,
+	0x9d, 0x3e, 0xea, 0x99, 0xc3, 0xb0, 0x59, 0xf8, 0x04, 0x96, 0xa6, 0x80, 0x84, 0x3d, 0x43, 0x1c,
+	0x07, 0xf6, 0x8b, 0x26, 0x79, 0x1b, 0x2e, 0x1f, 0x51, 0x73, 0x84, 0x81, 0xe9, 0xab, 0x49, 0xa6,
+	0x8f, 0x5d, 0xd4, 0x7d, 0x55, 0x6d, 0x66, 0x43, 0x51, 0x2b, 0x90, 0x99, 0xc4, 0x23, 0x00, 0xa9,
+	0xbd, 0x7d, 0x7d, 0xf7, 0xfe, 0x4e, 0xee, 0x12, 0x99, 0x87, 0xb9, 0xe6, 0xce, 0xfd, 0xbd, 0x9c,
+	0x42, 0xb2, 0x90, 0x6e, 0xea, 0xfb, 0x8f, 0xb6, 0x76, 0x1a, 0xb9, 0x19, 0xf5, 0x97, 0x19, 0xc8,
+	0xea, 0x48, 0xfb, 0xff, 0x67, 0x1e, 0xac, 0xc0, 0x65, 0x4e, 0xbb, 0x26, 0x06, 0x99, 0xe0, 0x77,
+	0xc4, 0xa8, 0x61, 0xf7, 0xf1, 0xb9, 0x4c, 0x85, 0x8c, 0xee, 0x77, 0x04, 0x4f, 0xcf, 0x31, 0x47,
+	0x96, 0xed, 0x5f, 0x76, 0x46, 0x0f, 0xbb, 0xa4, 0x0a, 0xe9, 0x21, 0x8e, 0xc5, 0x37, 0x2c, 0xaf,
+	0x2b, 0x5b, 0x7d, 0x3d, 0x81, 0x65, 0x1b, 0xc7, 0x2d, 0xe4, 0x7a, 0x6a, 0x28, 0xff, 0x8a, 0x18,
+	0xa6, 0x61, 0x19, 0x3c, 0x3f, 0x5f, 0x54, 0x4a, 0xb3, 0xba, 0xdf, 0x89, 0xdd, 0x7e, 0x26, 0x76,
+	0xfb, 0x2a, 0x87, 0xd5, 0x3a, 0x0e, 0x0c, 0x3b, 0x72, 0xb6, 0xb3, 0x1d, 0xfb, 0x18, 0xd2, 0x8e,
+	0x2b, 0x1f, 0xd8, 0xc0, 0xad, 0x3b, 0xa7, 0xbb, 0xb5, 0xef, 0x8b, 0xf5, 0x70, 0x95, 0xfa, 0xb7,
+	0x02, 0x8b, 0x0f, 0x1c, 0xcb, 0x32, 0xf8, 0xd9, 0xc1, 0xd6, 0xe1, 0x4a, 0xc4, 0xe3, 0x8e, 0xd1,
+	0x97, 0x31, 0x17, 0x36, 0x2f, 0xe9, 0x8b, 0x91, 0xf1, 0xad, 0x3e, 0xf9, 0x14, 0xae, 0x31, 0xc3,
+	0x1e, 0x98, 0xd8, 0x19, 0x31, 0xec, 0x44, 0xaf, 0x74, 0xf6, 0x15, 0x20, 0x37, 0x2f, 0xe9, 0x2b,
+	0xfe, 0x36, 0x4f, 0x18, 0x46, 0xa6, 0xc9, 0xfb, 0x90, 0x09, 0xdf, 0x68, 0xf1, 0x55, 0x8b, 0xef,
+	0xf3, 0x7a, 0xc2, 0x8e, 0xbb, 0x81, 0x46, 0x3f, 0x56, 0xd7, 0x17, 0x4f, 0x64, 0x98, 0xfa, 0x14,
+	0xae, 0x84, 0x87, 0x67, 0xae, 0x63, 0x33, 0x24, 0x0d, 0xc8, 0xf5, 0xe4, 0x48, 0x67, 0x52, 0x47,
+	0xa4, 0x0d, 0xd9, 0x6a, 0x21, 0xf6, 0x70, 0xb4, 0x43, 0x85, 0xbe, 0xe4, 0xaf, 0x99, 0x0c, 0xa8,
+	0x3a, 0x2c, 0xe9, 0x8e, 0x69, 0x76, 0x69, 0x6f, 0x78, 0xb6, 0xaf, 0x77, 0x92, 0x7d, 0x9d, 0x72,
+	0xb5, 0xfa, 0xd7, 0x02, 0xa4, 0x5b, 0xfe, 0xf1, 0xc8, 0x8f, 0xe2, 0xda, 0xa2, 0xa5, 0x80, 0xac,
+	0x27, 0x38, 0x90, 0x54, 0x2c, 0x0a, 0x85, 0x04, 0x61, 0x20, 0x51, 0xeb, 0x5f, 0xfd, 0xf1, 0xe7,
+	0xf7, 0x33, 0x1f, 0xaa, 0x35, 0x51, 0x78, 0xbe, 0x0c, 0x6b, 0xc8, 0x47, 0xae, 0xe7, 0x7c, 0x81,
+	0x3d, 0xce, 0xb4, 0xb2, 0x66, 0xd8, 0x8c, 0x53, 0xbb, 0x87, 0xa2, 0x1d, 0xce, 0x33, 0xad, 0xfc,
+	0x42, 0x0b, 0x0e, 0xc3, 0xc8, 0x37, 0x0a, 0xc0, 0x71, 0x49, 0x21, 0x6f, 0x26, 0x84, 0x8b, 0x55,
+	0x9c, 0x53, 0xa1, 0xee, 0x49, 0xa8, 0x1a, 0xd9, 0x90, 0x50, 0xa2, 0xc0, 0x9c, 0x03, 0x68, 0xc2,
+	0xa3, 0x95, 0x5f, 0x90, 0xef, 0x14, 0x58, 0x3c, 0x51, 0xbc, 0x12, 0xdd, 0x4a, 0x2a, 0x6f, 0x85,
+	0x6b, 0xb1, 0x5b, 0x6f, 0x88, 0x9f, 0x26, 0x21, 0x54, 0xf9, 0xdf, 0x43, 0xfd, 0xac, 0x00, 0x1c,
+	0xbf, 0xe4, 0x89, 0x3e, 0xc5, 0x1e, 0xfa, 0xc2, 0x5a, 0x82, 0x4a, 0x97, 0xbf, 0x34, 0x5a, 0xc8,
+	0xd5, 0x03, 0x09, 0xb5, 0xad, 0x3e, 0x92, 0x50, 0x41, 0xb0, 0x57, 0xe4, 0xaa, 0xe1, 0x24, 0x68,
+	0x4d, 0x29, 0x93, 0xdf, 0x15, 0x78, 0x2d, 0xc4, 0xe0, 0x1e, 0x52, 0xcb, 0xb0, 0x07, 0xe7, 0xc7,
+	0xbd, 0x9d, 0xa0, 0x6a, 0x52, 0x8f, 0x1b, 0xd4, 0x3c, 0xa6, 0x7e, 0x26, 0xa9, 0xdb, 0xea, 0xfe,
+	0x7f, 0x41, 0x1d, 0x61, 0xac, 0x29, 0xe5, 0x77, 0x14, 0xf2, 0xad, 0x02, 0x73, 0xa2, 0xfa, 0x90,
+	0x1b, 0x89, 0xd6, 0x4d, 0xca, 0xd2, 0x19, 0xd6, 0x6e, 0x4b, 0xc8, 0x86, 0x7a, 0xef, 0x22, 0x90,
+	0x1e, 0xd2, 0xbe, 0x30, 0xf5, 0x57, 0x05, 0x16, 0x27, 0xa4, 0xe7, 0x82, 0x3b, 0x97, 0x91, 0x6d,
+	0xc9, 0xb8, 0xa7, 0x6e, 0x5d, 0x84, 0x91, 0x45, 0xb9, 0x7c, 0x0b, 0x7f, 0x53, 0x20, 0x37, 0x5d,
+	0x9a, 0x48, 0x39, 0x81, 0xe8, 0x25, 0xf5, 0xab, 0x70, 0xe3, 0xf4, 0xf7, 0x5e, 0x7d, 0x2a, 0xc1,
+	0x0f, 0xd4, 0x9d, 0x8b, 0x80, 0x77, 0xa7, 0x82, 0x0b, 0xa3, 0x7f, 0x52, 0x20, 0xe5, 0x3f, 0xf0,
+	0xa4, 0x98, 0xf4, 0x3e, 0x46, 0x0b, 0x5f, 0xe1, 0xd6, 0x29, 0x0a, 0xbf, 0x3a, 0xa8, 0xbb, 0x12,
+	0xf4, 0xb1, 0x5a, 0xbf, 0x08, 0xa8, 0x5f, 0x2b, 0x04, 0xde, 0x0f, 0x0a, 0xcc, 0x87, 0x65, 0x82,
+	0xa8, 0x49, 0x29, 0x70, 0xb2, 0x86, 0xbc, 0xf4, 0x35, 0xda, 0x97, 0x5c, 0x5b, 0xea, 0xc3, 0x0b,
+	0x65, 0x67, 0x10, 0xac, 0xa6, 0x94, 0xeb, 0x14, 0xae, 0xf6, 0x1c, 0x2b, 0x4e, 0x54, 0x5f, 0x08,
+	0x2a, 0x50, 0x53, 0x00, 0x34, 0x95, 0x67, 0x1b, 0x81, 0x64, 0xe0, 0x98, 0xd4, 0x1e, 0x54, 0x1c,
+	0x6f, 0xa0, 0x0d, 0xd0, 0x96, 0x78, 0x9a, 0x3f, 0x45, 0x5d, 0x83, 0x45, 0xfe, 0x9f, 0xf9, 0x20,
+	0x68, 0x76, 0x53, 0x52, 0xf4, 0xee, 0x3f, 0x01, 0x00, 0x00, 0xff, 0xff, 0xa8, 0x5d, 0xc1, 0xa8,
+	0x65, 0x0e, 0x00, 0x00,
+}
diff --git a/googleapis/spanner/v1/transaction.pb.go b/googleapis/spanner/v1/transaction.pb.go
new file mode 100644
index 00000000..59aedb85
--- /dev/null
+++ b/googleapis/spanner/v1/transaction.pb.go
@@ -0,0 +1,830 @@
+// Code generated by protoc-gen-go.
+// source: google/spanner/v1/transaction.proto
+// DO NOT EDIT!
+
+package spanner
+
+import proto "github.com/golang/protobuf/proto"
+import fmt "fmt"
+import math "math"
+import _ "google.golang.org/genproto/googleapis/api/annotations"
+import google_protobuf2 "github.com/golang/protobuf/ptypes/duration"
+import google_protobuf3 "github.com/golang/protobuf/ptypes/timestamp"
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ = proto.Marshal
+var _ = fmt.Errorf
+var _ = math.Inf
+
+// # Transactions
+//
+//
+// Each session can have at most one active transaction at a time. After the
+// active transaction is completed, the session can immediately be
+// re-used for the next transaction. It is not necessary to create a
+// new session for each transaction.
+//
+// # Transaction Modes
+//
+// Cloud Spanner supports two transaction modes:
+//
+//   1. Locking read-write. This type of transaction is the only way
+//      to write data into Cloud Spanner. These transactions rely on
+//      pessimistic locking and, if necessary, two-phase commit.
+//      Locking read-write transactions may abort, requiring the
+//      application to retry.
+//
+//   2. Snapshot read-only. This transaction type provides guaranteed
+//      consistency across several reads, but does not allow
+//      writes. Snapshot read-only transactions can be configured to
+//      read at timestamps in the past. Snapshot read-only
+//      transactions do not need to be committed.
+//
+// For transactions that only read, snapshot read-only transactions
+// provide simpler semantics and are almost always faster. In
+// particular, read-only transactions do not take locks, so they do
+// not conflict with read-write transactions. As a consequence of not
+// taking locks, they also do not abort, so retry loops are not needed.
+//
+// Transactions may only read/write data in a single database. They
+// may, however, read/write data in different tables within that
+// database.
+//
+// ## Locking Read-Write Transactions
+//
+// Locking transactions may be used to atomically read-modify-write
+// data anywhere in a database. This type of transaction is externally
+// consistent.
+//
+// Clients should attempt to minimize the amount of time a transaction
+// is active. Faster transactions commit with higher probability
+// and cause less contention. Cloud Spanner attempts to keep read locks
+// active as long as the transaction continues to do reads, and the
+// transaction has not been terminated by
+// [Commit][google.spanner.v1.Spanner.Commit] or
+// [Rollback][google.spanner.v1.Spanner.Rollback].  Long periods of
+// inactivity at the client may cause Cloud Spanner to release a
+// transaction's locks and abort it.
+//
+// Reads performed within a transaction acquire locks on the data
+// being read. Writes can only be done at commit time, after all reads
+// have been completed.
+// Conceptually, a read-write transaction consists of zero or more
+// reads or SQL queries followed by
+// [Commit][google.spanner.v1.Spanner.Commit]. At any time before
+// [Commit][google.spanner.v1.Spanner.Commit], the client can send a
+// [Rollback][google.spanner.v1.Spanner.Rollback] request to abort the
+// transaction.
+//
+// ### Semantics
+//
+// Cloud Spanner can commit the transaction if all read locks it acquired
+// are still valid at commit time, and it is able to acquire write
+// locks for all writes. Cloud Spanner can abort the transaction for any
+// reason. If a commit attempt returns `ABORTED`, Cloud Spanner guarantees
+// that the transaction has not modified any user data in Cloud Spanner.
+//
+// Unless the transaction commits, Cloud Spanner makes no guarantees about
+// how long the transaction's locks were held for. It is an error to
+// use Cloud Spanner locks for any sort of mutual exclusion other than
+// between Cloud Spanner transactions themselves.
+//
+// ### Retrying Aborted Transactions
+//
+// When a transaction aborts, the application can choose to retry the
+// whole transaction again. To maximize the chances of successfully
+// committing the retry, the client should execute the retry in the
+// same session as the original attempt. The original session's lock
+// priority increases with each consecutive abort, meaning that each
+// attempt has a slightly better chance of success than the previous.
+//
+// Under some circumstances (e.g., many transactions attempting to
+// modify the same row(s)), a transaction can abort many times in a
+// short period before successfully committing. Thus, it is not a good
+// idea to cap the number of retries a transaction can attempt;
+// instead, it is better to limit the total amount of wall time spent
+// retrying.
+//
+// ### Idle Transactions
+//
+// A transaction is considered idle if it has no outstanding reads or
+// SQL queries and has not started a read or SQL query within the last 10
+// seconds. Idle transactions can be aborted by Cloud Spanner so that they
+// don't hold on to locks indefinitely. In that case, the commit will
+// fail with error `ABORTED`.
+//
+// If this behavior is undesirable, periodically executing a simple
+// SQL query in the transaction (e.g., `SELECT 1`) prevents the
+// transaction from becoming idle.
+//
+// ## Snapshot Read-Only Transactions
+//
+// Snapshot read-only transactions provides a simpler method than
+// locking read-write transactions for doing several consistent
+// reads. However, this type of transaction does not support writes.
+//
+// Snapshot transactions do not take locks. Instead, they work by
+// choosing a Cloud Spanner timestamp, then executing all reads at that
+// timestamp. Since they do not acquire locks, they do not block
+// concurrent read-write transactions.
+//
+// Unlike locking read-write transactions, snapshot read-only
+// transactions never abort. They can fail if the chosen read
+// timestamp is garbage collected; however, the default garbage
+// collection policy is generous enough that most applications do not
+// need to worry about this in practice.
+//
+// Snapshot read-only transactions do not need to call
+// [Commit][google.spanner.v1.Spanner.Commit] or
+// [Rollback][google.spanner.v1.Spanner.Rollback] (and in fact are not
+// permitted to do so).
+//
+// To execute a snapshot transaction, the client specifies a timestamp
+// bound, which tells Cloud Spanner how to choose a read timestamp.
+//
+// The types of timestamp bound are:
+//
+//   - Strong (the default).
+//   - Bounded staleness.
+//   - Exact staleness.
+//
+// If the Cloud Spanner database to be read is geographically distributed,
+// stale read-only transactions can execute more quickly than strong
+// or read-write transaction, because they are able to execute far
+// from the leader replica.
+//
+// Each type of timestamp bound is discussed in detail below.
+//
+// ### Strong
+//
+// Strong reads are guaranteed to see the effects of all transactions
+// that have committed before the start of the read. Furthermore, all
+// rows yielded by a single read are consistent with each other -- if
+// any part of the read observes a transaction, all parts of the read
+// see the transaction.
+//
+// Strong reads are not repeatable: two consecutive strong read-only
+// transactions might return inconsistent results if there are
+// concurrent writes. If consistency across reads is required, the
+// reads should be executed within a transaction or at an exact read
+// timestamp.
+//
+// See [TransactionOptions.ReadOnly.strong][google.spanner.v1.TransactionOptions.ReadOnly.strong].
+//
+// ### Exact Staleness
+//
+// These timestamp bounds execute reads at a user-specified
+// timestamp. Reads at a timestamp are guaranteed to see a consistent
+// prefix of the global transaction history: they observe
+// modifications done by all transactions with a commit timestamp <=
+// the read timestamp, and observe none of the modifications done by
+// transactions with a larger commit timestamp. They will block until
+// all conflicting transactions that may be assigned commit timestamps
+// <= the read timestamp have finished.
+//
+// The timestamp can either be expressed as an absolute Cloud Spanner commit
+// timestamp or a staleness relative to the current time.
+//
+// These modes do not require a "negotiation phase" to pick a
+// timestamp. As a result, they execute slightly faster than the
+// equivalent boundedly stale concurrency modes. On the other hand,
+// boundedly stale reads usually return fresher results.
+//
+// See [TransactionOptions.ReadOnly.read_timestamp][google.spanner.v1.TransactionOptions.ReadOnly.read_timestamp] and
+// [TransactionOptions.ReadOnly.exact_staleness][google.spanner.v1.TransactionOptions.ReadOnly.exact_staleness].
+//
+// ### Bounded Staleness
+//
+// Bounded staleness modes allow Cloud Spanner to pick the read timestamp,
+// subject to a user-provided staleness bound. Cloud Spanner chooses the
+// newest timestamp within the staleness bound that allows execution
+// of the reads at the closest available replica without blocking.
+//
+// All rows yielded are consistent with each other -- if any part of
+// the read observes a transaction, all parts of the read see the
+// transaction. Boundedly stale reads are not repeatable: two stale
+// reads, even if they use the same staleness bound, can execute at
+// different timestamps and thus return inconsistent results.
+//
+// Boundedly stale reads execute in two phases: the first phase
+// negotiates a timestamp among all replicas needed to serve the
+// read. In the second phase, reads are executed at the negotiated
+// timestamp.
+//
+// As a result of the two phase execution, bounded staleness reads are
+// usually a little slower than comparable exact staleness
+// reads. However, they are typically able to return fresher
+// results, and are more likely to execute at the closest replica.
+//
+// Because the timestamp negotiation requires up-front knowledge of
+// which rows will be read, it can only be used with single-use
+// read-only transactions.
+//
+// See [TransactionOptions.ReadOnly.max_staleness][google.spanner.v1.TransactionOptions.ReadOnly.max_staleness] and
+// [TransactionOptions.ReadOnly.min_read_timestamp][google.spanner.v1.TransactionOptions.ReadOnly.min_read_timestamp].
+//
+// ### Old Read Timestamps and Garbage Collection
+//
+// Cloud Spanner continuously garbage collects deleted and overwritten data
+// in the background to reclaim storage space. This process is known
+// as "version GC". By default, version GC reclaims versions after they
+// are one hour old. Because of this, Cloud Spanner cannot perform reads
+// at read timestamps more than one hour in the past. This
+// restriction also applies to in-progress reads and/or SQL queries whose
+// timestamp become too old while executing. Reads and SQL queries with
+// too-old read timestamps fail with the error `FAILED_PRECONDITION`.
+type TransactionOptions struct {
+	// Required. The type of transaction.
+	//
+	// Types that are valid to be assigned to Mode:
+	//	*TransactionOptions_ReadWrite_
+	//	*TransactionOptions_ReadOnly_
+	Mode isTransactionOptions_Mode `protobuf_oneof:"mode"`
+}
+
+func (m *TransactionOptions) Reset()                    { *m = TransactionOptions{} }
+func (m *TransactionOptions) String() string            { return proto.CompactTextString(m) }
+func (*TransactionOptions) ProtoMessage()               {}
+func (*TransactionOptions) Descriptor() ([]byte, []int) { return fileDescriptor5, []int{0} }
+
+type isTransactionOptions_Mode interface {
+	isTransactionOptions_Mode()
+}
+
+type TransactionOptions_ReadWrite_ struct {
+	ReadWrite *TransactionOptions_ReadWrite `protobuf:"bytes,1,opt,name=read_write,json=readWrite,oneof"`
+}
+type TransactionOptions_ReadOnly_ struct {
+	ReadOnly *TransactionOptions_ReadOnly `protobuf:"bytes,2,opt,name=read_only,json=readOnly,oneof"`
+}
+
+func (*TransactionOptions_ReadWrite_) isTransactionOptions_Mode() {}
+func (*TransactionOptions_ReadOnly_) isTransactionOptions_Mode()  {}
+
+func (m *TransactionOptions) GetMode() isTransactionOptions_Mode {
+	if m != nil {
+		return m.Mode
+	}
+	return nil
+}
+
+func (m *TransactionOptions) GetReadWrite() *TransactionOptions_ReadWrite {
+	if x, ok := m.GetMode().(*TransactionOptions_ReadWrite_); ok {
+		return x.ReadWrite
+	}
+	return nil
+}
+
+func (m *TransactionOptions) GetReadOnly() *TransactionOptions_ReadOnly {
+	if x, ok := m.GetMode().(*TransactionOptions_ReadOnly_); ok {
+		return x.ReadOnly
+	}
+	return nil
+}
+
+// XXX_OneofFuncs is for the internal use of the proto package.
+func (*TransactionOptions) XXX_OneofFuncs() (func(msg proto.Message, b *proto.Buffer) error, func(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error), func(msg proto.Message) (n int), []interface{}) {
+	return _TransactionOptions_OneofMarshaler, _TransactionOptions_OneofUnmarshaler, _TransactionOptions_OneofSizer, []interface{}{
+		(*TransactionOptions_ReadWrite_)(nil),
+		(*TransactionOptions_ReadOnly_)(nil),
+	}
+}
+
+func _TransactionOptions_OneofMarshaler(msg proto.Message, b *proto.Buffer) error {
+	m := msg.(*TransactionOptions)
+	// mode
+	switch x := m.Mode.(type) {
+	case *TransactionOptions_ReadWrite_:
+		b.EncodeVarint(1<<3 | proto.WireBytes)
+		if err := b.EncodeMessage(x.ReadWrite); err != nil {
+			return err
+		}
+	case *TransactionOptions_ReadOnly_:
+		b.EncodeVarint(2<<3 | proto.WireBytes)
+		if err := b.EncodeMessage(x.ReadOnly); err != nil {
+			return err
+		}
+	case nil:
+	default:
+		return fmt.Errorf("TransactionOptions.Mode has unexpected type %T", x)
+	}
+	return nil
+}
+
+func _TransactionOptions_OneofUnmarshaler(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error) {
+	m := msg.(*TransactionOptions)
+	switch tag {
+	case 1: // mode.read_write
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		msg := new(TransactionOptions_ReadWrite)
+		err := b.DecodeMessage(msg)
+		m.Mode = &TransactionOptions_ReadWrite_{msg}
+		return true, err
+	case 2: // mode.read_only
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		msg := new(TransactionOptions_ReadOnly)
+		err := b.DecodeMessage(msg)
+		m.Mode = &TransactionOptions_ReadOnly_{msg}
+		return true, err
+	default:
+		return false, nil
+	}
+}
+
+func _TransactionOptions_OneofSizer(msg proto.Message) (n int) {
+	m := msg.(*TransactionOptions)
+	// mode
+	switch x := m.Mode.(type) {
+	case *TransactionOptions_ReadWrite_:
+		s := proto.Size(x.ReadWrite)
+		n += proto.SizeVarint(1<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(s))
+		n += s
+	case *TransactionOptions_ReadOnly_:
+		s := proto.Size(x.ReadOnly)
+		n += proto.SizeVarint(2<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(s))
+		n += s
+	case nil:
+	default:
+		panic(fmt.Sprintf("proto: unexpected type %T in oneof", x))
+	}
+	return n
+}
+
+// Options for read-write transactions.
+type TransactionOptions_ReadWrite struct {
+}
+
+func (m *TransactionOptions_ReadWrite) Reset()                    { *m = TransactionOptions_ReadWrite{} }
+func (m *TransactionOptions_ReadWrite) String() string            { return proto.CompactTextString(m) }
+func (*TransactionOptions_ReadWrite) ProtoMessage()               {}
+func (*TransactionOptions_ReadWrite) Descriptor() ([]byte, []int) { return fileDescriptor5, []int{0, 0} }
+
+// Options for read-only transactions.
+type TransactionOptions_ReadOnly struct {
+	// How to choose the timestamp for the read-only transaction.
+	//
+	// Types that are valid to be assigned to TimestampBound:
+	//	*TransactionOptions_ReadOnly_Strong
+	//	*TransactionOptions_ReadOnly_MinReadTimestamp
+	//	*TransactionOptions_ReadOnly_MaxStaleness
+	//	*TransactionOptions_ReadOnly_ReadTimestamp
+	//	*TransactionOptions_ReadOnly_ExactStaleness
+	TimestampBound isTransactionOptions_ReadOnly_TimestampBound `protobuf_oneof:"timestamp_bound"`
+	// If true, the Cloud Spanner-selected read timestamp is included in
+	// the [Transaction][google.spanner.v1.Transaction] message that describes the transaction.
+	ReturnReadTimestamp bool `protobuf:"varint,6,opt,name=return_read_timestamp,json=returnReadTimestamp" json:"return_read_timestamp,omitempty"`
+}
+
+func (m *TransactionOptions_ReadOnly) Reset()                    { *m = TransactionOptions_ReadOnly{} }
+func (m *TransactionOptions_ReadOnly) String() string            { return proto.CompactTextString(m) }
+func (*TransactionOptions_ReadOnly) ProtoMessage()               {}
+func (*TransactionOptions_ReadOnly) Descriptor() ([]byte, []int) { return fileDescriptor5, []int{0, 1} }
+
+type isTransactionOptions_ReadOnly_TimestampBound interface {
+	isTransactionOptions_ReadOnly_TimestampBound()
+}
+
+type TransactionOptions_ReadOnly_Strong struct {
+	Strong bool `protobuf:"varint,1,opt,name=strong,oneof"`
+}
+type TransactionOptions_ReadOnly_MinReadTimestamp struct {
+	MinReadTimestamp *google_protobuf3.Timestamp `protobuf:"bytes,2,opt,name=min_read_timestamp,json=minReadTimestamp,oneof"`
+}
+type TransactionOptions_ReadOnly_MaxStaleness struct {
+	MaxStaleness *google_protobuf2.Duration `protobuf:"bytes,3,opt,name=max_staleness,json=maxStaleness,oneof"`
+}
+type TransactionOptions_ReadOnly_ReadTimestamp struct {
+	ReadTimestamp *google_protobuf3.Timestamp `protobuf:"bytes,4,opt,name=read_timestamp,json=readTimestamp,oneof"`
+}
+type TransactionOptions_ReadOnly_ExactStaleness struct {
+	ExactStaleness *google_protobuf2.Duration `protobuf:"bytes,5,opt,name=exact_staleness,json=exactStaleness,oneof"`
+}
+
+func (*TransactionOptions_ReadOnly_Strong) isTransactionOptions_ReadOnly_TimestampBound()           {}
+func (*TransactionOptions_ReadOnly_MinReadTimestamp) isTransactionOptions_ReadOnly_TimestampBound() {}
+func (*TransactionOptions_ReadOnly_MaxStaleness) isTransactionOptions_ReadOnly_TimestampBound()     {}
+func (*TransactionOptions_ReadOnly_ReadTimestamp) isTransactionOptions_ReadOnly_TimestampBound()    {}
+func (*TransactionOptions_ReadOnly_ExactStaleness) isTransactionOptions_ReadOnly_TimestampBound()   {}
+
+func (m *TransactionOptions_ReadOnly) GetTimestampBound() isTransactionOptions_ReadOnly_TimestampBound {
+	if m != nil {
+		return m.TimestampBound
+	}
+	return nil
+}
+
+func (m *TransactionOptions_ReadOnly) GetStrong() bool {
+	if x, ok := m.GetTimestampBound().(*TransactionOptions_ReadOnly_Strong); ok {
+		return x.Strong
+	}
+	return false
+}
+
+func (m *TransactionOptions_ReadOnly) GetMinReadTimestamp() *google_protobuf3.Timestamp {
+	if x, ok := m.GetTimestampBound().(*TransactionOptions_ReadOnly_MinReadTimestamp); ok {
+		return x.MinReadTimestamp
+	}
+	return nil
+}
+
+func (m *TransactionOptions_ReadOnly) GetMaxStaleness() *google_protobuf2.Duration {
+	if x, ok := m.GetTimestampBound().(*TransactionOptions_ReadOnly_MaxStaleness); ok {
+		return x.MaxStaleness
+	}
+	return nil
+}
+
+func (m *TransactionOptions_ReadOnly) GetReadTimestamp() *google_protobuf3.Timestamp {
+	if x, ok := m.GetTimestampBound().(*TransactionOptions_ReadOnly_ReadTimestamp); ok {
+		return x.ReadTimestamp
+	}
+	return nil
+}
+
+func (m *TransactionOptions_ReadOnly) GetExactStaleness() *google_protobuf2.Duration {
+	if x, ok := m.GetTimestampBound().(*TransactionOptions_ReadOnly_ExactStaleness); ok {
+		return x.ExactStaleness
+	}
+	return nil
+}
+
+func (m *TransactionOptions_ReadOnly) GetReturnReadTimestamp() bool {
+	if m != nil {
+		return m.ReturnReadTimestamp
+	}
+	return false
+}
+
+// XXX_OneofFuncs is for the internal use of the proto package.
+func (*TransactionOptions_ReadOnly) XXX_OneofFuncs() (func(msg proto.Message, b *proto.Buffer) error, func(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error), func(msg proto.Message) (n int), []interface{}) {
+	return _TransactionOptions_ReadOnly_OneofMarshaler, _TransactionOptions_ReadOnly_OneofUnmarshaler, _TransactionOptions_ReadOnly_OneofSizer, []interface{}{
+		(*TransactionOptions_ReadOnly_Strong)(nil),
+		(*TransactionOptions_ReadOnly_MinReadTimestamp)(nil),
+		(*TransactionOptions_ReadOnly_MaxStaleness)(nil),
+		(*TransactionOptions_ReadOnly_ReadTimestamp)(nil),
+		(*TransactionOptions_ReadOnly_ExactStaleness)(nil),
+	}
+}
+
+func _TransactionOptions_ReadOnly_OneofMarshaler(msg proto.Message, b *proto.Buffer) error {
+	m := msg.(*TransactionOptions_ReadOnly)
+	// timestamp_bound
+	switch x := m.TimestampBound.(type) {
+	case *TransactionOptions_ReadOnly_Strong:
+		t := uint64(0)
+		if x.Strong {
+			t = 1
+		}
+		b.EncodeVarint(1<<3 | proto.WireVarint)
+		b.EncodeVarint(t)
+	case *TransactionOptions_ReadOnly_MinReadTimestamp:
+		b.EncodeVarint(2<<3 | proto.WireBytes)
+		if err := b.EncodeMessage(x.MinReadTimestamp); err != nil {
+			return err
+		}
+	case *TransactionOptions_ReadOnly_MaxStaleness:
+		b.EncodeVarint(3<<3 | proto.WireBytes)
+		if err := b.EncodeMessage(x.MaxStaleness); err != nil {
+			return err
+		}
+	case *TransactionOptions_ReadOnly_ReadTimestamp:
+		b.EncodeVarint(4<<3 | proto.WireBytes)
+		if err := b.EncodeMessage(x.ReadTimestamp); err != nil {
+			return err
+		}
+	case *TransactionOptions_ReadOnly_ExactStaleness:
+		b.EncodeVarint(5<<3 | proto.WireBytes)
+		if err := b.EncodeMessage(x.ExactStaleness); err != nil {
+			return err
+		}
+	case nil:
+	default:
+		return fmt.Errorf("TransactionOptions_ReadOnly.TimestampBound has unexpected type %T", x)
+	}
+	return nil
+}
+
+func _TransactionOptions_ReadOnly_OneofUnmarshaler(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error) {
+	m := msg.(*TransactionOptions_ReadOnly)
+	switch tag {
+	case 1: // timestamp_bound.strong
+		if wire != proto.WireVarint {
+			return true, proto.ErrInternalBadWireType
+		}
+		x, err := b.DecodeVarint()
+		m.TimestampBound = &TransactionOptions_ReadOnly_Strong{x != 0}
+		return true, err
+	case 2: // timestamp_bound.min_read_timestamp
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		msg := new(google_protobuf3.Timestamp)
+		err := b.DecodeMessage(msg)
+		m.TimestampBound = &TransactionOptions_ReadOnly_MinReadTimestamp{msg}
+		return true, err
+	case 3: // timestamp_bound.max_staleness
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		msg := new(google_protobuf2.Duration)
+		err := b.DecodeMessage(msg)
+		m.TimestampBound = &TransactionOptions_ReadOnly_MaxStaleness{msg}
+		return true, err
+	case 4: // timestamp_bound.read_timestamp
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		msg := new(google_protobuf3.Timestamp)
+		err := b.DecodeMessage(msg)
+		m.TimestampBound = &TransactionOptions_ReadOnly_ReadTimestamp{msg}
+		return true, err
+	case 5: // timestamp_bound.exact_staleness
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		msg := new(google_protobuf2.Duration)
+		err := b.DecodeMessage(msg)
+		m.TimestampBound = &TransactionOptions_ReadOnly_ExactStaleness{msg}
+		return true, err
+	default:
+		return false, nil
+	}
+}
+
+func _TransactionOptions_ReadOnly_OneofSizer(msg proto.Message) (n int) {
+	m := msg.(*TransactionOptions_ReadOnly)
+	// timestamp_bound
+	switch x := m.TimestampBound.(type) {
+	case *TransactionOptions_ReadOnly_Strong:
+		n += proto.SizeVarint(1<<3 | proto.WireVarint)
+		n += 1
+	case *TransactionOptions_ReadOnly_MinReadTimestamp:
+		s := proto.Size(x.MinReadTimestamp)
+		n += proto.SizeVarint(2<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(s))
+		n += s
+	case *TransactionOptions_ReadOnly_MaxStaleness:
+		s := proto.Size(x.MaxStaleness)
+		n += proto.SizeVarint(3<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(s))
+		n += s
+	case *TransactionOptions_ReadOnly_ReadTimestamp:
+		s := proto.Size(x.ReadTimestamp)
+		n += proto.SizeVarint(4<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(s))
+		n += s
+	case *TransactionOptions_ReadOnly_ExactStaleness:
+		s := proto.Size(x.ExactStaleness)
+		n += proto.SizeVarint(5<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(s))
+		n += s
+	case nil:
+	default:
+		panic(fmt.Sprintf("proto: unexpected type %T in oneof", x))
+	}
+	return n
+}
+
+// A transaction.
+type Transaction struct {
+	// `id` may be used to identify the transaction in subsequent
+	// [Read][google.spanner.v1.Spanner.Read],
+	// [ExecuteSql][google.spanner.v1.Spanner.ExecuteSql],
+	// [Commit][google.spanner.v1.Spanner.Commit], or
+	// [Rollback][google.spanner.v1.Spanner.Rollback] calls.
+	//
+	// Single-use read-only transactions do not have IDs, because
+	// single-use transactions do not support multiple requests.
+	Id []byte `protobuf:"bytes,1,opt,name=id,proto3" json:"id,omitempty"`
+	// For snapshot read-only transactions, the read timestamp chosen
+	// for the transaction. Not returned by default: see
+	// [TransactionOptions.ReadOnly.return_read_timestamp][google.spanner.v1.TransactionOptions.ReadOnly.return_read_timestamp].
+	ReadTimestamp *google_protobuf3.Timestamp `protobuf:"bytes,2,opt,name=read_timestamp,json=readTimestamp" json:"read_timestamp,omitempty"`
+}
+
+func (m *Transaction) Reset()                    { *m = Transaction{} }
+func (m *Transaction) String() string            { return proto.CompactTextString(m) }
+func (*Transaction) ProtoMessage()               {}
+func (*Transaction) Descriptor() ([]byte, []int) { return fileDescriptor5, []int{1} }
+
+func (m *Transaction) GetId() []byte {
+	if m != nil {
+		return m.Id
+	}
+	return nil
+}
+
+func (m *Transaction) GetReadTimestamp() *google_protobuf3.Timestamp {
+	if m != nil {
+		return m.ReadTimestamp
+	}
+	return nil
+}
+
+// This message is used to select the transaction in which a
+// [Read][google.spanner.v1.Spanner.Read] or
+// [ExecuteSql][google.spanner.v1.Spanner.ExecuteSql] call runs.
+//
+// See [TransactionOptions][google.spanner.v1.TransactionOptions] for more information about transactions.
+type TransactionSelector struct {
+	// If no fields are set, the default is a single use transaction
+	// with strong concurrency.
+	//
+	// Types that are valid to be assigned to Selector:
+	//	*TransactionSelector_SingleUse
+	//	*TransactionSelector_Id
+	//	*TransactionSelector_Begin
+	Selector isTransactionSelector_Selector `protobuf_oneof:"selector"`
+}
+
+func (m *TransactionSelector) Reset()                    { *m = TransactionSelector{} }
+func (m *TransactionSelector) String() string            { return proto.CompactTextString(m) }
+func (*TransactionSelector) ProtoMessage()               {}
+func (*TransactionSelector) Descriptor() ([]byte, []int) { return fileDescriptor5, []int{2} }
+
+type isTransactionSelector_Selector interface {
+	isTransactionSelector_Selector()
+}
+
+type TransactionSelector_SingleUse struct {
+	SingleUse *TransactionOptions `protobuf:"bytes,1,opt,name=single_use,json=singleUse,oneof"`
+}
+type TransactionSelector_Id struct {
+	Id []byte `protobuf:"bytes,2,opt,name=id,proto3,oneof"`
+}
+type TransactionSelector_Begin struct {
+	Begin *TransactionOptions `protobuf:"bytes,3,opt,name=begin,oneof"`
+}
+
+func (*TransactionSelector_SingleUse) isTransactionSelector_Selector() {}
+func (*TransactionSelector_Id) isTransactionSelector_Selector()        {}
+func (*TransactionSelector_Begin) isTransactionSelector_Selector()     {}
+
+func (m *TransactionSelector) GetSelector() isTransactionSelector_Selector {
+	if m != nil {
+		return m.Selector
+	}
+	return nil
+}
+
+func (m *TransactionSelector) GetSingleUse() *TransactionOptions {
+	if x, ok := m.GetSelector().(*TransactionSelector_SingleUse); ok {
+		return x.SingleUse
+	}
+	return nil
+}
+
+func (m *TransactionSelector) GetId() []byte {
+	if x, ok := m.GetSelector().(*TransactionSelector_Id); ok {
+		return x.Id
+	}
+	return nil
+}
+
+func (m *TransactionSelector) GetBegin() *TransactionOptions {
+	if x, ok := m.GetSelector().(*TransactionSelector_Begin); ok {
+		return x.Begin
+	}
+	return nil
+}
+
+// XXX_OneofFuncs is for the internal use of the proto package.
+func (*TransactionSelector) XXX_OneofFuncs() (func(msg proto.Message, b *proto.Buffer) error, func(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error), func(msg proto.Message) (n int), []interface{}) {
+	return _TransactionSelector_OneofMarshaler, _TransactionSelector_OneofUnmarshaler, _TransactionSelector_OneofSizer, []interface{}{
+		(*TransactionSelector_SingleUse)(nil),
+		(*TransactionSelector_Id)(nil),
+		(*TransactionSelector_Begin)(nil),
+	}
+}
+
+func _TransactionSelector_OneofMarshaler(msg proto.Message, b *proto.Buffer) error {
+	m := msg.(*TransactionSelector)
+	// selector
+	switch x := m.Selector.(type) {
+	case *TransactionSelector_SingleUse:
+		b.EncodeVarint(1<<3 | proto.WireBytes)
+		if err := b.EncodeMessage(x.SingleUse); err != nil {
+			return err
+		}
+	case *TransactionSelector_Id:
+		b.EncodeVarint(2<<3 | proto.WireBytes)
+		b.EncodeRawBytes(x.Id)
+	case *TransactionSelector_Begin:
+		b.EncodeVarint(3<<3 | proto.WireBytes)
+		if err := b.EncodeMessage(x.Begin); err != nil {
+			return err
+		}
+	case nil:
+	default:
+		return fmt.Errorf("TransactionSelector.Selector has unexpected type %T", x)
+	}
+	return nil
+}
+
+func _TransactionSelector_OneofUnmarshaler(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error) {
+	m := msg.(*TransactionSelector)
+	switch tag {
+	case 1: // selector.single_use
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		msg := new(TransactionOptions)
+		err := b.DecodeMessage(msg)
+		m.Selector = &TransactionSelector_SingleUse{msg}
+		return true, err
+	case 2: // selector.id
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		x, err := b.DecodeRawBytes(true)
+		m.Selector = &TransactionSelector_Id{x}
+		return true, err
+	case 3: // selector.begin
+		if wire != proto.WireBytes {
+			return true, proto.ErrInternalBadWireType
+		}
+		msg := new(TransactionOptions)
+		err := b.DecodeMessage(msg)
+		m.Selector = &TransactionSelector_Begin{msg}
+		return true, err
+	default:
+		return false, nil
+	}
+}
+
+func _TransactionSelector_OneofSizer(msg proto.Message) (n int) {
+	m := msg.(*TransactionSelector)
+	// selector
+	switch x := m.Selector.(type) {
+	case *TransactionSelector_SingleUse:
+		s := proto.Size(x.SingleUse)
+		n += proto.SizeVarint(1<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(s))
+		n += s
+	case *TransactionSelector_Id:
+		n += proto.SizeVarint(2<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(len(x.Id)))
+		n += len(x.Id)
+	case *TransactionSelector_Begin:
+		s := proto.Size(x.Begin)
+		n += proto.SizeVarint(3<<3 | proto.WireBytes)
+		n += proto.SizeVarint(uint64(s))
+		n += s
+	case nil:
+	default:
+		panic(fmt.Sprintf("proto: unexpected type %T in oneof", x))
+	}
+	return n
+}
+
+func init() {
+	proto.RegisterType((*TransactionOptions)(nil), "google.spanner.v1.TransactionOptions")
+	proto.RegisterType((*TransactionOptions_ReadWrite)(nil), "google.spanner.v1.TransactionOptions.ReadWrite")
+	proto.RegisterType((*TransactionOptions_ReadOnly)(nil), "google.spanner.v1.TransactionOptions.ReadOnly")
+	proto.RegisterType((*Transaction)(nil), "google.spanner.v1.Transaction")
+	proto.RegisterType((*TransactionSelector)(nil), "google.spanner.v1.TransactionSelector")
+}
+
+func init() { proto.RegisterFile("google/spanner/v1/transaction.proto", fileDescriptor5) }
+
+var fileDescriptor5 = []byte{
+	// 503 bytes of a gzipped FileDescriptorProto
+	0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x8c, 0x94, 0xd1, 0x6a, 0xdb, 0x30,
+	0x14, 0x86, 0x9d, 0x34, 0x0d, 0xe9, 0x49, 0x9a, 0xa6, 0x2a, 0x85, 0xcc, 0x8c, 0x6d, 0x64, 0x0c,
+	0x76, 0x65, 0xd3, 0xee, 0x66, 0x30, 0x06, 0x5b, 0x56, 0x86, 0x19, 0x8c, 0x06, 0xb7, 0x63, 0xb0,
+	0x1b, 0x4f, 0x89, 0xcf, 0x8c, 0xc0, 0x96, 0x8c, 0x24, 0x77, 0xe9, 0xfd, 0x9e, 0x6a, 0x6f, 0xb1,
+	0x37, 0x1a, 0x96, 0xe5, 0xc4, 0x8d, 0x2f, 0x9a, 0x3b, 0x9f, 0x9c, 0xff, 0xff, 0xf5, 0xe9, 0x1c,
+	0x11, 0x78, 0x99, 0x08, 0x91, 0xa4, 0xe8, 0xab, 0x9c, 0x72, 0x8e, 0xd2, 0xbf, 0xbb, 0xf0, 0xb5,
+	0xa4, 0x5c, 0xd1, 0x95, 0x66, 0x82, 0x7b, 0xb9, 0x14, 0x5a, 0x90, 0xd3, 0x4a, 0xe4, 0x59, 0x91,
+	0x77, 0x77, 0xe1, 0x3e, 0xb5, 0x3e, 0x9a, 0x33, 0x9f, 0x72, 0x2e, 0x34, 0x2d, 0xf5, 0xaa, 0x32,
+	0xb8, 0xcf, 0x6c, 0xd7, 0x54, 0xcb, 0xe2, 0x97, 0x1f, 0x17, 0x92, 0x6e, 0x03, 0xdd, 0xe7, 0xbb,
+	0x7d, 0xcd, 0x32, 0x54, 0x9a, 0x66, 0x79, 0x25, 0x98, 0xfd, 0xeb, 0x01, 0xb9, 0xdd, 0x72, 0x5c,
+	0xe7, 0x26, 0x9d, 0x2c, 0x00, 0x24, 0xd2, 0x38, 0xfa, 0x2d, 0x99, 0xc6, 0x69, 0xe7, 0x45, 0xe7,
+	0xf5, 0xf0, 0xd2, 0xf7, 0x5a, 0x74, 0x5e, 0xdb, 0xea, 0x85, 0x48, 0xe3, 0xef, 0xa5, 0x2d, 0x70,
+	0xc2, 0x23, 0x59, 0x17, 0xe4, 0x2b, 0x98, 0x22, 0x12, 0x3c, 0xbd, 0x9f, 0x76, 0x4d, 0xa0, 0xb7,
+	0x7f, 0xe0, 0x35, 0x4f, 0xef, 0x03, 0x27, 0x1c, 0x48, 0xfb, 0xed, 0x0e, 0xe1, 0x68, 0x73, 0x90,
+	0xfb, 0xe7, 0x00, 0x06, 0xb5, 0x8a, 0x4c, 0xa1, 0xaf, 0xb4, 0x14, 0x3c, 0x31, 0xd8, 0x83, 0xc0,
+	0x09, 0x6d, 0x4d, 0xbe, 0x00, 0xc9, 0x18, 0x8f, 0x0c, 0xc6, 0x66, 0x0e, 0x96, 0xc5, 0xad, 0x59,
+	0xea, 0x49, 0x79, 0xb7, 0xb5, 0x22, 0x70, 0xc2, 0x49, 0xc6, 0x78, 0x79, 0xc0, 0xe6, 0x37, 0xf2,
+	0x01, 0x8e, 0x33, 0xba, 0x8e, 0x94, 0xa6, 0x29, 0x72, 0x54, 0x6a, 0x7a, 0x60, 0x62, 0x9e, 0xb4,
+	0x62, 0xae, 0xec, 0x42, 0x02, 0x27, 0x1c, 0x65, 0x74, 0x7d, 0x53, 0x1b, 0xc8, 0x27, 0x18, 0xef,
+	0x90, 0xf4, 0xf6, 0x20, 0x39, 0x96, 0x0f, 0x30, 0xae, 0xe0, 0x04, 0xd7, 0x74, 0xa5, 0x1b, 0x20,
+	0x87, 0x8f, 0x83, 0x8c, 0x8d, 0x67, 0x8b, 0x72, 0x09, 0xe7, 0x12, 0x75, 0x21, 0x5b, 0xb3, 0xe9,
+	0x97, 0x13, 0x0c, 0xcf, 0xaa, 0xe6, 0x83, 0x01, 0xcc, 0x4f, 0xe1, 0x64, 0xa3, 0x8b, 0x96, 0xa2,
+	0xe0, 0xf1, 0xbc, 0x0f, 0xbd, 0x4c, 0xc4, 0x38, 0xfb, 0x09, 0xc3, 0xc6, 0x1a, 0xc9, 0x18, 0xba,
+	0x2c, 0x36, 0xcb, 0x18, 0x85, 0x5d, 0x16, 0x93, 0x8f, 0xad, 0x8b, 0x3f, 0xba, 0x82, 0x9d, 0x6b,
+	0xcf, 0xfe, 0x76, 0xe0, 0xac, 0x71, 0xc4, 0x0d, 0xa6, 0xb8, 0xd2, 0x42, 0x92, 0xcf, 0x00, 0x8a,
+	0xf1, 0x24, 0xc5, 0xa8, 0x50, 0xf5, 0xb3, 0x7d, 0xb5, 0xd7, 0x2b, 0x2b, 0x1f, 0x6b, 0x65, 0xfd,
+	0xa6, 0x90, 0x4c, 0x0c, 0x72, 0x89, 0x35, 0x0a, 0x1c, 0x03, 0xfd, 0x1e, 0x0e, 0x97, 0x98, 0x30,
+	0x6e, 0xf7, 0xbc, 0x77, 0x68, 0xe5, 0x9a, 0x03, 0x0c, 0x94, 0x85, 0x9c, 0x23, 0x9c, 0xaf, 0x44,
+	0xd6, 0x0e, 0x98, 0x4f, 0x1a, 0x09, 0x8b, 0x72, 0x06, 0x8b, 0xce, 0x8f, 0xb7, 0x56, 0x96, 0x88,
+	0x94, 0xf2, 0xc4, 0x13, 0x32, 0xf1, 0x13, 0xe4, 0x66, 0x42, 0x7e, 0xd5, 0xa2, 0x39, 0x53, 0x8d,
+	0x7f, 0x95, 0x77, 0xf6, 0x73, 0xd9, 0x37, 0xa2, 0x37, 0xff, 0x03, 0x00, 0x00, 0xff, 0xff, 0xd6,
+	0x9c, 0xa4, 0x92, 0x79, 0x04, 0x00, 0x00,
+}
diff --git a/googleapis/spanner/v1/type.pb.go b/googleapis/spanner/v1/type.pb.go
new file mode 100644
index 00000000..ff193941
--- /dev/null
+++ b/googleapis/spanner/v1/type.pb.go
@@ -0,0 +1,216 @@
+// Code generated by protoc-gen-go.
+// source: google/spanner/v1/type.proto
+// DO NOT EDIT!
+
+package spanner
+
+import proto "github.com/golang/protobuf/proto"
+import fmt "fmt"
+import math "math"
+import _ "google.golang.org/genproto/googleapis/api/annotations"
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ = proto.Marshal
+var _ = fmt.Errorf
+var _ = math.Inf
+
+// `TypeCode` is used as part of [Type][google.spanner.v1.Type] to
+// indicate the type of a Cloud Spanner value.
+//
+// Each legal value of a type can be encoded to or decoded from a JSON
+// value, using the encodings described below. All Cloud Spanner values can
+// be `null`, regardless of type; `null`s are always encoded as a JSON
+// `null`.
+type TypeCode int32
+
+const (
+	// Not specified.
+	TypeCode_TYPE_CODE_UNSPECIFIED TypeCode = 0
+	// Encoded as JSON `true` or `false`.
+	TypeCode_BOOL TypeCode = 1
+	// Encoded as `string`, in decimal format.
+	TypeCode_INT64 TypeCode = 2
+	// Encoded as `number`, or the strings `"NaN"`, `"Infinity"`, or
+	// `"-Infinity"`.
+	TypeCode_FLOAT64 TypeCode = 3
+	// Encoded as `string` in RFC 3339 timestamp format. The time zone
+	// must be present, and must be `"Z"`.
+	TypeCode_TIMESTAMP TypeCode = 4
+	// Encoded as `string` in RFC 3339 date format.
+	TypeCode_DATE TypeCode = 5
+	// Encoded as `string`.
+	TypeCode_STRING TypeCode = 6
+	// Encoded as a base64-encoded `string`, as described in RFC 4648,
+	// section 4.
+	TypeCode_BYTES TypeCode = 7
+	// Encoded as `list`, where the list elements are represented
+	// according to [array_element_type][google.spanner.v1.Type.array_element_type].
+	TypeCode_ARRAY TypeCode = 8
+	// Encoded as `list`, where list element `i` is represented according
+	// to [struct_type.fields[i]][google.spanner.v1.StructType.fields].
+	TypeCode_STRUCT TypeCode = 9
+)
+
+var TypeCode_name = map[int32]string{
+	0: "TYPE_CODE_UNSPECIFIED",
+	1: "BOOL",
+	2: "INT64",
+	3: "FLOAT64",
+	4: "TIMESTAMP",
+	5: "DATE",
+	6: "STRING",
+	7: "BYTES",
+	8: "ARRAY",
+	9: "STRUCT",
+}
+var TypeCode_value = map[string]int32{
+	"TYPE_CODE_UNSPECIFIED": 0,
+	"BOOL":                  1,
+	"INT64":                 2,
+	"FLOAT64":               3,
+	"TIMESTAMP":             4,
+	"DATE":                  5,
+	"STRING":                6,
+	"BYTES":                 7,
+	"ARRAY":                 8,
+	"STRUCT":                9,
+}
+
+func (x TypeCode) String() string {
+	return proto.EnumName(TypeCode_name, int32(x))
+}
+func (TypeCode) EnumDescriptor() ([]byte, []int) { return fileDescriptor6, []int{0} }
+
+// `Type` indicates the type of a Cloud Spanner value, as might be stored in a
+// table cell or returned from an SQL query.
+type Type struct {
+	// Required. The [TypeCode][google.spanner.v1.TypeCode] for this type.
+	Code TypeCode `protobuf:"varint,1,opt,name=code,enum=google.spanner.v1.TypeCode" json:"code,omitempty"`
+	// If [code][google.spanner.v1.Type.code] == [ARRAY][google.spanner.v1.TypeCode.ARRAY], then `array_element_type`
+	// is the type of the array elements.
+	ArrayElementType *Type `protobuf:"bytes,2,opt,name=array_element_type,json=arrayElementType" json:"array_element_type,omitempty"`
+	// If [code][google.spanner.v1.Type.code] == [STRUCT][google.spanner.v1.TypeCode.STRUCT], then `struct_type`
+	// provides type information for the struct's fields.
+	StructType *StructType `protobuf:"bytes,3,opt,name=struct_type,json=structType" json:"struct_type,omitempty"`
+}
+
+func (m *Type) Reset()                    { *m = Type{} }
+func (m *Type) String() string            { return proto.CompactTextString(m) }
+func (*Type) ProtoMessage()               {}
+func (*Type) Descriptor() ([]byte, []int) { return fileDescriptor6, []int{0} }
+
+func (m *Type) GetCode() TypeCode {
+	if m != nil {
+		return m.Code
+	}
+	return TypeCode_TYPE_CODE_UNSPECIFIED
+}
+
+func (m *Type) GetArrayElementType() *Type {
+	if m != nil {
+		return m.ArrayElementType
+	}
+	return nil
+}
+
+func (m *Type) GetStructType() *StructType {
+	if m != nil {
+		return m.StructType
+	}
+	return nil
+}
+
+// `StructType` defines the fields of a [STRUCT][google.spanner.v1.TypeCode.STRUCT] type.
+type StructType struct {
+	// The list of fields that make up this struct. Order is
+	// significant, because values of this struct type are represented as
+	// lists, where the order of field values matches the order of
+	// fields in the [StructType][google.spanner.v1.StructType]. In turn, the order of fields
+	// matches the order of columns in a read request, or the order of
+	// fields in the `SELECT` clause of a query.
+	Fields []*StructType_Field `protobuf:"bytes,1,rep,name=fields" json:"fields,omitempty"`
+}
+
+func (m *StructType) Reset()                    { *m = StructType{} }
+func (m *StructType) String() string            { return proto.CompactTextString(m) }
+func (*StructType) ProtoMessage()               {}
+func (*StructType) Descriptor() ([]byte, []int) { return fileDescriptor6, []int{1} }
+
+func (m *StructType) GetFields() []*StructType_Field {
+	if m != nil {
+		return m.Fields
+	}
+	return nil
+}
+
+// Message representing a single field of a struct.
+type StructType_Field struct {
+	// The name of the field. For reads, this is the column name. For
+	// SQL queries, it is the column alias (e.g., `"Word"` in the
+	// query `"SELECT 'hello' AS Word"`), or the column name (e.g.,
+	// `"ColName"` in the query `"SELECT ColName FROM Table"`). Some
+	// columns might have an empty name (e.g., !"SELECT
+	// UPPER(ColName)"`). Note that a query result can contain
+	// multiple fields with the same name.
+	Name string `protobuf:"bytes,1,opt,name=name" json:"name,omitempty"`
+	// The type of the field.
+	Type *Type `protobuf:"bytes,2,opt,name=type" json:"type,omitempty"`
+}
+
+func (m *StructType_Field) Reset()                    { *m = StructType_Field{} }
+func (m *StructType_Field) String() string            { return proto.CompactTextString(m) }
+func (*StructType_Field) ProtoMessage()               {}
+func (*StructType_Field) Descriptor() ([]byte, []int) { return fileDescriptor6, []int{1, 0} }
+
+func (m *StructType_Field) GetName() string {
+	if m != nil {
+		return m.Name
+	}
+	return ""
+}
+
+func (m *StructType_Field) GetType() *Type {
+	if m != nil {
+		return m.Type
+	}
+	return nil
+}
+
+func init() {
+	proto.RegisterType((*Type)(nil), "google.spanner.v1.Type")
+	proto.RegisterType((*StructType)(nil), "google.spanner.v1.StructType")
+	proto.RegisterType((*StructType_Field)(nil), "google.spanner.v1.StructType.Field")
+	proto.RegisterEnum("google.spanner.v1.TypeCode", TypeCode_name, TypeCode_value)
+}
+
+func init() { proto.RegisterFile("google/spanner/v1/type.proto", fileDescriptor6) }
+
+var fileDescriptor6 = []byte{
+	// 413 bytes of a gzipped FileDescriptorProto
+	0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x8c, 0x92, 0xd1, 0x8a, 0xd3, 0x40,
+	0x14, 0x86, 0x9d, 0x6d, 0xda, 0x6d, 0x4e, 0x51, 0xc6, 0x81, 0xc5, 0xba, 0x2a, 0x94, 0xf5, 0xa6,
+	0x28, 0x24, 0x6c, 0x15, 0x11, 0x16, 0x84, 0x34, 0x9d, 0x6a, 0x60, 0xb7, 0x09, 0xc9, 0xec, 0x45,
+	0xbd, 0x30, 0x8c, 0xed, 0x18, 0x02, 0xe9, 0x4c, 0x48, 0xe2, 0x42, 0x5f, 0xc2, 0x1b, 0xdf, 0xc7,
+	0x67, 0x93, 0x99, 0x64, 0x55, 0xa8, 0xca, 0xde, 0xfd, 0x33, 0xff, 0xff, 0x9d, 0x39, 0x73, 0x38,
+	0xf0, 0x34, 0x53, 0x2a, 0x2b, 0x84, 0x5b, 0x97, 0x5c, 0x4a, 0x51, 0xb9, 0x37, 0xe7, 0x6e, 0xb3,
+	0x2f, 0x85, 0x53, 0x56, 0xaa, 0x51, 0xe4, 0x61, 0xeb, 0x3a, 0x9d, 0xeb, 0xdc, 0x9c, 0x9f, 0xde,
+	0x02, 0xbc, 0xcc, 0x5d, 0x2e, 0xa5, 0x6a, 0x78, 0x93, 0x2b, 0x59, 0xb7, 0xc0, 0xd9, 0x0f, 0x04,
+	0x16, 0xdb, 0x97, 0x82, 0xb8, 0x60, 0x6d, 0xd4, 0x56, 0x8c, 0xd1, 0x04, 0x4d, 0x1f, 0xcc, 0x9e,
+	0x38, 0x07, 0x85, 0x1c, 0x1d, 0xf3, 0xd5, 0x56, 0xc4, 0x26, 0x48, 0x28, 0x10, 0x5e, 0x55, 0x7c,
+	0x9f, 0x8a, 0x42, 0xec, 0x84, 0x6c, 0x52, 0xdd, 0xc6, 0xf8, 0x68, 0x82, 0xa6, 0xa3, 0xd9, 0xa3,
+	0x7f, 0xe0, 0x31, 0x36, 0x08, 0x6d, 0x09, 0xf3, 0xee, 0x3b, 0x18, 0xd5, 0x4d, 0xf5, 0x75, 0xd3,
+	0xf1, 0x3d, 0xc3, 0x3f, 0xfb, 0x0b, 0x9f, 0x98, 0x94, 0xa9, 0x02, 0xf5, 0x2f, 0x7d, 0xf6, 0x1d,
+	0x01, 0xfc, 0xb6, 0xc8, 0x05, 0x0c, 0xbe, 0xe4, 0xa2, 0xd8, 0xd6, 0x63, 0x34, 0xe9, 0x4d, 0x47,
+	0xb3, 0xe7, 0xff, 0xad, 0xe4, 0x2c, 0x75, 0x36, 0xee, 0x90, 0xd3, 0x0f, 0xd0, 0x37, 0x17, 0x84,
+	0x80, 0x25, 0xf9, 0xae, 0x1d, 0x86, 0x1d, 0x1b, 0x4d, 0x5e, 0x82, 0x75, 0x97, 0x1f, 0x9a, 0xd0,
+	0x8b, 0x6f, 0x08, 0x86, 0xb7, 0xf3, 0x22, 0x8f, 0xe1, 0x84, 0xad, 0x23, 0x9a, 0xfa, 0xe1, 0x82,
+	0xa6, 0xd7, 0xab, 0x24, 0xa2, 0x7e, 0xb0, 0x0c, 0xe8, 0x02, 0xdf, 0x23, 0x43, 0xb0, 0xe6, 0x61,
+	0x78, 0x89, 0x11, 0xb1, 0xa1, 0x1f, 0xac, 0xd8, 0x9b, 0xd7, 0xf8, 0x88, 0x8c, 0xe0, 0x78, 0x79,
+	0x19, 0x7a, 0xfa, 0xd0, 0x23, 0xf7, 0xc1, 0x66, 0xc1, 0x15, 0x4d, 0x98, 0x77, 0x15, 0x61, 0x4b,
+	0x03, 0x0b, 0x8f, 0x51, 0xdc, 0x27, 0x00, 0x83, 0x84, 0xc5, 0xc1, 0xea, 0x3d, 0x1e, 0x68, 0x78,
+	0xbe, 0x66, 0x34, 0xc1, 0xc7, 0x5a, 0x7a, 0x71, 0xec, 0xad, 0xf1, 0xb0, 0x4b, 0x5c, 0xfb, 0x0c,
+	0xdb, 0xf3, 0x4f, 0x70, 0xb2, 0x51, 0xbb, 0xc3, 0xa6, 0xe7, 0xb6, 0x6e, 0x33, 0xd2, 0xbb, 0x10,
+	0xa1, 0x8f, 0x6f, 0x3b, 0x3f, 0x53, 0x05, 0x97, 0x99, 0xa3, 0xaa, 0xcc, 0xcd, 0x84, 0x34, 0x9b,
+	0xe2, 0xb6, 0x16, 0x2f, 0xf3, 0xfa, 0x8f, 0xdd, 0xbb, 0xe8, 0xe4, 0xe7, 0x81, 0x09, 0xbd, 0xfa,
+	0x19, 0x00, 0x00, 0xff, 0xff, 0xc9, 0x01, 0x17, 0xda, 0x9f, 0x02, 0x00, 0x00,
+}
-- 
GitLab