diff --git a/acceptance/openstack/compute/compute_test.go b/acceptance/openstack/compute/compute_test.go
new file mode 100644
index 0000000..7473f13
--- /dev/null
+++ b/acceptance/openstack/compute/compute_test.go
@@ -0,0 +1,369 @@
+// +build acceptance
+
+package compute
+
+import (
+	"fmt"
+	"github.com/rackspace/gophercloud/openstack/compute/flavors"
+	"github.com/rackspace/gophercloud/openstack/compute/images"
+	"github.com/rackspace/gophercloud/openstack/compute/servers"
+	"os"
+	"testing"
+	"github.com/rackspace/gophercloud/acceptance/tools"
+)
+
+var service = "compute"
+
+func TestListServers(t *testing.T) {
+	ts, err := tools.SetupForList(service)
+	if err != nil {
+		t.Error(err)
+		return
+	}
+
+	fmt.Fprintln(ts.W, "ID\tRegion\tName\tStatus\tIPv4\tIPv6\t")
+
+	region := os.Getenv("OS_REGION_NAME")
+	n := 0
+	for _, ep := range ts.EPs {
+		if (region != "") && (region != ep.Region) {
+			continue
+		}
+
+		client := servers.NewClient(ep.PublicURL, ts.A, ts.O)
+
+		listResults, err := servers.List(client)
+		if err != nil {
+			t.Error(err)
+			return
+		}
+
+		svrs, err := servers.GetServers(listResults)
+		if err != nil {
+			t.Error(err)
+			return
+		}
+
+		n = n + len(svrs)
+
+		for _, s := range svrs {
+			fmt.Fprintf(ts.W, "%s\t%s\t%s\t%s\t%s\t%s\t\n", s.Id, s.Name, ep.Region, s.Status, s.AccessIPv4, s.AccessIPv6)
+		}
+	}
+	ts.W.Flush()
+	fmt.Printf("--------\n%d servers listed.\n", n)
+}
+
+func TestListImages(t *testing.T) {
+	ts, err := tools.SetupForList(service)
+	if err != nil {
+		t.Error(err)
+		return
+	}
+
+	fmt.Fprintln(ts.W, "ID\tRegion\tName\tStatus\tCreated\t")
+
+	region := os.Getenv("OS_REGION_NAME")
+	n := 0
+	for _, ep := range ts.EPs {
+		if (region != "") && (region != ep.Region) {
+			continue
+		}
+
+		client := images.NewClient(ep.PublicURL, ts.A, ts.O)
+
+		listResults, err := images.List(client)
+		if err != nil {
+			t.Error(err)
+			return
+		}
+
+		imgs, err := images.GetImages(listResults)
+		if err != nil {
+			t.Error(err)
+			return
+		}
+
+		n = n + len(imgs)
+
+		for _, i := range imgs {
+			fmt.Fprintf(ts.W, "%s\t%s\t%s\t%s\t%s\t\n", i.Id, ep.Region, i.Name, i.Status, i.Created)
+		}
+	}
+	ts.W.Flush()
+	fmt.Printf("--------\n%d images listed.\n", n)
+}
+
+func TestListFlavors(t *testing.T) {
+	ts, err := tools.SetupForList(service)
+	if err != nil {
+		t.Error(err)
+		return
+	}
+
+	fmt.Fprintln(ts.W, "ID\tRegion\tName\tRAM\tDisk\tVCPUs\t")
+
+	region := os.Getenv("OS_REGION_NAME")
+	n := 0
+	for _, ep := range ts.EPs {
+		if (region != "") && (region != ep.Region) {
+			continue
+		}
+
+		client := flavors.NewClient(ep.PublicURL, ts.A, ts.O)
+
+		listResults, err := flavors.List(client, flavors.ListFilterOptions{})
+		if err != nil {
+			t.Error(err)
+			return
+		}
+
+		flavs, err := flavors.GetFlavors(listResults)
+		if err != nil {
+			t.Error(err)
+			return
+		}
+
+		n = n + len(flavs)
+
+		for _, f := range flavs {
+			fmt.Fprintf(ts.W, "%s\t%s\t%s\t%d\t%d\t%d\t\n", f.Id, ep.Region, f.Name, f.Ram, f.Disk, f.VCpus)
+		}
+	}
+	ts.W.Flush()
+	fmt.Printf("--------\n%d flavors listed.\n", n)
+}
+
+func TestGetFlavor(t *testing.T) {
+	ts, err := tools.SetupForCRUD()
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	region := os.Getenv("OS_REGION_NAME")
+	for _, ep := range ts.EPs {
+		if (region != "") && (region != ep.Region) {
+			continue
+		}
+		client := flavors.NewClient(ep.PublicURL, ts.A, ts.O)
+
+		getResults, err := flavors.Get(client, ts.FlavorId)
+		if err != nil {
+			t.Fatal(err)
+		}
+		flav, err := flavors.GetFlavor(getResults)
+		if err != nil {
+			t.Fatal(err)
+		}
+		fmt.Printf("%#v\n", flav)
+	}
+}
+
+func TestCreateDestroyServer(t *testing.T) {
+	ts, err := tools.SetupForCRUD()
+	if err != nil {
+		t.Error(err)
+		return
+	}
+
+	err = tools.CreateServer(ts)
+	if err != nil {
+		t.Error(err)
+		return
+	}
+
+	// We put this in a defer so that it gets executed even in the face of errors or panics.
+	defer func() {
+		servers.Delete(ts.Client, ts.CreatedServer.Id)
+	}()
+
+	err = tools.WaitForStatus(ts, "ACTIVE")
+	if err != nil {
+		t.Error(err)
+	}
+}
+
+func TestUpdateServer(t *testing.T) {
+	ts, err := tools.SetupForCRUD()
+	if err != nil {
+		t.Error(err)
+		return
+	}
+
+	err = tools.CreateServer(ts)
+	if err != nil {
+		t.Error(err)
+		return
+	}
+
+	defer func() {
+		servers.Delete(ts.Client, ts.CreatedServer.Id)
+	}()
+
+	err = tools.WaitForStatus(ts, "ACTIVE")
+	if err != nil {
+		t.Error(err)
+		return
+	}
+
+	err = tools.ChangeServerName(ts)
+	if err != nil {
+		t.Error(err)
+		return
+	}
+}
+
+func TestActionChangeAdminPassword(t *testing.T) {
+	t.Parallel()
+
+	ts, err := tools.SetupForCRUD()
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	err = tools.CreateServer(ts)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	defer func(){
+		servers.Delete(ts.Client, ts.CreatedServer.Id)
+	}()
+
+	err = tools.WaitForStatus(ts, "ACTIVE")
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	err = tools.ChangeAdminPassword(ts)
+	if err != nil {
+		t.Fatal(err)
+	}
+}
+
+func TestActionReboot(t *testing.T) {
+	t.Parallel()
+
+	ts, err := tools.SetupForCRUD()
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	err = tools.CreateServer(ts)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	defer func(){
+		servers.Delete(ts.Client, ts.CreatedServer.Id)
+	}()
+
+	err = tools.WaitForStatus(ts, "ACTIVE")
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	err = servers.Reboot(ts.Client, ts.CreatedServer.Id, "aldhjflaskhjf")
+	if err == nil {
+		t.Fatal("Expected the SDK to provide an ArgumentError here")
+	}
+
+	err = tools.RebootServer(ts)
+	if err != nil {
+		t.Fatal(err)
+	}
+}
+
+func TestActionRebuild(t *testing.T) {
+	t.Parallel()
+
+	ts, err := tools.SetupForCRUD()
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	err = tools.CreateServer(ts)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	defer func(){
+		servers.Delete(ts.Client, ts.CreatedServer.Id)
+	}()
+
+	err = tools.WaitForStatus(ts, "ACTIVE")
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	err = tools.RebuildServer(ts)
+	if err != nil {
+		t.Fatal(err)
+	}
+}
+
+func TestActionResizeConfirm(t *testing.T) {
+	t.Parallel()
+	
+	ts, err := tools.SetupForCRUD()
+	if err != nil {
+		t.Fatal(err)
+	}
+	
+	err = tools.CreateServer(ts)
+	if err != nil {
+		t.Fatal(err)
+	}
+	
+	defer func(){
+		servers.Delete(ts.Client, ts.CreatedServer.Id)
+	}()
+	
+	err = tools.WaitForStatus(ts, "ACTIVE")
+	if err != nil {
+		t.Fatal(err)
+	}
+	
+	err = tools.ResizeServer(ts)
+	if err != nil {
+		t.Fatal(err)
+	}
+	
+	err = tools.ConfirmResize(ts)
+	if err != nil {
+		t.Fatal(err)
+	}
+}
+
+func TestActionResizeRevert(t *testing.T) {
+	t.Parallel()
+	
+	ts, err := tools.SetupForCRUD()
+	if err != nil {
+		t.Fatal(err)
+	}
+	
+	err = tools.CreateServer(ts)
+	if err != nil {
+		t.Fatal(err)
+	}
+	
+	defer func(){
+		servers.Delete(ts.Client, ts.CreatedServer.Id)
+	}()
+	
+	err = tools.WaitForStatus(ts, "ACTIVE")
+	if err != nil {
+		t.Fatal(err)
+	}
+	
+	err = tools.ResizeServer(ts)
+	if err != nil {
+		t.Fatal(err)
+	}
+	
+	err = tools.RevertResize(ts)
+	if err != nil {
+		t.Fatal(err)
+	}
+}
diff --git a/acceptance/openstack/compute/pkg.go b/acceptance/openstack/compute/pkg.go
new file mode 100644
index 0000000..a887fe9
--- /dev/null
+++ b/acceptance/openstack/compute/pkg.go
@@ -0,0 +1 @@
+package compute
diff --git a/acceptance/openstack/compute_test.go b/acceptance/openstack/compute/test.go
similarity index 100%
rename from acceptance/openstack/compute_test.go
rename to acceptance/openstack/compute/test.go
diff --git a/acceptance/openstack/compute/tools_test.go b/acceptance/openstack/compute/tools_test.go
new file mode 100644
index 0000000..0469053
--- /dev/null
+++ b/acceptance/openstack/compute/tools_test.go
@@ -0,0 +1,364 @@
+// +build acceptance
+
+package compute
+
+import (
+	"crypto/rand"
+	"fmt"
+	"github.com/rackspace/gophercloud/openstack/compute/servers"
+	"github.com/rackspace/gophercloud/openstack/identity"
+	"github.com/rackspace/gophercloud/openstack/utils"
+	"os"
+	"text/tabwriter"
+	"time"
+)
+
+var errTimeout = fmt.Errorf("Timeout.")
+
+type testState struct {
+	o             identity.AuthOptions
+	a             identity.AuthResults
+	sc            *identity.ServiceCatalog
+	eps           []identity.Endpoint
+	w             *tabwriter.Writer
+	imageId       string
+	flavorId      string
+	region        string
+	ep            string
+	client        *servers.Client
+	createdServer *servers.Server
+	gottenServer  *servers.Server
+	updatedServer *servers.Server
+	serverName    string
+	alternateName string
+	flavorIdResize string
+}
+
+func SetupForList(service string) (*testState, error) {
+	var err error
+
+	ts := new(testState)
+
+	ts.o, err = utils.AuthOptions()
+	if err != nil {
+		return ts, err
+	}
+
+	ts.a, err = identity.Authenticate(ts.o)
+	if err != nil {
+		return ts, err
+	}
+
+	ts.sc, err = identity.GetServiceCatalog(ts.a)
+	if err != nil {
+		return ts, err
+	}
+
+	ts.eps, err = FindAllEndpoints(ts.sc, service)
+	if err != nil {
+		return ts, err
+	}
+
+	ts.w = new(tabwriter.Writer)
+	ts.w.Init(os.Stdout, 2, 8, 2, ' ', 0)
+
+	return ts, nil
+}
+
+func SetupForCRUD() (*testState, error) {
+	ts, err := SetupForList("compute")
+	if err != nil {
+		return ts, err
+	}
+
+	ts.imageId = os.Getenv("OS_IMAGE_ID")
+	if ts.imageId == "" {
+		return ts, fmt.Errorf("Expected OS_IMAGE_ID environment variable to be set")
+	}
+
+	ts.flavorId = os.Getenv("OS_FLAVOR_ID")
+	if ts.flavorId == "" {
+		return ts, fmt.Errorf("Expected OS_FLAVOR_ID environment variable to be set")
+	}
+
+	ts.flavorIdResize = os.Getenv("OS_FLAVOR_ID_RESIZE")
+	if ts.flavorIdResize == "" {
+		return ts, fmt.Errorf("Expected OS_FLAVOR_ID_RESIZE environment variable to be set")
+	}
+
+	if ts.flavorIdResize == ts.flavorId {
+		return ts, fmt.Errorf("OS_FLAVOR_ID and OS_FLAVOR_ID_RESIZE cannot be the same")
+	}
+
+	ts.region = os.Getenv("OS_REGION_NAME")
+	if ts.region == "" {
+		ts.region = ts.eps[0].Region
+	}
+
+	ts.ep, err = FindEndpointForRegion(ts.eps, ts.region)
+	if err != nil {
+		return ts, err
+	}
+
+	return ts, err
+}
+
+func FindAllEndpoints(sc *identity.ServiceCatalog, service string) ([]identity.Endpoint, error) {
+	ces, err := sc.CatalogEntries()
+	if err != nil {
+		return nil, err
+	}
+
+	for _, ce := range ces {
+		if ce.Type == service {
+			return ce.Endpoints, nil
+		}
+	}
+
+	return nil, fmt.Errorf(service + " endpoint not found.")
+}
+
+func FindEndpointForRegion(eps []identity.Endpoint, r string) (string, error) {
+	for _, ep := range eps {
+		if ep.Region == r {
+			return ep.PublicURL, nil
+		}
+	}
+	return "", fmt.Errorf("Unknown region %s", r)
+}
+
+func CountDown(ts *testState, timeout int) (bool, int, error) {
+	if timeout < 1 {
+		return false, 0, errTimeout
+	}
+	time.Sleep(1 * time.Second)
+	timeout--
+
+	gr, err := servers.GetDetail(ts.client, ts.createdServer.Id)
+	if err != nil {
+		return false, timeout, err
+	}
+
+	ts.gottenServer, err = servers.GetServer(gr)
+	if err != nil {
+		return false, timeout, err
+	}
+
+	return true, timeout, nil
+}
+
+func CreateServer(ts *testState) error {
+	ts.serverName = RandomString("ACPTTEST", 16)
+	fmt.Printf("Attempting to create server: %s\n", ts.serverName)
+
+	ts.client = servers.NewClient(ts.ep, ts.a, ts.o)
+
+	cr, err := servers.Create(ts.client, map[string]interface{}{
+		"flavorRef": ts.flavorId,
+		"imageRef":  ts.imageId,
+		"name":      ts.serverName,
+	})
+	if err != nil {
+		return err
+	}
+
+	ts.createdServer, err = servers.GetServer(cr)
+	return err
+}
+
+func WaitForStatus(ts *testState, s string) error {
+	var (
+		inProgress bool
+		timeout    int
+		err        error
+	)
+
+	for inProgress, timeout, err = CountDown(ts, 300); inProgress; inProgress, timeout, err = CountDown(ts, timeout) {
+		if ts.gottenServer.Id != ts.createdServer.Id {
+			return fmt.Errorf("created server id (%s) != gotten server id (%s)", ts.createdServer.Id, ts.gottenServer.Id)
+		}
+
+		if ts.gottenServer.Status == s {
+			fmt.Printf("Server reached state %s after %d seconds (approximately)\n", s, 300-timeout)
+			break
+		}
+	}
+
+	if err == errTimeout {
+		fmt.Printf("Time out -- I'm not waiting around.\n")
+		err = nil
+	}
+
+	return err
+}
+
+func ChangeServerName(ts *testState) error {
+	var (
+		inProgress bool
+		timeout    int
+	)
+
+	ts.alternateName = RandomString("ACPTTEST", 16)
+	for ts.alternateName == ts.serverName {
+		ts.alternateName = RandomString("ACPTTEST", 16)
+	}
+	fmt.Println("Attempting to change server name")
+
+	ur, err := servers.Update(ts.client, ts.createdServer.Id, map[string]interface{}{
+		"name": ts.alternateName,
+	})
+	if err != nil {
+		return err
+	}
+
+	ts.updatedServer, err = servers.GetServer(ur)
+	if err != nil {
+		return err
+	}
+
+	if ts.updatedServer.Id != ts.createdServer.Id {
+		return fmt.Errorf("Expected updated and created server to share the same ID")
+	}
+
+	for inProgress, timeout, err = CountDown(ts, 300); inProgress; inProgress, timeout, err = CountDown(ts, timeout) {
+		if ts.gottenServer.Id != ts.updatedServer.Id {
+			return fmt.Errorf("Updated server ID (%s) != gotten server ID (%s)", ts.updatedServer.Id, ts.gottenServer.Id)
+		}
+
+		if ts.gottenServer.Name == ts.alternateName {
+			fmt.Printf("Server updated after %d seconds (approximately)\n", 300-timeout)
+			break
+		}
+	}
+
+	if err == errTimeout {
+		fmt.Printf("I'm not waiting around.\n")
+		err = nil
+	}
+
+	return err
+}
+
+func MakeNewPassword(oldPass string) string {
+	fmt.Println("Current password: "+oldPass)
+	randomPassword := RandomString("", 16)
+	for randomPassword == oldPass {
+		randomPassword = RandomString("", 16)
+	}
+	fmt.Println("    New password: "+randomPassword)
+	return randomPassword
+}
+
+func ChangeAdminPassword(ts *testState) error {
+	randomPassword := MakeNewPassword(ts.createdServer.AdminPass)
+	
+	err := servers.ChangeAdminPassword(ts.client, ts.createdServer.Id, randomPassword)
+	if err != nil {
+		return err
+	}
+	
+	err = WaitForStatus(ts, "PASSWORD")
+	if err != nil {
+		return err
+	}
+	
+	return WaitForStatus(ts, "ACTIVE")
+}
+
+func RebootServer(ts *testState) error {
+	fmt.Println("Attempting reboot of server "+ts.createdServer.Id)
+	err := servers.Reboot(ts.client, ts.createdServer.Id, servers.OSReboot)
+	if err != nil {
+		return err
+	}
+	
+	err = WaitForStatus(ts, "REBOOT")
+	if err != nil {
+		return err
+	}
+	
+	return WaitForStatus(ts, "ACTIVE")
+}
+
+func RebuildServer(ts *testState) error {
+	fmt.Println("Attempting to rebuild server "+ts.createdServer.Id)
+
+	newPassword := MakeNewPassword(ts.createdServer.AdminPass)
+	newName := RandomString("ACPTTEST", 16)
+	sr, err := servers.Rebuild(ts.client, ts.createdServer.Id, newName, newPassword, ts.imageId, nil)
+	if err != nil {
+		return err
+	}
+	
+	s, err := servers.GetServer(sr)
+	if err != nil {
+		return err
+	}
+	if s.Id != ts.createdServer.Id {
+		return fmt.Errorf("Expected rebuilt server ID of %s; got %s", ts.createdServer.Id, s.Id)
+	}
+
+	err = WaitForStatus(ts, "REBUILD")
+	if err != nil {
+		return err
+	}
+	
+	return WaitForStatus(ts, "ACTIVE")
+}
+
+func ResizeServer(ts *testState) error {
+	fmt.Println("Attempting to resize server "+ts.createdServer.Id)
+
+	err := servers.Resize(ts.client, ts.createdServer.Id, ts.flavorIdResize)
+	if err != nil {
+		return err
+	}
+
+	err = WaitForStatus(ts, "RESIZE")
+	if err != nil {
+		return err
+	}
+
+	return WaitForStatus(ts, "VERIFY_RESIZE")
+}
+
+func ConfirmResize(ts *testState) error {
+	fmt.Println("Attempting to confirm resize for server "+ts.createdServer.Id)
+	
+	err := servers.ConfirmResize(ts.client, ts.createdServer.Id)
+	if err != nil {
+		return err
+	}
+	
+	return WaitForStatus(ts, "ACTIVE")
+}
+
+func RevertResize(ts *testState) error {
+	fmt.Println("Attempting to revert resize for server "+ts.createdServer.Id)
+	
+	err := servers.RevertResize(ts.client, ts.createdServer.Id)
+	if err != nil {
+		return err
+	}
+
+	err = WaitForStatus(ts, "REVERT_RESIZE")
+	if err != nil {
+		return err
+	}
+
+	return WaitForStatus(ts, "ACTIVE")
+}
+
+// randomString generates a string of given length, but random content.
+// All content will be within the ASCII graphic character set.
+// (Implementation from Even Shaw's contribution on
+// http://stackoverflow.com/questions/12771930/what-is-the-fastest-way-to-generate-a-long-random-string-in-go).
+func RandomString(prefix string, n int) string {
+	const alphanum = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"
+	var bytes = make([]byte, n)
+	rand.Read(bytes)
+	for i, b := range bytes {
+		bytes[i] = alphanum[b%byte(len(alphanum))]
+	}
+	return prefix + string(bytes)
+}
diff --git a/acceptance/tools/tools.go b/acceptance/tools/tools.go
new file mode 100644
index 0000000..ebb660a
--- /dev/null
+++ b/acceptance/tools/tools.go
@@ -0,0 +1,364 @@
+// +build acceptance
+
+package tools
+
+import (
+	"crypto/rand"
+	"fmt"
+	"github.com/rackspace/gophercloud/openstack/compute/servers"
+	"github.com/rackspace/gophercloud/openstack/identity"
+	"github.com/rackspace/gophercloud/openstack/utils"
+	"os"
+	"text/tabwriter"
+	"time"
+)
+
+var errTimeout = fmt.Errorf("Timeout.")
+
+type testState struct {
+	O             identity.AuthOptions
+	A             identity.AuthResults
+	SC            *identity.ServiceCatalog
+	EPs           []identity.Endpoint
+	W             *tabwriter.Writer
+	ImageId       string
+	FlavorId      string
+	Region        string
+	EP            string
+	Client        *servers.Client
+	CreatedServer *servers.Server
+	GottenServer  *servers.Server
+	UpdatedServer *servers.Server
+	ServerName    string
+	AlternateName string
+	FlavorIdResize string
+}
+
+func SetupForList(service string) (*testState, error) {
+	var err error
+
+	ts := new(testState)
+
+	ts.O, err = utils.AuthOptions()
+	if err != nil {
+		return ts, err
+	}
+
+	ts.A, err = identity.Authenticate(ts.O)
+	if err != nil {
+		return ts, err
+	}
+
+	ts.SC, err = identity.GetServiceCatalog(ts.A)
+	if err != nil {
+		return ts, err
+	}
+
+	ts.EPs, err = FindAllEndpoints(ts.SC, service)
+	if err != nil {
+		return ts, err
+	}
+
+	ts.W = new(tabwriter.Writer)
+	ts.W.Init(os.Stdout, 2, 8, 2, ' ', 0)
+
+	return ts, nil
+}
+
+func SetupForCRUD() (*testState, error) {
+	ts, err := SetupForList("compute")
+	if err != nil {
+		return ts, err
+	}
+
+	ts.ImageId = os.Getenv("OS_IMAGE_ID")
+	if ts.ImageId == "" {
+		return ts, fmt.Errorf("Expected OS_IMAGE_ID environment variable to be set")
+	}
+
+	ts.FlavorId = os.Getenv("OS_FLAVOR_ID")
+	if ts.FlavorId == "" {
+		return ts, fmt.Errorf("Expected OS_FLAVOR_ID environment variable to be set")
+	}
+
+	ts.FlavorIdResize = os.Getenv("OS_FLAVOR_ID_RESIZE")
+	if ts.FlavorIdResize == "" {
+		return ts, fmt.Errorf("Expected OS_FLAVOR_ID_RESIZE environment variable to be set")
+	}
+
+	if ts.FlavorIdResize == ts.FlavorId {
+		return ts, fmt.Errorf("OS_FLAVOR_ID and OS_FLAVOR_ID_RESIZE cannot be the same")
+	}
+
+	ts.Region = os.Getenv("OS_REGION_NAME")
+	if ts.Region == "" {
+		ts.Region = ts.EPs[0].Region
+	}
+
+	ts.EP, err = FindEndpointForRegion(ts.EPs, ts.Region)
+	if err != nil {
+		return ts, err
+	}
+
+	return ts, err
+}
+
+func FindAllEndpoints(sc *identity.ServiceCatalog, service string) ([]identity.Endpoint, error) {
+	ces, err := sc.CatalogEntries()
+	if err != nil {
+		return nil, err
+	}
+
+	for _, ce := range ces {
+		if ce.Type == service {
+			return ce.Endpoints, nil
+		}
+	}
+
+	return nil, fmt.Errorf(service + " endpoint not found.")
+}
+
+func FindEndpointForRegion(eps []identity.Endpoint, r string) (string, error) {
+	for _, ep := range eps {
+		if ep.Region == r {
+			return ep.PublicURL, nil
+		}
+	}
+	return "", fmt.Errorf("Unknown region %s", r)
+}
+
+func CountDown(ts *testState, timeout int) (bool, int, error) {
+	if timeout < 1 {
+		return false, 0, errTimeout
+	}
+	time.Sleep(1 * time.Second)
+	timeout--
+
+	gr, err := servers.GetDetail(ts.Client, ts.CreatedServer.Id)
+	if err != nil {
+		return false, timeout, err
+	}
+
+	ts.GottenServer, err = servers.GetServer(gr)
+	if err != nil {
+		return false, timeout, err
+	}
+
+	return true, timeout, nil
+}
+
+func CreateServer(ts *testState) error {
+	ts.ServerName = RandomString("ACPTTEST", 16)
+	fmt.Printf("Attempting to create server: %s\n", ts.ServerName)
+
+	ts.Client = servers.NewClient(ts.EP, ts.A, ts.O)
+
+	cr, err := servers.Create(ts.Client, map[string]interface{}{
+		"flavorRef": ts.FlavorId,
+		"imageRef":  ts.ImageId,
+		"name":      ts.ServerName,
+	})
+	if err != nil {
+		return err
+	}
+
+	ts.CreatedServer, err = servers.GetServer(cr)
+	return err
+}
+
+func WaitForStatus(ts *testState, s string) error {
+	var (
+		inProgress bool
+		timeout    int
+		err        error
+	)
+
+	for inProgress, timeout, err = CountDown(ts, 300); inProgress; inProgress, timeout, err = CountDown(ts, timeout) {
+		if ts.GottenServer.Id != ts.CreatedServer.Id {
+			return fmt.Errorf("created server id (%s) != gotten server id (%s)", ts.CreatedServer.Id, ts.GottenServer.Id)
+		}
+
+		if ts.GottenServer.Status == s {
+			fmt.Printf("Server reached state %s after %d seconds (approximately)\n", s, 300-timeout)
+			break
+		}
+	}
+
+	if err == errTimeout {
+		fmt.Printf("Time out -- I'm not waiting around.\n")
+		err = nil
+	}
+
+	return err
+}
+
+func ChangeServerName(ts *testState) error {
+	var (
+		inProgress bool
+		timeout    int
+	)
+
+	ts.AlternateName = RandomString("ACPTTEST", 16)
+	for ts.AlternateName == ts.ServerName {
+		ts.AlternateName = RandomString("ACPTTEST", 16)
+	}
+	fmt.Println("Attempting to change server name")
+
+	ur, err := servers.Update(ts.Client, ts.CreatedServer.Id, map[string]interface{}{
+		"name": ts.AlternateName,
+	})
+	if err != nil {
+		return err
+	}
+
+	ts.UpdatedServer, err = servers.GetServer(ur)
+	if err != nil {
+		return err
+	}
+
+	if ts.UpdatedServer.Id != ts.CreatedServer.Id {
+		return fmt.Errorf("Expected updated and created server to share the same ID")
+	}
+
+	for inProgress, timeout, err = CountDown(ts, 300); inProgress; inProgress, timeout, err = CountDown(ts, timeout) {
+		if ts.GottenServer.Id != ts.UpdatedServer.Id {
+			return fmt.Errorf("Updated server ID (%s) != gotten server ID (%s)", ts.UpdatedServer.Id, ts.GottenServer.Id)
+		}
+
+		if ts.GottenServer.Name == ts.AlternateName {
+			fmt.Printf("Server updated after %d seconds (approximately)\n", 300-timeout)
+			break
+		}
+	}
+
+	if err == errTimeout {
+		fmt.Printf("I'm not waiting around.\n")
+		err = nil
+	}
+
+	return err
+}
+
+func MakeNewPassword(oldPass string) string {
+	fmt.Println("Current password: "+oldPass)
+	randomPassword := RandomString("", 16)
+	for randomPassword == oldPass {
+		randomPassword = RandomString("", 16)
+	}
+	fmt.Println("    New password: "+randomPassword)
+	return randomPassword
+}
+
+func ChangeAdminPassword(ts *testState) error {
+	randomPassword := MakeNewPassword(ts.CreatedServer.AdminPass)
+	
+	err := servers.ChangeAdminPassword(ts.Client, ts.CreatedServer.Id, randomPassword)
+	if err != nil {
+		return err
+	}
+	
+	err = WaitForStatus(ts, "PASSWORD")
+	if err != nil {
+		return err
+	}
+	
+	return WaitForStatus(ts, "ACTIVE")
+}
+
+func RebootServer(ts *testState) error {
+	fmt.Println("Attempting reboot of server "+ts.CreatedServer.Id)
+	err := servers.Reboot(ts.Client, ts.CreatedServer.Id, servers.OSReboot)
+	if err != nil {
+		return err
+	}
+	
+	err = WaitForStatus(ts, "REBOOT")
+	if err != nil {
+		return err
+	}
+	
+	return WaitForStatus(ts, "ACTIVE")
+}
+
+func RebuildServer(ts *testState) error {
+	fmt.Println("Attempting to rebuild server "+ts.CreatedServer.Id)
+
+	newPassword := MakeNewPassword(ts.CreatedServer.AdminPass)
+	newName := RandomString("ACPTTEST", 16)
+	sr, err := servers.Rebuild(ts.Client, ts.CreatedServer.Id, newName, newPassword, ts.ImageId, nil)
+	if err != nil {
+		return err
+	}
+	
+	s, err := servers.GetServer(sr)
+	if err != nil {
+		return err
+	}
+	if s.Id != ts.CreatedServer.Id {
+		return fmt.Errorf("Expected rebuilt server ID of %s; got %s", ts.CreatedServer.Id, s.Id)
+	}
+
+	err = WaitForStatus(ts, "REBUILD")
+	if err != nil {
+		return err
+	}
+	
+	return WaitForStatus(ts, "ACTIVE")
+}
+
+func ResizeServer(ts *testState) error {
+	fmt.Println("Attempting to resize server "+ts.CreatedServer.Id)
+
+	err := servers.Resize(ts.Client, ts.CreatedServer.Id, ts.FlavorIdResize)
+	if err != nil {
+		return err
+	}
+
+	err = WaitForStatus(ts, "RESIZE")
+	if err != nil {
+		return err
+	}
+
+	return WaitForStatus(ts, "VERIFY_RESIZE")
+}
+
+func ConfirmResize(ts *testState) error {
+	fmt.Println("Attempting to confirm resize for server "+ts.CreatedServer.Id)
+	
+	err := servers.ConfirmResize(ts.Client, ts.CreatedServer.Id)
+	if err != nil {
+		return err
+	}
+	
+	return WaitForStatus(ts, "ACTIVE")
+}
+
+func RevertResize(ts *testState) error {
+	fmt.Println("Attempting to revert resize for server "+ts.CreatedServer.Id)
+	
+	err := servers.RevertResize(ts.Client, ts.CreatedServer.Id)
+	if err != nil {
+		return err
+	}
+
+	err = WaitForStatus(ts, "REVERT_RESIZE")
+	if err != nil {
+		return err
+	}
+
+	return WaitForStatus(ts, "ACTIVE")
+}
+
+// randomString generates a string of given length, but random content.
+// All content will be within the ASCII graphic character set.
+// (Implementation from Even Shaw's contribution on
+// http://stackoverflow.com/questions/12771930/what-is-the-fastest-way-to-generate-a-long-random-string-in-go).
+func RandomString(prefix string, n int) string {
+	const alphanum = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"
+	var bytes = make([]byte, n)
+	rand.Read(bytes)
+	for i, b := range bytes {
+		bytes[i] = alphanum[b%byte(len(alphanum))]
+	}
+	return prefix + string(bytes)
+}
