diff --git a/fxctx/fxctx.go b/fxctx/fxctx.go
deleted file mode 100644
index d62bf9e..0000000
--- a/fxctx/fxctx.go
+++ /dev/null
@@ -1,39 +0,0 @@
-// Copyright 2018 The Fuchsia Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-package fxctx
-
-import (
-	"context"
-	"encoding/json"
-	"fmt"
-)
-
-// ContextKey is used to store values in Context objects.
-type ContextKey string
-
-// Set associates a JSON encodable value with a key in a Context object.
-func Set(ctx context.Context, key ContextKey, value interface{}) (context.Context, error) {
-	data, err := json.Marshal(value)
-	if err != nil {
-		return nil, err
-	}
-
-	return context.WithValue(ctx, key, data), nil
-}
-
-// Get reads a value from a Context into `out`.  Returns true iff the given key is present
-// in the Context, even if the key cannot be read into `out`.
-func Get(ctx context.Context, key ContextKey, out interface{}) error {
-	value := ctx.Value(key)
-	if value == nil {
-		return fmt.Errorf("not found %v", key)
-	}
-
-	bytes, ok := value.([]byte)
-	if !ok {
-		return fmt.Errorf("expected a []byte value for %v but got %v", key, value)
-	}
-
-	return json.Unmarshal(bytes, out)
-}
diff --git a/fxctx/fxctx_test.go b/fxctx/fxctx_test.go
deleted file mode 100644
index 8c2d956..0000000
--- a/fxctx/fxctx_test.go
+++ /dev/null
@@ -1,143 +0,0 @@
-// Copyright 2018 The Fuchsia Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-package fxctx_test
-
-import (
-	"context"
-	"fmt"
-	"reflect"
-	"testing"
-
-	"fuchsia.googlesource.com/infra/infra/fxctx"
-)
-
-const TestKey = fxctx.ContextKey("test-key")
-
-// A testCase for Get().  InputValue is the value to store in the context.  The encoded
-// value is decoded from the Context into OutputValue.  ExpectOK indicates whether Get
-// should return true (the value is present in the Context). ExpectError indicates whether
-// Get should return an error.
-type getTestCase struct {
-	InputValue  interface{}
-	OutputValue interface{}
-	ExpectError bool
-}
-
-func TestGet(t *testing.T) {
-	testGet := func(t *testing.T, testCase getTestCase) {
-		ctx := context.Background()
-		if testCase.InputValue != nil {
-			var err error
-			ctx, err = fxctx.Set(ctx, TestKey, testCase.InputValue)
-			if err != nil {
-				t.Fatal(err)
-			}
-		}
-
-		err := fxctx.Get(ctx, TestKey, testCase.OutputValue)
-
-		if testCase.ExpectError != (err != nil) {
-			expectation := "did not expect error"
-			reality := fmt.Sprintf("got error: %v", err)
-			if testCase.ExpectError {
-				expectation = "expected error"
-				reality = "got nil"
-			}
-
-			t.Errorf("%s but %s", expectation, reality)
-		}
-	}
-
-	t.Run("should error if the key is not present", func(t *testing.T) {
-		// Pass nil as InputValue to simulate a missing key.
-		testGet(t, getTestCase{
-			InputValue:  nil,
-			OutputValue: new(string),
-			ExpectError: true,
-		})
-	})
-
-	t.Run("should return true and error if the value cannot be decoded", func(t *testing.T) {
-		// A map cannot be decoded into a string.
-		testGet(t, getTestCase{
-			InputValue:  map[string]string{"foo": "hi"},
-			OutputValue: new(string),
-			ExpectError: true,
-		})
-	})
-
-	t.Run("should return true and decode a value", func(t *testing.T) {
-		testGet(t, getTestCase{
-			InputValue:  "hello world!",
-			OutputValue: new(string),
-			ExpectError: false,
-		})
-	})
-}
-
-// A test case for Set().  Key and Value are the key-value pair to set in the Context.
-// ExpectedContext is the expected output Context.  ExpectError indicates whether Set
-// should return an error.
-type setTestCase struct {
-	Key             fxctx.ContextKey
-	Value           interface{}
-	ExpectedContext context.Context
-	ExpectError     bool
-}
-
-func TestSet(t *testing.T) {
-	testSet := func(t *testing.T, testCase setTestCase) {
-		ctx, err := fxctx.Set(context.Background(), testCase.Key, testCase.Value)
-
-		if testCase.ExpectError != (err != nil) {
-			expectation := "did not expect error"
-			reality := fmt.Sprintf("got error: %v", err)
-			if testCase.ExpectError {
-				expectation = "expected error"
-				reality = "got nil"
-			}
-			t.Errorf("%s but %s", expectation, reality)
-		}
-
-		if !reflect.DeepEqual(ctx, testCase.ExpectedContext) {
-			t.Errorf("Invalid context\nExpected %+v\nGot %+v",
-				testCase.ExpectedContext, ctx)
-		}
-	}
-
-	t.Run("should fail if the value cannot be encoded", func(t *testing.T) {
-		// Channels cannot be encoded as JSON.
-		channel := make(chan int)
-		defer close(channel)
-
-		testSet(t, setTestCase{
-			Value:           channel,
-			Key:             TestKey,
-			ExpectedContext: nil,
-			ExpectError:     true,
-		})
-
-		// Functions cannot be encoded as JSON.
-		aFunction := func() {}
-
-		testSet(t, setTestCase{
-			Value:           aFunction,
-			Key:             TestKey,
-			ExpectedContext: nil,
-			ExpectError:     true,
-		})
-	})
-
-	t.Run("should return a context with the value marshaled as JSON", func(t *testing.T) {
-		testSet(t, setTestCase{
-			Value: "Hello, World!",
-			Key:   TestKey,
-			ExpectedContext: context.WithValue(
-				context.Background(),
-				TestKey,
-				[]byte("\"Hello, World!\"")),
-			ExpectError: false,
-		})
-	})
-}
diff --git a/fxtesting/testing.go b/fxtesting/testing.go
deleted file mode 100644
index 0c6b067..0000000
--- a/fxtesting/testing.go
+++ /dev/null
@@ -1,38 +0,0 @@
-package fxtesting
-
-import (
-	"testing"
-)
-
-// T wraps a testing.T to add Fuchsia-specific test functionality.
-// Example Usage:
-//    t.Run("a_test", func(t *testing.T) {
-//      fxt := T{t}
-//      fxt.AssertNil(MaybeError())
-//    })
-type T struct {
-	*testing.T
-}
-
-// IsPresubmitMode returns true iff running in short mode.  To enable short mode, run
-// `go test -short`.  Long running tests and integration tests should Skip() themselves if
-// this flag is set.  See https://golang.org/pkg/testing/ for an explanation of the
-// testing package's short flag.
-func IsPresubmitMode() bool {
-	return testing.Short()
-}
-
-// AssertNil raises a fatal error if the error is not nil.
-func (t *T) AssertNil(err error) {
-	if err != nil {
-		t.Fatal(err)
-	}
-}
-
-// Assert raises a fatal error with the given message if a condition is not met. A single
-// string message is required at minimum to aid in debugging test failures.
-func (t *T) Assert(condition bool, format string, args ...interface{}) {
-	if !condition {
-		t.Fatalf(format, args...)
-	}
-}
diff --git a/fxtime/time.go b/fxtime/time.go
deleted file mode 100644
index d4c14e4..0000000
--- a/fxtime/time.go
+++ /dev/null
@@ -1,65 +0,0 @@
-// Copyright 2018 The Fuchsia Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package fxtime
-
-import (
-	"time"
-)
-
-// Clock tells the current time.  Time is always given in UTC.
-type Clock interface {
-	Now() time.Time
-}
-
-func NewClock() Clock {
-	return clock{}
-}
-
-// NewFixedClock returns a clock that always tells the same time. This is useful for
-// testing.
-func NewFixedClock(moment time.Time) Clock {
-	return fixedClock{moment: moment}
-}
-
-// Stopwatch measures time intervals.
-type Stopwatch interface {
-	Restart() time.Time
-	Elapsed() time.Duration
-}
-
-// NewStopwatch returns a new stopwatch. The watch's initial time is set to clock.Now()
-func NewStopwatch(clock Clock) Stopwatch {
-	sw := &stopwatch{clock: clock}
-	sw.Restart()
-	return sw
-}
-
-type stopwatch struct {
-	clock Clock
-	start time.Time
-}
-
-func (s *stopwatch) Restart() time.Time {
-	s.start = s.clock.Now()
-	return s.start
-}
-
-func (s stopwatch) Elapsed() time.Duration {
-	return s.clock.Now().Sub(s.start)
-}
-
-type clock struct{}
-
-func (c clock) Now() time.Time {
-	return time.Now().UTC()
-}
-
-type fixedClock struct {
-	moment time.Time
-}
-
-func (c fixedClock) Now() time.Time {
-	return c.moment.UTC()
-}
diff --git a/fxtime/time_test.go b/fxtime/time_test.go
deleted file mode 100644
index cbdbfb1..0000000
--- a/fxtime/time_test.go
+++ /dev/null
@@ -1,74 +0,0 @@
-package fxtime_test
-
-import (
-	"testing"
-	"time"
-
-	"fuchsia.googlesource.com/infra/infra/fxtime"
-)
-
-func TestFixedClock(t *testing.T) {
-	t.Run("Now should return a fixed time", func(t *testing.T) {
-		now := time.Date(1, 2, 3, 4, 5, 6, 7, time.UTC)
-		clock := fxtime.NewFixedClock(now)
-		expectTime(t, now, clock.Now())
-		expectTime(t, now, clock.Now())
-	})
-}
-
-func TestStopwatch(t *testing.T) {
-	now := time.Date(0, 0, 0, 0, 0, 0, 0, time.UTC)
-
-	t.Run("Restart should return the current time", func(t *testing.T) {
-		clock := &TestClock{
-			nowTimes: []time.Time{now, now.Add(time.Hour)},
-		}
-		stopwatch := fxtime.NewStopwatch(clock)
-		expectTime(t, clock.nowTimes[1], stopwatch.Restart())
-	})
-
-	t.Run("Elapsed should return the duration since Restart() was last called",
-		func(t *testing.T) {
-			clock := &TestClock{
-				nowTimes: []time.Time{
-					now,
-					now.Add(time.Hour),
-					now.Add(24 * time.Hour),
-					now.Add(72 * time.Hour),
-				},
-			}
-			stopwatch := fxtime.NewStopwatch(clock)
-			expectTime(t, clock.nowTimes[1], stopwatch.Restart())
-			duration := clock.nowTimes[2].Sub(clock.nowTimes[1])
-			expectDuration(t, duration, stopwatch.Elapsed())
-			duration = clock.nowTimes[3].Sub(clock.nowTimes[1])
-			expectDuration(t, duration, stopwatch.Elapsed())
-		})
-}
-
-func expectTime(t *testing.T, expected, actual time.Time) {
-	if expected != actual {
-		t.Fatalf("expected time %v but got %v", expected, actual)
-	}
-}
-
-func expectDuration(t *testing.T, expected, actual time.Duration) {
-	if expected != actual {
-		t.Fatalf("expected duration %v but got %v", expected, actual)
-	}
-}
-
-// TestClock is used to test Stopwatch.
-type TestClock struct {
-	// List of Times to return when Now is called.
-	nowTimes []time.Time
-	// Current index in nowTimes
-	i uint
-}
-
-// Returns the current time. This will panic if called more than len(nowTimes) times.
-func (c *TestClock) Now() time.Time {
-	t := c.nowTimes[c.i]
-	c.i += 1
-	return t
-}
diff --git a/resultstore/context_helpers.go b/resultstore/context_helpers.go
deleted file mode 100644
index e892e6a..0000000
--- a/resultstore/context_helpers.go
+++ /dev/null
@@ -1,44 +0,0 @@
-// Copyright 2018 The Fuchsia Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package resultstore
-
-import (
-	"context"
-
-	"fuchsia.googlesource.com/infra/infra/fxctx"
-)
-
-const (
-	// TestUUIDKey references a UUID to use for testing.
-	TestUUIDKey = fxctx.ContextKey("test-uuid")
-
-	// AuthTokenKey references the auth token to use in ResultStore requests.
-	AuthTokenKey = fxctx.ContextKey("auth-token")
-)
-
-// TestUUID gets the test UUID, if present. Errors if the value is missing or cannot be
-// read from the Context.
-func TestUUID(ctx context.Context) (string, error) {
-	var uuid string
-	err := fxctx.Get(ctx, TestUUIDKey, &uuid)
-	return uuid, err
-}
-
-// SetTestUUID sets a UUID to use for testing.
-func SetTestUUID(ctx context.Context, uuid string) (context.Context, error) {
-	return fxctx.Set(ctx, TestUUIDKey, uuid)
-}
-
-// AuthToken gets the auth token to use in ResultStore requests.
-func AuthToken(ctx context.Context) (string, error) {
-	var token string
-	err := fxctx.Get(ctx, AuthTokenKey, &token)
-	return token, err
-}
-
-// SetAuthToken sets the auth token to use in ResultStore requests.
-func SetAuthToken(ctx context.Context, value string) (context.Context, error) {
-	return fxctx.Set(ctx, AuthTokenKey, value)
-}
diff --git a/resultstore/doc.go b/resultstore/doc.go
deleted file mode 100644
index 668c91d..0000000
--- a/resultstore/doc.go
+++ /dev/null
@@ -1,20 +0,0 @@
-// Copyright 2018 The Fuchsia Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-// Package resultstore is an abstraction over the ResultStore Upload API proto definitions.
-//
-// UploadClient is a wrapper around the ResultStoreUpload client libraries.  Each of the
-// entities in this package wrap individual messages, and convert to and from their
-// counterparts. These wrappers are more easily filled from user input than raw proto messages.
-//
-// See https://github.com/googleapis/googleapis/tree/master/google/devtools/resultstore/v2
-// for more details on the proto definitions.
-//
-// Run 'go generate ./...' to regenerate mock sources in this package.
-//
-//go:generate mockgen -destination=mocks/proto_mocks.go -package=mock_resultstore google.golang.org/genproto/googleapis/devtools/resultstore/v2 ResultStoreUploadClient
-//go:generate mockgen -destination=mocks/mock_upload_client.go -package=mock_resultstore fuchsia.googlesource.com/infra/infra/resultstore UploadClient
-//
-// Do not forget to add the Fuchsia copyright header at the top of the generated file.
-package resultstore
diff --git a/resultstore/entity.go b/resultstore/entity.go
deleted file mode 100644
index 0a4176d..0000000
--- a/resultstore/entity.go
+++ /dev/null
@@ -1,346 +0,0 @@
-// Copyright 2018 The Fuchsia Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package resultstore
-
-import (
-	"log"
-	"time"
-
-	"github.com/golang/protobuf/ptypes"
-	"github.com/golang/protobuf/ptypes/duration"
-	"github.com/golang/protobuf/ptypes/timestamp"
-	api "google.golang.org/genproto/googleapis/devtools/resultstore/v2"
-)
-
-const (
-	// The filename to use for a test's log file. Result Store recognizes this file name
-	// and displays it by default when a target is opened in the UI.
-	testLogName = "test.log"
-)
-
-// Invocation maps to a ResultStore Invocation.
-//
-// See https://github.com/googleapis/googleapis/blob/master/google/devtools/resultstore/v2/invocation.proto
-// for more documentation.
-type Invocation struct {
-	Name       string
-	ID         string
-	ProjectID  string
-	Users      []string
-	Labels     []string
-	Properties map[string]string
-	LogURL     string
-	Status     Status
-	StartTime  time.Time
-	Duration   time.Duration
-}
-
-func (i Invocation) ToResultStoreInvocation() *api.Invocation {
-	output := &api.Invocation{
-		Name: i.Name,
-		StatusAttributes: &api.StatusAttributes{
-			Status: i.Status.ToResultStoreStatus(),
-		},
-		InvocationAttributes: &api.InvocationAttributes{
-			ProjectId: i.ProjectID,
-			Users:     i.Users,
-			Labels:    i.Labels,
-		},
-		Files: []*api.File{
-			&api.File{Uid: "invocation.log", Uri: i.LogURL},
-		},
-		Properties: mapToProperties(i.Properties),
-	}
-
-	// Leave ID nil if unspecified since resultstore throws an error when this field is
-	// set and does not match the original ID supplied when creating the Invocation.
-	if i.ID != "" {
-		output.Id = &api.Invocation_Id{
-			InvocationId: i.ID,
-		}
-	}
-
-	// Leave timing attributes nil if unspecified since resultstore throws an error when
-	// timing data contains invalid values such as Go's zero-value for time.Time.
-	if (i.StartTime != time.Time{}) || i.Duration != 0 {
-		output.Timing = &api.Timing{
-			StartTime: timeToProtoTimestamp(i.StartTime),
-			Duration:  durationToProtoDuration(i.Duration),
-		}
-	}
-
-	return output
-}
-
-func (i *Invocation) FromResultStoreInvocation(input *api.Invocation) {
-	*i = Invocation{
-		Name: input.GetName(),
-		ID:   input.GetId().InvocationId,
-	}
-}
-
-// Configuration maps to a ResultStore Configuration.
-//
-// See https://github.com/googleapis/googleapis/blob/master/google/devtools/resultstore/v2/configuration.proto
-// for more documentation.
-type Configuration struct {
-	Name         string
-	ID           string
-	InvocationID string
-	Properties   map[string]string
-}
-
-func (c Configuration) ToResultStoreConfiguration() *api.Configuration {
-	return &api.Configuration{
-		Name: c.Name,
-		Id: &api.Configuration_Id{
-			InvocationId:    c.InvocationID,
-			ConfigurationId: c.ID,
-		},
-		Properties: mapToProperties(c.Properties),
-	}
-}
-
-func (c *Configuration) FromResultStoreConfiguration(input *api.Configuration) {
-	*c = Configuration{
-		Name:         input.GetName(),
-		ID:           input.GetId().ConfigurationId,
-		InvocationID: input.GetId().InvocationId,
-	}
-}
-
-// Target maps to a ResultStore Target.
-//
-// See https://github.com/googleapis/googleapis/blob/master/google/devtools/resultstore/v2/target.proto
-// for more documentation.
-type Target struct {
-	Name       string
-	ID         *TargetID
-	Properties map[string]string
-	Status     Status
-	StartTime  time.Time
-	Duration   time.Duration
-	TestLogURI string
-}
-type TargetID struct {
-	ID           string
-	InvocationID string
-}
-
-func (t Target) ToResultStoreTarget() *api.Target {
-	var id *api.Target_Id
-	if t.ID != nil {
-		id = &api.Target_Id{
-			InvocationId: t.ID.InvocationID,
-			TargetId:     t.ID.ID,
-		}
-	}
-
-	return &api.Target{
-		Name: t.Name,
-		Id:   id,
-		Timing: &api.Timing{
-			StartTime: timeToProtoTimestamp(t.StartTime),
-			Duration:  durationToProtoDuration(t.Duration),
-		},
-		StatusAttributes: &api.StatusAttributes{
-			Status: t.Status.ToResultStoreStatus(),
-		},
-		Properties: mapToProperties(t.Properties),
-		Visible:    true,
-		Files: []*api.File{
-			&api.File{
-				Uid: testLogName,
-				Uri: t.TestLogURI,
-			},
-		},
-	}
-}
-
-func (t *Target) FromResultStoreTarget(input *api.Target) {
-	*t = Target{
-		Name: input.GetName(),
-		ID: &TargetID{
-			ID:           input.GetId().TargetId,
-			InvocationID: input.GetId().InvocationId,
-		},
-	}
-}
-
-// ConfiguredTarget maps to a ResultStore ConfiguredTarget.
-//
-// See https://github.com/googleapis/googleapis/blob/master/google/devtools/resultstore/v2/configured_target.proto
-// for more documentation.
-type ConfiguredTarget struct {
-	Name       string
-	ID         *ConfiguredTargetID
-	Properties map[string]string
-	Status     Status
-	StartTime  time.Time
-	Duration   time.Duration
-}
-type ConfiguredTargetID struct {
-	InvocationID string
-	TargetID     string
-	ConfigID     string
-}
-
-func (t ConfiguredTarget) ToResultStoreConfiguredTarget() *api.ConfiguredTarget {
-	var id *api.ConfiguredTarget_Id
-	if t.ID != nil {
-		id = &api.ConfiguredTarget_Id{
-			InvocationId:    t.ID.InvocationID,
-			TargetId:        t.ID.TargetID,
-			ConfigurationId: t.ID.ConfigID,
-		}
-	}
-
-	return &api.ConfiguredTarget{
-		Name: t.Name,
-		Id:   id,
-		StatusAttributes: &api.StatusAttributes{
-			Status: t.Status.ToResultStoreStatus(),
-		},
-		Timing: &api.Timing{
-			StartTime: timeToProtoTimestamp(t.StartTime),
-			Duration:  durationToProtoDuration(t.Duration),
-		},
-		Properties: mapToProperties(t.Properties),
-	}
-}
-
-func (t *ConfiguredTarget) FromResultStoreConfiguredTarget(input *api.ConfiguredTarget) {
-	*t = ConfiguredTarget{
-		Name: input.GetName(),
-		ID: &ConfiguredTargetID{
-			InvocationID: input.GetId().InvocationId,
-			TargetID:     input.GetId().TargetId,
-			ConfigID:     input.GetId().ConfigurationId,
-		},
-	}
-}
-
-// TestAction maps to a ResultStore Action with a child TestAction.
-//
-// See https://github.com/googleapis/googleapis/blob/master/google/devtools/resultstore/v2/action.proto
-// for more documentation.
-type TestAction struct {
-	Name       string
-	ID         *TestActionID
-	TestSuite  string
-	TestLogURI string
-	StartTime  time.Time
-	Duration   time.Duration
-	Status     Status
-}
-type TestActionID struct {
-	ID           string
-	InvocationID string
-	TargetID     string
-	ConfigID     string
-}
-
-func (a TestAction) ToResultStoreAction() *api.Action {
-	var id *api.Action_Id
-	if a.ID != nil {
-		id = &api.Action_Id{
-			InvocationId:    a.ID.InvocationID,
-			TargetId:        a.ID.TargetID,
-			ConfigurationId: a.ID.ConfigID,
-			ActionId:        a.ID.ID,
-		}
-	}
-	return &api.Action{
-		Name: a.Name,
-		Id:   id,
-		StatusAttributes: &api.StatusAttributes{
-			Status: a.Status.ToResultStoreStatus(),
-		},
-		ActionType: &api.Action_TestAction{
-			TestAction: &api.TestAction{
-				TestSuite: &api.TestSuite{
-					SuiteName: a.TestSuite,
-				},
-			},
-		},
-		Files: []*api.File{
-			&api.File{
-				Uid: testLogName,
-				Uri: a.TestLogURI,
-			},
-		},
-		Timing: &api.Timing{
-			StartTime: timeToProtoTimestamp(a.StartTime),
-			Duration:  durationToProtoDuration(a.Duration),
-		},
-	}
-}
-
-func (a *TestAction) FromResultStoreAction(input *api.Action) {
-	*a = TestAction{
-		Name: input.GetName(),
-		ID: &TestActionID{
-			InvocationID: input.GetId().InvocationId,
-			TargetID:     input.GetId().TargetId,
-			ConfigID:     input.GetId().ConfigurationId,
-			ID:           input.GetId().ActionId,
-		},
-	}
-}
-
-// Status describes the status of a ResultStore entity.
-//
-// See https://github.com/googleapis/googleapis/blob/master/google/devtools/resultstore/v2/common.proto
-// for more documentation.
-type Status string
-
-const (
-	Building = Status("BUILDING")
-	Passed   = Status("PASSED")
-	Failed   = Status("FAILED")
-	TimedOut = Status("TIMED_OUT")
-	Testing  = Status("TESTING")
-	Unknown  = Status("Unknown")
-)
-
-func (r Status) ToResultStoreStatus() api.Status {
-	switch r {
-	case Building:
-		return api.Status_BUILDING
-	case Failed:
-		return api.Status_FAILED
-	case Passed:
-		return api.Status_PASSED
-	case Testing:
-		return api.Status_TESTING
-	case TimedOut:
-		return api.Status_TIMED_OUT
-	default:
-		log.Printf("unknown test status: %v", r)
-		return api.Status_UNKNOWN
-	}
-}
-
-func timeToProtoTimestamp(input time.Time) *timestamp.Timestamp {
-	output, err := ptypes.TimestampProto(input)
-	if err != nil {
-		// We should never get here unless the caller manually created some strange,
-		// invalid time.Time value or the ResultStore API returned a nil value.
-		panic(err.Error())
-	}
-	return output
-}
-
-func durationToProtoDuration(input time.Duration) *duration.Duration {
-	return ptypes.DurationProto(input)
-}
-
-func mapToProperties(input map[string]string) []*api.Property {
-	var props []*api.Property
-	for k, v := range input {
-		props = append(props, &api.Property{Key: k, Value: v})
-	}
-	return props
-}
diff --git a/resultstore/fields/fields.go b/resultstore/fields/fields.go
deleted file mode 100644
index 3b979bf..0000000
--- a/resultstore/fields/fields.go
+++ /dev/null
@@ -1,15 +0,0 @@
-// Copyright 2019 The Fuchsia Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-// Package fields defines constants for Result Store Upload API proto message fields that
-// are referenced when calling UpdateXXXX methods on UploadClient.  Add constants to this
-/// package as needed.
-package fields
-
-const (
-	StartTime        = "timing.start_time"
-	Duration         = "timing.duration"
-	StatusAttributes = "status_attributes"
-	Files            = "files"
-)
diff --git a/resultstore/mocks/mock_upload_client.go b/resultstore/mocks/mock_upload_client.go
deleted file mode 100644
index 7bd7782..0000000
--- a/resultstore/mocks/mock_upload_client.go
+++ /dev/null
@@ -1,212 +0,0 @@
-// Code generated by MockGen. DO NOT EDIT.
-// Source: fuchsia.googlesource.com/infra/infra/resultstore (interfaces: UploadClient)
-
-// Package mock_resultstore is a generated GoMock package.
-package mock_resultstore
-
-import (
-	context "context"
-	resultstore "fuchsia.googlesource.com/infra/infra/resultstore"
-	gomock "github.com/golang/mock/gomock"
-	reflect "reflect"
-)
-
-// MockUploadClient is a mock of UploadClient interface
-type MockUploadClient struct {
-	ctrl     *gomock.Controller
-	recorder *MockUploadClientMockRecorder
-}
-
-// MockUploadClientMockRecorder is the mock recorder for MockUploadClient
-type MockUploadClientMockRecorder struct {
-	mock *MockUploadClient
-}
-
-// NewMockUploadClient creates a new mock instance
-func NewMockUploadClient(ctrl *gomock.Controller) *MockUploadClient {
-	mock := &MockUploadClient{ctrl: ctrl}
-	mock.recorder = &MockUploadClientMockRecorder{mock}
-	return mock
-}
-
-// EXPECT returns an object that allows the caller to indicate expected use
-func (m *MockUploadClient) EXPECT() *MockUploadClientMockRecorder {
-	return m.recorder
-}
-
-// CreateConfiguration mocks base method
-func (m *MockUploadClient) CreateConfiguration(arg0 context.Context, arg1 *resultstore.Configuration, arg2 string) (*resultstore.Configuration, error) {
-	m.ctrl.T.Helper()
-	ret := m.ctrl.Call(m, "CreateConfiguration", arg0, arg1, arg2)
-	ret0, _ := ret[0].(*resultstore.Configuration)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// CreateConfiguration indicates an expected call of CreateConfiguration
-func (mr *MockUploadClientMockRecorder) CreateConfiguration(arg0, arg1, arg2 interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateConfiguration", reflect.TypeOf((*MockUploadClient)(nil).CreateConfiguration), arg0, arg1, arg2)
-}
-
-// CreateConfiguredTarget mocks base method
-func (m *MockUploadClient) CreateConfiguredTarget(arg0 context.Context, arg1 *resultstore.ConfiguredTarget, arg2 string) (*resultstore.ConfiguredTarget, error) {
-	m.ctrl.T.Helper()
-	ret := m.ctrl.Call(m, "CreateConfiguredTarget", arg0, arg1, arg2)
-	ret0, _ := ret[0].(*resultstore.ConfiguredTarget)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// CreateConfiguredTarget indicates an expected call of CreateConfiguredTarget
-func (mr *MockUploadClientMockRecorder) CreateConfiguredTarget(arg0, arg1, arg2 interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateConfiguredTarget", reflect.TypeOf((*MockUploadClient)(nil).CreateConfiguredTarget), arg0, arg1, arg2)
-}
-
-// CreateInvocation mocks base method
-func (m *MockUploadClient) CreateInvocation(arg0 context.Context, arg1 *resultstore.Invocation) (*resultstore.Invocation, error) {
-	m.ctrl.T.Helper()
-	ret := m.ctrl.Call(m, "CreateInvocation", arg0, arg1)
-	ret0, _ := ret[0].(*resultstore.Invocation)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// CreateInvocation indicates an expected call of CreateInvocation
-func (mr *MockUploadClientMockRecorder) CreateInvocation(arg0, arg1 interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateInvocation", reflect.TypeOf((*MockUploadClient)(nil).CreateInvocation), arg0, arg1)
-}
-
-// CreateTarget mocks base method
-func (m *MockUploadClient) CreateTarget(arg0 context.Context, arg1 *resultstore.Target, arg2 string) (*resultstore.Target, error) {
-	m.ctrl.T.Helper()
-	ret := m.ctrl.Call(m, "CreateTarget", arg0, arg1, arg2)
-	ret0, _ := ret[0].(*resultstore.Target)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// CreateTarget indicates an expected call of CreateTarget
-func (mr *MockUploadClientMockRecorder) CreateTarget(arg0, arg1, arg2 interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateTarget", reflect.TypeOf((*MockUploadClient)(nil).CreateTarget), arg0, arg1, arg2)
-}
-
-// CreateTestAction mocks base method
-func (m *MockUploadClient) CreateTestAction(arg0 context.Context, arg1 *resultstore.TestAction, arg2 string) (*resultstore.TestAction, error) {
-	m.ctrl.T.Helper()
-	ret := m.ctrl.Call(m, "CreateTestAction", arg0, arg1, arg2)
-	ret0, _ := ret[0].(*resultstore.TestAction)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// CreateTestAction indicates an expected call of CreateTestAction
-func (mr *MockUploadClientMockRecorder) CreateTestAction(arg0, arg1, arg2 interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateTestAction", reflect.TypeOf((*MockUploadClient)(nil).CreateTestAction), arg0, arg1, arg2)
-}
-
-// FinishConfiguredTarget mocks base method
-func (m *MockUploadClient) FinishConfiguredTarget(arg0 context.Context, arg1 string) error {
-	m.ctrl.T.Helper()
-	ret := m.ctrl.Call(m, "FinishConfiguredTarget", arg0, arg1)
-	ret0, _ := ret[0].(error)
-	return ret0
-}
-
-// FinishConfiguredTarget indicates an expected call of FinishConfiguredTarget
-func (mr *MockUploadClientMockRecorder) FinishConfiguredTarget(arg0, arg1 interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "FinishConfiguredTarget", reflect.TypeOf((*MockUploadClient)(nil).FinishConfiguredTarget), arg0, arg1)
-}
-
-// FinishInvocation mocks base method
-func (m *MockUploadClient) FinishInvocation(arg0 context.Context, arg1 string) error {
-	m.ctrl.T.Helper()
-	ret := m.ctrl.Call(m, "FinishInvocation", arg0, arg1)
-	ret0, _ := ret[0].(error)
-	return ret0
-}
-
-// FinishInvocation indicates an expected call of FinishInvocation
-func (mr *MockUploadClientMockRecorder) FinishInvocation(arg0, arg1 interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "FinishInvocation", reflect.TypeOf((*MockUploadClient)(nil).FinishInvocation), arg0, arg1)
-}
-
-// FinishTarget mocks base method
-func (m *MockUploadClient) FinishTarget(arg0 context.Context, arg1 string) error {
-	m.ctrl.T.Helper()
-	ret := m.ctrl.Call(m, "FinishTarget", arg0, arg1)
-	ret0, _ := ret[0].(error)
-	return ret0
-}
-
-// FinishTarget indicates an expected call of FinishTarget
-func (mr *MockUploadClientMockRecorder) FinishTarget(arg0, arg1 interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "FinishTarget", reflect.TypeOf((*MockUploadClient)(nil).FinishTarget), arg0, arg1)
-}
-
-// UpdateConfiguredTarget mocks base method
-func (m *MockUploadClient) UpdateConfiguredTarget(arg0 context.Context, arg1 *resultstore.ConfiguredTarget, arg2 []string) (*resultstore.ConfiguredTarget, error) {
-	m.ctrl.T.Helper()
-	ret := m.ctrl.Call(m, "UpdateConfiguredTarget", arg0, arg1, arg2)
-	ret0, _ := ret[0].(*resultstore.ConfiguredTarget)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// UpdateConfiguredTarget indicates an expected call of UpdateConfiguredTarget
-func (mr *MockUploadClientMockRecorder) UpdateConfiguredTarget(arg0, arg1, arg2 interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateConfiguredTarget", reflect.TypeOf((*MockUploadClient)(nil).UpdateConfiguredTarget), arg0, arg1, arg2)
-}
-
-// UpdateInvocation mocks base method
-func (m *MockUploadClient) UpdateInvocation(arg0 context.Context, arg1 *resultstore.Invocation, arg2 []string) (*resultstore.Invocation, error) {
-	m.ctrl.T.Helper()
-	ret := m.ctrl.Call(m, "UpdateInvocation", arg0, arg1, arg2)
-	ret0, _ := ret[0].(*resultstore.Invocation)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// UpdateInvocation indicates an expected call of UpdateInvocation
-func (mr *MockUploadClientMockRecorder) UpdateInvocation(arg0, arg1, arg2 interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateInvocation", reflect.TypeOf((*MockUploadClient)(nil).UpdateInvocation), arg0, arg1, arg2)
-}
-
-// UpdateTarget mocks base method
-func (m *MockUploadClient) UpdateTarget(arg0 context.Context, arg1 *resultstore.Target, arg2 []string) (*resultstore.Target, error) {
-	m.ctrl.T.Helper()
-	ret := m.ctrl.Call(m, "UpdateTarget", arg0, arg1, arg2)
-	ret0, _ := ret[0].(*resultstore.Target)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// UpdateTarget indicates an expected call of UpdateTarget
-func (mr *MockUploadClientMockRecorder) UpdateTarget(arg0, arg1, arg2 interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateTarget", reflect.TypeOf((*MockUploadClient)(nil).UpdateTarget), arg0, arg1, arg2)
-}
-
-// UpdateTestAction mocks base method
-func (m *MockUploadClient) UpdateTestAction(arg0 context.Context, arg1 *resultstore.TestAction, arg2 []string) (*resultstore.TestAction, error) {
-	m.ctrl.T.Helper()
-	ret := m.ctrl.Call(m, "UpdateTestAction", arg0, arg1, arg2)
-	ret0, _ := ret[0].(*resultstore.TestAction)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// UpdateTestAction indicates an expected call of UpdateTestAction
-func (mr *MockUploadClientMockRecorder) UpdateTestAction(arg0, arg1, arg2 interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateTestAction", reflect.TypeOf((*MockUploadClient)(nil).UpdateTestAction), arg0, arg1, arg2)
-}
diff --git a/resultstore/mocks/proto_mocks.go b/resultstore/mocks/proto_mocks.go
deleted file mode 100644
index 1d97322..0000000
--- a/resultstore/mocks/proto_mocks.go
+++ /dev/null
@@ -1,336 +0,0 @@
-// Code generated by MockGen. DO NOT EDIT.
-// Source: google.golang.org/genproto/googleapis/devtools/resultstore/v2 (interfaces: ResultStoreUploadClient)
-
-// Package mock_resultstore is a generated GoMock package.
-package mock_resultstore
-
-import (
-	context "context"
-	gomock "github.com/golang/mock/gomock"
-	v2 "google.golang.org/genproto/googleapis/devtools/resultstore/v2"
-	grpc "google.golang.org/grpc"
-	reflect "reflect"
-)
-
-// MockResultStoreUploadClient is a mock of ResultStoreUploadClient interface
-type MockResultStoreUploadClient struct {
-	ctrl     *gomock.Controller
-	recorder *MockResultStoreUploadClientMockRecorder
-}
-
-// MockResultStoreUploadClientMockRecorder is the mock recorder for MockResultStoreUploadClient
-type MockResultStoreUploadClientMockRecorder struct {
-	mock *MockResultStoreUploadClient
-}
-
-// NewMockResultStoreUploadClient creates a new mock instance
-func NewMockResultStoreUploadClient(ctrl *gomock.Controller) *MockResultStoreUploadClient {
-	mock := &MockResultStoreUploadClient{ctrl: ctrl}
-	mock.recorder = &MockResultStoreUploadClientMockRecorder{mock}
-	return mock
-}
-
-// EXPECT returns an object that allows the caller to indicate expected use
-func (m *MockResultStoreUploadClient) EXPECT() *MockResultStoreUploadClientMockRecorder {
-	return m.recorder
-}
-
-// CreateAction mocks base method
-func (m *MockResultStoreUploadClient) CreateAction(arg0 context.Context, arg1 *v2.CreateActionRequest, arg2 ...grpc.CallOption) (*v2.Action, error) {
-	m.ctrl.T.Helper()
-	varargs := []interface{}{arg0, arg1}
-	for _, a := range arg2 {
-		varargs = append(varargs, a)
-	}
-	ret := m.ctrl.Call(m, "CreateAction", varargs...)
-	ret0, _ := ret[0].(*v2.Action)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// CreateAction indicates an expected call of CreateAction
-func (mr *MockResultStoreUploadClientMockRecorder) CreateAction(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	varargs := append([]interface{}{arg0, arg1}, arg2...)
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateAction", reflect.TypeOf((*MockResultStoreUploadClient)(nil).CreateAction), varargs...)
-}
-
-// CreateConfiguration mocks base method
-func (m *MockResultStoreUploadClient) CreateConfiguration(arg0 context.Context, arg1 *v2.CreateConfigurationRequest, arg2 ...grpc.CallOption) (*v2.Configuration, error) {
-	m.ctrl.T.Helper()
-	varargs := []interface{}{arg0, arg1}
-	for _, a := range arg2 {
-		varargs = append(varargs, a)
-	}
-	ret := m.ctrl.Call(m, "CreateConfiguration", varargs...)
-	ret0, _ := ret[0].(*v2.Configuration)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// CreateConfiguration indicates an expected call of CreateConfiguration
-func (mr *MockResultStoreUploadClientMockRecorder) CreateConfiguration(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	varargs := append([]interface{}{arg0, arg1}, arg2...)
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateConfiguration", reflect.TypeOf((*MockResultStoreUploadClient)(nil).CreateConfiguration), varargs...)
-}
-
-// CreateConfiguredTarget mocks base method
-func (m *MockResultStoreUploadClient) CreateConfiguredTarget(arg0 context.Context, arg1 *v2.CreateConfiguredTargetRequest, arg2 ...grpc.CallOption) (*v2.ConfiguredTarget, error) {
-	m.ctrl.T.Helper()
-	varargs := []interface{}{arg0, arg1}
-	for _, a := range arg2 {
-		varargs = append(varargs, a)
-	}
-	ret := m.ctrl.Call(m, "CreateConfiguredTarget", varargs...)
-	ret0, _ := ret[0].(*v2.ConfiguredTarget)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// CreateConfiguredTarget indicates an expected call of CreateConfiguredTarget
-func (mr *MockResultStoreUploadClientMockRecorder) CreateConfiguredTarget(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	varargs := append([]interface{}{arg0, arg1}, arg2...)
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateConfiguredTarget", reflect.TypeOf((*MockResultStoreUploadClient)(nil).CreateConfiguredTarget), varargs...)
-}
-
-// CreateFileSet mocks base method
-func (m *MockResultStoreUploadClient) CreateFileSet(arg0 context.Context, arg1 *v2.CreateFileSetRequest, arg2 ...grpc.CallOption) (*v2.FileSet, error) {
-	m.ctrl.T.Helper()
-	varargs := []interface{}{arg0, arg1}
-	for _, a := range arg2 {
-		varargs = append(varargs, a)
-	}
-	ret := m.ctrl.Call(m, "CreateFileSet", varargs...)
-	ret0, _ := ret[0].(*v2.FileSet)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// CreateFileSet indicates an expected call of CreateFileSet
-func (mr *MockResultStoreUploadClientMockRecorder) CreateFileSet(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	varargs := append([]interface{}{arg0, arg1}, arg2...)
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateFileSet", reflect.TypeOf((*MockResultStoreUploadClient)(nil).CreateFileSet), varargs...)
-}
-
-// CreateInvocation mocks base method
-func (m *MockResultStoreUploadClient) CreateInvocation(arg0 context.Context, arg1 *v2.CreateInvocationRequest, arg2 ...grpc.CallOption) (*v2.Invocation, error) {
-	m.ctrl.T.Helper()
-	varargs := []interface{}{arg0, arg1}
-	for _, a := range arg2 {
-		varargs = append(varargs, a)
-	}
-	ret := m.ctrl.Call(m, "CreateInvocation", varargs...)
-	ret0, _ := ret[0].(*v2.Invocation)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// CreateInvocation indicates an expected call of CreateInvocation
-func (mr *MockResultStoreUploadClientMockRecorder) CreateInvocation(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	varargs := append([]interface{}{arg0, arg1}, arg2...)
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateInvocation", reflect.TypeOf((*MockResultStoreUploadClient)(nil).CreateInvocation), varargs...)
-}
-
-// CreateTarget mocks base method
-func (m *MockResultStoreUploadClient) CreateTarget(arg0 context.Context, arg1 *v2.CreateTargetRequest, arg2 ...grpc.CallOption) (*v2.Target, error) {
-	m.ctrl.T.Helper()
-	varargs := []interface{}{arg0, arg1}
-	for _, a := range arg2 {
-		varargs = append(varargs, a)
-	}
-	ret := m.ctrl.Call(m, "CreateTarget", varargs...)
-	ret0, _ := ret[0].(*v2.Target)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// CreateTarget indicates an expected call of CreateTarget
-func (mr *MockResultStoreUploadClientMockRecorder) CreateTarget(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	varargs := append([]interface{}{arg0, arg1}, arg2...)
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateTarget", reflect.TypeOf((*MockResultStoreUploadClient)(nil).CreateTarget), varargs...)
-}
-
-// FinishConfiguredTarget mocks base method
-func (m *MockResultStoreUploadClient) FinishConfiguredTarget(arg0 context.Context, arg1 *v2.FinishConfiguredTargetRequest, arg2 ...grpc.CallOption) (*v2.FinishConfiguredTargetResponse, error) {
-	m.ctrl.T.Helper()
-	varargs := []interface{}{arg0, arg1}
-	for _, a := range arg2 {
-		varargs = append(varargs, a)
-	}
-	ret := m.ctrl.Call(m, "FinishConfiguredTarget", varargs...)
-	ret0, _ := ret[0].(*v2.FinishConfiguredTargetResponse)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// FinishConfiguredTarget indicates an expected call of FinishConfiguredTarget
-func (mr *MockResultStoreUploadClientMockRecorder) FinishConfiguredTarget(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	varargs := append([]interface{}{arg0, arg1}, arg2...)
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "FinishConfiguredTarget", reflect.TypeOf((*MockResultStoreUploadClient)(nil).FinishConfiguredTarget), varargs...)
-}
-
-// FinishInvocation mocks base method
-func (m *MockResultStoreUploadClient) FinishInvocation(arg0 context.Context, arg1 *v2.FinishInvocationRequest, arg2 ...grpc.CallOption) (*v2.FinishInvocationResponse, error) {
-	m.ctrl.T.Helper()
-	varargs := []interface{}{arg0, arg1}
-	for _, a := range arg2 {
-		varargs = append(varargs, a)
-	}
-	ret := m.ctrl.Call(m, "FinishInvocation", varargs...)
-	ret0, _ := ret[0].(*v2.FinishInvocationResponse)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// FinishInvocation indicates an expected call of FinishInvocation
-func (mr *MockResultStoreUploadClientMockRecorder) FinishInvocation(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	varargs := append([]interface{}{arg0, arg1}, arg2...)
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "FinishInvocation", reflect.TypeOf((*MockResultStoreUploadClient)(nil).FinishInvocation), varargs...)
-}
-
-// FinishTarget mocks base method
-func (m *MockResultStoreUploadClient) FinishTarget(arg0 context.Context, arg1 *v2.FinishTargetRequest, arg2 ...grpc.CallOption) (*v2.FinishTargetResponse, error) {
-	m.ctrl.T.Helper()
-	varargs := []interface{}{arg0, arg1}
-	for _, a := range arg2 {
-		varargs = append(varargs, a)
-	}
-	ret := m.ctrl.Call(m, "FinishTarget", varargs...)
-	ret0, _ := ret[0].(*v2.FinishTargetResponse)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// FinishTarget indicates an expected call of FinishTarget
-func (mr *MockResultStoreUploadClientMockRecorder) FinishTarget(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	varargs := append([]interface{}{arg0, arg1}, arg2...)
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "FinishTarget", reflect.TypeOf((*MockResultStoreUploadClient)(nil).FinishTarget), varargs...)
-}
-
-// UpdateAction mocks base method
-func (m *MockResultStoreUploadClient) UpdateAction(arg0 context.Context, arg1 *v2.UpdateActionRequest, arg2 ...grpc.CallOption) (*v2.Action, error) {
-	m.ctrl.T.Helper()
-	varargs := []interface{}{arg0, arg1}
-	for _, a := range arg2 {
-		varargs = append(varargs, a)
-	}
-	ret := m.ctrl.Call(m, "UpdateAction", varargs...)
-	ret0, _ := ret[0].(*v2.Action)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// UpdateAction indicates an expected call of UpdateAction
-func (mr *MockResultStoreUploadClientMockRecorder) UpdateAction(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	varargs := append([]interface{}{arg0, arg1}, arg2...)
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateAction", reflect.TypeOf((*MockResultStoreUploadClient)(nil).UpdateAction), varargs...)
-}
-
-// UpdateConfiguration mocks base method
-func (m *MockResultStoreUploadClient) UpdateConfiguration(arg0 context.Context, arg1 *v2.UpdateConfigurationRequest, arg2 ...grpc.CallOption) (*v2.Configuration, error) {
-	m.ctrl.T.Helper()
-	varargs := []interface{}{arg0, arg1}
-	for _, a := range arg2 {
-		varargs = append(varargs, a)
-	}
-	ret := m.ctrl.Call(m, "UpdateConfiguration", varargs...)
-	ret0, _ := ret[0].(*v2.Configuration)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// UpdateConfiguration indicates an expected call of UpdateConfiguration
-func (mr *MockResultStoreUploadClientMockRecorder) UpdateConfiguration(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	varargs := append([]interface{}{arg0, arg1}, arg2...)
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateConfiguration", reflect.TypeOf((*MockResultStoreUploadClient)(nil).UpdateConfiguration), varargs...)
-}
-
-// UpdateConfiguredTarget mocks base method
-func (m *MockResultStoreUploadClient) UpdateConfiguredTarget(arg0 context.Context, arg1 *v2.UpdateConfiguredTargetRequest, arg2 ...grpc.CallOption) (*v2.ConfiguredTarget, error) {
-	m.ctrl.T.Helper()
-	varargs := []interface{}{arg0, arg1}
-	for _, a := range arg2 {
-		varargs = append(varargs, a)
-	}
-	ret := m.ctrl.Call(m, "UpdateConfiguredTarget", varargs...)
-	ret0, _ := ret[0].(*v2.ConfiguredTarget)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// UpdateConfiguredTarget indicates an expected call of UpdateConfiguredTarget
-func (mr *MockResultStoreUploadClientMockRecorder) UpdateConfiguredTarget(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	varargs := append([]interface{}{arg0, arg1}, arg2...)
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateConfiguredTarget", reflect.TypeOf((*MockResultStoreUploadClient)(nil).UpdateConfiguredTarget), varargs...)
-}
-
-// UpdateFileSet mocks base method
-func (m *MockResultStoreUploadClient) UpdateFileSet(arg0 context.Context, arg1 *v2.UpdateFileSetRequest, arg2 ...grpc.CallOption) (*v2.FileSet, error) {
-	m.ctrl.T.Helper()
-	varargs := []interface{}{arg0, arg1}
-	for _, a := range arg2 {
-		varargs = append(varargs, a)
-	}
-	ret := m.ctrl.Call(m, "UpdateFileSet", varargs...)
-	ret0, _ := ret[0].(*v2.FileSet)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// UpdateFileSet indicates an expected call of UpdateFileSet
-func (mr *MockResultStoreUploadClientMockRecorder) UpdateFileSet(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	varargs := append([]interface{}{arg0, arg1}, arg2...)
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateFileSet", reflect.TypeOf((*MockResultStoreUploadClient)(nil).UpdateFileSet), varargs...)
-}
-
-// UpdateInvocation mocks base method
-func (m *MockResultStoreUploadClient) UpdateInvocation(arg0 context.Context, arg1 *v2.UpdateInvocationRequest, arg2 ...grpc.CallOption) (*v2.Invocation, error) {
-	m.ctrl.T.Helper()
-	varargs := []interface{}{arg0, arg1}
-	for _, a := range arg2 {
-		varargs = append(varargs, a)
-	}
-	ret := m.ctrl.Call(m, "UpdateInvocation", varargs...)
-	ret0, _ := ret[0].(*v2.Invocation)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// UpdateInvocation indicates an expected call of UpdateInvocation
-func (mr *MockResultStoreUploadClientMockRecorder) UpdateInvocation(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	varargs := append([]interface{}{arg0, arg1}, arg2...)
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateInvocation", reflect.TypeOf((*MockResultStoreUploadClient)(nil).UpdateInvocation), varargs...)
-}
-
-// UpdateTarget mocks base method
-func (m *MockResultStoreUploadClient) UpdateTarget(arg0 context.Context, arg1 *v2.UpdateTargetRequest, arg2 ...grpc.CallOption) (*v2.Target, error) {
-	m.ctrl.T.Helper()
-	varargs := []interface{}{arg0, arg1}
-	for _, a := range arg2 {
-		varargs = append(varargs, a)
-	}
-	ret := m.ctrl.Call(m, "UpdateTarget", varargs...)
-	ret0, _ := ret[0].(*v2.Target)
-	ret1, _ := ret[1].(error)
-	return ret0, ret1
-}
-
-// UpdateTarget indicates an expected call of UpdateTarget
-func (mr *MockResultStoreUploadClientMockRecorder) UpdateTarget(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call {
-	mr.mock.ctrl.T.Helper()
-	varargs := append([]interface{}{arg0, arg1}, arg2...)
-	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateTarget", reflect.TypeOf((*MockResultStoreUploadClient)(nil).UpdateTarget), varargs...)
-}
diff --git a/resultstore/resultstore.go b/resultstore/resultstore.go
deleted file mode 100644
index 8fa4fe2..0000000
--- a/resultstore/resultstore.go
+++ /dev/null
@@ -1,80 +0,0 @@
-// Copyright 2018 The Fuchsia Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package resultstore
-
-import (
-	"context"
-	"crypto/x509"
-	"fmt"
-
-	api "google.golang.org/genproto/googleapis/devtools/resultstore/v2"
-	"google.golang.org/grpc"
-	"google.golang.org/grpc/credentials"
-)
-
-const (
-	// Google Cloud API scope required to use ResultStore Upload API.
-	scope = "https://www.googleapis.com/auth/cloud-platform"
-)
-
-// Connect returns a new UploadClient connected to the ResultStore backend at the given host.
-func Connect(ctx context.Context, environment Environment, creds credentials.PerRPCCredentials) (UploadClient, error) {
-	pool, err := x509.SystemCertPool()
-	if err != nil {
-		return nil, fmt.Errorf("failed to create cert pool: %v", err)
-	}
-
-	transportCreds := credentials.NewClientTLSFromCert(pool, "")
-
-	conn, err := grpc.Dial(
-		environment.GRPCServiceAddress(),
-		grpc.WithTransportCredentials(transportCreds),
-		grpc.WithPerRPCCredentials(creds),
-	)
-	if err != nil {
-		return nil, err
-	}
-	return NewUploadClient(api.NewResultStoreUploadClient(conn)), nil
-}
-
-// Environment describes which ResultStore environment to use.
-type Environment string
-
-// Environment constants.
-const (
-	Production Environment = "production"
-	Staging    Environment = "staging"
-)
-
-// Returns the URL of the Invocation with the given ID in this Environment.
-func (e Environment) InvocationURL(invocationID string) string {
-	return fmt.Sprintf("https://%s/results/invocations/%s/targets", e.frontendHostname(), invocationID)
-}
-
-// FrontendHostname is the hostname of the ResultStore UI for this Environment.
-func (e Environment) frontendHostname() string {
-	switch e {
-	case Production:
-		return "source.cloud.google.com"
-	case Staging:
-		return "grimoire-stagingprod.corp.google.com"
-	default:
-		// We should never get here.
-		panic("invalid environment: " + e)
-	}
-}
-
-// GRPCServiceAddress is the address of the ResultStoreUpload gRPC service.
-func (e Environment) GRPCServiceAddress() string {
-	switch e {
-	case Production:
-		return "resultstore.googleapis.com:443"
-	case Staging:
-		return "staging-resultstore.googleapis.com:443"
-	default:
-		// We should never get here.
-		panic("invalid environment: " + e)
-	}
-}
diff --git a/resultstore/upload_client.go b/resultstore/upload_client.go
deleted file mode 100644
index fd7849c..0000000
--- a/resultstore/upload_client.go
+++ /dev/null
@@ -1,329 +0,0 @@
-// Copyright 2018 The Fuchsia Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package resultstore
-
-import (
-	"context"
-	"log"
-
-	"github.com/google/uuid"
-	api "google.golang.org/genproto/googleapis/devtools/resultstore/v2"
-	"google.golang.org/genproto/protobuf/field_mask"
-)
-
-// UploadClient wraps the ResultStoreUpload client libraries.
-//
-// UploadClient generates UUIDs for each request sent to Resultstore. If the provided
-// Context object contains a non-empty string value for TestUUIDKey, that value is
-// used instead. This is done by calling `SetTestUUID(ctx, "uuid")`.
-//
-// UploadClient requires an Invocation's authorization token to be set in the provided Context.
-// This can be done by calling: `SetAuthToken(ctx, "auth-token")`.
-type UploadClient interface {
-	// CreateInvocation creates an Invocation in ResultStore. This must be called before
-	// any other "Create" methods, since all resources belong to an Invocation.
-	CreateInvocation(context.Context, *Invocation) (*Invocation, error)
-
-	// CreateConfiguration creates a new Configuration. Configurations typically represent
-	// build or test environments.
-	CreateConfiguration(context.Context, *Configuration, string) (*Configuration, error)
-
-	// CreateTarget creates a new build or test target for the Invocation with the given
-	// name.
-	CreateTarget(context.Context, *Target, string) (*Target, error)
-
-	// CreateConfiguredTarget creates a new ConfiguredTarget for the Target with the given
-	// name. ConfiguredTargets represent targets executing with a specific Configuration.
-	CreateConfiguredTarget(context.Context, *ConfiguredTarget, string) (*ConfiguredTarget, error)
-
-	// CreateTestAction creates a new Action for the ConfiguredTarget with the given name.
-	CreateTestAction(context.Context, *TestAction, string) (*TestAction, error)
-
-	// UpdateTestAction updates a list of TestAction properties (proto field paths) to the
-	// values specified in the given TestAction.  Fields that match the mask but aren't
-	// populated in the given TestAction are cleared.
-	UpdateTestAction(context.Context, *TestAction, []string) (*TestAction, error)
-
-	// UpdateConfiguredTarget updates a list of ConfiguredTarget properties (proto field
-	// paths) to the values specified in the given ConfiguredTarget.  Fields that match
-	// the mask but aren't populated in the given ConfiguredTarget are cleared.
-	UpdateConfiguredTarget(context.Context, *ConfiguredTarget, []string) (*ConfiguredTarget, error)
-
-	// UpdateTarget updates a list of Target properties (proto field paths) to the values
-	// specified in the given Target.  Fields that match the mask but aren't populated in
-	// the given Target are cleared.
-	UpdateTarget(context.Context, *Target, []string) (*Target, error)
-
-	// UpdateInvocation updates a list of Invocation properties (proto field paths) to the
-	// values specified in the given Invocation.  Fields that match the mask but aren't
-	// populated in the given Invocation are cleared.
-	UpdateInvocation(context.Context, *Invocation, []string) (*Invocation, error)
-
-	// FinishConfiguredTarget closes a ConfiguredTarget for editing.
-	FinishConfiguredTarget(context.Context, string) error
-
-	// FinishTarget closes a Target for editing.
-	FinishTarget(context.Context, string) error
-
-	// FinishInvocation closes an Invocation for editing.
-	FinishInvocation(context.Context, string) error
-}
-
-// NewUploadClient creates a new UploadClient. This is visible for testing; Use `Connect` instead.
-func NewUploadClient(client api.ResultStoreUploadClient) UploadClient {
-	return &uploadClient{client: client}
-}
-
-// The default UploadClient implementation.
-type uploadClient struct {
-	client api.ResultStoreUploadClient
-}
-
-// uuid generates an RFC-4122 compliant Version 4 UUID.  If the provided Context contains
-// a non-empty string value for TestUUIDKey, that value will be used instead. If there was
-// an error when reading the UUID from the context, a message describing the error is
-// logged.
-func (c *uploadClient) uuid(ctx context.Context) string {
-	value, err := TestUUID(ctx)
-
-	if err != nil {
-		log.Println(err)
-		return uuid.New().String()
-	}
-
-	if value == "" {
-		return uuid.New().String()
-	}
-
-	return value
-}
-
-func (c *uploadClient) CreateInvocation(ctx context.Context, invocation *Invocation) (*Invocation, error) {
-	authToken, err := AuthToken(ctx)
-	if err != nil {
-		return nil, err
-	}
-
-	res, err := c.client.CreateInvocation(ctx, &api.CreateInvocationRequest{
-		RequestId:          c.uuid(ctx),
-		AuthorizationToken: authToken,
-		InvocationId:       invocation.ID,
-		Invocation:         invocation.ToResultStoreInvocation(),
-	})
-	if err != nil {
-		return nil, err
-	}
-
-	output := new(Invocation)
-	output.FromResultStoreInvocation(res)
-	return output, nil
-}
-
-func (c *uploadClient) CreateConfiguration(ctx context.Context, config *Configuration, invocationName string) (*Configuration, error) {
-	authToken, err := AuthToken(ctx)
-	if err != nil {
-		return nil, err
-	}
-
-	res, err := c.client.CreateConfiguration(ctx, &api.CreateConfigurationRequest{
-		RequestId:          c.uuid(ctx),
-		AuthorizationToken: authToken,
-		Parent:             invocationName,
-		ConfigId:           config.ID,
-		Configuration:      config.ToResultStoreConfiguration(),
-	})
-	if err != nil {
-		return nil, err
-	}
-
-	output := new(Configuration)
-	output.FromResultStoreConfiguration(res)
-	return output, nil
-}
-
-func (c *uploadClient) CreateTarget(ctx context.Context, target *Target, invocationName string) (*Target, error) {
-	authToken, err := AuthToken(ctx)
-	if err != nil {
-		return nil, err
-	}
-
-	res, err := c.client.CreateTarget(ctx, &api.CreateTargetRequest{
-		RequestId:          c.uuid(ctx),
-		AuthorizationToken: authToken,
-		Parent:             invocationName,
-		TargetId:           target.ID.ID,
-		Target:             target.ToResultStoreTarget(),
-	})
-	if err != nil {
-		return nil, err
-	}
-
-	output := new(Target)
-	output.FromResultStoreTarget(res)
-	return output, nil
-}
-
-func (c *uploadClient) CreateConfiguredTarget(ctx context.Context, configTarget *ConfiguredTarget, targetName string) (*ConfiguredTarget, error) {
-	authToken, err := AuthToken(ctx)
-	if err != nil {
-		return nil, err
-	}
-
-	res, err := c.client.CreateConfiguredTarget(ctx, &api.CreateConfiguredTargetRequest{
-		AuthorizationToken: authToken,
-		RequestId:          c.uuid(ctx),
-		Parent:             targetName,
-		ConfigId:           configTarget.ID.ConfigID,
-		ConfiguredTarget:   configTarget.ToResultStoreConfiguredTarget(),
-	})
-	if err != nil {
-		return nil, err
-	}
-
-	output := new(ConfiguredTarget)
-	output.FromResultStoreConfiguredTarget(res)
-	return output, nil
-}
-
-func (c *uploadClient) CreateTestAction(ctx context.Context, action *TestAction, configTargetName string) (*TestAction, error) {
-	authToken, err := AuthToken(ctx)
-	if err != nil {
-		return nil, err
-	}
-
-	res, err := c.client.CreateAction(ctx, &api.CreateActionRequest{
-		AuthorizationToken: authToken,
-		RequestId:          c.uuid(ctx),
-		Parent:             configTargetName,
-		ActionId:           action.ID.ID,
-		Action:             action.ToResultStoreAction(),
-	})
-	if err != nil {
-		return nil, err
-	}
-
-	output := new(TestAction)
-	output.FromResultStoreAction(res)
-	return output, nil
-}
-
-func (c *uploadClient) UpdateTestAction(ctx context.Context, action *TestAction, fields []string) (*TestAction, error) {
-	authToken, err := AuthToken(ctx)
-	if err != nil {
-		return nil, err
-	}
-
-	res, err := c.client.UpdateAction(ctx, &api.UpdateActionRequest{
-		AuthorizationToken: authToken,
-		Action:             action.ToResultStoreAction(),
-		UpdateMask:         &field_mask.FieldMask{Paths: fields},
-	})
-	if err != nil {
-		return nil, err
-	}
-
-	output := new(TestAction)
-	output.FromResultStoreAction(res)
-	return output, nil
-}
-
-func (c *uploadClient) UpdateConfiguredTarget(ctx context.Context, configTarget *ConfiguredTarget, fields []string) (*ConfiguredTarget, error) {
-	authToken, err := AuthToken(ctx)
-	if err != nil {
-		return nil, err
-	}
-
-	res, err := c.client.UpdateConfiguredTarget(ctx, &api.UpdateConfiguredTargetRequest{
-		AuthorizationToken: authToken,
-		ConfiguredTarget:   configTarget.ToResultStoreConfiguredTarget(),
-		UpdateMask:         &field_mask.FieldMask{Paths: fields},
-	})
-	if err != nil {
-		return nil, err
-	}
-
-	output := new(ConfiguredTarget)
-	output.FromResultStoreConfiguredTarget(res)
-	return output, nil
-}
-
-func (c *uploadClient) UpdateTarget(ctx context.Context, target *Target, fields []string) (*Target, error) {
-	authToken, err := AuthToken(ctx)
-	if err != nil {
-		return nil, err
-	}
-
-	res, err := c.client.UpdateTarget(ctx, &api.UpdateTargetRequest{
-		AuthorizationToken: authToken,
-		UpdateMask:         &field_mask.FieldMask{Paths: fields},
-		Target:             target.ToResultStoreTarget(),
-	})
-	if err != nil {
-		return nil, err
-	}
-
-	output := new(Target)
-	output.FromResultStoreTarget(res)
-	return output, nil
-}
-
-func (c *uploadClient) UpdateInvocation(ctx context.Context, invocation *Invocation, fields []string) (*Invocation, error) {
-	authToken, err := AuthToken(ctx)
-	if err != nil {
-		return nil, err
-	}
-
-	res, err := c.client.UpdateInvocation(ctx, &api.UpdateInvocationRequest{
-		AuthorizationToken: authToken,
-		UpdateMask:         &field_mask.FieldMask{Paths: fields},
-		Invocation:         invocation.ToResultStoreInvocation(),
-	})
-	if err != nil {
-		return nil, err
-	}
-
-	output := new(Invocation)
-	output.FromResultStoreInvocation(res)
-	return output, nil
-}
-
-func (c *uploadClient) FinishConfiguredTarget(ctx context.Context, name string) error {
-	authToken, err := AuthToken(ctx)
-	if err != nil {
-		return err
-	}
-
-	_, err = c.client.FinishConfiguredTarget(ctx, &api.FinishConfiguredTargetRequest{
-		AuthorizationToken: authToken,
-		Name:               name,
-	})
-	return err
-}
-
-func (c *uploadClient) FinishTarget(ctx context.Context, name string) error {
-	authToken, err := AuthToken(ctx)
-	if err != nil {
-		return err
-	}
-
-	_, err = c.client.FinishTarget(ctx, &api.FinishTargetRequest{
-		AuthorizationToken: authToken,
-		Name:               name,
-	})
-	return err
-}
-
-func (c *uploadClient) FinishInvocation(ctx context.Context, name string) error {
-	authToken, err := AuthToken(ctx)
-	if err != nil {
-		return err
-	}
-
-	_, err = c.client.FinishInvocation(ctx, &api.FinishInvocationRequest{
-		AuthorizationToken: authToken,
-		Name:               name,
-	})
-	return err
-}
diff --git a/resultstore/upload_client_test.go b/resultstore/upload_client_test.go
deleted file mode 100644
index f4c7085..0000000
--- a/resultstore/upload_client_test.go
+++ /dev/null
@@ -1,527 +0,0 @@
-// Copyright 2018 The Fuchsia Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package resultstore_test
-
-import (
-	"context"
-	"reflect"
-	"testing"
-	"time"
-
-	"fuchsia.googlesource.com/infra/infra/resultstore"
-	mocks "fuchsia.googlesource.com/infra/infra/resultstore/mocks"
-	"github.com/golang/mock/gomock"
-
-	api "google.golang.org/genproto/googleapis/devtools/resultstore/v2"
-	"google.golang.org/genproto/protobuf/field_mask"
-)
-
-var (
-	// The value of entity start times and durations is not important for these tests,
-	// so we use the same value everywhere.
-	may18_1993 = time.Date(1993, time.May, 18, 0, 0, 0, 0, time.UTC)
-)
-
-const (
-	// The specific values of the UUIDs are not important for these tests. We just want to
-	// verify that the client sets some value other than the empty string, so we just use
-	// the same UUID everywhere.
-	testUUID = "uuid"
-
-	// The specific value of the auth token included in requests is not important. What
-	// matters is that the value in an RPC matches the value given to the UploadClient.
-	// Reuse this same value in all test cases.
-	testAuthToken = "auth_token"
-)
-
-type tester struct {
-	client resultstore.UploadClient
-	mock   *mocks.MockResultStoreUploadClient
-}
-
-func TestUploadClient(t *testing.T) {
-	tests := []struct {
-		// The method being tested. Keep tests ordered alphabetically by method name.
-		method string
-
-		// A brief test case description.
-		description string
-
-		// Exercises the method under test.
-		execute func(ctx context.Context, tester *tester) (interface{}, error)
-
-		// The expected output of the method
-		output interface{}
-	}{
-		{
-			method:      "CreateConfiguration",
-			description: "should rmake an RPC to create a Configuration",
-			output: &resultstore.Configuration{
-				Name:         "resultstore_configuration_name",
-				ID:           "configuration_id",
-				InvocationID: "invocation_id",
-			},
-			execute: func(ctx context.Context, tester *tester) (interface{}, error) {
-				input := &resultstore.Configuration{
-					ID:           "configuration_id",
-					InvocationID: "invocation_id",
-					Properties:   map[string]string{"key": "value"},
-				}
-
-				response := &api.Configuration{
-					Name: "resultstore_configuration_name",
-					Id: &api.Configuration_Id{
-						ConfigurationId: "configuration_id",
-						InvocationId:    "invocation_id",
-					},
-				}
-
-				tester.mock.EXPECT().
-					CreateConfiguration(ctx, &api.CreateConfigurationRequest{
-						RequestId:          testUUID,
-						AuthorizationToken: testAuthToken,
-						Parent:             "invocation_name",
-						ConfigId:           "configuration_id",
-						Configuration:      input.ToResultStoreConfiguration(),
-					}).
-					Return(response, nil)
-
-				return tester.client.CreateConfiguration(ctx, input, "invocation_name")
-			},
-		},
-		{
-			method:      "CreateConfiguredTarget",
-			description: "should make an RPC to create a ConfiguredTarget",
-			output: &resultstore.ConfiguredTarget{
-				Name: "resultstore_configured_target_name",
-				ID: &resultstore.ConfiguredTargetID{
-					InvocationID: "invocation_id",
-					ConfigID:     "configuration_id",
-					TargetID:     "target_id",
-				},
-			},
-			execute: func(ctx context.Context, tester *tester) (interface{}, error) {
-				input := &resultstore.ConfiguredTarget{
-					ID: &resultstore.ConfiguredTargetID{
-						InvocationID: "invocation_id",
-						TargetID:     "target_id",
-						ConfigID:     "configuration_id",
-					},
-					Properties: map[string]string{"key": "value"},
-					StartTime:  may18_1993,
-					Status:     resultstore.Passed,
-				}
-
-				response := &api.ConfiguredTarget{
-					Name: "resultstore_configured_target_name",
-					Id: &api.ConfiguredTarget_Id{
-						InvocationId:    "invocation_id",
-						ConfigurationId: "configuration_id",
-						TargetId:        "target_id",
-					},
-				}
-
-				tester.mock.EXPECT().
-					CreateConfiguredTarget(ctx, &api.CreateConfiguredTargetRequest{
-						RequestId:          testUUID,
-						AuthorizationToken: testAuthToken,
-						Parent:             "target_name",
-						ConfigId:           input.ID.ConfigID,
-						ConfiguredTarget:   input.ToResultStoreConfiguredTarget(),
-					}).
-					Return(response, nil)
-
-				return tester.client.CreateConfiguredTarget(ctx, input, "target_name")
-			},
-		},
-		{
-			method:      "CreateInvocation",
-			description: "should make an RPC to create an Invocation",
-			output: &resultstore.Invocation{
-				Name: "resultstore_invocation_name",
-				ID:   "invocation_id",
-			},
-			execute: func(ctx context.Context, tester *tester) (interface{}, error) {
-				input := &resultstore.Invocation{
-					ProjectID:  "123456789",
-					ID:         "invocation_id",
-					Users:      []string{"user"},
-					Labels:     []string{"label"},
-					Properties: map[string]string{"key": "value"},
-					LogURL:     "http://test.log",
-					StartTime:  may18_1993,
-					Status:     resultstore.Passed,
-				}
-
-				response := &api.Invocation{
-					Name: "resultstore_invocation_name",
-					Id: &api.Invocation_Id{
-						InvocationId: "invocation_id",
-					},
-				}
-
-				tester.mock.EXPECT().
-					CreateInvocation(ctx, &api.CreateInvocationRequest{
-						RequestId:          testUUID,
-						AuthorizationToken: testAuthToken,
-						InvocationId:       "invocation_id",
-						Invocation:         input.ToResultStoreInvocation(),
-					}).
-					Return(response, nil)
-
-				return tester.client.CreateInvocation(ctx, input)
-			},
-		},
-		{
-			method:      "CreateTarget",
-			description: "should make an RPC to create a Target",
-			output: &resultstore.Target{
-				Name: "resultstore_target_name",
-				ID: &resultstore.TargetID{
-					ID:           "target_id",
-					InvocationID: "invocation_id",
-				},
-			},
-			execute: func(ctx context.Context, tester *tester) (interface{}, error) {
-				input := &resultstore.Target{
-					ID: &resultstore.TargetID{
-						ID: "target_id",
-					},
-					Properties: map[string]string{"key": "value"},
-					StartTime:  may18_1993,
-					Status:     resultstore.Passed,
-				}
-
-				response := &api.Target{
-					Name: "resultstore_target_name",
-					Id: &api.Target_Id{
-						TargetId:     "target_id",
-						InvocationId: "invocation_id",
-					},
-				}
-
-				tester.mock.EXPECT().
-					CreateTarget(ctx, &api.CreateTargetRequest{
-						RequestId:          testUUID,
-						AuthorizationToken: testAuthToken,
-						Parent:             "invocation_name",
-						TargetId:           input.ID.ID,
-						Target:             input.ToResultStoreTarget(),
-					}).
-					Return(response, nil)
-
-				return tester.client.CreateTarget(ctx, input, "invocation_name")
-			},
-		},
-		{
-			method:      "CreateTestAction",
-			description: "should make an RPC to create a Test Action",
-			output: &resultstore.TestAction{
-				Name: "resultstore_action_name",
-				ID: &resultstore.TestActionID{
-					InvocationID: "invocation_id",
-					ConfigID:     "configuration_id",
-					TargetID:     "target_id",
-				},
-			},
-			execute: func(ctx context.Context, tester *tester) (interface{}, error) {
-				input := &resultstore.TestAction{
-					ID: &resultstore.TestActionID{
-						ID:           "test",
-						InvocationID: "invocation_id",
-						TargetID:     "target_id",
-						ConfigID:     "configuration_id",
-					},
-					TestSuite:  "test_suite",
-					TestLogURI: "http://test.log",
-					StartTime:  may18_1993,
-					Status:     resultstore.Passed,
-				}
-
-				response := &api.Action{
-					Name: "resultstore_action_name",
-					Id: &api.Action_Id{
-						InvocationId:    "invocation_id",
-						ConfigurationId: "configuration_id",
-						TargetId:        "target_id",
-					},
-				}
-
-				tester.mock.EXPECT().
-					CreateAction(ctx, &api.CreateActionRequest{
-						RequestId:          testUUID,
-						AuthorizationToken: testAuthToken,
-						Parent:             "configured_target_name",
-						ActionId:           "test",
-						Action:             input.ToResultStoreAction(),
-					}).
-					Return(response, nil)
-
-				return tester.client.CreateTestAction(ctx, input, "configured_target_name")
-
-			},
-		},
-		{
-			method:      "FinishConfiguredTarget",
-			description: "should make an RPC to finish a ConfiguredTarget",
-			execute: func(ctx context.Context, tester *tester) (interface{}, error) {
-				tester.mock.EXPECT().
-					FinishConfiguredTarget(ctx, &api.FinishConfiguredTargetRequest{
-						AuthorizationToken: testAuthToken,
-						Name:               "configured_target_name",
-					}).
-					Return(&api.FinishConfiguredTargetResponse{}, nil)
-
-				return nil, tester.client.FinishConfiguredTarget(ctx, "configured_target_name")
-			},
-		},
-		{
-			method:      "FinishInvocation",
-			description: "should make an RPC to finish an Invocation",
-			execute: func(ctx context.Context, tester *tester) (interface{}, error) {
-				tester.mock.EXPECT().
-					FinishInvocation(ctx, &api.FinishInvocationRequest{
-						AuthorizationToken: testAuthToken,
-						Name:               "invocation_name",
-					}).
-					Return(&api.FinishInvocationResponse{}, nil)
-
-				return nil, tester.client.FinishInvocation(ctx, "invocation_name")
-			},
-		},
-		{
-			method:      "FinishTarget",
-			description: "should make an RPC to finish a Target",
-			execute: func(ctx context.Context, tester *tester) (interface{}, error) {
-				tester.mock.EXPECT().
-					FinishTarget(ctx, &api.FinishTargetRequest{
-						AuthorizationToken: testAuthToken,
-						Name:               "target_name",
-					}).
-					Return(&api.FinishTargetResponse{}, nil)
-
-				return nil, tester.client.FinishTarget(ctx, "target_name")
-			},
-		},
-		{
-			method:      "UpdateConfiguredTarget",
-			description: "should make an RPC to update a ConfiguredTarget",
-			output: &resultstore.ConfiguredTarget{
-				Name: "resultstore_configured_target_name",
-				ID: &resultstore.ConfiguredTargetID{
-					InvocationID: "invocation_id",
-					ConfigID:     "configuration_id",
-					TargetID:     "target_id",
-				},
-			},
-			execute: func(ctx context.Context, tester *tester) (interface{}, error) {
-				input := &resultstore.ConfiguredTarget{
-					ID: &resultstore.ConfiguredTargetID{
-						InvocationID: "invocation_id",
-						TargetID:     "target_id",
-						ConfigID:     "configuration_id",
-					},
-					Properties: map[string]string{"key": "value"},
-					Status:     resultstore.Passed,
-					StartTime:  may18_1993,
-					Duration:   time.Hour,
-				}
-
-				response := &api.ConfiguredTarget{
-					Name: "resultstore_configured_target_name",
-					Id: &api.ConfiguredTarget_Id{
-						InvocationId:    "invocation_id",
-						ConfigurationId: "configuration_id",
-						TargetId:        "target_id",
-					},
-				}
-
-				fieldsToUpdate := []string{"timing.duration", "status_attributes"}
-
-				tester.mock.EXPECT().
-					UpdateConfiguredTarget(ctx, &api.UpdateConfiguredTargetRequest{
-						AuthorizationToken: testAuthToken,
-						ConfiguredTarget:   input.ToResultStoreConfiguredTarget(),
-						UpdateMask:         &field_mask.FieldMask{Paths: fieldsToUpdate},
-					}).
-					Return(response, nil)
-
-				return tester.client.UpdateConfiguredTarget(ctx, input, fieldsToUpdate)
-			},
-		},
-		{
-			method:      "UpdateInvocation",
-			description: "should make an RPC to update an Invocation",
-			output: &resultstore.Invocation{
-				Name: "resultstore_invocation_name",
-				ID:   "invocation_id",
-			},
-			execute: func(ctx context.Context, tester *tester) (interface{}, error) {
-				input := &resultstore.Invocation{
-					ID:         "invocation_id",
-					Properties: map[string]string{"key": "value"},
-					ProjectID:  "project_id",
-					StartTime:  may18_1993,
-					Duration:   time.Hour,
-					Users:      []string{"users"},
-					Labels:     []string{"label"},
-					LogURL:     "url",
-					Status:     resultstore.Passed,
-				}
-
-				response := &api.Invocation{
-					Name: "resultstore_invocation_name",
-					Id: &api.Invocation_Id{
-						InvocationId: "invocation_id",
-					},
-				}
-
-				fieldsToUpdate := []string{"timing.duration", "status_attributes"}
-
-				tester.mock.EXPECT().
-					UpdateInvocation(ctx, &api.UpdateInvocationRequest{
-						AuthorizationToken: testAuthToken,
-						Invocation:         input.ToResultStoreInvocation(),
-						UpdateMask:         &field_mask.FieldMask{Paths: fieldsToUpdate},
-					}).
-					Return(response, nil)
-
-				return tester.client.UpdateInvocation(ctx, input, fieldsToUpdate)
-			},
-		},
-		{
-			method:      "UpdateTarget",
-			description: "should make an RPC to update a Target",
-			output: &resultstore.Target{
-				Name: "resultstore_target_name",
-				ID: &resultstore.TargetID{
-					ID:           "target_id",
-					InvocationID: "invocation_id",
-				},
-			},
-			execute: func(ctx context.Context, tester *tester) (interface{}, error) {
-				input := &resultstore.Target{
-					ID: &resultstore.TargetID{
-						ID:           "target_id",
-						InvocationID: "invocation_id",
-					},
-					Properties: map[string]string{"key": "value"},
-					StartTime:  may18_1993,
-					Duration:   time.Hour,
-					Status:     resultstore.Passed,
-				}
-
-				response := &api.Target{
-					Name: "resultstore_target_name",
-					Id: &api.Target_Id{
-						TargetId:     "target_id",
-						InvocationId: "invocation_id",
-					},
-				}
-
-				fieldsToUpdate := []string{"timing.duration", "status_attributes"}
-
-				tester.mock.EXPECT().
-					UpdateTarget(ctx, &api.UpdateTargetRequest{
-						AuthorizationToken: testAuthToken,
-						Target:             input.ToResultStoreTarget(),
-						UpdateMask:         &field_mask.FieldMask{Paths: fieldsToUpdate},
-					}).
-					Return(response, nil)
-
-				return tester.client.UpdateTarget(ctx, input, fieldsToUpdate)
-			},
-		},
-		{
-			method:      "UpdateTestAction",
-			description: "should make an RPC to update a Test Action",
-			output: &resultstore.TestAction{
-				Name: "resultstore_action_name",
-				ID: &resultstore.TestActionID{
-					ID:           "action_id",
-					InvocationID: "invocation_id",
-					ConfigID:     "configuration_id",
-					TargetID:     "target_id",
-				},
-			},
-			execute: func(ctx context.Context, tester *tester) (interface{}, error) {
-				input := &resultstore.TestAction{
-					ID: &resultstore.TestActionID{
-						ID:           "test",
-						InvocationID: "invocation_id",
-						TargetID:     "target_id",
-						ConfigID:     "configuration_id",
-					},
-					TestSuite:  "test_suite",
-					TestLogURI: "http://test.log",
-					StartTime:  may18_1993,
-					Duration:   time.Hour,
-					Status:     resultstore.Passed,
-				}
-
-				response := &api.Action{
-					Name: "resultstore_action_name",
-					Id: &api.Action_Id{
-						ActionId:        "action_id",
-						InvocationId:    "invocation_id",
-						ConfigurationId: "configuration_id",
-						TargetId:        "target_id",
-					},
-				}
-
-				fieldsToUpdate := []string{"timing.duration", "status_attributes"}
-
-				tester.mock.EXPECT().
-					UpdateAction(ctx, &api.UpdateActionRequest{
-						AuthorizationToken: testAuthToken,
-						Action:             input.ToResultStoreAction(),
-						UpdateMask:         &field_mask.FieldMask{Paths: fieldsToUpdate},
-					}).
-					Return(response, nil)
-
-				return tester.client.UpdateTestAction(ctx, input, fieldsToUpdate)
-			},
-		},
-	}
-
-	setup := func(t *testing.T) (context.Context, resultstore.UploadClient, *mocks.MockResultStoreUploadClient, *gomock.Controller) {
-		ctx, err := resultstore.SetTestUUID(context.Background(), testUUID)
-		if err != nil {
-			t.Fatal(err)
-		}
-
-		ctx, err = resultstore.SetAuthToken(ctx, testAuthToken)
-		if err != nil {
-			t.Fatal(err)
-		}
-
-		controller := gomock.NewController(t)
-		mock := mocks.NewMockResultStoreUploadClient(controller)
-		client := resultstore.NewUploadClient(mock)
-		return ctx, client, mock, controller
-	}
-
-	for _, tt := range tests {
-		ctx, client, mock, controller := setup(t)
-		defer controller.Finish()
-
-		t.Run(tt.method, func(t *testing.T) {
-			t.Run(tt.description, func(t *testing.T) {
-				actual, err := tt.execute(ctx, &tester{client: client, mock: mock})
-				if err != nil {
-					t.Error(err.Error())
-					return
-				}
-
-				expected := tt.output
-				if !reflect.DeepEqual(expected, actual) {
-					t.Errorf("objects do not match:\n")
-					t.Errorf("Expected: %+v\n", expected)
-					t.Errorf("Actual:   %+v\n", actual)
-				}
-			})
-		})
-	}
-}
