jcapik pushed to kubernetes (f21). "Bump to upstream 68298f08a4980f95dfbf7b9f58bfec1808fb2670"

notifications at fedoraproject.org notifications at fedoraproject.org
Wed Jun 10 14:48:40 UTC 2015


From f0566ef5c85dc66755370041053f4d203a01074b Mon Sep 17 00:00:00 2001
From: Eric Paris <eparis at redhat.com>
Date: Fri, 9 Jan 2015 12:46:53 -0500
Subject: Bump to upstream 68298f08a4980f95dfbf7b9f58bfec1808fb2670


diff --git a/.gitignore b/.gitignore
index def3adf..f828fe7 100644
--- a/.gitignore
+++ b/.gitignore
@@ -29,3 +29,4 @@
 /kubernetes-993ef88.tar.gz
 /kubernetes-5ef34bf.tar.gz
 /kubernetes-52e165a.tar.gz
+/kubernetes-68298f0.tar.gz
diff --git a/0001-remove-all-third-party-software.patch b/0001-remove-all-third-party-software.patch
index afb02ab..5bd73ad 100644
--- a/0001-remove-all-third-party-software.patch
+++ b/0001-remove-all-third-party-software.patch
@@ -1,10 +1,10 @@
-From 4b46f840338013715d09dec378bcd2fbd62fa87d Mon Sep 17 00:00:00 2001
+From 8ffddead8da8731a3c8c7e89946702c6902f7689 Mon Sep 17 00:00:00 2001
 From: Eric Paris <eparis at redhat.com>
-Date: Thu, 21 Aug 2014 13:55:27 -0400
+Date: Fri, 9 Jan 2015 12:09:22 -0500
 Subject: [PATCH] remove all third party software
 
 ---
- Godeps/Godeps.json                                 |   166 -
+ Godeps/Godeps.json                                 |   217 -
  Godeps/Readme                                      |     5 -
  Godeps/_workspace/.gitignore                       |     2 -
  .../_workspace/src/code.google.com/p/gcfg/LICENSE  |    57 -
@@ -75,6 +75,40 @@ Subject: [PATCH] remove all third party software
  .../googleapi/transport/apikey.go                  |    38 -
  .../p/google-api-go-client/googleapi/types.go      |   150 -
  .../p/google-api-go-client/googleapi/types_test.go |    44 -
+ .../src/github.com/Sirupsen/logrus/.gitignore      |     1 -
+ .../src/github.com/Sirupsen/logrus/.travis.yml     |    10 -
+ .../src/github.com/Sirupsen/logrus/LICENSE         |    21 -
+ .../src/github.com/Sirupsen/logrus/README.md       |   352 -
+ .../src/github.com/Sirupsen/logrus/entry.go        |   248 -
+ .../src/github.com/Sirupsen/logrus/entry_test.go   |    53 -
+ .../Sirupsen/logrus/examples/basic/basic.go        |    40 -
+ .../Sirupsen/logrus/examples/hook/hook.go          |    35 -
+ .../src/github.com/Sirupsen/logrus/exported.go     |   182 -
+ .../src/github.com/Sirupsen/logrus/formatter.go    |    44 -
+ .../Sirupsen/logrus/formatter_bench_test.go        |    88 -
+ .../src/github.com/Sirupsen/logrus/hook_test.go    |   122 -
+ .../src/github.com/Sirupsen/logrus/hooks.go        |    34 -
+ .../Sirupsen/logrus/hooks/airbrake/airbrake.go     |    54 -
+ .../Sirupsen/logrus/hooks/papertrail/README.md     |    28 -
+ .../Sirupsen/logrus/hooks/papertrail/papertrail.go |    54 -
+ .../logrus/hooks/papertrail/papertrail_test.go     |    26 -
+ .../Sirupsen/logrus/hooks/sentry/README.md         |    61 -
+ .../Sirupsen/logrus/hooks/sentry/sentry.go         |   100 -
+ .../Sirupsen/logrus/hooks/sentry/sentry_test.go    |    97 -
+ .../Sirupsen/logrus/hooks/syslog/README.md         |    20 -
+ .../Sirupsen/logrus/hooks/syslog/syslog.go         |    59 -
+ .../Sirupsen/logrus/hooks/syslog/syslog_test.go    |    26 -
+ .../github.com/Sirupsen/logrus/json_formatter.go   |    26 -
+ .../src/github.com/Sirupsen/logrus/logger.go       |   161 -
+ .../src/github.com/Sirupsen/logrus/logrus.go       |    94 -
+ .../src/github.com/Sirupsen/logrus/logrus_test.go  |   283 -
+ .../github.com/Sirupsen/logrus/terminal_darwin.go  |    12 -
+ .../github.com/Sirupsen/logrus/terminal_freebsd.go |    20 -
+ .../github.com/Sirupsen/logrus/terminal_linux.go   |    12 -
+ .../Sirupsen/logrus/terminal_notwindows.go         |    21 -
+ .../github.com/Sirupsen/logrus/terminal_windows.go |    27 -
+ .../github.com/Sirupsen/logrus/text_formatter.go   |   124 -
+ .../Sirupsen/logrus/text_formatter_test.go         |    33 -
  .../github.com/coreos/go-etcd/etcd/add_child.go    |    23 -
  .../coreos/go-etcd/etcd/add_child_test.go          |    73 -
  .../src/github.com/coreos/go-etcd/etcd/client.go   |   435 -
@@ -115,6 +149,82 @@ Subject: [PATCH] remove all third party software
  .../src/github.com/davecgh/go-spew/spew/spew.go    |   148 -
  .../github.com/davecgh/go-spew/spew/spew_test.go   |   308 -
  .../davecgh/go-spew/spew/testdata/dumpcgo.go       |    82 -
+ .../docker/docker/pkg/archive/MAINTAINERS          |     2 -
+ .../github.com/docker/docker/pkg/archive/README.md |     1 -
+ .../docker/docker/pkg/archive/archive.go           |   802 -
+ .../docker/docker/pkg/archive/archive_test.go      |   625 -
+ .../docker/docker/pkg/archive/archive_unix.go      |    39 -
+ .../docker/docker/pkg/archive/archive_windows.go   |    12 -
+ .../docker/docker/pkg/archive/changes.go           |   413 -
+ .../docker/docker/pkg/archive/changes_test.go      |   301 -
+ .../github.com/docker/docker/pkg/archive/diff.go   |   165 -
+ .../docker/docker/pkg/archive/diff_test.go         |   191 -
+ .../docker/docker/pkg/archive/example_changes.go   |    97 -
+ .../docker/docker/pkg/archive/testdata/broken.tar  |   Bin 13824 -> 0 bytes
+ .../docker/docker/pkg/archive/time_linux.go        |    16 -
+ .../docker/docker/pkg/archive/time_unsupported.go  |    16 -
+ .../docker/docker/pkg/archive/utils_test.go        |   166 -
+ .../github.com/docker/docker/pkg/archive/wrap.go   |    59 -
+ .../docker/docker/pkg/fileutils/fileutils.go       |    26 -
+ .../docker/docker/pkg/ioutils/readers.go           |   114 -
+ .../docker/docker/pkg/ioutils/readers_test.go      |    34 -
+ .../docker/docker/pkg/ioutils/writers.go           |    39 -
+ .../github.com/docker/docker/pkg/pools/pools.go    |   111 -
+ .../docker/docker/pkg/pools/pools_nopool.go        |    73 -
+ .../docker/docker/pkg/promise/promise.go           |    11 -
+ .../docker/docker/pkg/system/MAINTAINERS           |     2 -
+ .../github.com/docker/docker/pkg/system/errors.go  |     9 -
+ .../github.com/docker/docker/pkg/system/lstat.go   |    16 -
+ .../docker/docker/pkg/system/lstat_test.go         |    27 -
+ .../docker/docker/pkg/system/lstat_windows.go      |     8 -
+ .../github.com/docker/docker/pkg/system/meminfo.go |    17 -
+ .../docker/docker/pkg/system/meminfo_linux.go      |    67 -
+ .../docker/docker/pkg/system/meminfo_linux_test.go |    37 -
+ .../docker/pkg/system/meminfo_unsupported.go       |     7 -
+ .../github.com/docker/docker/pkg/system/mknod.go   |    18 -
+ .../docker/docker/pkg/system/mknod_windows.go      |    12 -
+ .../github.com/docker/docker/pkg/system/stat.go    |    42 -
+ .../docker/docker/pkg/system/stat_linux.go         |    14 -
+ .../docker/docker/pkg/system/stat_test.go          |    36 -
+ .../docker/docker/pkg/system/stat_unsupported.go   |    16 -
+ .../docker/docker/pkg/system/stat_windows.go       |    12 -
+ .../github.com/docker/docker/pkg/system/umask.go   |    11 -
+ .../docker/docker/pkg/system/umask_windows.go      |     8 -
+ .../docker/docker/pkg/system/utimes_darwin.go      |    11 -
+ .../docker/docker/pkg/system/utimes_freebsd.go     |    24 -
+ .../docker/docker/pkg/system/utimes_linux.go       |    28 -
+ .../docker/docker/pkg/system/utimes_test.go        |    65 -
+ .../docker/docker/pkg/system/utimes_unsupported.go |    13 -
+ .../docker/docker/pkg/system/xattrs_linux.go       |    59 -
+ .../docker/docker/pkg/system/xattrs_unsupported.go |    11 -
+ .../github.com/docker/docker/pkg/units/MAINTAINERS |     2 -
+ .../github.com/docker/docker/pkg/units/duration.go |    31 -
+ .../docker/docker/pkg/units/duration_test.go       |    46 -
+ .../src/github.com/docker/docker/pkg/units/size.go |    91 -
+ .../docker/docker/pkg/units/size_test.go           |   108 -
+ .../p/go/src/pkg/archive/tar/common.go             |   305 -
+ .../p/go/src/pkg/archive/tar/example_test.go       |    79 -
+ .../p/go/src/pkg/archive/tar/reader.go             |   820 -
+ .../p/go/src/pkg/archive/tar/reader_test.go        |   743 -
+ .../p/go/src/pkg/archive/tar/stat_atim.go          |    20 -
+ .../p/go/src/pkg/archive/tar/stat_atimespec.go     |    20 -
+ .../p/go/src/pkg/archive/tar/stat_unix.go          |    32 -
+ .../p/go/src/pkg/archive/tar/tar_test.go           |   284 -
+ .../p/go/src/pkg/archive/tar/testdata/gnu.tar      |   Bin 3072 -> 0 bytes
+ .../p/go/src/pkg/archive/tar/testdata/nil-uid.tar  |   Bin 1024 -> 0 bytes
+ .../p/go/src/pkg/archive/tar/testdata/pax.tar      |   Bin 10240 -> 0 bytes
+ .../p/go/src/pkg/archive/tar/testdata/small.txt    |     1 -
+ .../p/go/src/pkg/archive/tar/testdata/small2.txt   |     1 -
+ .../pkg/archive/tar/testdata/sparse-formats.tar    |   Bin 17920 -> 0 bytes
+ .../p/go/src/pkg/archive/tar/testdata/star.tar     |   Bin 3072 -> 0 bytes
+ .../p/go/src/pkg/archive/tar/testdata/ustar.tar    |   Bin 2048 -> 0 bytes
+ .../p/go/src/pkg/archive/tar/testdata/v7.tar       |   Bin 3584 -> 0 bytes
+ .../pkg/archive/tar/testdata/writer-big-long.tar   |   Bin 4096 -> 0 bytes
+ .../go/src/pkg/archive/tar/testdata/writer-big.tar |   Bin 4096 -> 0 bytes
+ .../p/go/src/pkg/archive/tar/testdata/writer.tar   |   Bin 3584 -> 0 bytes
+ .../p/go/src/pkg/archive/tar/testdata/xattrs.tar   |   Bin 5120 -> 0 bytes
+ .../p/go/src/pkg/archive/tar/writer.go             |   396 -
+ .../p/go/src/pkg/archive/tar/writer_test.go        |   491 -
  .../github.com/elazarl/go-bindata-assetfs/LICENSE  |    23 -
  .../elazarl/go-bindata-assetfs/README.md           |    18 -
  .../elazarl/go-bindata-assetfs/assetfs.go          |   141 -
@@ -203,35 +313,47 @@ Subject: [PATCH] remove all third party software
  .../emicklei/go-restful/web_service_container.go   |    39 -
  .../emicklei/go-restful/web_service_test.go        |   115 -
  .../github.com/fsouza/go-dockerclient/.travis.yml  |    13 -
- .../src/github.com/fsouza/go-dockerclient/AUTHORS  |    44 -
+ .../src/github.com/fsouza/go-dockerclient/AUTHORS  |    50 -
  .../fsouza/go-dockerclient/DOCKER-LICENSE          |     6 -
  .../src/github.com/fsouza/go-dockerclient/LICENSE  |    22 -
  .../fsouza/go-dockerclient/README.markdown         |    42 -
- .../github.com/fsouza/go-dockerclient/change.go    |    36 -
+ .../fsouza/go-dockerclient/build_test.go           |   144 -
+ .../github.com/fsouza/go-dockerclient/change.go    |    43 -
  .../fsouza/go-dockerclient/change_test.go          |    26 -
- .../github.com/fsouza/go-dockerclient/client.go    |   546 -
- .../fsouza/go-dockerclient/client_test.go          |   290 -
- .../github.com/fsouza/go-dockerclient/container.go |   731 -
- .../fsouza/go-dockerclient/container_test.go       |  1495 --
+ .../github.com/fsouza/go-dockerclient/client.go    |   636 -
+ .../fsouza/go-dockerclient/client_test.go          |   368 -
+ .../github.com/fsouza/go-dockerclient/container.go |   760 -
+ .../fsouza/go-dockerclient/container_test.go       |  1524 --
  .../src/github.com/fsouza/go-dockerclient/env.go   |   168 -
  .../github.com/fsouza/go-dockerclient/env_test.go  |   349 -
- .../src/github.com/fsouza/go-dockerclient/event.go |   278 -
- .../fsouza/go-dockerclient/event_test.go           |    93 -
+ .../src/github.com/fsouza/go-dockerclient/event.go |   309 -
+ .../fsouza/go-dockerclient/event_test.go           |   129 -
  .../fsouza/go-dockerclient/example_test.go         |   168 -
- .../src/github.com/fsouza/go-dockerclient/exec.go  |   126 -
+ .../src/github.com/fsouza/go-dockerclient/exec.go  |   129 -
  .../github.com/fsouza/go-dockerclient/exec_test.go |   128 -
- .../src/github.com/fsouza/go-dockerclient/image.go |   417 -
- .../fsouza/go-dockerclient/image_test.go           |   861 -
+ .../src/github.com/fsouza/go-dockerclient/image.go |   458 -
+ .../fsouza/go-dockerclient/image_test.go           |   878 -
  .../src/github.com/fsouza/go-dockerclient/misc.go  |    59 -
  .../github.com/fsouza/go-dockerclient/misc_test.go |   159 -
  .../github.com/fsouza/go-dockerclient/signal.go    |    49 -
  .../github.com/fsouza/go-dockerclient/stdcopy.go   |    91 -
  .../fsouza/go-dockerclient/stdcopy_test.go         |   255 -
+ .../src/github.com/fsouza/go-dockerclient/tar.go   |    99 -
+ .../fsouza/go-dockerclient/testing/bin/fmtpolice   |    38 -
+ .../go-dockerclient/testing/data/.dockerignore     |     3 -
  .../fsouza/go-dockerclient/testing/data/Dockerfile |    15 -
+ .../fsouza/go-dockerclient/testing/data/barfile    |     0
+ .../fsouza/go-dockerclient/testing/data/ca.pem     |    18 -
+ .../fsouza/go-dockerclient/testing/data/cert.pem   |    18 -
  .../go-dockerclient/testing/data/container.tar     |   Bin 2048 -> 0 bytes
  .../go-dockerclient/testing/data/dockerfile.tar    |   Bin 2560 -> 0 bytes
- .../fsouza/go-dockerclient/testing/server.go       |   692 -
- .../fsouza/go-dockerclient/testing/server_test.go  |  1017 --
+ .../fsouza/go-dockerclient/testing/data/foofile    |     0
+ .../fsouza/go-dockerclient/testing/data/key.pem    |    27 -
+ .../fsouza/go-dockerclient/testing/data/server.pem |    18 -
+ .../go-dockerclient/testing/data/serverkey.pem     |    27 -
+ .../fsouza/go-dockerclient/testing/data/symlink    |     1 -
+ .../fsouza/go-dockerclient/testing/server.go       |   744 -
+ .../fsouza/go-dockerclient/testing/server_test.go  |  1091 --
  .../fsouza/go-dockerclient/testing/writer.go       |    43 -
  .../src/github.com/ghodss/yaml/.gitignore          |    20 -
  .../_workspace/src/github.com/ghodss/yaml/LICENSE  |    50 -
@@ -260,18 +382,69 @@ Subject: [PATCH] remove all third party software
  .../src/github.com/google/gofuzz/example_test.go   |   225 -
  .../src/github.com/google/gofuzz/fuzz.go           |   366 -
  .../src/github.com/google/gofuzz/fuzz_test.go      |   258 -
- Godeps/_workspace/src/github.com/kr/text/License   |    19 -
- Godeps/_workspace/src/github.com/kr/text/Readme    |     3 -
- .../src/github.com/kr/text/colwriter/Readme        |     5 -
- .../src/github.com/kr/text/colwriter/column.go     |   147 -
- .../github.com/kr/text/colwriter/column_test.go    |    90 -
- Godeps/_workspace/src/github.com/kr/text/doc.go    |     3 -
- Godeps/_workspace/src/github.com/kr/text/indent.go |    74 -
- .../src/github.com/kr/text/indent_test.go          |   119 -
- Godeps/_workspace/src/github.com/kr/text/mc/Readme |     9 -
- Godeps/_workspace/src/github.com/kr/text/mc/mc.go  |    62 -
- Godeps/_workspace/src/github.com/kr/text/wrap.go   |    86 -
- .../_workspace/src/github.com/kr/text/wrap_test.go |    44 -
+ .../src/github.com/imdario/mergo/.travis.yml       |     2 -
+ .../src/github.com/imdario/mergo/LICENSE           |    28 -
+ .../src/github.com/imdario/mergo/README.md         |    68 -
+ .../_workspace/src/github.com/imdario/mergo/doc.go |    44 -
+ .../_workspace/src/github.com/imdario/mergo/map.go |   146 -
+ .../src/github.com/imdario/mergo/merge.go          |    99 -
+ .../src/github.com/imdario/mergo/mergo.go          |    90 -
+ .../src/github.com/imdario/mergo/mergo_test.go     |   288 -
+ .../github.com/imdario/mergo/testdata/license.yml  |     3 -
+ .../github.com/imdario/mergo/testdata/thing.yml    |     5 -
+ .../_workspace/src/github.com/miekg/dns/.gitignore |     4 -
+ .../src/github.com/miekg/dns/.travis.yml           |    21 -
+ Godeps/_workspace/src/github.com/miekg/dns/AUTHORS |     1 -
+ .../src/github.com/miekg/dns/CONTRIBUTORS          |     9 -
+ .../_workspace/src/github.com/miekg/dns/COPYRIGHT  |     9 -
+ Godeps/_workspace/src/github.com/miekg/dns/LICENSE |    32 -
+ .../_workspace/src/github.com/miekg/dns/README.md  |   140 -
+ .../_workspace/src/github.com/miekg/dns/client.go  |   319 -
+ .../src/github.com/miekg/dns/client_test.go        |   195 -
+ .../src/github.com/miekg/dns/clientconfig.go       |    94 -
+ .../src/github.com/miekg/dns/defaults.go           |   242 -
+ Godeps/_workspace/src/github.com/miekg/dns/dns.go  |   193 -
+ .../src/github.com/miekg/dns/dns_test.go           |   511 -
+ .../_workspace/src/github.com/miekg/dns/dnssec.go  |   756 -
+ .../src/github.com/miekg/dns/dnssec_test.go        |   672 -
+ .../src/github.com/miekg/dns/dyn_test.go           |     3 -
+ Godeps/_workspace/src/github.com/miekg/dns/edns.go |   501 -
+ .../src/github.com/miekg/dns/edns_test.go          |    48 -
+ .../src/github.com/miekg/dns/example_test.go       |   147 -
+ .../src/github.com/miekg/dns/idn/example_test.go   |    18 -
+ .../src/github.com/miekg/dns/idn/punycode.go       |   268 -
+ .../src/github.com/miekg/dns/idn/punycode_test.go  |    94 -
+ .../_workspace/src/github.com/miekg/dns/keygen.go  |   157 -
+ .../_workspace/src/github.com/miekg/dns/kscan.go   |   244 -
+ .../_workspace/src/github.com/miekg/dns/labels.go  |   162 -
+ .../src/github.com/miekg/dns/labels_test.go        |   214 -
+ Godeps/_workspace/src/github.com/miekg/dns/msg.go  |  1899 ---
+ .../_workspace/src/github.com/miekg/dns/nsecx.go   |   110 -
+ .../src/github.com/miekg/dns/nsecx_test.go         |    33 -
+ .../src/github.com/miekg/dns/parse_test.go         |  1276 --
+ .../src/github.com/miekg/dns/privaterr.go          |   122 -
+ .../src/github.com/miekg/dns/privaterr_test.go     |   169 -
+ .../_workspace/src/github.com/miekg/dns/rawmsg.go  |    95 -
+ .../_workspace/src/github.com/miekg/dns/scanner.go |    43 -
+ .../_workspace/src/github.com/miekg/dns/server.go  |   626 -
+ .../src/github.com/miekg/dns/server_test.go        |   401 -
+ Godeps/_workspace/src/github.com/miekg/dns/sig0.go |   262 -
+ .../src/github.com/miekg/dns/sig0_test.go          |    96 -
+ .../src/github.com/miekg/dns/singleinflight.go     |    57 -
+ Godeps/_workspace/src/github.com/miekg/dns/tlsa.go |    84 -
+ Godeps/_workspace/src/github.com/miekg/dns/tsig.go |   378 -
+ .../_workspace/src/github.com/miekg/dns/types.go   |  1697 --
+ .../src/github.com/miekg/dns/types_test.go         |    42 -
+ Godeps/_workspace/src/github.com/miekg/dns/udp.go  |    55 -
+ .../src/github.com/miekg/dns/udp_linux.go          |    63 -
+ .../src/github.com/miekg/dns/udp_other.go          |    17 -
+ .../src/github.com/miekg/dns/udp_windows.go        |    34 -
+ .../_workspace/src/github.com/miekg/dns/update.go  |   138 -
+ .../src/github.com/miekg/dns/update_test.go        |   105 -
+ Godeps/_workspace/src/github.com/miekg/dns/xfr.go  |   236 -
+ .../src/github.com/miekg/dns/zgenerate.go          |   157 -
+ .../_workspace/src/github.com/miekg/dns/zscan.go   |   956 --
+ .../src/github.com/miekg/dns/zscan_rr.go           |  2155 ---
  .../src/github.com/mitchellh/goamz/aws/attempt.go  |    74 -
  .../github.com/mitchellh/goamz/aws/attempt_test.go |    57 -
  .../src/github.com/mitchellh/goamz/aws/aws.go      |   423 -
@@ -303,71 +476,430 @@ Subject: [PATCH] remove all third party software
  .../src/github.com/racker/perigee/README.md        |   120 -
  .../src/github.com/racker/perigee/api.go           |   269 -
  .../src/github.com/racker/perigee/api_test.go      |   226 -
- .../github.com/rackspace/gophercloud/.editorconfig |    16 -
  .../github.com/rackspace/gophercloud/.travis.yml   |    14 -
- .../rackspace/gophercloud/CONTRIBUTORS.md          |     6 -
+ .../rackspace/gophercloud/CONTRIBUTING.md          |   275 -
+ .../rackspace/gophercloud/CONTRIBUTORS.md          |    12 -
  .../src/github.com/rackspace/gophercloud/LICENSE   |   191 -
- .../rackspace/gophercloud/README.asciidoc          |    44 -
- .../gophercloud/acceptance/00-authentication.go    |    30 -
- .../gophercloud/acceptance/01-authentication.go    |    22 -
- .../gophercloud/acceptance/02-list-servers.go      |    62 -
- .../acceptance/03-get-server-details.go            |   134 -
- .../gophercloud/acceptance/04-create-server.go     |    47 -
- .../gophercloud/acceptance/05-list-images.go       |    32 -
- .../gophercloud/acceptance/06-list-flavors.go      |    32 -
- .../acceptance/07-change-admin-password.go         |    49 -
- .../gophercloud/acceptance/08-reauthentication.go  |    50 -
- .../gophercloud/acceptance/09-resize-server.go     |   102 -
- .../gophercloud/acceptance/10-reboot-server.go     |    45 -
- .../acceptance/11-rescue-unrescue-server.go        |    52 -
- .../gophercloud/acceptance/12-update-server.go     |    46 -
- .../gophercloud/acceptance/13-rebuild-server.go    |    46 -
- .../gophercloud/acceptance/14-list-addresses.go    |    66 -
- .../gophercloud/acceptance/15-list-keypairs.go     |    32 -
- .../acceptance/16-create-delete-keypair.go         |    45 -
- .../acceptance/17-create-delete-image.go           |    52 -
- .../acceptance/18-osutil-authentication.go         |    19 -
- .../acceptance/19-list-addresses-0.1.go            |    58 -
- .../gophercloud/acceptance/99-delete-server.go     |    48 -
- .../rackspace/gophercloud/acceptance/libargs.go    |   239 -
- .../github.com/rackspace/gophercloud/api_fetch.go  |    49 -
- .../rackspace/gophercloud/authenticate.go          |   257 -
- .../rackspace/gophercloud/authenticate_test.go     |   264 -
- .../rackspace/gophercloud/common_types.go          |    24 -
- .../github.com/rackspace/gophercloud/context.go    |   150 -
- .../rackspace/gophercloud/context_test.go          |    28 -
- .../src/github.com/rackspace/gophercloud/errors.go |    39 -
- .../github.com/rackspace/gophercloud/flavors.go    |    55 -
- .../rackspace/gophercloud/floating_ips.go          |    88 -
- .../rackspace/gophercloud/global_context.go        |    67 -
- .../src/github.com/rackspace/gophercloud/images.go |   106 -
- .../github.com/rackspace/gophercloud/interfaces.go |   247 -
- .../github.com/rackspace/gophercloud/keypairs.go   |    98 -
- .../rackspace/gophercloud/osutil/auth.go           |    64 -
- .../rackspace/gophercloud/osutil/region.go         |     9 -
- .../github.com/rackspace/gophercloud/package.go    |     7 -
- .../src/github.com/rackspace/gophercloud/reauth.go |    36 -
- .../rackspace/gophercloud/reauth_test.go           |   133 -
- .../gophercloud/scripts/create-environment.sh      |    26 -
- .../rackspace/gophercloud/scripts/test-all.sh      |    37 -
- .../github.com/rackspace/gophercloud/servers.go    |   807 -
- .../rackspace/gophercloud/servers_test.go          |    54 -
- .../rackspace/gophercloud/service_catalog.go       |    75 -
- .../rackspace/gophercloud/service_catalog_test.go  |   190 -
- .../rackspace/gophercloud/transport_double_test.go |   103 -
+ .../src/github.com/rackspace/gophercloud/README.md |   161 -
+ .../github.com/rackspace/gophercloud/UPGRADING.md  |   338 -
+ .../rackspace/gophercloud/acceptance/README.md     |    57 -
+ .../openstack/blockstorage/v1/snapshots_test.go    |    70 -
+ .../openstack/blockstorage/v1/volumes_test.go      |    63 -
+ .../openstack/blockstorage/v1/volumetypes_test.go  |    49 -
+ .../acceptance/openstack/client_test.go            |    40 -
+ .../openstack/compute/v2/bootfromvolume_test.go    |    50 -
+ .../openstack/compute/v2/compute_test.go           |    97 -
+ .../openstack/compute/v2/extension_test.go         |    47 -
+ .../openstack/compute/v2/flavors_test.go           |    57 -
+ .../acceptance/openstack/compute/v2/images_test.go |    37 -
+ .../acceptance/openstack/compute/v2/pkg.go         |     3 -
+ .../openstack/compute/v2/servers_test.go           |   393 -
+ .../openstack/identity/v2/extension_test.go        |    46 -
+ .../openstack/identity/v2/identity_test.go         |    47 -
+ .../acceptance/openstack/identity/v2/pkg.go        |     1 -
+ .../openstack/identity/v2/tenant_test.go           |    32 -
+ .../acceptance/openstack/identity/v2/token_test.go |    38 -
+ .../openstack/identity/v3/endpoint_test.go         |   111 -
+ .../openstack/identity/v3/identity_test.go         |    39 -
+ .../acceptance/openstack/identity/v3/pkg.go        |     1 -
+ .../openstack/identity/v3/service_test.go          |    36 -
+ .../acceptance/openstack/identity/v3/token_test.go |    42 -
+ .../openstack/networking/v2/apiversion_test.go     |    51 -
+ .../acceptance/openstack/networking/v2/common.go   |    39 -
+ .../openstack/networking/v2/extension_test.go      |    45 -
+ .../networking/v2/extensions/layer3_test.go        |   300 -
+ .../networking/v2/extensions/lbaas/common.go       |    78 -
+ .../networking/v2/extensions/lbaas/member_test.go  |    95 -
+ .../networking/v2/extensions/lbaas/monitor_test.go |    77 -
+ .../networking/v2/extensions/lbaas/pkg.go          |     1 -
+ .../networking/v2/extensions/lbaas/pool_test.go    |    98 -
+ .../networking/v2/extensions/lbaas/vip_test.go     |   101 -
+ .../openstack/networking/v2/extensions/pkg.go      |     1 -
+ .../networking/v2/extensions/provider_test.go      |    68 -
+ .../networking/v2/extensions/security_test.go      |   171 -
+ .../openstack/networking/v2/network_test.go        |    68 -
+ .../acceptance/openstack/networking/v2/pkg.go      |     1 -
+ .../openstack/networking/v2/port_test.go           |   117 -
+ .../openstack/networking/v2/subnet_test.go         |    86 -
+ .../openstack/objectstorage/v1/accounts_test.go    |    44 -
+ .../openstack/objectstorage/v1/common.go           |    28 -
+ .../openstack/objectstorage/v1/containers_test.go  |    89 -
+ .../openstack/objectstorage/v1/objects_test.go     |   119 -
+ .../gophercloud/acceptance/openstack/pkg.go        |     4 -
+ .../acceptance/rackspace/blockstorage/v1/common.go |    38 -
+ .../rackspace/blockstorage/v1/snapshot_test.go     |    82 -
+ .../rackspace/blockstorage/v1/volume_test.go       |    71 -
+ .../rackspace/blockstorage/v1/volume_type_test.go  |    46 -
+ .../acceptance/rackspace/client_test.go            |    28 -
+ .../rackspace/compute/v2/bootfromvolume_test.go    |    46 -
+ .../rackspace/compute/v2/compute_test.go           |    60 -
+ .../rackspace/compute/v2/flavors_test.go           |    61 -
+ .../acceptance/rackspace/compute/v2/images_test.go |    63 -
+ .../rackspace/compute/v2/keypairs_test.go          |    87 -
+ .../rackspace/compute/v2/networks_test.go          |    53 -
+ .../acceptance/rackspace/compute/v2/pkg.go         |     1 -
+ .../rackspace/compute/v2/servers_test.go           |   199 -
+ .../rackspace/compute/v2/virtualinterfaces_test.go |    53 -
+ .../rackspace/identity/v2/extension_test.go        |    54 -
+ .../rackspace/identity/v2/identity_test.go         |    50 -
+ .../rackspace/identity/v2/tenant_test.go           |    37 -
+ .../rackspace/objectstorage/v1/accounts_test.go    |    33 -
+ .../rackspace/objectstorage/v1/bulk_test.go        |    23 -
+ .../objectstorage/v1/cdncontainers_test.go         |    61 -
+ .../rackspace/objectstorage/v1/cdnobjects_test.go  |    46 -
+ .../rackspace/objectstorage/v1/common.go           |    54 -
+ .../rackspace/objectstorage/v1/containers_test.go  |    85 -
+ .../rackspace/objectstorage/v1/objects_test.go     |   112 -
+ .../gophercloud/acceptance/rackspace/pkg.go        |     1 -
+ .../rackspace/gophercloud/acceptance/tools/pkg.go  |     1 -
+ .../gophercloud/acceptance/tools/tools.go          |    82 -
+ .../rackspace/gophercloud/auth_options.go          |    38 -
+ .../rackspace/gophercloud/auth_results.go          |    15 -
+ .../rackspace/gophercloud/endpoint_search.go       |    65 -
+ .../rackspace/gophercloud/endpoint_search_test.go  |    19 -
+ .../rackspace/gophercloud/openstack/auth_env.go    |    58 -
+ .../openstack/blockstorage/v1/apiversions/doc.go   |     3 -
+ .../blockstorage/v1/apiversions/requests.go        |    28 -
+ .../blockstorage/v1/apiversions/requests_test.go   |   145 -
+ .../blockstorage/v1/apiversions/results.go         |    58 -
+ .../openstack/blockstorage/v1/apiversions/urls.go  |    15 -
+ .../blockstorage/v1/apiversions/urls_test.go       |    26 -
+ .../openstack/blockstorage/v1/snapshots/doc.go     |     5 -
+ .../blockstorage/v1/snapshots/fixtures.go          |   114 -
+ .../blockstorage/v1/snapshots/requests.go          |   188 -
+ .../blockstorage/v1/snapshots/requests_test.go     |   104 -
+ .../openstack/blockstorage/v1/snapshots/results.go |   123 -
+ .../openstack/blockstorage/v1/snapshots/urls.go    |    27 -
+ .../blockstorage/v1/snapshots/urls_test.go         |    50 -
+ .../openstack/blockstorage/v1/snapshots/util.go    |    22 -
+ .../blockstorage/v1/snapshots/util_test.go         |    38 -
+ .../openstack/blockstorage/v1/volumes/doc.go       |     5 -
+ .../openstack/blockstorage/v1/volumes/fixtures.go  |   105 -
+ .../openstack/blockstorage/v1/volumes/requests.go  |   217 -
+ .../blockstorage/v1/volumes/requests_test.go       |    95 -
+ .../openstack/blockstorage/v1/volumes/results.go   |   113 -
+ .../openstack/blockstorage/v1/volumes/urls.go      |    23 -
+ .../openstack/blockstorage/v1/volumes/urls_test.go |    44 -
+ .../openstack/blockstorage/v1/volumes/util.go      |    22 -
+ .../openstack/blockstorage/v1/volumes/util_test.go |    38 -
+ .../openstack/blockstorage/v1/volumetypes/doc.go   |     9 -
+ .../blockstorage/v1/volumetypes/fixtures.go        |    60 -
+ .../blockstorage/v1/volumetypes/requests.go        |    87 -
+ .../blockstorage/v1/volumetypes/requests_test.go   |   118 -
+ .../blockstorage/v1/volumetypes/results.go         |    72 -
+ .../openstack/blockstorage/v1/volumetypes/urls.go  |    19 -
+ .../blockstorage/v1/volumetypes/urls_test.go       |    38 -
+ .../rackspace/gophercloud/openstack/client.go      |   205 -
+ .../rackspace/gophercloud/openstack/client_test.go |   161 -
+ .../gophercloud/openstack/common/README.md         |     3 -
+ .../gophercloud/openstack/common/extensions/doc.go |    15 -
+ .../openstack/common/extensions/errors.go          |     1 -
+ .../openstack/common/extensions/fixtures.go        |    91 -
+ .../openstack/common/extensions/requests.go        |    26 -
+ .../openstack/common/extensions/requests_test.go   |    38 -
+ .../openstack/common/extensions/results.go         |    65 -
+ .../openstack/common/extensions/urls.go            |    13 -
+ .../openstack/common/extensions/urls_test.go       |    26 -
+ .../v2/extensions/bootfromvolume/requests.go       |   111 -
+ .../v2/extensions/bootfromvolume/requests_test.go  |    51 -
+ .../v2/extensions/bootfromvolume/results.go        |    10 -
+ .../compute/v2/extensions/bootfromvolume/urls.go   |     7 -
+ .../v2/extensions/bootfromvolume/urls_test.go      |    16 -
+ .../openstack/compute/v2/extensions/delegate.go    |    23 -
+ .../compute/v2/extensions/delegate_test.go         |    96 -
+ .../compute/v2/extensions/diskconfig/doc.go        |     3 -
+ .../compute/v2/extensions/diskconfig/requests.go   |   114 -
+ .../v2/extensions/diskconfig/requests_test.go      |    87 -
+ .../compute/v2/extensions/diskconfig/results.go    |    60 -
+ .../v2/extensions/diskconfig/results_test.go       |    68 -
+ .../openstack/compute/v2/extensions/doc.go         |     3 -
+ .../compute/v2/extensions/keypairs/doc.go          |     3 -
+ .../compute/v2/extensions/keypairs/fixtures.go     |   171 -
+ .../compute/v2/extensions/keypairs/requests.go     |    88 -
+ .../v2/extensions/keypairs/requests_test.go        |    71 -
+ .../compute/v2/extensions/keypairs/results.go      |    94 -
+ .../compute/v2/extensions/keypairs/urls.go         |    25 -
+ .../compute/v2/extensions/keypairs/urls_test.go    |    40 -
+ .../openstack/compute/v2/flavors/doc.go            |     7 -
+ .../openstack/compute/v2/flavors/requests.go       |    72 -
+ .../openstack/compute/v2/flavors/requests_test.go  |   129 -
+ .../openstack/compute/v2/flavors/results.go        |   122 -
+ .../openstack/compute/v2/flavors/urls.go           |    13 -
+ .../openstack/compute/v2/flavors/urls_test.go      |    26 -
+ .../gophercloud/openstack/compute/v2/images/doc.go |     7 -
+ .../openstack/compute/v2/images/requests.go        |    71 -
+ .../openstack/compute/v2/images/requests_test.go   |   175 -
+ .../openstack/compute/v2/images/results.go         |    90 -
+ .../openstack/compute/v2/images/urls.go            |    11 -
+ .../openstack/compute/v2/images/urls_test.go       |    26 -
+ .../openstack/compute/v2/servers/doc.go            |     6 -
+ .../openstack/compute/v2/servers/fixtures.go       |   459 -
+ .../openstack/compute/v2/servers/requests.go       |   538 -
+ .../openstack/compute/v2/servers/requests_test.go  |   176 -
+ .../openstack/compute/v2/servers/results.go        |   150 -
+ .../openstack/compute/v2/servers/urls.go           |    31 -
+ .../openstack/compute/v2/servers/urls_test.go      |    56 -
+ .../openstack/compute/v2/servers/util.go           |    20 -
+ .../openstack/compute/v2/servers/util_test.go      |    38 -
+ .../gophercloud/openstack/endpoint_location.go     |   124 -
+ .../openstack/endpoint_location_test.go            |   225 -
+ .../openstack/identity/v2/extensions/delegate.go   |    52 -
+ .../identity/v2/extensions/delegate_test.go        |    38 -
+ .../openstack/identity/v2/extensions/doc.go        |     3 -
+ .../openstack/identity/v2/extensions/fixtures.go   |    60 -
+ .../openstack/identity/v2/tenants/doc.go           |     7 -
+ .../openstack/identity/v2/tenants/fixtures.go      |    65 -
+ .../openstack/identity/v2/tenants/requests.go      |    33 -
+ .../openstack/identity/v2/tenants/requests_test.go |    29 -
+ .../openstack/identity/v2/tenants/results.go       |    62 -
+ .../openstack/identity/v2/tenants/urls.go          |     7 -
+ .../openstack/identity/v2/tokens/doc.go            |     5 -
+ .../openstack/identity/v2/tokens/errors.go         |    30 -
+ .../openstack/identity/v2/tokens/fixtures.go       |   128 -
+ .../openstack/identity/v2/tokens/requests.go       |    87 -
+ .../openstack/identity/v2/tokens/requests_test.go  |   140 -
+ .../openstack/identity/v2/tokens/results.go        |   133 -
+ .../openstack/identity/v2/tokens/urls.go           |     8 -
+ .../openstack/identity/v3/endpoints/doc.go         |     6 -
+ .../openstack/identity/v3/endpoints/errors.go      |    21 -
+ .../openstack/identity/v3/endpoints/requests.go    |   133 -
+ .../identity/v3/endpoints/requests_test.go         |   226 -
+ .../openstack/identity/v3/endpoints/results.go     |    82 -
+ .../openstack/identity/v3/endpoints/urls.go        |    11 -
+ .../openstack/identity/v3/endpoints/urls_test.go   |    23 -
+ .../openstack/identity/v3/services/doc.go          |     3 -
+ .../openstack/identity/v3/services/requests.go     |    91 -
+ .../identity/v3/services/requests_test.go          |   209 -
+ .../openstack/identity/v3/services/results.go      |    80 -
+ .../openstack/identity/v3/services/urls.go         |    11 -
+ .../openstack/identity/v3/services/urls_test.go    |    23 -
+ .../openstack/identity/v3/tokens/doc.go            |     6 -
+ .../openstack/identity/v3/tokens/errors.go         |    72 -
+ .../openstack/identity/v3/tokens/requests.go       |   286 -
+ .../openstack/identity/v3/tokens/requests_test.go  |   514 -
+ .../openstack/identity/v3/tokens/results.go        |    73 -
+ .../openstack/identity/v3/tokens/urls.go           |     7 -
+ .../openstack/identity/v3/tokens/urls_test.go      |    21 -
+ .../openstack/networking/v2/apiversions/doc.go     |     4 -
+ .../openstack/networking/v2/apiversions/errors.go  |     1 -
+ .../networking/v2/apiversions/requests.go          |    21 -
+ .../networking/v2/apiversions/requests_test.go     |   182 -
+ .../openstack/networking/v2/apiversions/results.go |    77 -
+ .../openstack/networking/v2/apiversions/urls.go    |    15 -
+ .../networking/v2/apiversions/urls_test.go         |    26 -
+ .../openstack/networking/v2/common/common_tests.go |    14 -
+ .../openstack/networking/v2/extensions/delegate.go |    41 -
+ .../networking/v2/extensions/delegate_test.go      |   105 -
+ .../networking/v2/extensions/external/doc.go       |     3 -
+ .../networking/v2/extensions/external/requests.go  |    56 -
+ .../networking/v2/extensions/external/results.go   |    81 -
+ .../v2/extensions/external/results_test.go         |   254 -
+ .../networking/v2/extensions/layer3/doc.go         |     5 -
+ .../v2/extensions/layer3/floatingips/requests.go   |   190 -
+ .../extensions/layer3/floatingips/requests_test.go |   306 -
+ .../v2/extensions/layer3/floatingips/results.go    |   127 -
+ .../v2/extensions/layer3/floatingips/urls.go       |    13 -
+ .../v2/extensions/layer3/routers/requests.go       |   246 -
+ .../v2/extensions/layer3/routers/requests_test.go  |   338 -
+ .../v2/extensions/layer3/routers/results.go        |   161 -
+ .../v2/extensions/layer3/routers/urls.go           |    21 -
+ .../networking/v2/extensions/lbaas/doc.go          |     3 -
+ .../v2/extensions/lbaas/members/requests.go        |   139 -
+ .../v2/extensions/lbaas/members/requests_test.go   |   243 -
+ .../v2/extensions/lbaas/members/results.go         |   122 -
+ .../networking/v2/extensions/lbaas/members/urls.go |    16 -
+ .../v2/extensions/lbaas/monitors/requests.go       |   282 -
+ .../v2/extensions/lbaas/monitors/requests_test.go  |   312 -
+ .../v2/extensions/lbaas/monitors/results.go        |   147 -
+ .../v2/extensions/lbaas/monitors/urls.go           |    16 -
+ .../v2/extensions/lbaas/pools/requests.go          |   205 -
+ .../v2/extensions/lbaas/pools/requests_test.go     |   317 -
+ .../v2/extensions/lbaas/pools/results.go           |   146 -
+ .../networking/v2/extensions/lbaas/pools/urls.go   |    25 -
+ .../v2/extensions/lbaas/vips/requests.go           |   273 -
+ .../v2/extensions/lbaas/vips/requests_test.go      |   336 -
+ .../networking/v2/extensions/lbaas/vips/results.go |   166 -
+ .../networking/v2/extensions/lbaas/vips/urls.go    |    16 -
+ .../networking/v2/extensions/provider/doc.go       |    21 -
+ .../networking/v2/extensions/provider/results.go   |   124 -
+ .../v2/extensions/provider/results_test.go         |   253 -
+ .../networking/v2/extensions/security/doc.go       |    32 -
+ .../v2/extensions/security/groups/requests.go      |   107 -
+ .../v2/extensions/security/groups/requests_test.go |   213 -
+ .../v2/extensions/security/groups/results.go       |   108 -
+ .../v2/extensions/security/groups/urls.go          |    13 -
+ .../v2/extensions/security/rules/requests.go       |   183 -
+ .../v2/extensions/security/rules/requests_test.go  |   243 -
+ .../v2/extensions/security/rules/results.go        |   133 -
+ .../v2/extensions/security/rules/urls.go           |    13 -
+ .../openstack/networking/v2/networks/doc.go        |     9 -
+ .../openstack/networking/v2/networks/errors.go     |     1 -
+ .../openstack/networking/v2/networks/requests.go   |   209 -
+ .../networking/v2/networks/requests_test.go        |   275 -
+ .../openstack/networking/v2/networks/results.go    |   116 -
+ .../openstack/networking/v2/networks/urls.go       |    27 -
+ .../openstack/networking/v2/networks/urls_test.go  |    38 -
+ .../openstack/networking/v2/ports/doc.go           |     8 -
+ .../openstack/networking/v2/ports/errors.go        |    11 -
+ .../openstack/networking/v2/ports/requests.go      |   245 -
+ .../openstack/networking/v2/ports/requests_test.go |   321 -
+ .../openstack/networking/v2/ports/results.go       |   126 -
+ .../openstack/networking/v2/ports/urls.go          |    31 -
+ .../openstack/networking/v2/ports/urls_test.go     |    44 -
+ .../openstack/networking/v2/subnets/doc.go         |    10 -
+ .../openstack/networking/v2/subnets/errors.go      |    13 -
+ .../openstack/networking/v2/subnets/requests.go    |   254 -
+ .../networking/v2/subnets/requests_test.go         |   362 -
+ .../openstack/networking/v2/subnets/results.go     |   132 -
+ .../openstack/networking/v2/subnets/urls.go        |    31 -
+ .../openstack/networking/v2/subnets/urls_test.go   |    44 -
+ .../openstack/objectstorage/v1/accounts/doc.go     |     8 -
+ .../objectstorage/v1/accounts/fixtures.go          |    38 -
+ .../objectstorage/v1/accounts/requests.go          |   106 -
+ .../objectstorage/v1/accounts/requests_test.go     |    33 -
+ .../openstack/objectstorage/v1/accounts/results.go |    34 -
+ .../openstack/objectstorage/v1/accounts/urls.go    |    11 -
+ .../objectstorage/v1/accounts/urls_test.go         |    26 -
+ .../openstack/objectstorage/v1/containers/doc.go   |     8 -
+ .../objectstorage/v1/containers/fixtures.go        |   132 -
+ .../objectstorage/v1/containers/requests.go        |   204 -
+ .../objectstorage/v1/containers/requests_test.go   |    91 -
+ .../objectstorage/v1/containers/results.go         |   139 -
+ .../openstack/objectstorage/v1/containers/urls.go  |    23 -
+ .../objectstorage/v1/containers/urls_test.go       |    43 -
+ .../openstack/objectstorage/v1/objects/doc.go      |     5 -
+ .../openstack/objectstorage/v1/objects/fixtures.go |   164 -
+ .../openstack/objectstorage/v1/objects/requests.go |   416 -
+ .../objectstorage/v1/objects/requests_test.go      |   132 -
+ .../openstack/objectstorage/v1/objects/results.go  |   162 -
+ .../openstack/objectstorage/v1/objects/urls.go     |    33 -
+ .../objectstorage/v1/objects/urls_test.go          |    56 -
+ .../gophercloud/openstack/utils/choose_version.go  |   114 -
+ .../openstack/utils/choose_version_test.go         |   105 -
+ .../github.com/rackspace/gophercloud/package.go    |    38 -
+ .../rackspace/gophercloud/pagination/http.go       |    64 -
+ .../rackspace/gophercloud/pagination/linked.go     |    61 -
+ .../gophercloud/pagination/linked_test.go          |   107 -
+ .../rackspace/gophercloud/pagination/marker.go     |    34 -
+ .../gophercloud/pagination/marker_test.go          |   113 -
+ .../rackspace/gophercloud/pagination/null.go       |    20 -
+ .../rackspace/gophercloud/pagination/pager.go      |   115 -
+ .../gophercloud/pagination/pagination_test.go      |    13 -
+ .../rackspace/gophercloud/pagination/pkg.go        |     4 -
+ .../rackspace/gophercloud/pagination/single.go     |     9 -
+ .../gophercloud/pagination/single_test.go          |    71 -
+ .../src/github.com/rackspace/gophercloud/params.go |   184 -
+ .../rackspace/gophercloud/params_test.go           |   142 -
+ .../rackspace/gophercloud/provider_client.go       |    33 -
+ .../rackspace/gophercloud/provider_client_test.go  |    16 -
+ .../rackspace/gophercloud/rackspace/auth_env.go    |    57 -
+ .../blockstorage/v1/snapshots/delegate.go          |   134 -
+ .../blockstorage/v1/snapshots/delegate_test.go     |    97 -
+ .../rackspace/blockstorage/v1/snapshots/doc.go     |     3 -
+ .../rackspace/blockstorage/v1/snapshots/results.go |   149 -
+ .../rackspace/blockstorage/v1/volumes/delegate.go  |    75 -
+ .../blockstorage/v1/volumes/delegate_test.go       |   106 -
+ .../rackspace/blockstorage/v1/volumes/doc.go       |     3 -
+ .../rackspace/blockstorage/v1/volumes/results.go   |    66 -
+ .../blockstorage/v1/volumetypes/delegate.go        |    18 -
+ .../blockstorage/v1/volumetypes/delegate_test.go   |    64 -
+ .../rackspace/blockstorage/v1/volumetypes/doc.go   |     3 -
+ .../blockstorage/v1/volumetypes/results.go         |    37 -
+ .../rackspace/gophercloud/rackspace/client.go      |   156 -
+ .../rackspace/gophercloud/rackspace/client_test.go |    38 -
+ .../compute/v2/bootfromvolume/delegate.go          |    12 -
+ .../compute/v2/bootfromvolume/delegate_test.go     |    52 -
+ .../rackspace/compute/v2/flavors/delegate.go       |    46 -
+ .../rackspace/compute/v2/flavors/delegate_test.go  |    62 -
+ .../rackspace/compute/v2/flavors/doc.go            |     3 -
+ .../rackspace/compute/v2/flavors/fixtures.go       |   128 -
+ .../rackspace/compute/v2/images/delegate.go        |    22 -
+ .../rackspace/compute/v2/images/delegate_test.go   |    62 -
+ .../gophercloud/rackspace/compute/v2/images/doc.go |     3 -
+ .../rackspace/compute/v2/images/fixtures.go        |   199 -
+ .../rackspace/compute/v2/keypairs/delegate.go      |    33 -
+ .../rackspace/compute/v2/keypairs/delegate_test.go |    72 -
+ .../rackspace/compute/v2/keypairs/doc.go           |     3 -
+ .../rackspace/compute/v2/networks/doc.go           |     3 -
+ .../rackspace/compute/v2/networks/requests.go      |   101 -
+ .../rackspace/compute/v2/networks/requests_test.go |   156 -
+ .../rackspace/compute/v2/networks/results.go       |    81 -
+ .../rackspace/compute/v2/networks/urls.go          |    27 -
+ .../rackspace/compute/v2/networks/urls_test.go     |    38 -
+ .../rackspace/compute/v2/servers/delegate.go       |    61 -
+ .../rackspace/compute/v2/servers/delegate_test.go  |   112 -
+ .../rackspace/compute/v2/servers/doc.go            |     3 -
+ .../rackspace/compute/v2/servers/fixtures.go       |   439 -
+ .../rackspace/compute/v2/servers/requests.go       |   158 -
+ .../rackspace/compute/v2/servers/requests_test.go  |    57 -
+ .../compute/v2/virtualinterfaces/requests.go       |    51 -
+ .../compute/v2/virtualinterfaces/requests_test.go  |   165 -
+ .../compute/v2/virtualinterfaces/results.go        |    81 -
+ .../rackspace/compute/v2/virtualinterfaces/urls.go |    15 -
+ .../compute/v2/virtualinterfaces/urls_test.go      |    32 -
+ .../rackspace/identity/v2/extensions/delegate.go   |    24 -
+ .../identity/v2/extensions/delegate_test.go        |    39 -
+ .../rackspace/identity/v2/extensions/doc.go        |     3 -
+ .../rackspace/identity/v2/tenants/delegate.go      |    17 -
+ .../rackspace/identity/v2/tenants/delegate_test.go |    28 -
+ .../rackspace/identity/v2/tenants/doc.go           |     3 -
+ .../rackspace/identity/v2/tokens/delegate.go       |    60 -
+ .../rackspace/identity/v2/tokens/delegate_test.go  |    36 -
+ .../rackspace/identity/v2/tokens/doc.go            |     3 -
+ .../objectstorage/v1/accounts/delegate.go          |    39 -
+ .../objectstorage/v1/accounts/delegate_test.go     |    30 -
+ .../rackspace/objectstorage/v1/accounts/doc.go     |     3 -
+ .../rackspace/objectstorage/v1/bulk/doc.go         |     3 -
+ .../rackspace/objectstorage/v1/bulk/requests.go    |    51 -
+ .../objectstorage/v1/bulk/requests_test.go         |    36 -
+ .../rackspace/objectstorage/v1/bulk/results.go     |    28 -
+ .../rackspace/objectstorage/v1/bulk/urls.go        |    11 -
+ .../rackspace/objectstorage/v1/bulk/urls_test.go   |    26 -
+ .../objectstorage/v1/cdncontainers/delegate.go     |    71 -
+ .../v1/cdncontainers/delegate_test.go              |    50 -
+ .../objectstorage/v1/cdncontainers/doc.go          |     3 -
+ .../objectstorage/v1/cdncontainers/requests.go     |    58 -
+ .../v1/cdncontainers/requests_test.go              |    29 -
+ .../objectstorage/v1/cdncontainers/results.go      |     8 -
+ .../objectstorage/v1/cdncontainers/urls.go         |     7 -
+ .../objectstorage/v1/cdncontainers/urls_test.go    |    20 -
+ .../objectstorage/v1/cdnobjects/delegate.go        |    11 -
+ .../objectstorage/v1/cdnobjects/delegate_test.go   |    19 -
+ .../rackspace/objectstorage/v1/cdnobjects/doc.go   |     3 -
+ .../objectstorage/v1/containers/delegate.go        |    93 -
+ .../objectstorage/v1/containers/delegate_test.go   |    91 -
+ .../rackspace/objectstorage/v1/containers/doc.go   |     3 -
+ .../rackspace/objectstorage/v1/objects/delegate.go |    90 -
+ .../objectstorage/v1/objects/delegate_test.go      |   115 -
+ .../rackspace/objectstorage/v1/objects/doc.go      |     3 -
+ .../github.com/rackspace/gophercloud/results.go    |    83 -
+ .../rackspace/gophercloud/script/acceptancetest    |     5 -
+ .../rackspace/gophercloud/script/bootstrap         |    26 -
+ .../rackspace/gophercloud/script/cibuild           |     5 -
+ .../github.com/rackspace/gophercloud/script/test   |     5 -
+ .../rackspace/gophercloud/script/unittest          |     5 -
+ .../rackspace/gophercloud/service_client.go        |    32 -
+ .../rackspace/gophercloud/service_client_test.go   |    14 -
+ .../gophercloud/testhelper/client/fake.go          |    17 -
+ .../gophercloud/testhelper/convenience.go          |   329 -
+ .../rackspace/gophercloud/testhelper/doc.go        |     4 -
+ .../gophercloud/testhelper/http_responses.go       |    91 -
+ .../src/github.com/rackspace/gophercloud/util.go   |    39 -
+ .../github.com/rackspace/gophercloud/util_test.go  |    14 -
  .../src/github.com/skratchdot/LICENSE-MIT          |    22 -
  .../github.com/skratchdot/open-golang/open/exec.go |    15 -
  .../skratchdot/open-golang/open/exec_darwin.go     |    15 -
  .../skratchdot/open-golang/open/exec_windows.go    |    21 -
  .../github.com/skratchdot/open-golang/open/open.go |    50 -
  .../skratchdot/open-golang/open/open_test.go       |    70 -
+ .../skynetservices/skydns/msg/service.go           |    95 -
  .../src/github.com/spf13/cobra/.gitignore          |    24 -
  .../src/github.com/spf13/cobra/.travis.yml         |     6 -
  .../src/github.com/spf13/cobra/LICENSE.txt         |   174 -
- .../src/github.com/spf13/cobra/README.md           |   397 -
- .../_workspace/src/github.com/spf13/cobra/cobra.go |    98 -
- .../src/github.com/spf13/cobra/cobra_test.go       |   507 -
- .../src/github.com/spf13/cobra/command.go          |   764 -
+ .../src/github.com/spf13/cobra/README.md           |   399 -
+ .../_workspace/src/github.com/spf13/cobra/cobra.go |   104 -
+ .../src/github.com/spf13/cobra/cobra_test.go       |   553 -
+ .../src/github.com/spf13/cobra/command.go          |   790 -
  .../_workspace/src/github.com/spf13/pflag/LICENSE  |    28 -
  .../src/github.com/spf13/pflag/README.md           |   155 -
  .../_workspace/src/github.com/spf13/pflag/bool.go  |    74 -
@@ -424,23 +956,6 @@ Subject: [PATCH] remove all third party software
  .../src/github.com/stretchr/testify/mock/doc.go    |    43 -
  .../src/github.com/stretchr/testify/mock/mock.go   |   505 -
  .../github.com/stretchr/testify/mock/mock_test.go  |   657 -
- .../github.com/tonnerre/golang-pretty/.gitignore   |     4 -
- .../src/github.com/tonnerre/golang-pretty/License  |    19 -
- .../src/github.com/tonnerre/golang-pretty/Readme   |     9 -
- .../tonnerre/golang-pretty/debian/changelog        |     5 -
- .../tonnerre/golang-pretty/debian/compat           |     1 -
- .../tonnerre/golang-pretty/debian/control          |    22 -
- .../tonnerre/golang-pretty/debian/copyright        |    30 -
- .../github.com/tonnerre/golang-pretty/debian/docs  |     1 -
- .../github.com/tonnerre/golang-pretty/debian/rules |    11 -
- .../tonnerre/golang-pretty/debian/source/format    |     1 -
- .../src/github.com/tonnerre/golang-pretty/diff.go  |   148 -
- .../github.com/tonnerre/golang-pretty/diff_test.go |    73 -
- .../tonnerre/golang-pretty/example_test.go         |    20 -
- .../github.com/tonnerre/golang-pretty/formatter.go |   300 -
- .../tonnerre/golang-pretty/formatter_test.go       |   146 -
- .../github.com/tonnerre/golang-pretty/pretty.go    |    98 -
- .../src/github.com/tonnerre/golang-pretty/zero.go  |    41 -
  .../src/github.com/vaughan0/go-ini/LICENSE         |    14 -
  .../src/github.com/vaughan0/go-ini/README.md       |    70 -
  .../src/github.com/vaughan0/go-ini/ini.go          |   123 -
@@ -562,7 +1077,17 @@ Subject: [PATCH] remove all third party software
  Godeps/_workspace/src/gopkg.in/v2/yaml/yaml.go     |   334 -
  Godeps/_workspace/src/gopkg.in/v2/yaml/yamlh.go    |   716 -
  .../src/gopkg.in/v2/yaml/yamlprivateh.go           |   173 -
- 558 files changed, 141865 deletions(-)
+ .../src/speter.net/go/exp/math/dec/inf/LICENSE     |    57 -
+ .../go/exp/math/dec/inf/benchmark_test.go          |   210 -
+ .../src/speter.net/go/exp/math/dec/inf/dec.go      |   615 -
+ .../go/exp/math/dec/inf/dec_go1_2_test.go          |    33 -
+ .../go/exp/math/dec/inf/dec_internal_test.go       |    40 -
+ .../src/speter.net/go/exp/math/dec/inf/dec_test.go |   379 -
+ .../speter.net/go/exp/math/dec/inf/example_test.go |    62 -
+ .../src/speter.net/go/exp/math/dec/inf/rounder.go  |   145 -
+ .../go/exp/math/dec/inf/rounder_example_test.go    |    72 -
+ .../speter.net/go/exp/math/dec/inf/rounder_test.go |   109 -
+ 1083 files changed, 197448 deletions(-)
  delete mode 100644 Godeps/Godeps.json
  delete mode 100644 Godeps/Readme
  delete mode 100644 Godeps/_workspace/.gitignore
@@ -634,6 +1159,40 @@ Subject: [PATCH] remove all third party software
  delete mode 100644 Godeps/_workspace/src/code.google.com/p/google-api-go-client/googleapi/transport/apikey.go
  delete mode 100644 Godeps/_workspace/src/code.google.com/p/google-api-go-client/googleapi/types.go
  delete mode 100644 Godeps/_workspace/src/code.google.com/p/google-api-go-client/googleapi/types_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/.gitignore
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/.travis.yml
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/LICENSE
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/README.md
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/entry.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/entry_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/examples/basic/basic.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/examples/hook/hook.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/exported.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/formatter.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/formatter_bench_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/hook_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/airbrake/airbrake.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/papertrail/README.md
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/papertrail/papertrail.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/papertrail/papertrail_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/sentry/README.md
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/sentry/sentry.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/sentry/sentry_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/syslog/README.md
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/syslog/syslog.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/syslog/syslog_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/json_formatter.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/logger.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/logrus.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/logrus_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_darwin.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_freebsd.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_linux.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_notwindows.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_windows.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/text_formatter.go
+ delete mode 100644 Godeps/_workspace/src/github.com/Sirupsen/logrus/text_formatter_test.go
  delete mode 100644 Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/add_child.go
  delete mode 100644 Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/add_child_test.go
  delete mode 100644 Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/client.go
@@ -674,6 +1233,82 @@ Subject: [PATCH] remove all third party software
  delete mode 100644 Godeps/_workspace/src/github.com/davecgh/go-spew/spew/spew.go
  delete mode 100644 Godeps/_workspace/src/github.com/davecgh/go-spew/spew/spew_test.go
  delete mode 100644 Godeps/_workspace/src/github.com/davecgh/go-spew/spew/testdata/dumpcgo.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/archive/MAINTAINERS
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/archive/README.md
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/archive/archive.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/archive/archive_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/archive/archive_unix.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/archive/archive_windows.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/archive/changes.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/archive/changes_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/archive/diff.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/archive/diff_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/archive/example_changes.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/archive/testdata/broken.tar
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/archive/time_linux.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/archive/time_unsupported.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/archive/utils_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/archive/wrap.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/fileutils/fileutils.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/ioutils/readers.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/ioutils/readers_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/ioutils/writers.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/pools/pools.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/pools/pools_nopool.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/promise/promise.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/MAINTAINERS
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/errors.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/lstat.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/lstat_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/lstat_windows.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/meminfo.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/meminfo_linux.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/meminfo_linux_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/meminfo_unsupported.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/mknod.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/mknod_windows.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat_linux.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat_unsupported.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat_windows.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/umask.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/umask_windows.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_darwin.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_freebsd.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_linux.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_unsupported.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/xattrs_linux.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/system/xattrs_unsupported.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/units/MAINTAINERS
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/units/duration.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/units/duration_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/units/size.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/pkg/units/size_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/common.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/example_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/reader.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/reader_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/stat_atim.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/stat_atimespec.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/stat_unix.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/tar_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/gnu.tar
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/nil-uid.tar
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/pax.tar
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/small.txt
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/small2.txt
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/sparse-formats.tar
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/star.tar
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/ustar.tar
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/v7.tar
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/writer-big-long.tar
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/writer-big.tar
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/writer.tar
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/xattrs.tar
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/writer.go
+ delete mode 100644 Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/writer_test.go
  delete mode 100644 Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/LICENSE
  delete mode 100644 Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/README.md
  delete mode 100644 Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/assetfs.go
@@ -766,6 +1401,7 @@ Subject: [PATCH] remove all third party software
  delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/DOCKER-LICENSE
  delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/LICENSE
  delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/README.markdown
+ delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/build_test.go
  delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/change.go
  delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/change_test.go
  delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/client.go
@@ -786,9 +1422,20 @@ Subject: [PATCH] remove all third party software
  delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/signal.go
  delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/stdcopy.go
  delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/stdcopy_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/tar.go
+ delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/bin/fmtpolice
+ delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/.dockerignore
  delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/Dockerfile
+ delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/barfile
+ delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/ca.pem
+ delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/cert.pem
  delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/container.tar
  delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/dockerfile.tar
+ delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/foofile
+ delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/key.pem
+ delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/server.pem
+ delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/serverkey.pem
+ delete mode 120000 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/symlink
  delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/server.go
  delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/server_test.go
  delete mode 100644 Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/writer.go
@@ -819,18 +1466,69 @@ Subject: [PATCH] remove all third party software
  delete mode 100644 Godeps/_workspace/src/github.com/google/gofuzz/example_test.go
  delete mode 100644 Godeps/_workspace/src/github.com/google/gofuzz/fuzz.go
  delete mode 100644 Godeps/_workspace/src/github.com/google/gofuzz/fuzz_test.go
- delete mode 100644 Godeps/_workspace/src/github.com/kr/text/License
- delete mode 100644 Godeps/_workspace/src/github.com/kr/text/Readme
- delete mode 100644 Godeps/_workspace/src/github.com/kr/text/colwriter/Readme
- delete mode 100644 Godeps/_workspace/src/github.com/kr/text/colwriter/column.go
- delete mode 100644 Godeps/_workspace/src/github.com/kr/text/colwriter/column_test.go
- delete mode 100644 Godeps/_workspace/src/github.com/kr/text/doc.go
- delete mode 100644 Godeps/_workspace/src/github.com/kr/text/indent.go
- delete mode 100644 Godeps/_workspace/src/github.com/kr/text/indent_test.go
- delete mode 100644 Godeps/_workspace/src/github.com/kr/text/mc/Readme
- delete mode 100644 Godeps/_workspace/src/github.com/kr/text/mc/mc.go
- delete mode 100644 Godeps/_workspace/src/github.com/kr/text/wrap.go
- delete mode 100644 Godeps/_workspace/src/github.com/kr/text/wrap_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/imdario/mergo/.travis.yml
+ delete mode 100644 Godeps/_workspace/src/github.com/imdario/mergo/LICENSE
+ delete mode 100644 Godeps/_workspace/src/github.com/imdario/mergo/README.md
+ delete mode 100644 Godeps/_workspace/src/github.com/imdario/mergo/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/imdario/mergo/map.go
+ delete mode 100644 Godeps/_workspace/src/github.com/imdario/mergo/merge.go
+ delete mode 100644 Godeps/_workspace/src/github.com/imdario/mergo/mergo.go
+ delete mode 100644 Godeps/_workspace/src/github.com/imdario/mergo/mergo_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/imdario/mergo/testdata/license.yml
+ delete mode 100644 Godeps/_workspace/src/github.com/imdario/mergo/testdata/thing.yml
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/.gitignore
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/.travis.yml
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/AUTHORS
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/CONTRIBUTORS
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/COPYRIGHT
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/LICENSE
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/README.md
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/client.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/client_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/clientconfig.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/defaults.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/dns.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/dns_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/dnssec.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/dnssec_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/dyn_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/edns.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/edns_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/example_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/idn/example_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/idn/punycode.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/idn/punycode_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/keygen.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/kscan.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/labels.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/labels_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/msg.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/nsecx.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/nsecx_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/parse_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/privaterr.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/privaterr_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/rawmsg.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/scanner.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/server.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/server_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/sig0.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/sig0_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/singleinflight.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/tlsa.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/tsig.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/types.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/types_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/udp.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/udp_linux.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/udp_other.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/udp_windows.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/update.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/update_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/xfr.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/zgenerate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/zscan.go
+ delete mode 100644 Godeps/_workspace/src/github.com/miekg/dns/zscan_rr.go
  delete mode 100644 Godeps/_workspace/src/github.com/mitchellh/goamz/aws/attempt.go
  delete mode 100644 Godeps/_workspace/src/github.com/mitchellh/goamz/aws/attempt_test.go
  delete mode 100644 Godeps/_workspace/src/github.com/mitchellh/goamz/aws/aws.go
@@ -862,64 +1560,423 @@ Subject: [PATCH] remove all third party software
  delete mode 100644 Godeps/_workspace/src/github.com/racker/perigee/README.md
  delete mode 100644 Godeps/_workspace/src/github.com/racker/perigee/api.go
  delete mode 100644 Godeps/_workspace/src/github.com/racker/perigee/api_test.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/.editorconfig
  delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/.travis.yml
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/CONTRIBUTING.md
  delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/CONTRIBUTORS.md
  delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/LICENSE
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/README.asciidoc
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/00-authentication.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/01-authentication.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/02-list-servers.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/03-get-server-details.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/04-create-server.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/05-list-images.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/06-list-flavors.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/07-change-admin-password.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/08-reauthentication.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/09-resize-server.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/10-reboot-server.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/11-rescue-unrescue-server.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/12-update-server.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/13-rebuild-server.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/14-list-addresses.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/15-list-keypairs.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/16-create-delete-keypair.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/17-create-delete-image.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/18-osutil-authentication.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/19-list-addresses-0.1.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/99-delete-server.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/libargs.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/api_fetch.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/authenticate.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/authenticate_test.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/common_types.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/context.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/context_test.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/errors.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/flavors.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/floating_ips.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/global_context.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/images.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/interfaces.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/keypairs.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/osutil/auth.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/osutil/region.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/README.md
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/UPGRADING.md
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/README.md
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/blockstorage/v1/snapshots_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/blockstorage/v1/volumes_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/blockstorage/v1/volumetypes_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/client_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/bootfromvolume_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/compute_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/extension_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/flavors_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/images_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/pkg.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/servers_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/extension_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/identity_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/pkg.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/tenant_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/token_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/endpoint_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/identity_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/pkg.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/service_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/token_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/apiversion_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/common.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extension_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/layer3_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/common.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/member_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/monitor_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/pkg.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/pool_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/vip_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/pkg.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/provider_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/security_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/network_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/pkg.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/port_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/subnet_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/objectstorage/v1/accounts_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/objectstorage/v1/common.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/objectstorage/v1/containers_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/objectstorage/v1/objects_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/pkg.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/blockstorage/v1/common.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/blockstorage/v1/snapshot_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/blockstorage/v1/volume_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/blockstorage/v1/volume_type_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/client_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/bootfromvolume_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/compute_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/flavors_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/images_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/keypairs_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/networks_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/pkg.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/servers_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/virtualinterfaces_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/identity/v2/extension_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/identity/v2/identity_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/identity/v2/tenant_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/accounts_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/bulk_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/cdncontainers_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/cdnobjects_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/common.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/containers_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/objects_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/pkg.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/tools/pkg.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/tools/tools.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/auth_options.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/auth_results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/endpoint_search.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/endpoint_search_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/auth_env.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/fixtures.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/util.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/util_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/fixtures.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/util.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/util_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/fixtures.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/client.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/client_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/README.md
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/errors.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/fixtures.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/results_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/fixtures.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/fixtures.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/util.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/util_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/endpoint_location.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/endpoint_location_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/extensions/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/extensions/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/extensions/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/extensions/fixtures.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/fixtures.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/errors.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/fixtures.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/errors.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/errors.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/errors.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/common/common_tests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/external/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/external/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/external/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/external/results_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/floatingips/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/floatingips/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/floatingips/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/floatingips/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/routers/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/routers/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/routers/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/routers/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/members/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/members/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/members/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/members/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/monitors/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/monitors/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/monitors/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/monitors/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/pools/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/pools/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/pools/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/pools/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/vips/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/vips/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/vips/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/vips/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/provider/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/provider/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/provider/results_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/groups/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/groups/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/groups/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/groups/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/errors.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/errors.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/errors.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/fixtures.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/fixtures.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/fixtures.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/utils/choose_version.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/utils/choose_version_test.go
  delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/package.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/reauth.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/reauth_test.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/scripts/create-environment.sh
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/scripts/test-all.sh
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/servers.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/servers_test.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/service_catalog.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/service_catalog_test.go
- delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/transport_double_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/http.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/linked.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/linked_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/marker.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/marker_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/null.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/pager.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/pagination_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/pkg.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/single.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/single_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/params.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/params_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/provider_client.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/provider_client_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/auth_env.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/snapshots/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/snapshots/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/snapshots/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/snapshots/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumes/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumes/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumes/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumes/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumetypes/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumetypes/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumetypes/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumetypes/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/client.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/client_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/bootfromvolume/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/bootfromvolume/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/flavors/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/flavors/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/flavors/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/flavors/fixtures.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/images/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/images/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/images/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/images/fixtures.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/keypairs/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/keypairs/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/keypairs/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/fixtures.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/extensions/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/extensions/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/extensions/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tenants/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tenants/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tenants/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tokens/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tokens/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tokens/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/accounts/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/accounts/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/accounts/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/requests.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/requests_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/urls.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/urls_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdnobjects/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdnobjects/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdnobjects/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/containers/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/containers/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/containers/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/objects/delegate.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/objects/delegate_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/objects/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/results.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/script/acceptancetest
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/script/bootstrap
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/script/cibuild
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/script/test
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/script/unittest
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/service_client.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/service_client_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/testhelper/client/fake.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/testhelper/convenience.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/testhelper/doc.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/testhelper/http_responses.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/util.go
+ delete mode 100644 Godeps/_workspace/src/github.com/rackspace/gophercloud/util_test.go
  delete mode 100644 Godeps/_workspace/src/github.com/skratchdot/LICENSE-MIT
  delete mode 100644 Godeps/_workspace/src/github.com/skratchdot/open-golang/open/exec.go
  delete mode 100644 Godeps/_workspace/src/github.com/skratchdot/open-golang/open/exec_darwin.go
  delete mode 100644 Godeps/_workspace/src/github.com/skratchdot/open-golang/open/exec_windows.go
  delete mode 100644 Godeps/_workspace/src/github.com/skratchdot/open-golang/open/open.go
  delete mode 100644 Godeps/_workspace/src/github.com/skratchdot/open-golang/open/open_test.go
+ delete mode 100644 Godeps/_workspace/src/github.com/skynetservices/skydns/msg/service.go
  delete mode 100644 Godeps/_workspace/src/github.com/spf13/cobra/.gitignore
  delete mode 100644 Godeps/_workspace/src/github.com/spf13/cobra/.travis.yml
  delete mode 100644 Godeps/_workspace/src/github.com/spf13/cobra/LICENSE.txt
@@ -983,23 +2040,6 @@ Subject: [PATCH] remove all third party software
  delete mode 100644 Godeps/_workspace/src/github.com/stretchr/testify/mock/doc.go
  delete mode 100644 Godeps/_workspace/src/github.com/stretchr/testify/mock/mock.go
  delete mode 100644 Godeps/_workspace/src/github.com/stretchr/testify/mock/mock_test.go
- delete mode 100644 Godeps/_workspace/src/github.com/tonnerre/golang-pretty/.gitignore
- delete mode 100644 Godeps/_workspace/src/github.com/tonnerre/golang-pretty/License
- delete mode 100644 Godeps/_workspace/src/github.com/tonnerre/golang-pretty/Readme
- delete mode 100644 Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/changelog
- delete mode 100644 Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/compat
- delete mode 100644 Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/control
- delete mode 100644 Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/copyright
- delete mode 100644 Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/docs
- delete mode 100644 Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/rules
- delete mode 100644 Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/source/format
- delete mode 100644 Godeps/_workspace/src/github.com/tonnerre/golang-pretty/diff.go
- delete mode 100644 Godeps/_workspace/src/github.com/tonnerre/golang-pretty/diff_test.go
- delete mode 100644 Godeps/_workspace/src/github.com/tonnerre/golang-pretty/example_test.go
- delete mode 100644 Godeps/_workspace/src/github.com/tonnerre/golang-pretty/formatter.go
- delete mode 100644 Godeps/_workspace/src/github.com/tonnerre/golang-pretty/formatter_test.go
- delete mode 100644 Godeps/_workspace/src/github.com/tonnerre/golang-pretty/pretty.go
- delete mode 100644 Godeps/_workspace/src/github.com/tonnerre/golang-pretty/zero.go
  delete mode 100644 Godeps/_workspace/src/github.com/vaughan0/go-ini/LICENSE
  delete mode 100644 Godeps/_workspace/src/github.com/vaughan0/go-ini/README.md
  delete mode 100644 Godeps/_workspace/src/github.com/vaughan0/go-ini/ini.go
@@ -1121,13 +2161,23 @@ Subject: [PATCH] remove all third party software
  delete mode 100644 Godeps/_workspace/src/gopkg.in/v2/yaml/yaml.go
  delete mode 100644 Godeps/_workspace/src/gopkg.in/v2/yaml/yamlh.go
  delete mode 100644 Godeps/_workspace/src/gopkg.in/v2/yaml/yamlprivateh.go
+ delete mode 100644 Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/LICENSE
+ delete mode 100644 Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/benchmark_test.go
+ delete mode 100644 Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/dec.go
+ delete mode 100644 Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/dec_go1_2_test.go
+ delete mode 100644 Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/dec_internal_test.go
+ delete mode 100644 Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/dec_test.go
+ delete mode 100644 Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/example_test.go
+ delete mode 100644 Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/rounder.go
+ delete mode 100644 Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/rounder_example_test.go
+ delete mode 100644 Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/rounder_test.go
 
 diff --git a/Godeps/Godeps.json b/Godeps/Godeps.json
 deleted file mode 100644
-index 06bc6a2..0000000
+index 48b7bba..0000000
 --- a/Godeps/Godeps.json
 +++ /dev/null
-@@ -1,166 +0,0 @@
+@@ -1,217 +0,0 @@
 -{
 -	"ImportPath": "github.com/GoogleCloudPlatform/kubernetes",
 -	"GoVersion": "go1.3",
@@ -1170,6 +2220,11 @@ index 06bc6a2..0000000
 -			"Rev": "98c78185197025f935947caac56a7b6d022f89d2"
 -		},
 -		{
+-			"ImportPath": "github.com/Sirupsen/logrus",
+-			"Comment": "v0.6.2-10-g51fe59a",
+-			"Rev": "51fe59aca108dc5680109e7b2051cbdcfa5a253c"
+-		},
+-		{
 -			"ImportPath": "github.com/coreos/go-etcd/etcd",
 -			"Comment": "v0.2.0-rc1-120-g23142f6",
 -			"Rev": "23142f6773a676cc2cae8dd0cb90b2ea761c853f"
@@ -1179,6 +2234,46 @@ index 06bc6a2..0000000
 -			"Rev": "83f84dc933714d51504ceed59f43ead21d096fe7"
 -		},
 -		{
+-			"ImportPath": "github.com/docker/docker/pkg/archive",
+-			"Comment": "v1.4.1-108-g364720b",
+-			"Rev": "364720b5e7e725cdc466171de873eefdb8609a33"
+-		},
+-		{
+-			"ImportPath": "github.com/docker/docker/pkg/fileutils",
+-			"Comment": "v1.4.1-108-g364720b",
+-			"Rev": "364720b5e7e725cdc466171de873eefdb8609a33"
+-		},
+-		{
+-			"ImportPath": "github.com/docker/docker/pkg/ioutils",
+-			"Comment": "v1.4.1-108-g364720b",
+-			"Rev": "364720b5e7e725cdc466171de873eefdb8609a33"
+-		},
+-		{
+-			"ImportPath": "github.com/docker/docker/pkg/pools",
+-			"Comment": "v1.4.1-108-g364720b",
+-			"Rev": "364720b5e7e725cdc466171de873eefdb8609a33"
+-		},
+-		{
+-			"ImportPath": "github.com/docker/docker/pkg/promise",
+-			"Comment": "v1.4.1-108-g364720b",
+-			"Rev": "364720b5e7e725cdc466171de873eefdb8609a33"
+-		},
+-		{
+-			"ImportPath": "github.com/docker/docker/pkg/system",
+-			"Comment": "v1.4.1-108-g364720b",
+-			"Rev": "364720b5e7e725cdc466171de873eefdb8609a33"
+-		},
+-		{
+-			"ImportPath": "github.com/docker/docker/pkg/units",
+-			"Comment": "v1.4.1-108-g364720b",
+-			"Rev": "364720b5e7e725cdc466171de873eefdb8609a33"
+-		},
+-		{
+-			"ImportPath": "github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar",
+-			"Comment": "v1.4.1-108-g364720b",
+-			"Rev": "364720b5e7e725cdc466171de873eefdb8609a33"
+-		},
+-		{
 -			"ImportPath": "github.com/elazarl/go-bindata-assetfs",
 -			"Rev": "ae4665cf2d188c65764c73fe4af5378acc549510"
 -		},
@@ -1189,8 +2284,8 @@ index 06bc6a2..0000000
 -		},
 -		{
 -			"ImportPath": "github.com/fsouza/go-dockerclient",
--			"Comment": "0.2.1-267-g15d2c6e",
--			"Rev": "15d2c6e3eb670c545d0af0604d7f9aff3871af04"
+-			"Comment": "0.2.1-334-g9c377ff",
+-			"Rev": "9c377ffd9aed48a012adf1c3fd517fe98394120b"
 -		},
 -		{
 -			"ImportPath": "github.com/ghodss/yaml",
@@ -1215,8 +2310,13 @@ index 06bc6a2..0000000
 -			"Rev": "aef70dacbc78771e35beb261bb3a72986adf7906"
 -		},
 -		{
--			"ImportPath": "github.com/kr/text",
--			"Rev": "6807e777504f54ad073ecef66747de158294b639"
+-			"ImportPath": "github.com/imdario/mergo",
+-			"Comment": "0.1.3-8-g6633656",
+-			"Rev": "6633656539c1639d9d78127b7d47c622b5d7b6dc"
+-		},
+-		{
+-			"ImportPath": "github.com/miekg/dns",
+-			"Rev": "3f504e8dabd5d562e997d19ce0200aa41973e1b2"
 -		},
 -		{
 -			"ImportPath": "github.com/mitchellh/goamz/aws",
@@ -1237,16 +2337,21 @@ index 06bc6a2..0000000
 -		},
 -		{
 -			"ImportPath": "github.com/rackspace/gophercloud",
--			"Comment": "v0.1.0-31-ge13cda2",
--			"Rev": "e13cda260ce48d63ce816f4fa72b6c6cd096596d"
+-			"Comment": "v1.0.0",
+-			"Rev": "da56de6a59e53fdd61be1b5d9b87df34c47ac420"
 -		},
 -		{
 -			"ImportPath": "github.com/skratchdot/open-golang/open",
 -			"Rev": "ba570a111973b539baf23c918213059543b5bb6e"
 -		},
 -		{
+-			"ImportPath": "github.com/skynetservices/skydns/msg",
+-			"Comment": "2.0.1d-2-g245a121",
+-			"Rev": "245a1216be2a7f5377ea56e957fdfa0de6ecd067"
+-		},
+-		{
 -			"ImportPath": "github.com/spf13/cobra",
--			"Rev": "b1e90a7943957b51bb96a13b44b844475bcf95c0"
+-			"Rev": "e1e66f7b4e667751cf530ddb6e72b79d6eeb0235"
 -		},
 -		{
 -			"ImportPath": "github.com/spf13/pflag",
@@ -1265,32 +2370,28 @@ index 06bc6a2..0000000
 -			"Rev": "37614ac27794505bf7867ca93aac883cadb6a5f7"
 -		},
 -		{
--			"ImportPath": "github.com/tonnerre/golang-pretty",
--			"Comment": "debian/0.0_git20130613-1-1-ge7fccc0",
--			"Rev": "e7fccc03e91bad289b96c21aa3312a220689bdd7"
--		},
--		{
 -			"ImportPath": "github.com/vaughan0/go-ini",
 -			"Rev": "a98ad7ee00ec53921f08832bc06ecf7fd600e6a1"
 -		},
 -		{
 -			"ImportPath": "golang.org/x/net/context",
--			"Comment": "null-214",
--			"Rev": "c043f0dc72e4cdd23ae039470ea9d63e6680a1b2"
+-			"Rev": "cbcac7bb8415db9b6cb4d1ebab1dc9afbd688b97"
 -		},
 -		{
 -			"ImportPath": "golang.org/x/net/html",
--			"Comment": "null-214",
--			"Rev": "c043f0dc72e4cdd23ae039470ea9d63e6680a1b2"
+-			"Rev": "cbcac7bb8415db9b6cb4d1ebab1dc9afbd688b97"
 -		},
 -		{
 -			"ImportPath": "golang.org/x/net/websocket",
--			"Comment": "null-214",
--			"Rev": "c043f0dc72e4cdd23ae039470ea9d63e6680a1b2"
+-			"Rev": "cbcac7bb8415db9b6cb4d1ebab1dc9afbd688b97"
 -		},
 -		{
 -			"ImportPath": "gopkg.in/v2/yaml",
 -			"Rev": "d466437aa4adc35830964cffc5b5f262c63ddcb4"
+-		},
+-		{
+-			"ImportPath": "speter.net/go/exp/math/dec/inf",
+-			"Rev": "42ca6cd68aa922bc3f32f1e056e61b65945d9ad7"
 -		}
 -	]
 -}
@@ -37674,5538 +38775,5378 @@ index a6b2045..0000000
 -		t.Fatalf("Unmarshal didn't produce same results.\n got: %#v\nwant: %#v\n", v, v2)
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/add_child.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/add_child.go
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/.gitignore b/Godeps/_workspace/src/github.com/Sirupsen/logrus/.gitignore
 deleted file mode 100644
-index 7122be0..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/add_child.go
+index 66be63a..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/.gitignore
 +++ /dev/null
-@@ -1,23 +0,0 @@
--package etcd
--
--// Add a new directory with a random etcd-generated key under the given path.
--func (c *Client) AddChildDir(key string, ttl uint64) (*Response, error) {
--	raw, err := c.post(key, "", ttl)
--
--	if err != nil {
--		return nil, err
--	}
+@@ -1 +0,0 @@
+-logrus
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/.travis.yml b/Godeps/_workspace/src/github.com/Sirupsen/logrus/.travis.yml
+deleted file mode 100644
+index c3af3ce..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/.travis.yml
++++ /dev/null
+@@ -1,10 +0,0 @@
+-language: go
+-go:
+-  - 1.2
+-  - 1.3
+-  - tip
+-install:
+-  - go get github.com/stretchr/testify
+-  - go get github.com/stvp/go-udp-testing
+-  - go get github.com/tobi/airbrake-go
+-  - go get github.com/getsentry/raven-go
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/LICENSE b/Godeps/_workspace/src/github.com/Sirupsen/logrus/LICENSE
+deleted file mode 100644
+index f090cb4..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/LICENSE
++++ /dev/null
+@@ -1,21 +0,0 @@
+-The MIT License (MIT)
 -
--	return raw.Unmarshal()
--}
+-Copyright (c) 2014 Simon Eskildsen
 -
--// Add a new file with a random etcd-generated key under the given path.
--func (c *Client) AddChild(key string, value string, ttl uint64) (*Response, error) {
--	raw, err := c.post(key, value, ttl)
+-Permission is hereby granted, free of charge, to any person obtaining a copy
+-of this software and associated documentation files (the "Software"), to deal
+-in the Software without restriction, including without limitation the rights
+-to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+-copies of the Software, and to permit persons to whom the Software is
+-furnished to do so, subject to the following conditions:
 -
--	if err != nil {
--		return nil, err
--	}
+-The above copyright notice and this permission notice shall be included in
+-all copies or substantial portions of the Software.
 -
--	return raw.Unmarshal()
--}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/add_child_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/add_child_test.go
+-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+-IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+-FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+-AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+-LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+-OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+-THE SOFTWARE.
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/README.md b/Godeps/_workspace/src/github.com/Sirupsen/logrus/README.md
 deleted file mode 100644
-index 26223ff..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/add_child_test.go
+index b6aa84c..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/README.md
 +++ /dev/null
-@@ -1,73 +0,0 @@
--package etcd
+@@ -1,352 +0,0 @@
+-# Logrus <img src="http://i.imgur.com/hTeVwmJ.png" width="40" height="40" alt=":walrus:" class="emoji" title=":walrus:"/>&nbsp;[![Build Status](https://travis-ci.org/Sirupsen/logrus.svg?branch=master)](https://travis-ci.org/Sirupsen/logrus)
 -
--import "testing"
+-Logrus is a structured logger for Go (golang), completely API compatible with
+-the standard library logger. [Godoc][godoc]. **Please note the Logrus API is not
+-yet stable (pre 1.0), the core API is unlikely change much but please version
+-control your Logrus to make sure you aren't fetching latest `master` on every
+-build.**
 -
--func TestAddChild(t *testing.T) {
--	c := NewClient(nil)
--	defer func() {
--		c.Delete("fooDir", true)
--		c.Delete("nonexistentDir", true)
--	}()
+-Nicely color-coded in development (when a TTY is attached, otherwise just
+-plain text):
 -
--	c.CreateDir("fooDir", 5)
+-![Colored](http://i.imgur.com/PY7qMwd.png)
 -
--	_, err := c.AddChild("fooDir", "v0", 5)
--	if err != nil {
--		t.Fatal(err)
--	}
+-With `log.Formatter = new(logrus.JSONFormatter)`, for easy parsing by logstash
+-or Splunk:
 -
--	_, err = c.AddChild("fooDir", "v1", 5)
--	if err != nil {
--		t.Fatal(err)
--	}
+-```json
+-{"animal":"walrus","level":"info","msg":"A group of walrus emerges from the
+-ocean","size":10,"time":"2014-03-10 19:57:38.562264131 -0400 EDT"}
 -
--	resp, err := c.Get("fooDir", true, false)
--	// The child with v0 should proceed the child with v1 because it's added
--	// earlier, so it should have a lower key.
--	if !(len(resp.Node.Nodes) == 2 && (resp.Node.Nodes[0].Value == "v0" && resp.Node.Nodes[1].Value == "v1")) {
--		t.Fatalf("AddChild 1 failed.  There should be two chlidren whose values are v0 and v1, respectively."+
--			"  The response was: %#v", resp)
--	}
+-{"level":"warning","msg":"The group's number increased tremendously!",
+-"number":122,"omg":true,"time":"2014-03-10 19:57:38.562471297 -0400 EDT"}
 -
--	// Creating a child under a nonexistent directory should succeed.
--	// The directory should be created.
--	resp, err = c.AddChild("nonexistentDir", "foo", 5)
--	if err != nil {
--		t.Fatal(err)
--	}
--}
+-{"animal":"walrus","level":"info","msg":"A giant walrus appears!",
+-"size":10,"time":"2014-03-10 19:57:38.562500591 -0400 EDT"}
 -
--func TestAddChildDir(t *testing.T) {
--	c := NewClient(nil)
--	defer func() {
--		c.Delete("fooDir", true)
--		c.Delete("nonexistentDir", true)
--	}()
+-{"animal":"walrus","level":"info","msg":"Tremendously sized cow enters the ocean.",
+-"size":9,"time":"2014-03-10 19:57:38.562527896 -0400 EDT"}
 -
--	c.CreateDir("fooDir", 5)
+-{"level":"fatal","msg":"The ice breaks!","number":100,"omg":true,
+-"time":"2014-03-10 19:57:38.562543128 -0400 EDT"}
+-```
 -
--	_, err := c.AddChildDir("fooDir", 5)
--	if err != nil {
--		t.Fatal(err)
--	}
+-With the default `log.Formatter = new(logrus.TextFormatter)` when a TTY is not
+-attached, the output is compatible with the
+-[l2met](http://r.32k.io/l2met-introduction) format:
 -
--	_, err = c.AddChildDir("fooDir", 5)
--	if err != nil {
--		t.Fatal(err)
--	}
+-```text
+-time="2014-04-20 15:36:23.830442383 -0400 EDT" level="info" msg="A group of walrus emerges from the ocean" animal="walrus" size=10
+-time="2014-04-20 15:36:23.830584199 -0400 EDT" level="warning" msg="The group's number increased tremendously!" omg=true number=122
+-time="2014-04-20 15:36:23.830596521 -0400 EDT" level="info" msg="A giant walrus appears!" animal="walrus" size=10
+-time="2014-04-20 15:36:23.830611837 -0400 EDT" level="info" msg="Tremendously sized cow enters the ocean." animal="walrus" size=9
+-time="2014-04-20 15:36:23.830626464 -0400 EDT" level="fatal" msg="The ice breaks!" omg=true number=100
+-```
 -
--	resp, err := c.Get("fooDir", true, false)
--	// The child with v0 should proceed the child with v1 because it's added
--	// earlier, so it should have a lower key.
--	if !(len(resp.Node.Nodes) == 2 && (len(resp.Node.Nodes[0].Nodes) == 0 && len(resp.Node.Nodes[1].Nodes) == 0)) {
--		t.Fatalf("AddChildDir 1 failed.  There should be two chlidren whose values are v0 and v1, respectively."+
--			"  The response was: %#v", resp)
--	}
+-#### Example
 -
--	// Creating a child under a nonexistent directory should succeed.
--	// The directory should be created.
--	resp, err = c.AddChildDir("nonexistentDir", 5)
--	if err != nil {
--		t.Fatal(err)
--	}
--}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/client.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/client.go
-deleted file mode 100644
-index f6ae548..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/client.go
-+++ /dev/null
-@@ -1,435 +0,0 @@
--package etcd
+-The simplest way to use Logrus is simply the package-level exported logger:
+-
+-```go
+-package main
 -
 -import (
--	"crypto/tls"
--	"crypto/x509"
--	"encoding/json"
--	"errors"
--	"io"
--	"io/ioutil"
--	"net"
--	"net/http"
--	"net/url"
--	"os"
--	"path"
--	"time"
+-  log "github.com/Sirupsen/logrus"
 -)
 -
--// See SetConsistency for how to use these constants.
--const (
--	// Using strings rather than iota because the consistency level
--	// could be persisted to disk, so it'd be better to use
--	// human-readable values.
--	STRONG_CONSISTENCY = "STRONG"
--	WEAK_CONSISTENCY   = "WEAK"
--)
+-func main() {
+-  log.WithFields(log.Fields{
+-    "animal": "walrus",
+-  }).Info("A walrus appears")
+-}
+-```
 -
--const (
--	defaultBufferSize = 10
+-Note that it's completely api-compatible with the stdlib logger, so you can
+-replace your `log` imports everywhere with `log "github.com/Sirupsen/logrus"`
+-and you'll now have the flexibility of Logrus. You can customize it all you
+-want:
+-
+-```go
+-package main
+-
+-import (
+-  "os"
+-  log "github.com/Sirupsen/logrus"
+-  "github.com/Sirupsen/logrus/hooks/airbrake"
 -)
 -
--type Config struct {
--	CertFile    string        `json:"certFile"`
--	KeyFile     string        `json:"keyFile"`
--	CaCertFile  []string      `json:"caCertFiles"`
--	DialTimeout time.Duration `json:"timeout"`
--	Consistency string        `json:"consistency"`
+-func init() {
+-  // Log as JSON instead of the default ASCII formatter.
+-  log.SetFormatter(&log.JSONFormatter{})
+-
+-  // Use the Airbrake hook to report errors that have Error severity or above to
+-  // an exception tracker. You can create custom hooks, see the Hooks section.
+-  log.AddHook(&logrus_airbrake.AirbrakeHook{})
+-
+-  // Output to stderr instead of stdout, could also be a file.
+-  log.SetOutput(os.Stderr)
+-
+-  // Only log the warning severity or above.
+-  log.SetLevel(log.WarnLevel)
 -}
 -
--type Client struct {
--	config      Config   `json:"config"`
--	cluster     *Cluster `json:"cluster"`
--	httpClient  *http.Client
--	persistence io.Writer
--	cURLch      chan string
--	// CheckRetry can be used to control the policy for failed requests
--	// and modify the cluster if needed.
--	// The client calls it before sending requests again, and
--	// stops retrying if CheckRetry returns some error. The cases that
--	// this function needs to handle include no response and unexpected
--	// http status code of response.
--	// If CheckRetry is nil, client will call the default one
--	// `DefaultCheckRetry`.
--	// Argument cluster is the etcd.Cluster object that these requests have been made on.
--	// Argument numReqs is the number of http.Requests that have been made so far.
--	// Argument lastResp is the http.Responses from the last request.
--	// Argument err is the reason of the failure.
--	CheckRetry func(cluster *Cluster, numReqs int,
--		lastResp http.Response, err error) error
+-func main() {
+-  log.WithFields(log.Fields{
+-    "animal": "walrus",
+-    "size":   10,
+-  }).Info("A group of walrus emerges from the ocean")
+-
+-  log.WithFields(log.Fields{
+-    "omg":    true,
+-    "number": 122,
+-  }).Warn("The group's number increased tremendously!")
+-
+-  log.WithFields(log.Fields{
+-    "omg":    true,
+-    "number": 100,
+-  }).Fatal("The ice breaks!")
 -}
+-```
 -
--// NewClient create a basic client that is configured to be used
--// with the given machine list.
--func NewClient(machines []string) *Client {
--	config := Config{
--		// default timeout is one second
--		DialTimeout: time.Second,
--		// default consistency level is STRONG
--		Consistency: STRONG_CONSISTENCY,
--	}
+-For more advanced usage such as logging to multiple locations from the same
+-application, you can also create an instance of the `logrus` Logger:
 -
--	client := &Client{
--		cluster: NewCluster(machines),
--		config:  config,
--	}
+-```go
+-package main
 -
--	client.initHTTPClient()
--	client.saveConfig()
+-import (
+-  "github.com/Sirupsen/logrus"
+-)
 -
--	return client
+-// Create a new instance of the logger. You can have any number of instances.
+-var log = logrus.New()
+-
+-func main() {
+-  // The API for setting attributes is a little different than the package level
+-  // exported logger. See Godoc.
+-  log.Out = os.Stderr
+-
+-  log.WithFields(logrus.Fields{
+-    "animal": "walrus",
+-    "size":   10,
+-  }).Info("A group of walrus emerges from the ocean")
 -}
+-```
 -
--// NewTLSClient create a basic client with TLS configuration
--func NewTLSClient(machines []string, cert, key, caCert string) (*Client, error) {
--	// overwrite the default machine to use https
--	if len(machines) == 0 {
--		machines = []string{"https://127.0.0.1:4001"}
--	}
+-#### Fields
 -
--	config := Config{
--		// default timeout is one second
--		DialTimeout: time.Second,
--		// default consistency level is STRONG
--		Consistency: STRONG_CONSISTENCY,
--		CertFile:    cert,
--		KeyFile:     key,
--		CaCertFile:  make([]string, 0),
--	}
+-Logrus encourages careful, structured logging though logging fields instead of
+-long, unparseable error messages. For example, instead of: `log.Fatalf("Failed
+-to send event %s to topic %s with key %d")`, you should log the much more
+-discoverable:
 -
--	client := &Client{
--		cluster: NewCluster(machines),
--		config:  config,
--	}
+-```go
+-log.WithFields(log.Fields{
+-  "event": event,
+-  "topic": topic,
+-  "key": key,
+-}).Fatal("Failed to send event")
+-```
 -
--	err := client.initHTTPSClient(cert, key)
--	if err != nil {
--		return nil, err
--	}
+-We've found this API forces you to think about logging in a way that produces
+-much more useful logging messages. We've been in countless situations where just
+-a single added field to a log statement that was already there would've saved us
+-hours. The `WithFields` call is optional.
 -
--	err = client.AddRootCA(caCert)
+-In general, with Logrus using any of the `printf`-family functions should be
+-seen as a hint you should add a field, however, you can still use the
+-`printf`-family functions with Logrus.
 -
--	client.saveConfig()
+-#### Hooks
 -
--	return client, nil
+-You can add hooks for logging levels. For example to send errors to an exception
+-tracking service on `Error`, `Fatal` and `Panic`, info to StatsD or log to
+-multiple places simultaneously, e.g. syslog.
+-
+-```go
+-// Not the real implementation of the Airbrake hook. Just a simple sample.
+-import (
+-  log "github.com/Sirupsen/logrus"
+-)
+-
+-func init() {
+-  log.AddHook(new(AirbrakeHook))
 -}
 -
--// NewClientFromFile creates a client from a given file path.
--// The given file is expected to use the JSON format.
--func NewClientFromFile(fpath string) (*Client, error) {
--	fi, err := os.Open(fpath)
--	if err != nil {
--		return nil, err
--	}
+-type AirbrakeHook struct{}
 -
--	defer func() {
--		if err := fi.Close(); err != nil {
--			panic(err)
--		}
--	}()
+-// `Fire()` takes the entry that the hook is fired for. `entry.Data[]` contains
+-// the fields for the entry. See the Fields section of the README.
+-func (hook *AirbrakeHook) Fire(entry *logrus.Entry) error {
+-  err := airbrake.Notify(entry.Data["error"].(error))
+-  if err != nil {
+-    log.WithFields(log.Fields{
+-      "source":   "airbrake",
+-      "endpoint": airbrake.Endpoint,
+-    }).Info("Failed to send error to Airbrake")
+-  }
 -
--	return NewClientFromReader(fi)
+-  return nil
 -}
 -
--// NewClientFromReader creates a Client configured from a given reader.
--// The configuration is expected to use the JSON format.
--func NewClientFromReader(reader io.Reader) (*Client, error) {
--	c := new(Client)
+-// `Levels()` returns a slice of `Levels` the hook is fired for.
+-func (hook *AirbrakeHook) Levels() []log.Level {
+-  return []log.Level{
+-    log.ErrorLevel,
+-    log.FatalLevel,
+-    log.PanicLevel,
+-  }
+-}
+-```
 -
--	b, err := ioutil.ReadAll(reader)
--	if err != nil {
--		return nil, err
--	}
+-Logrus comes with built-in hooks. Add those, or your custom hook, in `init`:
 -
--	err = json.Unmarshal(b, c)
--	if err != nil {
--		return nil, err
--	}
--	if c.config.CertFile == "" {
--		c.initHTTPClient()
--	} else {
--		err = c.initHTTPSClient(c.config.CertFile, c.config.KeyFile)
--	}
+-```go
+-import (
+-  log "github.com/Sirupsen/logrus"
+-  "github.com/Sirupsen/logrus/hooks/airbrake"
+-  "github.com/Sirupsen/logrus/hooks/syslog"
+-  "log/syslog"
+-)
 -
--	if err != nil {
--		return nil, err
--	}
+-func init() {
+-  log.AddHook(new(logrus_airbrake.AirbrakeHook))
 -
--	for _, caCert := range c.config.CaCertFile {
--		if err := c.AddRootCA(caCert); err != nil {
--			return nil, err
--		}
--	}
+-  hook, err := logrus_syslog.NewSyslogHook("udp", "localhost:514", syslog.LOG_INFO, "")
+-  if err != nil {
+-    log.Error("Unable to connect to local syslog daemon")
+-  } else {
+-    log.AddHook(hook)
+-  }
+-}
+-```
 -
--	return c, nil
+-* [`github.com/Sirupsen/logrus/hooks/airbrake`](https://github.com/Sirupsen/logrus/blob/master/hooks/airbrake/airbrake.go)
+-  Send errors to an exception tracking service compatible with the Airbrake API.
+-  Uses [`airbrake-go`](https://github.com/tobi/airbrake-go) behind the scenes.
+-
+-* [`github.com/Sirupsen/logrus/hooks/papertrail`](https://github.com/Sirupsen/logrus/blob/master/hooks/papertrail/papertrail.go)
+-  Send errors to the Papertrail hosted logging service via UDP.
+-
+-* [`github.com/Sirupsen/logrus/hooks/syslog`](https://github.com/Sirupsen/logrus/blob/master/hooks/syslog/syslog.go)
+-  Send errors to remote syslog server.
+-  Uses standard library `log/syslog` behind the scenes.
+-
+-* [`github.com/nubo/hiprus`](https://github.com/nubo/hiprus)
+-  Send errors to a channel in hipchat.
+-
+-* [`github.com/sebest/logrusly`](https://github.com/sebest/logrusly)
+-  Send logs to Loggly (https://www.loggly.com/)
+-
+-#### Level logging
+-
+-Logrus has six logging levels: Debug, Info, Warning, Error, Fatal and Panic.
+-
+-```go
+-log.Debug("Useful debugging information.")
+-log.Info("Something noteworthy happened!")
+-log.Warn("You should probably take a look at this.")
+-log.Error("Something failed but I'm not quitting.")
+-// Calls os.Exit(1) after logging
+-log.Fatal("Bye.")
+-// Calls panic() after logging
+-log.Panic("I'm bailing.")
+-```
+-
+-You can set the logging level on a `Logger`, then it will only log entries with
+-that severity or anything above it:
+-
+-```go
+-// Will log anything that is info or above (warn, error, fatal, panic). Default.
+-log.SetLevel(log.InfoLevel)
+-```
+-
+-It may be useful to set `log.Level = logrus.DebugLevel` in a debug or verbose
+-environment if your application has that.
+-
+-#### Entries
+-
+-Besides the fields added with `WithField` or `WithFields` some fields are
+-automatically added to all logging events:
+-
+-1. `time`. The timestamp when the entry was created.
+-2. `msg`. The logging message passed to `{Info,Warn,Error,Fatal,Panic}` after
+-   the `AddFields` call. E.g. `Failed to send event.`
+-3. `level`. The logging level. E.g. `info`.
+-
+-#### Environments
+-
+-Logrus has no notion of environment.
+-
+-If you wish for hooks and formatters to only be used in specific environments,
+-you should handle that yourself. For example, if your application has a global
+-variable `Environment`, which is a string representation of the environment you
+-could do:
+-
+-```go
+-import (
+-  log "github.com/Sirupsen/logrus"
+-)
+-
+-init() {
+-  // do something here to set environment depending on an environment variable
+-  // or command-line flag
+-  if Environment == "production" {
+-    log.SetFormatter(logrus.JSONFormatter)
+-  } else {
+-    // The TextFormatter is default, you don't actually have to do this.
+-    log.SetFormatter(logrus.TextFormatter)
+-  }
 -}
+-```
 -
--// Override the Client's HTTP Transport object
--func (c *Client) SetTransport(tr *http.Transport) {
--	c.httpClient.Transport = tr
+-This configuration is how `logrus` was intended to be used, but JSON in
+-production is mostly only useful if you do log aggregation with tools like
+-Splunk or Logstash.
+-
+-#### Formatters
+-
+-The built-in logging formatters are:
+-
+-* `logrus.TextFormatter`. Logs the event in colors if stdout is a tty, otherwise
+-  without colors.
+-  * *Note:* to force colored output when there is no TTY, set the `ForceColors`
+-    field to `true`.  To force no colored output even if there is a TTY  set the
+-    `DisableColors` field to `true`
+-* `logrus.JSONFormatter`. Logs fields as JSON.
+-
+-Third party logging formatters:
+-
+-* [`zalgo`](https://github.com/aybabtme/logzalgo): invoking the P͉̫o̳̼̊w̖͈̰͎e̬͔̭͂r͚̼̹̲ ̫͓͉̳͈ō̠͕͖̚f̝͍̠ ͕̲̞͖͑Z̖̫̤̫ͪa͉̬͈̗l͖͎g̳̥o̰̥̅!̣͔̲̻͊̄ ̙̘̦̹̦.
+-
+-You can define your formatter by implementing the `Formatter` interface,
+-requiring a `Format` method. `Format` takes an `*Entry`. `entry.Data` is a
+-`Fields` type (`map[string]interface{}`) with all your fields as well as the
+-default ones (see Entries section above):
+-
+-```go
+-type MyJSONFormatter struct {
 -}
 -
--// initHTTPClient initializes a HTTP client for etcd client
--func (c *Client) initHTTPClient() {
--	tr := &http.Transport{
--		Dial: c.dial,
--		TLSClientConfig: &tls.Config{
--			InsecureSkipVerify: true,
--		},
--	}
--	c.httpClient = &http.Client{Transport: tr}
+-log.SetFormatter(new(MyJSONFormatter))
+-
+-func (f *JSONFormatter) Format(entry *Entry) ([]byte, error) {
+-  // Note this doesn't include Time, Level and Message which are available on
+-  // the Entry. Consult `godoc` on information about those fields or read the
+-  // source of the official loggers.
+-  serialized, err := json.Marshal(entry.Data)
+-    if err != nil {
+-      return nil, fmt.Errorf("Failed to marshal fields to JSON, %v", err)
+-    }
+-  return append(serialized, '\n'), nil
 -}
+-```
 -
--// initHTTPClient initializes a HTTPS client for etcd client
--func (c *Client) initHTTPSClient(cert, key string) error {
--	if cert == "" || key == "" {
--		return errors.New("Require both cert and key path")
--	}
+-#### Rotation
 -
--	tlsCert, err := tls.LoadX509KeyPair(cert, key)
--	if err != nil {
--		return err
--	}
+-Log rotation is not provided with Logrus. Log rotation should be done by an
+-external program (like `logrotated(8)`) that can compress and delete old log
+-entries. It should not be a feature of the application-level logger.
 -
--	tlsConfig := &tls.Config{
--		Certificates:       []tls.Certificate{tlsCert},
--		InsecureSkipVerify: true,
+-
+-[godoc]: https://godoc.org/github.com/Sirupsen/logrus
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/entry.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/entry.go
+deleted file mode 100644
+index e164eec..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/entry.go
++++ /dev/null
+@@ -1,248 +0,0 @@
+-package logrus
+-
+-import (
+-	"bytes"
+-	"fmt"
+-	"io"
+-	"os"
+-	"time"
+-)
+-
+-// An entry is the final or intermediate Logrus logging entry. It contains all
+-// the fields passed with WithField{,s}. It's finally logged when Debug, Info,
+-// Warn, Error, Fatal or Panic is called on it. These objects can be reused and
+-// passed around as much as you wish to avoid field duplication.
+-type Entry struct {
+-	Logger *Logger
+-
+-	// Contains all the fields set by the user.
+-	Data Fields
+-
+-	// Time at which the log entry was created
+-	Time time.Time
+-
+-	// Level the log entry was logged at: Debug, Info, Warn, Error, Fatal or Panic
+-	Level Level
+-
+-	// Message passed to Debug, Info, Warn, Error, Fatal or Panic
+-	Message string
+-}
+-
+-func NewEntry(logger *Logger) *Entry {
+-	return &Entry{
+-		Logger: logger,
+-		// Default is three fields, give a little extra room
+-		Data: make(Fields, 5),
 -	}
+-}
 -
--	tr := &http.Transport{
--		TLSClientConfig: tlsConfig,
--		Dial:            c.dial,
+-// Returns a reader for the entry, which is a proxy to the formatter.
+-func (entry *Entry) Reader() (*bytes.Buffer, error) {
+-	serialized, err := entry.Logger.Formatter.Format(entry)
+-	return bytes.NewBuffer(serialized), err
+-}
+-
+-// Returns the string representation from the reader and ultimately the
+-// formatter.
+-func (entry *Entry) String() (string, error) {
+-	reader, err := entry.Reader()
+-	if err != nil {
+-		return "", err
 -	}
 -
--	c.httpClient = &http.Client{Transport: tr}
--	return nil
+-	return reader.String(), err
 -}
 -
--// SetPersistence sets a writer to which the config will be
--// written every time it's changed.
--func (c *Client) SetPersistence(writer io.Writer) {
--	c.persistence = writer
+-// Add a single field to the Entry.
+-func (entry *Entry) WithField(key string, value interface{}) *Entry {
+-	return entry.WithFields(Fields{key: value})
 -}
 -
--// SetConsistency changes the consistency level of the client.
--//
--// When consistency is set to STRONG_CONSISTENCY, all requests,
--// including GET, are sent to the leader.  This means that, assuming
--// the absence of leader failures, GET requests are guaranteed to see
--// the changes made by previous requests.
--//
--// When consistency is set to WEAK_CONSISTENCY, other requests
--// are still sent to the leader, but GET requests are sent to a
--// random server from the server pool.  This reduces the read
--// load on the leader, but it's not guaranteed that the GET requests
--// will see changes made by previous requests (they might have not
--// yet been committed on non-leader servers).
--func (c *Client) SetConsistency(consistency string) error {
--	if !(consistency == STRONG_CONSISTENCY || consistency == WEAK_CONSISTENCY) {
--		return errors.New("The argument must be either STRONG_CONSISTENCY or WEAK_CONSISTENCY.")
+-// Add a map of fields to the Entry.
+-func (entry *Entry) WithFields(fields Fields) *Entry {
+-	data := Fields{}
+-	for k, v := range entry.Data {
+-		data[k] = v
 -	}
--	c.config.Consistency = consistency
--	return nil
+-	for k, v := range fields {
+-		data[k] = v
+-	}
+-	return &Entry{Logger: entry.Logger, Data: data}
 -}
 -
--// Sets the DialTimeout value
--func (c *Client) SetDialTimeout(d time.Duration) {
--	c.config.DialTimeout = d
--}
+-func (entry *Entry) log(level Level, msg string) {
+-	entry.Time = time.Now()
+-	entry.Level = level
+-	entry.Message = msg
 -
--// AddRootCA adds a root CA cert for the etcd client
--func (c *Client) AddRootCA(caCert string) error {
--	if c.httpClient == nil {
--		return errors.New("Client has not been initialized yet!")
+-	if err := entry.Logger.Hooks.Fire(level, entry); err != nil {
+-		entry.Logger.mu.Lock()
+-		fmt.Fprintf(os.Stderr, "Failed to fire hook: %v\n", err)
+-		entry.Logger.mu.Unlock()
 -	}
 -
--	certBytes, err := ioutil.ReadFile(caCert)
+-	reader, err := entry.Reader()
 -	if err != nil {
--		return err
+-		entry.Logger.mu.Lock()
+-		fmt.Fprintf(os.Stderr, "Failed to obtain reader, %v\n", err)
+-		entry.Logger.mu.Unlock()
 -	}
 -
--	tr, ok := c.httpClient.Transport.(*http.Transport)
+-	entry.Logger.mu.Lock()
+-	defer entry.Logger.mu.Unlock()
 -
--	if !ok {
--		panic("AddRootCA(): Transport type assert should not fail")
+-	_, err = io.Copy(entry.Logger.Out, reader)
+-	if err != nil {
+-		fmt.Fprintf(os.Stderr, "Failed to write to log, %v\n", err)
 -	}
 -
--	if tr.TLSClientConfig.RootCAs == nil {
--		caCertPool := x509.NewCertPool()
--		ok = caCertPool.AppendCertsFromPEM(certBytes)
--		if ok {
--			tr.TLSClientConfig.RootCAs = caCertPool
--		}
--		tr.TLSClientConfig.InsecureSkipVerify = false
--	} else {
--		ok = tr.TLSClientConfig.RootCAs.AppendCertsFromPEM(certBytes)
+-	// To avoid Entry#log() returning a value that only would make sense for
+-	// panic() to use in Entry#Panic(), we avoid the allocation by checking
+-	// directly here.
+-	if level <= PanicLevel {
+-		panic(entry)
 -	}
+-}
 -
--	if !ok {
--		err = errors.New("Unable to load caCert")
+-func (entry *Entry) Debug(args ...interface{}) {
+-	if entry.Logger.Level >= DebugLevel {
+-		entry.log(DebugLevel, fmt.Sprint(args...))
 -	}
+-}
 -
--	c.config.CaCertFile = append(c.config.CaCertFile, caCert)
--	c.saveConfig()
--
--	return err
+-func (entry *Entry) Print(args ...interface{}) {
+-	entry.Info(args...)
 -}
 -
--// SetCluster updates cluster information using the given machine list.
--func (c *Client) SetCluster(machines []string) bool {
--	success := c.internalSyncCluster(machines)
--	return success
+-func (entry *Entry) Info(args ...interface{}) {
+-	if entry.Logger.Level >= InfoLevel {
+-		entry.log(InfoLevel, fmt.Sprint(args...))
+-	}
 -}
 -
--func (c *Client) GetCluster() []string {
--	return c.cluster.Machines
+-func (entry *Entry) Warn(args ...interface{}) {
+-	if entry.Logger.Level >= WarnLevel {
+-		entry.log(WarnLevel, fmt.Sprint(args...))
+-	}
 -}
 -
--// SyncCluster updates the cluster information using the internal machine list.
--func (c *Client) SyncCluster() bool {
--	return c.internalSyncCluster(c.cluster.Machines)
+-func (entry *Entry) Error(args ...interface{}) {
+-	if entry.Logger.Level >= ErrorLevel {
+-		entry.log(ErrorLevel, fmt.Sprint(args...))
+-	}
 -}
 -
--// internalSyncCluster syncs cluster information using the given machine list.
--func (c *Client) internalSyncCluster(machines []string) bool {
--	for _, machine := range machines {
--		httpPath := c.createHttpPath(machine, path.Join(version, "machines"))
--		resp, err := c.httpClient.Get(httpPath)
--		if err != nil {
--			// try another machine in the cluster
--			continue
--		} else {
--			b, err := ioutil.ReadAll(resp.Body)
--			resp.Body.Close()
--			if err != nil {
--				// try another machine in the cluster
--				continue
--			}
+-func (entry *Entry) Fatal(args ...interface{}) {
+-	if entry.Logger.Level >= FatalLevel {
+-		entry.log(FatalLevel, fmt.Sprint(args...))
+-	}
+-	os.Exit(1)
+-}
 -
--			// update Machines List
--			c.cluster.updateFromStr(string(b))
+-func (entry *Entry) Panic(args ...interface{}) {
+-	if entry.Logger.Level >= PanicLevel {
+-		entry.log(PanicLevel, fmt.Sprint(args...))
+-	}
+-	panic(fmt.Sprint(args...))
+-}
 -
--			// update leader
--			// the first one in the machine list is the leader
--			c.cluster.switchLeader(0)
+-// Entry Printf family functions
 -
--			logger.Debug("sync.machines ", c.cluster.Machines)
--			c.saveConfig()
--			return true
--		}
+-func (entry *Entry) Debugf(format string, args ...interface{}) {
+-	if entry.Logger.Level >= DebugLevel {
+-		entry.Debug(fmt.Sprintf(format, args...))
 -	}
--	return false
 -}
 -
--// createHttpPath creates a complete HTTP URL.
--// serverName should contain both the host name and a port number, if any.
--func (c *Client) createHttpPath(serverName string, _path string) string {
--	u, err := url.Parse(serverName)
--	if err != nil {
--		panic(err)
+-func (entry *Entry) Infof(format string, args ...interface{}) {
+-	if entry.Logger.Level >= InfoLevel {
+-		entry.Info(fmt.Sprintf(format, args...))
 -	}
+-}
 -
--	u.Path = path.Join(u.Path, _path)
+-func (entry *Entry) Printf(format string, args ...interface{}) {
+-	entry.Infof(format, args...)
+-}
 -
--	if u.Scheme == "" {
--		u.Scheme = "http"
+-func (entry *Entry) Warnf(format string, args ...interface{}) {
+-	if entry.Logger.Level >= WarnLevel {
+-		entry.Warn(fmt.Sprintf(format, args...))
 -	}
--	return u.String()
 -}
 -
--// dial attempts to open a TCP connection to the provided address, explicitly
--// enabling keep-alives with a one-second interval.
--func (c *Client) dial(network, addr string) (net.Conn, error) {
--	conn, err := net.DialTimeout(network, addr, c.config.DialTimeout)
--	if err != nil {
--		return nil, err
--	}
+-func (entry *Entry) Warningf(format string, args ...interface{}) {
+-	entry.Warnf(format, args...)
+-}
 -
--	tcpConn, ok := conn.(*net.TCPConn)
--	if !ok {
--		return nil, errors.New("Failed type-assertion of net.Conn as *net.TCPConn")
+-func (entry *Entry) Errorf(format string, args ...interface{}) {
+-	if entry.Logger.Level >= ErrorLevel {
+-		entry.Error(fmt.Sprintf(format, args...))
 -	}
+-}
 -
--	// Keep TCP alive to check whether or not the remote machine is down
--	if err = tcpConn.SetKeepAlive(true); err != nil {
--		return nil, err
+-func (entry *Entry) Fatalf(format string, args ...interface{}) {
+-	if entry.Logger.Level >= FatalLevel {
+-		entry.Fatal(fmt.Sprintf(format, args...))
 -	}
+-}
 -
--	if err = tcpConn.SetKeepAlivePeriod(time.Second); err != nil {
--		return nil, err
+-func (entry *Entry) Panicf(format string, args ...interface{}) {
+-	if entry.Logger.Level >= PanicLevel {
+-		entry.Panic(fmt.Sprintf(format, args...))
 -	}
--
--	return tcpConn, nil
 -}
 -
--func (c *Client) OpenCURL() {
--	c.cURLch = make(chan string, defaultBufferSize)
--}
+-// Entry Println family functions
 -
--func (c *Client) CloseCURL() {
--	c.cURLch = nil
+-func (entry *Entry) Debugln(args ...interface{}) {
+-	if entry.Logger.Level >= DebugLevel {
+-		entry.Debug(entry.sprintlnn(args...))
+-	}
 -}
 -
--func (c *Client) sendCURL(command string) {
--	go func() {
--		select {
--		case c.cURLch <- command:
--		default:
--		}
--	}()
+-func (entry *Entry) Infoln(args ...interface{}) {
+-	if entry.Logger.Level >= InfoLevel {
+-		entry.Info(entry.sprintlnn(args...))
+-	}
 -}
 -
--func (c *Client) RecvCURL() string {
--	return <-c.cURLch
+-func (entry *Entry) Println(args ...interface{}) {
+-	entry.Infoln(args...)
 -}
 -
--// saveConfig saves the current config using c.persistence.
--func (c *Client) saveConfig() error {
--	if c.persistence != nil {
--		b, err := json.Marshal(c)
--		if err != nil {
--			return err
--		}
--
--		_, err = c.persistence.Write(b)
--		if err != nil {
--			return err
--		}
+-func (entry *Entry) Warnln(args ...interface{}) {
+-	if entry.Logger.Level >= WarnLevel {
+-		entry.Warn(entry.sprintlnn(args...))
 -	}
--
--	return nil
 -}
 -
--// MarshalJSON implements the Marshaller interface
--// as defined by the standard JSON package.
--func (c *Client) MarshalJSON() ([]byte, error) {
--	b, err := json.Marshal(struct {
--		Config  Config   `json:"config"`
--		Cluster *Cluster `json:"cluster"`
--	}{
--		Config:  c.config,
--		Cluster: c.cluster,
--	})
+-func (entry *Entry) Warningln(args ...interface{}) {
+-	entry.Warnln(args...)
+-}
 -
--	if err != nil {
--		return nil, err
+-func (entry *Entry) Errorln(args ...interface{}) {
+-	if entry.Logger.Level >= ErrorLevel {
+-		entry.Error(entry.sprintlnn(args...))
 -	}
+-}
 -
--	return b, nil
+-func (entry *Entry) Fatalln(args ...interface{}) {
+-	if entry.Logger.Level >= FatalLevel {
+-		entry.Fatal(entry.sprintlnn(args...))
+-	}
 -}
 -
--// UnmarshalJSON implements the Unmarshaller interface
--// as defined by the standard JSON package.
--func (c *Client) UnmarshalJSON(b []byte) error {
--	temp := struct {
--		Config  Config   `json:"config"`
--		Cluster *Cluster `json:"cluster"`
--	}{}
--	err := json.Unmarshal(b, &temp)
--	if err != nil {
--		return err
+-func (entry *Entry) Panicln(args ...interface{}) {
+-	if entry.Logger.Level >= PanicLevel {
+-		entry.Panic(entry.sprintlnn(args...))
 -	}
+-}
 -
--	c.cluster = temp.Cluster
--	c.config = temp.Config
--	return nil
+-// Sprintlnn => Sprint no newline. This is to get the behavior of how
+-// fmt.Sprintln where spaces are always added between operands, regardless of
+-// their type. Instead of vendoring the Sprintln implementation to spare a
+-// string allocation, we do the simplest thing.
+-func (entry *Entry) sprintlnn(args ...interface{}) string {
+-	msg := fmt.Sprintln(args...)
+-	return msg[:len(msg)-1]
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/client_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/client_test.go
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/entry_test.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/entry_test.go
 deleted file mode 100644
-index c245e47..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/client_test.go
+index 98717df..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/entry_test.go
 +++ /dev/null
-@@ -1,96 +0,0 @@
--package etcd
+@@ -1,53 +0,0 @@
+-package logrus
 -
 -import (
--	"encoding/json"
+-	"bytes"
 -	"fmt"
--	"net"
--	"net/url"
--	"os"
 -	"testing"
--)
 -
--// To pass this test, we need to create a cluster of 3 machines
--// The server should be listening on 127.0.0.1:4001, 4002, 4003
--func TestSync(t *testing.T) {
--	fmt.Println("Make sure there are three nodes at 0.0.0.0:4001-4003")
+-	"github.com/stretchr/testify/assert"
+-)
 -
--	// Explicit trailing slash to ensure this doesn't reproduce:
--	// https://github.com/coreos/go-etcd/issues/82
--	c := NewClient([]string{"http://127.0.0.1:4001/"})
+-func TestEntryPanicln(t *testing.T) {
+-	errBoom := fmt.Errorf("boom time")
 -
--	success := c.SyncCluster()
--	if !success {
--		t.Fatal("cannot sync machines")
--	}
+-	defer func() {
+-		p := recover()
+-		assert.NotNil(t, p)
 -
--	for _, m := range c.GetCluster() {
--		u, err := url.Parse(m)
--		if err != nil {
--			t.Fatal(err)
--		}
--		if u.Scheme != "http" {
--			t.Fatal("scheme must be http")
+-		switch pVal := p.(type) {
+-		case *Entry:
+-			assert.Equal(t, "kaboom", pVal.Message)
+-			assert.Equal(t, errBoom, pVal.Data["err"])
+-		default:
+-			t.Fatalf("want type *Entry, got %T: %#v", pVal, pVal)
 -		}
+-	}()
 -
--		host, _, err := net.SplitHostPort(u.Host)
--		if err != nil {
--			t.Fatal(err)
--		}
--		if host != "127.0.0.1" {
--			t.Fatal("Host must be 127.0.0.1")
--		}
--	}
+-	logger := New()
+-	logger.Out = &bytes.Buffer{}
+-	entry := NewEntry(logger)
+-	entry.WithField("err", errBoom).Panicln("kaboom")
+-}
 -
--	badMachines := []string{"abc", "edef"}
+-func TestEntryPanicf(t *testing.T) {
+-	errBoom := fmt.Errorf("boom again")
 -
--	success = c.SetCluster(badMachines)
+-	defer func() {
+-		p := recover()
+-		assert.NotNil(t, p)
 -
--	if success {
--		t.Fatal("should not sync on bad machines")
--	}
+-		switch pVal := p.(type) {
+-		case *Entry:
+-			assert.Equal(t, "kaboom true", pVal.Message)
+-			assert.Equal(t, errBoom, pVal.Data["err"])
+-		default:
+-			t.Fatalf("want type *Entry, got %T: %#v", pVal, pVal)
+-		}
+-	}()
 -
--	goodMachines := []string{"127.0.0.1:4002"}
+-	logger := New()
+-	logger.Out = &bytes.Buffer{}
+-	entry := NewEntry(logger)
+-	entry.WithField("err", errBoom).Panicf("kaboom %v", true)
+-}
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/examples/basic/basic.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/examples/basic/basic.go
+deleted file mode 100644
+index a62ba45..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/examples/basic/basic.go
++++ /dev/null
+@@ -1,40 +0,0 @@
+-package main
 -
--	success = c.SetCluster(goodMachines)
+-import (
+-	"github.com/Sirupsen/logrus"
+-)
 -
--	if !success {
--		t.Fatal("cannot sync machines")
--	} else {
--		fmt.Println(c.cluster.Machines)
--	}
+-var log = logrus.New()
 -
+-func init() {
+-	log.Formatter = new(logrus.JSONFormatter)
+-	log.Formatter = new(logrus.TextFormatter) // default
 -}
 -
--func TestPersistence(t *testing.T) {
--	c := NewClient(nil)
--	c.SyncCluster()
--
--	fo, err := os.Create("config.json")
--	if err != nil {
--		t.Fatal(err)
--	}
+-func main() {
 -	defer func() {
--		if err := fo.Close(); err != nil {
--			panic(err)
+-		err := recover()
+-		if err != nil {
+-			log.WithFields(logrus.Fields{
+-				"omg":    true,
+-				"err":    err,
+-				"number": 100,
+-			}).Fatal("The ice breaks!")
 -		}
 -	}()
 -
--	c.SetPersistence(fo)
--	err = c.saveConfig()
--	if err != nil {
--		t.Fatal(err)
--	}
--
--	c2, err := NewClientFromFile("config.json")
--	if err != nil {
--		t.Fatal(err)
--	}
+-	log.WithFields(logrus.Fields{
+-		"animal": "walrus",
+-		"size":   10,
+-	}).Info("A group of walrus emerges from the ocean")
 -
--	// Verify that the two clients have the same config
--	b1, _ := json.Marshal(c)
--	b2, _ := json.Marshal(c2)
+-	log.WithFields(logrus.Fields{
+-		"omg":    true,
+-		"number": 122,
+-	}).Warn("The group's number increased tremendously!")
 -
--	if string(b1) != string(b2) {
--		t.Fatalf("The two configs should be equal!")
--	}
+-	log.WithFields(logrus.Fields{
+-		"animal": "orca",
+-		"size":   9009,
+-	}).Panic("It's over 9000!")
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/cluster.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/cluster.go
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/examples/hook/hook.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/examples/hook/hook.go
 deleted file mode 100644
-index aaa2054..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/cluster.go
+index 42e7a4c..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/examples/hook/hook.go
 +++ /dev/null
-@@ -1,51 +0,0 @@
--package etcd
+@@ -1,35 +0,0 @@
+-package main
 -
 -import (
--	"net/url"
--	"strings"
+-	"github.com/Sirupsen/logrus"
+-	"github.com/Sirupsen/logrus/hooks/airbrake"
+-	"github.com/tobi/airbrake-go"
 -)
 -
--type Cluster struct {
--	Leader   string   `json:"leader"`
--	Machines []string `json:"machines"`
+-var log = logrus.New()
+-
+-func init() {
+-	log.Formatter = new(logrus.TextFormatter) // default
+-	log.Hooks.Add(new(logrus_airbrake.AirbrakeHook))
 -}
 -
--func NewCluster(machines []string) *Cluster {
--	// if an empty slice was sent in then just assume HTTP 4001 on localhost
--	if len(machines) == 0 {
--		machines = []string{"http://127.0.0.1:4001"}
--	}
+-func main() {
+-	airbrake.Endpoint = "https://exceptions.whatever.com/notifier_api/v2/notices.xml"
+-	airbrake.ApiKey = "whatever"
+-	airbrake.Environment = "production"
 -
--	// default leader and machines
--	return &Cluster{
--		Leader:   machines[0],
--		Machines: machines,
--	}
--}
+-	log.WithFields(logrus.Fields{
+-		"animal": "walrus",
+-		"size":   10,
+-	}).Info("A group of walrus emerges from the ocean")
 -
--// switchLeader switch the current leader to machines[num]
--func (cl *Cluster) switchLeader(num int) {
--	logger.Debugf("switch.leader[from %v to %v]",
--		cl.Leader, cl.Machines[num])
+-	log.WithFields(logrus.Fields{
+-		"omg":    true,
+-		"number": 122,
+-	}).Warn("The group's number increased tremendously!")
 -
--	cl.Leader = cl.Machines[num]
+-	log.WithFields(logrus.Fields{
+-		"omg":    true,
+-		"number": 100,
+-	}).Fatal("The ice breaks!")
 -}
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/exported.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/exported.go
+deleted file mode 100644
+index d087124..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/exported.go
++++ /dev/null
+@@ -1,182 +0,0 @@
+-package logrus
 -
--func (cl *Cluster) updateFromStr(machines string) {
--	cl.Machines = strings.Split(machines, ", ")
--}
+-import (
+-	"io"
+-)
 -
--func (cl *Cluster) updateLeader(leader string) {
--	logger.Debugf("update.leader[%s,%s]", cl.Leader, leader)
--	cl.Leader = leader
+-var (
+-	// std is the name of the standard logger in stdlib `log`
+-	std = New()
+-)
+-
+-// SetOutput sets the standard logger output.
+-func SetOutput(out io.Writer) {
+-	std.mu.Lock()
+-	defer std.mu.Unlock()
+-	std.Out = out
 -}
 -
--func (cl *Cluster) updateLeaderFromURL(u *url.URL) {
--	var leader string
--	if u.Scheme == "" {
--		leader = "http://" + u.Host
--	} else {
--		leader = u.Scheme + "://" + u.Host
--	}
--	cl.updateLeader(leader)
+-// SetFormatter sets the standard logger formatter.
+-func SetFormatter(formatter Formatter) {
+-	std.mu.Lock()
+-	defer std.mu.Unlock()
+-	std.Formatter = formatter
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_delete.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_delete.go
-deleted file mode 100644
-index 11131bb..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_delete.go
-+++ /dev/null
-@@ -1,34 +0,0 @@
--package etcd
 -
--import "fmt"
+-// SetLevel sets the standard logger level.
+-func SetLevel(level Level) {
+-	std.mu.Lock()
+-	defer std.mu.Unlock()
+-	std.Level = level
+-}
 -
--func (c *Client) CompareAndDelete(key string, prevValue string, prevIndex uint64) (*Response, error) {
--	raw, err := c.RawCompareAndDelete(key, prevValue, prevIndex)
--	if err != nil {
--		return nil, err
--	}
+-// GetLevel returns the standard logger level.
+-func GetLevel() Level {
+-	return std.Level
+-}
 -
--	return raw.Unmarshal()
+-// AddHook adds a hook to the standard logger hooks.
+-func AddHook(hook Hook) {
+-	std.mu.Lock()
+-	defer std.mu.Unlock()
+-	std.Hooks.Add(hook)
 -}
 -
--func (c *Client) RawCompareAndDelete(key string, prevValue string, prevIndex uint64) (*RawResponse, error) {
--	if prevValue == "" && prevIndex == 0 {
--		return nil, fmt.Errorf("You must give either prevValue or prevIndex.")
--	}
+-// WithField creates an entry from the standard logger and adds a field to
+-// it. If you want multiple fields, use `WithFields`.
+-//
+-// Note that it doesn't log until you call Debug, Print, Info, Warn, Fatal
+-// or Panic on the Entry it returns.
+-func WithField(key string, value interface{}) *Entry {
+-	return std.WithField(key, value)
+-}
 -
--	options := Options{}
--	if prevValue != "" {
--		options["prevValue"] = prevValue
--	}
--	if prevIndex != 0 {
--		options["prevIndex"] = prevIndex
--	}
+-// WithFields creates an entry from the standard logger and adds multiple
+-// fields to it. This is simply a helper for `WithField`, invoking it
+-// once for each field.
+-//
+-// Note that it doesn't log until you call Debug, Print, Info, Warn, Fatal
+-// or Panic on the Entry it returns.
+-func WithFields(fields Fields) *Entry {
+-	return std.WithFields(fields)
+-}
 -
--	raw, err := c.delete(key, options)
+-// Debug logs a message at level Debug on the standard logger.
+-func Debug(args ...interface{}) {
+-	std.Debug(args...)
+-}
 -
--	if err != nil {
--		return nil, err
--	}
+-// Print logs a message at level Info on the standard logger.
+-func Print(args ...interface{}) {
+-	std.Print(args...)
+-}
 -
--	return raw, err
+-// Info logs a message at level Info on the standard logger.
+-func Info(args ...interface{}) {
+-	std.Info(args...)
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_delete_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_delete_test.go
-deleted file mode 100644
-index 223e50f..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_delete_test.go
-+++ /dev/null
-@@ -1,46 +0,0 @@
--package etcd
 -
--import (
--	"testing"
--)
+-// Warn logs a message at level Warn on the standard logger.
+-func Warn(args ...interface{}) {
+-	std.Warn(args...)
+-}
 -
--func TestCompareAndDelete(t *testing.T) {
--	c := NewClient(nil)
--	defer func() {
--		c.Delete("foo", true)
--	}()
+-// Warning logs a message at level Warn on the standard logger.
+-func Warning(args ...interface{}) {
+-	std.Warning(args...)
+-}
 -
--	c.Set("foo", "bar", 5)
+-// Error logs a message at level Error on the standard logger.
+-func Error(args ...interface{}) {
+-	std.Error(args...)
+-}
 -
--	// This should succeed an correct prevValue
--	resp, err := c.CompareAndDelete("foo", "bar", 0)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if !(resp.PrevNode.Value == "bar" && resp.PrevNode.Key == "/foo" && resp.PrevNode.TTL == 5) {
--		t.Fatalf("CompareAndDelete 1 prevNode failed: %#v", resp)
--	}
+-// Panic logs a message at level Panic on the standard logger.
+-func Panic(args ...interface{}) {
+-	std.Panic(args...)
+-}
 -
--	resp, _ = c.Set("foo", "bar", 5)
--	// This should fail because it gives an incorrect prevValue
--	_, err = c.CompareAndDelete("foo", "xxx", 0)
--	if err == nil {
--		t.Fatalf("CompareAndDelete 2 should have failed.  The response is: %#v", resp)
--	}
+-// Fatal logs a message at level Fatal on the standard logger.
+-func Fatal(args ...interface{}) {
+-	std.Fatal(args...)
+-}
 -
--	// This should succeed because it gives an correct prevIndex
--	resp, err = c.CompareAndDelete("foo", "", resp.Node.ModifiedIndex)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if !(resp.PrevNode.Value == "bar" && resp.PrevNode.Key == "/foo" && resp.PrevNode.TTL == 5) {
--		t.Fatalf("CompareAndSwap 3 prevNode failed: %#v", resp)
--	}
+-// Debugf logs a message at level Debug on the standard logger.
+-func Debugf(format string, args ...interface{}) {
+-	std.Debugf(format, args...)
+-}
 -
--	c.Set("foo", "bar", 5)
--	// This should fail because it gives an incorrect prevIndex
--	resp, err = c.CompareAndDelete("foo", "", 29817514)
--	if err == nil {
--		t.Fatalf("CompareAndDelete 4 should have failed.  The response is: %#v", resp)
--	}
+-// Printf logs a message at level Info on the standard logger.
+-func Printf(format string, args ...interface{}) {
+-	std.Printf(format, args...)
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_swap.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_swap.go
-deleted file mode 100644
-index bb4f906..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_swap.go
-+++ /dev/null
-@@ -1,36 +0,0 @@
--package etcd
 -
--import "fmt"
+-// Infof logs a message at level Info on the standard logger.
+-func Infof(format string, args ...interface{}) {
+-	std.Infof(format, args...)
+-}
 -
--func (c *Client) CompareAndSwap(key string, value string, ttl uint64,
--	prevValue string, prevIndex uint64) (*Response, error) {
--	raw, err := c.RawCompareAndSwap(key, value, ttl, prevValue, prevIndex)
--	if err != nil {
--		return nil, err
--	}
+-// Warnf logs a message at level Warn on the standard logger.
+-func Warnf(format string, args ...interface{}) {
+-	std.Warnf(format, args...)
+-}
 -
--	return raw.Unmarshal()
+-// Warningf logs a message at level Warn on the standard logger.
+-func Warningf(format string, args ...interface{}) {
+-	std.Warningf(format, args...)
 -}
 -
--func (c *Client) RawCompareAndSwap(key string, value string, ttl uint64,
--	prevValue string, prevIndex uint64) (*RawResponse, error) {
--	if prevValue == "" && prevIndex == 0 {
--		return nil, fmt.Errorf("You must give either prevValue or prevIndex.")
--	}
+-// Errorf logs a message at level Error on the standard logger.
+-func Errorf(format string, args ...interface{}) {
+-	std.Errorf(format, args...)
+-}
 -
--	options := Options{}
--	if prevValue != "" {
--		options["prevValue"] = prevValue
--	}
--	if prevIndex != 0 {
--		options["prevIndex"] = prevIndex
--	}
+-// Panicf logs a message at level Panic on the standard logger.
+-func Panicf(format string, args ...interface{}) {
+-	std.Panicf(format, args...)
+-}
 -
--	raw, err := c.put(key, value, ttl, options)
+-// Fatalf logs a message at level Fatal on the standard logger.
+-func Fatalf(format string, args ...interface{}) {
+-	std.Fatalf(format, args...)
+-}
 -
--	if err != nil {
--		return nil, err
--	}
+-// Debugln logs a message at level Debug on the standard logger.
+-func Debugln(args ...interface{}) {
+-	std.Debugln(args...)
+-}
 -
--	return raw, err
+-// Println logs a message at level Info on the standard logger.
+-func Println(args ...interface{}) {
+-	std.Println(args...)
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_swap_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_swap_test.go
-deleted file mode 100644
-index 14a1b00..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_swap_test.go
-+++ /dev/null
-@@ -1,57 +0,0 @@
--package etcd
 -
--import (
--	"testing"
--)
+-// Infoln logs a message at level Info on the standard logger.
+-func Infoln(args ...interface{}) {
+-	std.Infoln(args...)
+-}
 -
--func TestCompareAndSwap(t *testing.T) {
--	c := NewClient(nil)
--	defer func() {
--		c.Delete("foo", true)
--	}()
+-// Warnln logs a message at level Warn on the standard logger.
+-func Warnln(args ...interface{}) {
+-	std.Warnln(args...)
+-}
 -
--	c.Set("foo", "bar", 5)
+-// Warningln logs a message at level Warn on the standard logger.
+-func Warningln(args ...interface{}) {
+-	std.Warningln(args...)
+-}
 -
--	// This should succeed
--	resp, err := c.CompareAndSwap("foo", "bar2", 5, "bar", 0)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if !(resp.Node.Value == "bar2" && resp.Node.Key == "/foo" && resp.Node.TTL == 5) {
--		t.Fatalf("CompareAndSwap 1 failed: %#v", resp)
--	}
+-// Errorln logs a message at level Error on the standard logger.
+-func Errorln(args ...interface{}) {
+-	std.Errorln(args...)
+-}
 -
--	if !(resp.PrevNode.Value == "bar" && resp.PrevNode.Key == "/foo" && resp.PrevNode.TTL == 5) {
--		t.Fatalf("CompareAndSwap 1 prevNode failed: %#v", resp)
--	}
+-// Panicln logs a message at level Panic on the standard logger.
+-func Panicln(args ...interface{}) {
+-	std.Panicln(args...)
+-}
 -
--	// This should fail because it gives an incorrect prevValue
--	resp, err = c.CompareAndSwap("foo", "bar3", 5, "xxx", 0)
--	if err == nil {
--		t.Fatalf("CompareAndSwap 2 should have failed.  The response is: %#v", resp)
--	}
+-// Fatalln logs a message at level Fatal on the standard logger.
+-func Fatalln(args ...interface{}) {
+-	std.Fatalln(args...)
+-}
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/formatter.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/formatter.go
+deleted file mode 100644
+index 038ce9f..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/formatter.go
++++ /dev/null
+@@ -1,44 +0,0 @@
+-package logrus
 -
--	resp, err = c.Set("foo", "bar", 5)
--	if err != nil {
--		t.Fatal(err)
--	}
+-// The Formatter interface is used to implement a custom Formatter. It takes an
+-// `Entry`. It exposes all the fields, including the default ones:
+-//
+-// * `entry.Data["msg"]`. The message passed from Info, Warn, Error ..
+-// * `entry.Data["time"]`. The timestamp.
+-// * `entry.Data["level"]. The level the entry was logged at.
+-//
+-// Any additional fields added with `WithField` or `WithFields` are also in
+-// `entry.Data`. Format is expected to return an array of bytes which are then
+-// logged to `logger.Out`.
+-type Formatter interface {
+-	Format(*Entry) ([]byte, error)
+-}
 -
--	// This should succeed
--	resp, err = c.CompareAndSwap("foo", "bar2", 5, "", resp.Node.ModifiedIndex)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if !(resp.Node.Value == "bar2" && resp.Node.Key == "/foo" && resp.Node.TTL == 5) {
--		t.Fatalf("CompareAndSwap 3 failed: %#v", resp)
+-// This is to not silently overwrite `time`, `msg` and `level` fields when
+-// dumping it. If this code wasn't there doing:
+-//
+-//  logrus.WithField("level", 1).Info("hello")
+-//
+-// Would just silently drop the user provided level. Instead with this code
+-// it'll logged as:
+-//
+-//  {"level": "info", "fields.level": 1, "msg": "hello", "time": "..."}
+-//
+-// It's not exported because it's still using Data in an opinionated way. It's to
+-// avoid code duplication between the two default formatters.
+-func prefixFieldClashes(data Fields) {
+-	_, ok := data["time"]
+-	if ok {
+-		data["fields.time"] = data["time"]
 -	}
 -
--	if !(resp.PrevNode.Value == "bar" && resp.PrevNode.Key == "/foo" && resp.PrevNode.TTL == 5) {
--		t.Fatalf("CompareAndSwap 3 prevNode failed: %#v", resp)
+-	_, ok = data["msg"]
+-	if ok {
+-		data["fields.msg"] = data["msg"]
 -	}
 -
--	// This should fail because it gives an incorrect prevIndex
--	resp, err = c.CompareAndSwap("foo", "bar3", 5, "", 29817514)
--	if err == nil {
--		t.Fatalf("CompareAndSwap 4 should have failed.  The response is: %#v", resp)
+-	_, ok = data["level"]
+-	if ok {
+-		data["fields.level"] = data["level"]
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/debug.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/debug.go
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/formatter_bench_test.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/formatter_bench_test.go
 deleted file mode 100644
-index 0f77788..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/debug.go
+index 77989da..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/formatter_bench_test.go
 +++ /dev/null
-@@ -1,55 +0,0 @@
--package etcd
+@@ -1,88 +0,0 @@
+-package logrus
 -
 -import (
--	"fmt"
--	"io/ioutil"
--	"log"
--	"strings"
+-	"testing"
+-	"time"
 -)
 -
--var logger *etcdLogger
+-// smallFields is a small size data set for benchmarking
+-var smallFields = Fields{
+-	"foo":   "bar",
+-	"baz":   "qux",
+-	"one":   "two",
+-	"three": "four",
+-}
 -
--func SetLogger(l *log.Logger) {
--	logger = &etcdLogger{l}
+-// largeFields is a large size data set for benchmarking
+-var largeFields = Fields{
+-	"foo":       "bar",
+-	"baz":       "qux",
+-	"one":       "two",
+-	"three":     "four",
+-	"five":      "six",
+-	"seven":     "eight",
+-	"nine":      "ten",
+-	"eleven":    "twelve",
+-	"thirteen":  "fourteen",
+-	"fifteen":   "sixteen",
+-	"seventeen": "eighteen",
+-	"nineteen":  "twenty",
+-	"a":         "b",
+-	"c":         "d",
+-	"e":         "f",
+-	"g":         "h",
+-	"i":         "j",
+-	"k":         "l",
+-	"m":         "n",
+-	"o":         "p",
+-	"q":         "r",
+-	"s":         "t",
+-	"u":         "v",
+-	"w":         "x",
+-	"y":         "z",
+-	"this":      "will",
+-	"make":      "thirty",
+-	"entries":   "yeah",
 -}
 -
--func GetLogger() *log.Logger {
--	return logger.log
+-func BenchmarkSmallTextFormatter(b *testing.B) {
+-	doBenchmark(b, &TextFormatter{DisableColors: true}, smallFields)
 -}
 -
--type etcdLogger struct {
--	log *log.Logger
+-func BenchmarkLargeTextFormatter(b *testing.B) {
+-	doBenchmark(b, &TextFormatter{DisableColors: true}, largeFields)
 -}
 -
--func (p *etcdLogger) Debug(args ...interface{}) {
--	msg := "DEBUG: " + fmt.Sprint(args...)
--	p.log.Println(msg)
+-func BenchmarkSmallColoredTextFormatter(b *testing.B) {
+-	doBenchmark(b, &TextFormatter{ForceColors: true}, smallFields)
 -}
 -
--func (p *etcdLogger) Debugf(f string, args ...interface{}) {
--	msg := "DEBUG: " + fmt.Sprintf(f, args...)
--	// Append newline if necessary
--	if !strings.HasSuffix(msg, "\n") {
--		msg = msg + "\n"
--	}
--	p.log.Print(msg)
+-func BenchmarkLargeColoredTextFormatter(b *testing.B) {
+-	doBenchmark(b, &TextFormatter{ForceColors: true}, largeFields)
 -}
 -
--func (p *etcdLogger) Warning(args ...interface{}) {
--	msg := "WARNING: " + fmt.Sprint(args...)
--	p.log.Println(msg)
+-func BenchmarkSmallJSONFormatter(b *testing.B) {
+-	doBenchmark(b, &JSONFormatter{}, smallFields)
 -}
 -
--func (p *etcdLogger) Warningf(f string, args ...interface{}) {
--	msg := "WARNING: " + fmt.Sprintf(f, args...)
--	// Append newline if necessary
--	if !strings.HasSuffix(msg, "\n") {
--		msg = msg + "\n"
--	}
--	p.log.Print(msg)
+-func BenchmarkLargeJSONFormatter(b *testing.B) {
+-	doBenchmark(b, &JSONFormatter{}, largeFields)
 -}
 -
--func init() {
--	// Default logger uses the go default log.
--	SetLogger(log.New(ioutil.Discard, "go-etcd", log.LstdFlags))
+-func doBenchmark(b *testing.B, formatter Formatter, fields Fields) {
+-	entry := &Entry{
+-		Time:    time.Time{},
+-		Level:   InfoLevel,
+-		Message: "message",
+-		Data:    fields,
+-	}
+-	var d []byte
+-	var err error
+-	for i := 0; i < b.N; i++ {
+-		d, err = formatter.Format(entry)
+-		if err != nil {
+-			b.Fatal(err)
+-		}
+-		b.SetBytes(int64(len(d)))
+-	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/debug_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/debug_test.go
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hook_test.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/hook_test.go
 deleted file mode 100644
-index 97f6d11..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/debug_test.go
+index 13f34cb..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hook_test.go
 +++ /dev/null
-@@ -1,28 +0,0 @@
--package etcd
+@@ -1,122 +0,0 @@
+-package logrus
 -
 -import (
 -	"testing"
+-
+-	"github.com/stretchr/testify/assert"
 -)
 -
--type Foo struct{}
--type Bar struct {
--	one string
--	two int
+-type TestHook struct {
+-	Fired bool
 -}
 -
--// Tests that logs don't panic with arbitrary interfaces
--func TestDebug(t *testing.T) {
--	f := &Foo{}
--	b := &Bar{"asfd", 3}
--	for _, test := range []interface{}{
--		1234,
--		"asdf",
--		f,
--		b,
--	} {
--		logger.Debug(test)
--		logger.Debugf("something, %s", test)
--		logger.Warning(test)
--		logger.Warningf("something, %s", test)
+-func (hook *TestHook) Fire(entry *Entry) error {
+-	hook.Fired = true
+-	return nil
+-}
+-
+-func (hook *TestHook) Levels() []Level {
+-	return []Level{
+-		DebugLevel,
+-		InfoLevel,
+-		WarnLevel,
+-		ErrorLevel,
+-		FatalLevel,
+-		PanicLevel,
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/delete.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/delete.go
-deleted file mode 100644
-index b37accd..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/delete.go
-+++ /dev/null
-@@ -1,40 +0,0 @@
--package etcd
 -
--// Delete deletes the given key.
--//
--// When recursive set to false, if the key points to a
--// directory the method will fail.
--//
--// When recursive set to true, if the key points to a file,
--// the file will be deleted; if the key points to a directory,
--// then everything under the directory (including all child directories)
--// will be deleted.
--func (c *Client) Delete(key string, recursive bool) (*Response, error) {
--	raw, err := c.RawDelete(key, recursive, false)
+-func TestHookFires(t *testing.T) {
+-	hook := new(TestHook)
 -
--	if err != nil {
--		return nil, err
--	}
+-	LogAndAssertJSON(t, func(log *Logger) {
+-		log.Hooks.Add(hook)
+-		assert.Equal(t, hook.Fired, false)
 -
--	return raw.Unmarshal()
+-		log.Print("test")
+-	}, func(fields Fields) {
+-		assert.Equal(t, hook.Fired, true)
+-	})
 -}
 -
--// DeleteDir deletes an empty directory or a key value pair
--func (c *Client) DeleteDir(key string) (*Response, error) {
--	raw, err := c.RawDelete(key, false, true)
--
--	if err != nil {
--		return nil, err
--	}
+-type ModifyHook struct {
+-}
 -
--	return raw.Unmarshal()
+-func (hook *ModifyHook) Fire(entry *Entry) error {
+-	entry.Data["wow"] = "whale"
+-	return nil
 -}
 -
--func (c *Client) RawDelete(key string, recursive bool, dir bool) (*RawResponse, error) {
--	ops := Options{
--		"recursive": recursive,
--		"dir":       dir,
+-func (hook *ModifyHook) Levels() []Level {
+-	return []Level{
+-		DebugLevel,
+-		InfoLevel,
+-		WarnLevel,
+-		ErrorLevel,
+-		FatalLevel,
+-		PanicLevel,
 -	}
+-}
 -
--	return c.delete(key, ops)
+-func TestHookCanModifyEntry(t *testing.T) {
+-	hook := new(ModifyHook)
+-
+-	LogAndAssertJSON(t, func(log *Logger) {
+-		log.Hooks.Add(hook)
+-		log.WithField("wow", "elephant").Print("test")
+-	}, func(fields Fields) {
+-		assert.Equal(t, fields["wow"], "whale")
+-	})
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/delete_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/delete_test.go
-deleted file mode 100644
-index 5904971..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/delete_test.go
-+++ /dev/null
-@@ -1,81 +0,0 @@
--package etcd
 -
--import (
--	"testing"
--)
+-func TestCanFireMultipleHooks(t *testing.T) {
+-	hook1 := new(ModifyHook)
+-	hook2 := new(TestHook)
 -
--func TestDelete(t *testing.T) {
--	c := NewClient(nil)
--	defer func() {
--		c.Delete("foo", true)
--	}()
+-	LogAndAssertJSON(t, func(log *Logger) {
+-		log.Hooks.Add(hook1)
+-		log.Hooks.Add(hook2)
 -
--	c.Set("foo", "bar", 5)
--	resp, err := c.Delete("foo", false)
--	if err != nil {
--		t.Fatal(err)
--	}
+-		log.WithField("wow", "elephant").Print("test")
+-	}, func(fields Fields) {
+-		assert.Equal(t, fields["wow"], "whale")
+-		assert.Equal(t, hook2.Fired, true)
+-	})
+-}
 -
--	if !(resp.Node.Value == "") {
--		t.Fatalf("Delete failed with %s", resp.Node.Value)
--	}
+-type ErrorHook struct {
+-	Fired bool
+-}
 -
--	if !(resp.PrevNode.Value == "bar") {
--		t.Fatalf("Delete PrevNode failed with %s", resp.Node.Value)
--	}
+-func (hook *ErrorHook) Fire(entry *Entry) error {
+-	hook.Fired = true
+-	return nil
+-}
 -
--	resp, err = c.Delete("foo", false)
--	if err == nil {
--		t.Fatalf("Delete should have failed because the key foo did not exist.  "+
--			"The response was: %v", resp)
+-func (hook *ErrorHook) Levels() []Level {
+-	return []Level{
+-		ErrorLevel,
 -	}
 -}
 -
--func TestDeleteAll(t *testing.T) {
--	c := NewClient(nil)
--	defer func() {
--		c.Delete("foo", true)
--		c.Delete("fooDir", true)
--	}()
+-func TestErrorHookShouldntFireOnInfo(t *testing.T) {
+-	hook := new(ErrorHook)
 -
--	c.SetDir("foo", 5)
--	// test delete an empty dir
--	resp, err := c.DeleteDir("foo")
--	if err != nil {
--		t.Fatal(err)
--	}
+-	LogAndAssertJSON(t, func(log *Logger) {
+-		log.Hooks.Add(hook)
+-		log.Info("test")
+-	}, func(fields Fields) {
+-		assert.Equal(t, hook.Fired, false)
+-	})
+-}
 -
--	if !(resp.Node.Value == "") {
--		t.Fatalf("DeleteAll 1 failed: %#v", resp)
--	}
+-func TestErrorHookShouldFireOnError(t *testing.T) {
+-	hook := new(ErrorHook)
 -
--	if !(resp.PrevNode.Dir == true && resp.PrevNode.Value == "") {
--		t.Fatalf("DeleteAll 1 PrevNode failed: %#v", resp)
--	}
+-	LogAndAssertJSON(t, func(log *Logger) {
+-		log.Hooks.Add(hook)
+-		log.Error("test")
+-	}, func(fields Fields) {
+-		assert.Equal(t, hook.Fired, true)
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks.go
+deleted file mode 100644
+index 0da2b36..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks.go
++++ /dev/null
+@@ -1,34 +0,0 @@
+-package logrus
 -
--	c.CreateDir("fooDir", 5)
--	c.Set("fooDir/foo", "bar", 5)
--	_, err = c.DeleteDir("fooDir")
--	if err == nil {
--		t.Fatal("should not able to delete a non-empty dir with deletedir")
--	}
+-// A hook to be fired when logging on the logging levels returned from
+-// `Levels()` on your implementation of the interface. Note that this is not
+-// fired in a goroutine or a channel with workers, you should handle such
+-// functionality yourself if your call is non-blocking and you don't wish for
+-// the logging calls for levels returned from `Levels()` to block.
+-type Hook interface {
+-	Levels() []Level
+-	Fire(*Entry) error
+-}
 -
--	resp, err = c.Delete("fooDir", true)
--	if err != nil {
--		t.Fatal(err)
--	}
+-// Internal type for storing the hooks on a logger instance.
+-type levelHooks map[Level][]Hook
 -
--	if !(resp.Node.Value == "") {
--		t.Fatalf("DeleteAll 2 failed: %#v", resp)
+-// Add a hook to an instance of logger. This is called with
+-// `log.Hooks.Add(new(MyHook))` where `MyHook` implements the `Hook` interface.
+-func (hooks levelHooks) Add(hook Hook) {
+-	for _, level := range hook.Levels() {
+-		hooks[level] = append(hooks[level], hook)
 -	}
+-}
 -
--	if !(resp.PrevNode.Dir == true && resp.PrevNode.Value == "") {
--		t.Fatalf("DeleteAll 2 PrevNode failed: %#v", resp)
+-// Fire all the hooks for the passed level. Used by `entry.log` to fire
+-// appropriate hooks for a log entry.
+-func (hooks levelHooks) Fire(level Level, entry *Entry) error {
+-	for _, hook := range hooks[level] {
+-		if err := hook.Fire(entry); err != nil {
+-			return err
+-		}
 -	}
 -
--	resp, err = c.Delete("foo", true)
--	if err == nil {
--		t.Fatalf("DeleteAll should have failed because the key foo did not exist.  "+
--			"The response was: %v", resp)
--	}
+-	return nil
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/error.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/error.go
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/airbrake/airbrake.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/airbrake/airbrake.go
 deleted file mode 100644
-index 7e69287..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/error.go
+index 880d21e..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/airbrake/airbrake.go
 +++ /dev/null
-@@ -1,48 +0,0 @@
--package etcd
+@@ -1,54 +0,0 @@
+-package logrus_airbrake
 -
 -import (
--	"encoding/json"
--	"fmt"
+-	"github.com/Sirupsen/logrus"
+-	"github.com/tobi/airbrake-go"
 -)
 -
--const (
--	ErrCodeEtcdNotReachable = 501
--)
+-// AirbrakeHook to send exceptions to an exception-tracking service compatible
+-// with the Airbrake API. You must set:
+-// * airbrake.Endpoint
+-// * airbrake.ApiKey
+-// * airbrake.Environment (only sends exceptions when set to "production")
+-//
+-// Before using this hook, to send an error. Entries that trigger an Error,
+-// Fatal or Panic should now include an "error" field to send to Airbrake.
+-type AirbrakeHook struct{}
+-
+-func (hook *AirbrakeHook) Fire(entry *logrus.Entry) error {
+-	if entry.Data["error"] == nil {
+-		entry.Logger.WithFields(logrus.Fields{
+-			"source":   "airbrake",
+-			"endpoint": airbrake.Endpoint,
+-		}).Warn("Exceptions sent to Airbrake must have an 'error' key with the error")
+-		return nil
+-	}
 -
--var (
--	errorMap = map[int]string{
--		ErrCodeEtcdNotReachable: "All the given peers are not reachable",
+-	err, ok := entry.Data["error"].(error)
+-	if !ok {
+-		entry.Logger.WithFields(logrus.Fields{
+-			"source":   "airbrake",
+-			"endpoint": airbrake.Endpoint,
+-		}).Warn("Exceptions sent to Airbrake must have an `error` key of type `error`")
+-		return nil
 -	}
--)
 -
--type EtcdError struct {
--	ErrorCode int    `json:"errorCode"`
--	Message   string `json:"message"`
--	Cause     string `json:"cause,omitempty"`
--	Index     uint64 `json:"index"`
--}
+-	airErr := airbrake.Notify(err)
+-	if airErr != nil {
+-		entry.Logger.WithFields(logrus.Fields{
+-			"source":   "airbrake",
+-			"endpoint": airbrake.Endpoint,
+-			"error":    airErr,
+-		}).Warn("Failed to send error to Airbrake")
+-	}
 -
--func (e EtcdError) Error() string {
--	return fmt.Sprintf("%v: %v (%v) [%v]", e.ErrorCode, e.Message, e.Cause, e.Index)
+-	return nil
 -}
 -
--func newError(errorCode int, cause string, index uint64) *EtcdError {
--	return &EtcdError{
--		ErrorCode: errorCode,
--		Message:   errorMap[errorCode],
--		Cause:     cause,
--		Index:     index,
+-func (hook *AirbrakeHook) Levels() []logrus.Level {
+-	return []logrus.Level{
+-		logrus.ErrorLevel,
+-		logrus.FatalLevel,
+-		logrus.PanicLevel,
 -	}
 -}
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/papertrail/README.md b/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/papertrail/README.md
+deleted file mode 100644
+index ae61e92..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/papertrail/README.md
++++ /dev/null
+@@ -1,28 +0,0 @@
+-# Papertrail Hook for Logrus <img src="http://i.imgur.com/hTeVwmJ.png" width="40" height="40" alt=":walrus:" class="emoji" title=":walrus:" />
 -
--func handleError(b []byte) error {
--	etcdErr := new(EtcdError)
+-[Papertrail](https://papertrailapp.com) provides hosted log management. Once stored in Papertrail, you can [group](http://help.papertrailapp.com/kb/how-it-works/groups/) your logs on various dimensions, [search](http://help.papertrailapp.com/kb/how-it-works/search-syntax) them, and trigger [alerts](http://help.papertrailapp.com/kb/how-it-works/alerts).
 -
--	err := json.Unmarshal(b, etcdErr)
--	if err != nil {
--		logger.Warningf("cannot unmarshal etcd error: %v", err)
--		return err
--	}
+-In most deployments, you'll want to send logs to Papertrail via their [remote_syslog](http://help.papertrailapp.com/kb/configuration/configuring-centralized-logging-from-text-log-files-in-unix/) daemon, which requires no application-specific configuration. This hook is intended for relatively low-volume logging, likely in managed cloud hosting deployments where installing `remote_syslog` is not possible.
 -
--	return etcdErr
--}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/get.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/get.go
-deleted file mode 100644
-index 976bf07..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/get.go
-+++ /dev/null
-@@ -1,27 +0,0 @@
--package etcd
+-## Usage
 -
--// Get gets the file or directory associated with the given key.
--// If the key points to a directory, files and directories under
--// it will be returned in sorted or unsorted order, depending on
--// the sort flag.
--// If recursive is set to false, contents under child directories
--// will not be returned.
--// If recursive is set to true, all the contents will be returned.
--func (c *Client) Get(key string, sort, recursive bool) (*Response, error) {
--	raw, err := c.RawGet(key, sort, recursive)
+-You can find your Papertrail UDP port on your [Papertrail account page](https://papertrailapp.com/account/destinations). Substitute it below for `YOUR_PAPERTRAIL_UDP_PORT`.
 -
--	if err != nil {
--		return nil, err
--	}
+-For `YOUR_APP_NAME`, substitute a short string that will readily identify your application or service in the logs.
 -
--	return raw.Unmarshal()
--}
+-```go
+-import (
+-  "log/syslog"
+-  "github.com/Sirupsen/logrus"
+-  "github.com/Sirupsen/logrus/hooks/papertrail"
+-)
 -
--func (c *Client) RawGet(key string, sort, recursive bool) (*RawResponse, error) {
--	ops := Options{
--		"recursive": recursive,
--		"sorted":    sort,
--	}
+-func main() {
+-  log       := logrus.New()
+-  hook, err := logrus_papertrail.NewPapertrailHook("logs.papertrailapp.com", YOUR_PAPERTRAIL_UDP_PORT, YOUR_APP_NAME)
 -
--	return c.get(key, ops)
+-  if err == nil {
+-    log.Hooks.Add(hook)
+-  }
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/get_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/get_test.go
+-```
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/papertrail/papertrail.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/papertrail/papertrail.go
 deleted file mode 100644
-index 279c4e2..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/get_test.go
+index 12c56f2..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/papertrail/papertrail.go
 +++ /dev/null
-@@ -1,131 +0,0 @@
--package etcd
+@@ -1,54 +0,0 @@
+-package logrus_papertrail
 -
 -import (
--	"reflect"
--	"testing"
+-	"fmt"
+-	"net"
+-	"os"
+-	"time"
+-
+-	"github.com/Sirupsen/logrus"
 -)
 -
--// cleanNode scrubs Expiration, ModifiedIndex and CreatedIndex of a node.
--func cleanNode(n *Node) {
--	n.Expiration = nil
--	n.ModifiedIndex = 0
--	n.CreatedIndex = 0
--}
+-const (
+-	format = "Jan 2 15:04:05"
+-)
 -
--// cleanResult scrubs a result object two levels deep of Expiration,
--// ModifiedIndex and CreatedIndex.
--func cleanResult(result *Response) {
--	//  TODO(philips): make this recursive.
--	cleanNode(result.Node)
--	for i, _ := range result.Node.Nodes {
--		cleanNode(result.Node.Nodes[i])
--		for j, _ := range result.Node.Nodes[i].Nodes {
--			cleanNode(result.Node.Nodes[i].Nodes[j])
--		}
--	}
+-// PapertrailHook to send logs to a logging service compatible with the Papertrail API.
+-type PapertrailHook struct {
+-	Host    string
+-	Port    int
+-	AppName string
+-	UDPConn net.Conn
 -}
 -
--func TestGet(t *testing.T) {
--	c := NewClient(nil)
--	defer func() {
--		c.Delete("foo", true)
--	}()
--
--	c.Set("foo", "bar", 5)
+-// NewPapertrailHook creates a hook to be added to an instance of logger.
+-func NewPapertrailHook(host string, port int, appName string) (*PapertrailHook, error) {
+-	conn, err := net.Dial("udp", fmt.Sprintf("%s:%d", host, port))
+-	return &PapertrailHook{host, port, appName, conn}, err
+-}
 -
--	result, err := c.Get("foo", false, false)
+-// Fire is called when a log event is fired.
+-func (hook *PapertrailHook) Fire(entry *logrus.Entry) error {
+-	date := time.Now().Format(format)
+-	payload := fmt.Sprintf("<22> %s %s: [%s] %s", date, hook.AppName, entry.Level, entry.Message)
 -
+-	bytesWritten, err := hook.UDPConn.Write([]byte(payload))
 -	if err != nil {
--		t.Fatal(err)
+-		fmt.Fprintf(os.Stderr, "Unable to send log line to Papertrail via UDP. Wrote %d bytes before error: %v", bytesWritten, err)
+-		return err
 -	}
 -
--	if result.Node.Key != "/foo" || result.Node.Value != "bar" {
--		t.Fatalf("Get failed with %s %s %v", result.Node.Key, result.Node.Value, result.Node.TTL)
--	}
+-	return nil
+-}
 -
--	result, err = c.Get("goo", false, false)
--	if err == nil {
--		t.Fatalf("should not be able to get non-exist key")
+-// Levels returns the available logging levels.
+-func (hook *PapertrailHook) Levels() []logrus.Level {
+-	return []logrus.Level{
+-		logrus.PanicLevel,
+-		logrus.FatalLevel,
+-		logrus.ErrorLevel,
+-		logrus.WarnLevel,
+-		logrus.InfoLevel,
+-		logrus.DebugLevel,
 -	}
 -}
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/papertrail/papertrail_test.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/papertrail/papertrail_test.go
+deleted file mode 100644
+index 96318d0..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/papertrail/papertrail_test.go
++++ /dev/null
+@@ -1,26 +0,0 @@
+-package logrus_papertrail
 -
--func TestGetAll(t *testing.T) {
--	c := NewClient(nil)
--	defer func() {
--		c.Delete("fooDir", true)
--	}()
+-import (
+-	"fmt"
+-	"testing"
 -
--	c.CreateDir("fooDir", 5)
--	c.Set("fooDir/k0", "v0", 5)
--	c.Set("fooDir/k1", "v1", 5)
+-	"github.com/Sirupsen/logrus"
+-	"github.com/stvp/go-udp-testing"
+-)
 -
--	// Return kv-pairs in sorted order
--	result, err := c.Get("fooDir", true, false)
+-func TestWritingToUDP(t *testing.T) {
+-	port := 16661
+-	udp.SetAddr(fmt.Sprintf(":%d", port))
 -
+-	hook, err := NewPapertrailHook("localhost", port, "test")
 -	if err != nil {
--		t.Fatal(err)
+-		t.Errorf("Unable to connect to local UDP server.")
 -	}
 -
--	expected := Nodes{
--		&Node{
--			Key:   "/fooDir/k0",
--			Value: "v0",
--			TTL:   5,
--		},
--		&Node{
--			Key:   "/fooDir/k1",
--			Value: "v1",
--			TTL:   5,
--		},
--	}
+-	log := logrus.New()
+-	log.Hooks.Add(hook)
 -
--	cleanResult(result)
+-	udp.ShouldReceive(t, "foo", func() {
+-		log.Info("foo")
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/sentry/README.md b/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/sentry/README.md
+deleted file mode 100644
+index a409f3b..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/sentry/README.md
++++ /dev/null
+@@ -1,61 +0,0 @@
+-# Sentry Hook for Logrus <img src="http://i.imgur.com/hTeVwmJ.png" width="40" height="40" alt=":walrus:" class="emoji" title=":walrus:" />
 -
--	if !reflect.DeepEqual(result.Node.Nodes, expected) {
--		t.Fatalf("(actual) %v != (expected) %v", result.Node.Nodes, expected)
--	}
+-[Sentry](https://getsentry.com) provides both self-hosted and hosted
+-solutions for exception tracking.
+-Both client and server are
+-[open source](https://github.com/getsentry/sentry).
 -
--	// Test the `recursive` option
--	c.CreateDir("fooDir/childDir", 5)
--	c.Set("fooDir/childDir/k2", "v2", 5)
+-## Usage
 -
--	// Return kv-pairs in sorted order
--	result, err = c.Get("fooDir", true, true)
+-Every sentry application defined on the server gets a different
+-[DSN](https://www.getsentry.com/docs/). In the example below replace
+-`YOUR_DSN` with the one created for your application.
 -
--	cleanResult(result)
+-```go
+-import (
+-  "github.com/Sirupsen/logrus"
+-  "github.com/Sirupsen/logrus/hooks/sentry"
+-)
 -
--	if err != nil {
--		t.Fatal(err)
--	}
+-func main() {
+-  log       := logrus.New()
+-  hook, err := logrus_sentry.NewSentryHook(YOUR_DSN, []logrus.Level{
+-    logrus.PanicLevel,
+-    logrus.FatalLevel,
+-    logrus.ErrorLevel,
+-  })
+-
+-  if err == nil {
+-    log.Hooks.Add(hook)
+-  }
+-}
+-```
 -
--	expected = Nodes{
--		&Node{
--			Key: "/fooDir/childDir",
--			Dir: true,
--			Nodes: Nodes{
--				&Node{
--					Key:   "/fooDir/childDir/k2",
--					Value: "v2",
--					TTL:   5,
--				},
--			},
--			TTL: 5,
--		},
--		&Node{
--			Key:   "/fooDir/k0",
--			Value: "v0",
--			TTL:   5,
--		},
--		&Node{
--			Key:   "/fooDir/k1",
--			Value: "v1",
--			TTL:   5,
--		},
--	}
+-## Special fields
 -
--	cleanResult(result)
+-Some logrus fields have a special meaning in this hook,
+-these are server_name and logger.
+-When logs are sent to sentry these fields are treated differently.
+-- server_name (also known as hostname) is the name of the server which
+-is logging the event (hostname.example.com)
+-- logger is the part of the application which is logging the event.
+-In go this usually means setting it to the name of the package.
 -
--	if !reflect.DeepEqual(result.Node.Nodes, expected) {
--		t.Fatalf("(actual) %v != (expected) %v", result.Node.Nodes, expected)
--	}
--}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/options.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/options.go
+-## Timeout
+-
+-`Timeout` is the time the sentry hook will wait for a response
+-from the sentry server.
+-
+-If this time elapses with no response from
+-the server an error will be returned.
+-
+-If `Timeout` is set to 0 the SentryHook will not wait for a reply
+-and will assume a correct delivery.
+-
+-The SentryHook has a default timeout of `100 milliseconds` when created
+-with a call to `NewSentryHook`. This can be changed by assigning a value to the `Timeout` field:
+-
+-```go
+-hook, _ := logrus_sentry.NewSentryHook(...)
+-hook.Timeout = 20*time.Seconds
+-```
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/sentry/sentry.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/sentry/sentry.go
 deleted file mode 100644
-index 701c9b3..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/options.go
+index 379f281..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/sentry/sentry.go
 +++ /dev/null
-@@ -1,72 +0,0 @@
--package etcd
+@@ -1,100 +0,0 @@
+-package logrus_sentry
 -
 -import (
 -	"fmt"
--	"net/url"
--	"reflect"
--)
--
--type Options map[string]interface{}
+-	"time"
 -
--// An internally-used data structure that represents a mapping
--// between valid options and their kinds
--type validOptions map[string]reflect.Kind
+-	"github.com/Sirupsen/logrus"
+-	"github.com/getsentry/raven-go"
+-)
 -
--// Valid options for GET, PUT, POST, DELETE
--// Using CAPITALIZED_UNDERSCORE to emphasize that these
--// values are meant to be used as constants.
 -var (
--	VALID_GET_OPTIONS = validOptions{
--		"recursive":  reflect.Bool,
--		"consistent": reflect.Bool,
--		"sorted":     reflect.Bool,
--		"wait":       reflect.Bool,
--		"waitIndex":  reflect.Uint64,
+-	severityMap = map[logrus.Level]raven.Severity{
+-		logrus.DebugLevel: raven.DEBUG,
+-		logrus.InfoLevel:  raven.INFO,
+-		logrus.WarnLevel:  raven.WARNING,
+-		logrus.ErrorLevel: raven.ERROR,
+-		logrus.FatalLevel: raven.FATAL,
+-		logrus.PanicLevel: raven.FATAL,
 -	}
+-)
 -
--	VALID_PUT_OPTIONS = validOptions{
--		"prevValue": reflect.String,
--		"prevIndex": reflect.Uint64,
--		"prevExist": reflect.Bool,
--		"dir":       reflect.Bool,
+-func getAndDel(d logrus.Fields, key string) (string, bool) {
+-	var (
+-		ok  bool
+-		v   interface{}
+-		val string
+-	)
+-	if v, ok = d[key]; !ok {
+-		return "", false
 -	}
 -
--	VALID_POST_OPTIONS = validOptions{}
--
--	VALID_DELETE_OPTIONS = validOptions{
--		"recursive": reflect.Bool,
--		"dir":       reflect.Bool,
--		"prevValue": reflect.String,
--		"prevIndex": reflect.Uint64,
+-	if val, ok = v.(string); !ok {
+-		return "", false
 -	}
--)
+-	delete(d, key)
+-	return val, true
+-}
 -
--// Convert options to a string of HTML parameters
--func (ops Options) toParameters(validOps validOptions) (string, error) {
--	p := "?"
--	values := url.Values{}
+-// SentryHook delivers logs to a sentry server.
+-type SentryHook struct {
+-	// Timeout sets the time to wait for a delivery error from the sentry server.
+-	// If this is set to zero the server will not wait for any response and will
+-	// consider the message correctly sent
+-	Timeout time.Duration
 -
--	if ops == nil {
--		return "", nil
+-	client *raven.Client
+-	levels []logrus.Level
+-}
+-
+-// NewSentryHook creates a hook to be added to an instance of logger
+-// and initializes the raven client.
+-// This method sets the timeout to 100 milliseconds.
+-func NewSentryHook(DSN string, levels []logrus.Level) (*SentryHook, error) {
+-	client, err := raven.NewClient(DSN, nil)
+-	if err != nil {
+-		return nil, err
 -	}
+-	return &SentryHook{100 * time.Millisecond, client, levels}, nil
+-}
 -
--	for k, v := range ops {
--		// Check if the given option is valid (that it exists)
--		kind := validOps[k]
--		if kind == reflect.Invalid {
--			return "", fmt.Errorf("Invalid option: %v", k)
--		}
+-// Called when an event should be sent to sentry
+-// Special fields that sentry uses to give more information to the server
+-// are extracted from entry.Data (if they are found)
+-// These fields are: logger and server_name
+-func (hook *SentryHook) Fire(entry *logrus.Entry) error {
+-	packet := &raven.Packet{
+-		Message:   entry.Message,
+-		Timestamp: raven.Timestamp(entry.Time),
+-		Level:     severityMap[entry.Level],
+-		Platform:  "go",
+-	}
 -
--		// Check if the given option is of the valid type
--		t := reflect.TypeOf(v)
--		if kind != t.Kind() {
--			return "", fmt.Errorf("Option %s should be of %v kind, not of %v kind.",
--				k, kind, t.Kind())
--		}
+-	d := entry.Data
 -
--		values.Set(k, fmt.Sprintf("%v", v))
+-	if logger, ok := getAndDel(d, "logger"); ok {
+-		packet.Logger = logger
 -	}
+-	if serverName, ok := getAndDel(d, "server_name"); ok {
+-		packet.ServerName = serverName
+-	}
+-	packet.Extra = map[string]interface{}(d)
 -
--	p += values.Encode()
--	return p, nil
+-	_, errCh := hook.client.Capture(packet, nil)
+-	timeout := hook.Timeout
+-	if timeout != 0 {
+-		timeoutCh := time.After(timeout)
+-		select {
+-		case err := <-errCh:
+-			return err
+-		case <-timeoutCh:
+-			return fmt.Errorf("no response from sentry server in %s", timeout)
+-		}
+-	}
+-	return nil
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/requests.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/requests.go
+-
+-// Levels returns the available logging levels.
+-func (hook *SentryHook) Levels() []logrus.Level {
+-	return hook.levels
+-}
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/sentry/sentry_test.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/sentry/sentry_test.go
 deleted file mode 100644
-index 5d8b45a..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/requests.go
+index 45f18d1..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/sentry/sentry_test.go
 +++ /dev/null
-@@ -1,377 +0,0 @@
--package etcd
+@@ -1,97 +0,0 @@
+-package logrus_sentry
 -
 -import (
--	"errors"
+-	"encoding/json"
 -	"fmt"
 -	"io/ioutil"
--	"math/rand"
 -	"net/http"
--	"net/url"
--	"path"
+-	"net/http/httptest"
 -	"strings"
--	"sync"
--	"time"
+-	"testing"
+-
+-	"github.com/Sirupsen/logrus"
+-	"github.com/getsentry/raven-go"
 -)
 -
--// Errors introduced by handling requests
--var (
--	ErrRequestCancelled = errors.New("sending request is cancelled")
+-const (
+-	message     = "error message"
+-	server_name = "testserver.internal"
+-	logger_name = "test.logger"
 -)
 -
--type RawRequest struct {
--	Method       string
--	RelativePath string
--	Values       url.Values
--	Cancel       <-chan bool
+-func getTestLogger() *logrus.Logger {
+-	l := logrus.New()
+-	l.Out = ioutil.Discard
+-	return l
 -}
 -
--// NewRawRequest returns a new RawRequest
--func NewRawRequest(method, relativePath string, values url.Values, cancel <-chan bool) *RawRequest {
--	return &RawRequest{
--		Method:       method,
--		RelativePath: relativePath,
--		Values:       values,
--		Cancel:       cancel,
--	}
--}
+-func WithTestDSN(t *testing.T, tf func(string, <-chan *raven.Packet)) {
+-	pch := make(chan *raven.Packet, 1)
+-	s := httptest.NewServer(http.HandlerFunc(func(rw http.ResponseWriter, req *http.Request) {
+-		defer req.Body.Close()
+-		d := json.NewDecoder(req.Body)
+-		p := &raven.Packet{}
+-		err := d.Decode(p)
+-		if err != nil {
+-			t.Fatal(err.Error())
+-		}
 -
--// getCancelable issues a cancelable GET request
--func (c *Client) getCancelable(key string, options Options,
--	cancel <-chan bool) (*RawResponse, error) {
--	logger.Debugf("get %s [%s]", key, c.cluster.Leader)
--	p := keyToPath(key)
+-		pch <- p
+-	}))
+-	defer s.Close()
 -
--	// If consistency level is set to STRONG, append
--	// the `consistent` query string.
--	if c.config.Consistency == STRONG_CONSISTENCY {
--		options["consistent"] = true
--	}
+-	fragments := strings.SplitN(s.URL, "://", 2)
+-	dsn := fmt.Sprintf(
+-		"%s://public:secret@%s/sentry/project-id",
+-		fragments[0],
+-		fragments[1],
+-	)
+-	tf(dsn, pch)
+-}
 -
--	str, err := options.toParameters(VALID_GET_OPTIONS)
--	if err != nil {
--		return nil, err
--	}
--	p += str
+-func TestSpecialFields(t *testing.T) {
+-	WithTestDSN(t, func(dsn string, pch <-chan *raven.Packet) {
+-		logger := getTestLogger()
 -
--	req := NewRawRequest("GET", p, nil, cancel)
--	resp, err := c.SendRequest(req)
+-		hook, err := NewSentryHook(dsn, []logrus.Level{
+-			logrus.ErrorLevel,
+-		})
 -
--	if err != nil {
--		return nil, err
--	}
+-		if err != nil {
+-			t.Fatal(err.Error())
+-		}
+-		logger.Hooks.Add(hook)
+-		logger.WithFields(logrus.Fields{
+-			"server_name": server_name,
+-			"logger":      logger_name,
+-		}).Error(message)
 -
--	return resp, nil
--}
+-		packet := <-pch
+-		if packet.Logger != logger_name {
+-			t.Errorf("logger should have been %s, was %s", logger_name, packet.Logger)
+-		}
 -
--// get issues a GET request
--func (c *Client) get(key string, options Options) (*RawResponse, error) {
--	return c.getCancelable(key, options, nil)
+-		if packet.ServerName != server_name {
+-			t.Errorf("server_name should have been %s, was %s", server_name, packet.ServerName)
+-		}
+-	})
 -}
 -
--// put issues a PUT request
--func (c *Client) put(key string, value string, ttl uint64,
--	options Options) (*RawResponse, error) {
+-func TestSentryHandler(t *testing.T) {
+-	WithTestDSN(t, func(dsn string, pch <-chan *raven.Packet) {
+-		logger := getTestLogger()
+-		hook, err := NewSentryHook(dsn, []logrus.Level{
+-			logrus.ErrorLevel,
+-		})
+-		if err != nil {
+-			t.Fatal(err.Error())
+-		}
+-		logger.Hooks.Add(hook)
 -
--	logger.Debugf("put %s, %s, ttl: %d, [%s]", key, value, ttl, c.cluster.Leader)
--	p := keyToPath(key)
+-		logger.Error(message)
+-		packet := <-pch
+-		if packet.Message != message {
+-			t.Errorf("message should have been %s, was %s", message, packet.Message)
+-		}
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/syslog/README.md b/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/syslog/README.md
+deleted file mode 100644
+index 4dbb8e7..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/syslog/README.md
++++ /dev/null
+@@ -1,20 +0,0 @@
+-# Syslog Hooks for Logrus <img src="http://i.imgur.com/hTeVwmJ.png" width="40" height="40" alt=":walrus:" class="emoji" title=":walrus:"/>
 -
--	str, err := options.toParameters(VALID_PUT_OPTIONS)
--	if err != nil {
--		return nil, err
--	}
--	p += str
+-## Usage
 -
--	req := NewRawRequest("PUT", p, buildValues(value, ttl), nil)
--	resp, err := c.SendRequest(req)
+-```go
+-import (
+-  "log/syslog"
+-  "github.com/Sirupsen/logrus"
+-  logrus_syslog "github.com/Sirupsen/logrus/hooks/syslog"
+-)
 -
--	if err != nil {
--		return nil, err
--	}
+-func main() {
+-  log       := logrus.New()
+-  hook, err := logrus_syslog.NewSyslogHook("udp", "localhost:514", syslog.LOG_INFO, "")
 -
--	return resp, nil
+-  if err == nil {
+-    log.Hooks.Add(hook)
+-  }
 -}
+-```
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/syslog/syslog.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/syslog/syslog.go
+deleted file mode 100644
+index b6fa374..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/syslog/syslog.go
++++ /dev/null
+@@ -1,59 +0,0 @@
+-package logrus_syslog
 -
--// post issues a POST request
--func (c *Client) post(key string, value string, ttl uint64) (*RawResponse, error) {
--	logger.Debugf("post %s, %s, ttl: %d, [%s]", key, value, ttl, c.cluster.Leader)
--	p := keyToPath(key)
+-import (
+-	"fmt"
+-	"github.com/Sirupsen/logrus"
+-	"log/syslog"
+-	"os"
+-)
 -
--	req := NewRawRequest("POST", p, buildValues(value, ttl), nil)
--	resp, err := c.SendRequest(req)
+-// SyslogHook to send logs via syslog.
+-type SyslogHook struct {
+-	Writer        *syslog.Writer
+-	SyslogNetwork string
+-	SyslogRaddr   string
+-}
+-
+-// Creates a hook to be added to an instance of logger. This is called with
+-// `hook, err := NewSyslogHook("udp", "localhost:514", syslog.LOG_DEBUG, "")`
+-// `if err == nil { log.Hooks.Add(hook) }`
+-func NewSyslogHook(network, raddr string, priority syslog.Priority, tag string) (*SyslogHook, error) {
+-	w, err := syslog.Dial(network, raddr, priority, tag)
+-	return &SyslogHook{w, network, raddr}, err
+-}
 -
+-func (hook *SyslogHook) Fire(entry *logrus.Entry) error {
+-	line, err := entry.String()
 -	if err != nil {
--		return nil, err
+-		fmt.Fprintf(os.Stderr, "Unable to read entry, %v", err)
+-		return err
 -	}
 -
--	return resp, nil
+-	switch entry.Level {
+-	case logrus.PanicLevel:
+-		return hook.Writer.Crit(line)
+-	case logrus.FatalLevel:
+-		return hook.Writer.Crit(line)
+-	case logrus.ErrorLevel:
+-		return hook.Writer.Err(line)
+-	case logrus.WarnLevel:
+-		return hook.Writer.Warning(line)
+-	case logrus.InfoLevel:
+-		return hook.Writer.Info(line)
+-	case logrus.DebugLevel:
+-		return hook.Writer.Debug(line)
+-	default:
+-		return nil
+-	}
 -}
 -
--// delete issues a DELETE request
--func (c *Client) delete(key string, options Options) (*RawResponse, error) {
--	logger.Debugf("delete %s [%s]", key, c.cluster.Leader)
--	p := keyToPath(key)
+-func (hook *SyslogHook) Levels() []logrus.Level {
+-	return []logrus.Level{
+-		logrus.PanicLevel,
+-		logrus.FatalLevel,
+-		logrus.ErrorLevel,
+-		logrus.WarnLevel,
+-		logrus.InfoLevel,
+-		logrus.DebugLevel,
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/syslog/syslog_test.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/syslog/syslog_test.go
+deleted file mode 100644
+index 42762dc..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/hooks/syslog/syslog_test.go
++++ /dev/null
+@@ -1,26 +0,0 @@
+-package logrus_syslog
+-
+-import (
+-	"github.com/Sirupsen/logrus"
+-	"log/syslog"
+-	"testing"
+-)
+-
+-func TestLocalhostAddAndPrint(t *testing.T) {
+-	log := logrus.New()
+-	hook, err := NewSyslogHook("udp", "localhost:514", syslog.LOG_INFO, "")
 -
--	str, err := options.toParameters(VALID_DELETE_OPTIONS)
 -	if err != nil {
--		return nil, err
+-		t.Errorf("Unable to connect to local syslog.")
 -	}
--	p += str
 -
--	req := NewRawRequest("DELETE", p, nil, nil)
--	resp, err := c.SendRequest(req)
+-	log.Hooks.Add(hook)
 -
--	if err != nil {
--		return nil, err
+-	for _, level := range hook.Levels() {
+-		if len(log.Hooks[level]) != 1 {
+-			t.Errorf("SyslogHook was not added. The length of log.Hooks[%v]: %v", level, len(log.Hooks[level]))
+-		}
 -	}
 -
--	return resp, nil
+-	log.Info("Congratulations!")
 -}
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/json_formatter.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/json_formatter.go
+deleted file mode 100644
+index b09227c..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/json_formatter.go
++++ /dev/null
+@@ -1,26 +0,0 @@
+-package logrus
 -
--// SendRequest sends a HTTP request and returns a Response as defined by etcd
--func (c *Client) SendRequest(rr *RawRequest) (*RawResponse, error) {
--
--	var req *http.Request
--	var resp *http.Response
--	var httpPath string
--	var err error
--	var respBody []byte
+-import (
+-	"encoding/json"
+-	"fmt"
+-	"time"
+-)
 -
--	var numReqs = 1
+-type JSONFormatter struct{}
 -
--	checkRetry := c.CheckRetry
--	if checkRetry == nil {
--		checkRetry = DefaultCheckRetry
+-func (f *JSONFormatter) Format(entry *Entry) ([]byte, error) {
+-	data := make(Fields, len(entry.Data)+3)
+-	for k, v := range entry.Data {
+-		data[k] = v
 -	}
+-	prefixFieldClashes(data)
+-	data["time"] = entry.Time.Format(time.RFC3339)
+-	data["msg"] = entry.Message
+-	data["level"] = entry.Level.String()
 -
--	cancelled := make(chan bool, 1)
--	reqLock := new(sync.Mutex)
--
--	if rr.Cancel != nil {
--		cancelRoutine := make(chan bool)
--		defer close(cancelRoutine)
+-	serialized, err := json.Marshal(data)
+-	if err != nil {
+-		return nil, fmt.Errorf("Failed to marshal fields to JSON, %v", err)
+-	}
+-	return append(serialized, '\n'), nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/logger.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/logger.go
+deleted file mode 100644
+index b392e54..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/logger.go
++++ /dev/null
+@@ -1,161 +0,0 @@
+-package logrus
 -
--		go func() {
--			select {
--			case <-rr.Cancel:
--				cancelled <- true
--				logger.Debug("send.request is cancelled")
--			case <-cancelRoutine:
--				return
--			}
+-import (
+-	"io"
+-	"os"
+-	"sync"
+-)
 -
--			// Repeat canceling request until this thread is stopped
--			// because we have no idea about whether it succeeds.
--			for {
--				reqLock.Lock()
--				c.httpClient.Transport.(*http.Transport).CancelRequest(req)
--				reqLock.Unlock()
+-type Logger struct {
+-	// The logs are `io.Copy`'d to this in a mutex. It's common to set this to a
+-	// file, or leave it default which is `os.Stdout`. You can also set this to
+-	// something more adventorous, such as logging to Kafka.
+-	Out io.Writer
+-	// Hooks for the logger instance. These allow firing events based on logging
+-	// levels and log entries. For example, to send errors to an error tracking
+-	// service, log to StatsD or dump the core on fatal errors.
+-	Hooks levelHooks
+-	// All log entries pass through the formatter before logged to Out. The
+-	// included formatters are `TextFormatter` and `JSONFormatter` for which
+-	// TextFormatter is the default. In development (when a TTY is attached) it
+-	// logs with colors, but to a file it wouldn't. You can easily implement your
+-	// own that implements the `Formatter` interface, see the `README` or included
+-	// formatters for examples.
+-	Formatter Formatter
+-	// The logging level the logger should log at. This is typically (and defaults
+-	// to) `logrus.Info`, which allows Info(), Warn(), Error() and Fatal() to be
+-	// logged. `logrus.Debug` is useful in
+-	Level Level
+-	// Used to sync writing to the log.
+-	mu sync.Mutex
+-}
 -
--				select {
--				case <-time.After(100 * time.Millisecond):
--				case <-cancelRoutine:
--					return
--				}
--			}
--		}()
+-// Creates a new logger. Configuration should be set by changing `Formatter`,
+-// `Out` and `Hooks` directly on the default logger instance. You can also just
+-// instantiate your own:
+-//
+-//    var log = &Logger{
+-//      Out: os.Stderr,
+-//      Formatter: new(JSONFormatter),
+-//      Hooks: make(levelHooks),
+-//      Level: logrus.DebugLevel,
+-//    }
+-//
+-// It's recommended to make this a global instance called `log`.
+-func New() *Logger {
+-	return &Logger{
+-		Out:       os.Stdout,
+-		Formatter: new(TextFormatter),
+-		Hooks:     make(levelHooks),
+-		Level:     InfoLevel,
 -	}
+-}
 -
--	// If we connect to a follower and consistency is required, retry until
--	// we connect to a leader
--	sleep := 25 * time.Millisecond
--	maxSleep := time.Second
--	for attempt := 0; ; attempt++ {
--		if attempt > 0 {
--			select {
--			case <-cancelled:
--				return nil, ErrRequestCancelled
--			case <-time.After(sleep):
--				sleep = sleep * 2
--				if sleep > maxSleep {
--					sleep = maxSleep
--				}
--			}
--		}
--
--		logger.Debug("Connecting to etcd: attempt", attempt+1, "for", rr.RelativePath)
--
--		if rr.Method == "GET" && c.config.Consistency == WEAK_CONSISTENCY {
--			// If it's a GET and consistency level is set to WEAK,
--			// then use a random machine.
--			httpPath = c.getHttpPath(true, rr.RelativePath)
--		} else {
--			// Else use the leader.
--			httpPath = c.getHttpPath(false, rr.RelativePath)
--		}
+-// Adds a field to the log entry, note that you it doesn't log until you call
+-// Debug, Print, Info, Warn, Fatal or Panic. It only creates a log entry.
+-// Ff you want multiple fields, use `WithFields`.
+-func (logger *Logger) WithField(key string, value interface{}) *Entry {
+-	return NewEntry(logger).WithField(key, value)
+-}
 -
--		// Return a cURL command if curlChan is set
--		if c.cURLch != nil {
--			command := fmt.Sprintf("curl -X %s %s", rr.Method, httpPath)
--			for key, value := range rr.Values {
--				command += fmt.Sprintf(" -d %s=%s", key, value[0])
--			}
--			c.sendCURL(command)
--		}
+-// Adds a struct of fields to the log entry. All it does is call `WithField` for
+-// each `Field`.
+-func (logger *Logger) WithFields(fields Fields) *Entry {
+-	return NewEntry(logger).WithFields(fields)
+-}
 -
--		logger.Debug("send.request.to ", httpPath, " | method ", rr.Method)
+-func (logger *Logger) Debugf(format string, args ...interface{}) {
+-	NewEntry(logger).Debugf(format, args...)
+-}
 -
--		reqLock.Lock()
--		if rr.Values == nil {
--			if req, err = http.NewRequest(rr.Method, httpPath, nil); err != nil {
--				return nil, err
--			}
--		} else {
--			body := strings.NewReader(rr.Values.Encode())
--			if req, err = http.NewRequest(rr.Method, httpPath, body); err != nil {
--				return nil, err
--			}
+-func (logger *Logger) Infof(format string, args ...interface{}) {
+-	NewEntry(logger).Infof(format, args...)
+-}
 -
--			req.Header.Set("Content-Type",
--				"application/x-www-form-urlencoded; param=value")
--		}
--		reqLock.Unlock()
+-func (logger *Logger) Printf(format string, args ...interface{}) {
+-	NewEntry(logger).Printf(format, args...)
+-}
 -
--		resp, err = c.httpClient.Do(req)
--		defer func() {
--			if resp != nil {
--				resp.Body.Close()
--			}
--		}()
+-func (logger *Logger) Warnf(format string, args ...interface{}) {
+-	NewEntry(logger).Warnf(format, args...)
+-}
 -
--		// If the request was cancelled, return ErrRequestCancelled directly
--		select {
--		case <-cancelled:
--			return nil, ErrRequestCancelled
--		default:
--		}
+-func (logger *Logger) Warningf(format string, args ...interface{}) {
+-	NewEntry(logger).Warnf(format, args...)
+-}
 -
--		numReqs++
+-func (logger *Logger) Errorf(format string, args ...interface{}) {
+-	NewEntry(logger).Errorf(format, args...)
+-}
 -
--		// network error, change a machine!
--		if err != nil {
--			logger.Debug("network error:", err.Error())
--			lastResp := http.Response{}
--			if checkErr := checkRetry(c.cluster, numReqs, lastResp, err); checkErr != nil {
--				return nil, checkErr
--			}
+-func (logger *Logger) Fatalf(format string, args ...interface{}) {
+-	NewEntry(logger).Fatalf(format, args...)
+-}
 -
--			c.cluster.switchLeader(attempt % len(c.cluster.Machines))
--			continue
--		}
+-func (logger *Logger) Panicf(format string, args ...interface{}) {
+-	NewEntry(logger).Panicf(format, args...)
+-}
 -
--		// if there is no error, it should receive response
--		logger.Debug("recv.response.from", httpPath)
+-func (logger *Logger) Debug(args ...interface{}) {
+-	NewEntry(logger).Debug(args...)
+-}
 -
--		if validHttpStatusCode[resp.StatusCode] {
--			// try to read byte code and break the loop
--			respBody, err = ioutil.ReadAll(resp.Body)
--			if err == nil {
--				logger.Debug("recv.success.", httpPath)
--				break
--			}
--			// ReadAll error may be caused due to cancel request
--			select {
--			case <-cancelled:
--				return nil, ErrRequestCancelled
--			default:
--			}
--		}
+-func (logger *Logger) Info(args ...interface{}) {
+-	NewEntry(logger).Info(args...)
+-}
 -
--		// if resp is TemporaryRedirect, set the new leader and retry
--		if resp.StatusCode == http.StatusTemporaryRedirect {
--			u, err := resp.Location()
+-func (logger *Logger) Print(args ...interface{}) {
+-	NewEntry(logger).Info(args...)
+-}
 -
--			if err != nil {
--				logger.Warning(err)
--			} else {
--				// Update cluster leader based on redirect location
--				// because it should point to the leader address
--				c.cluster.updateLeaderFromURL(u)
--				logger.Debug("recv.response.relocate", u.String())
--			}
--			resp.Body.Close()
--			continue
--		}
+-func (logger *Logger) Warn(args ...interface{}) {
+-	NewEntry(logger).Warn(args...)
+-}
 -
--		if checkErr := checkRetry(c.cluster, numReqs, *resp,
--			errors.New("Unexpected HTTP status code")); checkErr != nil {
--			return nil, checkErr
--		}
--		resp.Body.Close()
--	}
+-func (logger *Logger) Warning(args ...interface{}) {
+-	NewEntry(logger).Warn(args...)
+-}
 -
--	r := &RawResponse{
--		StatusCode: resp.StatusCode,
--		Body:       respBody,
--		Header:     resp.Header,
--	}
+-func (logger *Logger) Error(args ...interface{}) {
+-	NewEntry(logger).Error(args...)
+-}
 -
--	return r, nil
+-func (logger *Logger) Fatal(args ...interface{}) {
+-	NewEntry(logger).Fatal(args...)
 -}
 -
--// DefaultCheckRetry defines the retrying behaviour for bad HTTP requests
--// If we have retried 2 * machine number, stop retrying.
--// If status code is InternalServerError, sleep for 200ms.
--func DefaultCheckRetry(cluster *Cluster, numReqs int, lastResp http.Response,
--	err error) error {
+-func (logger *Logger) Panic(args ...interface{}) {
+-	NewEntry(logger).Panic(args...)
+-}
 -
--	if numReqs >= 2*len(cluster.Machines) {
--		return newError(ErrCodeEtcdNotReachable,
--			"Tried to connect to each peer twice and failed", 0)
--	}
+-func (logger *Logger) Debugln(args ...interface{}) {
+-	NewEntry(logger).Debugln(args...)
+-}
 -
--	code := lastResp.StatusCode
--	if code == http.StatusInternalServerError {
--		time.Sleep(time.Millisecond * 200)
+-func (logger *Logger) Infoln(args ...interface{}) {
+-	NewEntry(logger).Infoln(args...)
+-}
 -
--	}
+-func (logger *Logger) Println(args ...interface{}) {
+-	NewEntry(logger).Println(args...)
+-}
 -
--	logger.Warning("bad response status code", code)
--	return nil
+-func (logger *Logger) Warnln(args ...interface{}) {
+-	NewEntry(logger).Warnln(args...)
 -}
 -
--func (c *Client) getHttpPath(random bool, s ...string) string {
--	var machine string
--	if random {
--		machine = c.cluster.Machines[rand.Intn(len(c.cluster.Machines))]
--	} else {
--		machine = c.cluster.Leader
--	}
+-func (logger *Logger) Warningln(args ...interface{}) {
+-	NewEntry(logger).Warnln(args...)
+-}
 -
--	fullPath := machine + "/" + version
--	for _, seg := range s {
--		fullPath = fullPath + "/" + seg
--	}
+-func (logger *Logger) Errorln(args ...interface{}) {
+-	NewEntry(logger).Errorln(args...)
+-}
 -
--	return fullPath
+-func (logger *Logger) Fatalln(args ...interface{}) {
+-	NewEntry(logger).Fatalln(args...)
 -}
 -
--// buildValues builds a url.Values map according to the given value and ttl
--func buildValues(value string, ttl uint64) url.Values {
--	v := url.Values{}
+-func (logger *Logger) Panicln(args ...interface{}) {
+-	NewEntry(logger).Panicln(args...)
+-}
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/logrus.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/logrus.go
+deleted file mode 100644
+index 43ee12e..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/logrus.go
++++ /dev/null
+@@ -1,94 +0,0 @@
+-package logrus
 -
--	if value != "" {
--		v.Set("value", value)
--	}
+-import (
+-	"fmt"
+-	"log"
+-)
 -
--	if ttl > 0 {
--		v.Set("ttl", fmt.Sprintf("%v", ttl))
--	}
+-// Fields type, used to pass to `WithFields`.
+-type Fields map[string]interface{}
+-
+-// Level type
+-type Level uint8
+-
+-// Convert the Level to a string. E.g. PanicLevel becomes "panic".
+-func (level Level) String() string {
+-	switch level {
+-	case DebugLevel:
+-		return "debug"
+-	case InfoLevel:
+-		return "info"
+-	case WarnLevel:
+-		return "warning"
+-	case ErrorLevel:
+-		return "error"
+-	case FatalLevel:
+-		return "fatal"
+-	case PanicLevel:
+-		return "panic"
+-	}
+-
+-	return "unknown"
+-}
+-
+-// ParseLevel takes a string level and returns the Logrus log level constant.
+-func ParseLevel(lvl string) (Level, error) {
+-	switch lvl {
+-	case "panic":
+-		return PanicLevel, nil
+-	case "fatal":
+-		return FatalLevel, nil
+-	case "error":
+-		return ErrorLevel, nil
+-	case "warn", "warning":
+-		return WarnLevel, nil
+-	case "info":
+-		return InfoLevel, nil
+-	case "debug":
+-		return DebugLevel, nil
+-	}
+-
+-	var l Level
+-	return l, fmt.Errorf("not a valid logrus Level: %q", lvl)
+-}
+-
+-// These are the different logging levels. You can set the logging level to log
+-// on your instance of logger, obtained with `logrus.New()`.
+-const (
+-	// PanicLevel level, highest level of severity. Logs and then calls panic with the
+-	// message passed to Debug, Info, ...
+-	PanicLevel Level = iota
+-	// FatalLevel level. Logs and then calls `os.Exit(1)`. It will exit even if the
+-	// logging level is set to Panic.
+-	FatalLevel
+-	// ErrorLevel level. Logs. Used for errors that should definitely be noted.
+-	// Commonly used for hooks to send errors to an error tracking service.
+-	ErrorLevel
+-	// WarnLevel level. Non-critical entries that deserve eyes.
+-	WarnLevel
+-	// InfoLevel level. General operational entries about what's going on inside the
+-	// application.
+-	InfoLevel
+-	// DebugLevel level. Usually only enabled when debugging. Very verbose logging.
+-	DebugLevel
+-)
 -
--	return v
--}
+-// Won't compile if StdLogger can't be realized by a log.Logger
+-var _ StdLogger = &log.Logger{}
 -
--// convert key string to http path exclude version
--// for example: key[foo] -> path[keys/foo]
--// key[/] -> path[keys/]
--func keyToPath(key string) string {
--	p := path.Join("keys", key)
+-// StdLogger is what your logrus-enabled library should take, that way
+-// it'll accept a stdlib logger and a logrus logger. There's no standard
+-// interface, this is the closest we get, unfortunately.
+-type StdLogger interface {
+-	Print(...interface{})
+-	Printf(string, ...interface{})
+-	Println(...interface{})
 -
--	// corner case: if key is "/" or "//" ect
--	// path join will clear the tailing "/"
--	// we need to add it back
--	if p == "keys" {
--		p = "keys/"
--	}
+-	Fatal(...interface{})
+-	Fatalf(string, ...interface{})
+-	Fatalln(...interface{})
 -
--	return p
+-	Panic(...interface{})
+-	Panicf(string, ...interface{})
+-	Panicln(...interface{})
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/response.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/response.go
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/logrus_test.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/logrus_test.go
 deleted file mode 100644
-index 1fe9b4e..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/response.go
+index 5302542..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/logrus_test.go
 +++ /dev/null
-@@ -1,89 +0,0 @@
--package etcd
+@@ -1,283 +0,0 @@
+-package logrus
 -
 -import (
+-	"bytes"
 -	"encoding/json"
--	"net/http"
 -	"strconv"
--	"time"
--)
+-	"strings"
+-	"testing"
 -
--const (
--	rawResponse = iota
--	normalResponse
+-	"github.com/stretchr/testify/assert"
 -)
 -
--type responseType int
+-func LogAndAssertJSON(t *testing.T, log func(*Logger), assertions func(fields Fields)) {
+-	var buffer bytes.Buffer
+-	var fields Fields
 -
--type RawResponse struct {
--	StatusCode int
--	Body       []byte
--	Header     http.Header
--}
+-	logger := New()
+-	logger.Out = &buffer
+-	logger.Formatter = new(JSONFormatter)
 -
--var (
--	validHttpStatusCode = map[int]bool{
--		http.StatusCreated:            true,
--		http.StatusOK:                 true,
--		http.StatusBadRequest:         true,
--		http.StatusNotFound:           true,
--		http.StatusPreconditionFailed: true,
--		http.StatusForbidden:          true,
--	}
--)
+-	log(logger)
 -
--// Unmarshal parses RawResponse and stores the result in Response
--func (rr *RawResponse) Unmarshal() (*Response, error) {
--	if rr.StatusCode != http.StatusOK && rr.StatusCode != http.StatusCreated {
--		return nil, handleError(rr.Body)
--	}
+-	err := json.Unmarshal(buffer.Bytes(), &fields)
+-	assert.Nil(t, err)
 -
--	resp := new(Response)
+-	assertions(fields)
+-}
 -
--	err := json.Unmarshal(rr.Body, resp)
+-func LogAndAssertText(t *testing.T, log func(*Logger), assertions func(fields map[string]string)) {
+-	var buffer bytes.Buffer
 -
--	if err != nil {
--		return nil, err
+-	logger := New()
+-	logger.Out = &buffer
+-	logger.Formatter = &TextFormatter{
+-		DisableColors: true,
 -	}
 -
--	// attach index and term to response
--	resp.EtcdIndex, _ = strconv.ParseUint(rr.Header.Get("X-Etcd-Index"), 10, 64)
--	resp.RaftIndex, _ = strconv.ParseUint(rr.Header.Get("X-Raft-Index"), 10, 64)
--	resp.RaftTerm, _ = strconv.ParseUint(rr.Header.Get("X-Raft-Term"), 10, 64)
+-	log(logger)
 -
--	return resp, nil
+-	fields := make(map[string]string)
+-	for _, kv := range strings.Split(buffer.String(), " ") {
+-		if !strings.Contains(kv, "=") {
+-			continue
+-		}
+-		kvArr := strings.Split(kv, "=")
+-		key := strings.TrimSpace(kvArr[0])
+-		val := kvArr[1]
+-		if kvArr[1][0] == '"' {
+-			var err error
+-			val, err = strconv.Unquote(val)
+-			assert.NoError(t, err)
+-		}
+-		fields[key] = val
+-	}
+-	assertions(fields)
 -}
 -
--type Response struct {
--	Action    string `json:"action"`
--	Node      *Node  `json:"node"`
--	PrevNode  *Node  `json:"prevNode,omitempty"`
--	EtcdIndex uint64 `json:"etcdIndex"`
--	RaftIndex uint64 `json:"raftIndex"`
--	RaftTerm  uint64 `json:"raftTerm"`
+-func TestPrint(t *testing.T) {
+-	LogAndAssertJSON(t, func(log *Logger) {
+-		log.Print("test")
+-	}, func(fields Fields) {
+-		assert.Equal(t, fields["msg"], "test")
+-		assert.Equal(t, fields["level"], "info")
+-	})
 -}
 -
--type Node struct {
--	Key           string     `json:"key, omitempty"`
--	Value         string     `json:"value,omitempty"`
--	Dir           bool       `json:"dir,omitempty"`
--	Expiration    *time.Time `json:"expiration,omitempty"`
--	TTL           int64      `json:"ttl,omitempty"`
--	Nodes         Nodes      `json:"nodes,omitempty"`
--	ModifiedIndex uint64     `json:"modifiedIndex,omitempty"`
--	CreatedIndex  uint64     `json:"createdIndex,omitempty"`
+-func TestInfo(t *testing.T) {
+-	LogAndAssertJSON(t, func(log *Logger) {
+-		log.Info("test")
+-	}, func(fields Fields) {
+-		assert.Equal(t, fields["msg"], "test")
+-		assert.Equal(t, fields["level"], "info")
+-	})
 -}
 -
--type Nodes []*Node
+-func TestWarn(t *testing.T) {
+-	LogAndAssertJSON(t, func(log *Logger) {
+-		log.Warn("test")
+-	}, func(fields Fields) {
+-		assert.Equal(t, fields["msg"], "test")
+-		assert.Equal(t, fields["level"], "warning")
+-	})
+-}
 -
--// interfaces for sorting
--func (ns Nodes) Len() int {
--	return len(ns)
+-func TestInfolnShouldAddSpacesBetweenStrings(t *testing.T) {
+-	LogAndAssertJSON(t, func(log *Logger) {
+-		log.Infoln("test", "test")
+-	}, func(fields Fields) {
+-		assert.Equal(t, fields["msg"], "test test")
+-	})
 -}
 -
--func (ns Nodes) Less(i, j int) bool {
--	return ns[i].Key < ns[j].Key
+-func TestInfolnShouldAddSpacesBetweenStringAndNonstring(t *testing.T) {
+-	LogAndAssertJSON(t, func(log *Logger) {
+-		log.Infoln("test", 10)
+-	}, func(fields Fields) {
+-		assert.Equal(t, fields["msg"], "test 10")
+-	})
 -}
 -
--func (ns Nodes) Swap(i, j int) {
--	ns[i], ns[j] = ns[j], ns[i]
+-func TestInfolnShouldAddSpacesBetweenTwoNonStrings(t *testing.T) {
+-	LogAndAssertJSON(t, func(log *Logger) {
+-		log.Infoln(10, 10)
+-	}, func(fields Fields) {
+-		assert.Equal(t, fields["msg"], "10 10")
+-	})
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/set_curl_chan_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/set_curl_chan_test.go
-deleted file mode 100644
-index 756e317..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/set_curl_chan_test.go
-+++ /dev/null
-@@ -1,42 +0,0 @@
--package etcd
 -
--import (
--	"fmt"
--	"testing"
--)
+-func TestInfoShouldAddSpacesBetweenTwoNonStrings(t *testing.T) {
+-	LogAndAssertJSON(t, func(log *Logger) {
+-		log.Infoln(10, 10)
+-	}, func(fields Fields) {
+-		assert.Equal(t, fields["msg"], "10 10")
+-	})
+-}
 -
--func TestSetCurlChan(t *testing.T) {
--	c := NewClient(nil)
--	c.OpenCURL()
+-func TestInfoShouldNotAddSpacesBetweenStringAndNonstring(t *testing.T) {
+-	LogAndAssertJSON(t, func(log *Logger) {
+-		log.Info("test", 10)
+-	}, func(fields Fields) {
+-		assert.Equal(t, fields["msg"], "test10")
+-	})
+-}
 -
--	defer func() {
--		c.Delete("foo", true)
--	}()
+-func TestInfoShouldNotAddSpacesBetweenStrings(t *testing.T) {
+-	LogAndAssertJSON(t, func(log *Logger) {
+-		log.Info("test", "test")
+-	}, func(fields Fields) {
+-		assert.Equal(t, fields["msg"], "testtest")
+-	})
+-}
 -
--	_, err := c.Set("foo", "bar", 5)
--	if err != nil {
--		t.Fatal(err)
--	}
+-func TestWithFieldsShouldAllowAssignments(t *testing.T) {
+-	var buffer bytes.Buffer
+-	var fields Fields
 -
--	expected := fmt.Sprintf("curl -X PUT %s/v2/keys/foo -d value=bar -d ttl=5",
--		c.cluster.Leader)
--	actual := c.RecvCURL()
--	if expected != actual {
--		t.Fatalf(`Command "%s" is not equal to expected value "%s"`,
--			actual, expected)
--	}
+-	logger := New()
+-	logger.Out = &buffer
+-	logger.Formatter = new(JSONFormatter)
 -
--	c.SetConsistency(STRONG_CONSISTENCY)
--	_, err = c.Get("foo", false, false)
--	if err != nil {
--		t.Fatal(err)
--	}
+-	localLog := logger.WithFields(Fields{
+-		"key1": "value1",
+-	})
 -
--	expected = fmt.Sprintf("curl -X GET %s/v2/keys/foo?consistent=true&recursive=false&sorted=false",
--		c.cluster.Leader)
--	actual = c.RecvCURL()
--	if expected != actual {
--		t.Fatalf(`Command "%s" is not equal to expected value "%s"`,
--			actual, expected)
--	}
--}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/set_update_create.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/set_update_create.go
-deleted file mode 100644
-index cb0d567..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/set_update_create.go
-+++ /dev/null
-@@ -1,137 +0,0 @@
--package etcd
+-	localLog.WithField("key2", "value2").Info("test")
+-	err := json.Unmarshal(buffer.Bytes(), &fields)
+-	assert.Nil(t, err)
 -
--// Set sets the given key to the given value.
--// It will create a new key value pair or replace the old one.
--// It will not replace a existing directory.
--func (c *Client) Set(key string, value string, ttl uint64) (*Response, error) {
--	raw, err := c.RawSet(key, value, ttl)
+-	assert.Equal(t, "value2", fields["key2"])
+-	assert.Equal(t, "value1", fields["key1"])
 -
--	if err != nil {
--		return nil, err
--	}
+-	buffer = bytes.Buffer{}
+-	fields = Fields{}
+-	localLog.Info("test")
+-	err = json.Unmarshal(buffer.Bytes(), &fields)
+-	assert.Nil(t, err)
 -
--	return raw.Unmarshal()
+-	_, ok := fields["key2"]
+-	assert.Equal(t, false, ok)
+-	assert.Equal(t, "value1", fields["key1"])
 -}
 -
--// Set sets the given key to a directory.
--// It will create a new directory or replace the old key value pair by a directory.
--// It will not replace a existing directory.
--func (c *Client) SetDir(key string, ttl uint64) (*Response, error) {
--	raw, err := c.RawSetDir(key, ttl)
+-func TestUserSuppliedFieldDoesNotOverwriteDefaults(t *testing.T) {
+-	LogAndAssertJSON(t, func(log *Logger) {
+-		log.WithField("msg", "hello").Info("test")
+-	}, func(fields Fields) {
+-		assert.Equal(t, fields["msg"], "test")
+-	})
+-}
 -
--	if err != nil {
--		return nil, err
--	}
+-func TestUserSuppliedMsgFieldHasPrefix(t *testing.T) {
+-	LogAndAssertJSON(t, func(log *Logger) {
+-		log.WithField("msg", "hello").Info("test")
+-	}, func(fields Fields) {
+-		assert.Equal(t, fields["msg"], "test")
+-		assert.Equal(t, fields["fields.msg"], "hello")
+-	})
+-}
 -
--	return raw.Unmarshal()
+-func TestUserSuppliedTimeFieldHasPrefix(t *testing.T) {
+-	LogAndAssertJSON(t, func(log *Logger) {
+-		log.WithField("time", "hello").Info("test")
+-	}, func(fields Fields) {
+-		assert.Equal(t, fields["fields.time"], "hello")
+-	})
 -}
 -
--// CreateDir creates a directory. It succeeds only if
--// the given key does not yet exist.
--func (c *Client) CreateDir(key string, ttl uint64) (*Response, error) {
--	raw, err := c.RawCreateDir(key, ttl)
+-func TestUserSuppliedLevelFieldHasPrefix(t *testing.T) {
+-	LogAndAssertJSON(t, func(log *Logger) {
+-		log.WithField("level", 1).Info("test")
+-	}, func(fields Fields) {
+-		assert.Equal(t, fields["level"], "info")
+-		assert.Equal(t, fields["fields.level"], 1)
+-	})
+-}
 -
--	if err != nil {
--		return nil, err
--	}
--
--	return raw.Unmarshal()
+-func TestDefaultFieldsAreNotPrefixed(t *testing.T) {
+-	LogAndAssertText(t, func(log *Logger) {
+-		ll := log.WithField("herp", "derp")
+-		ll.Info("hello")
+-		ll.Info("bye")
+-	}, func(fields map[string]string) {
+-		for _, fieldName := range []string{"fields.level", "fields.time", "fields.msg"} {
+-			if _, ok := fields[fieldName]; ok {
+-				t.Fatalf("should not have prefixed %q: %v", fieldName, fields)
+-			}
+-		}
+-	})
 -}
 -
--// UpdateDir updates the given directory. It succeeds only if the
--// given key already exists.
--func (c *Client) UpdateDir(key string, ttl uint64) (*Response, error) {
--	raw, err := c.RawUpdateDir(key, ttl)
+-func TestDoubleLoggingDoesntPrefixPreviousFields(t *testing.T) {
 -
--	if err != nil {
--		return nil, err
--	}
+-	var buffer bytes.Buffer
+-	var fields Fields
+-
+-	logger := New()
+-	logger.Out = &buffer
+-	logger.Formatter = new(JSONFormatter)
+-
+-	llog := logger.WithField("context", "eating raw fish")
+-
+-	llog.Info("looks delicious")
+-
+-	err := json.Unmarshal(buffer.Bytes(), &fields)
+-	assert.NoError(t, err, "should have decoded first message")
+-	assert.Len(t, fields, 4, "should only have msg/time/level/context fields")
+-	assert.Equal(t, fields["msg"], "looks delicious")
+-	assert.Equal(t, fields["context"], "eating raw fish")
+-
+-	buffer.Reset()
+-
+-	llog.Warn("omg it is!")
+-
+-	err = json.Unmarshal(buffer.Bytes(), &fields)
+-	assert.NoError(t, err, "should have decoded second message")
+-	assert.Len(t, fields, 4, "should only have msg/time/level/context fields")
+-	assert.Equal(t, fields["msg"], "omg it is!")
+-	assert.Equal(t, fields["context"], "eating raw fish")
+-	assert.Nil(t, fields["fields.msg"], "should not have prefixed previous `msg` entry")
 -
--	return raw.Unmarshal()
 -}
 -
--// Create creates a file with the given value under the given key.  It succeeds
--// only if the given key does not yet exist.
--func (c *Client) Create(key string, value string, ttl uint64) (*Response, error) {
--	raw, err := c.RawCreate(key, value, ttl)
+-func TestConvertLevelToString(t *testing.T) {
+-	assert.Equal(t, "debug", DebugLevel.String())
+-	assert.Equal(t, "info", InfoLevel.String())
+-	assert.Equal(t, "warning", WarnLevel.String())
+-	assert.Equal(t, "error", ErrorLevel.String())
+-	assert.Equal(t, "fatal", FatalLevel.String())
+-	assert.Equal(t, "panic", PanicLevel.String())
+-}
 -
--	if err != nil {
--		return nil, err
--	}
+-func TestParseLevel(t *testing.T) {
+-	l, err := ParseLevel("panic")
+-	assert.Nil(t, err)
+-	assert.Equal(t, PanicLevel, l)
 -
--	return raw.Unmarshal()
+-	l, err = ParseLevel("fatal")
+-	assert.Nil(t, err)
+-	assert.Equal(t, FatalLevel, l)
+-
+-	l, err = ParseLevel("error")
+-	assert.Nil(t, err)
+-	assert.Equal(t, ErrorLevel, l)
+-
+-	l, err = ParseLevel("warn")
+-	assert.Nil(t, err)
+-	assert.Equal(t, WarnLevel, l)
+-
+-	l, err = ParseLevel("warning")
+-	assert.Nil(t, err)
+-	assert.Equal(t, WarnLevel, l)
+-
+-	l, err = ParseLevel("info")
+-	assert.Nil(t, err)
+-	assert.Equal(t, InfoLevel, l)
+-
+-	l, err = ParseLevel("debug")
+-	assert.Nil(t, err)
+-	assert.Equal(t, DebugLevel, l)
+-
+-	l, err = ParseLevel("invalid")
+-	assert.Equal(t, "not a valid logrus Level: \"invalid\"", err.Error())
 -}
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_darwin.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_darwin.go
+deleted file mode 100644
+index 8fe02a4..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_darwin.go
++++ /dev/null
+@@ -1,12 +0,0 @@
+-// Based on ssh/terminal:
+-// Copyright 2013 The Go Authors. All rights reserved.
+-// Use of this source code is governed by a BSD-style
+-// license that can be found in the LICENSE file.
 -
--// CreateInOrder creates a file with a key that's guaranteed to be higher than other
--// keys in the given directory. It is useful for creating queues.
--func (c *Client) CreateInOrder(dir string, value string, ttl uint64) (*Response, error) {
--	raw, err := c.RawCreateInOrder(dir, value, ttl)
+-package logrus
 -
--	if err != nil {
--		return nil, err
--	}
+-import "syscall"
 -
--	return raw.Unmarshal()
+-const ioctlReadTermios = syscall.TIOCGETA
+-
+-type Termios syscall.Termios
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_freebsd.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_freebsd.go
+deleted file mode 100644
+index 0428ee5..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_freebsd.go
++++ /dev/null
+@@ -1,20 +0,0 @@
+-/*
+-  Go 1.2 doesn't include Termios for FreeBSD. This should be added in 1.3 and this could be merged with terminal_darwin.
+-*/
+-package logrus
+-
+-import (
+-	"syscall"
+-)
+-
+-const ioctlReadTermios = syscall.TIOCGETA
+-
+-type Termios struct {
+-	Iflag  uint32
+-	Oflag  uint32
+-	Cflag  uint32
+-	Lflag  uint32
+-	Cc     [20]uint8
+-	Ispeed uint32
+-	Ospeed uint32
 -}
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_linux.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_linux.go
+deleted file mode 100644
+index a2c0b40..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_linux.go
++++ /dev/null
+@@ -1,12 +0,0 @@
+-// Based on ssh/terminal:
+-// Copyright 2013 The Go Authors. All rights reserved.
+-// Use of this source code is governed by a BSD-style
+-// license that can be found in the LICENSE file.
 -
--// Update updates the given key to the given value.  It succeeds only if the
--// given key already exists.
--func (c *Client) Update(key string, value string, ttl uint64) (*Response, error) {
--	raw, err := c.RawUpdate(key, value, ttl)
+-package logrus
 -
--	if err != nil {
--		return nil, err
--	}
+-import "syscall"
 -
--	return raw.Unmarshal()
+-const ioctlReadTermios = syscall.TCGETS
+-
+-type Termios syscall.Termios
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_notwindows.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_notwindows.go
+deleted file mode 100644
+index 276447b..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_notwindows.go
++++ /dev/null
+@@ -1,21 +0,0 @@
+-// Based on ssh/terminal:
+-// Copyright 2011 The Go Authors. All rights reserved.
+-// Use of this source code is governed by a BSD-style
+-// license that can be found in the LICENSE file.
+-
+-// +build linux,!appengine darwin freebsd
+-
+-package logrus
+-
+-import (
+-	"syscall"
+-	"unsafe"
+-)
+-
+-// IsTerminal returns true if the given file descriptor is a terminal.
+-func IsTerminal() bool {
+-	fd := syscall.Stdout
+-	var termios Termios
+-	_, _, err := syscall.Syscall6(syscall.SYS_IOCTL, uintptr(fd), ioctlReadTermios, uintptr(unsafe.Pointer(&termios)), 0, 0, 0)
+-	return err == 0
 -}
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_windows.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_windows.go
+deleted file mode 100644
+index 2e09f6f..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/terminal_windows.go
++++ /dev/null
+@@ -1,27 +0,0 @@
+-// Based on ssh/terminal:
+-// Copyright 2011 The Go Authors. All rights reserved.
+-// Use of this source code is governed by a BSD-style
+-// license that can be found in the LICENSE file.
 -
--func (c *Client) RawUpdateDir(key string, ttl uint64) (*RawResponse, error) {
--	ops := Options{
--		"prevExist": true,
--		"dir":       true,
--	}
+-// +build windows
 -
--	return c.put(key, "", ttl, ops)
+-package logrus
+-
+-import (
+-	"syscall"
+-	"unsafe"
+-)
+-
+-var kernel32 = syscall.NewLazyDLL("kernel32.dll")
+-
+-var (
+-	procGetConsoleMode = kernel32.NewProc("GetConsoleMode")
+-)
+-
+-// IsTerminal returns true if the given file descriptor is a terminal.
+-func IsTerminal() bool {
+-	fd := syscall.Stdout
+-	var st uint32
+-	r, _, e := syscall.Syscall(procGetConsoleMode.Addr(), 2, uintptr(fd), uintptr(unsafe.Pointer(&st)), 0)
+-	return r != 0 && e == 0
 -}
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/text_formatter.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/text_formatter.go
+deleted file mode 100644
+index 78e7889..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/text_formatter.go
++++ /dev/null
+@@ -1,124 +0,0 @@
+-package logrus
 -
--func (c *Client) RawCreateDir(key string, ttl uint64) (*RawResponse, error) {
--	ops := Options{
--		"prevExist": false,
--		"dir":       true,
--	}
+-import (
+-	"bytes"
+-	"fmt"
+-	"regexp"
+-	"sort"
+-	"strings"
+-	"time"
+-)
 -
--	return c.put(key, "", ttl, ops)
+-const (
+-	nocolor = 0
+-	red     = 31
+-	green   = 32
+-	yellow  = 33
+-	blue    = 34
+-)
+-
+-var (
+-	baseTimestamp time.Time
+-	isTerminal    bool
+-	noQuoteNeeded *regexp.Regexp
+-)
+-
+-func init() {
+-	baseTimestamp = time.Now()
+-	isTerminal = IsTerminal()
 -}
 -
--func (c *Client) RawSet(key string, value string, ttl uint64) (*RawResponse, error) {
--	return c.put(key, value, ttl, nil)
+-func miniTS() int {
+-	return int(time.Since(baseTimestamp) / time.Second)
 -}
 -
--func (c *Client) RawSetDir(key string, ttl uint64) (*RawResponse, error) {
--	ops := Options{
--		"dir": true,
+-type TextFormatter struct {
+-	// Set to true to bypass checking for a TTY before outputting colors.
+-	ForceColors   bool
+-	DisableColors bool
+-	// Set to true to disable timestamp logging (useful when the output
+-	// is redirected to a logging system already adding a timestamp)
+-	DisableTimestamp bool
+-}
+-
+-func (f *TextFormatter) Format(entry *Entry) ([]byte, error) {
+-
+-	var keys []string
+-	for k := range entry.Data {
+-		keys = append(keys, k)
 -	}
+-	sort.Strings(keys)
 -
--	return c.put(key, "", ttl, ops)
--}
+-	b := &bytes.Buffer{}
 -
--func (c *Client) RawUpdate(key string, value string, ttl uint64) (*RawResponse, error) {
--	ops := Options{
--		"prevExist": true,
+-	prefixFieldClashes(entry.Data)
+-
+-	isColored := (f.ForceColors || isTerminal) && !f.DisableColors
+-
+-	if isColored {
+-		printColored(b, entry, keys)
+-	} else {
+-		if !f.DisableTimestamp {
+-			f.appendKeyValue(b, "time", entry.Time.Format(time.RFC3339))
+-		}
+-		f.appendKeyValue(b, "level", entry.Level.String())
+-		f.appendKeyValue(b, "msg", entry.Message)
+-		for _, key := range keys {
+-			f.appendKeyValue(b, key, entry.Data[key])
+-		}
 -	}
 -
--	return c.put(key, value, ttl, ops)
+-	b.WriteByte('\n')
+-	return b.Bytes(), nil
 -}
 -
--func (c *Client) RawCreate(key string, value string, ttl uint64) (*RawResponse, error) {
--	ops := Options{
--		"prevExist": false,
+-func printColored(b *bytes.Buffer, entry *Entry, keys []string) {
+-	var levelColor int
+-	switch entry.Level {
+-	case WarnLevel:
+-		levelColor = yellow
+-	case ErrorLevel, FatalLevel, PanicLevel:
+-		levelColor = red
+-	default:
+-		levelColor = blue
 -	}
 -
--	return c.put(key, value, ttl, ops)
+-	levelText := strings.ToUpper(entry.Level.String())[0:4]
+-
+-	fmt.Fprintf(b, "\x1b[%dm%s\x1b[0m[%04d] %-44s ", levelColor, levelText, miniTS(), entry.Message)
+-	for _, k := range keys {
+-		v := entry.Data[k]
+-		fmt.Fprintf(b, " \x1b[%dm%s\x1b[0m=%v", levelColor, k, v)
+-	}
 -}
 -
--func (c *Client) RawCreateInOrder(dir string, value string, ttl uint64) (*RawResponse, error) {
--	return c.post(dir, value, ttl)
+-func needsQuoting(text string) bool {
+-	for _, ch := range text {
+-		if !((ch >= 'a' && ch <= 'z') ||
+-			(ch >= 'A' && ch <= 'Z') ||
+-			(ch >= '0' && ch < '9') ||
+-			ch == '-' || ch == '.') {
+-			return false
+-		}
+-	}
+-	return true
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/set_update_create_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/set_update_create_test.go
+-
+-func (f *TextFormatter) appendKeyValue(b *bytes.Buffer, key, value interface{}) {
+-	switch value.(type) {
+-	case string:
+-		if needsQuoting(value.(string)) {
+-			fmt.Fprintf(b, "%v=%s ", key, value)
+-		} else {
+-			fmt.Fprintf(b, "%v=%q ", key, value)
+-		}
+-	case error:
+-		if needsQuoting(value.(error).Error()) {
+-			fmt.Fprintf(b, "%v=%s ", key, value)
+-		} else {
+-			fmt.Fprintf(b, "%v=%q ", key, value)
+-		}
+-	default:
+-		fmt.Fprintf(b, "%v=%v ", key, value)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/Sirupsen/logrus/text_formatter_test.go b/Godeps/_workspace/src/github.com/Sirupsen/logrus/text_formatter_test.go
 deleted file mode 100644
-index ced0f06..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/set_update_create_test.go
+index f604f1b..0000000
+--- a/Godeps/_workspace/src/github.com/Sirupsen/logrus/text_formatter_test.go
 +++ /dev/null
-@@ -1,241 +0,0 @@
--package etcd
+@@ -1,33 +0,0 @@
+-package logrus
 -
 -import (
+-	"bytes"
+-	"errors"
+-
 -	"testing"
 -)
 -
--func TestSet(t *testing.T) {
--	c := NewClient(nil)
--	defer func() {
--		c.Delete("foo", true)
--	}()
+-func TestQuoting(t *testing.T) {
+-	tf := &TextFormatter{DisableColors: true}
 -
--	resp, err := c.Set("foo", "bar", 5)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if resp.Node.Key != "/foo" || resp.Node.Value != "bar" || resp.Node.TTL != 5 {
--		t.Fatalf("Set 1 failed: %#v", resp)
--	}
--	if resp.PrevNode != nil {
--		t.Fatalf("Set 1 PrevNode failed: %#v", resp)
+-	checkQuoting := func(q bool, value interface{}) {
+-		b, _ := tf.Format(WithField("test", value))
+-		idx := bytes.Index(b, ([]byte)("test="))
+-		cont := bytes.Contains(b[idx+5:], []byte{'"'})
+-		if cont != q {
+-			if q {
+-				t.Errorf("quoting expected for: %#v", value)
+-			} else {
+-				t.Errorf("quoting not expected for: %#v", value)
+-			}
+-		}
 -	}
 -
--	resp, err = c.Set("foo", "bar2", 5)
+-	checkQuoting(false, "abcd")
+-	checkQuoting(false, "v1.0")
+-	checkQuoting(true, "/foobar")
+-	checkQuoting(true, "x y")
+-	checkQuoting(true, "x,y")
+-	checkQuoting(false, errors.New("invalid"))
+-	checkQuoting(true, errors.New("invalid argument"))
+-}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/add_child.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/add_child.go
+deleted file mode 100644
+index 7122be0..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/add_child.go
++++ /dev/null
+@@ -1,23 +0,0 @@
+-package etcd
+-
+-// Add a new directory with a random etcd-generated key under the given path.
+-func (c *Client) AddChildDir(key string, ttl uint64) (*Response, error) {
+-	raw, err := c.post(key, "", ttl)
+-
 -	if err != nil {
--		t.Fatal(err)
--	}
--	if !(resp.Node.Key == "/foo" && resp.Node.Value == "bar2" && resp.Node.TTL == 5) {
--		t.Fatalf("Set 2 failed: %#v", resp)
+-		return nil, err
 -	}
--	if resp.PrevNode.Key != "/foo" || resp.PrevNode.Value != "bar" || resp.Node.TTL != 5 {
--		t.Fatalf("Set 2 PrevNode failed: %#v", resp)
+-
+-	return raw.Unmarshal()
+-}
+-
+-// Add a new file with a random etcd-generated key under the given path.
+-func (c *Client) AddChild(key string, value string, ttl uint64) (*Response, error) {
+-	raw, err := c.post(key, value, ttl)
+-
+-	if err != nil {
+-		return nil, err
 -	}
+-
+-	return raw.Unmarshal()
 -}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/add_child_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/add_child_test.go
+deleted file mode 100644
+index 26223ff..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/add_child_test.go
++++ /dev/null
+@@ -1,73 +0,0 @@
+-package etcd
 -
--func TestUpdate(t *testing.T) {
+-import "testing"
+-
+-func TestAddChild(t *testing.T) {
 -	c := NewClient(nil)
 -	defer func() {
--		c.Delete("foo", true)
--		c.Delete("nonexistent", true)
+-		c.Delete("fooDir", true)
+-		c.Delete("nonexistentDir", true)
 -	}()
 -
--	resp, err := c.Set("foo", "bar", 5)
+-	c.CreateDir("fooDir", 5)
 -
+-	_, err := c.AddChild("fooDir", "v0", 5)
 -	if err != nil {
 -		t.Fatal(err)
 -	}
 -
--	// This should succeed.
--	resp, err = c.Update("foo", "wakawaka", 5)
+-	_, err = c.AddChild("fooDir", "v1", 5)
 -	if err != nil {
 -		t.Fatal(err)
 -	}
 -
--	if !(resp.Action == "update" && resp.Node.Key == "/foo" && resp.Node.TTL == 5) {
--		t.Fatalf("Update 1 failed: %#v", resp)
--	}
--	if !(resp.PrevNode.Key == "/foo" && resp.PrevNode.Value == "bar" && resp.Node.TTL == 5) {
--		t.Fatalf("Update 1 prevValue failed: %#v", resp)
+-	resp, err := c.Get("fooDir", true, false)
+-	// The child with v0 should proceed the child with v1 because it's added
+-	// earlier, so it should have a lower key.
+-	if !(len(resp.Node.Nodes) == 2 && (resp.Node.Nodes[0].Value == "v0" && resp.Node.Nodes[1].Value == "v1")) {
+-		t.Fatalf("AddChild 1 failed.  There should be two chlidren whose values are v0 and v1, respectively."+
+-			"  The response was: %#v", resp)
 -	}
 -
--	// This should fail because the key does not exist.
--	resp, err = c.Update("nonexistent", "whatever", 5)
--	if err == nil {
--		t.Fatalf("The key %v did not exist, so the update should have failed."+
--			"The response was: %#v", resp.Node.Key, resp)
+-	// Creating a child under a nonexistent directory should succeed.
+-	// The directory should be created.
+-	resp, err = c.AddChild("nonexistentDir", "foo", 5)
+-	if err != nil {
+-		t.Fatal(err)
 -	}
 -}
 -
--func TestCreate(t *testing.T) {
+-func TestAddChildDir(t *testing.T) {
 -	c := NewClient(nil)
 -	defer func() {
--		c.Delete("newKey", true)
+-		c.Delete("fooDir", true)
+-		c.Delete("nonexistentDir", true)
 -	}()
 -
--	newKey := "/newKey"
--	newValue := "/newValue"
+-	c.CreateDir("fooDir", 5)
 -
--	// This should succeed
--	resp, err := c.Create(newKey, newValue, 5)
+-	_, err := c.AddChildDir("fooDir", 5)
 -	if err != nil {
 -		t.Fatal(err)
 -	}
 -
--	if !(resp.Action == "create" && resp.Node.Key == newKey &&
--		resp.Node.Value == newValue && resp.Node.TTL == 5) {
--		t.Fatalf("Create 1 failed: %#v", resp)
+-	_, err = c.AddChildDir("fooDir", 5)
+-	if err != nil {
+-		t.Fatal(err)
 -	}
--	if resp.PrevNode != nil {
--		t.Fatalf("Create 1 PrevNode failed: %#v", resp)
+-
+-	resp, err := c.Get("fooDir", true, false)
+-	// The child with v0 should proceed the child with v1 because it's added
+-	// earlier, so it should have a lower key.
+-	if !(len(resp.Node.Nodes) == 2 && (len(resp.Node.Nodes[0].Nodes) == 0 && len(resp.Node.Nodes[1].Nodes) == 0)) {
+-		t.Fatalf("AddChildDir 1 failed.  There should be two chlidren whose values are v0 and v1, respectively."+
+-			"  The response was: %#v", resp)
 -	}
 -
--	// This should fail, because the key is already there
--	resp, err = c.Create(newKey, newValue, 5)
--	if err == nil {
--		t.Fatalf("The key %v did exist, so the creation should have failed."+
--			"The response was: %#v", resp.Node.Key, resp)
+-	// Creating a child under a nonexistent directory should succeed.
+-	// The directory should be created.
+-	resp, err = c.AddChildDir("nonexistentDir", 5)
+-	if err != nil {
+-		t.Fatal(err)
 -	}
 -}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/client.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/client.go
+deleted file mode 100644
+index f6ae548..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/client.go
++++ /dev/null
+@@ -1,435 +0,0 @@
+-package etcd
 -
--func TestCreateInOrder(t *testing.T) {
--	c := NewClient(nil)
--	dir := "/queue"
--	defer func() {
--		c.DeleteDir(dir)
--	}()
+-import (
+-	"crypto/tls"
+-	"crypto/x509"
+-	"encoding/json"
+-	"errors"
+-	"io"
+-	"io/ioutil"
+-	"net"
+-	"net/http"
+-	"net/url"
+-	"os"
+-	"path"
+-	"time"
+-)
 -
--	var firstKey, secondKey string
+-// See SetConsistency for how to use these constants.
+-const (
+-	// Using strings rather than iota because the consistency level
+-	// could be persisted to disk, so it'd be better to use
+-	// human-readable values.
+-	STRONG_CONSISTENCY = "STRONG"
+-	WEAK_CONSISTENCY   = "WEAK"
+-)
 -
--	resp, err := c.CreateInOrder(dir, "1", 5)
--	if err != nil {
--		t.Fatal(err)
--	}
+-const (
+-	defaultBufferSize = 10
+-)
 -
--	if !(resp.Action == "create" && resp.Node.Value == "1" && resp.Node.TTL == 5) {
--		t.Fatalf("Create 1 failed: %#v", resp)
--	}
+-type Config struct {
+-	CertFile    string        `json:"certFile"`
+-	KeyFile     string        `json:"keyFile"`
+-	CaCertFile  []string      `json:"caCertFiles"`
+-	DialTimeout time.Duration `json:"timeout"`
+-	Consistency string        `json:"consistency"`
+-}
 -
--	firstKey = resp.Node.Key
+-type Client struct {
+-	config      Config   `json:"config"`
+-	cluster     *Cluster `json:"cluster"`
+-	httpClient  *http.Client
+-	persistence io.Writer
+-	cURLch      chan string
+-	// CheckRetry can be used to control the policy for failed requests
+-	// and modify the cluster if needed.
+-	// The client calls it before sending requests again, and
+-	// stops retrying if CheckRetry returns some error. The cases that
+-	// this function needs to handle include no response and unexpected
+-	// http status code of response.
+-	// If CheckRetry is nil, client will call the default one
+-	// `DefaultCheckRetry`.
+-	// Argument cluster is the etcd.Cluster object that these requests have been made on.
+-	// Argument numReqs is the number of http.Requests that have been made so far.
+-	// Argument lastResp is the http.Responses from the last request.
+-	// Argument err is the reason of the failure.
+-	CheckRetry func(cluster *Cluster, numReqs int,
+-		lastResp http.Response, err error) error
+-}
 -
--	resp, err = c.CreateInOrder(dir, "2", 5)
--	if err != nil {
--		t.Fatal(err)
+-// NewClient create a basic client that is configured to be used
+-// with the given machine list.
+-func NewClient(machines []string) *Client {
+-	config := Config{
+-		// default timeout is one second
+-		DialTimeout: time.Second,
+-		// default consistency level is STRONG
+-		Consistency: STRONG_CONSISTENCY,
 -	}
 -
--	if !(resp.Action == "create" && resp.Node.Value == "2" && resp.Node.TTL == 5) {
--		t.Fatalf("Create 2 failed: %#v", resp)
+-	client := &Client{
+-		cluster: NewCluster(machines),
+-		config:  config,
 -	}
 -
--	secondKey = resp.Node.Key
+-	client.initHTTPClient()
+-	client.saveConfig()
 -
--	if firstKey >= secondKey {
--		t.Fatalf("Expected first key to be greater than second key, but %s is not greater than %s",
--			firstKey, secondKey)
--	}
+-	return client
 -}
 -
--func TestSetDir(t *testing.T) {
--	c := NewClient(nil)
--	defer func() {
--		c.Delete("foo", true)
--		c.Delete("fooDir", true)
--	}()
--
--	resp, err := c.CreateDir("fooDir", 5)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if !(resp.Node.Key == "/fooDir" && resp.Node.Value == "" && resp.Node.TTL == 5) {
--		t.Fatalf("SetDir 1 failed: %#v", resp)
+-// NewTLSClient create a basic client with TLS configuration
+-func NewTLSClient(machines []string, cert, key, caCert string) (*Client, error) {
+-	// overwrite the default machine to use https
+-	if len(machines) == 0 {
+-		machines = []string{"https://127.0.0.1:4001"}
 -	}
--	if resp.PrevNode != nil {
--		t.Fatalf("SetDir 1 PrevNode failed: %#v", resp)
+-
+-	config := Config{
+-		// default timeout is one second
+-		DialTimeout: time.Second,
+-		// default consistency level is STRONG
+-		Consistency: STRONG_CONSISTENCY,
+-		CertFile:    cert,
+-		KeyFile:     key,
+-		CaCertFile:  make([]string, 0),
 -	}
 -
--	// This should fail because /fooDir already points to a directory
--	resp, err = c.CreateDir("/fooDir", 5)
--	if err == nil {
--		t.Fatalf("fooDir already points to a directory, so SetDir should have failed."+
--			"The response was: %#v", resp)
+-	client := &Client{
+-		cluster: NewCluster(machines),
+-		config:  config,
 -	}
 -
--	_, err = c.Set("foo", "bar", 5)
+-	err := client.initHTTPSClient(cert, key)
 -	if err != nil {
--		t.Fatal(err)
+-		return nil, err
 -	}
 -
--	// This should succeed
--	// It should replace the key
--	resp, err = c.SetDir("foo", 5)
+-	err = client.AddRootCA(caCert)
+-
+-	client.saveConfig()
+-
+-	return client, nil
+-}
+-
+-// NewClientFromFile creates a client from a given file path.
+-// The given file is expected to use the JSON format.
+-func NewClientFromFile(fpath string) (*Client, error) {
+-	fi, err := os.Open(fpath)
 -	if err != nil {
--		t.Fatal(err)
--	}
--	if !(resp.Node.Key == "/foo" && resp.Node.Value == "" && resp.Node.TTL == 5) {
--		t.Fatalf("SetDir 2 failed: %#v", resp)
--	}
--	if !(resp.PrevNode.Key == "/foo" && resp.PrevNode.Value == "bar" && resp.PrevNode.TTL == 5) {
--		t.Fatalf("SetDir 2 failed: %#v", resp)
+-		return nil, err
 -	}
--}
 -
--func TestUpdateDir(t *testing.T) {
--	c := NewClient(nil)
 -	defer func() {
--		c.Delete("fooDir", true)
+-		if err := fi.Close(); err != nil {
+-			panic(err)
+-		}
 -	}()
 -
--	resp, err := c.CreateDir("fooDir", 5)
+-	return NewClientFromReader(fi)
+-}
+-
+-// NewClientFromReader creates a Client configured from a given reader.
+-// The configuration is expected to use the JSON format.
+-func NewClientFromReader(reader io.Reader) (*Client, error) {
+-	c := new(Client)
+-
+-	b, err := ioutil.ReadAll(reader)
 -	if err != nil {
--		t.Fatal(err)
+-		return nil, err
 -	}
 -
--	// This should succeed.
--	resp, err = c.UpdateDir("fooDir", 5)
+-	err = json.Unmarshal(b, c)
 -	if err != nil {
--		t.Fatal(err)
+-		return nil, err
+-	}
+-	if c.config.CertFile == "" {
+-		c.initHTTPClient()
+-	} else {
+-		err = c.initHTTPSClient(c.config.CertFile, c.config.KeyFile)
 -	}
 -
--	if !(resp.Action == "update" && resp.Node.Key == "/fooDir" &&
--		resp.Node.Value == "" && resp.Node.TTL == 5) {
--		t.Fatalf("UpdateDir 1 failed: %#v", resp)
+-	if err != nil {
+-		return nil, err
 -	}
--	if !(resp.PrevNode.Key == "/fooDir" && resp.PrevNode.Dir == true && resp.PrevNode.TTL == 5) {
--		t.Fatalf("UpdateDir 1 PrevNode failed: %#v", resp)
+-
+-	for _, caCert := range c.config.CaCertFile {
+-		if err := c.AddRootCA(caCert); err != nil {
+-			return nil, err
+-		}
 -	}
 -
--	// This should fail because the key does not exist.
--	resp, err = c.UpdateDir("nonexistentDir", 5)
--	if err == nil {
--		t.Fatalf("The key %v did not exist, so the update should have failed."+
--			"The response was: %#v", resp.Node.Key, resp)
+-	return c, nil
+-}
+-
+-// Override the Client's HTTP Transport object
+-func (c *Client) SetTransport(tr *http.Transport) {
+-	c.httpClient.Transport = tr
+-}
+-
+-// initHTTPClient initializes a HTTP client for etcd client
+-func (c *Client) initHTTPClient() {
+-	tr := &http.Transport{
+-		Dial: c.dial,
+-		TLSClientConfig: &tls.Config{
+-			InsecureSkipVerify: true,
+-		},
 -	}
+-	c.httpClient = &http.Client{Transport: tr}
 -}
 -
--func TestCreateDir(t *testing.T) {
--	c := NewClient(nil)
--	defer func() {
--		c.Delete("fooDir", true)
--	}()
+-// initHTTPClient initializes a HTTPS client for etcd client
+-func (c *Client) initHTTPSClient(cert, key string) error {
+-	if cert == "" || key == "" {
+-		return errors.New("Require both cert and key path")
+-	}
 -
--	// This should succeed
--	resp, err := c.CreateDir("fooDir", 5)
+-	tlsCert, err := tls.LoadX509KeyPair(cert, key)
 -	if err != nil {
--		t.Fatal(err)
+-		return err
 -	}
 -
--	if !(resp.Action == "create" && resp.Node.Key == "/fooDir" &&
--		resp.Node.Value == "" && resp.Node.TTL == 5) {
--		t.Fatalf("CreateDir 1 failed: %#v", resp)
+-	tlsConfig := &tls.Config{
+-		Certificates:       []tls.Certificate{tlsCert},
+-		InsecureSkipVerify: true,
 -	}
--	if resp.PrevNode != nil {
--		t.Fatalf("CreateDir 1 PrevNode failed: %#v", resp)
+-
+-	tr := &http.Transport{
+-		TLSClientConfig: tlsConfig,
+-		Dial:            c.dial,
 -	}
 -
--	// This should fail, because the key is already there
--	resp, err = c.CreateDir("fooDir", 5)
--	if err == nil {
--		t.Fatalf("The key %v did exist, so the creation should have failed."+
--			"The response was: %#v", resp.Node.Key, resp)
+-	c.httpClient = &http.Client{Transport: tr}
+-	return nil
+-}
+-
+-// SetPersistence sets a writer to which the config will be
+-// written every time it's changed.
+-func (c *Client) SetPersistence(writer io.Writer) {
+-	c.persistence = writer
+-}
+-
+-// SetConsistency changes the consistency level of the client.
+-//
+-// When consistency is set to STRONG_CONSISTENCY, all requests,
+-// including GET, are sent to the leader.  This means that, assuming
+-// the absence of leader failures, GET requests are guaranteed to see
+-// the changes made by previous requests.
+-//
+-// When consistency is set to WEAK_CONSISTENCY, other requests
+-// are still sent to the leader, but GET requests are sent to a
+-// random server from the server pool.  This reduces the read
+-// load on the leader, but it's not guaranteed that the GET requests
+-// will see changes made by previous requests (they might have not
+-// yet been committed on non-leader servers).
+-func (c *Client) SetConsistency(consistency string) error {
+-	if !(consistency == STRONG_CONSISTENCY || consistency == WEAK_CONSISTENCY) {
+-		return errors.New("The argument must be either STRONG_CONSISTENCY or WEAK_CONSISTENCY.")
 -	}
+-	c.config.Consistency = consistency
+-	return nil
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/version.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/version.go
-deleted file mode 100644
-index b3d05df..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/version.go
-+++ /dev/null
-@@ -1,3 +0,0 @@
--package etcd
 -
--const version = "v2"
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/watch.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/watch.go
-deleted file mode 100644
-index aa8d3df..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/watch.go
-+++ /dev/null
-@@ -1,103 +0,0 @@
--package etcd
+-// Sets the DialTimeout value
+-func (c *Client) SetDialTimeout(d time.Duration) {
+-	c.config.DialTimeout = d
+-}
 -
--import (
--	"errors"
--)
+-// AddRootCA adds a root CA cert for the etcd client
+-func (c *Client) AddRootCA(caCert string) error {
+-	if c.httpClient == nil {
+-		return errors.New("Client has not been initialized yet!")
+-	}
 -
--// Errors introduced by the Watch command.
--var (
--	ErrWatchStoppedByUser = errors.New("Watch stopped by the user via stop channel")
--)
+-	certBytes, err := ioutil.ReadFile(caCert)
+-	if err != nil {
+-		return err
+-	}
 -
--// If recursive is set to true the watch returns the first change under the given
--// prefix since the given index.
--//
--// If recursive is set to false the watch returns the first change to the given key
--// since the given index.
--//
--// To watch for the latest change, set waitIndex = 0.
--//
--// If a receiver channel is given, it will be a long-term watch. Watch will block at the
--//channel. After someone receives the channel, it will go on to watch that
--// prefix.  If a stop channel is given, the client can close long-term watch using
--// the stop channel.
--func (c *Client) Watch(prefix string, waitIndex uint64, recursive bool,
--	receiver chan *Response, stop chan bool) (*Response, error) {
--	logger.Debugf("watch %s [%s]", prefix, c.cluster.Leader)
--	if receiver == nil {
--		raw, err := c.watchOnce(prefix, waitIndex, recursive, stop)
+-	tr, ok := c.httpClient.Transport.(*http.Transport)
 -
--		if err != nil {
--			return nil, err
+-	if !ok {
+-		panic("AddRootCA(): Transport type assert should not fail")
+-	}
+-
+-	if tr.TLSClientConfig.RootCAs == nil {
+-		caCertPool := x509.NewCertPool()
+-		ok = caCertPool.AppendCertsFromPEM(certBytes)
+-		if ok {
+-			tr.TLSClientConfig.RootCAs = caCertPool
 -		}
+-		tr.TLSClientConfig.InsecureSkipVerify = false
+-	} else {
+-		ok = tr.TLSClientConfig.RootCAs.AppendCertsFromPEM(certBytes)
+-	}
 -
--		return raw.Unmarshal()
+-	if !ok {
+-		err = errors.New("Unable to load caCert")
 -	}
--	defer close(receiver)
 -
--	for {
--		raw, err := c.watchOnce(prefix, waitIndex, recursive, stop)
+-	c.config.CaCertFile = append(c.config.CaCertFile, caCert)
+-	c.saveConfig()
 -
--		if err != nil {
--			return nil, err
--		}
+-	return err
+-}
 -
--		resp, err := raw.Unmarshal()
+-// SetCluster updates cluster information using the given machine list.
+-func (c *Client) SetCluster(machines []string) bool {
+-	success := c.internalSyncCluster(machines)
+-	return success
+-}
+-
+-func (c *Client) GetCluster() []string {
+-	return c.cluster.Machines
+-}
+-
+-// SyncCluster updates the cluster information using the internal machine list.
+-func (c *Client) SyncCluster() bool {
+-	return c.internalSyncCluster(c.cluster.Machines)
+-}
 -
+-// internalSyncCluster syncs cluster information using the given machine list.
+-func (c *Client) internalSyncCluster(machines []string) bool {
+-	for _, machine := range machines {
+-		httpPath := c.createHttpPath(machine, path.Join(version, "machines"))
+-		resp, err := c.httpClient.Get(httpPath)
 -		if err != nil {
--			return nil, err
+-			// try another machine in the cluster
+-			continue
+-		} else {
+-			b, err := ioutil.ReadAll(resp.Body)
+-			resp.Body.Close()
+-			if err != nil {
+-				// try another machine in the cluster
+-				continue
+-			}
+-
+-			// update Machines List
+-			c.cluster.updateFromStr(string(b))
+-
+-			// update leader
+-			// the first one in the machine list is the leader
+-			c.cluster.switchLeader(0)
+-
+-			logger.Debug("sync.machines ", c.cluster.Machines)
+-			c.saveConfig()
+-			return true
 -		}
+-	}
+-	return false
+-}
 -
--		waitIndex = resp.Node.ModifiedIndex + 1
--		receiver <- resp
+-// createHttpPath creates a complete HTTP URL.
+-// serverName should contain both the host name and a port number, if any.
+-func (c *Client) createHttpPath(serverName string, _path string) string {
+-	u, err := url.Parse(serverName)
+-	if err != nil {
+-		panic(err)
+-	}
+-
+-	u.Path = path.Join(u.Path, _path)
+-
+-	if u.Scheme == "" {
+-		u.Scheme = "http"
 -	}
+-	return u.String()
 -}
 -
--func (c *Client) RawWatch(prefix string, waitIndex uint64, recursive bool,
--	receiver chan *RawResponse, stop chan bool) (*RawResponse, error) {
+-// dial attempts to open a TCP connection to the provided address, explicitly
+-// enabling keep-alives with a one-second interval.
+-func (c *Client) dial(network, addr string) (net.Conn, error) {
+-	conn, err := net.DialTimeout(network, addr, c.config.DialTimeout)
+-	if err != nil {
+-		return nil, err
+-	}
 -
--	logger.Debugf("rawWatch %s [%s]", prefix, c.cluster.Leader)
--	if receiver == nil {
--		return c.watchOnce(prefix, waitIndex, recursive, stop)
+-	tcpConn, ok := conn.(*net.TCPConn)
+-	if !ok {
+-		return nil, errors.New("Failed type-assertion of net.Conn as *net.TCPConn")
 -	}
 -
--	for {
--		raw, err := c.watchOnce(prefix, waitIndex, recursive, stop)
+-	// Keep TCP alive to check whether or not the remote machine is down
+-	if err = tcpConn.SetKeepAlive(true); err != nil {
+-		return nil, err
+-	}
 -
--		if err != nil {
--			return nil, err
+-	if err = tcpConn.SetKeepAlivePeriod(time.Second); err != nil {
+-		return nil, err
+-	}
+-
+-	return tcpConn, nil
+-}
+-
+-func (c *Client) OpenCURL() {
+-	c.cURLch = make(chan string, defaultBufferSize)
+-}
+-
+-func (c *Client) CloseCURL() {
+-	c.cURLch = nil
+-}
+-
+-func (c *Client) sendCURL(command string) {
+-	go func() {
+-		select {
+-		case c.cURLch <- command:
+-		default:
 -		}
+-	}()
+-}
 -
--		resp, err := raw.Unmarshal()
+-func (c *Client) RecvCURL() string {
+-	return <-c.cURLch
+-}
 -
+-// saveConfig saves the current config using c.persistence.
+-func (c *Client) saveConfig() error {
+-	if c.persistence != nil {
+-		b, err := json.Marshal(c)
 -		if err != nil {
--			return nil, err
+-			return err
 -		}
 -
--		waitIndex = resp.Node.ModifiedIndex + 1
--		receiver <- raw
+-		_, err = c.persistence.Write(b)
+-		if err != nil {
+-			return err
+-		}
 -	}
+-
+-	return nil
 -}
 -
--// helper func
--// return when there is change under the given prefix
--func (c *Client) watchOnce(key string, waitIndex uint64, recursive bool, stop chan bool) (*RawResponse, error) {
+-// MarshalJSON implements the Marshaller interface
+-// as defined by the standard JSON package.
+-func (c *Client) MarshalJSON() ([]byte, error) {
+-	b, err := json.Marshal(struct {
+-		Config  Config   `json:"config"`
+-		Cluster *Cluster `json:"cluster"`
+-	}{
+-		Config:  c.config,
+-		Cluster: c.cluster,
+-	})
 -
--	options := Options{
--		"wait": true,
--	}
--	if waitIndex > 0 {
--		options["waitIndex"] = waitIndex
--	}
--	if recursive {
--		options["recursive"] = true
+-	if err != nil {
+-		return nil, err
 -	}
 -
--	resp, err := c.getCancelable(key, options, stop)
+-	return b, nil
+-}
 -
--	if err == ErrRequestCancelled {
--		return nil, ErrWatchStoppedByUser
+-// UnmarshalJSON implements the Unmarshaller interface
+-// as defined by the standard JSON package.
+-func (c *Client) UnmarshalJSON(b []byte) error {
+-	temp := struct {
+-		Config  Config   `json:"config"`
+-		Cluster *Cluster `json:"cluster"`
+-	}{}
+-	err := json.Unmarshal(b, &temp)
+-	if err != nil {
+-		return err
 -	}
 -
--	return resp, err
+-	c.cluster = temp.Cluster
+-	c.config = temp.Config
+-	return nil
 -}
-diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/watch_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/watch_test.go
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/client_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/client_test.go
 deleted file mode 100644
-index 43e1dfe..0000000
---- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/watch_test.go
+index c245e47..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/client_test.go
 +++ /dev/null
-@@ -1,119 +0,0 @@
+@@ -1,96 +0,0 @@
 -package etcd
 -
 -import (
+-	"encoding/json"
 -	"fmt"
--	"runtime"
+-	"net"
+-	"net/url"
+-	"os"
 -	"testing"
--	"time"
 -)
 -
--func TestWatch(t *testing.T) {
--	c := NewClient(nil)
--	defer func() {
--		c.Delete("watch_foo", true)
--	}()
+-// To pass this test, we need to create a cluster of 3 machines
+-// The server should be listening on 127.0.0.1:4001, 4002, 4003
+-func TestSync(t *testing.T) {
+-	fmt.Println("Make sure there are three nodes at 0.0.0.0:4001-4003")
 -
--	go setHelper("watch_foo", "bar", c)
+-	// Explicit trailing slash to ensure this doesn't reproduce:
+-	// https://github.com/coreos/go-etcd/issues/82
+-	c := NewClient([]string{"http://127.0.0.1:4001/"})
 -
--	resp, err := c.Watch("watch_foo", 0, false, nil, nil)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if !(resp.Node.Key == "/watch_foo" && resp.Node.Value == "bar") {
--		t.Fatalf("Watch 1 failed: %#v", resp)
+-	success := c.SyncCluster()
+-	if !success {
+-		t.Fatal("cannot sync machines")
 -	}
 -
--	go setHelper("watch_foo", "bar", c)
+-	for _, m := range c.GetCluster() {
+-		u, err := url.Parse(m)
+-		if err != nil {
+-			t.Fatal(err)
+-		}
+-		if u.Scheme != "http" {
+-			t.Fatal("scheme must be http")
+-		}
 -
--	resp, err = c.Watch("watch_foo", resp.Node.ModifiedIndex+1, false, nil, nil)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if !(resp.Node.Key == "/watch_foo" && resp.Node.Value == "bar") {
--		t.Fatalf("Watch 2 failed: %#v", resp)
+-		host, _, err := net.SplitHostPort(u.Host)
+-		if err != nil {
+-			t.Fatal(err)
+-		}
+-		if host != "127.0.0.1" {
+-			t.Fatal("Host must be 127.0.0.1")
+-		}
 -	}
 -
--	routineNum := runtime.NumGoroutine()
+-	badMachines := []string{"abc", "edef"}
 -
--	ch := make(chan *Response, 10)
--	stop := make(chan bool, 1)
+-	success = c.SetCluster(badMachines)
 -
--	go setLoop("watch_foo", "bar", c)
+-	if success {
+-		t.Fatal("should not sync on bad machines")
+-	}
 -
--	go receiver(ch, stop)
+-	goodMachines := []string{"127.0.0.1:4002"}
 -
--	_, err = c.Watch("watch_foo", 0, false, ch, stop)
--	if err != ErrWatchStoppedByUser {
--		t.Fatalf("Watch returned a non-user stop error")
--	}
+-	success = c.SetCluster(goodMachines)
 -
--	if newRoutineNum := runtime.NumGoroutine(); newRoutineNum != routineNum {
--		t.Fatalf("Routine numbers differ after watch stop: %v, %v", routineNum, newRoutineNum)
+-	if !success {
+-		t.Fatal("cannot sync machines")
+-	} else {
+-		fmt.Println(c.cluster.Machines)
 -	}
+-
 -}
 -
--func TestWatchAll(t *testing.T) {
+-func TestPersistence(t *testing.T) {
 -	c := NewClient(nil)
+-	c.SyncCluster()
+-
+-	fo, err := os.Create("config.json")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
 -	defer func() {
--		c.Delete("watch_foo", true)
+-		if err := fo.Close(); err != nil {
+-			panic(err)
+-		}
 -	}()
 -
--	go setHelper("watch_foo/foo", "bar", c)
--
--	resp, err := c.Watch("watch_foo", 0, true, nil, nil)
+-	c.SetPersistence(fo)
+-	err = c.saveConfig()
 -	if err != nil {
 -		t.Fatal(err)
 -	}
--	if !(resp.Node.Key == "/watch_foo/foo" && resp.Node.Value == "bar") {
--		t.Fatalf("WatchAll 1 failed: %#v", resp)
--	}
 -
--	go setHelper("watch_foo/foo", "bar", c)
--
--	resp, err = c.Watch("watch_foo", resp.Node.ModifiedIndex+1, true, nil, nil)
+-	c2, err := NewClientFromFile("config.json")
 -	if err != nil {
 -		t.Fatal(err)
 -	}
--	if !(resp.Node.Key == "/watch_foo/foo" && resp.Node.Value == "bar") {
--		t.Fatalf("WatchAll 2 failed: %#v", resp)
--	}
 -
--	ch := make(chan *Response, 10)
--	stop := make(chan bool, 1)
+-	// Verify that the two clients have the same config
+-	b1, _ := json.Marshal(c)
+-	b2, _ := json.Marshal(c2)
 -
--	routineNum := runtime.NumGoroutine()
+-	if string(b1) != string(b2) {
+-		t.Fatalf("The two configs should be equal!")
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/cluster.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/cluster.go
+deleted file mode 100644
+index aaa2054..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/cluster.go
++++ /dev/null
+@@ -1,51 +0,0 @@
+-package etcd
 -
--	go setLoop("watch_foo/foo", "bar", c)
+-import (
+-	"net/url"
+-	"strings"
+-)
 -
--	go receiver(ch, stop)
+-type Cluster struct {
+-	Leader   string   `json:"leader"`
+-	Machines []string `json:"machines"`
+-}
 -
--	_, err = c.Watch("watch_foo", 0, true, ch, stop)
--	if err != ErrWatchStoppedByUser {
--		t.Fatalf("Watch returned a non-user stop error")
+-func NewCluster(machines []string) *Cluster {
+-	// if an empty slice was sent in then just assume HTTP 4001 on localhost
+-	if len(machines) == 0 {
+-		machines = []string{"http://127.0.0.1:4001"}
 -	}
 -
--	if newRoutineNum := runtime.NumGoroutine(); newRoutineNum != routineNum {
--		t.Fatalf("Routine numbers differ after watch stop: %v, %v", routineNum, newRoutineNum)
+-	// default leader and machines
+-	return &Cluster{
+-		Leader:   machines[0],
+-		Machines: machines,
 -	}
 -}
 -
--func setHelper(key, value string, c *Client) {
--	time.Sleep(time.Second)
--	c.Set(key, value, 100)
--}
+-// switchLeader switch the current leader to machines[num]
+-func (cl *Cluster) switchLeader(num int) {
+-	logger.Debugf("switch.leader[from %v to %v]",
+-		cl.Leader, cl.Machines[num])
 -
--func setLoop(key, value string, c *Client) {
--	time.Sleep(time.Second)
--	for i := 0; i < 10; i++ {
--		newValue := fmt.Sprintf("%s_%v", value, i)
--		c.Set(key, newValue, 100)
--		time.Sleep(time.Second / 10)
--	}
+-	cl.Leader = cl.Machines[num]
 -}
 -
--func receiver(c chan *Response, stop chan bool) {
--	for i := 0; i < 10; i++ {
--		<-c
--	}
--	stop <- true
+-func (cl *Cluster) updateFromStr(machines string) {
+-	cl.Machines = strings.Split(machines, ", ")
 -}
-diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/common.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/common.go
-deleted file mode 100644
-index 0ce0df1..0000000
---- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/common.go
-+++ /dev/null
-@@ -1,371 +0,0 @@
--/*
-- * Copyright (c) 2013 Dave Collins <dave at davec.name>
-- *
-- * Permission to use, copy, modify, and distribute this software for any
-- * purpose with or without fee is hereby granted, provided that the above
-- * copyright notice and this permission notice appear in all copies.
-- *
-- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
-- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
-- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
-- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
-- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
-- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
-- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
-- */
 -
--package spew
+-func (cl *Cluster) updateLeader(leader string) {
+-	logger.Debugf("update.leader[%s,%s]", cl.Leader, leader)
+-	cl.Leader = leader
+-}
 -
--import (
--	"fmt"
--	"io"
--	"reflect"
--	"sort"
--	"strconv"
--	"unsafe"
--)
+-func (cl *Cluster) updateLeaderFromURL(u *url.URL) {
+-	var leader string
+-	if u.Scheme == "" {
+-		leader = "http://" + u.Host
+-	} else {
+-		leader = u.Scheme + "://" + u.Host
+-	}
+-	cl.updateLeader(leader)
+-}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_delete.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_delete.go
+deleted file mode 100644
+index 11131bb..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_delete.go
++++ /dev/null
+@@ -1,34 +0,0 @@
+-package etcd
 -
--const (
--	// ptrSize is the size of a pointer on the current arch.
--	ptrSize = unsafe.Sizeof((*byte)(nil))
--)
+-import "fmt"
 -
--var (
--	// offsetPtr, offsetScalar, and offsetFlag are the offsets for the
--	// internal reflect.Value fields.  These values are valid before golang
--	// commit ecccf07e7f9d which changed the format.  The are also valid
--	// after commit 82f48826c6c7 which changed the format again to mirror
--	// the original format.  Code in the init function updates these offsets
--	// as necessary.
--	offsetPtr    = uintptr(ptrSize)
--	offsetScalar = uintptr(0)
--	offsetFlag   = uintptr(ptrSize * 2)
+-func (c *Client) CompareAndDelete(key string, prevValue string, prevIndex uint64) (*Response, error) {
+-	raw, err := c.RawCompareAndDelete(key, prevValue, prevIndex)
+-	if err != nil {
+-		return nil, err
+-	}
 -
--	// flagKindWidth and flagKindShift indicate various bits that the
--	// reflect package uses internally to track kind information.
--	//
--	// flagRO indicates whether or not the value field of a reflect.Value is
--	// read-only.
--	//
--	// flagIndir indicates whether the value field of a reflect.Value is
--	// the actual data or a pointer to the data.
--	//
--	// These values are valid before golang commit 90a7c3c86944 which
--	// changed their positions.  Code in the init function updates these
--	// flags as necessary.
--	flagKindWidth = uintptr(5)
--	flagKindShift = uintptr(flagKindWidth - 1)
--	flagRO        = uintptr(1 << 0)
--	flagIndir     = uintptr(1 << 1)
--)
+-	return raw.Unmarshal()
+-}
 -
--func init() {
--	// Older versions of reflect.Value stored small integers directly in the
--	// ptr field (which is named val in the older versions).  Versions
--	// between commits ecccf07e7f9d and 82f48826c6c7 added a new field named
--	// scalar for this purpose which unfortunately came before the flag
--	// field, so the offset of the flag field is different for those
--	// versions.
--	//
--	// This code constructs a new reflect.Value from a known small integer
--	// and checks if the size of the reflect.Value struct indicates it has
--	// the scalar field. When it does, the offsets are updated accordingly.
--	vv := reflect.ValueOf(0xf00)
--	if unsafe.Sizeof(vv) == (ptrSize * 4) {
--		offsetScalar = ptrSize * 2
--		offsetFlag = ptrSize * 3
+-func (c *Client) RawCompareAndDelete(key string, prevValue string, prevIndex uint64) (*RawResponse, error) {
+-	if prevValue == "" && prevIndex == 0 {
+-		return nil, fmt.Errorf("You must give either prevValue or prevIndex.")
 -	}
 -
--	// Commit 90a7c3c86944 changed the flag positions such that the low
--	// order bits are the kind.  This code extracts the kind from the flags
--	// field and ensures it's the correct type.  When it's not, the flag
--	// order has been changed to the newer format, so the flags are updated
--	// accordingly.
--	upf := unsafe.Pointer(uintptr(unsafe.Pointer(&vv)) + offsetFlag)
--	upfv := *(*uintptr)(upf)
--	flagKindMask := uintptr((1<<flagKindWidth - 1) << flagKindShift)
--	if (upfv&flagKindMask)>>flagKindShift != uintptr(reflect.Int) {
--		flagKindShift = 0
--		flagRO = 1 << 5
--		flagIndir = 1 << 6
+-	options := Options{}
+-	if prevValue != "" {
+-		options["prevValue"] = prevValue
 -	}
--}
--
--// unsafeReflectValue converts the passed reflect.Value into a one that bypasses
--// the typical safety restrictions preventing access to unaddressable and
--// unexported data.  It works by digging the raw pointer to the underlying
--// value out of the protected value and generating a new unprotected (unsafe)
--// reflect.Value to it.
--//
--// This allows us to check for implementations of the Stringer and error
--// interfaces to be used for pretty printing ordinarily unaddressable and
--// inaccessible values such as unexported struct fields.
--func unsafeReflectValue(v reflect.Value) (rv reflect.Value) {
--	indirects := 1
--	vt := v.Type()
--	upv := unsafe.Pointer(uintptr(unsafe.Pointer(&v)) + offsetPtr)
--	rvf := *(*uintptr)(unsafe.Pointer(uintptr(unsafe.Pointer(&v)) + offsetFlag))
--	if rvf&flagIndir != 0 {
--		vt = reflect.PtrTo(v.Type())
--		indirects++
--	} else if offsetScalar != 0 {
--		// The value is in the scalar field when it's not one of the
--		// reference types.
--		switch vt.Kind() {
--		case reflect.Uintptr:
--		case reflect.Chan:
--		case reflect.Func:
--		case reflect.Map:
--		case reflect.Ptr:
--		case reflect.UnsafePointer:
--		default:
--			upv = unsafe.Pointer(uintptr(unsafe.Pointer(&v)) +
--				offsetScalar)
--		}
+-	if prevIndex != 0 {
+-		options["prevIndex"] = prevIndex
 -	}
 -
--	pv := reflect.NewAt(vt, upv)
--	rv = pv
--	for i := 0; i < indirects; i++ {
--		rv = rv.Elem()
+-	raw, err := c.delete(key, options)
+-
+-	if err != nil {
+-		return nil, err
 -	}
--	return rv
+-
+-	return raw, err
 -}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_delete_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_delete_test.go
+deleted file mode 100644
+index 223e50f..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_delete_test.go
++++ /dev/null
+@@ -1,46 +0,0 @@
+-package etcd
 -
--// Some constants in the form of bytes to avoid string overhead.  This mirrors
--// the technique used in the fmt package.
--var (
--	panicBytes            = []byte("(PANIC=")
--	plusBytes             = []byte("+")
--	iBytes                = []byte("i")
--	trueBytes             = []byte("true")
--	falseBytes            = []byte("false")
--	interfaceBytes        = []byte("(interface {})")
--	commaNewlineBytes     = []byte(",\n")
--	newlineBytes          = []byte("\n")
--	openBraceBytes        = []byte("{")
--	openBraceNewlineBytes = []byte("{\n")
--	closeBraceBytes       = []byte("}")
--	asteriskBytes         = []byte("*")
--	colonBytes            = []byte(":")
--	colonSpaceBytes       = []byte(": ")
--	openParenBytes        = []byte("(")
--	closeParenBytes       = []byte(")")
--	spaceBytes            = []byte(" ")
--	pointerChainBytes     = []byte("->")
--	nilAngleBytes         = []byte("<nil>")
--	maxNewlineBytes       = []byte("<max depth reached>\n")
--	maxShortBytes         = []byte("<max>")
--	circularBytes         = []byte("<already shown>")
--	circularShortBytes    = []byte("<shown>")
--	invalidAngleBytes     = []byte("<invalid>")
--	openBracketBytes      = []byte("[")
--	closeBracketBytes     = []byte("]")
--	percentBytes          = []byte("%")
--	precisionBytes        = []byte(".")
--	openAngleBytes        = []byte("<")
--	closeAngleBytes       = []byte(">")
--	openMapBytes          = []byte("map[")
--	closeMapBytes         = []byte("]")
--	lenEqualsBytes        = []byte("len=")
--	capEqualsBytes        = []byte("cap=")
+-import (
+-	"testing"
 -)
 -
--// hexDigits is used to map a decimal value to a hex digit.
--var hexDigits = "0123456789abcdef"
+-func TestCompareAndDelete(t *testing.T) {
+-	c := NewClient(nil)
+-	defer func() {
+-		c.Delete("foo", true)
+-	}()
 -
--// catchPanic handles any panics that might occur during the handleMethods
--// calls.
--func catchPanic(w io.Writer, v reflect.Value) {
--	if err := recover(); err != nil {
--		w.Write(panicBytes)
--		fmt.Fprintf(w, "%v", err)
--		w.Write(closeParenBytes)
--	}
--}
+-	c.Set("foo", "bar", 5)
 -
--// handleMethods attempts to call the Error and String methods on the underlying
--// type the passed reflect.Value represents and outputes the result to Writer w.
--//
--// It handles panics in any called methods by catching and displaying the error
--// as the formatted value.
--func handleMethods(cs *ConfigState, w io.Writer, v reflect.Value) (handled bool) {
--	// We need an interface to check if the type implements the error or
--	// Stringer interface.  However, the reflect package won't give us an
--	// interface on certain things like unexported struct fields in order
--	// to enforce visibility rules.  We use unsafe to bypass these restrictions
--	// since this package does not mutate the values.
--	if !v.CanInterface() {
--		v = unsafeReflectValue(v)
+-	// This should succeed an correct prevValue
+-	resp, err := c.CompareAndDelete("foo", "bar", 0)
+-	if err != nil {
+-		t.Fatal(err)
 -	}
--
--	// Choose whether or not to do error and Stringer interface lookups against
--	// the base type or a pointer to the base type depending on settings.
--	// Technically calling one of these methods with a pointer receiver can
--	// mutate the value, however, types which choose to satisify an error or
--	// Stringer interface with a pointer receiver should not be mutating their
--	// state inside these interface methods.
--	var viface interface{}
--	if !cs.DisablePointerMethods {
--		if !v.CanAddr() {
--			v = unsafeReflectValue(v)
--		}
--		viface = v.Addr().Interface()
--	} else {
--		if v.CanAddr() {
--			v = v.Addr()
--		}
--		viface = v.Interface()
+-	if !(resp.PrevNode.Value == "bar" && resp.PrevNode.Key == "/foo" && resp.PrevNode.TTL == 5) {
+-		t.Fatalf("CompareAndDelete 1 prevNode failed: %#v", resp)
 -	}
 -
--	// Is it an error or Stringer?
--	switch iface := viface.(type) {
--	case error:
--		defer catchPanic(w, v)
--		if cs.ContinueOnMethod {
--			w.Write(openParenBytes)
--			w.Write([]byte(iface.Error()))
--			w.Write(closeParenBytes)
--			w.Write(spaceBytes)
--			return false
--		}
--
--		w.Write([]byte(iface.Error()))
--		return true
+-	resp, _ = c.Set("foo", "bar", 5)
+-	// This should fail because it gives an incorrect prevValue
+-	_, err = c.CompareAndDelete("foo", "xxx", 0)
+-	if err == nil {
+-		t.Fatalf("CompareAndDelete 2 should have failed.  The response is: %#v", resp)
+-	}
 -
--	case fmt.Stringer:
--		defer catchPanic(w, v)
--		if cs.ContinueOnMethod {
--			w.Write(openParenBytes)
--			w.Write([]byte(iface.String()))
--			w.Write(closeParenBytes)
--			w.Write(spaceBytes)
--			return false
--		}
--		w.Write([]byte(iface.String()))
--		return true
+-	// This should succeed because it gives an correct prevIndex
+-	resp, err = c.CompareAndDelete("foo", "", resp.Node.ModifiedIndex)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !(resp.PrevNode.Value == "bar" && resp.PrevNode.Key == "/foo" && resp.PrevNode.TTL == 5) {
+-		t.Fatalf("CompareAndSwap 3 prevNode failed: %#v", resp)
 -	}
--	return false
--}
 -
--// printBool outputs a boolean value as true or false to Writer w.
--func printBool(w io.Writer, val bool) {
--	if val {
--		w.Write(trueBytes)
--	} else {
--		w.Write(falseBytes)
+-	c.Set("foo", "bar", 5)
+-	// This should fail because it gives an incorrect prevIndex
+-	resp, err = c.CompareAndDelete("foo", "", 29817514)
+-	if err == nil {
+-		t.Fatalf("CompareAndDelete 4 should have failed.  The response is: %#v", resp)
 -	}
 -}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_swap.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_swap.go
+deleted file mode 100644
+index bb4f906..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_swap.go
++++ /dev/null
+@@ -1,36 +0,0 @@
+-package etcd
 -
--// printInt outputs a signed integer value to Writer w.
--func printInt(w io.Writer, val int64, base int) {
--	w.Write([]byte(strconv.FormatInt(val, base)))
--}
+-import "fmt"
 -
--// printUint outputs an unsigned integer value to Writer w.
--func printUint(w io.Writer, val uint64, base int) {
--	w.Write([]byte(strconv.FormatUint(val, base)))
--}
+-func (c *Client) CompareAndSwap(key string, value string, ttl uint64,
+-	prevValue string, prevIndex uint64) (*Response, error) {
+-	raw, err := c.RawCompareAndSwap(key, value, ttl, prevValue, prevIndex)
+-	if err != nil {
+-		return nil, err
+-	}
 -
--// printFloat outputs a floating point value using the specified precision,
--// which is expected to be 32 or 64bit, to Writer w.
--func printFloat(w io.Writer, val float64, precision int) {
--	w.Write([]byte(strconv.FormatFloat(val, 'g', -1, precision)))
+-	return raw.Unmarshal()
 -}
 -
--// printComplex outputs a complex value using the specified float precision
--// for the real and imaginary parts to Writer w.
--func printComplex(w io.Writer, c complex128, floatPrecision int) {
--	r := real(c)
--	w.Write(openParenBytes)
--	w.Write([]byte(strconv.FormatFloat(r, 'g', -1, floatPrecision)))
--	i := imag(c)
--	if i >= 0 {
--		w.Write(plusBytes)
+-func (c *Client) RawCompareAndSwap(key string, value string, ttl uint64,
+-	prevValue string, prevIndex uint64) (*RawResponse, error) {
+-	if prevValue == "" && prevIndex == 0 {
+-		return nil, fmt.Errorf("You must give either prevValue or prevIndex.")
 -	}
--	w.Write([]byte(strconv.FormatFloat(i, 'g', -1, floatPrecision)))
--	w.Write(iBytes)
--	w.Write(closeParenBytes)
--}
 -
--// printHexPtr outputs a uintptr formatted as hexidecimal with a leading '0x'
--// prefix to Writer w.
--func printHexPtr(w io.Writer, p uintptr) {
--	// Null pointer.
--	num := uint64(p)
--	if num == 0 {
--		w.Write(nilAngleBytes)
--		return
+-	options := Options{}
+-	if prevValue != "" {
+-		options["prevValue"] = prevValue
+-	}
+-	if prevIndex != 0 {
+-		options["prevIndex"] = prevIndex
 -	}
 -
--	// Max uint64 is 16 bytes in hex + 2 bytes for '0x' prefix
--	buf := make([]byte, 18)
+-	raw, err := c.put(key, value, ttl, options)
 -
--	// It's simpler to construct the hex string right to left.
--	base := uint64(16)
--	i := len(buf) - 1
--	for num >= base {
--		buf[i] = hexDigits[num%base]
--		num /= base
--		i--
+-	if err != nil {
+-		return nil, err
 -	}
--	buf[i] = hexDigits[num]
--
--	// Add '0x' prefix.
--	i--
--	buf[i] = 'x'
--	i--
--	buf[i] = '0'
 -
--	// Strip unused leading bytes.
--	buf = buf[i:]
--	w.Write(buf)
+-	return raw, err
 -}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_swap_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_swap_test.go
+deleted file mode 100644
+index 14a1b00..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/compare_and_swap_test.go
++++ /dev/null
+@@ -1,57 +0,0 @@
+-package etcd
 -
--// valuesSorter implements sort.Interface to allow a slice of reflect.Value
--// elements to be sorted.
--type valuesSorter struct {
--	values []reflect.Value
--}
+-import (
+-	"testing"
+-)
 -
--// Len returns the number of values in the slice.  It is part of the
--// sort.Interface implementation.
--func (s *valuesSorter) Len() int {
--	return len(s.values)
--}
+-func TestCompareAndSwap(t *testing.T) {
+-	c := NewClient(nil)
+-	defer func() {
+-		c.Delete("foo", true)
+-	}()
 -
--// Swap swaps the values at the passed indices.  It is part of the
--// sort.Interface implementation.
--func (s *valuesSorter) Swap(i, j int) {
--	s.values[i], s.values[j] = s.values[j], s.values[i]
--}
+-	c.Set("foo", "bar", 5)
 -
--// Less returns whether the value at index i should sort before the
--// value at index j.  It is part of the sort.Interface implementation.
--func (s *valuesSorter) Less(i, j int) bool {
--	switch s.values[i].Kind() {
--	case reflect.Bool:
--		return !s.values[i].Bool() && s.values[j].Bool()
--	case reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64, reflect.Int:
--		return s.values[i].Int() < s.values[j].Int()
--	case reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uint:
--		return s.values[i].Uint() < s.values[j].Uint()
--	case reflect.Float32, reflect.Float64:
--		return s.values[i].Float() < s.values[j].Float()
--	case reflect.String:
--		return s.values[i].String() < s.values[j].String()
--	case reflect.Uintptr:
--		return s.values[i].Uint() < s.values[j].Uint()
+-	// This should succeed
+-	resp, err := c.CompareAndSwap("foo", "bar2", 5, "bar", 0)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !(resp.Node.Value == "bar2" && resp.Node.Key == "/foo" && resp.Node.TTL == 5) {
+-		t.Fatalf("CompareAndSwap 1 failed: %#v", resp)
 -	}
--	return s.values[i].String() < s.values[j].String()
--}
 -
--// sortValues is a generic sort function for native types: int, uint, bool,
--// string and uintptr.  Other inputs are sorted according to their
--// Value.String() value to ensure display stability.
--func sortValues(values []reflect.Value) {
--	if len(values) == 0 {
--		return
+-	if !(resp.PrevNode.Value == "bar" && resp.PrevNode.Key == "/foo" && resp.PrevNode.TTL == 5) {
+-		t.Fatalf("CompareAndSwap 1 prevNode failed: %#v", resp)
+-	}
+-
+-	// This should fail because it gives an incorrect prevValue
+-	resp, err = c.CompareAndSwap("foo", "bar3", 5, "xxx", 0)
+-	if err == nil {
+-		t.Fatalf("CompareAndSwap 2 should have failed.  The response is: %#v", resp)
+-	}
+-
+-	resp, err = c.Set("foo", "bar", 5)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	// This should succeed
+-	resp, err = c.CompareAndSwap("foo", "bar2", 5, "", resp.Node.ModifiedIndex)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !(resp.Node.Value == "bar2" && resp.Node.Key == "/foo" && resp.Node.TTL == 5) {
+-		t.Fatalf("CompareAndSwap 3 failed: %#v", resp)
+-	}
+-
+-	if !(resp.PrevNode.Value == "bar" && resp.PrevNode.Key == "/foo" && resp.PrevNode.TTL == 5) {
+-		t.Fatalf("CompareAndSwap 3 prevNode failed: %#v", resp)
+-	}
+-
+-	// This should fail because it gives an incorrect prevIndex
+-	resp, err = c.CompareAndSwap("foo", "bar3", 5, "", 29817514)
+-	if err == nil {
+-		t.Fatalf("CompareAndSwap 4 should have failed.  The response is: %#v", resp)
 -	}
--	sort.Sort(&valuesSorter{values})
 -}
-diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/common_test.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/common_test.go
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/debug.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/debug.go
 deleted file mode 100644
-index 3bea81f..0000000
---- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/common_test.go
+index 0f77788..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/debug.go
 +++ /dev/null
-@@ -1,192 +0,0 @@
--/*
-- * Copyright (c) 2013 Dave Collins <dave at davec.name>
-- *
-- * Permission to use, copy, modify, and distribute this software for any
-- * purpose with or without fee is hereby granted, provided that the above
-- * copyright notice and this permission notice appear in all copies.
-- *
-- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
-- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
-- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
-- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
-- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
-- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
-- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
-- */
--
--package spew_test
+@@ -1,55 +0,0 @@
+-package etcd
 -
 -import (
 -	"fmt"
--	"github.com/davecgh/go-spew/spew"
--	"reflect"
--	"testing"
+-	"io/ioutil"
+-	"log"
+-	"strings"
 -)
 -
--// custom type to test Stinger interface on non-pointer receiver.
--type stringer string
+-var logger *etcdLogger
 -
--// String implements the Stringer interface for testing invocation of custom
--// stringers on types with non-pointer receivers.
--func (s stringer) String() string {
--	return "stringer " + string(s)
+-func SetLogger(l *log.Logger) {
+-	logger = &etcdLogger{l}
 -}
 -
--// custom type to test Stinger interface on pointer receiver.
--type pstringer string
+-func GetLogger() *log.Logger {
+-	return logger.log
+-}
 -
--// String implements the Stringer interface for testing invocation of custom
--// stringers on types with only pointer receivers.
--func (s *pstringer) String() string {
--	return "stringer " + string(*s)
+-type etcdLogger struct {
+-	log *log.Logger
 -}
 -
--// xref1 and xref2 are cross referencing structs for testing circular reference
--// detection.
--type xref1 struct {
--	ps2 *xref2
+-func (p *etcdLogger) Debug(args ...interface{}) {
+-	msg := "DEBUG: " + fmt.Sprint(args...)
+-	p.log.Println(msg)
 -}
--type xref2 struct {
--	ps1 *xref1
+-
+-func (p *etcdLogger) Debugf(f string, args ...interface{}) {
+-	msg := "DEBUG: " + fmt.Sprintf(f, args...)
+-	// Append newline if necessary
+-	if !strings.HasSuffix(msg, "\n") {
+-		msg = msg + "\n"
+-	}
+-	p.log.Print(msg)
 -}
 -
--// indirCir1, indirCir2, and indirCir3 are used to generate an indirect circular
--// reference for testing detection.
--type indirCir1 struct {
--	ps2 *indirCir2
+-func (p *etcdLogger) Warning(args ...interface{}) {
+-	msg := "WARNING: " + fmt.Sprint(args...)
+-	p.log.Println(msg)
 -}
--type indirCir2 struct {
--	ps3 *indirCir3
+-
+-func (p *etcdLogger) Warningf(f string, args ...interface{}) {
+-	msg := "WARNING: " + fmt.Sprintf(f, args...)
+-	// Append newline if necessary
+-	if !strings.HasSuffix(msg, "\n") {
+-		msg = msg + "\n"
+-	}
+-	p.log.Print(msg)
 -}
--type indirCir3 struct {
--	ps1 *indirCir1
+-
+-func init() {
+-	// Default logger uses the go default log.
+-	SetLogger(log.New(ioutil.Discard, "go-etcd", log.LstdFlags))
 -}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/debug_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/debug_test.go
+deleted file mode 100644
+index 97f6d11..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/debug_test.go
++++ /dev/null
+@@ -1,28 +0,0 @@
+-package etcd
 -
--// embed is used to test embedded structures.
--type embed struct {
--	a string
+-import (
+-	"testing"
+-)
+-
+-type Foo struct{}
+-type Bar struct {
+-	one string
+-	two int
 -}
 -
--// embedwrap is used to test embedded structures.
--type embedwrap struct {
--	*embed
--	e *embed
+-// Tests that logs don't panic with arbitrary interfaces
+-func TestDebug(t *testing.T) {
+-	f := &Foo{}
+-	b := &Bar{"asfd", 3}
+-	for _, test := range []interface{}{
+-		1234,
+-		"asdf",
+-		f,
+-		b,
+-	} {
+-		logger.Debug(test)
+-		logger.Debugf("something, %s", test)
+-		logger.Warning(test)
+-		logger.Warningf("something, %s", test)
+-	}
 -}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/delete.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/delete.go
+deleted file mode 100644
+index b37accd..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/delete.go
++++ /dev/null
+@@ -1,40 +0,0 @@
+-package etcd
 -
--// panicer is used to intentionally cause a panic for testing spew properly
--// handles them
--type panicer int
+-// Delete deletes the given key.
+-//
+-// When recursive set to false, if the key points to a
+-// directory the method will fail.
+-//
+-// When recursive set to true, if the key points to a file,
+-// the file will be deleted; if the key points to a directory,
+-// then everything under the directory (including all child directories)
+-// will be deleted.
+-func (c *Client) Delete(key string, recursive bool) (*Response, error) {
+-	raw, err := c.RawDelete(key, recursive, false)
 -
--func (p panicer) String() string {
--	panic("test panic")
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	return raw.Unmarshal()
 -}
 -
--// customError is used to test custom error interface invocation.
--type customError int
+-// DeleteDir deletes an empty directory or a key value pair
+-func (c *Client) DeleteDir(key string) (*Response, error) {
+-	raw, err := c.RawDelete(key, false, true)
 -
--func (e customError) Error() string {
--	return fmt.Sprintf("error: %d", int(e))
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	return raw.Unmarshal()
 -}
 -
--// stringizeWants converts a slice of wanted test output into a format suitable
--// for a test error message.
--func stringizeWants(wants []string) string {
--	s := ""
--	for i, want := range wants {
--		if i > 0 {
--			s += fmt.Sprintf("want%d: %s", i+1, want)
--		} else {
--			s += "want: " + want
--		}
+-func (c *Client) RawDelete(key string, recursive bool, dir bool) (*RawResponse, error) {
+-	ops := Options{
+-		"recursive": recursive,
+-		"dir":       dir,
 -	}
--	return s
+-
+-	return c.delete(key, ops)
 -}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/delete_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/delete_test.go
+deleted file mode 100644
+index 5904971..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/delete_test.go
++++ /dev/null
+@@ -1,81 +0,0 @@
+-package etcd
 -
--// testFailed returns whether or not a test failed by checking if the result
--// of the test is in the slice of wanted strings.
--func testFailed(result string, wants []string) bool {
--	for _, want := range wants {
--		if result == want {
--			return false
--		}
+-import (
+-	"testing"
+-)
+-
+-func TestDelete(t *testing.T) {
+-	c := NewClient(nil)
+-	defer func() {
+-		c.Delete("foo", true)
+-	}()
+-
+-	c.Set("foo", "bar", 5)
+-	resp, err := c.Delete("foo", false)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	if !(resp.Node.Value == "") {
+-		t.Fatalf("Delete failed with %s", resp.Node.Value)
+-	}
+-
+-	if !(resp.PrevNode.Value == "bar") {
+-		t.Fatalf("Delete PrevNode failed with %s", resp.Node.Value)
+-	}
+-
+-	resp, err = c.Delete("foo", false)
+-	if err == nil {
+-		t.Fatalf("Delete should have failed because the key foo did not exist.  "+
+-			"The response was: %v", resp)
 -	}
--	return true
 -}
 -
--// TestSortValues ensures the sort functionality for relect.Value based sorting
--// works as intended.
--func TestSortValues(t *testing.T) {
--	getInterfaces := func(values []reflect.Value) []interface{} {
--		interfaces := []interface{}{}
--		for _, v := range values {
--			interfaces = append(interfaces, v.Interface())
--		}
--		return interfaces
+-func TestDeleteAll(t *testing.T) {
+-	c := NewClient(nil)
+-	defer func() {
+-		c.Delete("foo", true)
+-		c.Delete("fooDir", true)
+-	}()
+-
+-	c.SetDir("foo", 5)
+-	// test delete an empty dir
+-	resp, err := c.DeleteDir("foo")
+-	if err != nil {
+-		t.Fatal(err)
 -	}
 -
--	v := reflect.ValueOf
+-	if !(resp.Node.Value == "") {
+-		t.Fatalf("DeleteAll 1 failed: %#v", resp)
+-	}
 -
--	a := v("a")
--	b := v("b")
--	c := v("c")
--	embedA := v(embed{"a"})
--	embedB := v(embed{"b"})
--	embedC := v(embed{"c"})
--	tests := []struct {
--		input    []reflect.Value
--		expected []reflect.Value
--	}{
--		// No values.
--		{
--			[]reflect.Value{},
--			[]reflect.Value{},
--		},
--		// Bools.
--		{
--			[]reflect.Value{v(false), v(true), v(false)},
--			[]reflect.Value{v(false), v(false), v(true)},
--		},
--		// Ints.
--		{
--			[]reflect.Value{v(2), v(1), v(3)},
--			[]reflect.Value{v(1), v(2), v(3)},
--		},
--		// Uints.
--		{
--			[]reflect.Value{v(uint8(2)), v(uint8(1)), v(uint8(3))},
--			[]reflect.Value{v(uint8(1)), v(uint8(2)), v(uint8(3))},
--		},
--		// Floats.
--		{
--			[]reflect.Value{v(2.0), v(1.0), v(3.0)},
--			[]reflect.Value{v(1.0), v(2.0), v(3.0)},
--		},
--		// Strings.
--		{
--			[]reflect.Value{b, a, c},
--			[]reflect.Value{a, b, c},
--		},
--		// Uintptrs.
--		{
--			[]reflect.Value{v(uintptr(2)), v(uintptr(1)), v(uintptr(3))},
--			[]reflect.Value{v(uintptr(1)), v(uintptr(2)), v(uintptr(3))},
--		},
--		// Invalid.
--		{
--			[]reflect.Value{embedB, embedA, embedC},
--			[]reflect.Value{embedB, embedA, embedC},
--		},
+-	if !(resp.PrevNode.Dir == true && resp.PrevNode.Value == "") {
+-		t.Fatalf("DeleteAll 1 PrevNode failed: %#v", resp)
 -	}
--	for _, test := range tests {
--		spew.SortValues(test.input)
--		// reflect.DeepEqual cannot really make sense of reflect.Value,
--		// probably because of all the pointer tricks. For instance,
--		// v(2.0) != v(2.0) on a 32-bits system. Turn them into interface{}
--		// instead.
--		input := getInterfaces(test.input)
--		expected := getInterfaces(test.expected)
--		if !reflect.DeepEqual(input, expected) {
--			t.Errorf("Sort mismatch:\n %v != %v", input, expected)
--		}
+-
+-	c.CreateDir("fooDir", 5)
+-	c.Set("fooDir/foo", "bar", 5)
+-	_, err = c.DeleteDir("fooDir")
+-	if err == nil {
+-		t.Fatal("should not able to delete a non-empty dir with deletedir")
+-	}
+-
+-	resp, err = c.Delete("fooDir", true)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	if !(resp.Node.Value == "") {
+-		t.Fatalf("DeleteAll 2 failed: %#v", resp)
+-	}
+-
+-	if !(resp.PrevNode.Dir == true && resp.PrevNode.Value == "") {
+-		t.Fatalf("DeleteAll 2 PrevNode failed: %#v", resp)
+-	}
+-
+-	resp, err = c.Delete("foo", true)
+-	if err == nil {
+-		t.Fatalf("DeleteAll should have failed because the key foo did not exist.  "+
+-			"The response was: %v", resp)
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/config.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/config.go
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/error.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/error.go
 deleted file mode 100644
-index e516675..0000000
---- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/config.go
+index 7e69287..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/error.go
 +++ /dev/null
-@@ -1,288 +0,0 @@
--/*
-- * Copyright (c) 2013 Dave Collins <dave at davec.name>
-- *
-- * Permission to use, copy, modify, and distribute this software for any
-- * purpose with or without fee is hereby granted, provided that the above
-- * copyright notice and this permission notice appear in all copies.
-- *
-- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
-- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
-- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
-- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
-- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
-- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
-- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
-- */
--
--package spew
+@@ -1,48 +0,0 @@
+-package etcd
 -
 -import (
--	"bytes"
+-	"encoding/json"
 -	"fmt"
--	"io"
--	"os"
 -)
 -
--// ConfigState houses the configuration options used by spew to format and
--// display values.  There is a global instance, Config, that is used to control
--// all top-level Formatter and Dump functionality.  Each ConfigState instance
--// provides methods equivalent to the top-level functions.
--//
--// The zero value for ConfigState provides no indentation.  You would typically
--// want to set it to a space or a tab.
--//
--// Alternatively, you can use NewDefaultConfig to get a ConfigState instance
--// with default settings.  See the documentation of NewDefaultConfig for default
--// values.
--type ConfigState struct {
--	// Indent specifies the string to use for each indentation level.  The
--	// global config instance that all top-level functions use set this to a
--	// single space by default.  If you would like more indentation, you might
--	// set this to a tab with "\t" or perhaps two spaces with "  ".
--	Indent string
--
--	// MaxDepth controls the maximum number of levels to descend into nested
--	// data structures.  The default, 0, means there is no limit.
--	//
--	// NOTE: Circular data structures are properly detected, so it is not
--	// necessary to set this value unless you specifically want to limit deeply
--	// nested data structures.
--	MaxDepth int
+-const (
+-	ErrCodeEtcdNotReachable = 501
+-)
 -
--	// DisableMethods specifies whether or not error and Stringer interfaces are
--	// invoked for types that implement them.
--	DisableMethods bool
+-var (
+-	errorMap = map[int]string{
+-		ErrCodeEtcdNotReachable: "All the given peers are not reachable",
+-	}
+-)
 -
--	// DisablePointerMethods specifies whether or not to check for and invoke
--	// error and Stringer interfaces on types which only accept a pointer
--	// receiver when the current type is not a pointer.
--	//
--	// NOTE: This might be an unsafe action since calling one of these methods
--	// with a pointer receiver could technically mutate the value, however,
--	// in practice, types which choose to satisify an error or Stringer
--	// interface with a pointer receiver should not be mutating their state
--	// inside these interface methods.
--	DisablePointerMethods bool
+-type EtcdError struct {
+-	ErrorCode int    `json:"errorCode"`
+-	Message   string `json:"message"`
+-	Cause     string `json:"cause,omitempty"`
+-	Index     uint64 `json:"index"`
+-}
 -
--	// ContinueOnMethod specifies whether or not recursion should continue once
--	// a custom error or Stringer interface is invoked.  The default, false,
--	// means it will print the results of invoking the custom error or Stringer
--	// interface and return immediately instead of continuing to recurse into
--	// the internals of the data type.
--	//
--	// NOTE: This flag does not have any effect if method invocation is disabled
--	// via the DisableMethods or DisablePointerMethods options.
--	ContinueOnMethod bool
+-func (e EtcdError) Error() string {
+-	return fmt.Sprintf("%v: %v (%v) [%v]", e.ErrorCode, e.Message, e.Cause, e.Index)
+-}
 -
--	// SortKeys specifies map keys should be sorted before being printed. Use
--	// this to have a more deterministic, diffable output.  Note that only
--	// native types (bool, int, uint, floats, uintptr and string) are supported
--	// with other types sorted according to the reflect.Value.String() output
--	// which guarantees display stability.
--	SortKeys bool
+-func newError(errorCode int, cause string, index uint64) *EtcdError {
+-	return &EtcdError{
+-		ErrorCode: errorCode,
+-		Message:   errorMap[errorCode],
+-		Cause:     cause,
+-		Index:     index,
+-	}
 -}
 -
--// Config is the active configuration of the top-level functions.
--// The configuration can be changed by modifying the contents of spew.Config.
--var Config = ConfigState{Indent: " "}
+-func handleError(b []byte) error {
+-	etcdErr := new(EtcdError)
 -
--// Errorf is a wrapper for fmt.Errorf that treats each argument as if it were
--// passed with a Formatter interface returned by c.NewFormatter.  It returns
--// the formatted string as a value that satisfies error.  See NewFormatter
--// for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Errorf(format, c.NewFormatter(a), c.NewFormatter(b))
--func (c *ConfigState) Errorf(format string, a ...interface{}) (err error) {
--	return fmt.Errorf(format, c.convertArgs(a)...)
--}
+-	err := json.Unmarshal(b, etcdErr)
+-	if err != nil {
+-		logger.Warningf("cannot unmarshal etcd error: %v", err)
+-		return err
+-	}
 -
--// Fprint is a wrapper for fmt.Fprint that treats each argument as if it were
--// passed with a Formatter interface returned by c.NewFormatter.  It returns
--// the number of bytes written and any write error encountered.  See
--// NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Fprint(w, c.NewFormatter(a), c.NewFormatter(b))
--func (c *ConfigState) Fprint(w io.Writer, a ...interface{}) (n int, err error) {
--	return fmt.Fprint(w, c.convertArgs(a)...)
+-	return etcdErr
 -}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/get.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/get.go
+deleted file mode 100644
+index 976bf07..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/get.go
++++ /dev/null
+@@ -1,27 +0,0 @@
+-package etcd
 -
--// Fprintf is a wrapper for fmt.Fprintf that treats each argument as if it were
--// passed with a Formatter interface returned by c.NewFormatter.  It returns
--// the number of bytes written and any write error encountered.  See
--// NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Fprintf(w, format, c.NewFormatter(a), c.NewFormatter(b))
--func (c *ConfigState) Fprintf(w io.Writer, format string, a ...interface{}) (n int, err error) {
--	return fmt.Fprintf(w, format, c.convertArgs(a)...)
--}
+-// Get gets the file or directory associated with the given key.
+-// If the key points to a directory, files and directories under
+-// it will be returned in sorted or unsorted order, depending on
+-// the sort flag.
+-// If recursive is set to false, contents under child directories
+-// will not be returned.
+-// If recursive is set to true, all the contents will be returned.
+-func (c *Client) Get(key string, sort, recursive bool) (*Response, error) {
+-	raw, err := c.RawGet(key, sort, recursive)
 -
--// Fprintln is a wrapper for fmt.Fprintln that treats each argument as if it
--// passed with a Formatter interface returned by c.NewFormatter.  See
--// NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Fprintln(w, c.NewFormatter(a), c.NewFormatter(b))
--func (c *ConfigState) Fprintln(w io.Writer, a ...interface{}) (n int, err error) {
--	return fmt.Fprintln(w, c.convertArgs(a)...)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	return raw.Unmarshal()
 -}
 -
--// Print is a wrapper for fmt.Print that treats each argument as if it were
--// passed with a Formatter interface returned by c.NewFormatter.  It returns
--// the number of bytes written and any write error encountered.  See
--// NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Print(c.NewFormatter(a), c.NewFormatter(b))
--func (c *ConfigState) Print(a ...interface{}) (n int, err error) {
--	return fmt.Print(c.convertArgs(a)...)
--}
+-func (c *Client) RawGet(key string, sort, recursive bool) (*RawResponse, error) {
+-	ops := Options{
+-		"recursive": recursive,
+-		"sorted":    sort,
+-	}
 -
--// Printf is a wrapper for fmt.Printf that treats each argument as if it were
--// passed with a Formatter interface returned by c.NewFormatter.  It returns
--// the number of bytes written and any write error encountered.  See
--// NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Printf(format, c.NewFormatter(a), c.NewFormatter(b))
--func (c *ConfigState) Printf(format string, a ...interface{}) (n int, err error) {
--	return fmt.Printf(format, c.convertArgs(a)...)
+-	return c.get(key, ops)
 -}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/get_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/get_test.go
+deleted file mode 100644
+index 279c4e2..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/get_test.go
++++ /dev/null
+@@ -1,131 +0,0 @@
+-package etcd
 -
--// Println is a wrapper for fmt.Println that treats each argument as if it were
--// passed with a Formatter interface returned by c.NewFormatter.  It returns
--// the number of bytes written and any write error encountered.  See
--// NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Println(c.NewFormatter(a), c.NewFormatter(b))
--func (c *ConfigState) Println(a ...interface{}) (n int, err error) {
--	return fmt.Println(c.convertArgs(a)...)
--}
+-import (
+-	"reflect"
+-	"testing"
+-)
 -
--// Sprint is a wrapper for fmt.Sprint that treats each argument as if it were
--// passed with a Formatter interface returned by c.NewFormatter.  It returns
--// the resulting string.  See NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Sprint(c.NewFormatter(a), c.NewFormatter(b))
--func (c *ConfigState) Sprint(a ...interface{}) string {
--	return fmt.Sprint(c.convertArgs(a)...)
+-// cleanNode scrubs Expiration, ModifiedIndex and CreatedIndex of a node.
+-func cleanNode(n *Node) {
+-	n.Expiration = nil
+-	n.ModifiedIndex = 0
+-	n.CreatedIndex = 0
 -}
 -
--// Sprintf is a wrapper for fmt.Sprintf that treats each argument as if it were
--// passed with a Formatter interface returned by c.NewFormatter.  It returns
--// the resulting string.  See NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Sprintf(format, c.NewFormatter(a), c.NewFormatter(b))
--func (c *ConfigState) Sprintf(format string, a ...interface{}) string {
--	return fmt.Sprintf(format, c.convertArgs(a)...)
+-// cleanResult scrubs a result object two levels deep of Expiration,
+-// ModifiedIndex and CreatedIndex.
+-func cleanResult(result *Response) {
+-	//  TODO(philips): make this recursive.
+-	cleanNode(result.Node)
+-	for i, _ := range result.Node.Nodes {
+-		cleanNode(result.Node.Nodes[i])
+-		for j, _ := range result.Node.Nodes[i].Nodes {
+-			cleanNode(result.Node.Nodes[i].Nodes[j])
+-		}
+-	}
 -}
 -
--// Sprintln is a wrapper for fmt.Sprintln that treats each argument as if it
--// were passed with a Formatter interface returned by c.NewFormatter.  It
--// returns the resulting string.  See NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Sprintln(c.NewFormatter(a), c.NewFormatter(b))
--func (c *ConfigState) Sprintln(a ...interface{}) string {
--	return fmt.Sprintln(c.convertArgs(a)...)
--}
+-func TestGet(t *testing.T) {
+-	c := NewClient(nil)
+-	defer func() {
+-		c.Delete("foo", true)
+-	}()
 -
--/*
--NewFormatter returns a custom formatter that satisfies the fmt.Formatter
--interface.  As a result, it integrates cleanly with standard fmt package
--printing functions.  The formatter is useful for inline printing of smaller data
--types similar to the standard %v format specifier.
+-	c.Set("foo", "bar", 5)
 -
--The custom formatter only responds to the %v (most compact), %+v (adds pointer
--addresses), %#v (adds types), and %#+v (adds types and pointer addresses) verb
--combinations.  Any other verbs such as %x and %q will be sent to the the
--standard fmt package for formatting.  In addition, the custom formatter ignores
--the width and precision arguments (however they will still work on the format
--specifiers not handled by the custom formatter).
+-	result, err := c.Get("foo", false, false)
 -
--Typically this function shouldn't be called directly.  It is much easier to make
--use of the custom formatter by calling one of the convenience functions such as
--c.Printf, c.Println, or c.Printf.
--*/
--func (c *ConfigState) NewFormatter(v interface{}) fmt.Formatter {
--	return newFormatter(c, v)
--}
+-	if err != nil {
+-		t.Fatal(err)
+-	}
 -
--// Fdump formats and displays the passed arguments to io.Writer w.  It formats
--// exactly the same as Dump.
--func (c *ConfigState) Fdump(w io.Writer, a ...interface{}) {
--	fdump(c, w, a...)
--}
+-	if result.Node.Key != "/foo" || result.Node.Value != "bar" {
+-		t.Fatalf("Get failed with %s %s %v", result.Node.Key, result.Node.Value, result.Node.TTL)
+-	}
 -
--/*
--Dump displays the passed parameters to standard out with newlines, customizable
--indentation, and additional debug information such as complete types and all
--pointer addresses used to indirect to the final value.  It provides the
--following features over the built-in printing facilities provided by the fmt
--package:
+-	result, err = c.Get("goo", false, false)
+-	if err == nil {
+-		t.Fatalf("should not be able to get non-exist key")
+-	}
+-}
 -
--	* Pointers are dereferenced and followed
--	* Circular data structures are detected and handled properly
--	* Custom Stringer/error interfaces are optionally invoked, including
--	  on unexported types
--	* Custom types which only implement the Stringer/error interfaces via
--	  a pointer receiver are optionally invoked when passing non-pointer
--	  variables
--	* Byte arrays and slices are dumped like the hexdump -C command which
--	  includes offsets, byte values in hex, and ASCII output
+-func TestGetAll(t *testing.T) {
+-	c := NewClient(nil)
+-	defer func() {
+-		c.Delete("fooDir", true)
+-	}()
 -
--The configuration options are controlled by modifying the public members
--of c.  See ConfigState for options documentation.
+-	c.CreateDir("fooDir", 5)
+-	c.Set("fooDir/k0", "v0", 5)
+-	c.Set("fooDir/k1", "v1", 5)
 -
--See Fdump if you would prefer dumping to an arbitrary io.Writer or Sdump to
--get the formatted result as a string.
--*/
--func (c *ConfigState) Dump(a ...interface{}) {
--	fdump(c, os.Stdout, a...)
--}
+-	// Return kv-pairs in sorted order
+-	result, err := c.Get("fooDir", true, false)
 -
--// Sdump returns a string with the passed arguments formatted exactly the same
--// as Dump.
--func (c *ConfigState) Sdump(a ...interface{}) string {
--	var buf bytes.Buffer
--	fdump(c, &buf, a...)
--	return buf.String()
--}
+-	if err != nil {
+-		t.Fatal(err)
+-	}
 -
--// convertArgs accepts a slice of arguments and returns a slice of the same
--// length with each argument converted to a spew Formatter interface using
--// the ConfigState associated with s.
--func (c *ConfigState) convertArgs(args []interface{}) (formatters []interface{}) {
--	formatters = make([]interface{}, len(args))
--	for index, arg := range args {
--		formatters[index] = newFormatter(c, arg)
+-	expected := Nodes{
+-		&Node{
+-			Key:   "/fooDir/k0",
+-			Value: "v0",
+-			TTL:   5,
+-		},
+-		&Node{
+-			Key:   "/fooDir/k1",
+-			Value: "v1",
+-			TTL:   5,
+-		},
 -	}
--	return formatters
--}
 -
--// NewDefaultConfig returns a ConfigState with the following default settings.
--//
--// 	Indent: " "
--// 	MaxDepth: 0
--// 	DisableMethods: false
--// 	DisablePointerMethods: false
--// 	ContinueOnMethod: false
--// 	SortKeys: false
--func NewDefaultConfig() *ConfigState {
--	return &ConfigState{Indent: " "}
--}
-diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/doc.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/doc.go
-deleted file mode 100644
-index a0d73ac..0000000
---- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/doc.go
-+++ /dev/null
-@@ -1,196 +0,0 @@
--/*
-- * Copyright (c) 2013 Dave Collins <dave at davec.name>
-- *
-- * Permission to use, copy, modify, and distribute this software for any
-- * purpose with or without fee is hereby granted, provided that the above
-- * copyright notice and this permission notice appear in all copies.
-- *
-- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
-- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
-- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
-- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
-- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
-- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
-- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
-- */
+-	cleanResult(result)
 -
--/*
--Package spew implements a deep pretty printer for Go data structures to aid in
--debugging.
+-	if !reflect.DeepEqual(result.Node.Nodes, expected) {
+-		t.Fatalf("(actual) %v != (expected) %v", result.Node.Nodes, expected)
+-	}
 -
--A quick overview of the additional features spew provides over the built-in
--printing facilities for Go data types are as follows:
+-	// Test the `recursive` option
+-	c.CreateDir("fooDir/childDir", 5)
+-	c.Set("fooDir/childDir/k2", "v2", 5)
 -
--	* Pointers are dereferenced and followed
--	* Circular data structures are detected and handled properly
--	* Custom Stringer/error interfaces are optionally invoked, including
--	  on unexported types
--	* Custom types which only implement the Stringer/error interfaces via
--	  a pointer receiver are optionally invoked when passing non-pointer
--	  variables
--	* Byte arrays and slices are dumped like the hexdump -C command which
--	  includes offsets, byte values in hex, and ASCII output (only when using
--	  Dump style)
+-	// Return kv-pairs in sorted order
+-	result, err = c.Get("fooDir", true, true)
 -
--There are two different approaches spew allows for dumping Go data structures:
+-	cleanResult(result)
 -
--	* Dump style which prints with newlines, customizable indentation,
--	  and additional debug information such as types and all pointer addresses
--	  used to indirect to the final value
--	* A custom Formatter interface that integrates cleanly with the standard fmt
--	  package and replaces %v, %+v, %#v, and %#+v to provide inline printing
--	  similar to the default %v while providing the additional functionality
--	  outlined above and passing unsupported format verbs such as %x and %q
--	  along to fmt
+-	if err != nil {
+-		t.Fatal(err)
+-	}
 -
--Quick Start
+-	expected = Nodes{
+-		&Node{
+-			Key: "/fooDir/childDir",
+-			Dir: true,
+-			Nodes: Nodes{
+-				&Node{
+-					Key:   "/fooDir/childDir/k2",
+-					Value: "v2",
+-					TTL:   5,
+-				},
+-			},
+-			TTL: 5,
+-		},
+-		&Node{
+-			Key:   "/fooDir/k0",
+-			Value: "v0",
+-			TTL:   5,
+-		},
+-		&Node{
+-			Key:   "/fooDir/k1",
+-			Value: "v1",
+-			TTL:   5,
+-		},
+-	}
 -
--This section demonstrates how to quickly get started with spew.  See the
--sections below for further details on formatting and configuration options.
+-	cleanResult(result)
 -
--To dump a variable with full newlines, indentation, type, and pointer
--information use Dump, Fdump, or Sdump:
--	spew.Dump(myVar1, myVar2, ...)
--	spew.Fdump(someWriter, myVar1, myVar2, ...)
--	str := spew.Sdump(myVar1, myVar2, ...)
+-	if !reflect.DeepEqual(result.Node.Nodes, expected) {
+-		t.Fatalf("(actual) %v != (expected) %v", result.Node.Nodes, expected)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/options.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/options.go
+deleted file mode 100644
+index 701c9b3..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/options.go
++++ /dev/null
+@@ -1,72 +0,0 @@
+-package etcd
 -
--Alternatively, if you would prefer to use format strings with a compacted inline
--printing style, use the convenience wrappers Printf, Fprintf, etc with
--%v (most compact), %+v (adds pointer addresses), %#v (adds types), or
--%#+v (adds types and pointer addresses):
--	spew.Printf("myVar1: %v -- myVar2: %+v", myVar1, myVar2)
--	spew.Printf("myVar3: %#v -- myVar4: %#+v", myVar3, myVar4)
--	spew.Fprintf(someWriter, "myVar1: %v -- myVar2: %+v", myVar1, myVar2)
--	spew.Fprintf(someWriter, "myVar3: %#v -- myVar4: %#+v", myVar3, myVar4)
+-import (
+-	"fmt"
+-	"net/url"
+-	"reflect"
+-)
 -
--Configuration Options
+-type Options map[string]interface{}
 -
--Configuration of spew is handled by fields in the ConfigState type.  For
--convenience, all of the top-level functions use a global state available
--via the spew.Config global.
+-// An internally-used data structure that represents a mapping
+-// between valid options and their kinds
+-type validOptions map[string]reflect.Kind
 -
--It is also possible to create a ConfigState instance that provides methods
--equivalent to the top-level functions.  This allows concurrent configuration
--options.  See the ConfigState documentation for more details.
+-// Valid options for GET, PUT, POST, DELETE
+-// Using CAPITALIZED_UNDERSCORE to emphasize that these
+-// values are meant to be used as constants.
+-var (
+-	VALID_GET_OPTIONS = validOptions{
+-		"recursive":  reflect.Bool,
+-		"consistent": reflect.Bool,
+-		"sorted":     reflect.Bool,
+-		"wait":       reflect.Bool,
+-		"waitIndex":  reflect.Uint64,
+-	}
 -
--The following configuration options are available:
--	* Indent
--		String to use for each indentation level for Dump functions.
--		It is a single space by default.  A popular alternative is "\t".
+-	VALID_PUT_OPTIONS = validOptions{
+-		"prevValue": reflect.String,
+-		"prevIndex": reflect.Uint64,
+-		"prevExist": reflect.Bool,
+-		"dir":       reflect.Bool,
+-	}
 -
--	* MaxDepth
--		Maximum number of levels to descend into nested data structures.
--		There is no limit by default.
+-	VALID_POST_OPTIONS = validOptions{}
 -
--	* DisableMethods
--		Disables invocation of error and Stringer interface methods.
--		Method invocation is enabled by default.
+-	VALID_DELETE_OPTIONS = validOptions{
+-		"recursive": reflect.Bool,
+-		"dir":       reflect.Bool,
+-		"prevValue": reflect.String,
+-		"prevIndex": reflect.Uint64,
+-	}
+-)
 -
--	* DisablePointerMethods
--		Disables invocation of error and Stringer interface methods on types
--		which only accept pointer receivers from non-pointer variables.
--		Pointer method invocation is enabled by default.
+-// Convert options to a string of HTML parameters
+-func (ops Options) toParameters(validOps validOptions) (string, error) {
+-	p := "?"
+-	values := url.Values{}
 -
--	* ContinueOnMethod
--		Enables recursion into types after invoking error and Stringer interface
--		methods. Recursion after method invocation is disabled by default.
+-	if ops == nil {
+-		return "", nil
+-	}
 -
--	* SortKeys
--		Specifies map keys should be sorted before being printed. Use
--		this to have a more deterministic, diffable output.  Note that
--		only native types (bool, int, uint, floats, uintptr and string)
--		are supported with other types sorted according to the
--		reflect.Value.String() output which guarantees display stability.
--		Natural map order is used by default.
+-	for k, v := range ops {
+-		// Check if the given option is valid (that it exists)
+-		kind := validOps[k]
+-		if kind == reflect.Invalid {
+-			return "", fmt.Errorf("Invalid option: %v", k)
+-		}
 -
--Dump Usage
+-		// Check if the given option is of the valid type
+-		t := reflect.TypeOf(v)
+-		if kind != t.Kind() {
+-			return "", fmt.Errorf("Option %s should be of %v kind, not of %v kind.",
+-				k, kind, t.Kind())
+-		}
 -
--Simply call spew.Dump with a list of variables you want to dump:
+-		values.Set(k, fmt.Sprintf("%v", v))
+-	}
 -
--	spew.Dump(myVar1, myVar2, ...)
+-	p += values.Encode()
+-	return p, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/requests.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/requests.go
+deleted file mode 100644
+index 5d8b45a..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/requests.go
++++ /dev/null
+@@ -1,377 +0,0 @@
+-package etcd
 -
--You may also call spew.Fdump if you would prefer to output to an arbitrary
--io.Writer.  For example, to dump to standard error:
+-import (
+-	"errors"
+-	"fmt"
+-	"io/ioutil"
+-	"math/rand"
+-	"net/http"
+-	"net/url"
+-	"path"
+-	"strings"
+-	"sync"
+-	"time"
+-)
 -
--	spew.Fdump(os.Stderr, myVar1, myVar2, ...)
+-// Errors introduced by handling requests
+-var (
+-	ErrRequestCancelled = errors.New("sending request is cancelled")
+-)
 -
--A third option is to call spew.Sdump to get the formatted output as a string:
+-type RawRequest struct {
+-	Method       string
+-	RelativePath string
+-	Values       url.Values
+-	Cancel       <-chan bool
+-}
 -
--	str := spew.Sdump(myVar1, myVar2, ...)
+-// NewRawRequest returns a new RawRequest
+-func NewRawRequest(method, relativePath string, values url.Values, cancel <-chan bool) *RawRequest {
+-	return &RawRequest{
+-		Method:       method,
+-		RelativePath: relativePath,
+-		Values:       values,
+-		Cancel:       cancel,
+-	}
+-}
 -
--Sample Dump Output
+-// getCancelable issues a cancelable GET request
+-func (c *Client) getCancelable(key string, options Options,
+-	cancel <-chan bool) (*RawResponse, error) {
+-	logger.Debugf("get %s [%s]", key, c.cluster.Leader)
+-	p := keyToPath(key)
 -
--See the Dump example for details on the setup of the types and variables being
--shown here.
+-	// If consistency level is set to STRONG, append
+-	// the `consistent` query string.
+-	if c.config.Consistency == STRONG_CONSISTENCY {
+-		options["consistent"] = true
+-	}
 -
--	(main.Foo) {
--	 unexportedField: (*main.Bar)(0xf84002e210)({
--	  flag: (main.Flag) flagTwo,
--	  data: (uintptr) <nil>
--	 }),
--	 ExportedField: (map[interface {}]interface {}) (len=1) {
--	  (string) (len=3) "one": (bool) true
--	 }
+-	str, err := options.toParameters(VALID_GET_OPTIONS)
+-	if err != nil {
+-		return nil, err
 -	}
+-	p += str
 -
--Byte (and uint8) arrays and slices are displayed uniquely like the hexdump -C
--command as shown.
--	([]uint8) (len=32 cap=32) {
--	 00000000  11 12 13 14 15 16 17 18  19 1a 1b 1c 1d 1e 1f 20  |............... |
--	 00000010  21 22 23 24 25 26 27 28  29 2a 2b 2c 2d 2e 2f 30  |!"#$%&'()*+,-./0|
--	 00000020  31 32                                             |12|
+-	req := NewRawRequest("GET", p, nil, cancel)
+-	resp, err := c.SendRequest(req)
+-
+-	if err != nil {
+-		return nil, err
 -	}
 -
--Custom Formatter
+-	return resp, nil
+-}
 -
--Spew provides a custom formatter that implements the fmt.Formatter interface
--so that it integrates cleanly with standard fmt package printing functions. The
--formatter is useful for inline printing of smaller data types similar to the
--standard %v format specifier.
+-// get issues a GET request
+-func (c *Client) get(key string, options Options) (*RawResponse, error) {
+-	return c.getCancelable(key, options, nil)
+-}
 -
--The custom formatter only responds to the %v (most compact), %+v (adds pointer
--addresses), %#v (adds types), or %#+v (adds types and pointer addresses) verb
--combinations.  Any other verbs such as %x and %q will be sent to the the
--standard fmt package for formatting.  In addition, the custom formatter ignores
--the width and precision arguments (however they will still work on the format
--specifiers not handled by the custom formatter).
+-// put issues a PUT request
+-func (c *Client) put(key string, value string, ttl uint64,
+-	options Options) (*RawResponse, error) {
 -
--Custom Formatter Usage
+-	logger.Debugf("put %s, %s, ttl: %d, [%s]", key, value, ttl, c.cluster.Leader)
+-	p := keyToPath(key)
 -
--The simplest way to make use of the spew custom formatter is to call one of the
--convenience functions such as spew.Printf, spew.Println, or spew.Printf.  The
--functions have syntax you are most likely already familiar with:
+-	str, err := options.toParameters(VALID_PUT_OPTIONS)
+-	if err != nil {
+-		return nil, err
+-	}
+-	p += str
 -
--	spew.Printf("myVar1: %v -- myVar2: %+v", myVar1, myVar2)
--	spew.Printf("myVar3: %#v -- myVar4: %#+v", myVar3, myVar4)
--	spew.Println(myVar, myVar2)
--	spew.Fprintf(os.Stderr, "myVar1: %v -- myVar2: %+v", myVar1, myVar2)
--	spew.Fprintf(os.Stderr, "myVar3: %#v -- myVar4: %#+v", myVar3, myVar4)
+-	req := NewRawRequest("PUT", p, buildValues(value, ttl), nil)
+-	resp, err := c.SendRequest(req)
 -
--See the Index for the full list convenience functions.
+-	if err != nil {
+-		return nil, err
+-	}
 -
--Sample Formatter Output
+-	return resp, nil
+-}
 -
--Double pointer to a uint8:
--	  %v: <**>5
--	 %+v: <**>(0xf8400420d0->0xf8400420c8)5
--	 %#v: (**uint8)5
--	%#+v: (**uint8)(0xf8400420d0->0xf8400420c8)5
+-// post issues a POST request
+-func (c *Client) post(key string, value string, ttl uint64) (*RawResponse, error) {
+-	logger.Debugf("post %s, %s, ttl: %d, [%s]", key, value, ttl, c.cluster.Leader)
+-	p := keyToPath(key)
 -
--Pointer to circular struct with a uint8 field and a pointer to itself:
--	  %v: <*>{1 <*><shown>}
--	 %+v: <*>(0xf84003e260){ui8:1 c:<*>(0xf84003e260)<shown>}
--	 %#v: (*main.circular){ui8:(uint8)1 c:(*main.circular)<shown>}
--	%#+v: (*main.circular)(0xf84003e260){ui8:(uint8)1 c:(*main.circular)(0xf84003e260)<shown>}
+-	req := NewRawRequest("POST", p, buildValues(value, ttl), nil)
+-	resp, err := c.SendRequest(req)
 -
--See the Printf example for details on the setup of variables being shown
--here.
+-	if err != nil {
+-		return nil, err
+-	}
 -
--Errors
+-	return resp, nil
+-}
 -
--Since it is possible for custom Stringer/error interfaces to panic, spew
--detects them and handles them internally by printing the panic information
--inline with the output.  Since spew is intended to provide deep pretty printing
--capabilities on structures, it intentionally does not return any errors.
--*/
--package spew
-diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dump.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dump.go
-deleted file mode 100644
-index 02d4c9d..0000000
---- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dump.go
-+++ /dev/null
-@@ -1,500 +0,0 @@
--/*
-- * Copyright (c) 2013 Dave Collins <dave at davec.name>
-- *
-- * Permission to use, copy, modify, and distribute this software for any
-- * purpose with or without fee is hereby granted, provided that the above
-- * copyright notice and this permission notice appear in all copies.
-- *
-- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
-- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
-- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
-- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
-- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
-- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
-- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
-- */
+-// delete issues a DELETE request
+-func (c *Client) delete(key string, options Options) (*RawResponse, error) {
+-	logger.Debugf("delete %s [%s]", key, c.cluster.Leader)
+-	p := keyToPath(key)
 -
--package spew
+-	str, err := options.toParameters(VALID_DELETE_OPTIONS)
+-	if err != nil {
+-		return nil, err
+-	}
+-	p += str
 -
--import (
--	"bytes"
--	"encoding/hex"
--	"fmt"
--	"io"
--	"os"
--	"reflect"
--	"regexp"
--	"strconv"
--	"strings"
--)
+-	req := NewRawRequest("DELETE", p, nil, nil)
+-	resp, err := c.SendRequest(req)
 -
--var (
--	// uint8Type is a reflect.Type representing a uint8.  It is used to
--	// convert cgo types to uint8 slices for hexdumping.
--	uint8Type = reflect.TypeOf(uint8(0))
+-	if err != nil {
+-		return nil, err
+-	}
 -
--	// cCharRE is a regular expression that matches a cgo char.
--	// It is used to detect character arrays to hexdump them.
--	cCharRE = regexp.MustCompile("^.*\\._Ctype_char$")
+-	return resp, nil
+-}
 -
--	// cUnsignedCharRE is a regular expression that matches a cgo unsigned
--	// char.  It is used to detect unsigned character arrays to hexdump
--	// them.
--	cUnsignedCharRE = regexp.MustCompile("^.*\\._Ctype_unsignedchar$")
+-// SendRequest sends a HTTP request and returns a Response as defined by etcd
+-func (c *Client) SendRequest(rr *RawRequest) (*RawResponse, error) {
 -
--	// cUint8tCharRE is a regular expression that matches a cgo uint8_t.
--	// It is used to detect uint8_t arrays to hexdump them.
--	cUint8tCharRE = regexp.MustCompile("^.*\\._Ctype_uint8_t$")
--)
+-	var req *http.Request
+-	var resp *http.Response
+-	var httpPath string
+-	var err error
+-	var respBody []byte
 -
--// dumpState contains information about the state of a dump operation.
--type dumpState struct {
--	w                io.Writer
--	depth            int
--	pointers         map[uintptr]int
--	ignoreNextType   bool
--	ignoreNextIndent bool
--	cs               *ConfigState
--}
+-	var numReqs = 1
 -
--// indent performs indentation according to the depth level and cs.Indent
--// option.
--func (d *dumpState) indent() {
--	if d.ignoreNextIndent {
--		d.ignoreNextIndent = false
--		return
+-	checkRetry := c.CheckRetry
+-	if checkRetry == nil {
+-		checkRetry = DefaultCheckRetry
 -	}
--	d.w.Write(bytes.Repeat([]byte(d.cs.Indent), d.depth))
--}
 -
--// unpackValue returns values inside of non-nil interfaces when possible.
--// This is useful for data types like structs, arrays, slices, and maps which
--// can contain varying types packed inside an interface.
--func (d *dumpState) unpackValue(v reflect.Value) reflect.Value {
--	if v.Kind() == reflect.Interface && !v.IsNil() {
--		v = v.Elem()
+-	cancelled := make(chan bool, 1)
+-	reqLock := new(sync.Mutex)
+-
+-	if rr.Cancel != nil {
+-		cancelRoutine := make(chan bool)
+-		defer close(cancelRoutine)
+-
+-		go func() {
+-			select {
+-			case <-rr.Cancel:
+-				cancelled <- true
+-				logger.Debug("send.request is cancelled")
+-			case <-cancelRoutine:
+-				return
+-			}
+-
+-			// Repeat canceling request until this thread is stopped
+-			// because we have no idea about whether it succeeds.
+-			for {
+-				reqLock.Lock()
+-				c.httpClient.Transport.(*http.Transport).CancelRequest(req)
+-				reqLock.Unlock()
+-
+-				select {
+-				case <-time.After(100 * time.Millisecond):
+-				case <-cancelRoutine:
+-					return
+-				}
+-			}
+-		}()
 -	}
--	return v
--}
 -
--// dumpPtr handles formatting of pointers by indirecting them as necessary.
--func (d *dumpState) dumpPtr(v reflect.Value) {
--	// Remove pointers at or below the current depth from map used to detect
--	// circular refs.
--	for k, depth := range d.pointers {
--		if depth >= d.depth {
--			delete(d.pointers, k)
+-	// If we connect to a follower and consistency is required, retry until
+-	// we connect to a leader
+-	sleep := 25 * time.Millisecond
+-	maxSleep := time.Second
+-	for attempt := 0; ; attempt++ {
+-		if attempt > 0 {
+-			select {
+-			case <-cancelled:
+-				return nil, ErrRequestCancelled
+-			case <-time.After(sleep):
+-				sleep = sleep * 2
+-				if sleep > maxSleep {
+-					sleep = maxSleep
+-				}
+-			}
 -		}
--	}
 -
--	// Keep list of all dereferenced pointers to show later.
--	pointerChain := make([]uintptr, 0)
+-		logger.Debug("Connecting to etcd: attempt", attempt+1, "for", rr.RelativePath)
 -
--	// Figure out how many levels of indirection there are by dereferencing
--	// pointers and unpacking interfaces down the chain while detecting circular
--	// references.
--	nilFound := false
--	cycleFound := false
--	indirects := 0
--	ve := v
--	for ve.Kind() == reflect.Ptr {
--		if ve.IsNil() {
--			nilFound = true
--			break
--		}
--		indirects++
--		addr := ve.Pointer()
--		pointerChain = append(pointerChain, addr)
--		if pd, ok := d.pointers[addr]; ok && pd < d.depth {
--			cycleFound = true
--			indirects--
--			break
+-		if rr.Method == "GET" && c.config.Consistency == WEAK_CONSISTENCY {
+-			// If it's a GET and consistency level is set to WEAK,
+-			// then use a random machine.
+-			httpPath = c.getHttpPath(true, rr.RelativePath)
+-		} else {
+-			// Else use the leader.
+-			httpPath = c.getHttpPath(false, rr.RelativePath)
 -		}
--		d.pointers[addr] = d.depth
 -
--		ve = ve.Elem()
--		if ve.Kind() == reflect.Interface {
--			if ve.IsNil() {
--				nilFound = true
--				break
+-		// Return a cURL command if curlChan is set
+-		if c.cURLch != nil {
+-			command := fmt.Sprintf("curl -X %s %s", rr.Method, httpPath)
+-			for key, value := range rr.Values {
+-				command += fmt.Sprintf(" -d %s=%s", key, value[0])
 -			}
--			ve = ve.Elem()
+-			c.sendCURL(command)
 -		}
--	}
 -
--	// Display type information.
--	d.w.Write(openParenBytes)
--	d.w.Write(bytes.Repeat(asteriskBytes, indirects))
--	d.w.Write([]byte(ve.Type().String()))
--	d.w.Write(closeParenBytes)
+-		logger.Debug("send.request.to ", httpPath, " | method ", rr.Method)
 -
--	// Display pointer information.
--	if len(pointerChain) > 0 {
--		d.w.Write(openParenBytes)
--		for i, addr := range pointerChain {
--			if i > 0 {
--				d.w.Write(pointerChainBytes)
+-		reqLock.Lock()
+-		if rr.Values == nil {
+-			if req, err = http.NewRequest(rr.Method, httpPath, nil); err != nil {
+-				return nil, err
+-			}
+-		} else {
+-			body := strings.NewReader(rr.Values.Encode())
+-			if req, err = http.NewRequest(rr.Method, httpPath, body); err != nil {
+-				return nil, err
 -			}
--			printHexPtr(d.w, addr)
--		}
--		d.w.Write(closeParenBytes)
--	}
 -
--	// Display dereferenced value.
--	d.w.Write(openParenBytes)
--	switch {
--	case nilFound == true:
--		d.w.Write(nilAngleBytes)
+-			req.Header.Set("Content-Type",
+-				"application/x-www-form-urlencoded; param=value")
+-		}
+-		reqLock.Unlock()
 -
--	case cycleFound == true:
--		d.w.Write(circularBytes)
+-		resp, err = c.httpClient.Do(req)
+-		defer func() {
+-			if resp != nil {
+-				resp.Body.Close()
+-			}
+-		}()
 -
--	default:
--		d.ignoreNextType = true
--		d.dump(ve)
--	}
--	d.w.Write(closeParenBytes)
--}
+-		// If the request was cancelled, return ErrRequestCancelled directly
+-		select {
+-		case <-cancelled:
+-			return nil, ErrRequestCancelled
+-		default:
+-		}
 -
--// dumpSlice handles formatting of arrays and slices.  Byte (uint8 under
--// reflection) arrays and slices are dumped in hexdump -C fashion.
--func (d *dumpState) dumpSlice(v reflect.Value) {
--	// Determine whether this type should be hex dumped or not.  Also,
--	// for types which should be hexdumped, try to use the underlying data
--	// first, then fall back to trying to convert them to a uint8 slice.
--	var buf []uint8
--	doConvert := false
--	doHexDump := false
--	numEntries := v.Len()
--	if numEntries > 0 {
--		vt := v.Index(0).Type()
--		vts := vt.String()
--		switch {
--		// C types that need to be converted.
--		case cCharRE.MatchString(vts):
--			fallthrough
--		case cUnsignedCharRE.MatchString(vts):
--			fallthrough
--		case cUint8tCharRE.MatchString(vts):
--			doConvert = true
+-		numReqs++
 -
--		// Try to use existing uint8 slices and fall back to converting
--		// and copying if that fails.
--		case vt.Kind() == reflect.Uint8:
--			// We need an addressable interface to convert the type back
--			// into a byte slice.  However, the reflect package won't give
--			// us an interface on certain things like unexported struct
--			// fields in order to enforce visibility rules.  We use unsafe
--			// to bypass these restrictions since this package does not
--			// mutate the values.
--			vs := v
--			if !vs.CanInterface() || !vs.CanAddr() {
--				vs = unsafeReflectValue(vs)
+-		// network error, change a machine!
+-		if err != nil {
+-			logger.Debug("network error:", err.Error())
+-			lastResp := http.Response{}
+-			if checkErr := checkRetry(c.cluster, numReqs, lastResp, err); checkErr != nil {
+-				return nil, checkErr
 -			}
--			vs = vs.Slice(0, numEntries)
 -
--			// Use the existing uint8 slice if it can be type
--			// asserted.
--			iface := vs.Interface()
--			if slice, ok := iface.([]uint8); ok {
--				buf = slice
--				doHexDump = true
+-			c.cluster.switchLeader(attempt % len(c.cluster.Machines))
+-			continue
+-		}
+-
+-		// if there is no error, it should receive response
+-		logger.Debug("recv.response.from", httpPath)
+-
+-		if validHttpStatusCode[resp.StatusCode] {
+-			// try to read byte code and break the loop
+-			respBody, err = ioutil.ReadAll(resp.Body)
+-			if err == nil {
+-				logger.Debug("recv.success.", httpPath)
 -				break
 -			}
--
--			// The underlying data needs to be converted if it can't
--			// be type asserted to a uint8 slice.
--			doConvert = true
+-			// ReadAll error may be caused due to cancel request
+-			select {
+-			case <-cancelled:
+-				return nil, ErrRequestCancelled
+-			default:
+-			}
 -		}
 -
--		// Copy and convert the underlying type if needed.
--		if doConvert && vt.ConvertibleTo(uint8Type) {
--			// Convert and copy each element into a uint8 byte
--			// slice.
--			buf = make([]uint8, numEntries)
--			for i := 0; i < numEntries; i++ {
--				vv := v.Index(i)
--				buf[i] = uint8(vv.Convert(uint8Type).Uint())
+-		// if resp is TemporaryRedirect, set the new leader and retry
+-		if resp.StatusCode == http.StatusTemporaryRedirect {
+-			u, err := resp.Location()
+-
+-			if err != nil {
+-				logger.Warning(err)
+-			} else {
+-				// Update cluster leader based on redirect location
+-				// because it should point to the leader address
+-				c.cluster.updateLeaderFromURL(u)
+-				logger.Debug("recv.response.relocate", u.String())
 -			}
--			doHexDump = true
+-			resp.Body.Close()
+-			continue
 -		}
--	}
 -
--	// Hexdump the entire slice as needed.
--	if doHexDump {
--		indent := strings.Repeat(d.cs.Indent, d.depth)
--		str := indent + hex.Dump(buf)
--		str = strings.Replace(str, "\n", "\n"+indent, -1)
--		str = strings.TrimRight(str, d.cs.Indent)
--		d.w.Write([]byte(str))
--		return
+-		if checkErr := checkRetry(c.cluster, numReqs, *resp,
+-			errors.New("Unexpected HTTP status code")); checkErr != nil {
+-			return nil, checkErr
+-		}
+-		resp.Body.Close()
 -	}
 -
--	// Recursively call dump for each item.
--	for i := 0; i < numEntries; i++ {
--		d.dump(d.unpackValue(v.Index(i)))
--		if i < (numEntries - 1) {
--			d.w.Write(commaNewlineBytes)
--		} else {
--			d.w.Write(newlineBytes)
--		}
+-	r := &RawResponse{
+-		StatusCode: resp.StatusCode,
+-		Body:       respBody,
+-		Header:     resp.Header,
 -	}
+-
+-	return r, nil
 -}
 -
--// dump is the main workhorse for dumping a value.  It uses the passed reflect
--// value to figure out what kind of object we are dealing with and formats it
--// appropriately.  It is a recursive function, however circular data structures
--// are detected and handled properly.
--func (d *dumpState) dump(v reflect.Value) {
--	// Handle invalid reflect values immediately.
--	kind := v.Kind()
--	if kind == reflect.Invalid {
--		d.w.Write(invalidAngleBytes)
--		return
--	}
+-// DefaultCheckRetry defines the retrying behaviour for bad HTTP requests
+-// If we have retried 2 * machine number, stop retrying.
+-// If status code is InternalServerError, sleep for 200ms.
+-func DefaultCheckRetry(cluster *Cluster, numReqs int, lastResp http.Response,
+-	err error) error {
 -
--	// Handle pointers specially.
--	if kind == reflect.Ptr {
--		d.indent()
--		d.dumpPtr(v)
--		return
+-	if numReqs >= 2*len(cluster.Machines) {
+-		return newError(ErrCodeEtcdNotReachable,
+-			"Tried to connect to each peer twice and failed", 0)
 -	}
 -
--	// Print type information unless already handled elsewhere.
--	if !d.ignoreNextType {
--		d.indent()
--		d.w.Write(openParenBytes)
--		d.w.Write([]byte(v.Type().String()))
--		d.w.Write(closeParenBytes)
--		d.w.Write(spaceBytes)
--	}
--	d.ignoreNextType = false
+-	code := lastResp.StatusCode
+-	if code == http.StatusInternalServerError {
+-		time.Sleep(time.Millisecond * 200)
 -
--	// Display length and capacity if the built-in len and cap functions
--	// work with the value's kind and the len/cap itself is non-zero.
--	valueLen, valueCap := 0, 0
--	switch v.Kind() {
--	case reflect.Array, reflect.Slice, reflect.Chan:
--		valueLen, valueCap = v.Len(), v.Cap()
--	case reflect.Map, reflect.String:
--		valueLen = v.Len()
--	}
--	if valueLen != 0 || valueCap != 0 {
--		d.w.Write(openParenBytes)
--		if valueLen != 0 {
--			d.w.Write(lenEqualsBytes)
--			printInt(d.w, int64(valueLen), 10)
--		}
--		if valueCap != 0 {
--			if valueLen != 0 {
--				d.w.Write(spaceBytes)
--			}
--			d.w.Write(capEqualsBytes)
--			printInt(d.w, int64(valueCap), 10)
--		}
--		d.w.Write(closeParenBytes)
--		d.w.Write(spaceBytes)
 -	}
 -
--	// Call Stringer/error interfaces if they exist and the handle methods flag
--	// is enabled
--	if !d.cs.DisableMethods {
--		if (kind != reflect.Invalid) && (kind != reflect.Interface) {
--			if handled := handleMethods(d.cs, d.w, v); handled {
--				return
--			}
--		}
+-	logger.Warning("bad response status code", code)
+-	return nil
+-}
+-
+-func (c *Client) getHttpPath(random bool, s ...string) string {
+-	var machine string
+-	if random {
+-		machine = c.cluster.Machines[rand.Intn(len(c.cluster.Machines))]
+-	} else {
+-		machine = c.cluster.Leader
 -	}
 -
--	switch kind {
--	case reflect.Invalid:
--		// Do nothing.  We should never get here since invalid has already
--		// been handled above.
+-	fullPath := machine + "/" + version
+-	for _, seg := range s {
+-		fullPath = fullPath + "/" + seg
+-	}
 -
--	case reflect.Bool:
--		printBool(d.w, v.Bool())
+-	return fullPath
+-}
 -
--	case reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64, reflect.Int:
--		printInt(d.w, v.Int(), 10)
+-// buildValues builds a url.Values map according to the given value and ttl
+-func buildValues(value string, ttl uint64) url.Values {
+-	v := url.Values{}
 -
--	case reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uint:
--		printUint(d.w, v.Uint(), 10)
+-	if value != "" {
+-		v.Set("value", value)
+-	}
 -
--	case reflect.Float32:
--		printFloat(d.w, v.Float(), 32)
+-	if ttl > 0 {
+-		v.Set("ttl", fmt.Sprintf("%v", ttl))
+-	}
 -
--	case reflect.Float64:
--		printFloat(d.w, v.Float(), 64)
+-	return v
+-}
 -
--	case reflect.Complex64:
--		printComplex(d.w, v.Complex(), 32)
+-// convert key string to http path exclude version
+-// for example: key[foo] -> path[keys/foo]
+-// key[/] -> path[keys/]
+-func keyToPath(key string) string {
+-	p := path.Join("keys", key)
 -
--	case reflect.Complex128:
--		printComplex(d.w, v.Complex(), 64)
+-	// corner case: if key is "/" or "//" ect
+-	// path join will clear the tailing "/"
+-	// we need to add it back
+-	if p == "keys" {
+-		p = "keys/"
+-	}
 -
--	case reflect.Slice:
--		if v.IsNil() {
--			d.w.Write(nilAngleBytes)
--			break
--		}
--		fallthrough
+-	return p
+-}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/response.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/response.go
+deleted file mode 100644
+index 1fe9b4e..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/response.go
++++ /dev/null
+@@ -1,89 +0,0 @@
+-package etcd
 -
--	case reflect.Array:
--		d.w.Write(openBraceNewlineBytes)
--		d.depth++
--		if (d.cs.MaxDepth != 0) && (d.depth > d.cs.MaxDepth) {
--			d.indent()
--			d.w.Write(maxNewlineBytes)
--		} else {
--			d.dumpSlice(v)
--		}
--		d.depth--
--		d.indent()
--		d.w.Write(closeBraceBytes)
+-import (
+-	"encoding/json"
+-	"net/http"
+-	"strconv"
+-	"time"
+-)
 -
--	case reflect.String:
--		d.w.Write([]byte(strconv.Quote(v.String())))
+-const (
+-	rawResponse = iota
+-	normalResponse
+-)
 -
--	case reflect.Interface:
--		// The only time we should get here is for nil interfaces due to
--		// unpackValue calls.
--		if v.IsNil() {
--			d.w.Write(nilAngleBytes)
--		}
+-type responseType int
 -
--	case reflect.Ptr:
--		// Do nothing.  We should never get here since pointers have already
--		// been handled above.
+-type RawResponse struct {
+-	StatusCode int
+-	Body       []byte
+-	Header     http.Header
+-}
 -
--	case reflect.Map:
--		d.w.Write(openBraceNewlineBytes)
--		d.depth++
--		if (d.cs.MaxDepth != 0) && (d.depth > d.cs.MaxDepth) {
--			d.indent()
--			d.w.Write(maxNewlineBytes)
--		} else {
--			numEntries := v.Len()
--			keys := v.MapKeys()
--			if d.cs.SortKeys {
--				sortValues(keys)
--			}
--			for i, key := range keys {
--				d.dump(d.unpackValue(key))
--				d.w.Write(colonSpaceBytes)
--				d.ignoreNextIndent = true
--				d.dump(d.unpackValue(v.MapIndex(key)))
--				if i < (numEntries - 1) {
--					d.w.Write(commaNewlineBytes)
--				} else {
--					d.w.Write(newlineBytes)
--				}
--			}
--		}
--		d.depth--
--		d.indent()
--		d.w.Write(closeBraceBytes)
+-var (
+-	validHttpStatusCode = map[int]bool{
+-		http.StatusCreated:            true,
+-		http.StatusOK:                 true,
+-		http.StatusBadRequest:         true,
+-		http.StatusNotFound:           true,
+-		http.StatusPreconditionFailed: true,
+-		http.StatusForbidden:          true,
+-	}
+-)
 -
--	case reflect.Struct:
--		d.w.Write(openBraceNewlineBytes)
--		d.depth++
--		if (d.cs.MaxDepth != 0) && (d.depth > d.cs.MaxDepth) {
--			d.indent()
--			d.w.Write(maxNewlineBytes)
--		} else {
--			vt := v.Type()
--			numFields := v.NumField()
--			for i := 0; i < numFields; i++ {
--				d.indent()
--				vtf := vt.Field(i)
--				d.w.Write([]byte(vtf.Name))
--				d.w.Write(colonSpaceBytes)
--				d.ignoreNextIndent = true
--				d.dump(d.unpackValue(v.Field(i)))
--				if i < (numFields - 1) {
--					d.w.Write(commaNewlineBytes)
--				} else {
--					d.w.Write(newlineBytes)
--				}
--			}
--		}
--		d.depth--
--		d.indent()
--		d.w.Write(closeBraceBytes)
+-// Unmarshal parses RawResponse and stores the result in Response
+-func (rr *RawResponse) Unmarshal() (*Response, error) {
+-	if rr.StatusCode != http.StatusOK && rr.StatusCode != http.StatusCreated {
+-		return nil, handleError(rr.Body)
+-	}
 -
--	case reflect.Uintptr:
--		printHexPtr(d.w, uintptr(v.Uint()))
+-	resp := new(Response)
 -
--	case reflect.UnsafePointer, reflect.Chan, reflect.Func:
--		printHexPtr(d.w, v.Pointer())
+-	err := json.Unmarshal(rr.Body, resp)
 -
--	// There were not any other types at the time this code was written, but
--	// fall back to letting the default fmt package handle it in case any new
--	// types are added.
--	default:
--		if v.CanInterface() {
--			fmt.Fprintf(d.w, "%v", v.Interface())
--		} else {
--			fmt.Fprintf(d.w, "%v", v.String())
--		}
+-	if err != nil {
+-		return nil, err
 -	}
--}
 -
--// fdump is a helper function to consolidate the logic from the various public
--// methods which take varying writers and config states.
--func fdump(cs *ConfigState, w io.Writer, a ...interface{}) {
--	for _, arg := range a {
--		if arg == nil {
--			w.Write(interfaceBytes)
--			w.Write(spaceBytes)
--			w.Write(nilAngleBytes)
--			w.Write(newlineBytes)
--			continue
--		}
+-	// attach index and term to response
+-	resp.EtcdIndex, _ = strconv.ParseUint(rr.Header.Get("X-Etcd-Index"), 10, 64)
+-	resp.RaftIndex, _ = strconv.ParseUint(rr.Header.Get("X-Raft-Index"), 10, 64)
+-	resp.RaftTerm, _ = strconv.ParseUint(rr.Header.Get("X-Raft-Term"), 10, 64)
 -
--		d := dumpState{w: w, cs: cs}
--		d.pointers = make(map[uintptr]int)
--		d.dump(reflect.ValueOf(arg))
--		d.w.Write(newlineBytes)
--	}
+-	return resp, nil
 -}
 -
--// Fdump formats and displays the passed arguments to io.Writer w.  It formats
--// exactly the same as Dump.
--func Fdump(w io.Writer, a ...interface{}) {
--	fdump(&Config, w, a...)
+-type Response struct {
+-	Action    string `json:"action"`
+-	Node      *Node  `json:"node"`
+-	PrevNode  *Node  `json:"prevNode,omitempty"`
+-	EtcdIndex uint64 `json:"etcdIndex"`
+-	RaftIndex uint64 `json:"raftIndex"`
+-	RaftTerm  uint64 `json:"raftTerm"`
 -}
 -
--// Sdump returns a string with the passed arguments formatted exactly the same
--// as Dump.
--func Sdump(a ...interface{}) string {
--	var buf bytes.Buffer
--	fdump(&Config, &buf, a...)
--	return buf.String()
+-type Node struct {
+-	Key           string     `json:"key, omitempty"`
+-	Value         string     `json:"value,omitempty"`
+-	Dir           bool       `json:"dir,omitempty"`
+-	Expiration    *time.Time `json:"expiration,omitempty"`
+-	TTL           int64      `json:"ttl,omitempty"`
+-	Nodes         Nodes      `json:"nodes,omitempty"`
+-	ModifiedIndex uint64     `json:"modifiedIndex,omitempty"`
+-	CreatedIndex  uint64     `json:"createdIndex,omitempty"`
 -}
 -
--/*
--Dump displays the passed parameters to standard out with newlines, customizable
--indentation, and additional debug information such as complete types and all
--pointer addresses used to indirect to the final value.  It provides the
--following features over the built-in printing facilities provided by the fmt
--package:
+-type Nodes []*Node
 -
--	* Pointers are dereferenced and followed
--	* Circular data structures are detected and handled properly
--	* Custom Stringer/error interfaces are optionally invoked, including
--	  on unexported types
--	* Custom types which only implement the Stringer/error interfaces via
--	  a pointer receiver are optionally invoked when passing non-pointer
--	  variables
--	* Byte arrays and slices are dumped like the hexdump -C command which
--	  includes offsets, byte values in hex, and ASCII output
+-// interfaces for sorting
+-func (ns Nodes) Len() int {
+-	return len(ns)
+-}
 -
--The configuration options are controlled by an exported package global,
--spew.Config.  See ConfigState for options documentation.
+-func (ns Nodes) Less(i, j int) bool {
+-	return ns[i].Key < ns[j].Key
+-}
 -
--See Fdump if you would prefer dumping to an arbitrary io.Writer or Sdump to
--get the formatted result as a string.
--*/
--func Dump(a ...interface{}) {
--	fdump(&Config, os.Stdout, a...)
+-func (ns Nodes) Swap(i, j int) {
+-	ns[i], ns[j] = ns[j], ns[i]
 -}
-diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dump_test.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dump_test.go
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/set_curl_chan_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/set_curl_chan_test.go
 deleted file mode 100644
-index f1a5644..0000000
---- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dump_test.go
+index 756e317..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/set_curl_chan_test.go
 +++ /dev/null
-@@ -1,978 +0,0 @@
--/*
-- * Copyright (c) 2013 Dave Collins <dave at davec.name>
-- *
-- * Permission to use, copy, modify, and distribute this software for any
-- * purpose with or without fee is hereby granted, provided that the above
-- * copyright notice and this permission notice appear in all copies.
-- *
-- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
-- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
-- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
-- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
-- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
-- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
-- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
-- */
--
--/*
--Test Summary:
--NOTE: For each test, a nil pointer, a single pointer and double pointer to the
--base test element are also tested to ensure proper indirection across all types.
--
--- Max int8, int16, int32, int64, int
--- Max uint8, uint16, uint32, uint64, uint
--- Boolean true and false
--- Standard complex64 and complex128
--- Array containing standard ints
--- Array containing type with custom formatter on pointer receiver only
--- Array containing interfaces
--- Array containing bytes
--- Slice containing standard float32 values
--- Slice containing type with custom formatter on pointer receiver only
--- Slice containing interfaces
--- Slice containing bytes
--- Nil slice
--- Standard string
--- Nil interface
--- Sub-interface
--- Map with string keys and int vals
--- Map with custom formatter type on pointer receiver only keys and vals
--- Map with interface keys and values
--- Map with nil interface value
--- Struct with primitives
--- Struct that contains another struct
--- Struct that contains custom type with Stringer pointer interface via both
--  exported and unexported fields
--- Struct that contains embedded struct and field to same struct
--- Uintptr to 0 (null pointer)
--- Uintptr address of real variable
--- Unsafe.Pointer to 0 (null pointer)
--- Unsafe.Pointer to address of real variable
--- Nil channel
--- Standard int channel
--- Function with no params and no returns
--- Function with param and no returns
--- Function with multiple params and multiple returns
--- Struct that is circular through self referencing
--- Structs that are circular through cross referencing
--- Structs that are indirectly circular
--- Type that panics in its Stringer interface
--*/
--
--package spew_test
+@@ -1,42 +0,0 @@
+-package etcd
 -
 -import (
--	"bytes"
 -	"fmt"
--	"github.com/davecgh/go-spew/spew"
 -	"testing"
--	"unsafe"
 -)
 -
--// dumpTest is used to describe a test to be perfomed against the Dump method.
--type dumpTest struct {
--	in    interface{}
--	wants []string
--}
+-func TestSetCurlChan(t *testing.T) {
+-	c := NewClient(nil)
+-	c.OpenCURL()
 -
--// dumpTests houses all of the tests to be performed against the Dump method.
--var dumpTests = make([]dumpTest, 0)
+-	defer func() {
+-		c.Delete("foo", true)
+-	}()
 -
--// addDumpTest is a helper method to append the passed input and desired result
--// to dumpTests
--func addDumpTest(in interface{}, wants ...string) {
--	test := dumpTest{in, wants}
--	dumpTests = append(dumpTests, test)
--}
+-	_, err := c.Set("foo", "bar", 5)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
 -
--func addIntDumpTests() {
--	// Max int8.
--	v := int8(127)
--	nv := (*int8)(nil)
--	pv := &v
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "int8"
--	vs := "127"
--	addDumpTest(v, "("+vt+") "+vs+"\n")
--	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
--	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
--	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
+-	expected := fmt.Sprintf("curl -X PUT %s/v2/keys/foo -d value=bar -d ttl=5",
+-		c.cluster.Leader)
+-	actual := c.RecvCURL()
+-	if expected != actual {
+-		t.Fatalf(`Command "%s" is not equal to expected value "%s"`,
+-			actual, expected)
+-	}
 -
--	// Max int16.
--	v2 := int16(32767)
--	nv2 := (*int16)(nil)
--	pv2 := &v2
--	v2Addr := fmt.Sprintf("%p", pv2)
--	pv2Addr := fmt.Sprintf("%p", &pv2)
--	v2t := "int16"
--	v2s := "32767"
--	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
--	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
--	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
--	addDumpTest(nv2, "(*"+v2t+")(<nil>)\n")
+-	c.SetConsistency(STRONG_CONSISTENCY)
+-	_, err = c.Get("foo", false, false)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
 -
--	// Max int32.
--	v3 := int32(2147483647)
--	nv3 := (*int32)(nil)
--	pv3 := &v3
--	v3Addr := fmt.Sprintf("%p", pv3)
--	pv3Addr := fmt.Sprintf("%p", &pv3)
--	v3t := "int32"
--	v3s := "2147483647"
--	addDumpTest(v3, "("+v3t+") "+v3s+"\n")
--	addDumpTest(pv3, "(*"+v3t+")("+v3Addr+")("+v3s+")\n")
--	addDumpTest(&pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")("+v3s+")\n")
--	addDumpTest(nv3, "(*"+v3t+")(<nil>)\n")
+-	expected = fmt.Sprintf("curl -X GET %s/v2/keys/foo?consistent=true&recursive=false&sorted=false",
+-		c.cluster.Leader)
+-	actual = c.RecvCURL()
+-	if expected != actual {
+-		t.Fatalf(`Command "%s" is not equal to expected value "%s"`,
+-			actual, expected)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/set_update_create.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/set_update_create.go
+deleted file mode 100644
+index cb0d567..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/set_update_create.go
++++ /dev/null
+@@ -1,137 +0,0 @@
+-package etcd
 -
--	// Max int64.
--	v4 := int64(9223372036854775807)
--	nv4 := (*int64)(nil)
--	pv4 := &v4
--	v4Addr := fmt.Sprintf("%p", pv4)
--	pv4Addr := fmt.Sprintf("%p", &pv4)
--	v4t := "int64"
--	v4s := "9223372036854775807"
--	addDumpTest(v4, "("+v4t+") "+v4s+"\n")
--	addDumpTest(pv4, "(*"+v4t+")("+v4Addr+")("+v4s+")\n")
--	addDumpTest(&pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")("+v4s+")\n")
--	addDumpTest(nv4, "(*"+v4t+")(<nil>)\n")
+-// Set sets the given key to the given value.
+-// It will create a new key value pair or replace the old one.
+-// It will not replace a existing directory.
+-func (c *Client) Set(key string, value string, ttl uint64) (*Response, error) {
+-	raw, err := c.RawSet(key, value, ttl)
 -
--	// Max int.
--	v5 := int(2147483647)
--	nv5 := (*int)(nil)
--	pv5 := &v5
--	v5Addr := fmt.Sprintf("%p", pv5)
--	pv5Addr := fmt.Sprintf("%p", &pv5)
--	v5t := "int"
--	v5s := "2147483647"
--	addDumpTest(v5, "("+v5t+") "+v5s+"\n")
--	addDumpTest(pv5, "(*"+v5t+")("+v5Addr+")("+v5s+")\n")
--	addDumpTest(&pv5, "(**"+v5t+")("+pv5Addr+"->"+v5Addr+")("+v5s+")\n")
--	addDumpTest(nv5, "(*"+v5t+")(<nil>)\n")
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	return raw.Unmarshal()
 -}
 -
--func addUintDumpTests() {
--	// Max uint8.
--	v := uint8(255)
--	nv := (*uint8)(nil)
--	pv := &v
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "uint8"
--	vs := "255"
--	addDumpTest(v, "("+vt+") "+vs+"\n")
--	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
--	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
--	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
+-// Set sets the given key to a directory.
+-// It will create a new directory or replace the old key value pair by a directory.
+-// It will not replace a existing directory.
+-func (c *Client) SetDir(key string, ttl uint64) (*Response, error) {
+-	raw, err := c.RawSetDir(key, ttl)
 -
--	// Max uint16.
--	v2 := uint16(65535)
--	nv2 := (*uint16)(nil)
--	pv2 := &v2
--	v2Addr := fmt.Sprintf("%p", pv2)
--	pv2Addr := fmt.Sprintf("%p", &pv2)
--	v2t := "uint16"
--	v2s := "65535"
--	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
--	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
--	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
--	addDumpTest(nv2, "(*"+v2t+")(<nil>)\n")
+-	if err != nil {
+-		return nil, err
+-	}
 -
--	// Max uint32.
--	v3 := uint32(4294967295)
--	nv3 := (*uint32)(nil)
--	pv3 := &v3
--	v3Addr := fmt.Sprintf("%p", pv3)
--	pv3Addr := fmt.Sprintf("%p", &pv3)
--	v3t := "uint32"
--	v3s := "4294967295"
--	addDumpTest(v3, "("+v3t+") "+v3s+"\n")
--	addDumpTest(pv3, "(*"+v3t+")("+v3Addr+")("+v3s+")\n")
--	addDumpTest(&pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")("+v3s+")\n")
--	addDumpTest(nv3, "(*"+v3t+")(<nil>)\n")
+-	return raw.Unmarshal()
+-}
 -
--	// Max uint64.
--	v4 := uint64(18446744073709551615)
--	nv4 := (*uint64)(nil)
--	pv4 := &v4
--	v4Addr := fmt.Sprintf("%p", pv4)
--	pv4Addr := fmt.Sprintf("%p", &pv4)
--	v4t := "uint64"
--	v4s := "18446744073709551615"
--	addDumpTest(v4, "("+v4t+") "+v4s+"\n")
--	addDumpTest(pv4, "(*"+v4t+")("+v4Addr+")("+v4s+")\n")
--	addDumpTest(&pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")("+v4s+")\n")
--	addDumpTest(nv4, "(*"+v4t+")(<nil>)\n")
+-// CreateDir creates a directory. It succeeds only if
+-// the given key does not yet exist.
+-func (c *Client) CreateDir(key string, ttl uint64) (*Response, error) {
+-	raw, err := c.RawCreateDir(key, ttl)
 -
--	// Max uint.
--	v5 := uint(4294967295)
--	nv5 := (*uint)(nil)
--	pv5 := &v5
--	v5Addr := fmt.Sprintf("%p", pv5)
--	pv5Addr := fmt.Sprintf("%p", &pv5)
--	v5t := "uint"
--	v5s := "4294967295"
--	addDumpTest(v5, "("+v5t+") "+v5s+"\n")
--	addDumpTest(pv5, "(*"+v5t+")("+v5Addr+")("+v5s+")\n")
--	addDumpTest(&pv5, "(**"+v5t+")("+pv5Addr+"->"+v5Addr+")("+v5s+")\n")
--	addDumpTest(nv5, "(*"+v5t+")(<nil>)\n")
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	return raw.Unmarshal()
 -}
 -
--func addBoolDumpTests() {
--	// Boolean true.
--	v := bool(true)
--	nv := (*bool)(nil)
--	pv := &v
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "bool"
--	vs := "true"
--	addDumpTest(v, "("+vt+") "+vs+"\n")
--	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
--	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
--	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
+-// UpdateDir updates the given directory. It succeeds only if the
+-// given key already exists.
+-func (c *Client) UpdateDir(key string, ttl uint64) (*Response, error) {
+-	raw, err := c.RawUpdateDir(key, ttl)
 -
--	// Boolean false.
--	v2 := bool(false)
--	pv2 := &v2
--	v2Addr := fmt.Sprintf("%p", pv2)
--	pv2Addr := fmt.Sprintf("%p", &pv2)
--	v2t := "bool"
--	v2s := "false"
--	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
--	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
--	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	return raw.Unmarshal()
 -}
 -
--func addFloatDumpTests() {
--	// Standard float32.
--	v := float32(3.1415)
--	nv := (*float32)(nil)
--	pv := &v
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "float32"
--	vs := "3.1415"
--	addDumpTest(v, "("+vt+") "+vs+"\n")
--	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
--	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
--	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
+-// Create creates a file with the given value under the given key.  It succeeds
+-// only if the given key does not yet exist.
+-func (c *Client) Create(key string, value string, ttl uint64) (*Response, error) {
+-	raw, err := c.RawCreate(key, value, ttl)
 -
--	// Standard float64.
--	v2 := float64(3.1415926)
--	nv2 := (*float64)(nil)
--	pv2 := &v2
--	v2Addr := fmt.Sprintf("%p", pv2)
--	pv2Addr := fmt.Sprintf("%p", &pv2)
--	v2t := "float64"
--	v2s := "3.1415926"
--	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
--	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
--	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
--	addDumpTest(nv2, "(*"+v2t+")(<nil>)\n")
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	return raw.Unmarshal()
 -}
 -
--func addComplexDumpTests() {
--	// Standard complex64.
--	v := complex(float32(6), -2)
--	nv := (*complex64)(nil)
--	pv := &v
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "complex64"
--	vs := "(6-2i)"
--	addDumpTest(v, "("+vt+") "+vs+"\n")
--	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
--	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
--	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
+-// CreateInOrder creates a file with a key that's guaranteed to be higher than other
+-// keys in the given directory. It is useful for creating queues.
+-func (c *Client) CreateInOrder(dir string, value string, ttl uint64) (*Response, error) {
+-	raw, err := c.RawCreateInOrder(dir, value, ttl)
 -
--	// Standard complex128.
--	v2 := complex(float64(-6), 2)
--	nv2 := (*complex128)(nil)
--	pv2 := &v2
--	v2Addr := fmt.Sprintf("%p", pv2)
--	pv2Addr := fmt.Sprintf("%p", &pv2)
--	v2t := "complex128"
--	v2s := "(-6+2i)"
--	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
--	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
--	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
--	addDumpTest(nv2, "(*"+v2t+")(<nil>)\n")
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	return raw.Unmarshal()
 -}
 -
--func addArrayDumpTests() {
--	// Array containing standard ints.
--	v := [3]int{1, 2, 3}
--	vLen := fmt.Sprintf("%d", len(v))
--	vCap := fmt.Sprintf("%d", cap(v))
--	nv := (*[3]int)(nil)
--	pv := &v
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "int"
--	vs := "(len=" + vLen + " cap=" + vCap + ") {\n (" + vt + ") 1,\n (" +
--		vt + ") 2,\n (" + vt + ") 3\n}"
--	addDumpTest(v, "([3]"+vt+") "+vs+"\n")
--	addDumpTest(pv, "(*[3]"+vt+")("+vAddr+")("+vs+")\n")
--	addDumpTest(&pv, "(**[3]"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
--	addDumpTest(nv, "(*[3]"+vt+")(<nil>)\n")
+-// Update updates the given key to the given value.  It succeeds only if the
+-// given key already exists.
+-func (c *Client) Update(key string, value string, ttl uint64) (*Response, error) {
+-	raw, err := c.RawUpdate(key, value, ttl)
 -
--	// Array containing type with custom formatter on pointer receiver only.
--	v2i0 := pstringer("1")
--	v2i1 := pstringer("2")
--	v2i2 := pstringer("3")
--	v2 := [3]pstringer{v2i0, v2i1, v2i2}
--	v2i0Len := fmt.Sprintf("%d", len(v2i0))
--	v2i1Len := fmt.Sprintf("%d", len(v2i1))
--	v2i2Len := fmt.Sprintf("%d", len(v2i2))
--	v2Len := fmt.Sprintf("%d", len(v2))
--	v2Cap := fmt.Sprintf("%d", cap(v2))
--	nv2 := (*[3]pstringer)(nil)
--	pv2 := &v2
--	v2Addr := fmt.Sprintf("%p", pv2)
--	pv2Addr := fmt.Sprintf("%p", &pv2)
--	v2t := "spew_test.pstringer"
--	v2s := "(len=" + v2Len + " cap=" + v2Cap + ") {\n (" + v2t + ") (len=" +
--		v2i0Len + ") stringer 1,\n (" + v2t + ") (len=" + v2i1Len +
--		") stringer 2,\n (" + v2t + ") (len=" + v2i2Len + ") " +
--		"stringer 3\n}"
--	addDumpTest(v2, "([3]"+v2t+") "+v2s+"\n")
--	addDumpTest(pv2, "(*[3]"+v2t+")("+v2Addr+")("+v2s+")\n")
--	addDumpTest(&pv2, "(**[3]"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
--	addDumpTest(nv2, "(*[3]"+v2t+")(<nil>)\n")
+-	if err != nil {
+-		return nil, err
+-	}
 -
--	// Array containing interfaces.
--	v3i0 := "one"
--	v3 := [3]interface{}{v3i0, int(2), uint(3)}
--	v3i0Len := fmt.Sprintf("%d", len(v3i0))
--	v3Len := fmt.Sprintf("%d", len(v3))
--	v3Cap := fmt.Sprintf("%d", cap(v3))
--	nv3 := (*[3]interface{})(nil)
--	pv3 := &v3
--	v3Addr := fmt.Sprintf("%p", pv3)
--	pv3Addr := fmt.Sprintf("%p", &pv3)
--	v3t := "[3]interface {}"
--	v3t2 := "string"
--	v3t3 := "int"
--	v3t4 := "uint"
--	v3s := "(len=" + v3Len + " cap=" + v3Cap + ") {\n (" + v3t2 + ") " +
--		"(len=" + v3i0Len + ") \"one\",\n (" + v3t3 + ") 2,\n (" +
--		v3t4 + ") 3\n}"
--	addDumpTest(v3, "("+v3t+") "+v3s+"\n")
--	addDumpTest(pv3, "(*"+v3t+")("+v3Addr+")("+v3s+")\n")
--	addDumpTest(&pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")("+v3s+")\n")
--	addDumpTest(nv3, "(*"+v3t+")(<nil>)\n")
+-	return raw.Unmarshal()
+-}
 -
--	// Array containing bytes.
--	v4 := [34]byte{
--		0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18,
--		0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 0x20,
--		0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28,
--		0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, 0x30,
--		0x31, 0x32,
+-func (c *Client) RawUpdateDir(key string, ttl uint64) (*RawResponse, error) {
+-	ops := Options{
+-		"prevExist": true,
+-		"dir":       true,
 -	}
--	v4Len := fmt.Sprintf("%d", len(v4))
--	v4Cap := fmt.Sprintf("%d", cap(v4))
--	nv4 := (*[34]byte)(nil)
--	pv4 := &v4
--	v4Addr := fmt.Sprintf("%p", pv4)
--	pv4Addr := fmt.Sprintf("%p", &pv4)
--	v4t := "[34]uint8"
--	v4s := "(len=" + v4Len + " cap=" + v4Cap + ") " +
--		"{\n 00000000  11 12 13 14 15 16 17 18  19 1a 1b 1c 1d 1e 1f 20" +
--		"  |............... |\n" +
--		" 00000010  21 22 23 24 25 26 27 28  29 2a 2b 2c 2d 2e 2f 30" +
--		"  |!\"#$%&'()*+,-./0|\n" +
--		" 00000020  31 32                                           " +
--		"  |12|\n}"
--	addDumpTest(v4, "("+v4t+") "+v4s+"\n")
--	addDumpTest(pv4, "(*"+v4t+")("+v4Addr+")("+v4s+")\n")
--	addDumpTest(&pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")("+v4s+")\n")
--	addDumpTest(nv4, "(*"+v4t+")(<nil>)\n")
+-
+-	return c.put(key, "", ttl, ops)
 -}
 -
--func addSliceDumpTests() {
--	// Slice containing standard float32 values.
--	v := []float32{3.14, 6.28, 12.56}
--	vLen := fmt.Sprintf("%d", len(v))
--	vCap := fmt.Sprintf("%d", cap(v))
--	nv := (*[]float32)(nil)
--	pv := &v
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "float32"
--	vs := "(len=" + vLen + " cap=" + vCap + ") {\n (" + vt + ") 3.14,\n (" +
--		vt + ") 6.28,\n (" + vt + ") 12.56\n}"
--	addDumpTest(v, "([]"+vt+") "+vs+"\n")
--	addDumpTest(pv, "(*[]"+vt+")("+vAddr+")("+vs+")\n")
--	addDumpTest(&pv, "(**[]"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
--	addDumpTest(nv, "(*[]"+vt+")(<nil>)\n")
+-func (c *Client) RawCreateDir(key string, ttl uint64) (*RawResponse, error) {
+-	ops := Options{
+-		"prevExist": false,
+-		"dir":       true,
+-	}
 -
--	// Slice containing type with custom formatter on pointer receiver only.
--	v2i0 := pstringer("1")
--	v2i1 := pstringer("2")
--	v2i2 := pstringer("3")
--	v2 := []pstringer{v2i0, v2i1, v2i2}
--	v2i0Len := fmt.Sprintf("%d", len(v2i0))
--	v2i1Len := fmt.Sprintf("%d", len(v2i1))
--	v2i2Len := fmt.Sprintf("%d", len(v2i2))
--	v2Len := fmt.Sprintf("%d", len(v2))
--	v2Cap := fmt.Sprintf("%d", cap(v2))
--	nv2 := (*[]pstringer)(nil)
--	pv2 := &v2
--	v2Addr := fmt.Sprintf("%p", pv2)
--	pv2Addr := fmt.Sprintf("%p", &pv2)
--	v2t := "spew_test.pstringer"
--	v2s := "(len=" + v2Len + " cap=" + v2Cap + ") {\n (" + v2t + ") (len=" +
--		v2i0Len + ") stringer 1,\n (" + v2t + ") (len=" + v2i1Len +
--		") stringer 2,\n (" + v2t + ") (len=" + v2i2Len + ") " +
--		"stringer 3\n}"
--	addDumpTest(v2, "([]"+v2t+") "+v2s+"\n")
--	addDumpTest(pv2, "(*[]"+v2t+")("+v2Addr+")("+v2s+")\n")
--	addDumpTest(&pv2, "(**[]"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
--	addDumpTest(nv2, "(*[]"+v2t+")(<nil>)\n")
+-	return c.put(key, "", ttl, ops)
+-}
 -
--	// Slice containing interfaces.
--	v3i0 := "one"
--	v3 := []interface{}{v3i0, int(2), uint(3), nil}
--	v3i0Len := fmt.Sprintf("%d", len(v3i0))
--	v3Len := fmt.Sprintf("%d", len(v3))
--	v3Cap := fmt.Sprintf("%d", cap(v3))
--	nv3 := (*[]interface{})(nil)
--	pv3 := &v3
--	v3Addr := fmt.Sprintf("%p", pv3)
--	pv3Addr := fmt.Sprintf("%p", &pv3)
--	v3t := "[]interface {}"
--	v3t2 := "string"
--	v3t3 := "int"
--	v3t4 := "uint"
--	v3t5 := "interface {}"
--	v3s := "(len=" + v3Len + " cap=" + v3Cap + ") {\n (" + v3t2 + ") " +
--		"(len=" + v3i0Len + ") \"one\",\n (" + v3t3 + ") 2,\n (" +
--		v3t4 + ") 3,\n (" + v3t5 + ") <nil>\n}"
--	addDumpTest(v3, "("+v3t+") "+v3s+"\n")
--	addDumpTest(pv3, "(*"+v3t+")("+v3Addr+")("+v3s+")\n")
--	addDumpTest(&pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")("+v3s+")\n")
--	addDumpTest(nv3, "(*"+v3t+")(<nil>)\n")
+-func (c *Client) RawSet(key string, value string, ttl uint64) (*RawResponse, error) {
+-	return c.put(key, value, ttl, nil)
+-}
 -
--	// Slice containing bytes.
--	v4 := []byte{
--		0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18,
--		0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 0x20,
--		0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28,
--		0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, 0x30,
--		0x31, 0x32,
+-func (c *Client) RawSetDir(key string, ttl uint64) (*RawResponse, error) {
+-	ops := Options{
+-		"dir": true,
 -	}
--	v4Len := fmt.Sprintf("%d", len(v4))
--	v4Cap := fmt.Sprintf("%d", cap(v4))
--	nv4 := (*[]byte)(nil)
--	pv4 := &v4
--	v4Addr := fmt.Sprintf("%p", pv4)
--	pv4Addr := fmt.Sprintf("%p", &pv4)
--	v4t := "[]uint8"
--	v4s := "(len=" + v4Len + " cap=" + v4Cap + ") " +
--		"{\n 00000000  11 12 13 14 15 16 17 18  19 1a 1b 1c 1d 1e 1f 20" +
--		"  |............... |\n" +
--		" 00000010  21 22 23 24 25 26 27 28  29 2a 2b 2c 2d 2e 2f 30" +
--		"  |!\"#$%&'()*+,-./0|\n" +
--		" 00000020  31 32                                           " +
--		"  |12|\n}"
--	addDumpTest(v4, "("+v4t+") "+v4s+"\n")
--	addDumpTest(pv4, "(*"+v4t+")("+v4Addr+")("+v4s+")\n")
--	addDumpTest(&pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")("+v4s+")\n")
--	addDumpTest(nv4, "(*"+v4t+")(<nil>)\n")
 -
--	// Nil slice.
--	v5 := []int(nil)
--	nv5 := (*[]int)(nil)
--	pv5 := &v5
--	v5Addr := fmt.Sprintf("%p", pv5)
--	pv5Addr := fmt.Sprintf("%p", &pv5)
--	v5t := "[]int"
--	v5s := "<nil>"
--	addDumpTest(v5, "("+v5t+") "+v5s+"\n")
--	addDumpTest(pv5, "(*"+v5t+")("+v5Addr+")("+v5s+")\n")
--	addDumpTest(&pv5, "(**"+v5t+")("+pv5Addr+"->"+v5Addr+")("+v5s+")\n")
--	addDumpTest(nv5, "(*"+v5t+")(<nil>)\n")
+-	return c.put(key, "", ttl, ops)
 -}
 -
--func addStringDumpTests() {
--	// Standard string.
--	v := "test"
--	vLen := fmt.Sprintf("%d", len(v))
--	nv := (*string)(nil)
--	pv := &v
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "string"
--	vs := "(len=" + vLen + ") \"test\""
--	addDumpTest(v, "("+vt+") "+vs+"\n")
--	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
--	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
--	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
+-func (c *Client) RawUpdate(key string, value string, ttl uint64) (*RawResponse, error) {
+-	ops := Options{
+-		"prevExist": true,
+-	}
+-
+-	return c.put(key, value, ttl, ops)
 -}
 -
--func addInterfaceDumpTests() {
--	// Nil interface.
--	var v interface{}
--	nv := (*interface{})(nil)
--	pv := &v
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "interface {}"
--	vs := "<nil>"
--	addDumpTest(v, "("+vt+") "+vs+"\n")
--	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
--	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
--	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
+-func (c *Client) RawCreate(key string, value string, ttl uint64) (*RawResponse, error) {
+-	ops := Options{
+-		"prevExist": false,
+-	}
 -
--	// Sub-interface.
--	v2 := interface{}(uint16(65535))
--	pv2 := &v2
--	v2Addr := fmt.Sprintf("%p", pv2)
--	pv2Addr := fmt.Sprintf("%p", &pv2)
--	v2t := "uint16"
--	v2s := "65535"
--	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
--	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
--	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
+-	return c.put(key, value, ttl, ops)
 -}
 -
--func addMapDumpTests() {
--	// Map with string keys and int vals.
--	k := "one"
--	kk := "two"
--	m := map[string]int{k: 1, kk: 2}
--	klen := fmt.Sprintf("%d", len(k)) // not kLen to shut golint up
--	kkLen := fmt.Sprintf("%d", len(kk))
--	mLen := fmt.Sprintf("%d", len(m))
--	nm := (*map[string]int)(nil)
--	pm := &m
--	mAddr := fmt.Sprintf("%p", pm)
--	pmAddr := fmt.Sprintf("%p", &pm)
--	mt := "map[string]int"
--	mt1 := "string"
--	mt2 := "int"
--	ms := "(len=" + mLen + ") {\n (" + mt1 + ") (len=" + klen + ") " +
--		"\"one\": (" + mt2 + ") 1,\n (" + mt1 + ") (len=" + kkLen +
--		") \"two\": (" + mt2 + ") 2\n}"
--	ms2 := "(len=" + mLen + ") {\n (" + mt1 + ") (len=" + kkLen + ") " +
--		"\"two\": (" + mt2 + ") 2,\n (" + mt1 + ") (len=" + klen +
--		") \"one\": (" + mt2 + ") 1\n}"
--	addDumpTest(m, "("+mt+") "+ms+"\n", "("+mt+") "+ms2+"\n")
--	addDumpTest(pm, "(*"+mt+")("+mAddr+")("+ms+")\n",
--		"(*"+mt+")("+mAddr+")("+ms2+")\n")
--	addDumpTest(&pm, "(**"+mt+")("+pmAddr+"->"+mAddr+")("+ms+")\n",
--		"(**"+mt+")("+pmAddr+"->"+mAddr+")("+ms2+")\n")
--	addDumpTest(nm, "(*"+mt+")(<nil>)\n")
--
--	// Map with custom formatter type on pointer receiver only keys and vals.
--	k2 := pstringer("one")
--	v2 := pstringer("1")
--	m2 := map[pstringer]pstringer{k2: v2}
--	k2Len := fmt.Sprintf("%d", len(k2))
--	v2Len := fmt.Sprintf("%d", len(v2))
--	m2Len := fmt.Sprintf("%d", len(m2))
--	nm2 := (*map[pstringer]pstringer)(nil)
--	pm2 := &m2
--	m2Addr := fmt.Sprintf("%p", pm2)
--	pm2Addr := fmt.Sprintf("%p", &pm2)
--	m2t := "map[spew_test.pstringer]spew_test.pstringer"
--	m2t1 := "spew_test.pstringer"
--	m2t2 := "spew_test.pstringer"
--	m2s := "(len=" + m2Len + ") {\n (" + m2t1 + ") (len=" + k2Len + ") " +
--		"stringer one: (" + m2t2 + ") (len=" + v2Len + ") stringer 1\n}"
--	addDumpTest(m2, "("+m2t+") "+m2s+"\n")
--	addDumpTest(pm2, "(*"+m2t+")("+m2Addr+")("+m2s+")\n")
--	addDumpTest(&pm2, "(**"+m2t+")("+pm2Addr+"->"+m2Addr+")("+m2s+")\n")
--	addDumpTest(nm2, "(*"+m2t+")(<nil>)\n")
+-func (c *Client) RawCreateInOrder(dir string, value string, ttl uint64) (*RawResponse, error) {
+-	return c.post(dir, value, ttl)
+-}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/set_update_create_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/set_update_create_test.go
+deleted file mode 100644
+index ced0f06..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/set_update_create_test.go
++++ /dev/null
+@@ -1,241 +0,0 @@
+-package etcd
 -
--	// Map with interface keys and values.
--	k3 := "one"
--	k3Len := fmt.Sprintf("%d", len(k3))
--	m3 := map[interface{}]interface{}{k3: 1}
--	m3Len := fmt.Sprintf("%d", len(m3))
--	nm3 := (*map[interface{}]interface{})(nil)
--	pm3 := &m3
--	m3Addr := fmt.Sprintf("%p", pm3)
--	pm3Addr := fmt.Sprintf("%p", &pm3)
--	m3t := "map[interface {}]interface {}"
--	m3t1 := "string"
--	m3t2 := "int"
--	m3s := "(len=" + m3Len + ") {\n (" + m3t1 + ") (len=" + k3Len + ") " +
--		"\"one\": (" + m3t2 + ") 1\n}"
--	addDumpTest(m3, "("+m3t+") "+m3s+"\n")
--	addDumpTest(pm3, "(*"+m3t+")("+m3Addr+")("+m3s+")\n")
--	addDumpTest(&pm3, "(**"+m3t+")("+pm3Addr+"->"+m3Addr+")("+m3s+")\n")
--	addDumpTest(nm3, "(*"+m3t+")(<nil>)\n")
+-import (
+-	"testing"
+-)
 -
--	// Map with nil interface value.
--	k4 := "nil"
--	k4Len := fmt.Sprintf("%d", len(k4))
--	m4 := map[string]interface{}{k4: nil}
--	m4Len := fmt.Sprintf("%d", len(m4))
--	nm4 := (*map[string]interface{})(nil)
--	pm4 := &m4
--	m4Addr := fmt.Sprintf("%p", pm4)
--	pm4Addr := fmt.Sprintf("%p", &pm4)
--	m4t := "map[string]interface {}"
--	m4t1 := "string"
--	m4t2 := "interface {}"
--	m4s := "(len=" + m4Len + ") {\n (" + m4t1 + ") (len=" + k4Len + ")" +
--		" \"nil\": (" + m4t2 + ") <nil>\n}"
--	addDumpTest(m4, "("+m4t+") "+m4s+"\n")
--	addDumpTest(pm4, "(*"+m4t+")("+m4Addr+")("+m4s+")\n")
--	addDumpTest(&pm4, "(**"+m4t+")("+pm4Addr+"->"+m4Addr+")("+m4s+")\n")
--	addDumpTest(nm4, "(*"+m4t+")(<nil>)\n")
--}
+-func TestSet(t *testing.T) {
+-	c := NewClient(nil)
+-	defer func() {
+-		c.Delete("foo", true)
+-	}()
 -
--func addStructDumpTests() {
--	// Struct with primitives.
--	type s1 struct {
--		a int8
--		b uint8
+-	resp, err := c.Set("foo", "bar", 5)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if resp.Node.Key != "/foo" || resp.Node.Value != "bar" || resp.Node.TTL != 5 {
+-		t.Fatalf("Set 1 failed: %#v", resp)
+-	}
+-	if resp.PrevNode != nil {
+-		t.Fatalf("Set 1 PrevNode failed: %#v", resp)
 -	}
--	v := s1{127, 255}
--	nv := (*s1)(nil)
--	pv := &v
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "spew_test.s1"
--	vt2 := "int8"
--	vt3 := "uint8"
--	vs := "{\n a: (" + vt2 + ") 127,\n b: (" + vt3 + ") 255\n}"
--	addDumpTest(v, "("+vt+") "+vs+"\n")
--	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
--	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
--	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
 -
--	// Struct that contains another struct.
--	type s2 struct {
--		s1 s1
--		b  bool
+-	resp, err = c.Set("foo", "bar2", 5)
+-	if err != nil {
+-		t.Fatal(err)
 -	}
--	v2 := s2{s1{127, 255}, true}
--	nv2 := (*s2)(nil)
--	pv2 := &v2
--	v2Addr := fmt.Sprintf("%p", pv2)
--	pv2Addr := fmt.Sprintf("%p", &pv2)
--	v2t := "spew_test.s2"
--	v2t2 := "spew_test.s1"
--	v2t3 := "int8"
--	v2t4 := "uint8"
--	v2t5 := "bool"
--	v2s := "{\n s1: (" + v2t2 + ") {\n  a: (" + v2t3 + ") 127,\n  b: (" +
--		v2t4 + ") 255\n },\n b: (" + v2t5 + ") true\n}"
--	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
--	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
--	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
--	addDumpTest(nv2, "(*"+v2t+")(<nil>)\n")
+-	if !(resp.Node.Key == "/foo" && resp.Node.Value == "bar2" && resp.Node.TTL == 5) {
+-		t.Fatalf("Set 2 failed: %#v", resp)
+-	}
+-	if resp.PrevNode.Key != "/foo" || resp.PrevNode.Value != "bar" || resp.Node.TTL != 5 {
+-		t.Fatalf("Set 2 PrevNode failed: %#v", resp)
+-	}
+-}
 -
--	// Struct that contains custom type with Stringer pointer interface via both
--	// exported and unexported fields.
--	type s3 struct {
--		s pstringer
--		S pstringer
+-func TestUpdate(t *testing.T) {
+-	c := NewClient(nil)
+-	defer func() {
+-		c.Delete("foo", true)
+-		c.Delete("nonexistent", true)
+-	}()
+-
+-	resp, err := c.Set("foo", "bar", 5)
+-
+-	if err != nil {
+-		t.Fatal(err)
 -	}
--	v3 := s3{"test", "test2"}
--	nv3 := (*s3)(nil)
--	pv3 := &v3
--	v3Addr := fmt.Sprintf("%p", pv3)
--	pv3Addr := fmt.Sprintf("%p", &pv3)
--	v3t := "spew_test.s3"
--	v3t2 := "spew_test.pstringer"
--	v3s := "{\n s: (" + v3t2 + ") (len=4) stringer test,\n S: (" + v3t2 +
--		") (len=5) stringer test2\n}"
--	addDumpTest(v3, "("+v3t+") "+v3s+"\n")
--	addDumpTest(pv3, "(*"+v3t+")("+v3Addr+")("+v3s+")\n")
--	addDumpTest(&pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")("+v3s+")\n")
--	addDumpTest(nv3, "(*"+v3t+")(<nil>)\n")
 -
--	// Struct that contains embedded struct and field to same struct.
--	e := embed{"embedstr"}
--	eLen := fmt.Sprintf("%d", len("embedstr"))
--	v4 := embedwrap{embed: &e, e: &e}
--	nv4 := (*embedwrap)(nil)
--	pv4 := &v4
--	eAddr := fmt.Sprintf("%p", &e)
--	v4Addr := fmt.Sprintf("%p", pv4)
--	pv4Addr := fmt.Sprintf("%p", &pv4)
--	v4t := "spew_test.embedwrap"
--	v4t2 := "spew_test.embed"
--	v4t3 := "string"
--	v4s := "{\n embed: (*" + v4t2 + ")(" + eAddr + ")({\n  a: (" + v4t3 +
--		") (len=" + eLen + ") \"embedstr\"\n }),\n e: (*" + v4t2 +
--		")(" + eAddr + ")({\n  a: (" + v4t3 + ") (len=" + eLen + ")" +
--		" \"embedstr\"\n })\n}"
--	addDumpTest(v4, "("+v4t+") "+v4s+"\n")
--	addDumpTest(pv4, "(*"+v4t+")("+v4Addr+")("+v4s+")\n")
--	addDumpTest(&pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")("+v4s+")\n")
--	addDumpTest(nv4, "(*"+v4t+")(<nil>)\n")
--}
+-	// This should succeed.
+-	resp, err = c.Update("foo", "wakawaka", 5)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
 -
--func addUintptrDumpTests() {
--	// Null pointer.
--	v := uintptr(0)
--	pv := &v
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "uintptr"
--	vs := "<nil>"
--	addDumpTest(v, "("+vt+") "+vs+"\n")
--	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
--	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
+-	if !(resp.Action == "update" && resp.Node.Key == "/foo" && resp.Node.TTL == 5) {
+-		t.Fatalf("Update 1 failed: %#v", resp)
+-	}
+-	if !(resp.PrevNode.Key == "/foo" && resp.PrevNode.Value == "bar" && resp.Node.TTL == 5) {
+-		t.Fatalf("Update 1 prevValue failed: %#v", resp)
+-	}
 -
--	// Address of real variable.
--	i := 1
--	v2 := uintptr(unsafe.Pointer(&i))
--	nv2 := (*uintptr)(nil)
--	pv2 := &v2
--	v2Addr := fmt.Sprintf("%p", pv2)
--	pv2Addr := fmt.Sprintf("%p", &pv2)
--	v2t := "uintptr"
--	v2s := fmt.Sprintf("%p", &i)
--	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
--	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
--	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
--	addDumpTest(nv2, "(*"+v2t+")(<nil>)\n")
+-	// This should fail because the key does not exist.
+-	resp, err = c.Update("nonexistent", "whatever", 5)
+-	if err == nil {
+-		t.Fatalf("The key %v did not exist, so the update should have failed."+
+-			"The response was: %#v", resp.Node.Key, resp)
+-	}
 -}
 -
--func addUnsafePointerDumpTests() {
--	// Null pointer.
--	v := unsafe.Pointer(uintptr(0))
--	nv := (*unsafe.Pointer)(nil)
--	pv := &v
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "unsafe.Pointer"
--	vs := "<nil>"
--	addDumpTest(v, "("+vt+") "+vs+"\n")
--	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
--	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
--	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
+-func TestCreate(t *testing.T) {
+-	c := NewClient(nil)
+-	defer func() {
+-		c.Delete("newKey", true)
+-	}()
 -
--	// Address of real variable.
--	i := 1
--	v2 := unsafe.Pointer(&i)
--	pv2 := &v2
--	v2Addr := fmt.Sprintf("%p", pv2)
--	pv2Addr := fmt.Sprintf("%p", &pv2)
--	v2t := "unsafe.Pointer"
--	v2s := fmt.Sprintf("%p", &i)
--	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
--	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
--	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
--	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
--}
+-	newKey := "/newKey"
+-	newValue := "/newValue"
 -
--func addChanDumpTests() {
--	// Nil channel.
--	var v chan int
--	pv := &v
--	nv := (*chan int)(nil)
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "chan int"
--	vs := "<nil>"
--	addDumpTest(v, "("+vt+") "+vs+"\n")
--	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
--	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
--	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
+-	// This should succeed
+-	resp, err := c.Create(newKey, newValue, 5)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
 -
--	// Real channel.
--	v2 := make(chan int)
--	pv2 := &v2
--	v2Addr := fmt.Sprintf("%p", pv2)
--	pv2Addr := fmt.Sprintf("%p", &pv2)
--	v2t := "chan int"
--	v2s := fmt.Sprintf("%p", v2)
--	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
--	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
--	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
+-	if !(resp.Action == "create" && resp.Node.Key == newKey &&
+-		resp.Node.Value == newValue && resp.Node.TTL == 5) {
+-		t.Fatalf("Create 1 failed: %#v", resp)
+-	}
+-	if resp.PrevNode != nil {
+-		t.Fatalf("Create 1 PrevNode failed: %#v", resp)
+-	}
+-
+-	// This should fail, because the key is already there
+-	resp, err = c.Create(newKey, newValue, 5)
+-	if err == nil {
+-		t.Fatalf("The key %v did exist, so the creation should have failed."+
+-			"The response was: %#v", resp.Node.Key, resp)
+-	}
 -}
 -
--func addFuncDumpTests() {
--	// Function with no params and no returns.
--	v := addIntDumpTests
--	nv := (*func())(nil)
--	pv := &v
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "func()"
--	vs := fmt.Sprintf("%p", v)
--	addDumpTest(v, "("+vt+") "+vs+"\n")
--	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
--	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
--	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
+-func TestCreateInOrder(t *testing.T) {
+-	c := NewClient(nil)
+-	dir := "/queue"
+-	defer func() {
+-		c.DeleteDir(dir)
+-	}()
 -
--	// Function with param and no returns.
--	v2 := TestDump
--	nv2 := (*func(*testing.T))(nil)
--	pv2 := &v2
--	v2Addr := fmt.Sprintf("%p", pv2)
--	pv2Addr := fmt.Sprintf("%p", &pv2)
--	v2t := "func(*testing.T)"
--	v2s := fmt.Sprintf("%p", v2)
--	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
--	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
--	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
--	addDumpTest(nv2, "(*"+v2t+")(<nil>)\n")
+-	var firstKey, secondKey string
 -
--	// Function with multiple params and multiple returns.
--	var v3 = func(i int, s string) (b bool, err error) {
--		return true, nil
+-	resp, err := c.CreateInOrder(dir, "1", 5)
+-	if err != nil {
+-		t.Fatal(err)
 -	}
--	nv3 := (*func(int, string) (bool, error))(nil)
--	pv3 := &v3
--	v3Addr := fmt.Sprintf("%p", pv3)
--	pv3Addr := fmt.Sprintf("%p", &pv3)
--	v3t := "func(int, string) (bool, error)"
--	v3s := fmt.Sprintf("%p", v3)
--	addDumpTest(v3, "("+v3t+") "+v3s+"\n")
--	addDumpTest(pv3, "(*"+v3t+")("+v3Addr+")("+v3s+")\n")
--	addDumpTest(&pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")("+v3s+")\n")
--	addDumpTest(nv3, "(*"+v3t+")(<nil>)\n")
--}
 -
--func addCircularDumpTests() {
--	// Struct that is circular through self referencing.
--	type circular struct {
--		c *circular
+-	if !(resp.Action == "create" && resp.Node.Value == "1" && resp.Node.TTL == 5) {
+-		t.Fatalf("Create 1 failed: %#v", resp)
 -	}
--	v := circular{nil}
--	v.c = &v
--	pv := &v
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "spew_test.circular"
--	vs := "{\n c: (*" + vt + ")(" + vAddr + ")({\n  c: (*" + vt + ")(" +
--		vAddr + ")(<already shown>)\n })\n}"
--	vs2 := "{\n c: (*" + vt + ")(" + vAddr + ")(<already shown>)\n}"
--	addDumpTest(v, "("+vt+") "+vs+"\n")
--	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs2+")\n")
--	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs2+")\n")
 -
--	// Structs that are circular through cross referencing.
--	v2 := xref1{nil}
--	ts2 := xref2{&v2}
--	v2.ps2 = &ts2
--	pv2 := &v2
--	ts2Addr := fmt.Sprintf("%p", &ts2)
--	v2Addr := fmt.Sprintf("%p", pv2)
--	pv2Addr := fmt.Sprintf("%p", &pv2)
--	v2t := "spew_test.xref1"
--	v2t2 := "spew_test.xref2"
--	v2s := "{\n ps2: (*" + v2t2 + ")(" + ts2Addr + ")({\n  ps1: (*" + v2t +
--		")(" + v2Addr + ")({\n   ps2: (*" + v2t2 + ")(" + ts2Addr +
--		")(<already shown>)\n  })\n })\n}"
--	v2s2 := "{\n ps2: (*" + v2t2 + ")(" + ts2Addr + ")({\n  ps1: (*" + v2t +
--		")(" + v2Addr + ")(<already shown>)\n })\n}"
--	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
--	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s2+")\n")
--	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s2+")\n")
+-	firstKey = resp.Node.Key
 -
--	// Structs that are indirectly circular.
--	v3 := indirCir1{nil}
--	tic2 := indirCir2{nil}
--	tic3 := indirCir3{&v3}
--	tic2.ps3 = &tic3
--	v3.ps2 = &tic2
--	pv3 := &v3
--	tic2Addr := fmt.Sprintf("%p", &tic2)
--	tic3Addr := fmt.Sprintf("%p", &tic3)
--	v3Addr := fmt.Sprintf("%p", pv3)
--	pv3Addr := fmt.Sprintf("%p", &pv3)
--	v3t := "spew_test.indirCir1"
--	v3t2 := "spew_test.indirCir2"
--	v3t3 := "spew_test.indirCir3"
--	v3s := "{\n ps2: (*" + v3t2 + ")(" + tic2Addr + ")({\n  ps3: (*" + v3t3 +
--		")(" + tic3Addr + ")({\n   ps1: (*" + v3t + ")(" + v3Addr +
--		")({\n    ps2: (*" + v3t2 + ")(" + tic2Addr +
--		")(<already shown>)\n   })\n  })\n })\n}"
--	v3s2 := "{\n ps2: (*" + v3t2 + ")(" + tic2Addr + ")({\n  ps3: (*" + v3t3 +
--		")(" + tic3Addr + ")({\n   ps1: (*" + v3t + ")(" + v3Addr +
--		")(<already shown>)\n  })\n })\n}"
--	addDumpTest(v3, "("+v3t+") "+v3s+"\n")
--	addDumpTest(pv3, "(*"+v3t+")("+v3Addr+")("+v3s2+")\n")
--	addDumpTest(&pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")("+v3s2+")\n")
--}
+-	resp, err = c.CreateInOrder(dir, "2", 5)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
 -
--func addPanicDumpTests() {
--	// Type that panics in its Stringer interface.
--	v := panicer(127)
--	nv := (*panicer)(nil)
--	pv := &v
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "spew_test.panicer"
--	vs := "(PANIC=test panic)127"
--	addDumpTest(v, "("+vt+") "+vs+"\n")
--	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
--	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
--	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
--}
+-	if !(resp.Action == "create" && resp.Node.Value == "2" && resp.Node.TTL == 5) {
+-		t.Fatalf("Create 2 failed: %#v", resp)
+-	}
 -
--func addErrorDumpTests() {
--	// Type that has a custom Error interface.
--	v := customError(127)
--	nv := (*customError)(nil)
--	pv := &v
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "spew_test.customError"
--	vs := "error: 127"
--	addDumpTest(v, "("+vt+") "+vs+"\n")
--	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
--	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
--	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
+-	secondKey = resp.Node.Key
+-
+-	if firstKey >= secondKey {
+-		t.Fatalf("Expected first key to be greater than second key, but %s is not greater than %s",
+-			firstKey, secondKey)
+-	}
 -}
 -
--// TestDump executes all of the tests described by dumpTests.
--func TestDump(t *testing.T) {
--	// Setup tests.
--	addIntDumpTests()
--	addUintDumpTests()
--	addBoolDumpTests()
--	addFloatDumpTests()
--	addComplexDumpTests()
--	addArrayDumpTests()
--	addSliceDumpTests()
--	addStringDumpTests()
--	addInterfaceDumpTests()
--	addMapDumpTests()
--	addStructDumpTests()
--	addUintptrDumpTests()
--	addUnsafePointerDumpTests()
--	addChanDumpTests()
--	addFuncDumpTests()
--	addCircularDumpTests()
--	addPanicDumpTests()
--	addErrorDumpTests()
--	addCgoDumpTests()
+-func TestSetDir(t *testing.T) {
+-	c := NewClient(nil)
+-	defer func() {
+-		c.Delete("foo", true)
+-		c.Delete("fooDir", true)
+-	}()
 -
--	t.Logf("Running %d tests", len(dumpTests))
--	for i, test := range dumpTests {
--		buf := new(bytes.Buffer)
--		spew.Fdump(buf, test.in)
--		s := buf.String()
--		if testFailed(s, test.wants) {
--			t.Errorf("Dump #%d\n got: %s %s", i, s, stringizeWants(test.wants))
--			continue
--		}
+-	resp, err := c.CreateDir("fooDir", 5)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !(resp.Node.Key == "/fooDir" && resp.Node.Value == "" && resp.Node.TTL == 5) {
+-		t.Fatalf("SetDir 1 failed: %#v", resp)
+-	}
+-	if resp.PrevNode != nil {
+-		t.Fatalf("SetDir 1 PrevNode failed: %#v", resp)
 -	}
--}
 -
--func TestDumpSortedKeys(t *testing.T) {
--	cfg := spew.ConfigState{SortKeys: true}
--	s := cfg.Sdump(map[int]string{1: "1", 3: "3", 2: "2"})
--	expected := `(map[int]string) (len=3) {
--(int) 1: (string) (len=1) "1",
--(int) 2: (string) (len=1) "2",
--(int) 3: (string) (len=1) "3"
--}
--`
--	if s != expected {
--		t.Errorf("Sorted keys mismatch:\n  %v %v", s, expected)
+-	// This should fail because /fooDir already points to a directory
+-	resp, err = c.CreateDir("/fooDir", 5)
+-	if err == nil {
+-		t.Fatalf("fooDir already points to a directory, so SetDir should have failed."+
+-			"The response was: %#v", resp)
+-	}
+-
+-	_, err = c.Set("foo", "bar", 5)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	// This should succeed
+-	// It should replace the key
+-	resp, err = c.SetDir("foo", 5)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !(resp.Node.Key == "/foo" && resp.Node.Value == "" && resp.Node.TTL == 5) {
+-		t.Fatalf("SetDir 2 failed: %#v", resp)
+-	}
+-	if !(resp.PrevNode.Key == "/foo" && resp.PrevNode.Value == "bar" && resp.PrevNode.TTL == 5) {
+-		t.Fatalf("SetDir 2 failed: %#v", resp)
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dumpcgo_test.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dumpcgo_test.go
-deleted file mode 100644
-index 9b8a358..0000000
---- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dumpcgo_test.go
-+++ /dev/null
-@@ -1,97 +0,0 @@
--// Copyright (c) 2013 Dave Collins <dave at davec.name>
--//
--// Permission to use, copy, modify, and distribute this software for any
--// purpose with or without fee is hereby granted, provided that the above
--// copyright notice and this permission notice appear in all copies.
--//
--// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
--// WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
--// MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
--// ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
--// WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
--// ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
--// OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
 -
--// NOTE: Due to the following build constraints, this file will only be compiled
--// when both cgo is supported and "-tags testcgo" is added to the go test
--// command line.  This means the cgo tests are only added (and hence run) when
--// specifially requested.  This configuration is used because spew itself
--// does not require cgo to run even though it does handle certain cgo types
--// specially.  Rather than forcing all clients to require cgo and an external
--// C compiler just to run the tests, this scheme makes them optional.
--// +build cgo,testcgo
+-func TestUpdateDir(t *testing.T) {
+-	c := NewClient(nil)
+-	defer func() {
+-		c.Delete("fooDir", true)
+-	}()
 -
--package spew_test
+-	resp, err := c.CreateDir("fooDir", 5)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
 -
--import (
--	"fmt"
--	"github.com/davecgh/go-spew/spew/testdata"
--)
+-	// This should succeed.
+-	resp, err = c.UpdateDir("fooDir", 5)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
 -
--func addCgoDumpTests() {
--	// C char pointer.
--	v := testdata.GetCgoCharPointer()
--	nv := testdata.GetCgoNullCharPointer()
--	pv := &v
--	vcAddr := fmt.Sprintf("%p", v)
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "*testdata._Ctype_char"
--	vs := "116"
--	addDumpTest(v, "("+vt+")("+vcAddr+")("+vs+")\n")
--	addDumpTest(pv, "(*"+vt+")("+vAddr+"->"+vcAddr+")("+vs+")\n")
--	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+"->"+vcAddr+")("+vs+")\n")
--	addDumpTest(nv, "("+vt+")(<nil>)\n")
+-	if !(resp.Action == "update" && resp.Node.Key == "/fooDir" &&
+-		resp.Node.Value == "" && resp.Node.TTL == 5) {
+-		t.Fatalf("UpdateDir 1 failed: %#v", resp)
+-	}
+-	if !(resp.PrevNode.Key == "/fooDir" && resp.PrevNode.Dir == true && resp.PrevNode.TTL == 5) {
+-		t.Fatalf("UpdateDir 1 PrevNode failed: %#v", resp)
+-	}
 -
--	// C char array.
--	v2, v2l, v2c := testdata.GetCgoCharArray()
--	v2Len := fmt.Sprintf("%d", v2l)
--	v2Cap := fmt.Sprintf("%d", v2c)
--	v2t := "[6]testdata._Ctype_char"
--	v2s := "(len=" + v2Len + " cap=" + v2Cap + ") " +
--		"{\n 00000000  74 65 73 74 32 00                               " +
--		"  |test2.|\n}"
--	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
+-	// This should fail because the key does not exist.
+-	resp, err = c.UpdateDir("nonexistentDir", 5)
+-	if err == nil {
+-		t.Fatalf("The key %v did not exist, so the update should have failed."+
+-			"The response was: %#v", resp.Node.Key, resp)
+-	}
+-}
 -
--	// C unsigned char array.
--	v3, v3l, v3c := testdata.GetCgoUnsignedCharArray()
--	v3Len := fmt.Sprintf("%d", v3l)
--	v3Cap := fmt.Sprintf("%d", v3c)
--	v3t := "[6]testdata._Ctype_unsignedchar"
--	v3s := "(len=" + v3Len + " cap=" + v3Cap + ") " +
--		"{\n 00000000  74 65 73 74 33 00                               " +
--		"  |test3.|\n}"
--	addDumpTest(v3, "("+v3t+") "+v3s+"\n")
+-func TestCreateDir(t *testing.T) {
+-	c := NewClient(nil)
+-	defer func() {
+-		c.Delete("fooDir", true)
+-	}()
 -
--	// C signed char array.
--	v4, v4l, v4c := testdata.GetCgoSignedCharArray()
--	v4Len := fmt.Sprintf("%d", v4l)
--	v4Cap := fmt.Sprintf("%d", v4c)
--	v4t := "[6]testdata._Ctype_schar"
--	v4t2 := "testdata._Ctype_schar"
--	v4s := "(len=" + v4Len + " cap=" + v4Cap + ") " +
--		"{\n (" + v4t2 + ") 116,\n (" + v4t2 + ") 101,\n (" + v4t2 +
--		") 115,\n (" + v4t2 + ") 116,\n (" + v4t2 + ") 52,\n (" + v4t2 +
--		") 0\n}"
--	addDumpTest(v4, "("+v4t+") "+v4s+"\n")
+-	// This should succeed
+-	resp, err := c.CreateDir("fooDir", 5)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
 -
--	// C uint8_t array.
--	v5, v5l, v5c := testdata.GetCgoUint8tArray()
--	v5Len := fmt.Sprintf("%d", v5l)
--	v5Cap := fmt.Sprintf("%d", v5c)
--	v5t := "[6]testdata._Ctype_uint8_t"
--	v5s := "(len=" + v5Len + " cap=" + v5Cap + ") " +
--		"{\n 00000000  74 65 73 74 35 00                               " +
--		"  |test5.|\n}"
--	addDumpTest(v5, "("+v5t+") "+v5s+"\n")
+-	if !(resp.Action == "create" && resp.Node.Key == "/fooDir" &&
+-		resp.Node.Value == "" && resp.Node.TTL == 5) {
+-		t.Fatalf("CreateDir 1 failed: %#v", resp)
+-	}
+-	if resp.PrevNode != nil {
+-		t.Fatalf("CreateDir 1 PrevNode failed: %#v", resp)
+-	}
 -
--	// C typedefed unsigned char array.
--	v6, v6l, v6c := testdata.GetCgoTypdefedUnsignedCharArray()
--	v6Len := fmt.Sprintf("%d", v6l)
--	v6Cap := fmt.Sprintf("%d", v6c)
--	v6t := "[6]testdata._Ctype_custom_uchar_t"
--	v6s := "(len=" + v6Len + " cap=" + v6Cap + ") " +
--		"{\n 00000000  74 65 73 74 36 00                               " +
--		"  |test6.|\n}"
--	addDumpTest(v6, "("+v6t+") "+v6s+"\n")
+-	// This should fail, because the key is already there
+-	resp, err = c.CreateDir("fooDir", 5)
+-	if err == nil {
+-		t.Fatalf("The key %v did exist, so the creation should have failed."+
+-			"The response was: %#v", resp.Node.Key, resp)
+-	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dumpnocgo_test.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dumpnocgo_test.go
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/version.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/version.go
 deleted file mode 100644
-index 52a0971..0000000
---- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dumpnocgo_test.go
+index b3d05df..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/version.go
 +++ /dev/null
-@@ -1,26 +0,0 @@
--// Copyright (c) 2013 Dave Collins <dave at davec.name>
--//
--// Permission to use, copy, modify, and distribute this software for any
--// purpose with or without fee is hereby granted, provided that the above
--// copyright notice and this permission notice appear in all copies.
--//
--// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
--// WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
--// MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
--// ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
--// WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
--// ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
--// OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
--
--// NOTE: Due to the following build constraints, this file will only be compiled
--// when either cgo is not supported or "-tags testcgo" is not added to the go
--// test command line.  This file intentionally does not setup any cgo tests in
--// this scenario.
--// +build !cgo !testcgo
--
--package spew_test
+@@ -1,3 +0,0 @@
+-package etcd
 -
--func addCgoDumpTests() {
--	// Don't add any tests for cgo since this file is only compiled when
--	// there should not be any cgo tests.
--}
-diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/example_test.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/example_test.go
+-const version = "v2"
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/watch.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/watch.go
 deleted file mode 100644
-index a7acd14..0000000
---- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/example_test.go
+index aa8d3df..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/watch.go
 +++ /dev/null
-@@ -1,230 +0,0 @@
--/*
-- * Copyright (c) 2013 Dave Collins <dave at davec.name>
-- *
-- * Permission to use, copy, modify, and distribute this software for any
-- * purpose with or without fee is hereby granted, provided that the above
-- * copyright notice and this permission notice appear in all copies.
-- *
-- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
-- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
-- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
-- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
-- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
-- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
-- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
-- */
--
--package spew_test
+@@ -1,103 +0,0 @@
+-package etcd
 -
 -import (
--	"fmt"
--	"github.com/davecgh/go-spew/spew"
+-	"errors"
 -)
 -
--type Flag int
--
--const (
--	flagOne Flag = iota
--	flagTwo
+-// Errors introduced by the Watch command.
+-var (
+-	ErrWatchStoppedByUser = errors.New("Watch stopped by the user via stop channel")
 -)
 -
--var flagStrings = map[Flag]string{
--	flagOne: "flagOne",
--	flagTwo: "flagTwo",
--}
+-// If recursive is set to true the watch returns the first change under the given
+-// prefix since the given index.
+-//
+-// If recursive is set to false the watch returns the first change to the given key
+-// since the given index.
+-//
+-// To watch for the latest change, set waitIndex = 0.
+-//
+-// If a receiver channel is given, it will be a long-term watch. Watch will block at the
+-//channel. After someone receives the channel, it will go on to watch that
+-// prefix.  If a stop channel is given, the client can close long-term watch using
+-// the stop channel.
+-func (c *Client) Watch(prefix string, waitIndex uint64, recursive bool,
+-	receiver chan *Response, stop chan bool) (*Response, error) {
+-	logger.Debugf("watch %s [%s]", prefix, c.cluster.Leader)
+-	if receiver == nil {
+-		raw, err := c.watchOnce(prefix, waitIndex, recursive, stop)
 -
--func (f Flag) String() string {
--	if s, ok := flagStrings[f]; ok {
--		return s
+-		if err != nil {
+-			return nil, err
+-		}
+-
+-		return raw.Unmarshal()
 -	}
--	return fmt.Sprintf("Unknown flag (%d)", int(f))
--}
+-	defer close(receiver)
 -
--type Bar struct {
--	flag Flag
--	data uintptr
--}
+-	for {
+-		raw, err := c.watchOnce(prefix, waitIndex, recursive, stop)
 -
--type Foo struct {
--	unexportedField Bar
--	ExportedField   map[interface{}]interface{}
+-		if err != nil {
+-			return nil, err
+-		}
+-
+-		resp, err := raw.Unmarshal()
+-
+-		if err != nil {
+-			return nil, err
+-		}
+-
+-		waitIndex = resp.Node.ModifiedIndex + 1
+-		receiver <- resp
+-	}
 -}
 -
--// This example demonstrates how to use Dump to dump variables to stdout.
--func ExampleDump() {
--	// The following package level declarations are assumed for this example:
--	/*
--		type Flag int
+-func (c *Client) RawWatch(prefix string, waitIndex uint64, recursive bool,
+-	receiver chan *RawResponse, stop chan bool) (*RawResponse, error) {
 -
--		const (
--			flagOne Flag = iota
--			flagTwo
--		)
+-	logger.Debugf("rawWatch %s [%s]", prefix, c.cluster.Leader)
+-	if receiver == nil {
+-		return c.watchOnce(prefix, waitIndex, recursive, stop)
+-	}
 -
--		var flagStrings = map[Flag]string{
--			flagOne: "flagOne",
--			flagTwo: "flagTwo",
--		}
+-	for {
+-		raw, err := c.watchOnce(prefix, waitIndex, recursive, stop)
 -
--		func (f Flag) String() string {
--			if s, ok := flagStrings[f]; ok {
--				return s
--			}
--			return fmt.Sprintf("Unknown flag (%d)", int(f))
+-		if err != nil {
+-			return nil, err
 -		}
 -
--		type Bar struct {
--			flag Flag
--			data uintptr
--		}
+-		resp, err := raw.Unmarshal()
 -
--		type Foo struct {
--			unexportedField Bar
--			ExportedField   map[interface{}]interface{}
+-		if err != nil {
+-			return nil, err
 -		}
--	*/
 -
--	// Setup some sample data structures for the example.
--	bar := Bar{Flag(flagTwo), uintptr(0)}
--	s1 := Foo{bar, map[interface{}]interface{}{"one": true}}
--	f := Flag(5)
--	b := []byte{
--		0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18,
--		0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 0x20,
--		0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28,
--		0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, 0x30,
--		0x31, 0x32,
+-		waitIndex = resp.Node.ModifiedIndex + 1
+-		receiver <- raw
 -	}
+-}
 -
--	// Dump!
--	spew.Dump(s1, f, b)
+-// helper func
+-// return when there is change under the given prefix
+-func (c *Client) watchOnce(key string, waitIndex uint64, recursive bool, stop chan bool) (*RawResponse, error) {
 -
--	// Output:
--	// (spew_test.Foo) {
--	//  unexportedField: (spew_test.Bar) {
--	//   flag: (spew_test.Flag) flagTwo,
--	//   data: (uintptr) <nil>
--	//  },
--	//  ExportedField: (map[interface {}]interface {}) (len=1) {
--	//   (string) (len=3) "one": (bool) true
--	//  }
--	// }
--	// (spew_test.Flag) Unknown flag (5)
--	// ([]uint8) (len=34 cap=34) {
--	//  00000000  11 12 13 14 15 16 17 18  19 1a 1b 1c 1d 1e 1f 20  |............... |
--	//  00000010  21 22 23 24 25 26 27 28  29 2a 2b 2c 2d 2e 2f 30  |!"#$%&'()*+,-./0|
--	//  00000020  31 32                                             |12|
--	// }
--	//
+-	options := Options{
+-		"wait": true,
+-	}
+-	if waitIndex > 0 {
+-		options["waitIndex"] = waitIndex
+-	}
+-	if recursive {
+-		options["recursive"] = true
+-	}
+-
+-	resp, err := c.getCancelable(key, options, stop)
+-
+-	if err == ErrRequestCancelled {
+-		return nil, ErrWatchStoppedByUser
+-	}
+-
+-	return resp, err
 -}
+diff --git a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/watch_test.go b/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/watch_test.go
+deleted file mode 100644
+index 43e1dfe..0000000
+--- a/Godeps/_workspace/src/github.com/coreos/go-etcd/etcd/watch_test.go
++++ /dev/null
+@@ -1,119 +0,0 @@
+-package etcd
 -
--// This example demonstrates how to use Printf to display a variable with a
--// format string and inline formatting.
--func ExamplePrintf() {
--	// Create a double pointer to a uint 8.
--	ui8 := uint8(5)
--	pui8 := &ui8
--	ppui8 := &pui8
+-import (
+-	"fmt"
+-	"runtime"
+-	"testing"
+-	"time"
+-)
 -
--	// Create a circular data type.
--	type circular struct {
--		ui8 uint8
--		c   *circular
+-func TestWatch(t *testing.T) {
+-	c := NewClient(nil)
+-	defer func() {
+-		c.Delete("watch_foo", true)
+-	}()
+-
+-	go setHelper("watch_foo", "bar", c)
+-
+-	resp, err := c.Watch("watch_foo", 0, false, nil, nil)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !(resp.Node.Key == "/watch_foo" && resp.Node.Value == "bar") {
+-		t.Fatalf("Watch 1 failed: %#v", resp)
 -	}
--	c := circular{ui8: 1}
--	c.c = &c
 -
--	// Print!
--	spew.Printf("ppui8: %v\n", ppui8)
--	spew.Printf("circular: %v\n", c)
+-	go setHelper("watch_foo", "bar", c)
 -
--	// Output:
--	// ppui8: <**>5
--	// circular: {1 <*>{1 <*><shown>}}
--}
+-	resp, err = c.Watch("watch_foo", resp.Node.ModifiedIndex+1, false, nil, nil)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !(resp.Node.Key == "/watch_foo" && resp.Node.Value == "bar") {
+-		t.Fatalf("Watch 2 failed: %#v", resp)
+-	}
 -
--// This example demonstrates how to use a ConfigState.
--func ExampleConfigState() {
--	// Modify the indent level of the ConfigState only.  The global
--	// configuration is not modified.
--	scs := spew.ConfigState{Indent: "\t"}
+-	routineNum := runtime.NumGoroutine()
 -
--	// Output using the ConfigState instance.
--	v := map[string]int{"one": 1}
--	scs.Printf("v: %v\n", v)
--	scs.Dump(v)
+-	ch := make(chan *Response, 10)
+-	stop := make(chan bool, 1)
 -
--	// Output:
--	// v: map[one:1]
--	// (map[string]int) (len=1) {
--	// 	(string) (len=3) "one": (int) 1
--	// }
+-	go setLoop("watch_foo", "bar", c)
+-
+-	go receiver(ch, stop)
+-
+-	_, err = c.Watch("watch_foo", 0, false, ch, stop)
+-	if err != ErrWatchStoppedByUser {
+-		t.Fatalf("Watch returned a non-user stop error")
+-	}
+-
+-	if newRoutineNum := runtime.NumGoroutine(); newRoutineNum != routineNum {
+-		t.Fatalf("Routine numbers differ after watch stop: %v, %v", routineNum, newRoutineNum)
+-	}
 -}
 -
--// This example demonstrates how to use ConfigState.Dump to dump variables to
--// stdout
--func ExampleConfigState_Dump() {
--	// See the top-level Dump example for details on the types used in this
--	// example.
+-func TestWatchAll(t *testing.T) {
+-	c := NewClient(nil)
+-	defer func() {
+-		c.Delete("watch_foo", true)
+-	}()
 -
--	// Create two ConfigState instances with different indentation.
--	scs := spew.ConfigState{Indent: "\t"}
--	scs2 := spew.ConfigState{Indent: " "}
+-	go setHelper("watch_foo/foo", "bar", c)
 -
--	// Setup some sample data structures for the example.
--	bar := Bar{Flag(flagTwo), uintptr(0)}
--	s1 := Foo{bar, map[interface{}]interface{}{"one": true}}
+-	resp, err := c.Watch("watch_foo", 0, true, nil, nil)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !(resp.Node.Key == "/watch_foo/foo" && resp.Node.Value == "bar") {
+-		t.Fatalf("WatchAll 1 failed: %#v", resp)
+-	}
 -
--	// Dump using the ConfigState instances.
--	scs.Dump(s1)
--	scs2.Dump(s1)
+-	go setHelper("watch_foo/foo", "bar", c)
 -
--	// Output:
--	// (spew_test.Foo) {
--	// 	unexportedField: (spew_test.Bar) {
--	// 		flag: (spew_test.Flag) flagTwo,
--	// 		data: (uintptr) <nil>
--	// 	},
--	// 	ExportedField: (map[interface {}]interface {}) (len=1) {
--	//		(string) (len=3) "one": (bool) true
--	// 	}
--	// }
--	// (spew_test.Foo) {
--	//  unexportedField: (spew_test.Bar) {
--	//   flag: (spew_test.Flag) flagTwo,
--	//   data: (uintptr) <nil>
--	//  },
--	//  ExportedField: (map[interface {}]interface {}) (len=1) {
--	//   (string) (len=3) "one": (bool) true
--	//  }
--	// }
--	//
--}
+-	resp, err = c.Watch("watch_foo", resp.Node.ModifiedIndex+1, true, nil, nil)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !(resp.Node.Key == "/watch_foo/foo" && resp.Node.Value == "bar") {
+-		t.Fatalf("WatchAll 2 failed: %#v", resp)
+-	}
 -
--// This example demonstrates how to use ConfigState.Printf to display a variable
--// with a format string and inline formatting.
--func ExampleConfigState_Printf() {
--	// See the top-level Dump example for details on the types used in this
--	// example.
+-	ch := make(chan *Response, 10)
+-	stop := make(chan bool, 1)
 -
--	// Create two ConfigState instances and modify the method handling of the
--	// first ConfigState only.
--	scs := spew.NewDefaultConfig()
--	scs2 := spew.NewDefaultConfig()
--	scs.DisableMethods = true
+-	routineNum := runtime.NumGoroutine()
 -
--	// Alternatively
--	// scs := spew.ConfigState{Indent: " ", DisableMethods: true}
--	// scs2 := spew.ConfigState{Indent: " "}
+-	go setLoop("watch_foo/foo", "bar", c)
 -
--	// This is of type Flag which implements a Stringer and has raw value 1.
--	f := flagTwo
+-	go receiver(ch, stop)
 -
--	// Dump using the ConfigState instances.
--	scs.Printf("f: %v\n", f)
--	scs2.Printf("f: %v\n", f)
+-	_, err = c.Watch("watch_foo", 0, true, ch, stop)
+-	if err != ErrWatchStoppedByUser {
+-		t.Fatalf("Watch returned a non-user stop error")
+-	}
 -
--	// Output:
--	// f: 1
--	// f: flagTwo
+-	if newRoutineNum := runtime.NumGoroutine(); newRoutineNum != routineNum {
+-		t.Fatalf("Routine numbers differ after watch stop: %v, %v", routineNum, newRoutineNum)
+-	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/format.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/format.go
+-
+-func setHelper(key, value string, c *Client) {
+-	time.Sleep(time.Second)
+-	c.Set(key, value, 100)
+-}
+-
+-func setLoop(key, value string, c *Client) {
+-	time.Sleep(time.Second)
+-	for i := 0; i < 10; i++ {
+-		newValue := fmt.Sprintf("%s_%v", value, i)
+-		c.Set(key, newValue, 100)
+-		time.Sleep(time.Second / 10)
+-	}
+-}
+-
+-func receiver(c chan *Response, stop chan bool) {
+-	for i := 0; i < 10; i++ {
+-		<-c
+-	}
+-	stop <- true
+-}
+diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/common.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/common.go
 deleted file mode 100644
-index b6b1fb0..0000000
---- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/format.go
+index 0ce0df1..0000000
+--- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/common.go
 +++ /dev/null
-@@ -1,413 +0,0 @@
+@@ -1,371 +0,0 @@
 -/*
 - * Copyright (c) 2013 Dave Collins <dave at davec.name>
 - *
@@ -43225,378 +44166,764 @@ index b6b1fb0..0000000
 -package spew
 -
 -import (
--	"bytes"
 -	"fmt"
+-	"io"
 -	"reflect"
+-	"sort"
 -	"strconv"
--	"strings"
+-	"unsafe"
 -)
 -
--// supportedFlags is a list of all the character flags supported by fmt package.
--const supportedFlags = "0-+# "
--
--// formatState implements the fmt.Formatter interface and contains information
--// about the state of a formatting operation.  The NewFormatter function can
--// be used to get a new Formatter which can be used directly as arguments
--// in standard fmt package printing calls.
--type formatState struct {
--	value          interface{}
--	fs             fmt.State
--	depth          int
--	pointers       map[uintptr]int
--	ignoreNextType bool
--	cs             *ConfigState
--}
--
--// buildDefaultFormat recreates the original format string without precision
--// and width information to pass in to fmt.Sprintf in the case of an
--// unrecognized type.  Unless new types are added to the language, this
--// function won't ever be called.
--func (f *formatState) buildDefaultFormat() (format string) {
--	buf := bytes.NewBuffer(percentBytes)
--
--	for _, flag := range supportedFlags {
--		if f.fs.Flag(int(flag)) {
--			buf.WriteRune(flag)
--		}
--	}
+-const (
+-	// ptrSize is the size of a pointer on the current arch.
+-	ptrSize = unsafe.Sizeof((*byte)(nil))
+-)
 -
--	buf.WriteRune('v')
+-var (
+-	// offsetPtr, offsetScalar, and offsetFlag are the offsets for the
+-	// internal reflect.Value fields.  These values are valid before golang
+-	// commit ecccf07e7f9d which changed the format.  The are also valid
+-	// after commit 82f48826c6c7 which changed the format again to mirror
+-	// the original format.  Code in the init function updates these offsets
+-	// as necessary.
+-	offsetPtr    = uintptr(ptrSize)
+-	offsetScalar = uintptr(0)
+-	offsetFlag   = uintptr(ptrSize * 2)
 -
--	format = buf.String()
--	return format
--}
+-	// flagKindWidth and flagKindShift indicate various bits that the
+-	// reflect package uses internally to track kind information.
+-	//
+-	// flagRO indicates whether or not the value field of a reflect.Value is
+-	// read-only.
+-	//
+-	// flagIndir indicates whether the value field of a reflect.Value is
+-	// the actual data or a pointer to the data.
+-	//
+-	// These values are valid before golang commit 90a7c3c86944 which
+-	// changed their positions.  Code in the init function updates these
+-	// flags as necessary.
+-	flagKindWidth = uintptr(5)
+-	flagKindShift = uintptr(flagKindWidth - 1)
+-	flagRO        = uintptr(1 << 0)
+-	flagIndir     = uintptr(1 << 1)
+-)
 -
--// constructOrigFormat recreates the original format string including precision
--// and width information to pass along to the standard fmt package.  This allows
--// automatic deferral of all format strings this package doesn't support.
--func (f *formatState) constructOrigFormat(verb rune) (format string) {
--	buf := bytes.NewBuffer(percentBytes)
+-func init() {
+-	// Older versions of reflect.Value stored small integers directly in the
+-	// ptr field (which is named val in the older versions).  Versions
+-	// between commits ecccf07e7f9d and 82f48826c6c7 added a new field named
+-	// scalar for this purpose which unfortunately came before the flag
+-	// field, so the offset of the flag field is different for those
+-	// versions.
+-	//
+-	// This code constructs a new reflect.Value from a known small integer
+-	// and checks if the size of the reflect.Value struct indicates it has
+-	// the scalar field. When it does, the offsets are updated accordingly.
+-	vv := reflect.ValueOf(0xf00)
+-	if unsafe.Sizeof(vv) == (ptrSize * 4) {
+-		offsetScalar = ptrSize * 2
+-		offsetFlag = ptrSize * 3
+-	}
 -
--	for _, flag := range supportedFlags {
--		if f.fs.Flag(int(flag)) {
--			buf.WriteRune(flag)
--		}
+-	// Commit 90a7c3c86944 changed the flag positions such that the low
+-	// order bits are the kind.  This code extracts the kind from the flags
+-	// field and ensures it's the correct type.  When it's not, the flag
+-	// order has been changed to the newer format, so the flags are updated
+-	// accordingly.
+-	upf := unsafe.Pointer(uintptr(unsafe.Pointer(&vv)) + offsetFlag)
+-	upfv := *(*uintptr)(upf)
+-	flagKindMask := uintptr((1<<flagKindWidth - 1) << flagKindShift)
+-	if (upfv&flagKindMask)>>flagKindShift != uintptr(reflect.Int) {
+-		flagKindShift = 0
+-		flagRO = 1 << 5
+-		flagIndir = 1 << 6
 -	}
+-}
 -
--	if width, ok := f.fs.Width(); ok {
--		buf.WriteString(strconv.Itoa(width))
+-// unsafeReflectValue converts the passed reflect.Value into a one that bypasses
+-// the typical safety restrictions preventing access to unaddressable and
+-// unexported data.  It works by digging the raw pointer to the underlying
+-// value out of the protected value and generating a new unprotected (unsafe)
+-// reflect.Value to it.
+-//
+-// This allows us to check for implementations of the Stringer and error
+-// interfaces to be used for pretty printing ordinarily unaddressable and
+-// inaccessible values such as unexported struct fields.
+-func unsafeReflectValue(v reflect.Value) (rv reflect.Value) {
+-	indirects := 1
+-	vt := v.Type()
+-	upv := unsafe.Pointer(uintptr(unsafe.Pointer(&v)) + offsetPtr)
+-	rvf := *(*uintptr)(unsafe.Pointer(uintptr(unsafe.Pointer(&v)) + offsetFlag))
+-	if rvf&flagIndir != 0 {
+-		vt = reflect.PtrTo(v.Type())
+-		indirects++
+-	} else if offsetScalar != 0 {
+-		// The value is in the scalar field when it's not one of the
+-		// reference types.
+-		switch vt.Kind() {
+-		case reflect.Uintptr:
+-		case reflect.Chan:
+-		case reflect.Func:
+-		case reflect.Map:
+-		case reflect.Ptr:
+-		case reflect.UnsafePointer:
+-		default:
+-			upv = unsafe.Pointer(uintptr(unsafe.Pointer(&v)) +
+-				offsetScalar)
+-		}
 -	}
 -
--	if precision, ok := f.fs.Precision(); ok {
--		buf.Write(precisionBytes)
--		buf.WriteString(strconv.Itoa(precision))
+-	pv := reflect.NewAt(vt, upv)
+-	rv = pv
+-	for i := 0; i < indirects; i++ {
+-		rv = rv.Elem()
 -	}
+-	return rv
+-}
 -
--	buf.WriteRune(verb)
+-// Some constants in the form of bytes to avoid string overhead.  This mirrors
+-// the technique used in the fmt package.
+-var (
+-	panicBytes            = []byte("(PANIC=")
+-	plusBytes             = []byte("+")
+-	iBytes                = []byte("i")
+-	trueBytes             = []byte("true")
+-	falseBytes            = []byte("false")
+-	interfaceBytes        = []byte("(interface {})")
+-	commaNewlineBytes     = []byte(",\n")
+-	newlineBytes          = []byte("\n")
+-	openBraceBytes        = []byte("{")
+-	openBraceNewlineBytes = []byte("{\n")
+-	closeBraceBytes       = []byte("}")
+-	asteriskBytes         = []byte("*")
+-	colonBytes            = []byte(":")
+-	colonSpaceBytes       = []byte(": ")
+-	openParenBytes        = []byte("(")
+-	closeParenBytes       = []byte(")")
+-	spaceBytes            = []byte(" ")
+-	pointerChainBytes     = []byte("->")
+-	nilAngleBytes         = []byte("<nil>")
+-	maxNewlineBytes       = []byte("<max depth reached>\n")
+-	maxShortBytes         = []byte("<max>")
+-	circularBytes         = []byte("<already shown>")
+-	circularShortBytes    = []byte("<shown>")
+-	invalidAngleBytes     = []byte("<invalid>")
+-	openBracketBytes      = []byte("[")
+-	closeBracketBytes     = []byte("]")
+-	percentBytes          = []byte("%")
+-	precisionBytes        = []byte(".")
+-	openAngleBytes        = []byte("<")
+-	closeAngleBytes       = []byte(">")
+-	openMapBytes          = []byte("map[")
+-	closeMapBytes         = []byte("]")
+-	lenEqualsBytes        = []byte("len=")
+-	capEqualsBytes        = []byte("cap=")
+-)
 -
--	format = buf.String()
--	return format
--}
+-// hexDigits is used to map a decimal value to a hex digit.
+-var hexDigits = "0123456789abcdef"
 -
--// unpackValue returns values inside of non-nil interfaces when possible and
--// ensures that types for values which have been unpacked from an interface
--// are displayed when the show types flag is also set.
--// This is useful for data types like structs, arrays, slices, and maps which
--// can contain varying types packed inside an interface.
--func (f *formatState) unpackValue(v reflect.Value) reflect.Value {
--	if v.Kind() == reflect.Interface {
--		f.ignoreNextType = false
--		if !v.IsNil() {
--			v = v.Elem()
--		}
+-// catchPanic handles any panics that might occur during the handleMethods
+-// calls.
+-func catchPanic(w io.Writer, v reflect.Value) {
+-	if err := recover(); err != nil {
+-		w.Write(panicBytes)
+-		fmt.Fprintf(w, "%v", err)
+-		w.Write(closeParenBytes)
 -	}
--	return v
 -}
 -
--// formatPtr handles formatting of pointers by indirecting them as necessary.
--func (f *formatState) formatPtr(v reflect.Value) {
--	// Display nil if top level pointer is nil.
--	showTypes := f.fs.Flag('#')
--	if v.IsNil() && (!showTypes || f.ignoreNextType) {
--		f.fs.Write(nilAngleBytes)
--		return
+-// handleMethods attempts to call the Error and String methods on the underlying
+-// type the passed reflect.Value represents and outputes the result to Writer w.
+-//
+-// It handles panics in any called methods by catching and displaying the error
+-// as the formatted value.
+-func handleMethods(cs *ConfigState, w io.Writer, v reflect.Value) (handled bool) {
+-	// We need an interface to check if the type implements the error or
+-	// Stringer interface.  However, the reflect package won't give us an
+-	// interface on certain things like unexported struct fields in order
+-	// to enforce visibility rules.  We use unsafe to bypass these restrictions
+-	// since this package does not mutate the values.
+-	if !v.CanInterface() {
+-		v = unsafeReflectValue(v)
 -	}
 -
--	// Remove pointers at or below the current depth from map used to detect
--	// circular refs.
--	for k, depth := range f.pointers {
--		if depth >= f.depth {
--			delete(f.pointers, k)
+-	// Choose whether or not to do error and Stringer interface lookups against
+-	// the base type or a pointer to the base type depending on settings.
+-	// Technically calling one of these methods with a pointer receiver can
+-	// mutate the value, however, types which choose to satisify an error or
+-	// Stringer interface with a pointer receiver should not be mutating their
+-	// state inside these interface methods.
+-	var viface interface{}
+-	if !cs.DisablePointerMethods {
+-		if !v.CanAddr() {
+-			v = unsafeReflectValue(v)
+-		}
+-		viface = v.Addr().Interface()
+-	} else {
+-		if v.CanAddr() {
+-			v = v.Addr()
 -		}
+-		viface = v.Interface()
 -	}
 -
--	// Keep list of all dereferenced pointers to possibly show later.
--	pointerChain := make([]uintptr, 0)
--
--	// Figure out how many levels of indirection there are by derferencing
--	// pointers and unpacking interfaces down the chain while detecting circular
--	// references.
--	nilFound := false
--	cycleFound := false
--	indirects := 0
--	ve := v
--	for ve.Kind() == reflect.Ptr {
--		if ve.IsNil() {
--			nilFound = true
--			break
--		}
--		indirects++
--		addr := ve.Pointer()
--		pointerChain = append(pointerChain, addr)
--		if pd, ok := f.pointers[addr]; ok && pd < f.depth {
--			cycleFound = true
--			indirects--
--			break
+-	// Is it an error or Stringer?
+-	switch iface := viface.(type) {
+-	case error:
+-		defer catchPanic(w, v)
+-		if cs.ContinueOnMethod {
+-			w.Write(openParenBytes)
+-			w.Write([]byte(iface.Error()))
+-			w.Write(closeParenBytes)
+-			w.Write(spaceBytes)
+-			return false
 -		}
--		f.pointers[addr] = f.depth
 -
--		ve = ve.Elem()
--		if ve.Kind() == reflect.Interface {
--			if ve.IsNil() {
--				nilFound = true
--				break
--			}
--			ve = ve.Elem()
+-		w.Write([]byte(iface.Error()))
+-		return true
+-
+-	case fmt.Stringer:
+-		defer catchPanic(w, v)
+-		if cs.ContinueOnMethod {
+-			w.Write(openParenBytes)
+-			w.Write([]byte(iface.String()))
+-			w.Write(closeParenBytes)
+-			w.Write(spaceBytes)
+-			return false
 -		}
+-		w.Write([]byte(iface.String()))
+-		return true
 -	}
+-	return false
+-}
 -
--	// Display type or indirection level depending on flags.
--	if showTypes && !f.ignoreNextType {
--		f.fs.Write(openParenBytes)
--		f.fs.Write(bytes.Repeat(asteriskBytes, indirects))
--		f.fs.Write([]byte(ve.Type().String()))
--		f.fs.Write(closeParenBytes)
+-// printBool outputs a boolean value as true or false to Writer w.
+-func printBool(w io.Writer, val bool) {
+-	if val {
+-		w.Write(trueBytes)
 -	} else {
--		if nilFound || cycleFound {
--			indirects += strings.Count(ve.Type().String(), "*")
--		}
--		f.fs.Write(openAngleBytes)
--		f.fs.Write([]byte(strings.Repeat("*", indirects)))
--		f.fs.Write(closeAngleBytes)
+-		w.Write(falseBytes)
 -	}
+-}
 -
--	// Display pointer information depending on flags.
--	if f.fs.Flag('+') && (len(pointerChain) > 0) {
--		f.fs.Write(openParenBytes)
--		for i, addr := range pointerChain {
--			if i > 0 {
--				f.fs.Write(pointerChainBytes)
--			}
--			printHexPtr(f.fs, addr)
--		}
--		f.fs.Write(closeParenBytes)
--	}
+-// printInt outputs a signed integer value to Writer w.
+-func printInt(w io.Writer, val int64, base int) {
+-	w.Write([]byte(strconv.FormatInt(val, base)))
+-}
 -
--	// Display dereferenced value.
--	switch {
--	case nilFound == true:
--		f.fs.Write(nilAngleBytes)
+-// printUint outputs an unsigned integer value to Writer w.
+-func printUint(w io.Writer, val uint64, base int) {
+-	w.Write([]byte(strconv.FormatUint(val, base)))
+-}
 -
--	case cycleFound == true:
--		f.fs.Write(circularShortBytes)
+-// printFloat outputs a floating point value using the specified precision,
+-// which is expected to be 32 or 64bit, to Writer w.
+-func printFloat(w io.Writer, val float64, precision int) {
+-	w.Write([]byte(strconv.FormatFloat(val, 'g', -1, precision)))
+-}
 -
--	default:
--		f.ignoreNextType = true
--		f.format(ve)
+-// printComplex outputs a complex value using the specified float precision
+-// for the real and imaginary parts to Writer w.
+-func printComplex(w io.Writer, c complex128, floatPrecision int) {
+-	r := real(c)
+-	w.Write(openParenBytes)
+-	w.Write([]byte(strconv.FormatFloat(r, 'g', -1, floatPrecision)))
+-	i := imag(c)
+-	if i >= 0 {
+-		w.Write(plusBytes)
 -	}
+-	w.Write([]byte(strconv.FormatFloat(i, 'g', -1, floatPrecision)))
+-	w.Write(iBytes)
+-	w.Write(closeParenBytes)
 -}
 -
--// format is the main workhorse for providing the Formatter interface.  It
--// uses the passed reflect value to figure out what kind of object we are
--// dealing with and formats it appropriately.  It is a recursive function,
--// however circular data structures are detected and handled properly.
--func (f *formatState) format(v reflect.Value) {
--	// Handle invalid reflect values immediately.
--	kind := v.Kind()
--	if kind == reflect.Invalid {
--		f.fs.Write(invalidAngleBytes)
+-// printHexPtr outputs a uintptr formatted as hexidecimal with a leading '0x'
+-// prefix to Writer w.
+-func printHexPtr(w io.Writer, p uintptr) {
+-	// Null pointer.
+-	num := uint64(p)
+-	if num == 0 {
+-		w.Write(nilAngleBytes)
 -		return
 -	}
 -
--	// Handle pointers specially.
--	if kind == reflect.Ptr {
--		f.formatPtr(v)
--		return
--	}
+-	// Max uint64 is 16 bytes in hex + 2 bytes for '0x' prefix
+-	buf := make([]byte, 18)
 -
--	// Print type information unless already handled elsewhere.
--	if !f.ignoreNextType && f.fs.Flag('#') {
--		f.fs.Write(openParenBytes)
--		f.fs.Write([]byte(v.Type().String()))
--		f.fs.Write(closeParenBytes)
+-	// It's simpler to construct the hex string right to left.
+-	base := uint64(16)
+-	i := len(buf) - 1
+-	for num >= base {
+-		buf[i] = hexDigits[num%base]
+-		num /= base
+-		i--
 -	}
--	f.ignoreNextType = false
+-	buf[i] = hexDigits[num]
 -
--	// Call Stringer/error interfaces if they exist and the handle methods
--	// flag is enabled.
--	if !f.cs.DisableMethods {
--		if (kind != reflect.Invalid) && (kind != reflect.Interface) {
--			if handled := handleMethods(f.cs, f.fs, v); handled {
--				return
--			}
--		}
--	}
+-	// Add '0x' prefix.
+-	i--
+-	buf[i] = 'x'
+-	i--
+-	buf[i] = '0'
 -
--	switch kind {
--	case reflect.Invalid:
--		// Do nothing.  We should never get here since invalid has already
--		// been handled above.
+-	// Strip unused leading bytes.
+-	buf = buf[i:]
+-	w.Write(buf)
+-}
 -
--	case reflect.Bool:
--		printBool(f.fs, v.Bool())
+-// valuesSorter implements sort.Interface to allow a slice of reflect.Value
+-// elements to be sorted.
+-type valuesSorter struct {
+-	values []reflect.Value
+-}
 -
--	case reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64, reflect.Int:
--		printInt(f.fs, v.Int(), 10)
+-// Len returns the number of values in the slice.  It is part of the
+-// sort.Interface implementation.
+-func (s *valuesSorter) Len() int {
+-	return len(s.values)
+-}
+-
+-// Swap swaps the values at the passed indices.  It is part of the
+-// sort.Interface implementation.
+-func (s *valuesSorter) Swap(i, j int) {
+-	s.values[i], s.values[j] = s.values[j], s.values[i]
+-}
 -
+-// Less returns whether the value at index i should sort before the
+-// value at index j.  It is part of the sort.Interface implementation.
+-func (s *valuesSorter) Less(i, j int) bool {
+-	switch s.values[i].Kind() {
+-	case reflect.Bool:
+-		return !s.values[i].Bool() && s.values[j].Bool()
+-	case reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64, reflect.Int:
+-		return s.values[i].Int() < s.values[j].Int()
 -	case reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uint:
--		printUint(f.fs, v.Uint(), 10)
+-		return s.values[i].Uint() < s.values[j].Uint()
+-	case reflect.Float32, reflect.Float64:
+-		return s.values[i].Float() < s.values[j].Float()
+-	case reflect.String:
+-		return s.values[i].String() < s.values[j].String()
+-	case reflect.Uintptr:
+-		return s.values[i].Uint() < s.values[j].Uint()
+-	}
+-	return s.values[i].String() < s.values[j].String()
+-}
 -
--	case reflect.Float32:
--		printFloat(f.fs, v.Float(), 32)
+-// sortValues is a generic sort function for native types: int, uint, bool,
+-// string and uintptr.  Other inputs are sorted according to their
+-// Value.String() value to ensure display stability.
+-func sortValues(values []reflect.Value) {
+-	if len(values) == 0 {
+-		return
+-	}
+-	sort.Sort(&valuesSorter{values})
+-}
+diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/common_test.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/common_test.go
+deleted file mode 100644
+index 3bea81f..0000000
+--- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/common_test.go
++++ /dev/null
+@@ -1,192 +0,0 @@
+-/*
+- * Copyright (c) 2013 Dave Collins <dave at davec.name>
+- *
+- * Permission to use, copy, modify, and distribute this software for any
+- * purpose with or without fee is hereby granted, provided that the above
+- * copyright notice and this permission notice appear in all copies.
+- *
+- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+- */
 -
--	case reflect.Float64:
--		printFloat(f.fs, v.Float(), 64)
+-package spew_test
 -
--	case reflect.Complex64:
--		printComplex(f.fs, v.Complex(), 32)
+-import (
+-	"fmt"
+-	"github.com/davecgh/go-spew/spew"
+-	"reflect"
+-	"testing"
+-)
 -
--	case reflect.Complex128:
--		printComplex(f.fs, v.Complex(), 64)
+-// custom type to test Stinger interface on non-pointer receiver.
+-type stringer string
 -
--	case reflect.Slice:
--		if v.IsNil() {
--			f.fs.Write(nilAngleBytes)
--			break
--		}
--		fallthrough
+-// String implements the Stringer interface for testing invocation of custom
+-// stringers on types with non-pointer receivers.
+-func (s stringer) String() string {
+-	return "stringer " + string(s)
+-}
 -
--	case reflect.Array:
--		f.fs.Write(openBracketBytes)
--		f.depth++
--		if (f.cs.MaxDepth != 0) && (f.depth > f.cs.MaxDepth) {
--			f.fs.Write(maxShortBytes)
--		} else {
--			numEntries := v.Len()
--			for i := 0; i < numEntries; i++ {
--				if i > 0 {
--					f.fs.Write(spaceBytes)
--				}
--				f.ignoreNextType = true
--				f.format(f.unpackValue(v.Index(i)))
--			}
--		}
--		f.depth--
--		f.fs.Write(closeBracketBytes)
+-// custom type to test Stinger interface on pointer receiver.
+-type pstringer string
 -
--	case reflect.String:
--		f.fs.Write([]byte(v.String()))
+-// String implements the Stringer interface for testing invocation of custom
+-// stringers on types with only pointer receivers.
+-func (s *pstringer) String() string {
+-	return "stringer " + string(*s)
+-}
 -
--	case reflect.Interface:
--		// The only time we should get here is for nil interfaces due to
--		// unpackValue calls.
--		if v.IsNil() {
--			f.fs.Write(nilAngleBytes)
--		}
+-// xref1 and xref2 are cross referencing structs for testing circular reference
+-// detection.
+-type xref1 struct {
+-	ps2 *xref2
+-}
+-type xref2 struct {
+-	ps1 *xref1
+-}
 -
--	case reflect.Ptr:
--		// Do nothing.  We should never get here since pointers have already
--		// been handled above.
+-// indirCir1, indirCir2, and indirCir3 are used to generate an indirect circular
+-// reference for testing detection.
+-type indirCir1 struct {
+-	ps2 *indirCir2
+-}
+-type indirCir2 struct {
+-	ps3 *indirCir3
+-}
+-type indirCir3 struct {
+-	ps1 *indirCir1
+-}
 -
--	case reflect.Map:
--		f.fs.Write(openMapBytes)
--		f.depth++
--		if (f.cs.MaxDepth != 0) && (f.depth > f.cs.MaxDepth) {
--			f.fs.Write(maxShortBytes)
--		} else {
--			keys := v.MapKeys()
--			if f.cs.SortKeys {
--				sortValues(keys)
--			}
--			for i, key := range keys {
--				if i > 0 {
--					f.fs.Write(spaceBytes)
--				}
--				f.ignoreNextType = true
--				f.format(f.unpackValue(key))
--				f.fs.Write(colonBytes)
--				f.ignoreNextType = true
--				f.format(f.unpackValue(v.MapIndex(key)))
--			}
--		}
--		f.depth--
--		f.fs.Write(closeMapBytes)
+-// embed is used to test embedded structures.
+-type embed struct {
+-	a string
+-}
 -
--	case reflect.Struct:
--		numFields := v.NumField()
--		f.fs.Write(openBraceBytes)
--		f.depth++
--		if (f.cs.MaxDepth != 0) && (f.depth > f.cs.MaxDepth) {
--			f.fs.Write(maxShortBytes)
--		} else {
--			vt := v.Type()
--			for i := 0; i < numFields; i++ {
--				if i > 0 {
--					f.fs.Write(spaceBytes)
--				}
--				vtf := vt.Field(i)
--				if f.fs.Flag('+') || f.fs.Flag('#') {
--					f.fs.Write([]byte(vtf.Name))
--					f.fs.Write(colonBytes)
--				}
--				f.format(f.unpackValue(v.Field(i)))
--			}
--		}
--		f.depth--
--		f.fs.Write(closeBraceBytes)
+-// embedwrap is used to test embedded structures.
+-type embedwrap struct {
+-	*embed
+-	e *embed
+-}
 -
--	case reflect.Uintptr:
--		printHexPtr(f.fs, uintptr(v.Uint()))
+-// panicer is used to intentionally cause a panic for testing spew properly
+-// handles them
+-type panicer int
 -
--	case reflect.UnsafePointer, reflect.Chan, reflect.Func:
--		printHexPtr(f.fs, v.Pointer())
+-func (p panicer) String() string {
+-	panic("test panic")
+-}
 -
--	// There were not any other types at the time this code was written, but
--	// fall back to letting the default fmt package handle it if any get added.
--	default:
--		format := f.buildDefaultFormat()
--		if v.CanInterface() {
--			fmt.Fprintf(f.fs, format, v.Interface())
+-// customError is used to test custom error interface invocation.
+-type customError int
+-
+-func (e customError) Error() string {
+-	return fmt.Sprintf("error: %d", int(e))
+-}
+-
+-// stringizeWants converts a slice of wanted test output into a format suitable
+-// for a test error message.
+-func stringizeWants(wants []string) string {
+-	s := ""
+-	for i, want := range wants {
+-		if i > 0 {
+-			s += fmt.Sprintf("want%d: %s", i+1, want)
 -		} else {
--			fmt.Fprintf(f.fs, format, v.String())
+-			s += "want: " + want
 -		}
 -	}
+-	return s
 -}
 -
--// Format satisfies the fmt.Formatter interface. See NewFormatter for usage
--// details.
--func (f *formatState) Format(fs fmt.State, verb rune) {
--	f.fs = fs
+-// testFailed returns whether or not a test failed by checking if the result
+-// of the test is in the slice of wanted strings.
+-func testFailed(result string, wants []string) bool {
+-	for _, want := range wants {
+-		if result == want {
+-			return false
+-		}
+-	}
+-	return true
+-}
 -
--	// Use standard formatting for verbs that are not v.
--	if verb != 'v' {
--		format := f.constructOrigFormat(verb)
--		fmt.Fprintf(fs, format, f.value)
--		return
+-// TestSortValues ensures the sort functionality for relect.Value based sorting
+-// works as intended.
+-func TestSortValues(t *testing.T) {
+-	getInterfaces := func(values []reflect.Value) []interface{} {
+-		interfaces := []interface{}{}
+-		for _, v := range values {
+-			interfaces = append(interfaces, v.Interface())
+-		}
+-		return interfaces
 -	}
 -
--	if f.value == nil {
--		if fs.Flag('#') {
--			fs.Write(interfaceBytes)
+-	v := reflect.ValueOf
+-
+-	a := v("a")
+-	b := v("b")
+-	c := v("c")
+-	embedA := v(embed{"a"})
+-	embedB := v(embed{"b"})
+-	embedC := v(embed{"c"})
+-	tests := []struct {
+-		input    []reflect.Value
+-		expected []reflect.Value
+-	}{
+-		// No values.
+-		{
+-			[]reflect.Value{},
+-			[]reflect.Value{},
+-		},
+-		// Bools.
+-		{
+-			[]reflect.Value{v(false), v(true), v(false)},
+-			[]reflect.Value{v(false), v(false), v(true)},
+-		},
+-		// Ints.
+-		{
+-			[]reflect.Value{v(2), v(1), v(3)},
+-			[]reflect.Value{v(1), v(2), v(3)},
+-		},
+-		// Uints.
+-		{
+-			[]reflect.Value{v(uint8(2)), v(uint8(1)), v(uint8(3))},
+-			[]reflect.Value{v(uint8(1)), v(uint8(2)), v(uint8(3))},
+-		},
+-		// Floats.
+-		{
+-			[]reflect.Value{v(2.0), v(1.0), v(3.0)},
+-			[]reflect.Value{v(1.0), v(2.0), v(3.0)},
+-		},
+-		// Strings.
+-		{
+-			[]reflect.Value{b, a, c},
+-			[]reflect.Value{a, b, c},
+-		},
+-		// Uintptrs.
+-		{
+-			[]reflect.Value{v(uintptr(2)), v(uintptr(1)), v(uintptr(3))},
+-			[]reflect.Value{v(uintptr(1)), v(uintptr(2)), v(uintptr(3))},
+-		},
+-		// Invalid.
+-		{
+-			[]reflect.Value{embedB, embedA, embedC},
+-			[]reflect.Value{embedB, embedA, embedC},
+-		},
+-	}
+-	for _, test := range tests {
+-		spew.SortValues(test.input)
+-		// reflect.DeepEqual cannot really make sense of reflect.Value,
+-		// probably because of all the pointer tricks. For instance,
+-		// v(2.0) != v(2.0) on a 32-bits system. Turn them into interface{}
+-		// instead.
+-		input := getInterfaces(test.input)
+-		expected := getInterfaces(test.expected)
+-		if !reflect.DeepEqual(input, expected) {
+-			t.Errorf("Sort mismatch:\n %v != %v", input, expected)
 -		}
--		fs.Write(nilAngleBytes)
--		return
 -	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/config.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/config.go
+deleted file mode 100644
+index e516675..0000000
+--- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/config.go
++++ /dev/null
+@@ -1,288 +0,0 @@
+-/*
+- * Copyright (c) 2013 Dave Collins <dave at davec.name>
+- *
+- * Permission to use, copy, modify, and distribute this software for any
+- * purpose with or without fee is hereby granted, provided that the above
+- * copyright notice and this permission notice appear in all copies.
+- *
+- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+- */
 -
--	f.format(reflect.ValueOf(f.value))
+-package spew
+-
+-import (
+-	"bytes"
+-	"fmt"
+-	"io"
+-	"os"
+-)
+-
+-// ConfigState houses the configuration options used by spew to format and
+-// display values.  There is a global instance, Config, that is used to control
+-// all top-level Formatter and Dump functionality.  Each ConfigState instance
+-// provides methods equivalent to the top-level functions.
+-//
+-// The zero value for ConfigState provides no indentation.  You would typically
+-// want to set it to a space or a tab.
+-//
+-// Alternatively, you can use NewDefaultConfig to get a ConfigState instance
+-// with default settings.  See the documentation of NewDefaultConfig for default
+-// values.
+-type ConfigState struct {
+-	// Indent specifies the string to use for each indentation level.  The
+-	// global config instance that all top-level functions use set this to a
+-	// single space by default.  If you would like more indentation, you might
+-	// set this to a tab with "\t" or perhaps two spaces with "  ".
+-	Indent string
+-
+-	// MaxDepth controls the maximum number of levels to descend into nested
+-	// data structures.  The default, 0, means there is no limit.
+-	//
+-	// NOTE: Circular data structures are properly detected, so it is not
+-	// necessary to set this value unless you specifically want to limit deeply
+-	// nested data structures.
+-	MaxDepth int
+-
+-	// DisableMethods specifies whether or not error and Stringer interfaces are
+-	// invoked for types that implement them.
+-	DisableMethods bool
+-
+-	// DisablePointerMethods specifies whether or not to check for and invoke
+-	// error and Stringer interfaces on types which only accept a pointer
+-	// receiver when the current type is not a pointer.
+-	//
+-	// NOTE: This might be an unsafe action since calling one of these methods
+-	// with a pointer receiver could technically mutate the value, however,
+-	// in practice, types which choose to satisify an error or Stringer
+-	// interface with a pointer receiver should not be mutating their state
+-	// inside these interface methods.
+-	DisablePointerMethods bool
+-
+-	// ContinueOnMethod specifies whether or not recursion should continue once
+-	// a custom error or Stringer interface is invoked.  The default, false,
+-	// means it will print the results of invoking the custom error or Stringer
+-	// interface and return immediately instead of continuing to recurse into
+-	// the internals of the data type.
+-	//
+-	// NOTE: This flag does not have any effect if method invocation is disabled
+-	// via the DisableMethods or DisablePointerMethods options.
+-	ContinueOnMethod bool
+-
+-	// SortKeys specifies map keys should be sorted before being printed. Use
+-	// this to have a more deterministic, diffable output.  Note that only
+-	// native types (bool, int, uint, floats, uintptr and string) are supported
+-	// with other types sorted according to the reflect.Value.String() output
+-	// which guarantees display stability.
+-	SortKeys bool
 -}
 -
--// newFormatter is a helper function to consolidate the logic from the various
--// public methods which take varying config states.
--func newFormatter(cs *ConfigState, v interface{}) fmt.Formatter {
--	fs := &formatState{value: v, cs: cs}
--	fs.pointers = make(map[uintptr]int)
--	return fs
+-// Config is the active configuration of the top-level functions.
+-// The configuration can be changed by modifying the contents of spew.Config.
+-var Config = ConfigState{Indent: " "}
+-
+-// Errorf is a wrapper for fmt.Errorf that treats each argument as if it were
+-// passed with a Formatter interface returned by c.NewFormatter.  It returns
+-// the formatted string as a value that satisfies error.  See NewFormatter
+-// for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Errorf(format, c.NewFormatter(a), c.NewFormatter(b))
+-func (c *ConfigState) Errorf(format string, a ...interface{}) (err error) {
+-	return fmt.Errorf(format, c.convertArgs(a)...)
+-}
+-
+-// Fprint is a wrapper for fmt.Fprint that treats each argument as if it were
+-// passed with a Formatter interface returned by c.NewFormatter.  It returns
+-// the number of bytes written and any write error encountered.  See
+-// NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Fprint(w, c.NewFormatter(a), c.NewFormatter(b))
+-func (c *ConfigState) Fprint(w io.Writer, a ...interface{}) (n int, err error) {
+-	return fmt.Fprint(w, c.convertArgs(a)...)
+-}
+-
+-// Fprintf is a wrapper for fmt.Fprintf that treats each argument as if it were
+-// passed with a Formatter interface returned by c.NewFormatter.  It returns
+-// the number of bytes written and any write error encountered.  See
+-// NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Fprintf(w, format, c.NewFormatter(a), c.NewFormatter(b))
+-func (c *ConfigState) Fprintf(w io.Writer, format string, a ...interface{}) (n int, err error) {
+-	return fmt.Fprintf(w, format, c.convertArgs(a)...)
+-}
+-
+-// Fprintln is a wrapper for fmt.Fprintln that treats each argument as if it
+-// passed with a Formatter interface returned by c.NewFormatter.  See
+-// NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Fprintln(w, c.NewFormatter(a), c.NewFormatter(b))
+-func (c *ConfigState) Fprintln(w io.Writer, a ...interface{}) (n int, err error) {
+-	return fmt.Fprintln(w, c.convertArgs(a)...)
+-}
+-
+-// Print is a wrapper for fmt.Print that treats each argument as if it were
+-// passed with a Formatter interface returned by c.NewFormatter.  It returns
+-// the number of bytes written and any write error encountered.  See
+-// NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Print(c.NewFormatter(a), c.NewFormatter(b))
+-func (c *ConfigState) Print(a ...interface{}) (n int, err error) {
+-	return fmt.Print(c.convertArgs(a)...)
+-}
+-
+-// Printf is a wrapper for fmt.Printf that treats each argument as if it were
+-// passed with a Formatter interface returned by c.NewFormatter.  It returns
+-// the number of bytes written and any write error encountered.  See
+-// NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Printf(format, c.NewFormatter(a), c.NewFormatter(b))
+-func (c *ConfigState) Printf(format string, a ...interface{}) (n int, err error) {
+-	return fmt.Printf(format, c.convertArgs(a)...)
+-}
+-
+-// Println is a wrapper for fmt.Println that treats each argument as if it were
+-// passed with a Formatter interface returned by c.NewFormatter.  It returns
+-// the number of bytes written and any write error encountered.  See
+-// NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Println(c.NewFormatter(a), c.NewFormatter(b))
+-func (c *ConfigState) Println(a ...interface{}) (n int, err error) {
+-	return fmt.Println(c.convertArgs(a)...)
+-}
+-
+-// Sprint is a wrapper for fmt.Sprint that treats each argument as if it were
+-// passed with a Formatter interface returned by c.NewFormatter.  It returns
+-// the resulting string.  See NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Sprint(c.NewFormatter(a), c.NewFormatter(b))
+-func (c *ConfigState) Sprint(a ...interface{}) string {
+-	return fmt.Sprint(c.convertArgs(a)...)
+-}
+-
+-// Sprintf is a wrapper for fmt.Sprintf that treats each argument as if it were
+-// passed with a Formatter interface returned by c.NewFormatter.  It returns
+-// the resulting string.  See NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Sprintf(format, c.NewFormatter(a), c.NewFormatter(b))
+-func (c *ConfigState) Sprintf(format string, a ...interface{}) string {
+-	return fmt.Sprintf(format, c.convertArgs(a)...)
+-}
+-
+-// Sprintln is a wrapper for fmt.Sprintln that treats each argument as if it
+-// were passed with a Formatter interface returned by c.NewFormatter.  It
+-// returns the resulting string.  See NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Sprintln(c.NewFormatter(a), c.NewFormatter(b))
+-func (c *ConfigState) Sprintln(a ...interface{}) string {
+-	return fmt.Sprintln(c.convertArgs(a)...)
 -}
 -
 -/*
@@ -43606,7 +44933,7 @@ index b6b1fb0..0000000
 -types similar to the standard %v format specifier.
 -
 -The custom formatter only responds to the %v (most compact), %+v (adds pointer
--addresses), %#v (adds types), or %#+v (adds types and pointer addresses) verb
+-addresses), %#v (adds types), and %#+v (adds types and pointer addresses) verb
 -combinations.  Any other verbs such as %x and %q will be sent to the the
 -standard fmt package for formatting.  In addition, the custom formatter ignores
 -the width and precision arguments (however they will still work on the format
@@ -43614,17 +44941,81 @@ index b6b1fb0..0000000
 -
 -Typically this function shouldn't be called directly.  It is much easier to make
 -use of the custom formatter by calling one of the convenience functions such as
--Printf, Println, or Fprintf.
+-c.Printf, c.Println, or c.Printf.
 -*/
--func NewFormatter(v interface{}) fmt.Formatter {
--	return newFormatter(&Config, v)
+-func (c *ConfigState) NewFormatter(v interface{}) fmt.Formatter {
+-	return newFormatter(c, v)
 -}
-diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/format_test.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/format_test.go
+-
+-// Fdump formats and displays the passed arguments to io.Writer w.  It formats
+-// exactly the same as Dump.
+-func (c *ConfigState) Fdump(w io.Writer, a ...interface{}) {
+-	fdump(c, w, a...)
+-}
+-
+-/*
+-Dump displays the passed parameters to standard out with newlines, customizable
+-indentation, and additional debug information such as complete types and all
+-pointer addresses used to indirect to the final value.  It provides the
+-following features over the built-in printing facilities provided by the fmt
+-package:
+-
+-	* Pointers are dereferenced and followed
+-	* Circular data structures are detected and handled properly
+-	* Custom Stringer/error interfaces are optionally invoked, including
+-	  on unexported types
+-	* Custom types which only implement the Stringer/error interfaces via
+-	  a pointer receiver are optionally invoked when passing non-pointer
+-	  variables
+-	* Byte arrays and slices are dumped like the hexdump -C command which
+-	  includes offsets, byte values in hex, and ASCII output
+-
+-The configuration options are controlled by modifying the public members
+-of c.  See ConfigState for options documentation.
+-
+-See Fdump if you would prefer dumping to an arbitrary io.Writer or Sdump to
+-get the formatted result as a string.
+-*/
+-func (c *ConfigState) Dump(a ...interface{}) {
+-	fdump(c, os.Stdout, a...)
+-}
+-
+-// Sdump returns a string with the passed arguments formatted exactly the same
+-// as Dump.
+-func (c *ConfigState) Sdump(a ...interface{}) string {
+-	var buf bytes.Buffer
+-	fdump(c, &buf, a...)
+-	return buf.String()
+-}
+-
+-// convertArgs accepts a slice of arguments and returns a slice of the same
+-// length with each argument converted to a spew Formatter interface using
+-// the ConfigState associated with s.
+-func (c *ConfigState) convertArgs(args []interface{}) (formatters []interface{}) {
+-	formatters = make([]interface{}, len(args))
+-	for index, arg := range args {
+-		formatters[index] = newFormatter(c, arg)
+-	}
+-	return formatters
+-}
+-
+-// NewDefaultConfig returns a ConfigState with the following default settings.
+-//
+-// 	Indent: " "
+-// 	MaxDepth: 0
+-// 	DisableMethods: false
+-// 	DisablePointerMethods: false
+-// 	ContinueOnMethod: false
+-// 	SortKeys: false
+-func NewDefaultConfig() *ConfigState {
+-	return &ConfigState{Indent: " "}
+-}
+diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/doc.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/doc.go
 deleted file mode 100644
-index 80c5ef9..0000000
---- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/format_test.go
+index a0d73ac..0000000
+--- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/doc.go
 +++ /dev/null
-@@ -1,1483 +0,0 @@
+@@ -1,196 +0,0 @@
 -/*
 - * Copyright (c) 2013 Dave Collins <dave at davec.name>
 - *
@@ -43642,22 +45033,732 @@ index 80c5ef9..0000000
 - */
 -
 -/*
--Test Summary:
--NOTE: For each test, a nil pointer, a single pointer and double pointer to the
--base test element are also tested to ensure proper indirection across all types.
+-Package spew implements a deep pretty printer for Go data structures to aid in
+-debugging.
 -
--- Max int8, int16, int32, int64, int
--- Max uint8, uint16, uint32, uint64, uint
--- Boolean true and false
--- Standard complex64 and complex128
--- Array containing standard ints
--- Array containing type with custom formatter on pointer receiver only
--- Array containing interfaces
--- Slice containing standard float32 values
--- Slice containing type with custom formatter on pointer receiver only
--- Slice containing interfaces
--- Nil slice
--- Standard string
+-A quick overview of the additional features spew provides over the built-in
+-printing facilities for Go data types are as follows:
+-
+-	* Pointers are dereferenced and followed
+-	* Circular data structures are detected and handled properly
+-	* Custom Stringer/error interfaces are optionally invoked, including
+-	  on unexported types
+-	* Custom types which only implement the Stringer/error interfaces via
+-	  a pointer receiver are optionally invoked when passing non-pointer
+-	  variables
+-	* Byte arrays and slices are dumped like the hexdump -C command which
+-	  includes offsets, byte values in hex, and ASCII output (only when using
+-	  Dump style)
+-
+-There are two different approaches spew allows for dumping Go data structures:
+-
+-	* Dump style which prints with newlines, customizable indentation,
+-	  and additional debug information such as types and all pointer addresses
+-	  used to indirect to the final value
+-	* A custom Formatter interface that integrates cleanly with the standard fmt
+-	  package and replaces %v, %+v, %#v, and %#+v to provide inline printing
+-	  similar to the default %v while providing the additional functionality
+-	  outlined above and passing unsupported format verbs such as %x and %q
+-	  along to fmt
+-
+-Quick Start
+-
+-This section demonstrates how to quickly get started with spew.  See the
+-sections below for further details on formatting and configuration options.
+-
+-To dump a variable with full newlines, indentation, type, and pointer
+-information use Dump, Fdump, or Sdump:
+-	spew.Dump(myVar1, myVar2, ...)
+-	spew.Fdump(someWriter, myVar1, myVar2, ...)
+-	str := spew.Sdump(myVar1, myVar2, ...)
+-
+-Alternatively, if you would prefer to use format strings with a compacted inline
+-printing style, use the convenience wrappers Printf, Fprintf, etc with
+-%v (most compact), %+v (adds pointer addresses), %#v (adds types), or
+-%#+v (adds types and pointer addresses):
+-	spew.Printf("myVar1: %v -- myVar2: %+v", myVar1, myVar2)
+-	spew.Printf("myVar3: %#v -- myVar4: %#+v", myVar3, myVar4)
+-	spew.Fprintf(someWriter, "myVar1: %v -- myVar2: %+v", myVar1, myVar2)
+-	spew.Fprintf(someWriter, "myVar3: %#v -- myVar4: %#+v", myVar3, myVar4)
+-
+-Configuration Options
+-
+-Configuration of spew is handled by fields in the ConfigState type.  For
+-convenience, all of the top-level functions use a global state available
+-via the spew.Config global.
+-
+-It is also possible to create a ConfigState instance that provides methods
+-equivalent to the top-level functions.  This allows concurrent configuration
+-options.  See the ConfigState documentation for more details.
+-
+-The following configuration options are available:
+-	* Indent
+-		String to use for each indentation level for Dump functions.
+-		It is a single space by default.  A popular alternative is "\t".
+-
+-	* MaxDepth
+-		Maximum number of levels to descend into nested data structures.
+-		There is no limit by default.
+-
+-	* DisableMethods
+-		Disables invocation of error and Stringer interface methods.
+-		Method invocation is enabled by default.
+-
+-	* DisablePointerMethods
+-		Disables invocation of error and Stringer interface methods on types
+-		which only accept pointer receivers from non-pointer variables.
+-		Pointer method invocation is enabled by default.
+-
+-	* ContinueOnMethod
+-		Enables recursion into types after invoking error and Stringer interface
+-		methods. Recursion after method invocation is disabled by default.
+-
+-	* SortKeys
+-		Specifies map keys should be sorted before being printed. Use
+-		this to have a more deterministic, diffable output.  Note that
+-		only native types (bool, int, uint, floats, uintptr and string)
+-		are supported with other types sorted according to the
+-		reflect.Value.String() output which guarantees display stability.
+-		Natural map order is used by default.
+-
+-Dump Usage
+-
+-Simply call spew.Dump with a list of variables you want to dump:
+-
+-	spew.Dump(myVar1, myVar2, ...)
+-
+-You may also call spew.Fdump if you would prefer to output to an arbitrary
+-io.Writer.  For example, to dump to standard error:
+-
+-	spew.Fdump(os.Stderr, myVar1, myVar2, ...)
+-
+-A third option is to call spew.Sdump to get the formatted output as a string:
+-
+-	str := spew.Sdump(myVar1, myVar2, ...)
+-
+-Sample Dump Output
+-
+-See the Dump example for details on the setup of the types and variables being
+-shown here.
+-
+-	(main.Foo) {
+-	 unexportedField: (*main.Bar)(0xf84002e210)({
+-	  flag: (main.Flag) flagTwo,
+-	  data: (uintptr) <nil>
+-	 }),
+-	 ExportedField: (map[interface {}]interface {}) (len=1) {
+-	  (string) (len=3) "one": (bool) true
+-	 }
+-	}
+-
+-Byte (and uint8) arrays and slices are displayed uniquely like the hexdump -C
+-command as shown.
+-	([]uint8) (len=32 cap=32) {
+-	 00000000  11 12 13 14 15 16 17 18  19 1a 1b 1c 1d 1e 1f 20  |............... |
+-	 00000010  21 22 23 24 25 26 27 28  29 2a 2b 2c 2d 2e 2f 30  |!"#$%&'()*+,-./0|
+-	 00000020  31 32                                             |12|
+-	}
+-
+-Custom Formatter
+-
+-Spew provides a custom formatter that implements the fmt.Formatter interface
+-so that it integrates cleanly with standard fmt package printing functions. The
+-formatter is useful for inline printing of smaller data types similar to the
+-standard %v format specifier.
+-
+-The custom formatter only responds to the %v (most compact), %+v (adds pointer
+-addresses), %#v (adds types), or %#+v (adds types and pointer addresses) verb
+-combinations.  Any other verbs such as %x and %q will be sent to the the
+-standard fmt package for formatting.  In addition, the custom formatter ignores
+-the width and precision arguments (however they will still work on the format
+-specifiers not handled by the custom formatter).
+-
+-Custom Formatter Usage
+-
+-The simplest way to make use of the spew custom formatter is to call one of the
+-convenience functions such as spew.Printf, spew.Println, or spew.Printf.  The
+-functions have syntax you are most likely already familiar with:
+-
+-	spew.Printf("myVar1: %v -- myVar2: %+v", myVar1, myVar2)
+-	spew.Printf("myVar3: %#v -- myVar4: %#+v", myVar3, myVar4)
+-	spew.Println(myVar, myVar2)
+-	spew.Fprintf(os.Stderr, "myVar1: %v -- myVar2: %+v", myVar1, myVar2)
+-	spew.Fprintf(os.Stderr, "myVar3: %#v -- myVar4: %#+v", myVar3, myVar4)
+-
+-See the Index for the full list convenience functions.
+-
+-Sample Formatter Output
+-
+-Double pointer to a uint8:
+-	  %v: <**>5
+-	 %+v: <**>(0xf8400420d0->0xf8400420c8)5
+-	 %#v: (**uint8)5
+-	%#+v: (**uint8)(0xf8400420d0->0xf8400420c8)5
+-
+-Pointer to circular struct with a uint8 field and a pointer to itself:
+-	  %v: <*>{1 <*><shown>}
+-	 %+v: <*>(0xf84003e260){ui8:1 c:<*>(0xf84003e260)<shown>}
+-	 %#v: (*main.circular){ui8:(uint8)1 c:(*main.circular)<shown>}
+-	%#+v: (*main.circular)(0xf84003e260){ui8:(uint8)1 c:(*main.circular)(0xf84003e260)<shown>}
+-
+-See the Printf example for details on the setup of variables being shown
+-here.
+-
+-Errors
+-
+-Since it is possible for custom Stringer/error interfaces to panic, spew
+-detects them and handles them internally by printing the panic information
+-inline with the output.  Since spew is intended to provide deep pretty printing
+-capabilities on structures, it intentionally does not return any errors.
+-*/
+-package spew
+diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dump.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dump.go
+deleted file mode 100644
+index 02d4c9d..0000000
+--- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dump.go
++++ /dev/null
+@@ -1,500 +0,0 @@
+-/*
+- * Copyright (c) 2013 Dave Collins <dave at davec.name>
+- *
+- * Permission to use, copy, modify, and distribute this software for any
+- * purpose with or without fee is hereby granted, provided that the above
+- * copyright notice and this permission notice appear in all copies.
+- *
+- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+- */
+-
+-package spew
+-
+-import (
+-	"bytes"
+-	"encoding/hex"
+-	"fmt"
+-	"io"
+-	"os"
+-	"reflect"
+-	"regexp"
+-	"strconv"
+-	"strings"
+-)
+-
+-var (
+-	// uint8Type is a reflect.Type representing a uint8.  It is used to
+-	// convert cgo types to uint8 slices for hexdumping.
+-	uint8Type = reflect.TypeOf(uint8(0))
+-
+-	// cCharRE is a regular expression that matches a cgo char.
+-	// It is used to detect character arrays to hexdump them.
+-	cCharRE = regexp.MustCompile("^.*\\._Ctype_char$")
+-
+-	// cUnsignedCharRE is a regular expression that matches a cgo unsigned
+-	// char.  It is used to detect unsigned character arrays to hexdump
+-	// them.
+-	cUnsignedCharRE = regexp.MustCompile("^.*\\._Ctype_unsignedchar$")
+-
+-	// cUint8tCharRE is a regular expression that matches a cgo uint8_t.
+-	// It is used to detect uint8_t arrays to hexdump them.
+-	cUint8tCharRE = regexp.MustCompile("^.*\\._Ctype_uint8_t$")
+-)
+-
+-// dumpState contains information about the state of a dump operation.
+-type dumpState struct {
+-	w                io.Writer
+-	depth            int
+-	pointers         map[uintptr]int
+-	ignoreNextType   bool
+-	ignoreNextIndent bool
+-	cs               *ConfigState
+-}
+-
+-// indent performs indentation according to the depth level and cs.Indent
+-// option.
+-func (d *dumpState) indent() {
+-	if d.ignoreNextIndent {
+-		d.ignoreNextIndent = false
+-		return
+-	}
+-	d.w.Write(bytes.Repeat([]byte(d.cs.Indent), d.depth))
+-}
+-
+-// unpackValue returns values inside of non-nil interfaces when possible.
+-// This is useful for data types like structs, arrays, slices, and maps which
+-// can contain varying types packed inside an interface.
+-func (d *dumpState) unpackValue(v reflect.Value) reflect.Value {
+-	if v.Kind() == reflect.Interface && !v.IsNil() {
+-		v = v.Elem()
+-	}
+-	return v
+-}
+-
+-// dumpPtr handles formatting of pointers by indirecting them as necessary.
+-func (d *dumpState) dumpPtr(v reflect.Value) {
+-	// Remove pointers at or below the current depth from map used to detect
+-	// circular refs.
+-	for k, depth := range d.pointers {
+-		if depth >= d.depth {
+-			delete(d.pointers, k)
+-		}
+-	}
+-
+-	// Keep list of all dereferenced pointers to show later.
+-	pointerChain := make([]uintptr, 0)
+-
+-	// Figure out how many levels of indirection there are by dereferencing
+-	// pointers and unpacking interfaces down the chain while detecting circular
+-	// references.
+-	nilFound := false
+-	cycleFound := false
+-	indirects := 0
+-	ve := v
+-	for ve.Kind() == reflect.Ptr {
+-		if ve.IsNil() {
+-			nilFound = true
+-			break
+-		}
+-		indirects++
+-		addr := ve.Pointer()
+-		pointerChain = append(pointerChain, addr)
+-		if pd, ok := d.pointers[addr]; ok && pd < d.depth {
+-			cycleFound = true
+-			indirects--
+-			break
+-		}
+-		d.pointers[addr] = d.depth
+-
+-		ve = ve.Elem()
+-		if ve.Kind() == reflect.Interface {
+-			if ve.IsNil() {
+-				nilFound = true
+-				break
+-			}
+-			ve = ve.Elem()
+-		}
+-	}
+-
+-	// Display type information.
+-	d.w.Write(openParenBytes)
+-	d.w.Write(bytes.Repeat(asteriskBytes, indirects))
+-	d.w.Write([]byte(ve.Type().String()))
+-	d.w.Write(closeParenBytes)
+-
+-	// Display pointer information.
+-	if len(pointerChain) > 0 {
+-		d.w.Write(openParenBytes)
+-		for i, addr := range pointerChain {
+-			if i > 0 {
+-				d.w.Write(pointerChainBytes)
+-			}
+-			printHexPtr(d.w, addr)
+-		}
+-		d.w.Write(closeParenBytes)
+-	}
+-
+-	// Display dereferenced value.
+-	d.w.Write(openParenBytes)
+-	switch {
+-	case nilFound == true:
+-		d.w.Write(nilAngleBytes)
+-
+-	case cycleFound == true:
+-		d.w.Write(circularBytes)
+-
+-	default:
+-		d.ignoreNextType = true
+-		d.dump(ve)
+-	}
+-	d.w.Write(closeParenBytes)
+-}
+-
+-// dumpSlice handles formatting of arrays and slices.  Byte (uint8 under
+-// reflection) arrays and slices are dumped in hexdump -C fashion.
+-func (d *dumpState) dumpSlice(v reflect.Value) {
+-	// Determine whether this type should be hex dumped or not.  Also,
+-	// for types which should be hexdumped, try to use the underlying data
+-	// first, then fall back to trying to convert them to a uint8 slice.
+-	var buf []uint8
+-	doConvert := false
+-	doHexDump := false
+-	numEntries := v.Len()
+-	if numEntries > 0 {
+-		vt := v.Index(0).Type()
+-		vts := vt.String()
+-		switch {
+-		// C types that need to be converted.
+-		case cCharRE.MatchString(vts):
+-			fallthrough
+-		case cUnsignedCharRE.MatchString(vts):
+-			fallthrough
+-		case cUint8tCharRE.MatchString(vts):
+-			doConvert = true
+-
+-		// Try to use existing uint8 slices and fall back to converting
+-		// and copying if that fails.
+-		case vt.Kind() == reflect.Uint8:
+-			// We need an addressable interface to convert the type back
+-			// into a byte slice.  However, the reflect package won't give
+-			// us an interface on certain things like unexported struct
+-			// fields in order to enforce visibility rules.  We use unsafe
+-			// to bypass these restrictions since this package does not
+-			// mutate the values.
+-			vs := v
+-			if !vs.CanInterface() || !vs.CanAddr() {
+-				vs = unsafeReflectValue(vs)
+-			}
+-			vs = vs.Slice(0, numEntries)
+-
+-			// Use the existing uint8 slice if it can be type
+-			// asserted.
+-			iface := vs.Interface()
+-			if slice, ok := iface.([]uint8); ok {
+-				buf = slice
+-				doHexDump = true
+-				break
+-			}
+-
+-			// The underlying data needs to be converted if it can't
+-			// be type asserted to a uint8 slice.
+-			doConvert = true
+-		}
+-
+-		// Copy and convert the underlying type if needed.
+-		if doConvert && vt.ConvertibleTo(uint8Type) {
+-			// Convert and copy each element into a uint8 byte
+-			// slice.
+-			buf = make([]uint8, numEntries)
+-			for i := 0; i < numEntries; i++ {
+-				vv := v.Index(i)
+-				buf[i] = uint8(vv.Convert(uint8Type).Uint())
+-			}
+-			doHexDump = true
+-		}
+-	}
+-
+-	// Hexdump the entire slice as needed.
+-	if doHexDump {
+-		indent := strings.Repeat(d.cs.Indent, d.depth)
+-		str := indent + hex.Dump(buf)
+-		str = strings.Replace(str, "\n", "\n"+indent, -1)
+-		str = strings.TrimRight(str, d.cs.Indent)
+-		d.w.Write([]byte(str))
+-		return
+-	}
+-
+-	// Recursively call dump for each item.
+-	for i := 0; i < numEntries; i++ {
+-		d.dump(d.unpackValue(v.Index(i)))
+-		if i < (numEntries - 1) {
+-			d.w.Write(commaNewlineBytes)
+-		} else {
+-			d.w.Write(newlineBytes)
+-		}
+-	}
+-}
+-
+-// dump is the main workhorse for dumping a value.  It uses the passed reflect
+-// value to figure out what kind of object we are dealing with and formats it
+-// appropriately.  It is a recursive function, however circular data structures
+-// are detected and handled properly.
+-func (d *dumpState) dump(v reflect.Value) {
+-	// Handle invalid reflect values immediately.
+-	kind := v.Kind()
+-	if kind == reflect.Invalid {
+-		d.w.Write(invalidAngleBytes)
+-		return
+-	}
+-
+-	// Handle pointers specially.
+-	if kind == reflect.Ptr {
+-		d.indent()
+-		d.dumpPtr(v)
+-		return
+-	}
+-
+-	// Print type information unless already handled elsewhere.
+-	if !d.ignoreNextType {
+-		d.indent()
+-		d.w.Write(openParenBytes)
+-		d.w.Write([]byte(v.Type().String()))
+-		d.w.Write(closeParenBytes)
+-		d.w.Write(spaceBytes)
+-	}
+-	d.ignoreNextType = false
+-
+-	// Display length and capacity if the built-in len and cap functions
+-	// work with the value's kind and the len/cap itself is non-zero.
+-	valueLen, valueCap := 0, 0
+-	switch v.Kind() {
+-	case reflect.Array, reflect.Slice, reflect.Chan:
+-		valueLen, valueCap = v.Len(), v.Cap()
+-	case reflect.Map, reflect.String:
+-		valueLen = v.Len()
+-	}
+-	if valueLen != 0 || valueCap != 0 {
+-		d.w.Write(openParenBytes)
+-		if valueLen != 0 {
+-			d.w.Write(lenEqualsBytes)
+-			printInt(d.w, int64(valueLen), 10)
+-		}
+-		if valueCap != 0 {
+-			if valueLen != 0 {
+-				d.w.Write(spaceBytes)
+-			}
+-			d.w.Write(capEqualsBytes)
+-			printInt(d.w, int64(valueCap), 10)
+-		}
+-		d.w.Write(closeParenBytes)
+-		d.w.Write(spaceBytes)
+-	}
+-
+-	// Call Stringer/error interfaces if they exist and the handle methods flag
+-	// is enabled
+-	if !d.cs.DisableMethods {
+-		if (kind != reflect.Invalid) && (kind != reflect.Interface) {
+-			if handled := handleMethods(d.cs, d.w, v); handled {
+-				return
+-			}
+-		}
+-	}
+-
+-	switch kind {
+-	case reflect.Invalid:
+-		// Do nothing.  We should never get here since invalid has already
+-		// been handled above.
+-
+-	case reflect.Bool:
+-		printBool(d.w, v.Bool())
+-
+-	case reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64, reflect.Int:
+-		printInt(d.w, v.Int(), 10)
+-
+-	case reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uint:
+-		printUint(d.w, v.Uint(), 10)
+-
+-	case reflect.Float32:
+-		printFloat(d.w, v.Float(), 32)
+-
+-	case reflect.Float64:
+-		printFloat(d.w, v.Float(), 64)
+-
+-	case reflect.Complex64:
+-		printComplex(d.w, v.Complex(), 32)
+-
+-	case reflect.Complex128:
+-		printComplex(d.w, v.Complex(), 64)
+-
+-	case reflect.Slice:
+-		if v.IsNil() {
+-			d.w.Write(nilAngleBytes)
+-			break
+-		}
+-		fallthrough
+-
+-	case reflect.Array:
+-		d.w.Write(openBraceNewlineBytes)
+-		d.depth++
+-		if (d.cs.MaxDepth != 0) && (d.depth > d.cs.MaxDepth) {
+-			d.indent()
+-			d.w.Write(maxNewlineBytes)
+-		} else {
+-			d.dumpSlice(v)
+-		}
+-		d.depth--
+-		d.indent()
+-		d.w.Write(closeBraceBytes)
+-
+-	case reflect.String:
+-		d.w.Write([]byte(strconv.Quote(v.String())))
+-
+-	case reflect.Interface:
+-		// The only time we should get here is for nil interfaces due to
+-		// unpackValue calls.
+-		if v.IsNil() {
+-			d.w.Write(nilAngleBytes)
+-		}
+-
+-	case reflect.Ptr:
+-		// Do nothing.  We should never get here since pointers have already
+-		// been handled above.
+-
+-	case reflect.Map:
+-		d.w.Write(openBraceNewlineBytes)
+-		d.depth++
+-		if (d.cs.MaxDepth != 0) && (d.depth > d.cs.MaxDepth) {
+-			d.indent()
+-			d.w.Write(maxNewlineBytes)
+-		} else {
+-			numEntries := v.Len()
+-			keys := v.MapKeys()
+-			if d.cs.SortKeys {
+-				sortValues(keys)
+-			}
+-			for i, key := range keys {
+-				d.dump(d.unpackValue(key))
+-				d.w.Write(colonSpaceBytes)
+-				d.ignoreNextIndent = true
+-				d.dump(d.unpackValue(v.MapIndex(key)))
+-				if i < (numEntries - 1) {
+-					d.w.Write(commaNewlineBytes)
+-				} else {
+-					d.w.Write(newlineBytes)
+-				}
+-			}
+-		}
+-		d.depth--
+-		d.indent()
+-		d.w.Write(closeBraceBytes)
+-
+-	case reflect.Struct:
+-		d.w.Write(openBraceNewlineBytes)
+-		d.depth++
+-		if (d.cs.MaxDepth != 0) && (d.depth > d.cs.MaxDepth) {
+-			d.indent()
+-			d.w.Write(maxNewlineBytes)
+-		} else {
+-			vt := v.Type()
+-			numFields := v.NumField()
+-			for i := 0; i < numFields; i++ {
+-				d.indent()
+-				vtf := vt.Field(i)
+-				d.w.Write([]byte(vtf.Name))
+-				d.w.Write(colonSpaceBytes)
+-				d.ignoreNextIndent = true
+-				d.dump(d.unpackValue(v.Field(i)))
+-				if i < (numFields - 1) {
+-					d.w.Write(commaNewlineBytes)
+-				} else {
+-					d.w.Write(newlineBytes)
+-				}
+-			}
+-		}
+-		d.depth--
+-		d.indent()
+-		d.w.Write(closeBraceBytes)
+-
+-	case reflect.Uintptr:
+-		printHexPtr(d.w, uintptr(v.Uint()))
+-
+-	case reflect.UnsafePointer, reflect.Chan, reflect.Func:
+-		printHexPtr(d.w, v.Pointer())
+-
+-	// There were not any other types at the time this code was written, but
+-	// fall back to letting the default fmt package handle it in case any new
+-	// types are added.
+-	default:
+-		if v.CanInterface() {
+-			fmt.Fprintf(d.w, "%v", v.Interface())
+-		} else {
+-			fmt.Fprintf(d.w, "%v", v.String())
+-		}
+-	}
+-}
+-
+-// fdump is a helper function to consolidate the logic from the various public
+-// methods which take varying writers and config states.
+-func fdump(cs *ConfigState, w io.Writer, a ...interface{}) {
+-	for _, arg := range a {
+-		if arg == nil {
+-			w.Write(interfaceBytes)
+-			w.Write(spaceBytes)
+-			w.Write(nilAngleBytes)
+-			w.Write(newlineBytes)
+-			continue
+-		}
+-
+-		d := dumpState{w: w, cs: cs}
+-		d.pointers = make(map[uintptr]int)
+-		d.dump(reflect.ValueOf(arg))
+-		d.w.Write(newlineBytes)
+-	}
+-}
+-
+-// Fdump formats and displays the passed arguments to io.Writer w.  It formats
+-// exactly the same as Dump.
+-func Fdump(w io.Writer, a ...interface{}) {
+-	fdump(&Config, w, a...)
+-}
+-
+-// Sdump returns a string with the passed arguments formatted exactly the same
+-// as Dump.
+-func Sdump(a ...interface{}) string {
+-	var buf bytes.Buffer
+-	fdump(&Config, &buf, a...)
+-	return buf.String()
+-}
+-
+-/*
+-Dump displays the passed parameters to standard out with newlines, customizable
+-indentation, and additional debug information such as complete types and all
+-pointer addresses used to indirect to the final value.  It provides the
+-following features over the built-in printing facilities provided by the fmt
+-package:
+-
+-	* Pointers are dereferenced and followed
+-	* Circular data structures are detected and handled properly
+-	* Custom Stringer/error interfaces are optionally invoked, including
+-	  on unexported types
+-	* Custom types which only implement the Stringer/error interfaces via
+-	  a pointer receiver are optionally invoked when passing non-pointer
+-	  variables
+-	* Byte arrays and slices are dumped like the hexdump -C command which
+-	  includes offsets, byte values in hex, and ASCII output
+-
+-The configuration options are controlled by an exported package global,
+-spew.Config.  See ConfigState for options documentation.
+-
+-See Fdump if you would prefer dumping to an arbitrary io.Writer or Sdump to
+-get the formatted result as a string.
+-*/
+-func Dump(a ...interface{}) {
+-	fdump(&Config, os.Stdout, a...)
+-}
+diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dump_test.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dump_test.go
+deleted file mode 100644
+index f1a5644..0000000
+--- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dump_test.go
++++ /dev/null
+@@ -1,978 +0,0 @@
+-/*
+- * Copyright (c) 2013 Dave Collins <dave at davec.name>
+- *
+- * Permission to use, copy, modify, and distribute this software for any
+- * purpose with or without fee is hereby granted, provided that the above
+- * copyright notice and this permission notice appear in all copies.
+- *
+- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+- */
+-
+-/*
+-Test Summary:
+-NOTE: For each test, a nil pointer, a single pointer and double pointer to the
+-base test element are also tested to ensure proper indirection across all types.
+-
+-- Max int8, int16, int32, int64, int
+-- Max uint8, uint16, uint32, uint64, uint
+-- Boolean true and false
+-- Standard complex64 and complex128
+-- Array containing standard ints
+-- Array containing type with custom formatter on pointer receiver only
+-- Array containing interfaces
+-- Array containing bytes
+-- Slice containing standard float32 values
+-- Slice containing type with custom formatter on pointer receiver only
+-- Slice containing interfaces
+-- Slice containing bytes
+-- Nil slice
+-- Standard string
 -- Nil interface
 -- Sub-interface
 -- Map with string keys and int vals
@@ -43682,13 +45783,6 @@ index 80c5ef9..0000000
 -- Structs that are circular through cross referencing
 -- Structs that are indirectly circular
 -- Type that panics in its Stringer interface
--- Type that has a custom Error interface
--- %x passthrough with uint
--- %#x passthrough with uint
--- %f passthrough with precision
--- %f passthrough with width and precision
--- %d passthrough with width
--- %q passthrough with string
 -*/
 -
 -package spew_test
@@ -43701,24 +45795,23 @@ index 80c5ef9..0000000
 -	"unsafe"
 -)
 -
--// formatterTest is used to describe a test to be perfomed against NewFormatter.
--type formatterTest struct {
--	format string
--	in     interface{}
--	wants  []string
+-// dumpTest is used to describe a test to be perfomed against the Dump method.
+-type dumpTest struct {
+-	in    interface{}
+-	wants []string
 -}
 -
--// formatterTests houses all of the tests to be performed against NewFormatter.
--var formatterTests = make([]formatterTest, 0)
+-// dumpTests houses all of the tests to be performed against the Dump method.
+-var dumpTests = make([]dumpTest, 0)
 -
--// addFormatterTest is a helper method to append the passed input and desired
--// result to formatterTests.
--func addFormatterTest(format string, in interface{}, wants ...string) {
--	test := formatterTest{format, in, wants}
--	formatterTests = append(formatterTests, test)
+-// addDumpTest is a helper method to append the passed input and desired result
+-// to dumpTests
+-func addDumpTest(in interface{}, wants ...string) {
+-	test := dumpTest{in, wants}
+-	dumpTests = append(dumpTests, test)
 -}
 -
--func addIntFormatterTests() {
+-func addIntDumpTests() {
 -	// Max int8.
 -	v := int8(127)
 -	nv := (*int8)(nil)
@@ -43727,22 +45820,10 @@ index 80c5ef9..0000000
 -	pvAddr := fmt.Sprintf("%p", &pv)
 -	vt := "int8"
 -	vs := "127"
--	addFormatterTest("%v", v, vs)
--	addFormatterTest("%v", pv, "<*>"+vs)
--	addFormatterTest("%v", &pv, "<**>"+vs)
--	addFormatterTest("%v", nv, "<nil>")
--	addFormatterTest("%+v", v, vs)
--	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
--	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%#v", v, "("+vt+")"+vs)
--	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
--	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
--	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
--	addFormatterTest("%#+v", v, "("+vt+")"+vs)
--	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
--	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-	addDumpTest(v, "("+vt+") "+vs+"\n")
+-	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
+-	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
+-	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
 -
 -	// Max int16.
 -	v2 := int16(32767)
@@ -43752,22 +45833,10 @@ index 80c5ef9..0000000
 -	pv2Addr := fmt.Sprintf("%p", &pv2)
 -	v2t := "int16"
 -	v2s := "32767"
--	addFormatterTest("%v", v2, v2s)
--	addFormatterTest("%v", pv2, "<*>"+v2s)
--	addFormatterTest("%v", &pv2, "<**>"+v2s)
--	addFormatterTest("%v", nv2, "<nil>")
--	addFormatterTest("%+v", v2, v2s)
--	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
--	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%+v", nv2, "<nil>")
--	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
--	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
--	addFormatterTest("%#v", nv2, "(*"+v2t+")"+"<nil>")
--	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", nv2, "(*"+v2t+")"+"<nil>")
+-	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
+-	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
+-	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
+-	addDumpTest(nv2, "(*"+v2t+")(<nil>)\n")
 -
 -	// Max int32.
 -	v3 := int32(2147483647)
@@ -43777,22 +45846,10 @@ index 80c5ef9..0000000
 -	pv3Addr := fmt.Sprintf("%p", &pv3)
 -	v3t := "int32"
 -	v3s := "2147483647"
--	addFormatterTest("%v", v3, v3s)
--	addFormatterTest("%v", pv3, "<*>"+v3s)
--	addFormatterTest("%v", &pv3, "<**>"+v3s)
--	addFormatterTest("%v", nv3, "<nil>")
--	addFormatterTest("%+v", v3, v3s)
--	addFormatterTest("%+v", pv3, "<*>("+v3Addr+")"+v3s)
--	addFormatterTest("%+v", &pv3, "<**>("+pv3Addr+"->"+v3Addr+")"+v3s)
--	addFormatterTest("%+v", nv3, "<nil>")
--	addFormatterTest("%#v", v3, "("+v3t+")"+v3s)
--	addFormatterTest("%#v", pv3, "(*"+v3t+")"+v3s)
--	addFormatterTest("%#v", &pv3, "(**"+v3t+")"+v3s)
--	addFormatterTest("%#v", nv3, "(*"+v3t+")"+"<nil>")
--	addFormatterTest("%#+v", v3, "("+v3t+")"+v3s)
--	addFormatterTest("%#+v", pv3, "(*"+v3t+")("+v3Addr+")"+v3s)
--	addFormatterTest("%#+v", &pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")"+v3s)
--	addFormatterTest("%#v", nv3, "(*"+v3t+")"+"<nil>")
+-	addDumpTest(v3, "("+v3t+") "+v3s+"\n")
+-	addDumpTest(pv3, "(*"+v3t+")("+v3Addr+")("+v3s+")\n")
+-	addDumpTest(&pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")("+v3s+")\n")
+-	addDumpTest(nv3, "(*"+v3t+")(<nil>)\n")
 -
 -	// Max int64.
 -	v4 := int64(9223372036854775807)
@@ -43802,22 +45859,10 @@ index 80c5ef9..0000000
 -	pv4Addr := fmt.Sprintf("%p", &pv4)
 -	v4t := "int64"
 -	v4s := "9223372036854775807"
--	addFormatterTest("%v", v4, v4s)
--	addFormatterTest("%v", pv4, "<*>"+v4s)
--	addFormatterTest("%v", &pv4, "<**>"+v4s)
--	addFormatterTest("%v", nv4, "<nil>")
--	addFormatterTest("%+v", v4, v4s)
--	addFormatterTest("%+v", pv4, "<*>("+v4Addr+")"+v4s)
--	addFormatterTest("%+v", &pv4, "<**>("+pv4Addr+"->"+v4Addr+")"+v4s)
--	addFormatterTest("%+v", nv4, "<nil>")
--	addFormatterTest("%#v", v4, "("+v4t+")"+v4s)
--	addFormatterTest("%#v", pv4, "(*"+v4t+")"+v4s)
--	addFormatterTest("%#v", &pv4, "(**"+v4t+")"+v4s)
--	addFormatterTest("%#v", nv4, "(*"+v4t+")"+"<nil>")
--	addFormatterTest("%#+v", v4, "("+v4t+")"+v4s)
--	addFormatterTest("%#+v", pv4, "(*"+v4t+")("+v4Addr+")"+v4s)
--	addFormatterTest("%#+v", &pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")"+v4s)
--	addFormatterTest("%#+v", nv4, "(*"+v4t+")"+"<nil>")
+-	addDumpTest(v4, "("+v4t+") "+v4s+"\n")
+-	addDumpTest(pv4, "(*"+v4t+")("+v4Addr+")("+v4s+")\n")
+-	addDumpTest(&pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")("+v4s+")\n")
+-	addDumpTest(nv4, "(*"+v4t+")(<nil>)\n")
 -
 -	// Max int.
 -	v5 := int(2147483647)
@@ -43827,25 +45872,13 @@ index 80c5ef9..0000000
 -	pv5Addr := fmt.Sprintf("%p", &pv5)
 -	v5t := "int"
 -	v5s := "2147483647"
--	addFormatterTest("%v", v5, v5s)
--	addFormatterTest("%v", pv5, "<*>"+v5s)
--	addFormatterTest("%v", &pv5, "<**>"+v5s)
--	addFormatterTest("%v", nv5, "<nil>")
--	addFormatterTest("%+v", v5, v5s)
--	addFormatterTest("%+v", pv5, "<*>("+v5Addr+")"+v5s)
--	addFormatterTest("%+v", &pv5, "<**>("+pv5Addr+"->"+v5Addr+")"+v5s)
--	addFormatterTest("%+v", nv5, "<nil>")
--	addFormatterTest("%#v", v5, "("+v5t+")"+v5s)
--	addFormatterTest("%#v", pv5, "(*"+v5t+")"+v5s)
--	addFormatterTest("%#v", &pv5, "(**"+v5t+")"+v5s)
--	addFormatterTest("%#v", nv5, "(*"+v5t+")"+"<nil>")
--	addFormatterTest("%#+v", v5, "("+v5t+")"+v5s)
--	addFormatterTest("%#+v", pv5, "(*"+v5t+")("+v5Addr+")"+v5s)
--	addFormatterTest("%#+v", &pv5, "(**"+v5t+")("+pv5Addr+"->"+v5Addr+")"+v5s)
--	addFormatterTest("%#+v", nv5, "(*"+v5t+")"+"<nil>")
+-	addDumpTest(v5, "("+v5t+") "+v5s+"\n")
+-	addDumpTest(pv5, "(*"+v5t+")("+v5Addr+")("+v5s+")\n")
+-	addDumpTest(&pv5, "(**"+v5t+")("+pv5Addr+"->"+v5Addr+")("+v5s+")\n")
+-	addDumpTest(nv5, "(*"+v5t+")(<nil>)\n")
 -}
 -
--func addUintFormatterTests() {
+-func addUintDumpTests() {
 -	// Max uint8.
 -	v := uint8(255)
 -	nv := (*uint8)(nil)
@@ -43854,22 +45887,10 @@ index 80c5ef9..0000000
 -	pvAddr := fmt.Sprintf("%p", &pv)
 -	vt := "uint8"
 -	vs := "255"
--	addFormatterTest("%v", v, vs)
--	addFormatterTest("%v", pv, "<*>"+vs)
--	addFormatterTest("%v", &pv, "<**>"+vs)
--	addFormatterTest("%v", nv, "<nil>")
--	addFormatterTest("%+v", v, vs)
--	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
--	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%#v", v, "("+vt+")"+vs)
--	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
--	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
--	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
--	addFormatterTest("%#+v", v, "("+vt+")"+vs)
--	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
--	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-	addDumpTest(v, "("+vt+") "+vs+"\n")
+-	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
+-	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
+-	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
 -
 -	// Max uint16.
 -	v2 := uint16(65535)
@@ -43879,22 +45900,10 @@ index 80c5ef9..0000000
 -	pv2Addr := fmt.Sprintf("%p", &pv2)
 -	v2t := "uint16"
 -	v2s := "65535"
--	addFormatterTest("%v", v2, v2s)
--	addFormatterTest("%v", pv2, "<*>"+v2s)
--	addFormatterTest("%v", &pv2, "<**>"+v2s)
--	addFormatterTest("%v", nv2, "<nil>")
--	addFormatterTest("%+v", v2, v2s)
--	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
--	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%+v", nv2, "<nil>")
--	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
--	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
--	addFormatterTest("%#v", nv2, "(*"+v2t+")"+"<nil>")
--	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", nv2, "(*"+v2t+")"+"<nil>")
+-	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
+-	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
+-	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
+-	addDumpTest(nv2, "(*"+v2t+")(<nil>)\n")
 -
 -	// Max uint32.
 -	v3 := uint32(4294967295)
@@ -43904,22 +45913,10 @@ index 80c5ef9..0000000
 -	pv3Addr := fmt.Sprintf("%p", &pv3)
 -	v3t := "uint32"
 -	v3s := "4294967295"
--	addFormatterTest("%v", v3, v3s)
--	addFormatterTest("%v", pv3, "<*>"+v3s)
--	addFormatterTest("%v", &pv3, "<**>"+v3s)
--	addFormatterTest("%v", nv3, "<nil>")
--	addFormatterTest("%+v", v3, v3s)
--	addFormatterTest("%+v", pv3, "<*>("+v3Addr+")"+v3s)
--	addFormatterTest("%+v", &pv3, "<**>("+pv3Addr+"->"+v3Addr+")"+v3s)
--	addFormatterTest("%+v", nv3, "<nil>")
--	addFormatterTest("%#v", v3, "("+v3t+")"+v3s)
--	addFormatterTest("%#v", pv3, "(*"+v3t+")"+v3s)
--	addFormatterTest("%#v", &pv3, "(**"+v3t+")"+v3s)
--	addFormatterTest("%#v", nv3, "(*"+v3t+")"+"<nil>")
--	addFormatterTest("%#+v", v3, "("+v3t+")"+v3s)
--	addFormatterTest("%#+v", pv3, "(*"+v3t+")("+v3Addr+")"+v3s)
--	addFormatterTest("%#+v", &pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")"+v3s)
--	addFormatterTest("%#v", nv3, "(*"+v3t+")"+"<nil>")
+-	addDumpTest(v3, "("+v3t+") "+v3s+"\n")
+-	addDumpTest(pv3, "(*"+v3t+")("+v3Addr+")("+v3s+")\n")
+-	addDumpTest(&pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")("+v3s+")\n")
+-	addDumpTest(nv3, "(*"+v3t+")(<nil>)\n")
 -
 -	// Max uint64.
 -	v4 := uint64(18446744073709551615)
@@ -43929,22 +45926,10 @@ index 80c5ef9..0000000
 -	pv4Addr := fmt.Sprintf("%p", &pv4)
 -	v4t := "uint64"
 -	v4s := "18446744073709551615"
--	addFormatterTest("%v", v4, v4s)
--	addFormatterTest("%v", pv4, "<*>"+v4s)
--	addFormatterTest("%v", &pv4, "<**>"+v4s)
--	addFormatterTest("%v", nv4, "<nil>")
--	addFormatterTest("%+v", v4, v4s)
--	addFormatterTest("%+v", pv4, "<*>("+v4Addr+")"+v4s)
--	addFormatterTest("%+v", &pv4, "<**>("+pv4Addr+"->"+v4Addr+")"+v4s)
--	addFormatterTest("%+v", nv4, "<nil>")
--	addFormatterTest("%#v", v4, "("+v4t+")"+v4s)
--	addFormatterTest("%#v", pv4, "(*"+v4t+")"+v4s)
--	addFormatterTest("%#v", &pv4, "(**"+v4t+")"+v4s)
--	addFormatterTest("%#v", nv4, "(*"+v4t+")"+"<nil>")
--	addFormatterTest("%#+v", v4, "("+v4t+")"+v4s)
--	addFormatterTest("%#+v", pv4, "(*"+v4t+")("+v4Addr+")"+v4s)
--	addFormatterTest("%#+v", &pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")"+v4s)
--	addFormatterTest("%#+v", nv4, "(*"+v4t+")"+"<nil>")
+-	addDumpTest(v4, "("+v4t+") "+v4s+"\n")
+-	addDumpTest(pv4, "(*"+v4t+")("+v4Addr+")("+v4s+")\n")
+-	addDumpTest(&pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")("+v4s+")\n")
+-	addDumpTest(nv4, "(*"+v4t+")(<nil>)\n")
 -
 -	// Max uint.
 -	v5 := uint(4294967295)
@@ -43954,25 +45939,13 @@ index 80c5ef9..0000000
 -	pv5Addr := fmt.Sprintf("%p", &pv5)
 -	v5t := "uint"
 -	v5s := "4294967295"
--	addFormatterTest("%v", v5, v5s)
--	addFormatterTest("%v", pv5, "<*>"+v5s)
--	addFormatterTest("%v", &pv5, "<**>"+v5s)
--	addFormatterTest("%v", nv5, "<nil>")
--	addFormatterTest("%+v", v5, v5s)
--	addFormatterTest("%+v", pv5, "<*>("+v5Addr+")"+v5s)
--	addFormatterTest("%+v", &pv5, "<**>("+pv5Addr+"->"+v5Addr+")"+v5s)
--	addFormatterTest("%+v", nv5, "<nil>")
--	addFormatterTest("%#v", v5, "("+v5t+")"+v5s)
--	addFormatterTest("%#v", pv5, "(*"+v5t+")"+v5s)
--	addFormatterTest("%#v", &pv5, "(**"+v5t+")"+v5s)
--	addFormatterTest("%#v", nv5, "(*"+v5t+")"+"<nil>")
--	addFormatterTest("%#+v", v5, "("+v5t+")"+v5s)
--	addFormatterTest("%#+v", pv5, "(*"+v5t+")("+v5Addr+")"+v5s)
--	addFormatterTest("%#+v", &pv5, "(**"+v5t+")("+pv5Addr+"->"+v5Addr+")"+v5s)
--	addFormatterTest("%#v", nv5, "(*"+v5t+")"+"<nil>")
+-	addDumpTest(v5, "("+v5t+") "+v5s+"\n")
+-	addDumpTest(pv5, "(*"+v5t+")("+v5Addr+")("+v5s+")\n")
+-	addDumpTest(&pv5, "(**"+v5t+")("+pv5Addr+"->"+v5Addr+")("+v5s+")\n")
+-	addDumpTest(nv5, "(*"+v5t+")(<nil>)\n")
 -}
 -
--func addBoolFormatterTests() {
+-func addBoolDumpTests() {
 -	// Boolean true.
 -	v := bool(true)
 -	nv := (*bool)(nil)
@@ -43981,22 +45954,10 @@ index 80c5ef9..0000000
 -	pvAddr := fmt.Sprintf("%p", &pv)
 -	vt := "bool"
 -	vs := "true"
--	addFormatterTest("%v", v, vs)
--	addFormatterTest("%v", pv, "<*>"+vs)
--	addFormatterTest("%v", &pv, "<**>"+vs)
--	addFormatterTest("%v", nv, "<nil>")
--	addFormatterTest("%+v", v, vs)
--	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
--	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%#v", v, "("+vt+")"+vs)
--	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
--	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
--	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
--	addFormatterTest("%#+v", v, "("+vt+")"+vs)
--	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
--	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-	addDumpTest(v, "("+vt+") "+vs+"\n")
+-	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
+-	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
+-	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
 -
 -	// Boolean false.
 -	v2 := bool(false)
@@ -44005,21 +45966,12 @@ index 80c5ef9..0000000
 -	pv2Addr := fmt.Sprintf("%p", &pv2)
 -	v2t := "bool"
 -	v2s := "false"
--	addFormatterTest("%v", v2, v2s)
--	addFormatterTest("%v", pv2, "<*>"+v2s)
--	addFormatterTest("%v", &pv2, "<**>"+v2s)
--	addFormatterTest("%+v", v2, v2s)
--	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
--	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
--	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
--	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
+-	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
+-	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
 -}
 -
--func addFloatFormatterTests() {
+-func addFloatDumpTests() {
 -	// Standard float32.
 -	v := float32(3.1415)
 -	nv := (*float32)(nil)
@@ -44028,22 +45980,10 @@ index 80c5ef9..0000000
 -	pvAddr := fmt.Sprintf("%p", &pv)
 -	vt := "float32"
 -	vs := "3.1415"
--	addFormatterTest("%v", v, vs)
--	addFormatterTest("%v", pv, "<*>"+vs)
--	addFormatterTest("%v", &pv, "<**>"+vs)
--	addFormatterTest("%v", nv, "<nil>")
--	addFormatterTest("%+v", v, vs)
--	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
--	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%#v", v, "("+vt+")"+vs)
--	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
--	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
--	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
--	addFormatterTest("%#+v", v, "("+vt+")"+vs)
--	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
--	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-	addDumpTest(v, "("+vt+") "+vs+"\n")
+-	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
+-	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
+-	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
 -
 -	// Standard float64.
 -	v2 := float64(3.1415926)
@@ -44053,25 +45993,13 @@ index 80c5ef9..0000000
 -	pv2Addr := fmt.Sprintf("%p", &pv2)
 -	v2t := "float64"
 -	v2s := "3.1415926"
--	addFormatterTest("%v", v2, v2s)
--	addFormatterTest("%v", pv2, "<*>"+v2s)
--	addFormatterTest("%v", &pv2, "<**>"+v2s)
--	addFormatterTest("%+v", nv2, "<nil>")
--	addFormatterTest("%+v", v2, v2s)
--	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
--	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%+v", nv2, "<nil>")
--	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
--	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
--	addFormatterTest("%#v", nv2, "(*"+v2t+")"+"<nil>")
--	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", nv2, "(*"+v2t+")"+"<nil>")
+-	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
+-	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
+-	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
+-	addDumpTest(nv2, "(*"+v2t+")(<nil>)\n")
 -}
 -
--func addComplexFormatterTests() {
+-func addComplexDumpTests() {
 -	// Standard complex64.
 -	v := complex(float32(6), -2)
 -	nv := (*complex64)(nil)
@@ -44080,22 +46008,10 @@ index 80c5ef9..0000000
 -	pvAddr := fmt.Sprintf("%p", &pv)
 -	vt := "complex64"
 -	vs := "(6-2i)"
--	addFormatterTest("%v", v, vs)
--	addFormatterTest("%v", pv, "<*>"+vs)
--	addFormatterTest("%v", &pv, "<**>"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%+v", v, vs)
--	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
--	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%#v", v, "("+vt+")"+vs)
--	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
--	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
--	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
--	addFormatterTest("%#+v", v, "("+vt+")"+vs)
--	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
--	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-	addDumpTest(v, "("+vt+") "+vs+"\n")
+-	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
+-	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
+-	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
 -
 -	// Standard complex128.
 -	v2 := complex(float64(-6), 2)
@@ -44105,77 +46021,59 @@ index 80c5ef9..0000000
 -	pv2Addr := fmt.Sprintf("%p", &pv2)
 -	v2t := "complex128"
 -	v2s := "(-6+2i)"
--	addFormatterTest("%v", v2, v2s)
--	addFormatterTest("%v", pv2, "<*>"+v2s)
--	addFormatterTest("%v", &pv2, "<**>"+v2s)
--	addFormatterTest("%+v", nv2, "<nil>")
--	addFormatterTest("%+v", v2, v2s)
--	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
--	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%+v", nv2, "<nil>")
--	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
--	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
--	addFormatterTest("%#v", nv2, "(*"+v2t+")"+"<nil>")
--	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", nv2, "(*"+v2t+")"+"<nil>")
+-	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
+-	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
+-	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
+-	addDumpTest(nv2, "(*"+v2t+")(<nil>)\n")
 -}
 -
--func addArrayFormatterTests() {
+-func addArrayDumpTests() {
 -	// Array containing standard ints.
 -	v := [3]int{1, 2, 3}
+-	vLen := fmt.Sprintf("%d", len(v))
+-	vCap := fmt.Sprintf("%d", cap(v))
 -	nv := (*[3]int)(nil)
 -	pv := &v
 -	vAddr := fmt.Sprintf("%p", pv)
 -	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "[3]int"
--	vs := "[1 2 3]"
--	addFormatterTest("%v", v, vs)
--	addFormatterTest("%v", pv, "<*>"+vs)
--	addFormatterTest("%v", &pv, "<**>"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%+v", v, vs)
--	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
--	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%#v", v, "("+vt+")"+vs)
--	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
--	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
--	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
--	addFormatterTest("%#+v", v, "("+vt+")"+vs)
--	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
--	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-	vt := "int"
+-	vs := "(len=" + vLen + " cap=" + vCap + ") {\n (" + vt + ") 1,\n (" +
+-		vt + ") 2,\n (" + vt + ") 3\n}"
+-	addDumpTest(v, "([3]"+vt+") "+vs+"\n")
+-	addDumpTest(pv, "(*[3]"+vt+")("+vAddr+")("+vs+")\n")
+-	addDumpTest(&pv, "(**[3]"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
+-	addDumpTest(nv, "(*[3]"+vt+")(<nil>)\n")
 -
 -	// Array containing type with custom formatter on pointer receiver only.
--	v2 := [3]pstringer{"1", "2", "3"}
+-	v2i0 := pstringer("1")
+-	v2i1 := pstringer("2")
+-	v2i2 := pstringer("3")
+-	v2 := [3]pstringer{v2i0, v2i1, v2i2}
+-	v2i0Len := fmt.Sprintf("%d", len(v2i0))
+-	v2i1Len := fmt.Sprintf("%d", len(v2i1))
+-	v2i2Len := fmt.Sprintf("%d", len(v2i2))
+-	v2Len := fmt.Sprintf("%d", len(v2))
+-	v2Cap := fmt.Sprintf("%d", cap(v2))
 -	nv2 := (*[3]pstringer)(nil)
 -	pv2 := &v2
 -	v2Addr := fmt.Sprintf("%p", pv2)
 -	pv2Addr := fmt.Sprintf("%p", &pv2)
--	v2t := "[3]spew_test.pstringer"
--	v2s := "[stringer 1 stringer 2 stringer 3]"
--	addFormatterTest("%v", v2, v2s)
--	addFormatterTest("%v", pv2, "<*>"+v2s)
--	addFormatterTest("%v", &pv2, "<**>"+v2s)
--	addFormatterTest("%+v", nv2, "<nil>")
--	addFormatterTest("%+v", v2, v2s)
--	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
--	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%+v", nv2, "<nil>")
--	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
--	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
--	addFormatterTest("%#v", nv2, "(*"+v2t+")"+"<nil>")
--	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", nv2, "(*"+v2t+")"+"<nil>")
+-	v2t := "spew_test.pstringer"
+-	v2s := "(len=" + v2Len + " cap=" + v2Cap + ") {\n (" + v2t + ") (len=" +
+-		v2i0Len + ") stringer 1,\n (" + v2t + ") (len=" + v2i1Len +
+-		") stringer 2,\n (" + v2t + ") (len=" + v2i2Len + ") " +
+-		"stringer 3\n}"
+-	addDumpTest(v2, "([3]"+v2t+") "+v2s+"\n")
+-	addDumpTest(pv2, "(*[3]"+v2t+")("+v2Addr+")("+v2s+")\n")
+-	addDumpTest(&pv2, "(**[3]"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
+-	addDumpTest(nv2, "(*[3]"+v2t+")(<nil>)\n")
 -
 -	// Array containing interfaces.
--	v3 := [3]interface{}{"one", int(2), uint(3)}
+-	v3i0 := "one"
+-	v3 := [3]interface{}{v3i0, int(2), uint(3)}
+-	v3i0Len := fmt.Sprintf("%d", len(v3i0))
+-	v3Len := fmt.Sprintf("%d", len(v3))
+-	v3Cap := fmt.Sprintf("%d", cap(v3))
 -	nv3 := (*[3]interface{})(nil)
 -	pv3 := &v3
 -	v3Addr := fmt.Sprintf("%p", pv3)
@@ -44184,79 +46082,89 @@ index 80c5ef9..0000000
 -	v3t2 := "string"
 -	v3t3 := "int"
 -	v3t4 := "uint"
--	v3s := "[one 2 3]"
--	v3s2 := "[(" + v3t2 + ")one (" + v3t3 + ")2 (" + v3t4 + ")3]"
--	addFormatterTest("%v", v3, v3s)
--	addFormatterTest("%v", pv3, "<*>"+v3s)
--	addFormatterTest("%v", &pv3, "<**>"+v3s)
--	addFormatterTest("%+v", nv3, "<nil>")
--	addFormatterTest("%+v", v3, v3s)
--	addFormatterTest("%+v", pv3, "<*>("+v3Addr+")"+v3s)
--	addFormatterTest("%+v", &pv3, "<**>("+pv3Addr+"->"+v3Addr+")"+v3s)
--	addFormatterTest("%+v", nv3, "<nil>")
--	addFormatterTest("%#v", v3, "("+v3t+")"+v3s2)
--	addFormatterTest("%#v", pv3, "(*"+v3t+")"+v3s2)
--	addFormatterTest("%#v", &pv3, "(**"+v3t+")"+v3s2)
--	addFormatterTest("%#v", nv3, "(*"+v3t+")"+"<nil>")
--	addFormatterTest("%#+v", v3, "("+v3t+")"+v3s2)
--	addFormatterTest("%#+v", pv3, "(*"+v3t+")("+v3Addr+")"+v3s2)
--	addFormatterTest("%#+v", &pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")"+v3s2)
--	addFormatterTest("%#+v", nv3, "(*"+v3t+")"+"<nil>")
+-	v3s := "(len=" + v3Len + " cap=" + v3Cap + ") {\n (" + v3t2 + ") " +
+-		"(len=" + v3i0Len + ") \"one\",\n (" + v3t3 + ") 2,\n (" +
+-		v3t4 + ") 3\n}"
+-	addDumpTest(v3, "("+v3t+") "+v3s+"\n")
+-	addDumpTest(pv3, "(*"+v3t+")("+v3Addr+")("+v3s+")\n")
+-	addDumpTest(&pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")("+v3s+")\n")
+-	addDumpTest(nv3, "(*"+v3t+")(<nil>)\n")
+-
+-	// Array containing bytes.
+-	v4 := [34]byte{
+-		0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18,
+-		0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 0x20,
+-		0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28,
+-		0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, 0x30,
+-		0x31, 0x32,
+-	}
+-	v4Len := fmt.Sprintf("%d", len(v4))
+-	v4Cap := fmt.Sprintf("%d", cap(v4))
+-	nv4 := (*[34]byte)(nil)
+-	pv4 := &v4
+-	v4Addr := fmt.Sprintf("%p", pv4)
+-	pv4Addr := fmt.Sprintf("%p", &pv4)
+-	v4t := "[34]uint8"
+-	v4s := "(len=" + v4Len + " cap=" + v4Cap + ") " +
+-		"{\n 00000000  11 12 13 14 15 16 17 18  19 1a 1b 1c 1d 1e 1f 20" +
+-		"  |............... |\n" +
+-		" 00000010  21 22 23 24 25 26 27 28  29 2a 2b 2c 2d 2e 2f 30" +
+-		"  |!\"#$%&'()*+,-./0|\n" +
+-		" 00000020  31 32                                           " +
+-		"  |12|\n}"
+-	addDumpTest(v4, "("+v4t+") "+v4s+"\n")
+-	addDumpTest(pv4, "(*"+v4t+")("+v4Addr+")("+v4s+")\n")
+-	addDumpTest(&pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")("+v4s+")\n")
+-	addDumpTest(nv4, "(*"+v4t+")(<nil>)\n")
 -}
 -
--func addSliceFormatterTests() {
+-func addSliceDumpTests() {
 -	// Slice containing standard float32 values.
 -	v := []float32{3.14, 6.28, 12.56}
+-	vLen := fmt.Sprintf("%d", len(v))
+-	vCap := fmt.Sprintf("%d", cap(v))
 -	nv := (*[]float32)(nil)
 -	pv := &v
 -	vAddr := fmt.Sprintf("%p", pv)
 -	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "[]float32"
--	vs := "[3.14 6.28 12.56]"
--	addFormatterTest("%v", v, vs)
--	addFormatterTest("%v", pv, "<*>"+vs)
--	addFormatterTest("%v", &pv, "<**>"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%+v", v, vs)
--	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
--	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%#v", v, "("+vt+")"+vs)
--	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
--	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
--	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
--	addFormatterTest("%#+v", v, "("+vt+")"+vs)
--	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
--	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-	vt := "float32"
+-	vs := "(len=" + vLen + " cap=" + vCap + ") {\n (" + vt + ") 3.14,\n (" +
+-		vt + ") 6.28,\n (" + vt + ") 12.56\n}"
+-	addDumpTest(v, "([]"+vt+") "+vs+"\n")
+-	addDumpTest(pv, "(*[]"+vt+")("+vAddr+")("+vs+")\n")
+-	addDumpTest(&pv, "(**[]"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
+-	addDumpTest(nv, "(*[]"+vt+")(<nil>)\n")
 -
 -	// Slice containing type with custom formatter on pointer receiver only.
--	v2 := []pstringer{"1", "2", "3"}
+-	v2i0 := pstringer("1")
+-	v2i1 := pstringer("2")
+-	v2i2 := pstringer("3")
+-	v2 := []pstringer{v2i0, v2i1, v2i2}
+-	v2i0Len := fmt.Sprintf("%d", len(v2i0))
+-	v2i1Len := fmt.Sprintf("%d", len(v2i1))
+-	v2i2Len := fmt.Sprintf("%d", len(v2i2))
+-	v2Len := fmt.Sprintf("%d", len(v2))
+-	v2Cap := fmt.Sprintf("%d", cap(v2))
 -	nv2 := (*[]pstringer)(nil)
 -	pv2 := &v2
 -	v2Addr := fmt.Sprintf("%p", pv2)
 -	pv2Addr := fmt.Sprintf("%p", &pv2)
--	v2t := "[]spew_test.pstringer"
--	v2s := "[stringer 1 stringer 2 stringer 3]"
--	addFormatterTest("%v", v2, v2s)
--	addFormatterTest("%v", pv2, "<*>"+v2s)
--	addFormatterTest("%v", &pv2, "<**>"+v2s)
--	addFormatterTest("%+v", nv2, "<nil>")
--	addFormatterTest("%+v", v2, v2s)
--	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
--	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%+v", nv2, "<nil>")
--	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
--	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
--	addFormatterTest("%#v", nv2, "(*"+v2t+")"+"<nil>")
--	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", nv2, "(*"+v2t+")"+"<nil>")
+-	v2t := "spew_test.pstringer"
+-	v2s := "(len=" + v2Len + " cap=" + v2Cap + ") {\n (" + v2t + ") (len=" +
+-		v2i0Len + ") stringer 1,\n (" + v2t + ") (len=" + v2i1Len +
+-		") stringer 2,\n (" + v2t + ") (len=" + v2i2Len + ") " +
+-		"stringer 3\n}"
+-	addDumpTest(v2, "([]"+v2t+") "+v2s+"\n")
+-	addDumpTest(pv2, "(*[]"+v2t+")("+v2Addr+")("+v2s+")\n")
+-	addDumpTest(&pv2, "(**[]"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
+-	addDumpTest(nv2, "(*[]"+v2t+")(<nil>)\n")
 -
 -	// Slice containing interfaces.
--	v3 := []interface{}{"one", int(2), uint(3), nil}
+-	v3i0 := "one"
+-	v3 := []interface{}{v3i0, int(2), uint(3), nil}
+-	v3i0Len := fmt.Sprintf("%d", len(v3i0))
+-	v3Len := fmt.Sprintf("%d", len(v3))
+-	v3Cap := fmt.Sprintf("%d", cap(v3))
 -	nv3 := (*[]interface{})(nil)
 -	pv3 := &v3
 -	v3Addr := fmt.Sprintf("%p", pv3)
@@ -44266,80 +46174,72 @@ index 80c5ef9..0000000
 -	v3t3 := "int"
 -	v3t4 := "uint"
 -	v3t5 := "interface {}"
--	v3s := "[one 2 3 <nil>]"
--	v3s2 := "[(" + v3t2 + ")one (" + v3t3 + ")2 (" + v3t4 + ")3 (" + v3t5 +
--		")<nil>]"
--	addFormatterTest("%v", v3, v3s)
--	addFormatterTest("%v", pv3, "<*>"+v3s)
--	addFormatterTest("%v", &pv3, "<**>"+v3s)
--	addFormatterTest("%+v", nv3, "<nil>")
--	addFormatterTest("%+v", v3, v3s)
--	addFormatterTest("%+v", pv3, "<*>("+v3Addr+")"+v3s)
--	addFormatterTest("%+v", &pv3, "<**>("+pv3Addr+"->"+v3Addr+")"+v3s)
--	addFormatterTest("%+v", nv3, "<nil>")
--	addFormatterTest("%#v", v3, "("+v3t+")"+v3s2)
--	addFormatterTest("%#v", pv3, "(*"+v3t+")"+v3s2)
--	addFormatterTest("%#v", &pv3, "(**"+v3t+")"+v3s2)
--	addFormatterTest("%#v", nv3, "(*"+v3t+")"+"<nil>")
--	addFormatterTest("%#+v", v3, "("+v3t+")"+v3s2)
--	addFormatterTest("%#+v", pv3, "(*"+v3t+")("+v3Addr+")"+v3s2)
--	addFormatterTest("%#+v", &pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")"+v3s2)
--	addFormatterTest("%#+v", nv3, "(*"+v3t+")"+"<nil>")
+-	v3s := "(len=" + v3Len + " cap=" + v3Cap + ") {\n (" + v3t2 + ") " +
+-		"(len=" + v3i0Len + ") \"one\",\n (" + v3t3 + ") 2,\n (" +
+-		v3t4 + ") 3,\n (" + v3t5 + ") <nil>\n}"
+-	addDumpTest(v3, "("+v3t+") "+v3s+"\n")
+-	addDumpTest(pv3, "(*"+v3t+")("+v3Addr+")("+v3s+")\n")
+-	addDumpTest(&pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")("+v3s+")\n")
+-	addDumpTest(nv3, "(*"+v3t+")(<nil>)\n")
 -
--	// Nil slice.
--	var v4 []int
--	nv4 := (*[]int)(nil)
+-	// Slice containing bytes.
+-	v4 := []byte{
+-		0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18,
+-		0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 0x20,
+-		0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28,
+-		0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, 0x30,
+-		0x31, 0x32,
+-	}
+-	v4Len := fmt.Sprintf("%d", len(v4))
+-	v4Cap := fmt.Sprintf("%d", cap(v4))
+-	nv4 := (*[]byte)(nil)
 -	pv4 := &v4
 -	v4Addr := fmt.Sprintf("%p", pv4)
 -	pv4Addr := fmt.Sprintf("%p", &pv4)
--	v4t := "[]int"
--	v4s := "<nil>"
--	addFormatterTest("%v", v4, v4s)
--	addFormatterTest("%v", pv4, "<*>"+v4s)
--	addFormatterTest("%v", &pv4, "<**>"+v4s)
--	addFormatterTest("%+v", nv4, "<nil>")
--	addFormatterTest("%+v", v4, v4s)
--	addFormatterTest("%+v", pv4, "<*>("+v4Addr+")"+v4s)
--	addFormatterTest("%+v", &pv4, "<**>("+pv4Addr+"->"+v4Addr+")"+v4s)
--	addFormatterTest("%+v", nv4, "<nil>")
--	addFormatterTest("%#v", v4, "("+v4t+")"+v4s)
--	addFormatterTest("%#v", pv4, "(*"+v4t+")"+v4s)
--	addFormatterTest("%#v", &pv4, "(**"+v4t+")"+v4s)
--	addFormatterTest("%#v", nv4, "(*"+v4t+")"+"<nil>")
--	addFormatterTest("%#+v", v4, "("+v4t+")"+v4s)
--	addFormatterTest("%#+v", pv4, "(*"+v4t+")("+v4Addr+")"+v4s)
--	addFormatterTest("%#+v", &pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")"+v4s)
--	addFormatterTest("%#+v", nv4, "(*"+v4t+")"+"<nil>")
+-	v4t := "[]uint8"
+-	v4s := "(len=" + v4Len + " cap=" + v4Cap + ") " +
+-		"{\n 00000000  11 12 13 14 15 16 17 18  19 1a 1b 1c 1d 1e 1f 20" +
+-		"  |............... |\n" +
+-		" 00000010  21 22 23 24 25 26 27 28  29 2a 2b 2c 2d 2e 2f 30" +
+-		"  |!\"#$%&'()*+,-./0|\n" +
+-		" 00000020  31 32                                           " +
+-		"  |12|\n}"
+-	addDumpTest(v4, "("+v4t+") "+v4s+"\n")
+-	addDumpTest(pv4, "(*"+v4t+")("+v4Addr+")("+v4s+")\n")
+-	addDumpTest(&pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")("+v4s+")\n")
+-	addDumpTest(nv4, "(*"+v4t+")(<nil>)\n")
+-
+-	// Nil slice.
+-	v5 := []int(nil)
+-	nv5 := (*[]int)(nil)
+-	pv5 := &v5
+-	v5Addr := fmt.Sprintf("%p", pv5)
+-	pv5Addr := fmt.Sprintf("%p", &pv5)
+-	v5t := "[]int"
+-	v5s := "<nil>"
+-	addDumpTest(v5, "("+v5t+") "+v5s+"\n")
+-	addDumpTest(pv5, "(*"+v5t+")("+v5Addr+")("+v5s+")\n")
+-	addDumpTest(&pv5, "(**"+v5t+")("+pv5Addr+"->"+v5Addr+")("+v5s+")\n")
+-	addDumpTest(nv5, "(*"+v5t+")(<nil>)\n")
 -}
 -
--func addStringFormatterTests() {
+-func addStringDumpTests() {
 -	// Standard string.
 -	v := "test"
+-	vLen := fmt.Sprintf("%d", len(v))
 -	nv := (*string)(nil)
 -	pv := &v
 -	vAddr := fmt.Sprintf("%p", pv)
 -	pvAddr := fmt.Sprintf("%p", &pv)
 -	vt := "string"
--	vs := "test"
--	addFormatterTest("%v", v, vs)
--	addFormatterTest("%v", pv, "<*>"+vs)
--	addFormatterTest("%v", &pv, "<**>"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%+v", v, vs)
--	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
--	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%#v", v, "("+vt+")"+vs)
--	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
--	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
--	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
--	addFormatterTest("%#+v", v, "("+vt+")"+vs)
--	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
--	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-	vs := "(len=" + vLen + ") \"test\""
+-	addDumpTest(v, "("+vt+") "+vs+"\n")
+-	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
+-	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
+-	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
 -}
 -
--func addInterfaceFormatterTests() {
+-func addInterfaceDumpTests() {
 -	// Nil interface.
 -	var v interface{}
 -	nv := (*interface{})(nil)
@@ -44348,22 +46248,10 @@ index 80c5ef9..0000000
 -	pvAddr := fmt.Sprintf("%p", &pv)
 -	vt := "interface {}"
 -	vs := "<nil>"
--	addFormatterTest("%v", v, vs)
--	addFormatterTest("%v", pv, "<*>"+vs)
--	addFormatterTest("%v", &pv, "<**>"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%+v", v, vs)
--	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
--	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%#v", v, "("+vt+")"+vs)
--	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
--	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
--	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
--	addFormatterTest("%#+v", v, "("+vt+")"+vs)
--	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
--	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-	addDumpTest(v, "("+vt+") "+vs+"\n")
+-	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
+-	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
+-	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
 -
 -	// Sub-interface.
 -	v2 := interface{}(uint16(65535))
@@ -44372,132 +46260,100 @@ index 80c5ef9..0000000
 -	pv2Addr := fmt.Sprintf("%p", &pv2)
 -	v2t := "uint16"
 -	v2s := "65535"
--	addFormatterTest("%v", v2, v2s)
--	addFormatterTest("%v", pv2, "<*>"+v2s)
--	addFormatterTest("%v", &pv2, "<**>"+v2s)
--	addFormatterTest("%+v", v2, v2s)
--	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
--	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
--	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
--	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
+-	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
+-	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
 -}
 -
--func addMapFormatterTests() {
+-func addMapDumpTests() {
 -	// Map with string keys and int vals.
--	v := map[string]int{"one": 1, "two": 2}
--	nv := (*map[string]int)(nil)
--	pv := &v
--	vAddr := fmt.Sprintf("%p", pv)
--	pvAddr := fmt.Sprintf("%p", &pv)
--	vt := "map[string]int"
--	vs := "map[one:1 two:2]"
--	vs2 := "map[two:2 one:1]"
--	addFormatterTest("%v", v, vs, vs2)
--	addFormatterTest("%v", pv, "<*>"+vs, "<*>"+vs2)
--	addFormatterTest("%v", &pv, "<**>"+vs, "<**>"+vs2)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%+v", v, vs, vs2)
--	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs, "<*>("+vAddr+")"+vs2)
--	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs,
--		"<**>("+pvAddr+"->"+vAddr+")"+vs2)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%#v", v, "("+vt+")"+vs, "("+vt+")"+vs2)
--	addFormatterTest("%#v", pv, "(*"+vt+")"+vs, "(*"+vt+")"+vs2)
--	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs, "(**"+vt+")"+vs2)
--	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
--	addFormatterTest("%#+v", v, "("+vt+")"+vs, "("+vt+")"+vs2)
--	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs,
--		"(*"+vt+")("+vAddr+")"+vs2)
--	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs,
--		"(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs2)
--	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-	k := "one"
+-	kk := "two"
+-	m := map[string]int{k: 1, kk: 2}
+-	klen := fmt.Sprintf("%d", len(k)) // not kLen to shut golint up
+-	kkLen := fmt.Sprintf("%d", len(kk))
+-	mLen := fmt.Sprintf("%d", len(m))
+-	nm := (*map[string]int)(nil)
+-	pm := &m
+-	mAddr := fmt.Sprintf("%p", pm)
+-	pmAddr := fmt.Sprintf("%p", &pm)
+-	mt := "map[string]int"
+-	mt1 := "string"
+-	mt2 := "int"
+-	ms := "(len=" + mLen + ") {\n (" + mt1 + ") (len=" + klen + ") " +
+-		"\"one\": (" + mt2 + ") 1,\n (" + mt1 + ") (len=" + kkLen +
+-		") \"two\": (" + mt2 + ") 2\n}"
+-	ms2 := "(len=" + mLen + ") {\n (" + mt1 + ") (len=" + kkLen + ") " +
+-		"\"two\": (" + mt2 + ") 2,\n (" + mt1 + ") (len=" + klen +
+-		") \"one\": (" + mt2 + ") 1\n}"
+-	addDumpTest(m, "("+mt+") "+ms+"\n", "("+mt+") "+ms2+"\n")
+-	addDumpTest(pm, "(*"+mt+")("+mAddr+")("+ms+")\n",
+-		"(*"+mt+")("+mAddr+")("+ms2+")\n")
+-	addDumpTest(&pm, "(**"+mt+")("+pmAddr+"->"+mAddr+")("+ms+")\n",
+-		"(**"+mt+")("+pmAddr+"->"+mAddr+")("+ms2+")\n")
+-	addDumpTest(nm, "(*"+mt+")(<nil>)\n")
 -
 -	// Map with custom formatter type on pointer receiver only keys and vals.
--	v2 := map[pstringer]pstringer{"one": "1"}
--	nv2 := (*map[pstringer]pstringer)(nil)
--	pv2 := &v2
--	v2Addr := fmt.Sprintf("%p", pv2)
--	pv2Addr := fmt.Sprintf("%p", &pv2)
--	v2t := "map[spew_test.pstringer]spew_test.pstringer"
--	v2s := "map[stringer one:stringer 1]"
--	addFormatterTest("%v", v2, v2s)
--	addFormatterTest("%v", pv2, "<*>"+v2s)
--	addFormatterTest("%v", &pv2, "<**>"+v2s)
--	addFormatterTest("%+v", nv2, "<nil>")
--	addFormatterTest("%+v", v2, v2s)
--	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
--	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%+v", nv2, "<nil>")
--	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
--	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
--	addFormatterTest("%#v", nv2, "(*"+v2t+")"+"<nil>")
--	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", nv2, "(*"+v2t+")"+"<nil>")
+-	k2 := pstringer("one")
+-	v2 := pstringer("1")
+-	m2 := map[pstringer]pstringer{k2: v2}
+-	k2Len := fmt.Sprintf("%d", len(k2))
+-	v2Len := fmt.Sprintf("%d", len(v2))
+-	m2Len := fmt.Sprintf("%d", len(m2))
+-	nm2 := (*map[pstringer]pstringer)(nil)
+-	pm2 := &m2
+-	m2Addr := fmt.Sprintf("%p", pm2)
+-	pm2Addr := fmt.Sprintf("%p", &pm2)
+-	m2t := "map[spew_test.pstringer]spew_test.pstringer"
+-	m2t1 := "spew_test.pstringer"
+-	m2t2 := "spew_test.pstringer"
+-	m2s := "(len=" + m2Len + ") {\n (" + m2t1 + ") (len=" + k2Len + ") " +
+-		"stringer one: (" + m2t2 + ") (len=" + v2Len + ") stringer 1\n}"
+-	addDumpTest(m2, "("+m2t+") "+m2s+"\n")
+-	addDumpTest(pm2, "(*"+m2t+")("+m2Addr+")("+m2s+")\n")
+-	addDumpTest(&pm2, "(**"+m2t+")("+pm2Addr+"->"+m2Addr+")("+m2s+")\n")
+-	addDumpTest(nm2, "(*"+m2t+")(<nil>)\n")
 -
 -	// Map with interface keys and values.
--	v3 := map[interface{}]interface{}{"one": 1}
--	nv3 := (*map[interface{}]interface{})(nil)
--	pv3 := &v3
--	v3Addr := fmt.Sprintf("%p", pv3)
--	pv3Addr := fmt.Sprintf("%p", &pv3)
--	v3t := "map[interface {}]interface {}"
--	v3t1 := "string"
--	v3t2 := "int"
--	v3s := "map[one:1]"
--	v3s2 := "map[(" + v3t1 + ")one:(" + v3t2 + ")1]"
--	addFormatterTest("%v", v3, v3s)
--	addFormatterTest("%v", pv3, "<*>"+v3s)
--	addFormatterTest("%v", &pv3, "<**>"+v3s)
--	addFormatterTest("%+v", nv3, "<nil>")
--	addFormatterTest("%+v", v3, v3s)
--	addFormatterTest("%+v", pv3, "<*>("+v3Addr+")"+v3s)
--	addFormatterTest("%+v", &pv3, "<**>("+pv3Addr+"->"+v3Addr+")"+v3s)
--	addFormatterTest("%+v", nv3, "<nil>")
--	addFormatterTest("%#v", v3, "("+v3t+")"+v3s2)
--	addFormatterTest("%#v", pv3, "(*"+v3t+")"+v3s2)
--	addFormatterTest("%#v", &pv3, "(**"+v3t+")"+v3s2)
--	addFormatterTest("%#v", nv3, "(*"+v3t+")"+"<nil>")
--	addFormatterTest("%#+v", v3, "("+v3t+")"+v3s2)
--	addFormatterTest("%#+v", pv3, "(*"+v3t+")("+v3Addr+")"+v3s2)
--	addFormatterTest("%#+v", &pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")"+v3s2)
--	addFormatterTest("%#+v", nv3, "(*"+v3t+")"+"<nil>")
+-	k3 := "one"
+-	k3Len := fmt.Sprintf("%d", len(k3))
+-	m3 := map[interface{}]interface{}{k3: 1}
+-	m3Len := fmt.Sprintf("%d", len(m3))
+-	nm3 := (*map[interface{}]interface{})(nil)
+-	pm3 := &m3
+-	m3Addr := fmt.Sprintf("%p", pm3)
+-	pm3Addr := fmt.Sprintf("%p", &pm3)
+-	m3t := "map[interface {}]interface {}"
+-	m3t1 := "string"
+-	m3t2 := "int"
+-	m3s := "(len=" + m3Len + ") {\n (" + m3t1 + ") (len=" + k3Len + ") " +
+-		"\"one\": (" + m3t2 + ") 1\n}"
+-	addDumpTest(m3, "("+m3t+") "+m3s+"\n")
+-	addDumpTest(pm3, "(*"+m3t+")("+m3Addr+")("+m3s+")\n")
+-	addDumpTest(&pm3, "(**"+m3t+")("+pm3Addr+"->"+m3Addr+")("+m3s+")\n")
+-	addDumpTest(nm3, "(*"+m3t+")(<nil>)\n")
 -
--	// Map with nil interface value
--	v4 := map[string]interface{}{"nil": nil}
--	nv4 := (*map[string]interface{})(nil)
--	pv4 := &v4
--	v4Addr := fmt.Sprintf("%p", pv4)
--	pv4Addr := fmt.Sprintf("%p", &pv4)
--	v4t := "map[string]interface {}"
--	v4t1 := "interface {}"
--	v4s := "map[nil:<nil>]"
--	v4s2 := "map[nil:(" + v4t1 + ")<nil>]"
--	addFormatterTest("%v", v4, v4s)
--	addFormatterTest("%v", pv4, "<*>"+v4s)
--	addFormatterTest("%v", &pv4, "<**>"+v4s)
--	addFormatterTest("%+v", nv4, "<nil>")
--	addFormatterTest("%+v", v4, v4s)
--	addFormatterTest("%+v", pv4, "<*>("+v4Addr+")"+v4s)
--	addFormatterTest("%+v", &pv4, "<**>("+pv4Addr+"->"+v4Addr+")"+v4s)
--	addFormatterTest("%+v", nv4, "<nil>")
--	addFormatterTest("%#v", v4, "("+v4t+")"+v4s2)
--	addFormatterTest("%#v", pv4, "(*"+v4t+")"+v4s2)
--	addFormatterTest("%#v", &pv4, "(**"+v4t+")"+v4s2)
--	addFormatterTest("%#v", nv4, "(*"+v4t+")"+"<nil>")
--	addFormatterTest("%#+v", v4, "("+v4t+")"+v4s2)
--	addFormatterTest("%#+v", pv4, "(*"+v4t+")("+v4Addr+")"+v4s2)
--	addFormatterTest("%#+v", &pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")"+v4s2)
--	addFormatterTest("%#+v", nv4, "(*"+v4t+")"+"<nil>")
+-	// Map with nil interface value.
+-	k4 := "nil"
+-	k4Len := fmt.Sprintf("%d", len(k4))
+-	m4 := map[string]interface{}{k4: nil}
+-	m4Len := fmt.Sprintf("%d", len(m4))
+-	nm4 := (*map[string]interface{})(nil)
+-	pm4 := &m4
+-	m4Addr := fmt.Sprintf("%p", pm4)
+-	pm4Addr := fmt.Sprintf("%p", &pm4)
+-	m4t := "map[string]interface {}"
+-	m4t1 := "string"
+-	m4t2 := "interface {}"
+-	m4s := "(len=" + m4Len + ") {\n (" + m4t1 + ") (len=" + k4Len + ")" +
+-		" \"nil\": (" + m4t2 + ") <nil>\n}"
+-	addDumpTest(m4, "("+m4t+") "+m4s+"\n")
+-	addDumpTest(pm4, "(*"+m4t+")("+m4Addr+")("+m4s+")\n")
+-	addDumpTest(&pm4, "(**"+m4t+")("+pm4Addr+"->"+m4Addr+")("+m4s+")\n")
+-	addDumpTest(nm4, "(*"+m4t+")(<nil>)\n")
 -}
 -
--func addStructFormatterTests() {
+-func addStructDumpTests() {
 -	// Struct with primitives.
 -	type s1 struct {
 -		a int8
@@ -44511,25 +46367,11 @@ index 80c5ef9..0000000
 -	vt := "spew_test.s1"
 -	vt2 := "int8"
 -	vt3 := "uint8"
--	vs := "{127 255}"
--	vs2 := "{a:127 b:255}"
--	vs3 := "{a:(" + vt2 + ")127 b:(" + vt3 + ")255}"
--	addFormatterTest("%v", v, vs)
--	addFormatterTest("%v", pv, "<*>"+vs)
--	addFormatterTest("%v", &pv, "<**>"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%+v", v, vs2)
--	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs2)
--	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs2)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%#v", v, "("+vt+")"+vs3)
--	addFormatterTest("%#v", pv, "(*"+vt+")"+vs3)
--	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs3)
--	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
--	addFormatterTest("%#+v", v, "("+vt+")"+vs3)
--	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs3)
--	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs3)
--	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-	vs := "{\n a: (" + vt2 + ") 127,\n b: (" + vt3 + ") 255\n}"
+-	addDumpTest(v, "("+vt+") "+vs+"\n")
+-	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
+-	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
+-	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
 -
 -	// Struct that contains another struct.
 -	type s2 struct {
@@ -44546,26 +46388,12 @@ index 80c5ef9..0000000
 -	v2t3 := "int8"
 -	v2t4 := "uint8"
 -	v2t5 := "bool"
--	v2s := "{{127 255} true}"
--	v2s2 := "{s1:{a:127 b:255} b:true}"
--	v2s3 := "{s1:(" + v2t2 + "){a:(" + v2t3 + ")127 b:(" + v2t4 + ")255} b:(" +
--		v2t5 + ")true}"
--	addFormatterTest("%v", v2, v2s)
--	addFormatterTest("%v", pv2, "<*>"+v2s)
--	addFormatterTest("%v", &pv2, "<**>"+v2s)
--	addFormatterTest("%+v", nv2, "<nil>")
--	addFormatterTest("%+v", v2, v2s2)
--	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s2)
--	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s2)
--	addFormatterTest("%+v", nv2, "<nil>")
--	addFormatterTest("%#v", v2, "("+v2t+")"+v2s3)
--	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s3)
--	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s3)
--	addFormatterTest("%#v", nv2, "(*"+v2t+")"+"<nil>")
--	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s3)
--	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s3)
--	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s3)
--	addFormatterTest("%#+v", nv2, "(*"+v2t+")"+"<nil>")
+-	v2s := "{\n s1: (" + v2t2 + ") {\n  a: (" + v2t3 + ") 127,\n  b: (" +
+-		v2t4 + ") 255\n },\n b: (" + v2t5 + ") true\n}"
+-	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
+-	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
+-	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
+-	addDumpTest(nv2, "(*"+v2t+")(<nil>)\n")
 -
 -	// Struct that contains custom type with Stringer pointer interface via both
 -	// exported and unexported fields.
@@ -44580,28 +46408,16 @@ index 80c5ef9..0000000
 -	pv3Addr := fmt.Sprintf("%p", &pv3)
 -	v3t := "spew_test.s3"
 -	v3t2 := "spew_test.pstringer"
--	v3s := "{stringer test stringer test2}"
--	v3s2 := "{s:stringer test S:stringer test2}"
--	v3s3 := "{s:(" + v3t2 + ")stringer test S:(" + v3t2 + ")stringer test2}"
--	addFormatterTest("%v", v3, v3s)
--	addFormatterTest("%v", pv3, "<*>"+v3s)
--	addFormatterTest("%v", &pv3, "<**>"+v3s)
--	addFormatterTest("%+v", nv3, "<nil>")
--	addFormatterTest("%+v", v3, v3s2)
--	addFormatterTest("%+v", pv3, "<*>("+v3Addr+")"+v3s2)
--	addFormatterTest("%+v", &pv3, "<**>("+pv3Addr+"->"+v3Addr+")"+v3s2)
--	addFormatterTest("%+v", nv3, "<nil>")
--	addFormatterTest("%#v", v3, "("+v3t+")"+v3s3)
--	addFormatterTest("%#v", pv3, "(*"+v3t+")"+v3s3)
--	addFormatterTest("%#v", &pv3, "(**"+v3t+")"+v3s3)
--	addFormatterTest("%#v", nv3, "(*"+v3t+")"+"<nil>")
--	addFormatterTest("%#+v", v3, "("+v3t+")"+v3s3)
--	addFormatterTest("%#+v", pv3, "(*"+v3t+")("+v3Addr+")"+v3s3)
--	addFormatterTest("%#+v", &pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")"+v3s3)
--	addFormatterTest("%#+v", nv3, "(*"+v3t+")"+"<nil>")
+-	v3s := "{\n s: (" + v3t2 + ") (len=4) stringer test,\n S: (" + v3t2 +
+-		") (len=5) stringer test2\n}"
+-	addDumpTest(v3, "("+v3t+") "+v3s+"\n")
+-	addDumpTest(pv3, "(*"+v3t+")("+v3Addr+")("+v3s+")\n")
+-	addDumpTest(&pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")("+v3s+")\n")
+-	addDumpTest(nv3, "(*"+v3t+")(<nil>)\n")
 -
 -	// Struct that contains embedded struct and field to same struct.
 -	e := embed{"embedstr"}
+-	eLen := fmt.Sprintf("%d", len("embedstr"))
 -	v4 := embedwrap{embed: &e, e: &e}
 -	nv4 := (*embedwrap)(nil)
 -	pv4 := &v4
@@ -44611,80 +46427,44 @@ index 80c5ef9..0000000
 -	v4t := "spew_test.embedwrap"
 -	v4t2 := "spew_test.embed"
 -	v4t3 := "string"
--	v4s := "{<*>{embedstr} <*>{embedstr}}"
--	v4s2 := "{embed:<*>(" + eAddr + "){a:embedstr} e:<*>(" + eAddr +
--		"){a:embedstr}}"
--	v4s3 := "{embed:(*" + v4t2 + "){a:(" + v4t3 + ")embedstr} e:(*" + v4t2 +
--		"){a:(" + v4t3 + ")embedstr}}"
--	v4s4 := "{embed:(*" + v4t2 + ")(" + eAddr + "){a:(" + v4t3 +
--		")embedstr} e:(*" + v4t2 + ")(" + eAddr + "){a:(" + v4t3 + ")embedstr}}"
--	addFormatterTest("%v", v4, v4s)
--	addFormatterTest("%v", pv4, "<*>"+v4s)
--	addFormatterTest("%v", &pv4, "<**>"+v4s)
--	addFormatterTest("%+v", nv4, "<nil>")
--	addFormatterTest("%+v", v4, v4s2)
--	addFormatterTest("%+v", pv4, "<*>("+v4Addr+")"+v4s2)
--	addFormatterTest("%+v", &pv4, "<**>("+pv4Addr+"->"+v4Addr+")"+v4s2)
--	addFormatterTest("%+v", nv4, "<nil>")
--	addFormatterTest("%#v", v4, "("+v4t+")"+v4s3)
--	addFormatterTest("%#v", pv4, "(*"+v4t+")"+v4s3)
--	addFormatterTest("%#v", &pv4, "(**"+v4t+")"+v4s3)
--	addFormatterTest("%#v", nv4, "(*"+v4t+")"+"<nil>")
--	addFormatterTest("%#+v", v4, "("+v4t+")"+v4s4)
--	addFormatterTest("%#+v", pv4, "(*"+v4t+")("+v4Addr+")"+v4s4)
--	addFormatterTest("%#+v", &pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")"+v4s4)
--	addFormatterTest("%#+v", nv4, "(*"+v4t+")"+"<nil>")
+-	v4s := "{\n embed: (*" + v4t2 + ")(" + eAddr + ")({\n  a: (" + v4t3 +
+-		") (len=" + eLen + ") \"embedstr\"\n }),\n e: (*" + v4t2 +
+-		")(" + eAddr + ")({\n  a: (" + v4t3 + ") (len=" + eLen + ")" +
+-		" \"embedstr\"\n })\n}"
+-	addDumpTest(v4, "("+v4t+") "+v4s+"\n")
+-	addDumpTest(pv4, "(*"+v4t+")("+v4Addr+")("+v4s+")\n")
+-	addDumpTest(&pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")("+v4s+")\n")
+-	addDumpTest(nv4, "(*"+v4t+")(<nil>)\n")
 -}
 -
--func addUintptrFormatterTests() {
+-func addUintptrDumpTests() {
 -	// Null pointer.
 -	v := uintptr(0)
--	nv := (*uintptr)(nil)
 -	pv := &v
 -	vAddr := fmt.Sprintf("%p", pv)
 -	pvAddr := fmt.Sprintf("%p", &pv)
 -	vt := "uintptr"
 -	vs := "<nil>"
--	addFormatterTest("%v", v, vs)
--	addFormatterTest("%v", pv, "<*>"+vs)
--	addFormatterTest("%v", &pv, "<**>"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%+v", v, vs)
--	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
--	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%#v", v, "("+vt+")"+vs)
--	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
--	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
--	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
--	addFormatterTest("%#+v", v, "("+vt+")"+vs)
--	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
--	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-	addDumpTest(v, "("+vt+") "+vs+"\n")
+-	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
+-	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
 -
 -	// Address of real variable.
 -	i := 1
 -	v2 := uintptr(unsafe.Pointer(&i))
+-	nv2 := (*uintptr)(nil)
 -	pv2 := &v2
 -	v2Addr := fmt.Sprintf("%p", pv2)
 -	pv2Addr := fmt.Sprintf("%p", &pv2)
 -	v2t := "uintptr"
 -	v2s := fmt.Sprintf("%p", &i)
--	addFormatterTest("%v", v2, v2s)
--	addFormatterTest("%v", pv2, "<*>"+v2s)
--	addFormatterTest("%v", &pv2, "<**>"+v2s)
--	addFormatterTest("%+v", v2, v2s)
--	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
--	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
--	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
--	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
+-	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
+-	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
+-	addDumpTest(nv2, "(*"+v2t+")(<nil>)\n")
 -}
 -
--func addUnsafePointerFormatterTests() {
+-func addUnsafePointerDumpTests() {
 -	// Null pointer.
 -	v := unsafe.Pointer(uintptr(0))
 -	nv := (*unsafe.Pointer)(nil)
@@ -44693,22 +46473,10 @@ index 80c5ef9..0000000
 -	pvAddr := fmt.Sprintf("%p", &pv)
 -	vt := "unsafe.Pointer"
 -	vs := "<nil>"
--	addFormatterTest("%v", v, vs)
--	addFormatterTest("%v", pv, "<*>"+vs)
--	addFormatterTest("%v", &pv, "<**>"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%+v", v, vs)
--	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
--	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%#v", v, "("+vt+")"+vs)
--	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
--	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
--	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
--	addFormatterTest("%#+v", v, "("+vt+")"+vs)
--	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
--	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-	addDumpTest(v, "("+vt+") "+vs+"\n")
+-	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
+-	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
+-	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
 -
 -	// Address of real variable.
 -	i := 1
@@ -44718,21 +46486,13 @@ index 80c5ef9..0000000
 -	pv2Addr := fmt.Sprintf("%p", &pv2)
 -	v2t := "unsafe.Pointer"
 -	v2s := fmt.Sprintf("%p", &i)
--	addFormatterTest("%v", v2, v2s)
--	addFormatterTest("%v", pv2, "<*>"+v2s)
--	addFormatterTest("%v", &pv2, "<**>"+v2s)
--	addFormatterTest("%+v", v2, v2s)
--	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
--	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
--	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
--	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
+-	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
+-	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
+-	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
 -}
 -
--func addChanFormatterTests() {
+-func addChanDumpTests() {
 -	// Nil channel.
 -	var v chan int
 -	pv := &v
@@ -44741,22 +46501,10 @@ index 80c5ef9..0000000
 -	pvAddr := fmt.Sprintf("%p", &pv)
 -	vt := "chan int"
 -	vs := "<nil>"
--	addFormatterTest("%v", v, vs)
--	addFormatterTest("%v", pv, "<*>"+vs)
--	addFormatterTest("%v", &pv, "<**>"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%+v", v, vs)
--	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
--	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%#v", v, "("+vt+")"+vs)
--	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
--	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
--	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
--	addFormatterTest("%#+v", v, "("+vt+")"+vs)
--	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
--	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-	addDumpTest(v, "("+vt+") "+vs+"\n")
+-	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
+-	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
+-	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
 -
 -	// Real channel.
 -	v2 := make(chan int)
@@ -44765,70 +46513,37 @@ index 80c5ef9..0000000
 -	pv2Addr := fmt.Sprintf("%p", &pv2)
 -	v2t := "chan int"
 -	v2s := fmt.Sprintf("%p", v2)
--	addFormatterTest("%v", v2, v2s)
--	addFormatterTest("%v", pv2, "<*>"+v2s)
--	addFormatterTest("%v", &pv2, "<**>"+v2s)
--	addFormatterTest("%+v", v2, v2s)
--	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
--	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
--	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
--	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
+-	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
+-	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
 -}
 -
--func addFuncFormatterTests() {
+-func addFuncDumpTests() {
 -	// Function with no params and no returns.
--	v := addIntFormatterTests
+-	v := addIntDumpTests
 -	nv := (*func())(nil)
 -	pv := &v
 -	vAddr := fmt.Sprintf("%p", pv)
 -	pvAddr := fmt.Sprintf("%p", &pv)
 -	vt := "func()"
 -	vs := fmt.Sprintf("%p", v)
--	addFormatterTest("%v", v, vs)
--	addFormatterTest("%v", pv, "<*>"+vs)
--	addFormatterTest("%v", &pv, "<**>"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%+v", v, vs)
--	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
--	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%#v", v, "("+vt+")"+vs)
--	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
--	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
--	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
--	addFormatterTest("%#+v", v, "("+vt+")"+vs)
--	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
--	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-	addDumpTest(v, "("+vt+") "+vs+"\n")
+-	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
+-	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
+-	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
 -
 -	// Function with param and no returns.
--	v2 := TestFormatter
+-	v2 := TestDump
 -	nv2 := (*func(*testing.T))(nil)
 -	pv2 := &v2
 -	v2Addr := fmt.Sprintf("%p", pv2)
 -	pv2Addr := fmt.Sprintf("%p", &pv2)
 -	v2t := "func(*testing.T)"
 -	v2s := fmt.Sprintf("%p", v2)
--	addFormatterTest("%v", v2, v2s)
--	addFormatterTest("%v", pv2, "<*>"+v2s)
--	addFormatterTest("%v", &pv2, "<**>"+v2s)
--	addFormatterTest("%+v", nv2, "<nil>")
--	addFormatterTest("%+v", v2, v2s)
--	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
--	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%+v", nv2, "<nil>")
--	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
--	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
--	addFormatterTest("%#v", nv2, "(*"+v2t+")"+"<nil>")
--	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
--	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
--	addFormatterTest("%#+v", nv2, "(*"+v2t+")"+"<nil>")
+-	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
+-	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s+")\n")
+-	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s+")\n")
+-	addDumpTest(nv2, "(*"+v2t+")(<nil>)\n")
 -
 -	// Function with multiple params and multiple returns.
 -	var v3 = func(i int, s string) (b bool, err error) {
@@ -44840,25 +46555,13 @@ index 80c5ef9..0000000
 -	pv3Addr := fmt.Sprintf("%p", &pv3)
 -	v3t := "func(int, string) (bool, error)"
 -	v3s := fmt.Sprintf("%p", v3)
--	addFormatterTest("%v", v3, v3s)
--	addFormatterTest("%v", pv3, "<*>"+v3s)
--	addFormatterTest("%v", &pv3, "<**>"+v3s)
--	addFormatterTest("%+v", nv3, "<nil>")
--	addFormatterTest("%+v", v3, v3s)
--	addFormatterTest("%+v", pv3, "<*>("+v3Addr+")"+v3s)
--	addFormatterTest("%+v", &pv3, "<**>("+pv3Addr+"->"+v3Addr+")"+v3s)
--	addFormatterTest("%+v", nv3, "<nil>")
--	addFormatterTest("%#v", v3, "("+v3t+")"+v3s)
--	addFormatterTest("%#v", pv3, "(*"+v3t+")"+v3s)
--	addFormatterTest("%#v", &pv3, "(**"+v3t+")"+v3s)
--	addFormatterTest("%#v", nv3, "(*"+v3t+")"+"<nil>")
--	addFormatterTest("%#+v", v3, "("+v3t+")"+v3s)
--	addFormatterTest("%#+v", pv3, "(*"+v3t+")("+v3Addr+")"+v3s)
--	addFormatterTest("%#+v", &pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")"+v3s)
--	addFormatterTest("%#+v", nv3, "(*"+v3t+")"+"<nil>")
+-	addDumpTest(v3, "("+v3t+") "+v3s+"\n")
+-	addDumpTest(pv3, "(*"+v3t+")("+v3Addr+")("+v3s+")\n")
+-	addDumpTest(&pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")("+v3s+")\n")
+-	addDumpTest(nv3, "(*"+v3t+")(<nil>)\n")
 -}
 -
--func addCircularFormatterTests() {
+-func addCircularDumpTests() {
 -	// Struct that is circular through self referencing.
 -	type circular struct {
 -		c *circular
@@ -44869,27 +46572,12 @@ index 80c5ef9..0000000
 -	vAddr := fmt.Sprintf("%p", pv)
 -	pvAddr := fmt.Sprintf("%p", &pv)
 -	vt := "spew_test.circular"
--	vs := "{<*>{<*><shown>}}"
--	vs2 := "{<*><shown>}"
--	vs3 := "{c:<*>(" + vAddr + "){c:<*>(" + vAddr + ")<shown>}}"
--	vs4 := "{c:<*>(" + vAddr + ")<shown>}"
--	vs5 := "{c:(*" + vt + "){c:(*" + vt + ")<shown>}}"
--	vs6 := "{c:(*" + vt + ")<shown>}"
--	vs7 := "{c:(*" + vt + ")(" + vAddr + "){c:(*" + vt + ")(" + vAddr +
--		")<shown>}}"
--	vs8 := "{c:(*" + vt + ")(" + vAddr + ")<shown>}"
--	addFormatterTest("%v", v, vs)
--	addFormatterTest("%v", pv, "<*>"+vs2)
--	addFormatterTest("%v", &pv, "<**>"+vs2)
--	addFormatterTest("%+v", v, vs3)
--	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs4)
--	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs4)
--	addFormatterTest("%#v", v, "("+vt+")"+vs5)
--	addFormatterTest("%#v", pv, "(*"+vt+")"+vs6)
--	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs6)
--	addFormatterTest("%#+v", v, "("+vt+")"+vs7)
--	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs8)
--	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs8)
+-	vs := "{\n c: (*" + vt + ")(" + vAddr + ")({\n  c: (*" + vt + ")(" +
+-		vAddr + ")(<already shown>)\n })\n}"
+-	vs2 := "{\n c: (*" + vt + ")(" + vAddr + ")(<already shown>)\n}"
+-	addDumpTest(v, "("+vt+") "+vs+"\n")
+-	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs2+")\n")
+-	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs2+")\n")
 -
 -	// Structs that are circular through cross referencing.
 -	v2 := xref1{nil}
@@ -44901,31 +46589,14 @@ index 80c5ef9..0000000
 -	pv2Addr := fmt.Sprintf("%p", &pv2)
 -	v2t := "spew_test.xref1"
 -	v2t2 := "spew_test.xref2"
--	v2s := "{<*>{<*>{<*><shown>}}}"
--	v2s2 := "{<*>{<*><shown>}}"
--	v2s3 := "{ps2:<*>(" + ts2Addr + "){ps1:<*>(" + v2Addr + "){ps2:<*>(" +
--		ts2Addr + ")<shown>}}}"
--	v2s4 := "{ps2:<*>(" + ts2Addr + "){ps1:<*>(" + v2Addr + ")<shown>}}"
--	v2s5 := "{ps2:(*" + v2t2 + "){ps1:(*" + v2t + "){ps2:(*" + v2t2 +
--		")<shown>}}}"
--	v2s6 := "{ps2:(*" + v2t2 + "){ps1:(*" + v2t + ")<shown>}}"
--	v2s7 := "{ps2:(*" + v2t2 + ")(" + ts2Addr + "){ps1:(*" + v2t +
--		")(" + v2Addr + "){ps2:(*" + v2t2 + ")(" + ts2Addr +
--		")<shown>}}}"
--	v2s8 := "{ps2:(*" + v2t2 + ")(" + ts2Addr + "){ps1:(*" + v2t +
--		")(" + v2Addr + ")<shown>}}"
--	addFormatterTest("%v", v2, v2s)
--	addFormatterTest("%v", pv2, "<*>"+v2s2)
--	addFormatterTest("%v", &pv2, "<**>"+v2s2)
--	addFormatterTest("%+v", v2, v2s3)
--	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s4)
--	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s4)
--	addFormatterTest("%#v", v2, "("+v2t+")"+v2s5)
--	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s6)
--	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s6)
--	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s7)
--	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s8)
--	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s8)
+-	v2s := "{\n ps2: (*" + v2t2 + ")(" + ts2Addr + ")({\n  ps1: (*" + v2t +
+-		")(" + v2Addr + ")({\n   ps2: (*" + v2t2 + ")(" + ts2Addr +
+-		")(<already shown>)\n  })\n })\n}"
+-	v2s2 := "{\n ps2: (*" + v2t2 + ")(" + ts2Addr + ")({\n  ps1: (*" + v2t +
+-		")(" + v2Addr + ")(<already shown>)\n })\n}"
+-	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
+-	addDumpTest(pv2, "(*"+v2t+")("+v2Addr+")("+v2s2+")\n")
+-	addDumpTest(&pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")("+v2s2+")\n")
 -
 -	// Structs that are indirectly circular.
 -	v3 := indirCir1{nil}
@@ -44941,36 +46612,19 @@ index 80c5ef9..0000000
 -	v3t := "spew_test.indirCir1"
 -	v3t2 := "spew_test.indirCir2"
 -	v3t3 := "spew_test.indirCir3"
--	v3s := "{<*>{<*>{<*>{<*><shown>}}}}"
--	v3s2 := "{<*>{<*>{<*><shown>}}}"
--	v3s3 := "{ps2:<*>(" + tic2Addr + "){ps3:<*>(" + tic3Addr + "){ps1:<*>(" +
--		v3Addr + "){ps2:<*>(" + tic2Addr + ")<shown>}}}}"
--	v3s4 := "{ps2:<*>(" + tic2Addr + "){ps3:<*>(" + tic3Addr + "){ps1:<*>(" +
--		v3Addr + ")<shown>}}}"
--	v3s5 := "{ps2:(*" + v3t2 + "){ps3:(*" + v3t3 + "){ps1:(*" + v3t +
--		"){ps2:(*" + v3t2 + ")<shown>}}}}"
--	v3s6 := "{ps2:(*" + v3t2 + "){ps3:(*" + v3t3 + "){ps1:(*" + v3t +
--		")<shown>}}}"
--	v3s7 := "{ps2:(*" + v3t2 + ")(" + tic2Addr + "){ps3:(*" + v3t3 + ")(" +
--		tic3Addr + "){ps1:(*" + v3t + ")(" + v3Addr + "){ps2:(*" + v3t2 +
--		")(" + tic2Addr + ")<shown>}}}}"
--	v3s8 := "{ps2:(*" + v3t2 + ")(" + tic2Addr + "){ps3:(*" + v3t3 + ")(" +
--		tic3Addr + "){ps1:(*" + v3t + ")(" + v3Addr + ")<shown>}}}"
--	addFormatterTest("%v", v3, v3s)
--	addFormatterTest("%v", pv3, "<*>"+v3s2)
--	addFormatterTest("%v", &pv3, "<**>"+v3s2)
--	addFormatterTest("%+v", v3, v3s3)
--	addFormatterTest("%+v", pv3, "<*>("+v3Addr+")"+v3s4)
--	addFormatterTest("%+v", &pv3, "<**>("+pv3Addr+"->"+v3Addr+")"+v3s4)
--	addFormatterTest("%#v", v3, "("+v3t+")"+v3s5)
--	addFormatterTest("%#v", pv3, "(*"+v3t+")"+v3s6)
--	addFormatterTest("%#v", &pv3, "(**"+v3t+")"+v3s6)
--	addFormatterTest("%#+v", v3, "("+v3t+")"+v3s7)
--	addFormatterTest("%#+v", pv3, "(*"+v3t+")("+v3Addr+")"+v3s8)
--	addFormatterTest("%#+v", &pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")"+v3s8)
+-	v3s := "{\n ps2: (*" + v3t2 + ")(" + tic2Addr + ")({\n  ps3: (*" + v3t3 +
+-		")(" + tic3Addr + ")({\n   ps1: (*" + v3t + ")(" + v3Addr +
+-		")({\n    ps2: (*" + v3t2 + ")(" + tic2Addr +
+-		")(<already shown>)\n   })\n  })\n })\n}"
+-	v3s2 := "{\n ps2: (*" + v3t2 + ")(" + tic2Addr + ")({\n  ps3: (*" + v3t3 +
+-		")(" + tic3Addr + ")({\n   ps1: (*" + v3t + ")(" + v3Addr +
+-		")(<already shown>)\n  })\n })\n}"
+-	addDumpTest(v3, "("+v3t+") "+v3s+"\n")
+-	addDumpTest(pv3, "(*"+v3t+")("+v3Addr+")("+v3s2+")\n")
+-	addDumpTest(&pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")("+v3s2+")\n")
 -}
 -
--func addPanicFormatterTests() {
+-func addPanicDumpTests() {
 -	// Type that panics in its Stringer interface.
 -	v := panicer(127)
 -	nv := (*panicer)(nil)
@@ -44979,25 +46633,13 @@ index 80c5ef9..0000000
 -	pvAddr := fmt.Sprintf("%p", &pv)
 -	vt := "spew_test.panicer"
 -	vs := "(PANIC=test panic)127"
--	addFormatterTest("%v", v, vs)
--	addFormatterTest("%v", pv, "<*>"+vs)
--	addFormatterTest("%v", &pv, "<**>"+vs)
--	addFormatterTest("%v", nv, "<nil>")
--	addFormatterTest("%+v", v, vs)
--	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
--	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%#v", v, "("+vt+")"+vs)
--	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
--	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
--	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
--	addFormatterTest("%#+v", v, "("+vt+")"+vs)
--	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
--	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-	addDumpTest(v, "("+vt+") "+vs+"\n")
+-	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
+-	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
+-	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
 -}
 -
--func addErrorFormatterTests() {
+-func addErrorDumpTests() {
 -	// Type that has a custom Error interface.
 -	v := customError(127)
 -	nv := (*customError)(nil)
@@ -45006,276 +46648,201 @@ index 80c5ef9..0000000
 -	pvAddr := fmt.Sprintf("%p", &pv)
 -	vt := "spew_test.customError"
 -	vs := "error: 127"
--	addFormatterTest("%v", v, vs)
--	addFormatterTest("%v", pv, "<*>"+vs)
--	addFormatterTest("%v", &pv, "<**>"+vs)
--	addFormatterTest("%v", nv, "<nil>")
--	addFormatterTest("%+v", v, vs)
--	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
--	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%+v", nv, "<nil>")
--	addFormatterTest("%#v", v, "("+vt+")"+vs)
--	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
--	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
--	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
--	addFormatterTest("%#+v", v, "("+vt+")"+vs)
--	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
--	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
--	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-	addDumpTest(v, "("+vt+") "+vs+"\n")
+-	addDumpTest(pv, "(*"+vt+")("+vAddr+")("+vs+")\n")
+-	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")("+vs+")\n")
+-	addDumpTest(nv, "(*"+vt+")(<nil>)\n")
 -}
 -
--func addPassthroughFormatterTests() {
--	// %x passthrough with uint.
--	v := uint(4294967295)
--	pv := &v
--	vAddr := fmt.Sprintf("%x", pv)
--	pvAddr := fmt.Sprintf("%x", &pv)
--	vs := "ffffffff"
--	addFormatterTest("%x", v, vs)
--	addFormatterTest("%x", pv, vAddr)
--	addFormatterTest("%x", &pv, pvAddr)
--
--	// %#x passthrough with uint.
--	v2 := int(2147483647)
--	pv2 := &v2
--	v2Addr := fmt.Sprintf("%#x", pv2)
--	pv2Addr := fmt.Sprintf("%#x", &pv2)
--	v2s := "0x7fffffff"
--	addFormatterTest("%#x", v2, v2s)
--	addFormatterTest("%#x", pv2, v2Addr)
--	addFormatterTest("%#x", &pv2, pv2Addr)
--
--	// %f passthrough with precision.
--	addFormatterTest("%.2f", 3.1415, "3.14")
--	addFormatterTest("%.3f", 3.1415, "3.142")
--	addFormatterTest("%.4f", 3.1415, "3.1415")
--
--	// %f passthrough with width and precision.
--	addFormatterTest("%5.2f", 3.1415, " 3.14")
--	addFormatterTest("%6.3f", 3.1415, " 3.142")
--	addFormatterTest("%7.4f", 3.1415, " 3.1415")
--
--	// %d passthrough with width.
--	addFormatterTest("%3d", 127, "127")
--	addFormatterTest("%4d", 127, " 127")
--	addFormatterTest("%5d", 127, "  127")
--
--	// %q passthrough with string.
--	addFormatterTest("%q", "test", "\"test\"")
--}
--
--// TestFormatter executes all of the tests described by formatterTests.
--func TestFormatter(t *testing.T) {
+-// TestDump executes all of the tests described by dumpTests.
+-func TestDump(t *testing.T) {
 -	// Setup tests.
--	addIntFormatterTests()
--	addUintFormatterTests()
--	addBoolFormatterTests()
--	addFloatFormatterTests()
--	addComplexFormatterTests()
--	addArrayFormatterTests()
--	addSliceFormatterTests()
--	addStringFormatterTests()
--	addInterfaceFormatterTests()
--	addMapFormatterTests()
--	addStructFormatterTests()
--	addUintptrFormatterTests()
--	addUnsafePointerFormatterTests()
--	addChanFormatterTests()
--	addFuncFormatterTests()
--	addCircularFormatterTests()
--	addPanicFormatterTests()
--	addErrorFormatterTests()
--	addPassthroughFormatterTests()
+-	addIntDumpTests()
+-	addUintDumpTests()
+-	addBoolDumpTests()
+-	addFloatDumpTests()
+-	addComplexDumpTests()
+-	addArrayDumpTests()
+-	addSliceDumpTests()
+-	addStringDumpTests()
+-	addInterfaceDumpTests()
+-	addMapDumpTests()
+-	addStructDumpTests()
+-	addUintptrDumpTests()
+-	addUnsafePointerDumpTests()
+-	addChanDumpTests()
+-	addFuncDumpTests()
+-	addCircularDumpTests()
+-	addPanicDumpTests()
+-	addErrorDumpTests()
+-	addCgoDumpTests()
 -
--	t.Logf("Running %d tests", len(formatterTests))
--	for i, test := range formatterTests {
+-	t.Logf("Running %d tests", len(dumpTests))
+-	for i, test := range dumpTests {
 -		buf := new(bytes.Buffer)
--		spew.Fprintf(buf, test.format, test.in)
+-		spew.Fdump(buf, test.in)
 -		s := buf.String()
 -		if testFailed(s, test.wants) {
--			t.Errorf("Formatter #%d format: %s got: %s %s", i, test.format, s,
--				stringizeWants(test.wants))
+-			t.Errorf("Dump #%d\n got: %s %s", i, s, stringizeWants(test.wants))
 -			continue
 -		}
 -	}
 -}
 -
--func TestPrintSortedKeys(t *testing.T) {
+-func TestDumpSortedKeys(t *testing.T) {
 -	cfg := spew.ConfigState{SortKeys: true}
--	s := cfg.Sprint(map[int]string{1: "1", 3: "3", 2: "2"})
--	expected := "map[1:1 2:2 3:3]"
+-	s := cfg.Sdump(map[int]string{1: "1", 3: "3", 2: "2"})
+-	expected := `(map[int]string) (len=3) {
+-(int) 1: (string) (len=1) "1",
+-(int) 2: (string) (len=1) "2",
+-(int) 3: (string) (len=1) "3"
+-}
+-`
 -	if s != expected {
 -		t.Errorf("Sorted keys mismatch:\n  %v %v", s, expected)
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/internal_test.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/internal_test.go
+diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dumpcgo_test.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dumpcgo_test.go
 deleted file mode 100644
-index 10dc0b1..0000000
---- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/internal_test.go
+index 9b8a358..0000000
+--- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dumpcgo_test.go
 +++ /dev/null
-@@ -1,156 +0,0 @@
--/*
-- * Copyright (c) 2013 Dave Collins <dave at davec.name>
-- *
-- * Permission to use, copy, modify, and distribute this software for any
-- * purpose with or without fee is hereby granted, provided that the above
-- * copyright notice and this permission notice appear in all copies.
-- *
-- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
-- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
-- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
-- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
-- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
-- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
-- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
-- */
+@@ -1,97 +0,0 @@
+-// Copyright (c) 2013 Dave Collins <dave at davec.name>
+-//
+-// Permission to use, copy, modify, and distribute this software for any
+-// purpose with or without fee is hereby granted, provided that the above
+-// copyright notice and this permission notice appear in all copies.
+-//
+-// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+-// WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+-// MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+-// ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+-// WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+-// ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+-// OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
 -
--/*
--This test file is part of the spew package rather than than the spew_test
--package because it needs access to internals to properly test certain cases
--which are not possible via the public interface since they should never happen.
--*/
+-// NOTE: Due to the following build constraints, this file will only be compiled
+-// when both cgo is supported and "-tags testcgo" is added to the go test
+-// command line.  This means the cgo tests are only added (and hence run) when
+-// specifially requested.  This configuration is used because spew itself
+-// does not require cgo to run even though it does handle certain cgo types
+-// specially.  Rather than forcing all clients to require cgo and an external
+-// C compiler just to run the tests, this scheme makes them optional.
+-// +build cgo,testcgo
 -
--package spew
+-package spew_test
 -
 -import (
--	"bytes"
--	"reflect"
--	"testing"
--	"unsafe"
+-	"fmt"
+-	"github.com/davecgh/go-spew/spew/testdata"
 -)
 -
--// dummyFmtState implements a fake fmt.State to use for testing invalid
--// reflect.Value handling.  This is necessary because the fmt package catches
--// invalid values before invoking the formatter on them.
--type dummyFmtState struct {
--	bytes.Buffer
--}
--
--func (dfs *dummyFmtState) Flag(f int) bool {
--	if f == int('+') {
--		return true
--	}
--	return false
--}
--
--func (dfs *dummyFmtState) Precision() (int, bool) {
--	return 0, false
--}
+-func addCgoDumpTests() {
+-	// C char pointer.
+-	v := testdata.GetCgoCharPointer()
+-	nv := testdata.GetCgoNullCharPointer()
+-	pv := &v
+-	vcAddr := fmt.Sprintf("%p", v)
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "*testdata._Ctype_char"
+-	vs := "116"
+-	addDumpTest(v, "("+vt+")("+vcAddr+")("+vs+")\n")
+-	addDumpTest(pv, "(*"+vt+")("+vAddr+"->"+vcAddr+")("+vs+")\n")
+-	addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+"->"+vcAddr+")("+vs+")\n")
+-	addDumpTest(nv, "("+vt+")(<nil>)\n")
 -
--func (dfs *dummyFmtState) Width() (int, bool) {
--	return 0, false
--}
+-	// C char array.
+-	v2, v2l, v2c := testdata.GetCgoCharArray()
+-	v2Len := fmt.Sprintf("%d", v2l)
+-	v2Cap := fmt.Sprintf("%d", v2c)
+-	v2t := "[6]testdata._Ctype_char"
+-	v2s := "(len=" + v2Len + " cap=" + v2Cap + ") " +
+-		"{\n 00000000  74 65 73 74 32 00                               " +
+-		"  |test2.|\n}"
+-	addDumpTest(v2, "("+v2t+") "+v2s+"\n")
 -
--// TestInvalidReflectValue ensures the dump and formatter code handles an
--// invalid reflect value properly.  This needs access to internal state since it
--// should never happen in real code and therefore can't be tested via the public
--// API.
--func TestInvalidReflectValue(t *testing.T) {
--	i := 1
+-	// C unsigned char array.
+-	v3, v3l, v3c := testdata.GetCgoUnsignedCharArray()
+-	v3Len := fmt.Sprintf("%d", v3l)
+-	v3Cap := fmt.Sprintf("%d", v3c)
+-	v3t := "[6]testdata._Ctype_unsignedchar"
+-	v3s := "(len=" + v3Len + " cap=" + v3Cap + ") " +
+-		"{\n 00000000  74 65 73 74 33 00                               " +
+-		"  |test3.|\n}"
+-	addDumpTest(v3, "("+v3t+") "+v3s+"\n")
 -
--	// Dump invalid reflect value.
--	v := new(reflect.Value)
--	buf := new(bytes.Buffer)
--	d := dumpState{w: buf, cs: &Config}
--	d.dump(*v)
--	s := buf.String()
--	want := "<invalid>"
--	if s != want {
--		t.Errorf("InvalidReflectValue #%d\n got: %s want: %s", i, s, want)
--	}
--	i++
+-	// C signed char array.
+-	v4, v4l, v4c := testdata.GetCgoSignedCharArray()
+-	v4Len := fmt.Sprintf("%d", v4l)
+-	v4Cap := fmt.Sprintf("%d", v4c)
+-	v4t := "[6]testdata._Ctype_schar"
+-	v4t2 := "testdata._Ctype_schar"
+-	v4s := "(len=" + v4Len + " cap=" + v4Cap + ") " +
+-		"{\n (" + v4t2 + ") 116,\n (" + v4t2 + ") 101,\n (" + v4t2 +
+-		") 115,\n (" + v4t2 + ") 116,\n (" + v4t2 + ") 52,\n (" + v4t2 +
+-		") 0\n}"
+-	addDumpTest(v4, "("+v4t+") "+v4s+"\n")
 -
--	// Formatter invalid reflect value.
--	buf2 := new(dummyFmtState)
--	f := formatState{value: *v, cs: &Config, fs: buf2}
--	f.format(*v)
--	s = buf2.String()
--	want = "<invalid>"
--	if s != want {
--		t.Errorf("InvalidReflectValue #%d got: %s want: %s", i, s, want)
--	}
--}
+-	// C uint8_t array.
+-	v5, v5l, v5c := testdata.GetCgoUint8tArray()
+-	v5Len := fmt.Sprintf("%d", v5l)
+-	v5Cap := fmt.Sprintf("%d", v5c)
+-	v5t := "[6]testdata._Ctype_uint8_t"
+-	v5s := "(len=" + v5Len + " cap=" + v5Cap + ") " +
+-		"{\n 00000000  74 65 73 74 35 00                               " +
+-		"  |test5.|\n}"
+-	addDumpTest(v5, "("+v5t+") "+v5s+"\n")
 -
--// changeKind uses unsafe to intentionally change the kind of a reflect.Value to
--// the maximum kind value which does not exist.  This is needed to test the
--// fallback code which punts to the standard fmt library for new types that
--// might get added to the language.
--func changeKind(v *reflect.Value, readOnly bool) {
--	rvf := (*uintptr)(unsafe.Pointer(uintptr(unsafe.Pointer(v)) + offsetFlag))
--	*rvf = *rvf | ((1<<flagKindWidth - 1) << flagKindShift)
--	if readOnly {
--		*rvf |= flagRO
--	} else {
--		*rvf &= ^uintptr(flagRO)
--	}
+-	// C typedefed unsigned char array.
+-	v6, v6l, v6c := testdata.GetCgoTypdefedUnsignedCharArray()
+-	v6Len := fmt.Sprintf("%d", v6l)
+-	v6Cap := fmt.Sprintf("%d", v6c)
+-	v6t := "[6]testdata._Ctype_custom_uchar_t"
+-	v6s := "(len=" + v6Len + " cap=" + v6Cap + ") " +
+-		"{\n 00000000  74 65 73 74 36 00                               " +
+-		"  |test6.|\n}"
+-	addDumpTest(v6, "("+v6t+") "+v6s+"\n")
 -}
+diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dumpnocgo_test.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dumpnocgo_test.go
+deleted file mode 100644
+index 52a0971..0000000
+--- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/dumpnocgo_test.go
++++ /dev/null
+@@ -1,26 +0,0 @@
+-// Copyright (c) 2013 Dave Collins <dave at davec.name>
+-//
+-// Permission to use, copy, modify, and distribute this software for any
+-// purpose with or without fee is hereby granted, provided that the above
+-// copyright notice and this permission notice appear in all copies.
+-//
+-// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+-// WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+-// MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+-// ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+-// WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+-// ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+-// OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
 -
--// TestAddedReflectValue tests functionaly of the dump and formatter code which
--// falls back to the standard fmt library for new types that might get added to
--// the language.
--func TestAddedReflectValue(t *testing.T) {
--	i := 1
--
--	// Dump using a reflect.Value that is exported.
--	v := reflect.ValueOf(int8(5))
--	changeKind(&v, false)
--	buf := new(bytes.Buffer)
--	d := dumpState{w: buf, cs: &Config}
--	d.dump(v)
--	s := buf.String()
--	want := "(int8) 5"
--	if s != want {
--		t.Errorf("TestAddedReflectValue #%d\n got: %s want: %s", i, s, want)
--	}
--	i++
--
--	// Dump using a reflect.Value that is not exported.
--	changeKind(&v, true)
--	buf.Reset()
--	d.dump(v)
--	s = buf.String()
--	want = "(int8) <int8 Value>"
--	if s != want {
--		t.Errorf("TestAddedReflectValue #%d\n got: %s want: %s", i, s, want)
--	}
--	i++
--
--	// Formatter using a reflect.Value that is exported.
--	changeKind(&v, false)
--	buf2 := new(dummyFmtState)
--	f := formatState{value: v, cs: &Config, fs: buf2}
--	f.format(v)
--	s = buf2.String()
--	want = "5"
--	if s != want {
--		t.Errorf("TestAddedReflectValue #%d got: %s want: %s", i, s, want)
--	}
--	i++
+-// NOTE: Due to the following build constraints, this file will only be compiled
+-// when either cgo is not supported or "-tags testcgo" is not added to the go
+-// test command line.  This file intentionally does not setup any cgo tests in
+-// this scenario.
+-// +build !cgo !testcgo
 -
--	// Formatter using a reflect.Value that is not exported.
--	changeKind(&v, true)
--	buf2.Reset()
--	f = formatState{value: v, cs: &Config, fs: buf2}
--	f.format(v)
--	s = buf2.String()
--	want = "<int8 Value>"
--	if s != want {
--		t.Errorf("TestAddedReflectValue #%d got: %s want: %s", i, s, want)
--	}
--}
+-package spew_test
 -
--// SortValues makes the internal sortValues function available to the test
--// package.
--func SortValues(values []reflect.Value) {
--	sortValues(values)
+-func addCgoDumpTests() {
+-	// Don't add any tests for cgo since this file is only compiled when
+-	// there should not be any cgo tests.
 -}
-diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/spew.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/spew.go
+diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/example_test.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/example_test.go
 deleted file mode 100644
-index d8233f5..0000000
---- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/spew.go
+index a7acd14..0000000
+--- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/example_test.go
 +++ /dev/null
-@@ -1,148 +0,0 @@
+@@ -1,230 +0,0 @@
 -/*
 - * Copyright (c) 2013 Dave Collins <dave at davec.name>
 - *
@@ -45292,144 +46859,226 @@ index d8233f5..0000000
 - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
 - */
 -
--package spew
+-package spew_test
 -
 -import (
 -	"fmt"
--	"io"
+-	"github.com/davecgh/go-spew/spew"
 -)
 -
--// Errorf is a wrapper for fmt.Errorf that treats each argument as if it were
--// passed with a default Formatter interface returned by NewFormatter.  It
--// returns the formatted string as a value that satisfies error.  See
--// NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Errorf(format, spew.NewFormatter(a), spew.NewFormatter(b))
--func Errorf(format string, a ...interface{}) (err error) {
--	return fmt.Errorf(format, convertArgs(a)...)
--}
+-type Flag int
 -
--// Fprint is a wrapper for fmt.Fprint that treats each argument as if it were
--// passed with a default Formatter interface returned by NewFormatter.  It
--// returns the number of bytes written and any write error encountered.  See
--// NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Fprint(w, spew.NewFormatter(a), spew.NewFormatter(b))
--func Fprint(w io.Writer, a ...interface{}) (n int, err error) {
--	return fmt.Fprint(w, convertArgs(a)...)
--}
+-const (
+-	flagOne Flag = iota
+-	flagTwo
+-)
 -
--// Fprintf is a wrapper for fmt.Fprintf that treats each argument as if it were
--// passed with a default Formatter interface returned by NewFormatter.  It
--// returns the number of bytes written and any write error encountered.  See
--// NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Fprintf(w, format, spew.NewFormatter(a), spew.NewFormatter(b))
--func Fprintf(w io.Writer, format string, a ...interface{}) (n int, err error) {
--	return fmt.Fprintf(w, format, convertArgs(a)...)
+-var flagStrings = map[Flag]string{
+-	flagOne: "flagOne",
+-	flagTwo: "flagTwo",
 -}
 -
--// Fprintln is a wrapper for fmt.Fprintln that treats each argument as if it
--// passed with a default Formatter interface returned by NewFormatter.  See
--// NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Fprintln(w, spew.NewFormatter(a), spew.NewFormatter(b))
--func Fprintln(w io.Writer, a ...interface{}) (n int, err error) {
--	return fmt.Fprintln(w, convertArgs(a)...)
+-func (f Flag) String() string {
+-	if s, ok := flagStrings[f]; ok {
+-		return s
+-	}
+-	return fmt.Sprintf("Unknown flag (%d)", int(f))
 -}
 -
--// Print is a wrapper for fmt.Print that treats each argument as if it were
--// passed with a default Formatter interface returned by NewFormatter.  It
--// returns the number of bytes written and any write error encountered.  See
--// NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Print(spew.NewFormatter(a), spew.NewFormatter(b))
--func Print(a ...interface{}) (n int, err error) {
--	return fmt.Print(convertArgs(a)...)
+-type Bar struct {
+-	flag Flag
+-	data uintptr
 -}
 -
--// Printf is a wrapper for fmt.Printf that treats each argument as if it were
--// passed with a default Formatter interface returned by NewFormatter.  It
--// returns the number of bytes written and any write error encountered.  See
--// NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Printf(format, spew.NewFormatter(a), spew.NewFormatter(b))
--func Printf(format string, a ...interface{}) (n int, err error) {
--	return fmt.Printf(format, convertArgs(a)...)
+-type Foo struct {
+-	unexportedField Bar
+-	ExportedField   map[interface{}]interface{}
 -}
 -
--// Println is a wrapper for fmt.Println that treats each argument as if it were
--// passed with a default Formatter interface returned by NewFormatter.  It
--// returns the number of bytes written and any write error encountered.  See
--// NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Println(spew.NewFormatter(a), spew.NewFormatter(b))
--func Println(a ...interface{}) (n int, err error) {
--	return fmt.Println(convertArgs(a)...)
+-// This example demonstrates how to use Dump to dump variables to stdout.
+-func ExampleDump() {
+-	// The following package level declarations are assumed for this example:
+-	/*
+-		type Flag int
+-
+-		const (
+-			flagOne Flag = iota
+-			flagTwo
+-		)
+-
+-		var flagStrings = map[Flag]string{
+-			flagOne: "flagOne",
+-			flagTwo: "flagTwo",
+-		}
+-
+-		func (f Flag) String() string {
+-			if s, ok := flagStrings[f]; ok {
+-				return s
+-			}
+-			return fmt.Sprintf("Unknown flag (%d)", int(f))
+-		}
+-
+-		type Bar struct {
+-			flag Flag
+-			data uintptr
+-		}
+-
+-		type Foo struct {
+-			unexportedField Bar
+-			ExportedField   map[interface{}]interface{}
+-		}
+-	*/
+-
+-	// Setup some sample data structures for the example.
+-	bar := Bar{Flag(flagTwo), uintptr(0)}
+-	s1 := Foo{bar, map[interface{}]interface{}{"one": true}}
+-	f := Flag(5)
+-	b := []byte{
+-		0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18,
+-		0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 0x20,
+-		0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28,
+-		0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, 0x30,
+-		0x31, 0x32,
+-	}
+-
+-	// Dump!
+-	spew.Dump(s1, f, b)
+-
+-	// Output:
+-	// (spew_test.Foo) {
+-	//  unexportedField: (spew_test.Bar) {
+-	//   flag: (spew_test.Flag) flagTwo,
+-	//   data: (uintptr) <nil>
+-	//  },
+-	//  ExportedField: (map[interface {}]interface {}) (len=1) {
+-	//   (string) (len=3) "one": (bool) true
+-	//  }
+-	// }
+-	// (spew_test.Flag) Unknown flag (5)
+-	// ([]uint8) (len=34 cap=34) {
+-	//  00000000  11 12 13 14 15 16 17 18  19 1a 1b 1c 1d 1e 1f 20  |............... |
+-	//  00000010  21 22 23 24 25 26 27 28  29 2a 2b 2c 2d 2e 2f 30  |!"#$%&'()*+,-./0|
+-	//  00000020  31 32                                             |12|
+-	// }
+-	//
 -}
 -
--// Sprint is a wrapper for fmt.Sprint that treats each argument as if it were
--// passed with a default Formatter interface returned by NewFormatter.  It
--// returns the resulting string.  See NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Sprint(spew.NewFormatter(a), spew.NewFormatter(b))
--func Sprint(a ...interface{}) string {
--	return fmt.Sprint(convertArgs(a)...)
+-// This example demonstrates how to use Printf to display a variable with a
+-// format string and inline formatting.
+-func ExamplePrintf() {
+-	// Create a double pointer to a uint 8.
+-	ui8 := uint8(5)
+-	pui8 := &ui8
+-	ppui8 := &pui8
+-
+-	// Create a circular data type.
+-	type circular struct {
+-		ui8 uint8
+-		c   *circular
+-	}
+-	c := circular{ui8: 1}
+-	c.c = &c
+-
+-	// Print!
+-	spew.Printf("ppui8: %v\n", ppui8)
+-	spew.Printf("circular: %v\n", c)
+-
+-	// Output:
+-	// ppui8: <**>5
+-	// circular: {1 <*>{1 <*><shown>}}
 -}
 -
--// Sprintf is a wrapper for fmt.Sprintf that treats each argument as if it were
--// passed with a default Formatter interface returned by NewFormatter.  It
--// returns the resulting string.  See NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Sprintf(format, spew.NewFormatter(a), spew.NewFormatter(b))
--func Sprintf(format string, a ...interface{}) string {
--	return fmt.Sprintf(format, convertArgs(a)...)
+-// This example demonstrates how to use a ConfigState.
+-func ExampleConfigState() {
+-	// Modify the indent level of the ConfigState only.  The global
+-	// configuration is not modified.
+-	scs := spew.ConfigState{Indent: "\t"}
+-
+-	// Output using the ConfigState instance.
+-	v := map[string]int{"one": 1}
+-	scs.Printf("v: %v\n", v)
+-	scs.Dump(v)
+-
+-	// Output:
+-	// v: map[one:1]
+-	// (map[string]int) (len=1) {
+-	// 	(string) (len=3) "one": (int) 1
+-	// }
 -}
 -
--// Sprintln is a wrapper for fmt.Sprintln that treats each argument as if it
--// were passed with a default Formatter interface returned by NewFormatter.  It
--// returns the resulting string.  See NewFormatter for formatting details.
--//
--// This function is shorthand for the following syntax:
--//
--//	fmt.Sprintln(spew.NewFormatter(a), spew.NewFormatter(b))
--func Sprintln(a ...interface{}) string {
--	return fmt.Sprintln(convertArgs(a)...)
+-// This example demonstrates how to use ConfigState.Dump to dump variables to
+-// stdout
+-func ExampleConfigState_Dump() {
+-	// See the top-level Dump example for details on the types used in this
+-	// example.
+-
+-	// Create two ConfigState instances with different indentation.
+-	scs := spew.ConfigState{Indent: "\t"}
+-	scs2 := spew.ConfigState{Indent: " "}
+-
+-	// Setup some sample data structures for the example.
+-	bar := Bar{Flag(flagTwo), uintptr(0)}
+-	s1 := Foo{bar, map[interface{}]interface{}{"one": true}}
+-
+-	// Dump using the ConfigState instances.
+-	scs.Dump(s1)
+-	scs2.Dump(s1)
+-
+-	// Output:
+-	// (spew_test.Foo) {
+-	// 	unexportedField: (spew_test.Bar) {
+-	// 		flag: (spew_test.Flag) flagTwo,
+-	// 		data: (uintptr) <nil>
+-	// 	},
+-	// 	ExportedField: (map[interface {}]interface {}) (len=1) {
+-	//		(string) (len=3) "one": (bool) true
+-	// 	}
+-	// }
+-	// (spew_test.Foo) {
+-	//  unexportedField: (spew_test.Bar) {
+-	//   flag: (spew_test.Flag) flagTwo,
+-	//   data: (uintptr) <nil>
+-	//  },
+-	//  ExportedField: (map[interface {}]interface {}) (len=1) {
+-	//   (string) (len=3) "one": (bool) true
+-	//  }
+-	// }
+-	//
 -}
 -
--// convertArgs accepts a slice of arguments and returns a slice of the same
--// length with each argument converted to a default spew Formatter interface.
--func convertArgs(args []interface{}) (formatters []interface{}) {
--	formatters = make([]interface{}, len(args))
--	for index, arg := range args {
--		formatters[index] = NewFormatter(arg)
--	}
--	return formatters
+-// This example demonstrates how to use ConfigState.Printf to display a variable
+-// with a format string and inline formatting.
+-func ExampleConfigState_Printf() {
+-	// See the top-level Dump example for details on the types used in this
+-	// example.
+-
+-	// Create two ConfigState instances and modify the method handling of the
+-	// first ConfigState only.
+-	scs := spew.NewDefaultConfig()
+-	scs2 := spew.NewDefaultConfig()
+-	scs.DisableMethods = true
+-
+-	// Alternatively
+-	// scs := spew.ConfigState{Indent: " ", DisableMethods: true}
+-	// scs2 := spew.ConfigState{Indent: " "}
+-
+-	// This is of type Flag which implements a Stringer and has raw value 1.
+-	f := flagTwo
+-
+-	// Dump using the ConfigState instances.
+-	scs.Printf("f: %v\n", f)
+-	scs2.Printf("f: %v\n", f)
+-
+-	// Output:
+-	// f: 1
+-	// f: flagTwo
 -}
-diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/spew_test.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/spew_test.go
+diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/format.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/format.go
 deleted file mode 100644
-index 3831ed2..0000000
---- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/spew_test.go
+index b6b1fb0..0000000
+--- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/format.go
 +++ /dev/null
-@@ -1,308 +0,0 @@
+@@ -1,413 +0,0 @@
 -/*
 - * Copyright (c) 2013 Dave Collins <dave at davec.name>
 - *
@@ -45446,38409 +47095,96480 @@ index 3831ed2..0000000
 - * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
 - */
 -
--package spew_test
+-package spew
 -
 -import (
 -	"bytes"
 -	"fmt"
--	"github.com/davecgh/go-spew/spew"
--	"io/ioutil"
--	"os"
--	"testing"
+-	"reflect"
+-	"strconv"
+-	"strings"
 -)
 -
--// spewFunc is used to identify which public function of the spew package or
--// ConfigState a test applies to.
--type spewFunc int
--
--const (
--	fCSFdump spewFunc = iota
--	fCSFprint
--	fCSFprintf
--	fCSFprintln
--	fCSPrint
--	fCSPrintln
--	fCSSdump
--	fCSSprint
--	fCSSprintf
--	fCSSprintln
--	fCSErrorf
--	fCSNewFormatter
--	fErrorf
--	fFprint
--	fFprintln
--	fPrint
--	fPrintln
--	fSdump
--	fSprint
--	fSprintf
--	fSprintln
--)
+-// supportedFlags is a list of all the character flags supported by fmt package.
+-const supportedFlags = "0-+# "
 -
--// Map of spewFunc values to names for pretty printing.
--var spewFuncStrings = map[spewFunc]string{
--	fCSFdump:        "ConfigState.Fdump",
--	fCSFprint:       "ConfigState.Fprint",
--	fCSFprintf:      "ConfigState.Fprintf",
--	fCSFprintln:     "ConfigState.Fprintln",
--	fCSSdump:        "ConfigState.Sdump",
--	fCSPrint:        "ConfigState.Print",
--	fCSPrintln:      "ConfigState.Println",
--	fCSSprint:       "ConfigState.Sprint",
--	fCSSprintf:      "ConfigState.Sprintf",
--	fCSSprintln:     "ConfigState.Sprintln",
--	fCSErrorf:       "ConfigState.Errorf",
--	fCSNewFormatter: "ConfigState.NewFormatter",
--	fErrorf:         "spew.Errorf",
--	fFprint:         "spew.Fprint",
--	fFprintln:       "spew.Fprintln",
--	fPrint:          "spew.Print",
--	fPrintln:        "spew.Println",
--	fSdump:          "spew.Sdump",
--	fSprint:         "spew.Sprint",
--	fSprintf:        "spew.Sprintf",
--	fSprintln:       "spew.Sprintln",
+-// formatState implements the fmt.Formatter interface and contains information
+-// about the state of a formatting operation.  The NewFormatter function can
+-// be used to get a new Formatter which can be used directly as arguments
+-// in standard fmt package printing calls.
+-type formatState struct {
+-	value          interface{}
+-	fs             fmt.State
+-	depth          int
+-	pointers       map[uintptr]int
+-	ignoreNextType bool
+-	cs             *ConfigState
 -}
 -
--func (f spewFunc) String() string {
--	if s, ok := spewFuncStrings[f]; ok {
--		return s
+-// buildDefaultFormat recreates the original format string without precision
+-// and width information to pass in to fmt.Sprintf in the case of an
+-// unrecognized type.  Unless new types are added to the language, this
+-// function won't ever be called.
+-func (f *formatState) buildDefaultFormat() (format string) {
+-	buf := bytes.NewBuffer(percentBytes)
+-
+-	for _, flag := range supportedFlags {
+-		if f.fs.Flag(int(flag)) {
+-			buf.WriteRune(flag)
+-		}
 -	}
--	return fmt.Sprintf("Unknown spewFunc (%d)", int(f))
--}
 -
--// spewTest is used to describe a test to be performed against the public
--// functions of the spew package or ConfigState.
--type spewTest struct {
--	cs     *spew.ConfigState
--	f      spewFunc
--	format string
--	in     interface{}
--	want   string
+-	buf.WriteRune('v')
+-
+-	format = buf.String()
+-	return format
 -}
 -
--// spewTests houses the tests to be performed against the public functions of
--// the spew package and ConfigState.
--//
--// These tests are only intended to ensure the public functions are exercised
--// and are intentionally not exhaustive of types.  The exhaustive type
--// tests are handled in the dump and format tests.
--var spewTests []spewTest
+-// constructOrigFormat recreates the original format string including precision
+-// and width information to pass along to the standard fmt package.  This allows
+-// automatic deferral of all format strings this package doesn't support.
+-func (f *formatState) constructOrigFormat(verb rune) (format string) {
+-	buf := bytes.NewBuffer(percentBytes)
 -
--// redirStdout is a helper function to return the standard output from f as a
--// byte slice.
--func redirStdout(f func()) ([]byte, error) {
--	tempFile, err := ioutil.TempFile("", "ss-test")
--	if err != nil {
--		return nil, err
+-	for _, flag := range supportedFlags {
+-		if f.fs.Flag(int(flag)) {
+-			buf.WriteRune(flag)
+-		}
 -	}
--	fileName := tempFile.Name()
--	defer os.Remove(fileName) // Ignore error
 -
--	origStdout := os.Stdout
--	os.Stdout = tempFile
--	f()
--	os.Stdout = origStdout
--	tempFile.Close()
+-	if width, ok := f.fs.Width(); ok {
+-		buf.WriteString(strconv.Itoa(width))
+-	}
 -
--	return ioutil.ReadFile(fileName)
--}
+-	if precision, ok := f.fs.Precision(); ok {
+-		buf.Write(precisionBytes)
+-		buf.WriteString(strconv.Itoa(precision))
+-	}
 -
--func initSpewTests() {
--	// Config states with various settings.
--	scsDefault := spew.NewDefaultConfig()
--	scsNoMethods := &spew.ConfigState{Indent: " ", DisableMethods: true}
--	scsNoPmethods := &spew.ConfigState{Indent: " ", DisablePointerMethods: true}
--	scsMaxDepth := &spew.ConfigState{Indent: " ", MaxDepth: 1}
--	scsContinue := &spew.ConfigState{Indent: " ", ContinueOnMethod: true}
+-	buf.WriteRune(verb)
 -
--	// Variables for tests on types which implement Stringer interface with and
--	// without a pointer receiver.
--	ts := stringer("test")
--	tps := pstringer("test")
+-	format = buf.String()
+-	return format
+-}
 -
--	// depthTester is used to test max depth handling for structs, array, slices
--	// and maps.
--	type depthTester struct {
--		ic    indirCir1
--		arr   [1]string
--		slice []string
--		m     map[string]int
+-// unpackValue returns values inside of non-nil interfaces when possible and
+-// ensures that types for values which have been unpacked from an interface
+-// are displayed when the show types flag is also set.
+-// This is useful for data types like structs, arrays, slices, and maps which
+-// can contain varying types packed inside an interface.
+-func (f *formatState) unpackValue(v reflect.Value) reflect.Value {
+-	if v.Kind() == reflect.Interface {
+-		f.ignoreNextType = false
+-		if !v.IsNil() {
+-			v = v.Elem()
+-		}
 -	}
--	dt := depthTester{indirCir1{nil}, [1]string{"arr"}, []string{"slice"},
--		map[string]int{"one": 1}}
--
--	// Variable for tests on types which implement error interface.
--	te := customError(10)
+-	return v
+-}
 -
--	spewTests = []spewTest{
--		{scsDefault, fCSFdump, "", int8(127), "(int8) 127\n"},
--		{scsDefault, fCSFprint, "", int16(32767), "32767"},
--		{scsDefault, fCSFprintf, "%v", int32(2147483647), "2147483647"},
--		{scsDefault, fCSFprintln, "", int(2147483647), "2147483647\n"},
--		{scsDefault, fCSPrint, "", int64(9223372036854775807), "9223372036854775807"},
--		{scsDefault, fCSPrintln, "", uint8(255), "255\n"},
--		{scsDefault, fCSSdump, "", uint8(64), "(uint8) 64\n"},
--		{scsDefault, fCSSprint, "", complex(1, 2), "(1+2i)"},
--		{scsDefault, fCSSprintf, "%v", complex(float32(3), 4), "(3+4i)"},
--		{scsDefault, fCSSprintln, "", complex(float64(5), 6), "(5+6i)\n"},
--		{scsDefault, fCSErrorf, "%#v", uint16(65535), "(uint16)65535"},
--		{scsDefault, fCSNewFormatter, "%v", uint32(4294967295), "4294967295"},
--		{scsDefault, fErrorf, "%v", uint64(18446744073709551615), "18446744073709551615"},
--		{scsDefault, fFprint, "", float32(3.14), "3.14"},
--		{scsDefault, fFprintln, "", float64(6.28), "6.28\n"},
--		{scsDefault, fPrint, "", true, "true"},
--		{scsDefault, fPrintln, "", false, "false\n"},
--		{scsDefault, fSdump, "", complex(-10, -20), "(complex128) (-10-20i)\n"},
--		{scsDefault, fSprint, "", complex(-1, -2), "(-1-2i)"},
--		{scsDefault, fSprintf, "%v", complex(float32(-3), -4), "(-3-4i)"},
--		{scsDefault, fSprintln, "", complex(float64(-5), -6), "(-5-6i)\n"},
--		{scsNoMethods, fCSFprint, "", ts, "test"},
--		{scsNoMethods, fCSFprint, "", &ts, "<*>test"},
--		{scsNoMethods, fCSFprint, "", tps, "test"},
--		{scsNoMethods, fCSFprint, "", &tps, "<*>test"},
--		{scsNoPmethods, fCSFprint, "", ts, "stringer test"},
--		{scsNoPmethods, fCSFprint, "", &ts, "<*>stringer test"},
--		{scsNoPmethods, fCSFprint, "", tps, "test"},
--		{scsNoPmethods, fCSFprint, "", &tps, "<*>stringer test"},
--		{scsMaxDepth, fCSFprint, "", dt, "{{<max>} [<max>] [<max>] map[<max>]}"},
--		{scsMaxDepth, fCSFdump, "", dt, "(spew_test.depthTester) {\n" +
--			" ic: (spew_test.indirCir1) {\n  <max depth reached>\n },\n" +
--			" arr: ([1]string) (len=1 cap=1) {\n  <max depth reached>\n },\n" +
--			" slice: ([]string) (len=1 cap=1) {\n  <max depth reached>\n },\n" +
--			" m: (map[string]int) (len=1) {\n  <max depth reached>\n }\n}\n"},
--		{scsContinue, fCSFprint, "", ts, "(stringer test) test"},
--		{scsContinue, fCSFdump, "", ts, "(spew_test.stringer) " +
--			"(len=4) (stringer test) \"test\"\n"},
--		{scsContinue, fCSFprint, "", te, "(error: 10) 10"},
--		{scsContinue, fCSFdump, "", te, "(spew_test.customError) " +
--			"(error: 10) 10\n"},
+-// formatPtr handles formatting of pointers by indirecting them as necessary.
+-func (f *formatState) formatPtr(v reflect.Value) {
+-	// Display nil if top level pointer is nil.
+-	showTypes := f.fs.Flag('#')
+-	if v.IsNil() && (!showTypes || f.ignoreNextType) {
+-		f.fs.Write(nilAngleBytes)
+-		return
 -	}
--}
 -
--// TestSpew executes all of the tests described by spewTests.
--func TestSpew(t *testing.T) {
--	initSpewTests()
+-	// Remove pointers at or below the current depth from map used to detect
+-	// circular refs.
+-	for k, depth := range f.pointers {
+-		if depth >= f.depth {
+-			delete(f.pointers, k)
+-		}
+-	}
 -
--	t.Logf("Running %d tests", len(spewTests))
--	for i, test := range spewTests {
--		buf := new(bytes.Buffer)
--		switch test.f {
--		case fCSFdump:
--			test.cs.Fdump(buf, test.in)
+-	// Keep list of all dereferenced pointers to possibly show later.
+-	pointerChain := make([]uintptr, 0)
 -
--		case fCSFprint:
--			test.cs.Fprint(buf, test.in)
+-	// Figure out how many levels of indirection there are by derferencing
+-	// pointers and unpacking interfaces down the chain while detecting circular
+-	// references.
+-	nilFound := false
+-	cycleFound := false
+-	indirects := 0
+-	ve := v
+-	for ve.Kind() == reflect.Ptr {
+-		if ve.IsNil() {
+-			nilFound = true
+-			break
+-		}
+-		indirects++
+-		addr := ve.Pointer()
+-		pointerChain = append(pointerChain, addr)
+-		if pd, ok := f.pointers[addr]; ok && pd < f.depth {
+-			cycleFound = true
+-			indirects--
+-			break
+-		}
+-		f.pointers[addr] = f.depth
 -
--		case fCSFprintf:
--			test.cs.Fprintf(buf, test.format, test.in)
+-		ve = ve.Elem()
+-		if ve.Kind() == reflect.Interface {
+-			if ve.IsNil() {
+-				nilFound = true
+-				break
+-			}
+-			ve = ve.Elem()
+-		}
+-	}
 -
--		case fCSFprintln:
--			test.cs.Fprintln(buf, test.in)
+-	// Display type or indirection level depending on flags.
+-	if showTypes && !f.ignoreNextType {
+-		f.fs.Write(openParenBytes)
+-		f.fs.Write(bytes.Repeat(asteriskBytes, indirects))
+-		f.fs.Write([]byte(ve.Type().String()))
+-		f.fs.Write(closeParenBytes)
+-	} else {
+-		if nilFound || cycleFound {
+-			indirects += strings.Count(ve.Type().String(), "*")
+-		}
+-		f.fs.Write(openAngleBytes)
+-		f.fs.Write([]byte(strings.Repeat("*", indirects)))
+-		f.fs.Write(closeAngleBytes)
+-	}
 -
--		case fCSPrint:
--			b, err := redirStdout(func() { test.cs.Print(test.in) })
--			if err != nil {
--				t.Errorf("%v #%d %v", test.f, i, err)
--				continue
+-	// Display pointer information depending on flags.
+-	if f.fs.Flag('+') && (len(pointerChain) > 0) {
+-		f.fs.Write(openParenBytes)
+-		for i, addr := range pointerChain {
+-			if i > 0 {
+-				f.fs.Write(pointerChainBytes)
 -			}
--			buf.Write(b)
+-			printHexPtr(f.fs, addr)
+-		}
+-		f.fs.Write(closeParenBytes)
+-	}
 -
--		case fCSPrintln:
--			b, err := redirStdout(func() { test.cs.Println(test.in) })
--			if err != nil {
--				t.Errorf("%v #%d %v", test.f, i, err)
--				continue
--			}
--			buf.Write(b)
+-	// Display dereferenced value.
+-	switch {
+-	case nilFound == true:
+-		f.fs.Write(nilAngleBytes)
 -
--		case fCSSdump:
--			str := test.cs.Sdump(test.in)
--			buf.WriteString(str)
+-	case cycleFound == true:
+-		f.fs.Write(circularShortBytes)
 -
--		case fCSSprint:
--			str := test.cs.Sprint(test.in)
--			buf.WriteString(str)
+-	default:
+-		f.ignoreNextType = true
+-		f.format(ve)
+-	}
+-}
 -
--		case fCSSprintf:
--			str := test.cs.Sprintf(test.format, test.in)
--			buf.WriteString(str)
+-// format is the main workhorse for providing the Formatter interface.  It
+-// uses the passed reflect value to figure out what kind of object we are
+-// dealing with and formats it appropriately.  It is a recursive function,
+-// however circular data structures are detected and handled properly.
+-func (f *formatState) format(v reflect.Value) {
+-	// Handle invalid reflect values immediately.
+-	kind := v.Kind()
+-	if kind == reflect.Invalid {
+-		f.fs.Write(invalidAngleBytes)
+-		return
+-	}
 -
--		case fCSSprintln:
--			str := test.cs.Sprintln(test.in)
--			buf.WriteString(str)
+-	// Handle pointers specially.
+-	if kind == reflect.Ptr {
+-		f.formatPtr(v)
+-		return
+-	}
 -
--		case fCSErrorf:
--			err := test.cs.Errorf(test.format, test.in)
--			buf.WriteString(err.Error())
+-	// Print type information unless already handled elsewhere.
+-	if !f.ignoreNextType && f.fs.Flag('#') {
+-		f.fs.Write(openParenBytes)
+-		f.fs.Write([]byte(v.Type().String()))
+-		f.fs.Write(closeParenBytes)
+-	}
+-	f.ignoreNextType = false
 -
--		case fCSNewFormatter:
--			fmt.Fprintf(buf, test.format, test.cs.NewFormatter(test.in))
+-	// Call Stringer/error interfaces if they exist and the handle methods
+-	// flag is enabled.
+-	if !f.cs.DisableMethods {
+-		if (kind != reflect.Invalid) && (kind != reflect.Interface) {
+-			if handled := handleMethods(f.cs, f.fs, v); handled {
+-				return
+-			}
+-		}
+-	}
 -
--		case fErrorf:
--			err := spew.Errorf(test.format, test.in)
--			buf.WriteString(err.Error())
+-	switch kind {
+-	case reflect.Invalid:
+-		// Do nothing.  We should never get here since invalid has already
+-		// been handled above.
 -
--		case fFprint:
--			spew.Fprint(buf, test.in)
+-	case reflect.Bool:
+-		printBool(f.fs, v.Bool())
 -
--		case fFprintln:
--			spew.Fprintln(buf, test.in)
+-	case reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64, reflect.Int:
+-		printInt(f.fs, v.Int(), 10)
 -
--		case fPrint:
--			b, err := redirStdout(func() { spew.Print(test.in) })
--			if err != nil {
--				t.Errorf("%v #%d %v", test.f, i, err)
--				continue
--			}
--			buf.Write(b)
+-	case reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uint:
+-		printUint(f.fs, v.Uint(), 10)
 -
--		case fPrintln:
--			b, err := redirStdout(func() { spew.Println(test.in) })
--			if err != nil {
--				t.Errorf("%v #%d %v", test.f, i, err)
--				continue
--			}
--			buf.Write(b)
+-	case reflect.Float32:
+-		printFloat(f.fs, v.Float(), 32)
 -
--		case fSdump:
--			str := spew.Sdump(test.in)
--			buf.WriteString(str)
+-	case reflect.Float64:
+-		printFloat(f.fs, v.Float(), 64)
 -
--		case fSprint:
--			str := spew.Sprint(test.in)
--			buf.WriteString(str)
+-	case reflect.Complex64:
+-		printComplex(f.fs, v.Complex(), 32)
 -
--		case fSprintf:
--			str := spew.Sprintf(test.format, test.in)
--			buf.WriteString(str)
+-	case reflect.Complex128:
+-		printComplex(f.fs, v.Complex(), 64)
 -
--		case fSprintln:
--			str := spew.Sprintln(test.in)
--			buf.WriteString(str)
+-	case reflect.Slice:
+-		if v.IsNil() {
+-			f.fs.Write(nilAngleBytes)
+-			break
+-		}
+-		fallthrough
 -
--		default:
--			t.Errorf("%v #%d unrecognized function", test.f, i)
--			continue
+-	case reflect.Array:
+-		f.fs.Write(openBracketBytes)
+-		f.depth++
+-		if (f.cs.MaxDepth != 0) && (f.depth > f.cs.MaxDepth) {
+-			f.fs.Write(maxShortBytes)
+-		} else {
+-			numEntries := v.Len()
+-			for i := 0; i < numEntries; i++ {
+-				if i > 0 {
+-					f.fs.Write(spaceBytes)
+-				}
+-				f.ignoreNextType = true
+-				f.format(f.unpackValue(v.Index(i)))
+-			}
 -		}
--		s := buf.String()
--		if test.want != s {
--			t.Errorf("ConfigState #%d\n got: %s want: %s", i, s, test.want)
--			continue
+-		f.depth--
+-		f.fs.Write(closeBracketBytes)
+-
+-	case reflect.String:
+-		f.fs.Write([]byte(v.String()))
+-
+-	case reflect.Interface:
+-		// The only time we should get here is for nil interfaces due to
+-		// unpackValue calls.
+-		if v.IsNil() {
+-			f.fs.Write(nilAngleBytes)
 -		}
--	}
--}
-diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/testdata/dumpcgo.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/testdata/dumpcgo.go
-deleted file mode 100644
-index 5c87dd4..0000000
---- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/testdata/dumpcgo.go
-+++ /dev/null
-@@ -1,82 +0,0 @@
--// Copyright (c) 2013 Dave Collins <dave at davec.name>
--//
--// Permission to use, copy, modify, and distribute this software for any
--// purpose with or without fee is hereby granted, provided that the above
--// copyright notice and this permission notice appear in all copies.
--//
--// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
--// WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
--// MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
--// ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
--// WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
--// ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
--// OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
 -
--// NOTE: Due to the following build constraints, this file will only be compiled
--// when both cgo is supported and "-tags testcgo" is added to the go test
--// command line.  This code should really only be in the dumpcgo_test.go file,
--// but unfortunately Go will not allow cgo in test files, so this is a
--// workaround to allow cgo types to be tested.  This configuration is used
--// because spew itself does not require cgo to run even though it does handle
--// certain cgo types specially.  Rather than forcing all clients to require cgo
--// and an external C compiler just to run the tests, this scheme makes them
--// optional.
--// +build cgo,testcgo
+-	case reflect.Ptr:
+-		// Do nothing.  We should never get here since pointers have already
+-		// been handled above.
 -
--package testdata
+-	case reflect.Map:
+-		f.fs.Write(openMapBytes)
+-		f.depth++
+-		if (f.cs.MaxDepth != 0) && (f.depth > f.cs.MaxDepth) {
+-			f.fs.Write(maxShortBytes)
+-		} else {
+-			keys := v.MapKeys()
+-			if f.cs.SortKeys {
+-				sortValues(keys)
+-			}
+-			for i, key := range keys {
+-				if i > 0 {
+-					f.fs.Write(spaceBytes)
+-				}
+-				f.ignoreNextType = true
+-				f.format(f.unpackValue(key))
+-				f.fs.Write(colonBytes)
+-				f.ignoreNextType = true
+-				f.format(f.unpackValue(v.MapIndex(key)))
+-			}
+-		}
+-		f.depth--
+-		f.fs.Write(closeMapBytes)
 -
--/*
--#include <stdint.h>
--typedef unsigned char custom_uchar_t;
+-	case reflect.Struct:
+-		numFields := v.NumField()
+-		f.fs.Write(openBraceBytes)
+-		f.depth++
+-		if (f.cs.MaxDepth != 0) && (f.depth > f.cs.MaxDepth) {
+-			f.fs.Write(maxShortBytes)
+-		} else {
+-			vt := v.Type()
+-			for i := 0; i < numFields; i++ {
+-				if i > 0 {
+-					f.fs.Write(spaceBytes)
+-				}
+-				vtf := vt.Field(i)
+-				if f.fs.Flag('+') || f.fs.Flag('#') {
+-					f.fs.Write([]byte(vtf.Name))
+-					f.fs.Write(colonBytes)
+-				}
+-				f.format(f.unpackValue(v.Field(i)))
+-			}
+-		}
+-		f.depth--
+-		f.fs.Write(closeBraceBytes)
 -
--char            *ncp = 0;
--char            *cp = "test";
--char             ca[6] = {'t', 'e', 's', 't', '2', '\0'};
--unsigned char    uca[6] = {'t', 'e', 's', 't', '3', '\0'};
--signed char      sca[6] = {'t', 'e', 's', 't', '4', '\0'};
--uint8_t          ui8ta[6] = {'t', 'e', 's', 't', '5', '\0'};
--custom_uchar_t   tuca[6] = {'t', 'e', 's', 't', '6', '\0'};
--*/
--import "C"
+-	case reflect.Uintptr:
+-		printHexPtr(f.fs, uintptr(v.Uint()))
 -
--// GetCgoNullCharPointer returns a null char pointer via cgo.  This is only
--// used for tests.
--func GetCgoNullCharPointer() interface{} {
--	return C.ncp
--}
+-	case reflect.UnsafePointer, reflect.Chan, reflect.Func:
+-		printHexPtr(f.fs, v.Pointer())
 -
--// GetCgoCharPointer returns a char pointer via cgo.  This is only used for
--// tests.
--func GetCgoCharPointer() interface{} {
--	return C.cp
+-	// There were not any other types at the time this code was written, but
+-	// fall back to letting the default fmt package handle it if any get added.
+-	default:
+-		format := f.buildDefaultFormat()
+-		if v.CanInterface() {
+-			fmt.Fprintf(f.fs, format, v.Interface())
+-		} else {
+-			fmt.Fprintf(f.fs, format, v.String())
+-		}
+-	}
 -}
 -
--// GetCgoCharArray returns a char array via cgo and the array's len and cap.
--// This is only used for tests.
--func GetCgoCharArray() (interface{}, int, int) {
--	return C.ca, len(C.ca), cap(C.ca)
--}
+-// Format satisfies the fmt.Formatter interface. See NewFormatter for usage
+-// details.
+-func (f *formatState) Format(fs fmt.State, verb rune) {
+-	f.fs = fs
 -
--// GetCgoUnsignedCharArray returns an unsigned char array via cgo and the
--// array's len and cap.  This is only used for tests.
--func GetCgoUnsignedCharArray() (interface{}, int, int) {
--	return C.uca, len(C.uca), cap(C.uca)
--}
+-	// Use standard formatting for verbs that are not v.
+-	if verb != 'v' {
+-		format := f.constructOrigFormat(verb)
+-		fmt.Fprintf(fs, format, f.value)
+-		return
+-	}
 -
--// GetCgoSignedCharArray returns a signed char array via cgo and the array's len
--// and cap.  This is only used for tests.
--func GetCgoSignedCharArray() (interface{}, int, int) {
--	return C.sca, len(C.sca), cap(C.sca)
--}
+-	if f.value == nil {
+-		if fs.Flag('#') {
+-			fs.Write(interfaceBytes)
+-		}
+-		fs.Write(nilAngleBytes)
+-		return
+-	}
 -
--// GetCgoUint8tArray returns a uint8_t array via cgo and the array's len and
--// cap.  This is only used for tests.
--func GetCgoUint8tArray() (interface{}, int, int) {
--	return C.ui8ta, len(C.ui8ta), cap(C.ui8ta)
+-	f.format(reflect.ValueOf(f.value))
 -}
 -
--// GetCgoTypdefedUnsignedCharArray returns a typedefed unsigned char array via
--// cgo and the array's len and cap.  This is only used for tests.
--func GetCgoTypdefedUnsignedCharArray() (interface{}, int, int) {
--	return C.tuca, len(C.tuca), cap(C.tuca)
+-// newFormatter is a helper function to consolidate the logic from the various
+-// public methods which take varying config states.
+-func newFormatter(cs *ConfigState, v interface{}) fmt.Formatter {
+-	fs := &formatState{value: v, cs: cs}
+-	fs.pointers = make(map[uintptr]int)
+-	return fs
 -}
-diff --git a/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/LICENSE b/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/LICENSE
-deleted file mode 100644
-index 5782c72..0000000
---- a/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/LICENSE
-+++ /dev/null
-@@ -1,23 +0,0 @@
--Copyright (c) 2014, Elazar Leibovich
--All rights reserved.
--
--Redistribution and use in source and binary forms, with or without
--modification, are permitted provided that the following conditions are met:
 -
--* Redistributions of source code must retain the above copyright notice, this
--  list of conditions and the following disclaimer.
+-/*
+-NewFormatter returns a custom formatter that satisfies the fmt.Formatter
+-interface.  As a result, it integrates cleanly with standard fmt package
+-printing functions.  The formatter is useful for inline printing of smaller data
+-types similar to the standard %v format specifier.
 -
--* Redistributions in binary form must reproduce the above copyright notice,
--  this list of conditions and the following disclaimer in the documentation
--  and/or other materials provided with the distribution.
+-The custom formatter only responds to the %v (most compact), %+v (adds pointer
+-addresses), %#v (adds types), or %#+v (adds types and pointer addresses) verb
+-combinations.  Any other verbs such as %x and %q will be sent to the the
+-standard fmt package for formatting.  In addition, the custom formatter ignores
+-the width and precision arguments (however they will still work on the format
+-specifiers not handled by the custom formatter).
 -
--THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
--AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
--IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
--DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
--FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
--DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
--SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
--CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
--OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
--OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
-diff --git a/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/README.md b/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/README.md
+-Typically this function shouldn't be called directly.  It is much easier to make
+-use of the custom formatter by calling one of the convenience functions such as
+-Printf, Println, or Fprintf.
+-*/
+-func NewFormatter(v interface{}) fmt.Formatter {
+-	return newFormatter(&Config, v)
+-}
+diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/format_test.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/format_test.go
 deleted file mode 100644
-index a3929a8..0000000
---- a/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/README.md
+index 80c5ef9..0000000
+--- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/format_test.go
 +++ /dev/null
-@@ -1,18 +0,0 @@
--go-bindata-http
--===============
--
--Serve embedded files from [jteeuwen/go-bindata](https://github.com/jteeuwen/go-bindata) with `net/http`.
--
--[GoDoc](http://godoc.org/github.com/elazarl/go-bindata-assetfs)
--
--After running
--
--    $ go-bindata data/...
+@@ -1,1483 +0,0 @@
+-/*
+- * Copyright (c) 2013 Dave Collins <dave at davec.name>
+- *
+- * Permission to use, copy, modify, and distribute this software for any
+- * purpose with or without fee is hereby granted, provided that the above
+- * copyright notice and this permission notice appear in all copies.
+- *
+- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+- */
 -
--Use
+-/*
+-Test Summary:
+-NOTE: For each test, a nil pointer, a single pointer and double pointer to the
+-base test element are also tested to ensure proper indirection across all types.
 -
--     http.Handle("/",
--        http.FileServer(
--        &assetfs.AssetFS{Asset: Asset, AssetDir: AssetDir, Prefix: "data"}))
+-- Max int8, int16, int32, int64, int
+-- Max uint8, uint16, uint32, uint64, uint
+-- Boolean true and false
+-- Standard complex64 and complex128
+-- Array containing standard ints
+-- Array containing type with custom formatter on pointer receiver only
+-- Array containing interfaces
+-- Slice containing standard float32 values
+-- Slice containing type with custom formatter on pointer receiver only
+-- Slice containing interfaces
+-- Nil slice
+-- Standard string
+-- Nil interface
+-- Sub-interface
+-- Map with string keys and int vals
+-- Map with custom formatter type on pointer receiver only keys and vals
+-- Map with interface keys and values
+-- Map with nil interface value
+-- Struct with primitives
+-- Struct that contains another struct
+-- Struct that contains custom type with Stringer pointer interface via both
+-  exported and unexported fields
+-- Struct that contains embedded struct and field to same struct
+-- Uintptr to 0 (null pointer)
+-- Uintptr address of real variable
+-- Unsafe.Pointer to 0 (null pointer)
+-- Unsafe.Pointer to address of real variable
+-- Nil channel
+-- Standard int channel
+-- Function with no params and no returns
+-- Function with param and no returns
+-- Function with multiple params and multiple returns
+-- Struct that is circular through self referencing
+-- Structs that are circular through cross referencing
+-- Structs that are indirectly circular
+-- Type that panics in its Stringer interface
+-- Type that has a custom Error interface
+-- %x passthrough with uint
+-- %#x passthrough with uint
+-- %f passthrough with precision
+-- %f passthrough with width and precision
+-- %d passthrough with width
+-- %q passthrough with string
+-*/
 -
--to serve files embedded from the `data` directory.
-diff --git a/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/assetfs.go b/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/assetfs.go
-deleted file mode 100644
-index 83cd94d..0000000
---- a/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/assetfs.go
-+++ /dev/null
-@@ -1,141 +0,0 @@
--package assetfs
+-package spew_test
 -
 -import (
 -	"bytes"
--	"errors"
 -	"fmt"
--	"io"
--	"io/ioutil"
--	"net/http"
--	"os"
--	"path"
--	"path/filepath"
--	"time"
+-	"github.com/davecgh/go-spew/spew"
+-	"testing"
+-	"unsafe"
 -)
 -
--// FakeFile implements os.FileInfo interface for a given path and size
--type FakeFile struct {
--	// Path is the path of this file
--	Path string
--	// Dir marks of the path is a directory
--	Dir bool
--	// Len is the length of the fake file, zero if it is a directory
--	Len int64
+-// formatterTest is used to describe a test to be perfomed against NewFormatter.
+-type formatterTest struct {
+-	format string
+-	in     interface{}
+-	wants  []string
 -}
 -
--func (f *FakeFile) Name() string {
--	_, name := filepath.Split(f.Path)
--	return name
--}
+-// formatterTests houses all of the tests to be performed against NewFormatter.
+-var formatterTests = make([]formatterTest, 0)
 -
--func (f *FakeFile) Mode() os.FileMode {
--	mode := os.FileMode(0644)
--	if f.Dir {
--		return mode | os.ModeDir
--	}
--	return mode
+-// addFormatterTest is a helper method to append the passed input and desired
+-// result to formatterTests.
+-func addFormatterTest(format string, in interface{}, wants ...string) {
+-	test := formatterTest{format, in, wants}
+-	formatterTests = append(formatterTests, test)
 -}
 -
--func (f *FakeFile) ModTime() time.Time {
--	return time.Unix(0, 0)
--}
+-func addIntFormatterTests() {
+-	// Max int8.
+-	v := int8(127)
+-	nv := (*int8)(nil)
+-	pv := &v
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "int8"
+-	vs := "127"
+-	addFormatterTest("%v", v, vs)
+-	addFormatterTest("%v", pv, "<*>"+vs)
+-	addFormatterTest("%v", &pv, "<**>"+vs)
+-	addFormatterTest("%v", nv, "<nil>")
+-	addFormatterTest("%+v", v, vs)
+-	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
+-	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%#v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
+-	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
+-	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
+-	addFormatterTest("%#+v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
+-	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
 -
--func (f *FakeFile) Size() int64 {
--	return f.Len
--}
+-	// Max int16.
+-	v2 := int16(32767)
+-	nv2 := (*int16)(nil)
+-	pv2 := &v2
+-	v2Addr := fmt.Sprintf("%p", pv2)
+-	pv2Addr := fmt.Sprintf("%p", &pv2)
+-	v2t := "int16"
+-	v2s := "32767"
+-	addFormatterTest("%v", v2, v2s)
+-	addFormatterTest("%v", pv2, "<*>"+v2s)
+-	addFormatterTest("%v", &pv2, "<**>"+v2s)
+-	addFormatterTest("%v", nv2, "<nil>")
+-	addFormatterTest("%+v", v2, v2s)
+-	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", nv2, "<nil>")
+-	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
+-	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
+-	addFormatterTest("%#v", nv2, "(*"+v2t+")"+"<nil>")
+-	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", nv2, "(*"+v2t+")"+"<nil>")
 -
--func (f *FakeFile) IsDir() bool {
--	return f.Mode().IsDir()
--}
+-	// Max int32.
+-	v3 := int32(2147483647)
+-	nv3 := (*int32)(nil)
+-	pv3 := &v3
+-	v3Addr := fmt.Sprintf("%p", pv3)
+-	pv3Addr := fmt.Sprintf("%p", &pv3)
+-	v3t := "int32"
+-	v3s := "2147483647"
+-	addFormatterTest("%v", v3, v3s)
+-	addFormatterTest("%v", pv3, "<*>"+v3s)
+-	addFormatterTest("%v", &pv3, "<**>"+v3s)
+-	addFormatterTest("%v", nv3, "<nil>")
+-	addFormatterTest("%+v", v3, v3s)
+-	addFormatterTest("%+v", pv3, "<*>("+v3Addr+")"+v3s)
+-	addFormatterTest("%+v", &pv3, "<**>("+pv3Addr+"->"+v3Addr+")"+v3s)
+-	addFormatterTest("%+v", nv3, "<nil>")
+-	addFormatterTest("%#v", v3, "("+v3t+")"+v3s)
+-	addFormatterTest("%#v", pv3, "(*"+v3t+")"+v3s)
+-	addFormatterTest("%#v", &pv3, "(**"+v3t+")"+v3s)
+-	addFormatterTest("%#v", nv3, "(*"+v3t+")"+"<nil>")
+-	addFormatterTest("%#+v", v3, "("+v3t+")"+v3s)
+-	addFormatterTest("%#+v", pv3, "(*"+v3t+")("+v3Addr+")"+v3s)
+-	addFormatterTest("%#+v", &pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")"+v3s)
+-	addFormatterTest("%#v", nv3, "(*"+v3t+")"+"<nil>")
 -
--func (f *FakeFile) Sys() interface{} {
--	return nil
--}
+-	// Max int64.
+-	v4 := int64(9223372036854775807)
+-	nv4 := (*int64)(nil)
+-	pv4 := &v4
+-	v4Addr := fmt.Sprintf("%p", pv4)
+-	pv4Addr := fmt.Sprintf("%p", &pv4)
+-	v4t := "int64"
+-	v4s := "9223372036854775807"
+-	addFormatterTest("%v", v4, v4s)
+-	addFormatterTest("%v", pv4, "<*>"+v4s)
+-	addFormatterTest("%v", &pv4, "<**>"+v4s)
+-	addFormatterTest("%v", nv4, "<nil>")
+-	addFormatterTest("%+v", v4, v4s)
+-	addFormatterTest("%+v", pv4, "<*>("+v4Addr+")"+v4s)
+-	addFormatterTest("%+v", &pv4, "<**>("+pv4Addr+"->"+v4Addr+")"+v4s)
+-	addFormatterTest("%+v", nv4, "<nil>")
+-	addFormatterTest("%#v", v4, "("+v4t+")"+v4s)
+-	addFormatterTest("%#v", pv4, "(*"+v4t+")"+v4s)
+-	addFormatterTest("%#v", &pv4, "(**"+v4t+")"+v4s)
+-	addFormatterTest("%#v", nv4, "(*"+v4t+")"+"<nil>")
+-	addFormatterTest("%#+v", v4, "("+v4t+")"+v4s)
+-	addFormatterTest("%#+v", pv4, "(*"+v4t+")("+v4Addr+")"+v4s)
+-	addFormatterTest("%#+v", &pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")"+v4s)
+-	addFormatterTest("%#+v", nv4, "(*"+v4t+")"+"<nil>")
 -
--// AssetFile implements http.File interface for a no-directory file with content
--type AssetFile struct {
--	*bytes.Reader
--	io.Closer
--	FakeFile
+-	// Max int.
+-	v5 := int(2147483647)
+-	nv5 := (*int)(nil)
+-	pv5 := &v5
+-	v5Addr := fmt.Sprintf("%p", pv5)
+-	pv5Addr := fmt.Sprintf("%p", &pv5)
+-	v5t := "int"
+-	v5s := "2147483647"
+-	addFormatterTest("%v", v5, v5s)
+-	addFormatterTest("%v", pv5, "<*>"+v5s)
+-	addFormatterTest("%v", &pv5, "<**>"+v5s)
+-	addFormatterTest("%v", nv5, "<nil>")
+-	addFormatterTest("%+v", v5, v5s)
+-	addFormatterTest("%+v", pv5, "<*>("+v5Addr+")"+v5s)
+-	addFormatterTest("%+v", &pv5, "<**>("+pv5Addr+"->"+v5Addr+")"+v5s)
+-	addFormatterTest("%+v", nv5, "<nil>")
+-	addFormatterTest("%#v", v5, "("+v5t+")"+v5s)
+-	addFormatterTest("%#v", pv5, "(*"+v5t+")"+v5s)
+-	addFormatterTest("%#v", &pv5, "(**"+v5t+")"+v5s)
+-	addFormatterTest("%#v", nv5, "(*"+v5t+")"+"<nil>")
+-	addFormatterTest("%#+v", v5, "("+v5t+")"+v5s)
+-	addFormatterTest("%#+v", pv5, "(*"+v5t+")("+v5Addr+")"+v5s)
+-	addFormatterTest("%#+v", &pv5, "(**"+v5t+")("+pv5Addr+"->"+v5Addr+")"+v5s)
+-	addFormatterTest("%#+v", nv5, "(*"+v5t+")"+"<nil>")
 -}
 -
--func NewAssetFile(name string, content []byte) *AssetFile {
--	return &AssetFile{
--		bytes.NewReader(content),
--		ioutil.NopCloser(nil),
--		FakeFile{name, false, int64(len(content))}}
--}
+-func addUintFormatterTests() {
+-	// Max uint8.
+-	v := uint8(255)
+-	nv := (*uint8)(nil)
+-	pv := &v
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "uint8"
+-	vs := "255"
+-	addFormatterTest("%v", v, vs)
+-	addFormatterTest("%v", pv, "<*>"+vs)
+-	addFormatterTest("%v", &pv, "<**>"+vs)
+-	addFormatterTest("%v", nv, "<nil>")
+-	addFormatterTest("%+v", v, vs)
+-	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
+-	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%#v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
+-	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
+-	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
+-	addFormatterTest("%#+v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
+-	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
 -
--func (f *AssetFile) Readdir(count int) ([]os.FileInfo, error) {
--	return nil, errors.New("not a directory")
--}
+-	// Max uint16.
+-	v2 := uint16(65535)
+-	nv2 := (*uint16)(nil)
+-	pv2 := &v2
+-	v2Addr := fmt.Sprintf("%p", pv2)
+-	pv2Addr := fmt.Sprintf("%p", &pv2)
+-	v2t := "uint16"
+-	v2s := "65535"
+-	addFormatterTest("%v", v2, v2s)
+-	addFormatterTest("%v", pv2, "<*>"+v2s)
+-	addFormatterTest("%v", &pv2, "<**>"+v2s)
+-	addFormatterTest("%v", nv2, "<nil>")
+-	addFormatterTest("%+v", v2, v2s)
+-	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", nv2, "<nil>")
+-	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
+-	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
+-	addFormatterTest("%#v", nv2, "(*"+v2t+")"+"<nil>")
+-	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", nv2, "(*"+v2t+")"+"<nil>")
 -
--func (f *AssetFile) Stat() (os.FileInfo, error) {
--	return f, nil
--}
+-	// Max uint32.
+-	v3 := uint32(4294967295)
+-	nv3 := (*uint32)(nil)
+-	pv3 := &v3
+-	v3Addr := fmt.Sprintf("%p", pv3)
+-	pv3Addr := fmt.Sprintf("%p", &pv3)
+-	v3t := "uint32"
+-	v3s := "4294967295"
+-	addFormatterTest("%v", v3, v3s)
+-	addFormatterTest("%v", pv3, "<*>"+v3s)
+-	addFormatterTest("%v", &pv3, "<**>"+v3s)
+-	addFormatterTest("%v", nv3, "<nil>")
+-	addFormatterTest("%+v", v3, v3s)
+-	addFormatterTest("%+v", pv3, "<*>("+v3Addr+")"+v3s)
+-	addFormatterTest("%+v", &pv3, "<**>("+pv3Addr+"->"+v3Addr+")"+v3s)
+-	addFormatterTest("%+v", nv3, "<nil>")
+-	addFormatterTest("%#v", v3, "("+v3t+")"+v3s)
+-	addFormatterTest("%#v", pv3, "(*"+v3t+")"+v3s)
+-	addFormatterTest("%#v", &pv3, "(**"+v3t+")"+v3s)
+-	addFormatterTest("%#v", nv3, "(*"+v3t+")"+"<nil>")
+-	addFormatterTest("%#+v", v3, "("+v3t+")"+v3s)
+-	addFormatterTest("%#+v", pv3, "(*"+v3t+")("+v3Addr+")"+v3s)
+-	addFormatterTest("%#+v", &pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")"+v3s)
+-	addFormatterTest("%#v", nv3, "(*"+v3t+")"+"<nil>")
 -
--// AssetDirectory implements http.File interface for a directory
--type AssetDirectory struct {
--	AssetFile
--	ChildrenRead int
--	Children     []os.FileInfo
--}
+-	// Max uint64.
+-	v4 := uint64(18446744073709551615)
+-	nv4 := (*uint64)(nil)
+-	pv4 := &v4
+-	v4Addr := fmt.Sprintf("%p", pv4)
+-	pv4Addr := fmt.Sprintf("%p", &pv4)
+-	v4t := "uint64"
+-	v4s := "18446744073709551615"
+-	addFormatterTest("%v", v4, v4s)
+-	addFormatterTest("%v", pv4, "<*>"+v4s)
+-	addFormatterTest("%v", &pv4, "<**>"+v4s)
+-	addFormatterTest("%v", nv4, "<nil>")
+-	addFormatterTest("%+v", v4, v4s)
+-	addFormatterTest("%+v", pv4, "<*>("+v4Addr+")"+v4s)
+-	addFormatterTest("%+v", &pv4, "<**>("+pv4Addr+"->"+v4Addr+")"+v4s)
+-	addFormatterTest("%+v", nv4, "<nil>")
+-	addFormatterTest("%#v", v4, "("+v4t+")"+v4s)
+-	addFormatterTest("%#v", pv4, "(*"+v4t+")"+v4s)
+-	addFormatterTest("%#v", &pv4, "(**"+v4t+")"+v4s)
+-	addFormatterTest("%#v", nv4, "(*"+v4t+")"+"<nil>")
+-	addFormatterTest("%#+v", v4, "("+v4t+")"+v4s)
+-	addFormatterTest("%#+v", pv4, "(*"+v4t+")("+v4Addr+")"+v4s)
+-	addFormatterTest("%#+v", &pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")"+v4s)
+-	addFormatterTest("%#+v", nv4, "(*"+v4t+")"+"<nil>")
 -
--func NewAssetDirectory(name string, children []string, fs *AssetFS) *AssetDirectory {
--	fileinfos := make([]os.FileInfo, 0, len(children))
--	for _, child := range children {
--		_, err := fs.AssetDir(filepath.Join(name, child))
--		fileinfos = append(fileinfos, &FakeFile{child, err == nil, 0})
--	}
--	return &AssetDirectory{
--		AssetFile{
--			bytes.NewReader(nil),
--			ioutil.NopCloser(nil),
--			FakeFile{name, true, 0},
--		},
--		0,
--		fileinfos}
+-	// Max uint.
+-	v5 := uint(4294967295)
+-	nv5 := (*uint)(nil)
+-	pv5 := &v5
+-	v5Addr := fmt.Sprintf("%p", pv5)
+-	pv5Addr := fmt.Sprintf("%p", &pv5)
+-	v5t := "uint"
+-	v5s := "4294967295"
+-	addFormatterTest("%v", v5, v5s)
+-	addFormatterTest("%v", pv5, "<*>"+v5s)
+-	addFormatterTest("%v", &pv5, "<**>"+v5s)
+-	addFormatterTest("%v", nv5, "<nil>")
+-	addFormatterTest("%+v", v5, v5s)
+-	addFormatterTest("%+v", pv5, "<*>("+v5Addr+")"+v5s)
+-	addFormatterTest("%+v", &pv5, "<**>("+pv5Addr+"->"+v5Addr+")"+v5s)
+-	addFormatterTest("%+v", nv5, "<nil>")
+-	addFormatterTest("%#v", v5, "("+v5t+")"+v5s)
+-	addFormatterTest("%#v", pv5, "(*"+v5t+")"+v5s)
+-	addFormatterTest("%#v", &pv5, "(**"+v5t+")"+v5s)
+-	addFormatterTest("%#v", nv5, "(*"+v5t+")"+"<nil>")
+-	addFormatterTest("%#+v", v5, "("+v5t+")"+v5s)
+-	addFormatterTest("%#+v", pv5, "(*"+v5t+")("+v5Addr+")"+v5s)
+-	addFormatterTest("%#+v", &pv5, "(**"+v5t+")("+pv5Addr+"->"+v5Addr+")"+v5s)
+-	addFormatterTest("%#v", nv5, "(*"+v5t+")"+"<nil>")
 -}
 -
--func (f *AssetDirectory) Readdir(count int) ([]os.FileInfo, error) {
--	fmt.Println(f, count)
--	if count <= 0 {
--		return f.Children, nil
--	}
--	if f.ChildrenRead+count > len(f.Children) {
--		count = len(f.Children) - f.ChildrenRead
--	}
--	rv := f.Children[f.ChildrenRead : f.ChildrenRead+count]
--	f.ChildrenRead += count
--	return rv, nil
--}
+-func addBoolFormatterTests() {
+-	// Boolean true.
+-	v := bool(true)
+-	nv := (*bool)(nil)
+-	pv := &v
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "bool"
+-	vs := "true"
+-	addFormatterTest("%v", v, vs)
+-	addFormatterTest("%v", pv, "<*>"+vs)
+-	addFormatterTest("%v", &pv, "<**>"+vs)
+-	addFormatterTest("%v", nv, "<nil>")
+-	addFormatterTest("%+v", v, vs)
+-	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
+-	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%#v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
+-	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
+-	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
+-	addFormatterTest("%#+v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
+-	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
 -
--func (f *AssetDirectory) Stat() (os.FileInfo, error) {
--	return f, nil
+-	// Boolean false.
+-	v2 := bool(false)
+-	pv2 := &v2
+-	v2Addr := fmt.Sprintf("%p", pv2)
+-	pv2Addr := fmt.Sprintf("%p", &pv2)
+-	v2t := "bool"
+-	v2s := "false"
+-	addFormatterTest("%v", v2, v2s)
+-	addFormatterTest("%v", pv2, "<*>"+v2s)
+-	addFormatterTest("%v", &pv2, "<**>"+v2s)
+-	addFormatterTest("%+v", v2, v2s)
+-	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
+-	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
+-	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
 -}
 -
--// AssetFS implements http.FileSystem, allowing
--// embedded files to be served from net/http package.
--type AssetFS struct {
--	// Asset should return content of file in path if exists
--	Asset func(path string) ([]byte, error)
--	// AssetDir should return list of files in the path
--	AssetDir func(path string) ([]string, error)
--	// Prefix would be prepended to http requests
--	Prefix string
--}
+-func addFloatFormatterTests() {
+-	// Standard float32.
+-	v := float32(3.1415)
+-	nv := (*float32)(nil)
+-	pv := &v
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "float32"
+-	vs := "3.1415"
+-	addFormatterTest("%v", v, vs)
+-	addFormatterTest("%v", pv, "<*>"+vs)
+-	addFormatterTest("%v", &pv, "<**>"+vs)
+-	addFormatterTest("%v", nv, "<nil>")
+-	addFormatterTest("%+v", v, vs)
+-	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
+-	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%#v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
+-	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
+-	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
+-	addFormatterTest("%#+v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
+-	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
 -
--func (fs *AssetFS) Open(name string) (http.File, error) {
--	name = path.Join(fs.Prefix, name)
--	if len(name) > 0 && name[0] == '/' {
--		name = name[1:]
--	}
--	if children, err := fs.AssetDir(name); err == nil {
--		return NewAssetDirectory(name, children, fs), nil
--	}
--	b, err := fs.Asset(name)
--	if err != nil {
--		return nil, err
--	}
--	return NewAssetFile(name, b), nil
+-	// Standard float64.
+-	v2 := float64(3.1415926)
+-	nv2 := (*float64)(nil)
+-	pv2 := &v2
+-	v2Addr := fmt.Sprintf("%p", pv2)
+-	pv2Addr := fmt.Sprintf("%p", &pv2)
+-	v2t := "float64"
+-	v2s := "3.1415926"
+-	addFormatterTest("%v", v2, v2s)
+-	addFormatterTest("%v", pv2, "<*>"+v2s)
+-	addFormatterTest("%v", &pv2, "<**>"+v2s)
+-	addFormatterTest("%+v", nv2, "<nil>")
+-	addFormatterTest("%+v", v2, v2s)
+-	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", nv2, "<nil>")
+-	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
+-	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
+-	addFormatterTest("%#v", nv2, "(*"+v2t+")"+"<nil>")
+-	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", nv2, "(*"+v2t+")"+"<nil>")
 -}
-diff --git a/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/doc.go b/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/doc.go
-deleted file mode 100644
-index a664249..0000000
---- a/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/doc.go
-+++ /dev/null
-@@ -1,13 +0,0 @@
--// assetfs allows packages to serve static content embedded
--// with the go-bindata tool with the standard net/http package.
--//
--// See https://github.com/jteeuwen/go-bindata for more information
--// about embedding binary data with go-bindata.
--//
--// Usage example, after running
--//    $ go-bindata data/...
--// use:
--//     http.Handle("/",
--//        http.FileServer(
--//        &assetfs.AssetFS{Asset: Asset, AssetDir: AssetDir, Prefix: "data"}))
--package assetfs
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/.gitignore b/Godeps/_workspace/src/github.com/emicklei/go-restful/.gitignore
-deleted file mode 100644
-index cece7be..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/.gitignore
-+++ /dev/null
-@@ -1,70 +0,0 @@
--# Compiled Object files, Static and Dynamic libs (Shared Objects)
--*.o
--*.a
--*.so
--
--# Folders
--_obj
--_test
--
--# Architecture specific extensions/prefixes
--*.[568vq]
--[568vq].out
--
--*.cgo1.go
--*.cgo2.c
--_cgo_defun.c
--_cgo_gotypes.go
--_cgo_export.*
 -
--_testmain.go
--
--*.exe
--
--restful.html
--
--*.out
--
--tmp.prof
+-func addComplexFormatterTests() {
+-	// Standard complex64.
+-	v := complex(float32(6), -2)
+-	nv := (*complex64)(nil)
+-	pv := &v
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "complex64"
+-	vs := "(6-2i)"
+-	addFormatterTest("%v", v, vs)
+-	addFormatterTest("%v", pv, "<*>"+vs)
+-	addFormatterTest("%v", &pv, "<**>"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%+v", v, vs)
+-	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
+-	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%#v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
+-	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
+-	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
+-	addFormatterTest("%#+v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
+-	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
 -
--go-restful.test
+-	// Standard complex128.
+-	v2 := complex(float64(-6), 2)
+-	nv2 := (*complex128)(nil)
+-	pv2 := &v2
+-	v2Addr := fmt.Sprintf("%p", pv2)
+-	pv2Addr := fmt.Sprintf("%p", &pv2)
+-	v2t := "complex128"
+-	v2s := "(-6+2i)"
+-	addFormatterTest("%v", v2, v2s)
+-	addFormatterTest("%v", pv2, "<*>"+v2s)
+-	addFormatterTest("%v", &pv2, "<**>"+v2s)
+-	addFormatterTest("%+v", nv2, "<nil>")
+-	addFormatterTest("%+v", v2, v2s)
+-	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", nv2, "<nil>")
+-	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
+-	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
+-	addFormatterTest("%#v", nv2, "(*"+v2t+")"+"<nil>")
+-	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", nv2, "(*"+v2t+")"+"<nil>")
+-}
 -
--examples/restful-basic-authentication
+-func addArrayFormatterTests() {
+-	// Array containing standard ints.
+-	v := [3]int{1, 2, 3}
+-	nv := (*[3]int)(nil)
+-	pv := &v
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "[3]int"
+-	vs := "[1 2 3]"
+-	addFormatterTest("%v", v, vs)
+-	addFormatterTest("%v", pv, "<*>"+vs)
+-	addFormatterTest("%v", &pv, "<**>"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%+v", v, vs)
+-	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
+-	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%#v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
+-	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
+-	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
+-	addFormatterTest("%#+v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
+-	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
 -
--examples/restful-encoding-filter
+-	// Array containing type with custom formatter on pointer receiver only.
+-	v2 := [3]pstringer{"1", "2", "3"}
+-	nv2 := (*[3]pstringer)(nil)
+-	pv2 := &v2
+-	v2Addr := fmt.Sprintf("%p", pv2)
+-	pv2Addr := fmt.Sprintf("%p", &pv2)
+-	v2t := "[3]spew_test.pstringer"
+-	v2s := "[stringer 1 stringer 2 stringer 3]"
+-	addFormatterTest("%v", v2, v2s)
+-	addFormatterTest("%v", pv2, "<*>"+v2s)
+-	addFormatterTest("%v", &pv2, "<**>"+v2s)
+-	addFormatterTest("%+v", nv2, "<nil>")
+-	addFormatterTest("%+v", v2, v2s)
+-	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", nv2, "<nil>")
+-	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
+-	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
+-	addFormatterTest("%#v", nv2, "(*"+v2t+")"+"<nil>")
+-	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", nv2, "(*"+v2t+")"+"<nil>")
 -
--examples/restful-filters
+-	// Array containing interfaces.
+-	v3 := [3]interface{}{"one", int(2), uint(3)}
+-	nv3 := (*[3]interface{})(nil)
+-	pv3 := &v3
+-	v3Addr := fmt.Sprintf("%p", pv3)
+-	pv3Addr := fmt.Sprintf("%p", &pv3)
+-	v3t := "[3]interface {}"
+-	v3t2 := "string"
+-	v3t3 := "int"
+-	v3t4 := "uint"
+-	v3s := "[one 2 3]"
+-	v3s2 := "[(" + v3t2 + ")one (" + v3t3 + ")2 (" + v3t4 + ")3]"
+-	addFormatterTest("%v", v3, v3s)
+-	addFormatterTest("%v", pv3, "<*>"+v3s)
+-	addFormatterTest("%v", &pv3, "<**>"+v3s)
+-	addFormatterTest("%+v", nv3, "<nil>")
+-	addFormatterTest("%+v", v3, v3s)
+-	addFormatterTest("%+v", pv3, "<*>("+v3Addr+")"+v3s)
+-	addFormatterTest("%+v", &pv3, "<**>("+pv3Addr+"->"+v3Addr+")"+v3s)
+-	addFormatterTest("%+v", nv3, "<nil>")
+-	addFormatterTest("%#v", v3, "("+v3t+")"+v3s2)
+-	addFormatterTest("%#v", pv3, "(*"+v3t+")"+v3s2)
+-	addFormatterTest("%#v", &pv3, "(**"+v3t+")"+v3s2)
+-	addFormatterTest("%#v", nv3, "(*"+v3t+")"+"<nil>")
+-	addFormatterTest("%#+v", v3, "("+v3t+")"+v3s2)
+-	addFormatterTest("%#+v", pv3, "(*"+v3t+")("+v3Addr+")"+v3s2)
+-	addFormatterTest("%#+v", &pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")"+v3s2)
+-	addFormatterTest("%#+v", nv3, "(*"+v3t+")"+"<nil>")
+-}
+-
+-func addSliceFormatterTests() {
+-	// Slice containing standard float32 values.
+-	v := []float32{3.14, 6.28, 12.56}
+-	nv := (*[]float32)(nil)
+-	pv := &v
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "[]float32"
+-	vs := "[3.14 6.28 12.56]"
+-	addFormatterTest("%v", v, vs)
+-	addFormatterTest("%v", pv, "<*>"+vs)
+-	addFormatterTest("%v", &pv, "<**>"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%+v", v, vs)
+-	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
+-	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%#v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
+-	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
+-	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
+-	addFormatterTest("%#+v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
+-	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-
+-	// Slice containing type with custom formatter on pointer receiver only.
+-	v2 := []pstringer{"1", "2", "3"}
+-	nv2 := (*[]pstringer)(nil)
+-	pv2 := &v2
+-	v2Addr := fmt.Sprintf("%p", pv2)
+-	pv2Addr := fmt.Sprintf("%p", &pv2)
+-	v2t := "[]spew_test.pstringer"
+-	v2s := "[stringer 1 stringer 2 stringer 3]"
+-	addFormatterTest("%v", v2, v2s)
+-	addFormatterTest("%v", pv2, "<*>"+v2s)
+-	addFormatterTest("%v", &pv2, "<**>"+v2s)
+-	addFormatterTest("%+v", nv2, "<nil>")
+-	addFormatterTest("%+v", v2, v2s)
+-	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", nv2, "<nil>")
+-	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
+-	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
+-	addFormatterTest("%#v", nv2, "(*"+v2t+")"+"<nil>")
+-	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", nv2, "(*"+v2t+")"+"<nil>")
+-
+-	// Slice containing interfaces.
+-	v3 := []interface{}{"one", int(2), uint(3), nil}
+-	nv3 := (*[]interface{})(nil)
+-	pv3 := &v3
+-	v3Addr := fmt.Sprintf("%p", pv3)
+-	pv3Addr := fmt.Sprintf("%p", &pv3)
+-	v3t := "[]interface {}"
+-	v3t2 := "string"
+-	v3t3 := "int"
+-	v3t4 := "uint"
+-	v3t5 := "interface {}"
+-	v3s := "[one 2 3 <nil>]"
+-	v3s2 := "[(" + v3t2 + ")one (" + v3t3 + ")2 (" + v3t4 + ")3 (" + v3t5 +
+-		")<nil>]"
+-	addFormatterTest("%v", v3, v3s)
+-	addFormatterTest("%v", pv3, "<*>"+v3s)
+-	addFormatterTest("%v", &pv3, "<**>"+v3s)
+-	addFormatterTest("%+v", nv3, "<nil>")
+-	addFormatterTest("%+v", v3, v3s)
+-	addFormatterTest("%+v", pv3, "<*>("+v3Addr+")"+v3s)
+-	addFormatterTest("%+v", &pv3, "<**>("+pv3Addr+"->"+v3Addr+")"+v3s)
+-	addFormatterTest("%+v", nv3, "<nil>")
+-	addFormatterTest("%#v", v3, "("+v3t+")"+v3s2)
+-	addFormatterTest("%#v", pv3, "(*"+v3t+")"+v3s2)
+-	addFormatterTest("%#v", &pv3, "(**"+v3t+")"+v3s2)
+-	addFormatterTest("%#v", nv3, "(*"+v3t+")"+"<nil>")
+-	addFormatterTest("%#+v", v3, "("+v3t+")"+v3s2)
+-	addFormatterTest("%#+v", pv3, "(*"+v3t+")("+v3Addr+")"+v3s2)
+-	addFormatterTest("%#+v", &pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")"+v3s2)
+-	addFormatterTest("%#+v", nv3, "(*"+v3t+")"+"<nil>")
+-
+-	// Nil slice.
+-	var v4 []int
+-	nv4 := (*[]int)(nil)
+-	pv4 := &v4
+-	v4Addr := fmt.Sprintf("%p", pv4)
+-	pv4Addr := fmt.Sprintf("%p", &pv4)
+-	v4t := "[]int"
+-	v4s := "<nil>"
+-	addFormatterTest("%v", v4, v4s)
+-	addFormatterTest("%v", pv4, "<*>"+v4s)
+-	addFormatterTest("%v", &pv4, "<**>"+v4s)
+-	addFormatterTest("%+v", nv4, "<nil>")
+-	addFormatterTest("%+v", v4, v4s)
+-	addFormatterTest("%+v", pv4, "<*>("+v4Addr+")"+v4s)
+-	addFormatterTest("%+v", &pv4, "<**>("+pv4Addr+"->"+v4Addr+")"+v4s)
+-	addFormatterTest("%+v", nv4, "<nil>")
+-	addFormatterTest("%#v", v4, "("+v4t+")"+v4s)
+-	addFormatterTest("%#v", pv4, "(*"+v4t+")"+v4s)
+-	addFormatterTest("%#v", &pv4, "(**"+v4t+")"+v4s)
+-	addFormatterTest("%#v", nv4, "(*"+v4t+")"+"<nil>")
+-	addFormatterTest("%#+v", v4, "("+v4t+")"+v4s)
+-	addFormatterTest("%#+v", pv4, "(*"+v4t+")("+v4Addr+")"+v4s)
+-	addFormatterTest("%#+v", &pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")"+v4s)
+-	addFormatterTest("%#+v", nv4, "(*"+v4t+")"+"<nil>")
+-}
+-
+-func addStringFormatterTests() {
+-	// Standard string.
+-	v := "test"
+-	nv := (*string)(nil)
+-	pv := &v
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "string"
+-	vs := "test"
+-	addFormatterTest("%v", v, vs)
+-	addFormatterTest("%v", pv, "<*>"+vs)
+-	addFormatterTest("%v", &pv, "<**>"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%+v", v, vs)
+-	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
+-	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%#v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
+-	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
+-	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
+-	addFormatterTest("%#+v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
+-	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-}
+-
+-func addInterfaceFormatterTests() {
+-	// Nil interface.
+-	var v interface{}
+-	nv := (*interface{})(nil)
+-	pv := &v
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "interface {}"
+-	vs := "<nil>"
+-	addFormatterTest("%v", v, vs)
+-	addFormatterTest("%v", pv, "<*>"+vs)
+-	addFormatterTest("%v", &pv, "<**>"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%+v", v, vs)
+-	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
+-	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%#v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
+-	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
+-	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
+-	addFormatterTest("%#+v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
+-	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-
+-	// Sub-interface.
+-	v2 := interface{}(uint16(65535))
+-	pv2 := &v2
+-	v2Addr := fmt.Sprintf("%p", pv2)
+-	pv2Addr := fmt.Sprintf("%p", &pv2)
+-	v2t := "uint16"
+-	v2s := "65535"
+-	addFormatterTest("%v", v2, v2s)
+-	addFormatterTest("%v", pv2, "<*>"+v2s)
+-	addFormatterTest("%v", &pv2, "<**>"+v2s)
+-	addFormatterTest("%+v", v2, v2s)
+-	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
+-	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
+-	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
+-}
+-
+-func addMapFormatterTests() {
+-	// Map with string keys and int vals.
+-	v := map[string]int{"one": 1, "two": 2}
+-	nv := (*map[string]int)(nil)
+-	pv := &v
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "map[string]int"
+-	vs := "map[one:1 two:2]"
+-	vs2 := "map[two:2 one:1]"
+-	addFormatterTest("%v", v, vs, vs2)
+-	addFormatterTest("%v", pv, "<*>"+vs, "<*>"+vs2)
+-	addFormatterTest("%v", &pv, "<**>"+vs, "<**>"+vs2)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%+v", v, vs, vs2)
+-	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs, "<*>("+vAddr+")"+vs2)
+-	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs,
+-		"<**>("+pvAddr+"->"+vAddr+")"+vs2)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%#v", v, "("+vt+")"+vs, "("+vt+")"+vs2)
+-	addFormatterTest("%#v", pv, "(*"+vt+")"+vs, "(*"+vt+")"+vs2)
+-	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs, "(**"+vt+")"+vs2)
+-	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
+-	addFormatterTest("%#+v", v, "("+vt+")"+vs, "("+vt+")"+vs2)
+-	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs,
+-		"(*"+vt+")("+vAddr+")"+vs2)
+-	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs,
+-		"(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs2)
+-	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-
+-	// Map with custom formatter type on pointer receiver only keys and vals.
+-	v2 := map[pstringer]pstringer{"one": "1"}
+-	nv2 := (*map[pstringer]pstringer)(nil)
+-	pv2 := &v2
+-	v2Addr := fmt.Sprintf("%p", pv2)
+-	pv2Addr := fmt.Sprintf("%p", &pv2)
+-	v2t := "map[spew_test.pstringer]spew_test.pstringer"
+-	v2s := "map[stringer one:stringer 1]"
+-	addFormatterTest("%v", v2, v2s)
+-	addFormatterTest("%v", pv2, "<*>"+v2s)
+-	addFormatterTest("%v", &pv2, "<**>"+v2s)
+-	addFormatterTest("%+v", nv2, "<nil>")
+-	addFormatterTest("%+v", v2, v2s)
+-	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", nv2, "<nil>")
+-	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
+-	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
+-	addFormatterTest("%#v", nv2, "(*"+v2t+")"+"<nil>")
+-	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", nv2, "(*"+v2t+")"+"<nil>")
+-
+-	// Map with interface keys and values.
+-	v3 := map[interface{}]interface{}{"one": 1}
+-	nv3 := (*map[interface{}]interface{})(nil)
+-	pv3 := &v3
+-	v3Addr := fmt.Sprintf("%p", pv3)
+-	pv3Addr := fmt.Sprintf("%p", &pv3)
+-	v3t := "map[interface {}]interface {}"
+-	v3t1 := "string"
+-	v3t2 := "int"
+-	v3s := "map[one:1]"
+-	v3s2 := "map[(" + v3t1 + ")one:(" + v3t2 + ")1]"
+-	addFormatterTest("%v", v3, v3s)
+-	addFormatterTest("%v", pv3, "<*>"+v3s)
+-	addFormatterTest("%v", &pv3, "<**>"+v3s)
+-	addFormatterTest("%+v", nv3, "<nil>")
+-	addFormatterTest("%+v", v3, v3s)
+-	addFormatterTest("%+v", pv3, "<*>("+v3Addr+")"+v3s)
+-	addFormatterTest("%+v", &pv3, "<**>("+pv3Addr+"->"+v3Addr+")"+v3s)
+-	addFormatterTest("%+v", nv3, "<nil>")
+-	addFormatterTest("%#v", v3, "("+v3t+")"+v3s2)
+-	addFormatterTest("%#v", pv3, "(*"+v3t+")"+v3s2)
+-	addFormatterTest("%#v", &pv3, "(**"+v3t+")"+v3s2)
+-	addFormatterTest("%#v", nv3, "(*"+v3t+")"+"<nil>")
+-	addFormatterTest("%#+v", v3, "("+v3t+")"+v3s2)
+-	addFormatterTest("%#+v", pv3, "(*"+v3t+")("+v3Addr+")"+v3s2)
+-	addFormatterTest("%#+v", &pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")"+v3s2)
+-	addFormatterTest("%#+v", nv3, "(*"+v3t+")"+"<nil>")
+-
+-	// Map with nil interface value
+-	v4 := map[string]interface{}{"nil": nil}
+-	nv4 := (*map[string]interface{})(nil)
+-	pv4 := &v4
+-	v4Addr := fmt.Sprintf("%p", pv4)
+-	pv4Addr := fmt.Sprintf("%p", &pv4)
+-	v4t := "map[string]interface {}"
+-	v4t1 := "interface {}"
+-	v4s := "map[nil:<nil>]"
+-	v4s2 := "map[nil:(" + v4t1 + ")<nil>]"
+-	addFormatterTest("%v", v4, v4s)
+-	addFormatterTest("%v", pv4, "<*>"+v4s)
+-	addFormatterTest("%v", &pv4, "<**>"+v4s)
+-	addFormatterTest("%+v", nv4, "<nil>")
+-	addFormatterTest("%+v", v4, v4s)
+-	addFormatterTest("%+v", pv4, "<*>("+v4Addr+")"+v4s)
+-	addFormatterTest("%+v", &pv4, "<**>("+pv4Addr+"->"+v4Addr+")"+v4s)
+-	addFormatterTest("%+v", nv4, "<nil>")
+-	addFormatterTest("%#v", v4, "("+v4t+")"+v4s2)
+-	addFormatterTest("%#v", pv4, "(*"+v4t+")"+v4s2)
+-	addFormatterTest("%#v", &pv4, "(**"+v4t+")"+v4s2)
+-	addFormatterTest("%#v", nv4, "(*"+v4t+")"+"<nil>")
+-	addFormatterTest("%#+v", v4, "("+v4t+")"+v4s2)
+-	addFormatterTest("%#+v", pv4, "(*"+v4t+")("+v4Addr+")"+v4s2)
+-	addFormatterTest("%#+v", &pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")"+v4s2)
+-	addFormatterTest("%#+v", nv4, "(*"+v4t+")"+"<nil>")
+-}
+-
+-func addStructFormatterTests() {
+-	// Struct with primitives.
+-	type s1 struct {
+-		a int8
+-		b uint8
+-	}
+-	v := s1{127, 255}
+-	nv := (*s1)(nil)
+-	pv := &v
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "spew_test.s1"
+-	vt2 := "int8"
+-	vt3 := "uint8"
+-	vs := "{127 255}"
+-	vs2 := "{a:127 b:255}"
+-	vs3 := "{a:(" + vt2 + ")127 b:(" + vt3 + ")255}"
+-	addFormatterTest("%v", v, vs)
+-	addFormatterTest("%v", pv, "<*>"+vs)
+-	addFormatterTest("%v", &pv, "<**>"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%+v", v, vs2)
+-	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs2)
+-	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs2)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%#v", v, "("+vt+")"+vs3)
+-	addFormatterTest("%#v", pv, "(*"+vt+")"+vs3)
+-	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs3)
+-	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
+-	addFormatterTest("%#+v", v, "("+vt+")"+vs3)
+-	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs3)
+-	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs3)
+-	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-
+-	// Struct that contains another struct.
+-	type s2 struct {
+-		s1 s1
+-		b  bool
+-	}
+-	v2 := s2{s1{127, 255}, true}
+-	nv2 := (*s2)(nil)
+-	pv2 := &v2
+-	v2Addr := fmt.Sprintf("%p", pv2)
+-	pv2Addr := fmt.Sprintf("%p", &pv2)
+-	v2t := "spew_test.s2"
+-	v2t2 := "spew_test.s1"
+-	v2t3 := "int8"
+-	v2t4 := "uint8"
+-	v2t5 := "bool"
+-	v2s := "{{127 255} true}"
+-	v2s2 := "{s1:{a:127 b:255} b:true}"
+-	v2s3 := "{s1:(" + v2t2 + "){a:(" + v2t3 + ")127 b:(" + v2t4 + ")255} b:(" +
+-		v2t5 + ")true}"
+-	addFormatterTest("%v", v2, v2s)
+-	addFormatterTest("%v", pv2, "<*>"+v2s)
+-	addFormatterTest("%v", &pv2, "<**>"+v2s)
+-	addFormatterTest("%+v", nv2, "<nil>")
+-	addFormatterTest("%+v", v2, v2s2)
+-	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s2)
+-	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s2)
+-	addFormatterTest("%+v", nv2, "<nil>")
+-	addFormatterTest("%#v", v2, "("+v2t+")"+v2s3)
+-	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s3)
+-	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s3)
+-	addFormatterTest("%#v", nv2, "(*"+v2t+")"+"<nil>")
+-	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s3)
+-	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s3)
+-	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s3)
+-	addFormatterTest("%#+v", nv2, "(*"+v2t+")"+"<nil>")
+-
+-	// Struct that contains custom type with Stringer pointer interface via both
+-	// exported and unexported fields.
+-	type s3 struct {
+-		s pstringer
+-		S pstringer
+-	}
+-	v3 := s3{"test", "test2"}
+-	nv3 := (*s3)(nil)
+-	pv3 := &v3
+-	v3Addr := fmt.Sprintf("%p", pv3)
+-	pv3Addr := fmt.Sprintf("%p", &pv3)
+-	v3t := "spew_test.s3"
+-	v3t2 := "spew_test.pstringer"
+-	v3s := "{stringer test stringer test2}"
+-	v3s2 := "{s:stringer test S:stringer test2}"
+-	v3s3 := "{s:(" + v3t2 + ")stringer test S:(" + v3t2 + ")stringer test2}"
+-	addFormatterTest("%v", v3, v3s)
+-	addFormatterTest("%v", pv3, "<*>"+v3s)
+-	addFormatterTest("%v", &pv3, "<**>"+v3s)
+-	addFormatterTest("%+v", nv3, "<nil>")
+-	addFormatterTest("%+v", v3, v3s2)
+-	addFormatterTest("%+v", pv3, "<*>("+v3Addr+")"+v3s2)
+-	addFormatterTest("%+v", &pv3, "<**>("+pv3Addr+"->"+v3Addr+")"+v3s2)
+-	addFormatterTest("%+v", nv3, "<nil>")
+-	addFormatterTest("%#v", v3, "("+v3t+")"+v3s3)
+-	addFormatterTest("%#v", pv3, "(*"+v3t+")"+v3s3)
+-	addFormatterTest("%#v", &pv3, "(**"+v3t+")"+v3s3)
+-	addFormatterTest("%#v", nv3, "(*"+v3t+")"+"<nil>")
+-	addFormatterTest("%#+v", v3, "("+v3t+")"+v3s3)
+-	addFormatterTest("%#+v", pv3, "(*"+v3t+")("+v3Addr+")"+v3s3)
+-	addFormatterTest("%#+v", &pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")"+v3s3)
+-	addFormatterTest("%#+v", nv3, "(*"+v3t+")"+"<nil>")
+-
+-	// Struct that contains embedded struct and field to same struct.
+-	e := embed{"embedstr"}
+-	v4 := embedwrap{embed: &e, e: &e}
+-	nv4 := (*embedwrap)(nil)
+-	pv4 := &v4
+-	eAddr := fmt.Sprintf("%p", &e)
+-	v4Addr := fmt.Sprintf("%p", pv4)
+-	pv4Addr := fmt.Sprintf("%p", &pv4)
+-	v4t := "spew_test.embedwrap"
+-	v4t2 := "spew_test.embed"
+-	v4t3 := "string"
+-	v4s := "{<*>{embedstr} <*>{embedstr}}"
+-	v4s2 := "{embed:<*>(" + eAddr + "){a:embedstr} e:<*>(" + eAddr +
+-		"){a:embedstr}}"
+-	v4s3 := "{embed:(*" + v4t2 + "){a:(" + v4t3 + ")embedstr} e:(*" + v4t2 +
+-		"){a:(" + v4t3 + ")embedstr}}"
+-	v4s4 := "{embed:(*" + v4t2 + ")(" + eAddr + "){a:(" + v4t3 +
+-		")embedstr} e:(*" + v4t2 + ")(" + eAddr + "){a:(" + v4t3 + ")embedstr}}"
+-	addFormatterTest("%v", v4, v4s)
+-	addFormatterTest("%v", pv4, "<*>"+v4s)
+-	addFormatterTest("%v", &pv4, "<**>"+v4s)
+-	addFormatterTest("%+v", nv4, "<nil>")
+-	addFormatterTest("%+v", v4, v4s2)
+-	addFormatterTest("%+v", pv4, "<*>("+v4Addr+")"+v4s2)
+-	addFormatterTest("%+v", &pv4, "<**>("+pv4Addr+"->"+v4Addr+")"+v4s2)
+-	addFormatterTest("%+v", nv4, "<nil>")
+-	addFormatterTest("%#v", v4, "("+v4t+")"+v4s3)
+-	addFormatterTest("%#v", pv4, "(*"+v4t+")"+v4s3)
+-	addFormatterTest("%#v", &pv4, "(**"+v4t+")"+v4s3)
+-	addFormatterTest("%#v", nv4, "(*"+v4t+")"+"<nil>")
+-	addFormatterTest("%#+v", v4, "("+v4t+")"+v4s4)
+-	addFormatterTest("%#+v", pv4, "(*"+v4t+")("+v4Addr+")"+v4s4)
+-	addFormatterTest("%#+v", &pv4, "(**"+v4t+")("+pv4Addr+"->"+v4Addr+")"+v4s4)
+-	addFormatterTest("%#+v", nv4, "(*"+v4t+")"+"<nil>")
+-}
+-
+-func addUintptrFormatterTests() {
+-	// Null pointer.
+-	v := uintptr(0)
+-	nv := (*uintptr)(nil)
+-	pv := &v
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "uintptr"
+-	vs := "<nil>"
+-	addFormatterTest("%v", v, vs)
+-	addFormatterTest("%v", pv, "<*>"+vs)
+-	addFormatterTest("%v", &pv, "<**>"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%+v", v, vs)
+-	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
+-	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%#v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
+-	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
+-	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
+-	addFormatterTest("%#+v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
+-	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-
+-	// Address of real variable.
+-	i := 1
+-	v2 := uintptr(unsafe.Pointer(&i))
+-	pv2 := &v2
+-	v2Addr := fmt.Sprintf("%p", pv2)
+-	pv2Addr := fmt.Sprintf("%p", &pv2)
+-	v2t := "uintptr"
+-	v2s := fmt.Sprintf("%p", &i)
+-	addFormatterTest("%v", v2, v2s)
+-	addFormatterTest("%v", pv2, "<*>"+v2s)
+-	addFormatterTest("%v", &pv2, "<**>"+v2s)
+-	addFormatterTest("%+v", v2, v2s)
+-	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
+-	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
+-	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
+-}
+-
+-func addUnsafePointerFormatterTests() {
+-	// Null pointer.
+-	v := unsafe.Pointer(uintptr(0))
+-	nv := (*unsafe.Pointer)(nil)
+-	pv := &v
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "unsafe.Pointer"
+-	vs := "<nil>"
+-	addFormatterTest("%v", v, vs)
+-	addFormatterTest("%v", pv, "<*>"+vs)
+-	addFormatterTest("%v", &pv, "<**>"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%+v", v, vs)
+-	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
+-	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%#v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
+-	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
+-	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
+-	addFormatterTest("%#+v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
+-	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-
+-	// Address of real variable.
+-	i := 1
+-	v2 := unsafe.Pointer(&i)
+-	pv2 := &v2
+-	v2Addr := fmt.Sprintf("%p", pv2)
+-	pv2Addr := fmt.Sprintf("%p", &pv2)
+-	v2t := "unsafe.Pointer"
+-	v2s := fmt.Sprintf("%p", &i)
+-	addFormatterTest("%v", v2, v2s)
+-	addFormatterTest("%v", pv2, "<*>"+v2s)
+-	addFormatterTest("%v", &pv2, "<**>"+v2s)
+-	addFormatterTest("%+v", v2, v2s)
+-	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
+-	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
+-	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
+-}
+-
+-func addChanFormatterTests() {
+-	// Nil channel.
+-	var v chan int
+-	pv := &v
+-	nv := (*chan int)(nil)
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "chan int"
+-	vs := "<nil>"
+-	addFormatterTest("%v", v, vs)
+-	addFormatterTest("%v", pv, "<*>"+vs)
+-	addFormatterTest("%v", &pv, "<**>"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%+v", v, vs)
+-	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
+-	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%#v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
+-	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
+-	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
+-	addFormatterTest("%#+v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
+-	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-
+-	// Real channel.
+-	v2 := make(chan int)
+-	pv2 := &v2
+-	v2Addr := fmt.Sprintf("%p", pv2)
+-	pv2Addr := fmt.Sprintf("%p", &pv2)
+-	v2t := "chan int"
+-	v2s := fmt.Sprintf("%p", v2)
+-	addFormatterTest("%v", v2, v2s)
+-	addFormatterTest("%v", pv2, "<*>"+v2s)
+-	addFormatterTest("%v", &pv2, "<**>"+v2s)
+-	addFormatterTest("%+v", v2, v2s)
+-	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
+-	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
+-	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
+-}
+-
+-func addFuncFormatterTests() {
+-	// Function with no params and no returns.
+-	v := addIntFormatterTests
+-	nv := (*func())(nil)
+-	pv := &v
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "func()"
+-	vs := fmt.Sprintf("%p", v)
+-	addFormatterTest("%v", v, vs)
+-	addFormatterTest("%v", pv, "<*>"+vs)
+-	addFormatterTest("%v", &pv, "<**>"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%+v", v, vs)
+-	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
+-	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%#v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
+-	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
+-	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
+-	addFormatterTest("%#+v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
+-	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-
+-	// Function with param and no returns.
+-	v2 := TestFormatter
+-	nv2 := (*func(*testing.T))(nil)
+-	pv2 := &v2
+-	v2Addr := fmt.Sprintf("%p", pv2)
+-	pv2Addr := fmt.Sprintf("%p", &pv2)
+-	v2t := "func(*testing.T)"
+-	v2s := fmt.Sprintf("%p", v2)
+-	addFormatterTest("%v", v2, v2s)
+-	addFormatterTest("%v", pv2, "<*>"+v2s)
+-	addFormatterTest("%v", &pv2, "<**>"+v2s)
+-	addFormatterTest("%+v", nv2, "<nil>")
+-	addFormatterTest("%+v", v2, v2s)
+-	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%+v", nv2, "<nil>")
+-	addFormatterTest("%#v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s)
+-	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s)
+-	addFormatterTest("%#v", nv2, "(*"+v2t+")"+"<nil>")
+-	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s)
+-	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s)
+-	addFormatterTest("%#+v", nv2, "(*"+v2t+")"+"<nil>")
+-
+-	// Function with multiple params and multiple returns.
+-	var v3 = func(i int, s string) (b bool, err error) {
+-		return true, nil
+-	}
+-	nv3 := (*func(int, string) (bool, error))(nil)
+-	pv3 := &v3
+-	v3Addr := fmt.Sprintf("%p", pv3)
+-	pv3Addr := fmt.Sprintf("%p", &pv3)
+-	v3t := "func(int, string) (bool, error)"
+-	v3s := fmt.Sprintf("%p", v3)
+-	addFormatterTest("%v", v3, v3s)
+-	addFormatterTest("%v", pv3, "<*>"+v3s)
+-	addFormatterTest("%v", &pv3, "<**>"+v3s)
+-	addFormatterTest("%+v", nv3, "<nil>")
+-	addFormatterTest("%+v", v3, v3s)
+-	addFormatterTest("%+v", pv3, "<*>("+v3Addr+")"+v3s)
+-	addFormatterTest("%+v", &pv3, "<**>("+pv3Addr+"->"+v3Addr+")"+v3s)
+-	addFormatterTest("%+v", nv3, "<nil>")
+-	addFormatterTest("%#v", v3, "("+v3t+")"+v3s)
+-	addFormatterTest("%#v", pv3, "(*"+v3t+")"+v3s)
+-	addFormatterTest("%#v", &pv3, "(**"+v3t+")"+v3s)
+-	addFormatterTest("%#v", nv3, "(*"+v3t+")"+"<nil>")
+-	addFormatterTest("%#+v", v3, "("+v3t+")"+v3s)
+-	addFormatterTest("%#+v", pv3, "(*"+v3t+")("+v3Addr+")"+v3s)
+-	addFormatterTest("%#+v", &pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")"+v3s)
+-	addFormatterTest("%#+v", nv3, "(*"+v3t+")"+"<nil>")
+-}
+-
+-func addCircularFormatterTests() {
+-	// Struct that is circular through self referencing.
+-	type circular struct {
+-		c *circular
+-	}
+-	v := circular{nil}
+-	v.c = &v
+-	pv := &v
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "spew_test.circular"
+-	vs := "{<*>{<*><shown>}}"
+-	vs2 := "{<*><shown>}"
+-	vs3 := "{c:<*>(" + vAddr + "){c:<*>(" + vAddr + ")<shown>}}"
+-	vs4 := "{c:<*>(" + vAddr + ")<shown>}"
+-	vs5 := "{c:(*" + vt + "){c:(*" + vt + ")<shown>}}"
+-	vs6 := "{c:(*" + vt + ")<shown>}"
+-	vs7 := "{c:(*" + vt + ")(" + vAddr + "){c:(*" + vt + ")(" + vAddr +
+-		")<shown>}}"
+-	vs8 := "{c:(*" + vt + ")(" + vAddr + ")<shown>}"
+-	addFormatterTest("%v", v, vs)
+-	addFormatterTest("%v", pv, "<*>"+vs2)
+-	addFormatterTest("%v", &pv, "<**>"+vs2)
+-	addFormatterTest("%+v", v, vs3)
+-	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs4)
+-	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs4)
+-	addFormatterTest("%#v", v, "("+vt+")"+vs5)
+-	addFormatterTest("%#v", pv, "(*"+vt+")"+vs6)
+-	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs6)
+-	addFormatterTest("%#+v", v, "("+vt+")"+vs7)
+-	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs8)
+-	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs8)
+-
+-	// Structs that are circular through cross referencing.
+-	v2 := xref1{nil}
+-	ts2 := xref2{&v2}
+-	v2.ps2 = &ts2
+-	pv2 := &v2
+-	ts2Addr := fmt.Sprintf("%p", &ts2)
+-	v2Addr := fmt.Sprintf("%p", pv2)
+-	pv2Addr := fmt.Sprintf("%p", &pv2)
+-	v2t := "spew_test.xref1"
+-	v2t2 := "spew_test.xref2"
+-	v2s := "{<*>{<*>{<*><shown>}}}"
+-	v2s2 := "{<*>{<*><shown>}}"
+-	v2s3 := "{ps2:<*>(" + ts2Addr + "){ps1:<*>(" + v2Addr + "){ps2:<*>(" +
+-		ts2Addr + ")<shown>}}}"
+-	v2s4 := "{ps2:<*>(" + ts2Addr + "){ps1:<*>(" + v2Addr + ")<shown>}}"
+-	v2s5 := "{ps2:(*" + v2t2 + "){ps1:(*" + v2t + "){ps2:(*" + v2t2 +
+-		")<shown>}}}"
+-	v2s6 := "{ps2:(*" + v2t2 + "){ps1:(*" + v2t + ")<shown>}}"
+-	v2s7 := "{ps2:(*" + v2t2 + ")(" + ts2Addr + "){ps1:(*" + v2t +
+-		")(" + v2Addr + "){ps2:(*" + v2t2 + ")(" + ts2Addr +
+-		")<shown>}}}"
+-	v2s8 := "{ps2:(*" + v2t2 + ")(" + ts2Addr + "){ps1:(*" + v2t +
+-		")(" + v2Addr + ")<shown>}}"
+-	addFormatterTest("%v", v2, v2s)
+-	addFormatterTest("%v", pv2, "<*>"+v2s2)
+-	addFormatterTest("%v", &pv2, "<**>"+v2s2)
+-	addFormatterTest("%+v", v2, v2s3)
+-	addFormatterTest("%+v", pv2, "<*>("+v2Addr+")"+v2s4)
+-	addFormatterTest("%+v", &pv2, "<**>("+pv2Addr+"->"+v2Addr+")"+v2s4)
+-	addFormatterTest("%#v", v2, "("+v2t+")"+v2s5)
+-	addFormatterTest("%#v", pv2, "(*"+v2t+")"+v2s6)
+-	addFormatterTest("%#v", &pv2, "(**"+v2t+")"+v2s6)
+-	addFormatterTest("%#+v", v2, "("+v2t+")"+v2s7)
+-	addFormatterTest("%#+v", pv2, "(*"+v2t+")("+v2Addr+")"+v2s8)
+-	addFormatterTest("%#+v", &pv2, "(**"+v2t+")("+pv2Addr+"->"+v2Addr+")"+v2s8)
+-
+-	// Structs that are indirectly circular.
+-	v3 := indirCir1{nil}
+-	tic2 := indirCir2{nil}
+-	tic3 := indirCir3{&v3}
+-	tic2.ps3 = &tic3
+-	v3.ps2 = &tic2
+-	pv3 := &v3
+-	tic2Addr := fmt.Sprintf("%p", &tic2)
+-	tic3Addr := fmt.Sprintf("%p", &tic3)
+-	v3Addr := fmt.Sprintf("%p", pv3)
+-	pv3Addr := fmt.Sprintf("%p", &pv3)
+-	v3t := "spew_test.indirCir1"
+-	v3t2 := "spew_test.indirCir2"
+-	v3t3 := "spew_test.indirCir3"
+-	v3s := "{<*>{<*>{<*>{<*><shown>}}}}"
+-	v3s2 := "{<*>{<*>{<*><shown>}}}"
+-	v3s3 := "{ps2:<*>(" + tic2Addr + "){ps3:<*>(" + tic3Addr + "){ps1:<*>(" +
+-		v3Addr + "){ps2:<*>(" + tic2Addr + ")<shown>}}}}"
+-	v3s4 := "{ps2:<*>(" + tic2Addr + "){ps3:<*>(" + tic3Addr + "){ps1:<*>(" +
+-		v3Addr + ")<shown>}}}"
+-	v3s5 := "{ps2:(*" + v3t2 + "){ps3:(*" + v3t3 + "){ps1:(*" + v3t +
+-		"){ps2:(*" + v3t2 + ")<shown>}}}}"
+-	v3s6 := "{ps2:(*" + v3t2 + "){ps3:(*" + v3t3 + "){ps1:(*" + v3t +
+-		")<shown>}}}"
+-	v3s7 := "{ps2:(*" + v3t2 + ")(" + tic2Addr + "){ps3:(*" + v3t3 + ")(" +
+-		tic3Addr + "){ps1:(*" + v3t + ")(" + v3Addr + "){ps2:(*" + v3t2 +
+-		")(" + tic2Addr + ")<shown>}}}}"
+-	v3s8 := "{ps2:(*" + v3t2 + ")(" + tic2Addr + "){ps3:(*" + v3t3 + ")(" +
+-		tic3Addr + "){ps1:(*" + v3t + ")(" + v3Addr + ")<shown>}}}"
+-	addFormatterTest("%v", v3, v3s)
+-	addFormatterTest("%v", pv3, "<*>"+v3s2)
+-	addFormatterTest("%v", &pv3, "<**>"+v3s2)
+-	addFormatterTest("%+v", v3, v3s3)
+-	addFormatterTest("%+v", pv3, "<*>("+v3Addr+")"+v3s4)
+-	addFormatterTest("%+v", &pv3, "<**>("+pv3Addr+"->"+v3Addr+")"+v3s4)
+-	addFormatterTest("%#v", v3, "("+v3t+")"+v3s5)
+-	addFormatterTest("%#v", pv3, "(*"+v3t+")"+v3s6)
+-	addFormatterTest("%#v", &pv3, "(**"+v3t+")"+v3s6)
+-	addFormatterTest("%#+v", v3, "("+v3t+")"+v3s7)
+-	addFormatterTest("%#+v", pv3, "(*"+v3t+")("+v3Addr+")"+v3s8)
+-	addFormatterTest("%#+v", &pv3, "(**"+v3t+")("+pv3Addr+"->"+v3Addr+")"+v3s8)
+-}
+-
+-func addPanicFormatterTests() {
+-	// Type that panics in its Stringer interface.
+-	v := panicer(127)
+-	nv := (*panicer)(nil)
+-	pv := &v
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "spew_test.panicer"
+-	vs := "(PANIC=test panic)127"
+-	addFormatterTest("%v", v, vs)
+-	addFormatterTest("%v", pv, "<*>"+vs)
+-	addFormatterTest("%v", &pv, "<**>"+vs)
+-	addFormatterTest("%v", nv, "<nil>")
+-	addFormatterTest("%+v", v, vs)
+-	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
+-	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%#v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
+-	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
+-	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
+-	addFormatterTest("%#+v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
+-	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-}
+-
+-func addErrorFormatterTests() {
+-	// Type that has a custom Error interface.
+-	v := customError(127)
+-	nv := (*customError)(nil)
+-	pv := &v
+-	vAddr := fmt.Sprintf("%p", pv)
+-	pvAddr := fmt.Sprintf("%p", &pv)
+-	vt := "spew_test.customError"
+-	vs := "error: 127"
+-	addFormatterTest("%v", v, vs)
+-	addFormatterTest("%v", pv, "<*>"+vs)
+-	addFormatterTest("%v", &pv, "<**>"+vs)
+-	addFormatterTest("%v", nv, "<nil>")
+-	addFormatterTest("%+v", v, vs)
+-	addFormatterTest("%+v", pv, "<*>("+vAddr+")"+vs)
+-	addFormatterTest("%+v", &pv, "<**>("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%+v", nv, "<nil>")
+-	addFormatterTest("%#v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#v", pv, "(*"+vt+")"+vs)
+-	addFormatterTest("%#v", &pv, "(**"+vt+")"+vs)
+-	addFormatterTest("%#v", nv, "(*"+vt+")"+"<nil>")
+-	addFormatterTest("%#+v", v, "("+vt+")"+vs)
+-	addFormatterTest("%#+v", pv, "(*"+vt+")("+vAddr+")"+vs)
+-	addFormatterTest("%#+v", &pv, "(**"+vt+")("+pvAddr+"->"+vAddr+")"+vs)
+-	addFormatterTest("%#+v", nv, "(*"+vt+")"+"<nil>")
+-}
+-
+-func addPassthroughFormatterTests() {
+-	// %x passthrough with uint.
+-	v := uint(4294967295)
+-	pv := &v
+-	vAddr := fmt.Sprintf("%x", pv)
+-	pvAddr := fmt.Sprintf("%x", &pv)
+-	vs := "ffffffff"
+-	addFormatterTest("%x", v, vs)
+-	addFormatterTest("%x", pv, vAddr)
+-	addFormatterTest("%x", &pv, pvAddr)
+-
+-	// %#x passthrough with uint.
+-	v2 := int(2147483647)
+-	pv2 := &v2
+-	v2Addr := fmt.Sprintf("%#x", pv2)
+-	pv2Addr := fmt.Sprintf("%#x", &pv2)
+-	v2s := "0x7fffffff"
+-	addFormatterTest("%#x", v2, v2s)
+-	addFormatterTest("%#x", pv2, v2Addr)
+-	addFormatterTest("%#x", &pv2, pv2Addr)
+-
+-	// %f passthrough with precision.
+-	addFormatterTest("%.2f", 3.1415, "3.14")
+-	addFormatterTest("%.3f", 3.1415, "3.142")
+-	addFormatterTest("%.4f", 3.1415, "3.1415")
+-
+-	// %f passthrough with width and precision.
+-	addFormatterTest("%5.2f", 3.1415, " 3.14")
+-	addFormatterTest("%6.3f", 3.1415, " 3.142")
+-	addFormatterTest("%7.4f", 3.1415, " 3.1415")
+-
+-	// %d passthrough with width.
+-	addFormatterTest("%3d", 127, "127")
+-	addFormatterTest("%4d", 127, " 127")
+-	addFormatterTest("%5d", 127, "  127")
+-
+-	// %q passthrough with string.
+-	addFormatterTest("%q", "test", "\"test\"")
+-}
+-
+-// TestFormatter executes all of the tests described by formatterTests.
+-func TestFormatter(t *testing.T) {
+-	// Setup tests.
+-	addIntFormatterTests()
+-	addUintFormatterTests()
+-	addBoolFormatterTests()
+-	addFloatFormatterTests()
+-	addComplexFormatterTests()
+-	addArrayFormatterTests()
+-	addSliceFormatterTests()
+-	addStringFormatterTests()
+-	addInterfaceFormatterTests()
+-	addMapFormatterTests()
+-	addStructFormatterTests()
+-	addUintptrFormatterTests()
+-	addUnsafePointerFormatterTests()
+-	addChanFormatterTests()
+-	addFuncFormatterTests()
+-	addCircularFormatterTests()
+-	addPanicFormatterTests()
+-	addErrorFormatterTests()
+-	addPassthroughFormatterTests()
+-
+-	t.Logf("Running %d tests", len(formatterTests))
+-	for i, test := range formatterTests {
+-		buf := new(bytes.Buffer)
+-		spew.Fprintf(buf, test.format, test.in)
+-		s := buf.String()
+-		if testFailed(s, test.wants) {
+-			t.Errorf("Formatter #%d format: %s got: %s %s", i, test.format, s,
+-				stringizeWants(test.wants))
+-			continue
+-		}
+-	}
+-}
+-
+-func TestPrintSortedKeys(t *testing.T) {
+-	cfg := spew.ConfigState{SortKeys: true}
+-	s := cfg.Sprint(map[int]string{1: "1", 3: "3", 2: "2"})
+-	expected := "map[1:1 2:2 3:3]"
+-	if s != expected {
+-		t.Errorf("Sorted keys mismatch:\n  %v %v", s, expected)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/internal_test.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/internal_test.go
+deleted file mode 100644
+index 10dc0b1..0000000
+--- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/internal_test.go
++++ /dev/null
+@@ -1,156 +0,0 @@
+-/*
+- * Copyright (c) 2013 Dave Collins <dave at davec.name>
+- *
+- * Permission to use, copy, modify, and distribute this software for any
+- * purpose with or without fee is hereby granted, provided that the above
+- * copyright notice and this permission notice appear in all copies.
+- *
+- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+- */
+-
+-/*
+-This test file is part of the spew package rather than than the spew_test
+-package because it needs access to internals to properly test certain cases
+-which are not possible via the public interface since they should never happen.
+-*/
+-
+-package spew
+-
+-import (
+-	"bytes"
+-	"reflect"
+-	"testing"
+-	"unsafe"
+-)
+-
+-// dummyFmtState implements a fake fmt.State to use for testing invalid
+-// reflect.Value handling.  This is necessary because the fmt package catches
+-// invalid values before invoking the formatter on them.
+-type dummyFmtState struct {
+-	bytes.Buffer
+-}
+-
+-func (dfs *dummyFmtState) Flag(f int) bool {
+-	if f == int('+') {
+-		return true
+-	}
+-	return false
+-}
+-
+-func (dfs *dummyFmtState) Precision() (int, bool) {
+-	return 0, false
+-}
+-
+-func (dfs *dummyFmtState) Width() (int, bool) {
+-	return 0, false
+-}
+-
+-// TestInvalidReflectValue ensures the dump and formatter code handles an
+-// invalid reflect value properly.  This needs access to internal state since it
+-// should never happen in real code and therefore can't be tested via the public
+-// API.
+-func TestInvalidReflectValue(t *testing.T) {
+-	i := 1
+-
+-	// Dump invalid reflect value.
+-	v := new(reflect.Value)
+-	buf := new(bytes.Buffer)
+-	d := dumpState{w: buf, cs: &Config}
+-	d.dump(*v)
+-	s := buf.String()
+-	want := "<invalid>"
+-	if s != want {
+-		t.Errorf("InvalidReflectValue #%d\n got: %s want: %s", i, s, want)
+-	}
+-	i++
+-
+-	// Formatter invalid reflect value.
+-	buf2 := new(dummyFmtState)
+-	f := formatState{value: *v, cs: &Config, fs: buf2}
+-	f.format(*v)
+-	s = buf2.String()
+-	want = "<invalid>"
+-	if s != want {
+-		t.Errorf("InvalidReflectValue #%d got: %s want: %s", i, s, want)
+-	}
+-}
+-
+-// changeKind uses unsafe to intentionally change the kind of a reflect.Value to
+-// the maximum kind value which does not exist.  This is needed to test the
+-// fallback code which punts to the standard fmt library for new types that
+-// might get added to the language.
+-func changeKind(v *reflect.Value, readOnly bool) {
+-	rvf := (*uintptr)(unsafe.Pointer(uintptr(unsafe.Pointer(v)) + offsetFlag))
+-	*rvf = *rvf | ((1<<flagKindWidth - 1) << flagKindShift)
+-	if readOnly {
+-		*rvf |= flagRO
+-	} else {
+-		*rvf &= ^uintptr(flagRO)
+-	}
+-}
+-
+-// TestAddedReflectValue tests functionaly of the dump and formatter code which
+-// falls back to the standard fmt library for new types that might get added to
+-// the language.
+-func TestAddedReflectValue(t *testing.T) {
+-	i := 1
+-
+-	// Dump using a reflect.Value that is exported.
+-	v := reflect.ValueOf(int8(5))
+-	changeKind(&v, false)
+-	buf := new(bytes.Buffer)
+-	d := dumpState{w: buf, cs: &Config}
+-	d.dump(v)
+-	s := buf.String()
+-	want := "(int8) 5"
+-	if s != want {
+-		t.Errorf("TestAddedReflectValue #%d\n got: %s want: %s", i, s, want)
+-	}
+-	i++
+-
+-	// Dump using a reflect.Value that is not exported.
+-	changeKind(&v, true)
+-	buf.Reset()
+-	d.dump(v)
+-	s = buf.String()
+-	want = "(int8) <int8 Value>"
+-	if s != want {
+-		t.Errorf("TestAddedReflectValue #%d\n got: %s want: %s", i, s, want)
+-	}
+-	i++
+-
+-	// Formatter using a reflect.Value that is exported.
+-	changeKind(&v, false)
+-	buf2 := new(dummyFmtState)
+-	f := formatState{value: v, cs: &Config, fs: buf2}
+-	f.format(v)
+-	s = buf2.String()
+-	want = "5"
+-	if s != want {
+-		t.Errorf("TestAddedReflectValue #%d got: %s want: %s", i, s, want)
+-	}
+-	i++
+-
+-	// Formatter using a reflect.Value that is not exported.
+-	changeKind(&v, true)
+-	buf2.Reset()
+-	f = formatState{value: v, cs: &Config, fs: buf2}
+-	f.format(v)
+-	s = buf2.String()
+-	want = "<int8 Value>"
+-	if s != want {
+-		t.Errorf("TestAddedReflectValue #%d got: %s want: %s", i, s, want)
+-	}
+-}
+-
+-// SortValues makes the internal sortValues function available to the test
+-// package.
+-func SortValues(values []reflect.Value) {
+-	sortValues(values)
+-}
+diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/spew.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/spew.go
+deleted file mode 100644
+index d8233f5..0000000
+--- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/spew.go
++++ /dev/null
+@@ -1,148 +0,0 @@
+-/*
+- * Copyright (c) 2013 Dave Collins <dave at davec.name>
+- *
+- * Permission to use, copy, modify, and distribute this software for any
+- * purpose with or without fee is hereby granted, provided that the above
+- * copyright notice and this permission notice appear in all copies.
+- *
+- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+- */
+-
+-package spew
+-
+-import (
+-	"fmt"
+-	"io"
+-)
+-
+-// Errorf is a wrapper for fmt.Errorf that treats each argument as if it were
+-// passed with a default Formatter interface returned by NewFormatter.  It
+-// returns the formatted string as a value that satisfies error.  See
+-// NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Errorf(format, spew.NewFormatter(a), spew.NewFormatter(b))
+-func Errorf(format string, a ...interface{}) (err error) {
+-	return fmt.Errorf(format, convertArgs(a)...)
+-}
+-
+-// Fprint is a wrapper for fmt.Fprint that treats each argument as if it were
+-// passed with a default Formatter interface returned by NewFormatter.  It
+-// returns the number of bytes written and any write error encountered.  See
+-// NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Fprint(w, spew.NewFormatter(a), spew.NewFormatter(b))
+-func Fprint(w io.Writer, a ...interface{}) (n int, err error) {
+-	return fmt.Fprint(w, convertArgs(a)...)
+-}
+-
+-// Fprintf is a wrapper for fmt.Fprintf that treats each argument as if it were
+-// passed with a default Formatter interface returned by NewFormatter.  It
+-// returns the number of bytes written and any write error encountered.  See
+-// NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Fprintf(w, format, spew.NewFormatter(a), spew.NewFormatter(b))
+-func Fprintf(w io.Writer, format string, a ...interface{}) (n int, err error) {
+-	return fmt.Fprintf(w, format, convertArgs(a)...)
+-}
+-
+-// Fprintln is a wrapper for fmt.Fprintln that treats each argument as if it
+-// passed with a default Formatter interface returned by NewFormatter.  See
+-// NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Fprintln(w, spew.NewFormatter(a), spew.NewFormatter(b))
+-func Fprintln(w io.Writer, a ...interface{}) (n int, err error) {
+-	return fmt.Fprintln(w, convertArgs(a)...)
+-}
+-
+-// Print is a wrapper for fmt.Print that treats each argument as if it were
+-// passed with a default Formatter interface returned by NewFormatter.  It
+-// returns the number of bytes written and any write error encountered.  See
+-// NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Print(spew.NewFormatter(a), spew.NewFormatter(b))
+-func Print(a ...interface{}) (n int, err error) {
+-	return fmt.Print(convertArgs(a)...)
+-}
+-
+-// Printf is a wrapper for fmt.Printf that treats each argument as if it were
+-// passed with a default Formatter interface returned by NewFormatter.  It
+-// returns the number of bytes written and any write error encountered.  See
+-// NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Printf(format, spew.NewFormatter(a), spew.NewFormatter(b))
+-func Printf(format string, a ...interface{}) (n int, err error) {
+-	return fmt.Printf(format, convertArgs(a)...)
+-}
+-
+-// Println is a wrapper for fmt.Println that treats each argument as if it were
+-// passed with a default Formatter interface returned by NewFormatter.  It
+-// returns the number of bytes written and any write error encountered.  See
+-// NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Println(spew.NewFormatter(a), spew.NewFormatter(b))
+-func Println(a ...interface{}) (n int, err error) {
+-	return fmt.Println(convertArgs(a)...)
+-}
+-
+-// Sprint is a wrapper for fmt.Sprint that treats each argument as if it were
+-// passed with a default Formatter interface returned by NewFormatter.  It
+-// returns the resulting string.  See NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Sprint(spew.NewFormatter(a), spew.NewFormatter(b))
+-func Sprint(a ...interface{}) string {
+-	return fmt.Sprint(convertArgs(a)...)
+-}
+-
+-// Sprintf is a wrapper for fmt.Sprintf that treats each argument as if it were
+-// passed with a default Formatter interface returned by NewFormatter.  It
+-// returns the resulting string.  See NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Sprintf(format, spew.NewFormatter(a), spew.NewFormatter(b))
+-func Sprintf(format string, a ...interface{}) string {
+-	return fmt.Sprintf(format, convertArgs(a)...)
+-}
+-
+-// Sprintln is a wrapper for fmt.Sprintln that treats each argument as if it
+-// were passed with a default Formatter interface returned by NewFormatter.  It
+-// returns the resulting string.  See NewFormatter for formatting details.
+-//
+-// This function is shorthand for the following syntax:
+-//
+-//	fmt.Sprintln(spew.NewFormatter(a), spew.NewFormatter(b))
+-func Sprintln(a ...interface{}) string {
+-	return fmt.Sprintln(convertArgs(a)...)
+-}
+-
+-// convertArgs accepts a slice of arguments and returns a slice of the same
+-// length with each argument converted to a default spew Formatter interface.
+-func convertArgs(args []interface{}) (formatters []interface{}) {
+-	formatters = make([]interface{}, len(args))
+-	for index, arg := range args {
+-		formatters[index] = NewFormatter(arg)
+-	}
+-	return formatters
+-}
+diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/spew_test.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/spew_test.go
+deleted file mode 100644
+index 3831ed2..0000000
+--- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/spew_test.go
++++ /dev/null
+@@ -1,308 +0,0 @@
+-/*
+- * Copyright (c) 2013 Dave Collins <dave at davec.name>
+- *
+- * Permission to use, copy, modify, and distribute this software for any
+- * purpose with or without fee is hereby granted, provided that the above
+- * copyright notice and this permission notice appear in all copies.
+- *
+- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+- */
+-
+-package spew_test
+-
+-import (
+-	"bytes"
+-	"fmt"
+-	"github.com/davecgh/go-spew/spew"
+-	"io/ioutil"
+-	"os"
+-	"testing"
+-)
+-
+-// spewFunc is used to identify which public function of the spew package or
+-// ConfigState a test applies to.
+-type spewFunc int
+-
+-const (
+-	fCSFdump spewFunc = iota
+-	fCSFprint
+-	fCSFprintf
+-	fCSFprintln
+-	fCSPrint
+-	fCSPrintln
+-	fCSSdump
+-	fCSSprint
+-	fCSSprintf
+-	fCSSprintln
+-	fCSErrorf
+-	fCSNewFormatter
+-	fErrorf
+-	fFprint
+-	fFprintln
+-	fPrint
+-	fPrintln
+-	fSdump
+-	fSprint
+-	fSprintf
+-	fSprintln
+-)
+-
+-// Map of spewFunc values to names for pretty printing.
+-var spewFuncStrings = map[spewFunc]string{
+-	fCSFdump:        "ConfigState.Fdump",
+-	fCSFprint:       "ConfigState.Fprint",
+-	fCSFprintf:      "ConfigState.Fprintf",
+-	fCSFprintln:     "ConfigState.Fprintln",
+-	fCSSdump:        "ConfigState.Sdump",
+-	fCSPrint:        "ConfigState.Print",
+-	fCSPrintln:      "ConfigState.Println",
+-	fCSSprint:       "ConfigState.Sprint",
+-	fCSSprintf:      "ConfigState.Sprintf",
+-	fCSSprintln:     "ConfigState.Sprintln",
+-	fCSErrorf:       "ConfigState.Errorf",
+-	fCSNewFormatter: "ConfigState.NewFormatter",
+-	fErrorf:         "spew.Errorf",
+-	fFprint:         "spew.Fprint",
+-	fFprintln:       "spew.Fprintln",
+-	fPrint:          "spew.Print",
+-	fPrintln:        "spew.Println",
+-	fSdump:          "spew.Sdump",
+-	fSprint:         "spew.Sprint",
+-	fSprintf:        "spew.Sprintf",
+-	fSprintln:       "spew.Sprintln",
+-}
+-
+-func (f spewFunc) String() string {
+-	if s, ok := spewFuncStrings[f]; ok {
+-		return s
+-	}
+-	return fmt.Sprintf("Unknown spewFunc (%d)", int(f))
+-}
+-
+-// spewTest is used to describe a test to be performed against the public
+-// functions of the spew package or ConfigState.
+-type spewTest struct {
+-	cs     *spew.ConfigState
+-	f      spewFunc
+-	format string
+-	in     interface{}
+-	want   string
+-}
+-
+-// spewTests houses the tests to be performed against the public functions of
+-// the spew package and ConfigState.
+-//
+-// These tests are only intended to ensure the public functions are exercised
+-// and are intentionally not exhaustive of types.  The exhaustive type
+-// tests are handled in the dump and format tests.
+-var spewTests []spewTest
+-
+-// redirStdout is a helper function to return the standard output from f as a
+-// byte slice.
+-func redirStdout(f func()) ([]byte, error) {
+-	tempFile, err := ioutil.TempFile("", "ss-test")
+-	if err != nil {
+-		return nil, err
+-	}
+-	fileName := tempFile.Name()
+-	defer os.Remove(fileName) // Ignore error
+-
+-	origStdout := os.Stdout
+-	os.Stdout = tempFile
+-	f()
+-	os.Stdout = origStdout
+-	tempFile.Close()
+-
+-	return ioutil.ReadFile(fileName)
+-}
+-
+-func initSpewTests() {
+-	// Config states with various settings.
+-	scsDefault := spew.NewDefaultConfig()
+-	scsNoMethods := &spew.ConfigState{Indent: " ", DisableMethods: true}
+-	scsNoPmethods := &spew.ConfigState{Indent: " ", DisablePointerMethods: true}
+-	scsMaxDepth := &spew.ConfigState{Indent: " ", MaxDepth: 1}
+-	scsContinue := &spew.ConfigState{Indent: " ", ContinueOnMethod: true}
+-
+-	// Variables for tests on types which implement Stringer interface with and
+-	// without a pointer receiver.
+-	ts := stringer("test")
+-	tps := pstringer("test")
+-
+-	// depthTester is used to test max depth handling for structs, array, slices
+-	// and maps.
+-	type depthTester struct {
+-		ic    indirCir1
+-		arr   [1]string
+-		slice []string
+-		m     map[string]int
+-	}
+-	dt := depthTester{indirCir1{nil}, [1]string{"arr"}, []string{"slice"},
+-		map[string]int{"one": 1}}
+-
+-	// Variable for tests on types which implement error interface.
+-	te := customError(10)
+-
+-	spewTests = []spewTest{
+-		{scsDefault, fCSFdump, "", int8(127), "(int8) 127\n"},
+-		{scsDefault, fCSFprint, "", int16(32767), "32767"},
+-		{scsDefault, fCSFprintf, "%v", int32(2147483647), "2147483647"},
+-		{scsDefault, fCSFprintln, "", int(2147483647), "2147483647\n"},
+-		{scsDefault, fCSPrint, "", int64(9223372036854775807), "9223372036854775807"},
+-		{scsDefault, fCSPrintln, "", uint8(255), "255\n"},
+-		{scsDefault, fCSSdump, "", uint8(64), "(uint8) 64\n"},
+-		{scsDefault, fCSSprint, "", complex(1, 2), "(1+2i)"},
+-		{scsDefault, fCSSprintf, "%v", complex(float32(3), 4), "(3+4i)"},
+-		{scsDefault, fCSSprintln, "", complex(float64(5), 6), "(5+6i)\n"},
+-		{scsDefault, fCSErrorf, "%#v", uint16(65535), "(uint16)65535"},
+-		{scsDefault, fCSNewFormatter, "%v", uint32(4294967295), "4294967295"},
+-		{scsDefault, fErrorf, "%v", uint64(18446744073709551615), "18446744073709551615"},
+-		{scsDefault, fFprint, "", float32(3.14), "3.14"},
+-		{scsDefault, fFprintln, "", float64(6.28), "6.28\n"},
+-		{scsDefault, fPrint, "", true, "true"},
+-		{scsDefault, fPrintln, "", false, "false\n"},
+-		{scsDefault, fSdump, "", complex(-10, -20), "(complex128) (-10-20i)\n"},
+-		{scsDefault, fSprint, "", complex(-1, -2), "(-1-2i)"},
+-		{scsDefault, fSprintf, "%v", complex(float32(-3), -4), "(-3-4i)"},
+-		{scsDefault, fSprintln, "", complex(float64(-5), -6), "(-5-6i)\n"},
+-		{scsNoMethods, fCSFprint, "", ts, "test"},
+-		{scsNoMethods, fCSFprint, "", &ts, "<*>test"},
+-		{scsNoMethods, fCSFprint, "", tps, "test"},
+-		{scsNoMethods, fCSFprint, "", &tps, "<*>test"},
+-		{scsNoPmethods, fCSFprint, "", ts, "stringer test"},
+-		{scsNoPmethods, fCSFprint, "", &ts, "<*>stringer test"},
+-		{scsNoPmethods, fCSFprint, "", tps, "test"},
+-		{scsNoPmethods, fCSFprint, "", &tps, "<*>stringer test"},
+-		{scsMaxDepth, fCSFprint, "", dt, "{{<max>} [<max>] [<max>] map[<max>]}"},
+-		{scsMaxDepth, fCSFdump, "", dt, "(spew_test.depthTester) {\n" +
+-			" ic: (spew_test.indirCir1) {\n  <max depth reached>\n },\n" +
+-			" arr: ([1]string) (len=1 cap=1) {\n  <max depth reached>\n },\n" +
+-			" slice: ([]string) (len=1 cap=1) {\n  <max depth reached>\n },\n" +
+-			" m: (map[string]int) (len=1) {\n  <max depth reached>\n }\n}\n"},
+-		{scsContinue, fCSFprint, "", ts, "(stringer test) test"},
+-		{scsContinue, fCSFdump, "", ts, "(spew_test.stringer) " +
+-			"(len=4) (stringer test) \"test\"\n"},
+-		{scsContinue, fCSFprint, "", te, "(error: 10) 10"},
+-		{scsContinue, fCSFdump, "", te, "(spew_test.customError) " +
+-			"(error: 10) 10\n"},
+-	}
+-}
+-
+-// TestSpew executes all of the tests described by spewTests.
+-func TestSpew(t *testing.T) {
+-	initSpewTests()
+-
+-	t.Logf("Running %d tests", len(spewTests))
+-	for i, test := range spewTests {
+-		buf := new(bytes.Buffer)
+-		switch test.f {
+-		case fCSFdump:
+-			test.cs.Fdump(buf, test.in)
+-
+-		case fCSFprint:
+-			test.cs.Fprint(buf, test.in)
+-
+-		case fCSFprintf:
+-			test.cs.Fprintf(buf, test.format, test.in)
+-
+-		case fCSFprintln:
+-			test.cs.Fprintln(buf, test.in)
+-
+-		case fCSPrint:
+-			b, err := redirStdout(func() { test.cs.Print(test.in) })
+-			if err != nil {
+-				t.Errorf("%v #%d %v", test.f, i, err)
+-				continue
+-			}
+-			buf.Write(b)
+-
+-		case fCSPrintln:
+-			b, err := redirStdout(func() { test.cs.Println(test.in) })
+-			if err != nil {
+-				t.Errorf("%v #%d %v", test.f, i, err)
+-				continue
+-			}
+-			buf.Write(b)
+-
+-		case fCSSdump:
+-			str := test.cs.Sdump(test.in)
+-			buf.WriteString(str)
+-
+-		case fCSSprint:
+-			str := test.cs.Sprint(test.in)
+-			buf.WriteString(str)
+-
+-		case fCSSprintf:
+-			str := test.cs.Sprintf(test.format, test.in)
+-			buf.WriteString(str)
+-
+-		case fCSSprintln:
+-			str := test.cs.Sprintln(test.in)
+-			buf.WriteString(str)
+-
+-		case fCSErrorf:
+-			err := test.cs.Errorf(test.format, test.in)
+-			buf.WriteString(err.Error())
+-
+-		case fCSNewFormatter:
+-			fmt.Fprintf(buf, test.format, test.cs.NewFormatter(test.in))
+-
+-		case fErrorf:
+-			err := spew.Errorf(test.format, test.in)
+-			buf.WriteString(err.Error())
+-
+-		case fFprint:
+-			spew.Fprint(buf, test.in)
+-
+-		case fFprintln:
+-			spew.Fprintln(buf, test.in)
+-
+-		case fPrint:
+-			b, err := redirStdout(func() { spew.Print(test.in) })
+-			if err != nil {
+-				t.Errorf("%v #%d %v", test.f, i, err)
+-				continue
+-			}
+-			buf.Write(b)
+-
+-		case fPrintln:
+-			b, err := redirStdout(func() { spew.Println(test.in) })
+-			if err != nil {
+-				t.Errorf("%v #%d %v", test.f, i, err)
+-				continue
+-			}
+-			buf.Write(b)
+-
+-		case fSdump:
+-			str := spew.Sdump(test.in)
+-			buf.WriteString(str)
+-
+-		case fSprint:
+-			str := spew.Sprint(test.in)
+-			buf.WriteString(str)
+-
+-		case fSprintf:
+-			str := spew.Sprintf(test.format, test.in)
+-			buf.WriteString(str)
+-
+-		case fSprintln:
+-			str := spew.Sprintln(test.in)
+-			buf.WriteString(str)
+-
+-		default:
+-			t.Errorf("%v #%d unrecognized function", test.f, i)
+-			continue
+-		}
+-		s := buf.String()
+-		if test.want != s {
+-			t.Errorf("ConfigState #%d\n got: %s want: %s", i, s, test.want)
+-			continue
+-		}
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/testdata/dumpcgo.go b/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/testdata/dumpcgo.go
+deleted file mode 100644
+index 5c87dd4..0000000
+--- a/Godeps/_workspace/src/github.com/davecgh/go-spew/spew/testdata/dumpcgo.go
++++ /dev/null
+@@ -1,82 +0,0 @@
+-// Copyright (c) 2013 Dave Collins <dave at davec.name>
+-//
+-// Permission to use, copy, modify, and distribute this software for any
+-// purpose with or without fee is hereby granted, provided that the above
+-// copyright notice and this permission notice appear in all copies.
+-//
+-// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+-// WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+-// MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+-// ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+-// WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+-// ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+-// OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+-
+-// NOTE: Due to the following build constraints, this file will only be compiled
+-// when both cgo is supported and "-tags testcgo" is added to the go test
+-// command line.  This code should really only be in the dumpcgo_test.go file,
+-// but unfortunately Go will not allow cgo in test files, so this is a
+-// workaround to allow cgo types to be tested.  This configuration is used
+-// because spew itself does not require cgo to run even though it does handle
+-// certain cgo types specially.  Rather than forcing all clients to require cgo
+-// and an external C compiler just to run the tests, this scheme makes them
+-// optional.
+-// +build cgo,testcgo
+-
+-package testdata
+-
+-/*
+-#include <stdint.h>
+-typedef unsigned char custom_uchar_t;
+-
+-char            *ncp = 0;
+-char            *cp = "test";
+-char             ca[6] = {'t', 'e', 's', 't', '2', '\0'};
+-unsigned char    uca[6] = {'t', 'e', 's', 't', '3', '\0'};
+-signed char      sca[6] = {'t', 'e', 's', 't', '4', '\0'};
+-uint8_t          ui8ta[6] = {'t', 'e', 's', 't', '5', '\0'};
+-custom_uchar_t   tuca[6] = {'t', 'e', 's', 't', '6', '\0'};
+-*/
+-import "C"
+-
+-// GetCgoNullCharPointer returns a null char pointer via cgo.  This is only
+-// used for tests.
+-func GetCgoNullCharPointer() interface{} {
+-	return C.ncp
+-}
+-
+-// GetCgoCharPointer returns a char pointer via cgo.  This is only used for
+-// tests.
+-func GetCgoCharPointer() interface{} {
+-	return C.cp
+-}
+-
+-// GetCgoCharArray returns a char array via cgo and the array's len and cap.
+-// This is only used for tests.
+-func GetCgoCharArray() (interface{}, int, int) {
+-	return C.ca, len(C.ca), cap(C.ca)
+-}
+-
+-// GetCgoUnsignedCharArray returns an unsigned char array via cgo and the
+-// array's len and cap.  This is only used for tests.
+-func GetCgoUnsignedCharArray() (interface{}, int, int) {
+-	return C.uca, len(C.uca), cap(C.uca)
+-}
+-
+-// GetCgoSignedCharArray returns a signed char array via cgo and the array's len
+-// and cap.  This is only used for tests.
+-func GetCgoSignedCharArray() (interface{}, int, int) {
+-	return C.sca, len(C.sca), cap(C.sca)
+-}
+-
+-// GetCgoUint8tArray returns a uint8_t array via cgo and the array's len and
+-// cap.  This is only used for tests.
+-func GetCgoUint8tArray() (interface{}, int, int) {
+-	return C.ui8ta, len(C.ui8ta), cap(C.ui8ta)
+-}
+-
+-// GetCgoTypdefedUnsignedCharArray returns a typedefed unsigned char array via
+-// cgo and the array's len and cap.  This is only used for tests.
+-func GetCgoTypdefedUnsignedCharArray() (interface{}, int, int) {
+-	return C.tuca, len(C.tuca), cap(C.tuca)
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/MAINTAINERS b/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/MAINTAINERS
+deleted file mode 100644
+index 2aac726..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/MAINTAINERS
++++ /dev/null
+@@ -1,2 +0,0 @@
+-Cristian Staretu <cristian.staretu at gmail.com> (@unclejack)
+-Tibor Vass <teabee89 at gmail.com> (@tiborvass)
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/README.md b/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/README.md
+deleted file mode 100644
+index 7307d96..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/README.md
++++ /dev/null
+@@ -1 +0,0 @@
+-This code provides helper functions for dealing with archive files.
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/archive.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/archive.go
+deleted file mode 100644
+index ec45d85..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/archive.go
++++ /dev/null
+@@ -1,802 +0,0 @@
+-package archive
+-
+-import (
+-	"bufio"
+-	"bytes"
+-	"compress/bzip2"
+-	"compress/gzip"
+-	"errors"
+-	"fmt"
+-	"io"
+-	"io/ioutil"
+-	"os"
+-	"os/exec"
+-	"path"
+-	"path/filepath"
+-	"strings"
+-	"syscall"
+-
+-	"github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar"
+-
+-	log "github.com/Sirupsen/logrus"
+-	"github.com/docker/docker/pkg/fileutils"
+-	"github.com/docker/docker/pkg/pools"
+-	"github.com/docker/docker/pkg/promise"
+-	"github.com/docker/docker/pkg/system"
+-)
+-
+-type (
+-	Archive       io.ReadCloser
+-	ArchiveReader io.Reader
+-	Compression   int
+-	TarOptions    struct {
+-		Includes    []string
+-		Excludes    []string
+-		Compression Compression
+-		NoLchown    bool
+-		Name        string
+-	}
+-
+-	// Archiver allows the reuse of most utility functions of this package
+-	// with a pluggable Untar function.
+-	Archiver struct {
+-		Untar func(io.Reader, string, *TarOptions) error
+-	}
+-
+-	// breakoutError is used to differentiate errors related to breaking out
+-	// When testing archive breakout in the unit tests, this error is expected
+-	// in order for the test to pass.
+-	breakoutError error
+-)
+-
+-var (
+-	ErrNotImplemented = errors.New("Function not implemented")
+-	defaultArchiver   = &Archiver{Untar}
+-)
+-
+-const (
+-	Uncompressed Compression = iota
+-	Bzip2
+-	Gzip
+-	Xz
+-)
+-
+-func IsArchive(header []byte) bool {
+-	compression := DetectCompression(header)
+-	if compression != Uncompressed {
+-		return true
+-	}
+-	r := tar.NewReader(bytes.NewBuffer(header))
+-	_, err := r.Next()
+-	return err == nil
+-}
+-
+-func DetectCompression(source []byte) Compression {
+-	for compression, m := range map[Compression][]byte{
+-		Bzip2: {0x42, 0x5A, 0x68},
+-		Gzip:  {0x1F, 0x8B, 0x08},
+-		Xz:    {0xFD, 0x37, 0x7A, 0x58, 0x5A, 0x00},
+-	} {
+-		if len(source) < len(m) {
+-			log.Debugf("Len too short")
+-			continue
+-		}
+-		if bytes.Compare(m, source[:len(m)]) == 0 {
+-			return compression
+-		}
+-	}
+-	return Uncompressed
+-}
+-
+-func xzDecompress(archive io.Reader) (io.ReadCloser, error) {
+-	args := []string{"xz", "-d", "-c", "-q"}
+-
+-	return CmdStream(exec.Command(args[0], args[1:]...), archive)
+-}
+-
+-func DecompressStream(archive io.Reader) (io.ReadCloser, error) {
+-	p := pools.BufioReader32KPool
+-	buf := p.Get(archive)
+-	bs, err := buf.Peek(10)
+-	if err != nil {
+-		return nil, err
+-	}
+-	log.Debugf("[tar autodetect] n: %v", bs)
+-
+-	compression := DetectCompression(bs)
+-	switch compression {
+-	case Uncompressed:
+-		readBufWrapper := p.NewReadCloserWrapper(buf, buf)
+-		return readBufWrapper, nil
+-	case Gzip:
+-		gzReader, err := gzip.NewReader(buf)
+-		if err != nil {
+-			return nil, err
+-		}
+-		readBufWrapper := p.NewReadCloserWrapper(buf, gzReader)
+-		return readBufWrapper, nil
+-	case Bzip2:
+-		bz2Reader := bzip2.NewReader(buf)
+-		readBufWrapper := p.NewReadCloserWrapper(buf, bz2Reader)
+-		return readBufWrapper, nil
+-	case Xz:
+-		xzReader, err := xzDecompress(buf)
+-		if err != nil {
+-			return nil, err
+-		}
+-		readBufWrapper := p.NewReadCloserWrapper(buf, xzReader)
+-		return readBufWrapper, nil
+-	default:
+-		return nil, fmt.Errorf("Unsupported compression format %s", (&compression).Extension())
+-	}
+-}
+-
+-func CompressStream(dest io.WriteCloser, compression Compression) (io.WriteCloser, error) {
+-	p := pools.BufioWriter32KPool
+-	buf := p.Get(dest)
+-	switch compression {
+-	case Uncompressed:
+-		writeBufWrapper := p.NewWriteCloserWrapper(buf, buf)
+-		return writeBufWrapper, nil
+-	case Gzip:
+-		gzWriter := gzip.NewWriter(dest)
+-		writeBufWrapper := p.NewWriteCloserWrapper(buf, gzWriter)
+-		return writeBufWrapper, nil
+-	case Bzip2, Xz:
+-		// archive/bzip2 does not support writing, and there is no xz support at all
+-		// However, this is not a problem as docker only currently generates gzipped tars
+-		return nil, fmt.Errorf("Unsupported compression format %s", (&compression).Extension())
+-	default:
+-		return nil, fmt.Errorf("Unsupported compression format %s", (&compression).Extension())
+-	}
+-}
+-
+-func (compression *Compression) Extension() string {
+-	switch *compression {
+-	case Uncompressed:
+-		return "tar"
+-	case Bzip2:
+-		return "tar.bz2"
+-	case Gzip:
+-		return "tar.gz"
+-	case Xz:
+-		return "tar.xz"
+-	}
+-	return ""
+-}
+-
+-type tarAppender struct {
+-	TarWriter *tar.Writer
+-	Buffer    *bufio.Writer
+-
+-	// for hardlink mapping
+-	SeenFiles map[uint64]string
+-}
+-
+-func (ta *tarAppender) addTarFile(path, name string) error {
+-	fi, err := os.Lstat(path)
+-	if err != nil {
+-		return err
+-	}
+-
+-	link := ""
+-	if fi.Mode()&os.ModeSymlink != 0 {
+-		if link, err = os.Readlink(path); err != nil {
+-			return err
+-		}
+-	}
+-
+-	hdr, err := tar.FileInfoHeader(fi, link)
+-	if err != nil {
+-		return err
+-	}
+-
+-	if fi.IsDir() && !strings.HasSuffix(name, "/") {
+-		name = name + "/"
+-	}
+-
+-	hdr.Name = name
+-
+-	nlink, inode, err := setHeaderForSpecialDevice(hdr, ta, name, fi.Sys())
+-	if err != nil {
+-		return err
+-	}
+-
+-	// if it's a regular file and has more than 1 link,
+-	// it's hardlinked, so set the type flag accordingly
+-	if fi.Mode().IsRegular() && nlink > 1 {
+-		// a link should have a name that it links too
+-		// and that linked name should be first in the tar archive
+-		if oldpath, ok := ta.SeenFiles[inode]; ok {
+-			hdr.Typeflag = tar.TypeLink
+-			hdr.Linkname = oldpath
+-			hdr.Size = 0 // This Must be here for the writer math to add up!
+-		} else {
+-			ta.SeenFiles[inode] = name
+-		}
+-	}
+-
+-	capability, _ := system.Lgetxattr(path, "security.capability")
+-	if capability != nil {
+-		hdr.Xattrs = make(map[string]string)
+-		hdr.Xattrs["security.capability"] = string(capability)
+-	}
+-
+-	if err := ta.TarWriter.WriteHeader(hdr); err != nil {
+-		return err
+-	}
+-
+-	if hdr.Typeflag == tar.TypeReg {
+-		file, err := os.Open(path)
+-		if err != nil {
+-			return err
+-		}
+-
+-		ta.Buffer.Reset(ta.TarWriter)
+-		defer ta.Buffer.Reset(nil)
+-		_, err = io.Copy(ta.Buffer, file)
+-		file.Close()
+-		if err != nil {
+-			return err
+-		}
+-		err = ta.Buffer.Flush()
+-		if err != nil {
+-			return err
+-		}
+-	}
+-
+-	return nil
+-}
+-
+-func createTarFile(path, extractDir string, hdr *tar.Header, reader io.Reader, Lchown bool) error {
+-	// hdr.Mode is in linux format, which we can use for sycalls,
+-	// but for os.Foo() calls we need the mode converted to os.FileMode,
+-	// so use hdrInfo.Mode() (they differ for e.g. setuid bits)
+-	hdrInfo := hdr.FileInfo()
+-
+-	switch hdr.Typeflag {
+-	case tar.TypeDir:
+-		// Create directory unless it exists as a directory already.
+-		// In that case we just want to merge the two
+-		if fi, err := os.Lstat(path); !(err == nil && fi.IsDir()) {
+-			if err := os.Mkdir(path, hdrInfo.Mode()); err != nil {
+-				return err
+-			}
+-		}
+-
+-	case tar.TypeReg, tar.TypeRegA:
+-		// Source is regular file
+-		file, err := os.OpenFile(path, os.O_CREATE|os.O_WRONLY, hdrInfo.Mode())
+-		if err != nil {
+-			return err
+-		}
+-		if _, err := io.Copy(file, reader); err != nil {
+-			file.Close()
+-			return err
+-		}
+-		file.Close()
+-
+-	case tar.TypeBlock, tar.TypeChar, tar.TypeFifo:
+-		mode := uint32(hdr.Mode & 07777)
+-		switch hdr.Typeflag {
+-		case tar.TypeBlock:
+-			mode |= syscall.S_IFBLK
+-		case tar.TypeChar:
+-			mode |= syscall.S_IFCHR
+-		case tar.TypeFifo:
+-			mode |= syscall.S_IFIFO
+-		}
+-
+-		if err := system.Mknod(path, mode, int(system.Mkdev(hdr.Devmajor, hdr.Devminor))); err != nil {
+-			return err
+-		}
+-
+-	case tar.TypeLink:
+-		targetPath := filepath.Join(extractDir, hdr.Linkname)
+-		// check for hardlink breakout
+-		if !strings.HasPrefix(targetPath, extractDir) {
+-			return breakoutError(fmt.Errorf("invalid hardlink %q -> %q", targetPath, hdr.Linkname))
+-		}
+-		if err := os.Link(targetPath, path); err != nil {
+-			return err
+-		}
+-
+-	case tar.TypeSymlink:
+-		// 	path 				-> hdr.Linkname = targetPath
+-		// e.g. /extractDir/path/to/symlink 	-> ../2/file	= /extractDir/path/2/file
+-		targetPath := filepath.Join(filepath.Dir(path), hdr.Linkname)
+-
+-		// the reason we don't need to check symlinks in the path (with FollowSymlinkInScope) is because
+-		// that symlink would first have to be created, which would be caught earlier, at this very check:
+-		if !strings.HasPrefix(targetPath, extractDir) {
+-			return breakoutError(fmt.Errorf("invalid symlink %q -> %q", path, hdr.Linkname))
+-		}
+-		if err := os.Symlink(hdr.Linkname, path); err != nil {
+-			return err
+-		}
+-
+-	case tar.TypeXGlobalHeader:
+-		log.Debugf("PAX Global Extended Headers found and ignored")
+-		return nil
+-
+-	default:
+-		return fmt.Errorf("Unhandled tar header type %d\n", hdr.Typeflag)
+-	}
+-
+-	if err := os.Lchown(path, hdr.Uid, hdr.Gid); err != nil && Lchown {
+-		return err
+-	}
+-
+-	for key, value := range hdr.Xattrs {
+-		if err := system.Lsetxattr(path, key, []byte(value), 0); err != nil {
+-			return err
+-		}
+-	}
+-
+-	// There is no LChmod, so ignore mode for symlink. Also, this
+-	// must happen after chown, as that can modify the file mode
+-	if hdr.Typeflag != tar.TypeSymlink {
+-		if err := os.Chmod(path, hdrInfo.Mode()); err != nil {
+-			return err
+-		}
+-	}
+-
+-	ts := []syscall.Timespec{timeToTimespec(hdr.AccessTime), timeToTimespec(hdr.ModTime)}
+-	// syscall.UtimesNano doesn't support a NOFOLLOW flag atm, and
+-	if hdr.Typeflag != tar.TypeSymlink {
+-		if err := system.UtimesNano(path, ts); err != nil && err != system.ErrNotSupportedPlatform {
+-			return err
+-		}
+-	} else {
+-		if err := system.LUtimesNano(path, ts); err != nil && err != system.ErrNotSupportedPlatform {
+-			return err
+-		}
+-	}
+-	return nil
+-}
+-
+-// Tar creates an archive from the directory at `path`, and returns it as a
+-// stream of bytes.
+-func Tar(path string, compression Compression) (io.ReadCloser, error) {
+-	return TarWithOptions(path, &TarOptions{Compression: compression})
+-}
+-
+-func escapeName(name string) string {
+-	escaped := make([]byte, 0)
+-	for i, c := range []byte(name) {
+-		if i == 0 && c == '/' {
+-			continue
+-		}
+-		// all printable chars except "-" which is 0x2d
+-		if (0x20 <= c && c <= 0x7E) && c != 0x2d {
+-			escaped = append(escaped, c)
+-		} else {
+-			escaped = append(escaped, fmt.Sprintf("\\%03o", c)...)
+-		}
+-	}
+-	return string(escaped)
+-}
+-
+-// TarWithOptions creates an archive from the directory at `path`, only including files whose relative
+-// paths are included in `options.Includes` (if non-nil) or not in `options.Excludes`.
+-func TarWithOptions(srcPath string, options *TarOptions) (io.ReadCloser, error) {
+-	pipeReader, pipeWriter := io.Pipe()
+-
+-	compressWriter, err := CompressStream(pipeWriter, options.Compression)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	go func() {
+-		ta := &tarAppender{
+-			TarWriter: tar.NewWriter(compressWriter),
+-			Buffer:    pools.BufioWriter32KPool.Get(nil),
+-			SeenFiles: make(map[uint64]string),
+-		}
+-		// this buffer is needed for the duration of this piped stream
+-		defer pools.BufioWriter32KPool.Put(ta.Buffer)
+-
+-		// In general we log errors here but ignore them because
+-		// during e.g. a diff operation the container can continue
+-		// mutating the filesystem and we can see transient errors
+-		// from this
+-
+-		if options.Includes == nil {
+-			options.Includes = []string{"."}
+-		}
+-
+-		var renamedRelFilePath string // For when tar.Options.Name is set
+-		for _, include := range options.Includes {
+-			filepath.Walk(filepath.Join(srcPath, include), func(filePath string, f os.FileInfo, err error) error {
+-				if err != nil {
+-					log.Debugf("Tar: Can't stat file %s to tar: %s", srcPath, err)
+-					return nil
+-				}
+-
+-				relFilePath, err := filepath.Rel(srcPath, filePath)
+-				if err != nil || (relFilePath == "." && f.IsDir()) {
+-					// Error getting relative path OR we are looking
+-					// at the root path. Skip in both situations.
+-					return nil
+-				}
+-
+-				skip, err := fileutils.Matches(relFilePath, options.Excludes)
+-				if err != nil {
+-					log.Debugf("Error matching %s", relFilePath, err)
+-					return err
+-				}
+-
+-				if skip {
+-					if f.IsDir() {
+-						return filepath.SkipDir
+-					}
+-					return nil
+-				}
+-
+-				// Rename the base resource
+-				if options.Name != "" && filePath == srcPath+"/"+filepath.Base(relFilePath) {
+-					renamedRelFilePath = relFilePath
+-				}
+-				// Set this to make sure the items underneath also get renamed
+-				if options.Name != "" {
+-					relFilePath = strings.Replace(relFilePath, renamedRelFilePath, options.Name, 1)
+-				}
+-
+-				if err := ta.addTarFile(filePath, relFilePath); err != nil {
+-					log.Debugf("Can't add file %s to tar: %s", srcPath, err)
+-				}
+-				return nil
+-			})
+-		}
+-
+-		// Make sure to check the error on Close.
+-		if err := ta.TarWriter.Close(); err != nil {
+-			log.Debugf("Can't close tar writer: %s", err)
+-		}
+-		if err := compressWriter.Close(); err != nil {
+-			log.Debugf("Can't close compress writer: %s", err)
+-		}
+-		if err := pipeWriter.Close(); err != nil {
+-			log.Debugf("Can't close pipe writer: %s", err)
+-		}
+-	}()
+-
+-	return pipeReader, nil
+-}
+-
+-func Unpack(decompressedArchive io.Reader, dest string, options *TarOptions) error {
+-	tr := tar.NewReader(decompressedArchive)
+-	trBuf := pools.BufioReader32KPool.Get(nil)
+-	defer pools.BufioReader32KPool.Put(trBuf)
+-
+-	var dirs []*tar.Header
+-
+-	// Iterate through the files in the archive.
+-loop:
+-	for {
+-		hdr, err := tr.Next()
+-		if err == io.EOF {
+-			// end of tar archive
+-			break
+-		}
+-		if err != nil {
+-			return err
+-		}
+-
+-		// Normalize name, for safety and for a simple is-root check
+-		// This keeps "../" as-is, but normalizes "/../" to "/"
+-		hdr.Name = filepath.Clean(hdr.Name)
+-
+-		for _, exclude := range options.Excludes {
+-			if strings.HasPrefix(hdr.Name, exclude) {
+-				continue loop
+-			}
+-		}
+-
+-		if !strings.HasSuffix(hdr.Name, "/") {
+-			// Not the root directory, ensure that the parent directory exists
+-			parent := filepath.Dir(hdr.Name)
+-			parentPath := filepath.Join(dest, parent)
+-			if _, err := os.Lstat(parentPath); err != nil && os.IsNotExist(err) {
+-				err = os.MkdirAll(parentPath, 0777)
+-				if err != nil {
+-					return err
+-				}
+-			}
+-		}
+-
+-		path := filepath.Join(dest, hdr.Name)
+-		rel, err := filepath.Rel(dest, path)
+-		if err != nil {
+-			return err
+-		}
+-		if strings.HasPrefix(rel, "..") {
+-			return breakoutError(fmt.Errorf("%q is outside of %q", hdr.Name, dest))
+-		}
+-
+-		// If path exits we almost always just want to remove and replace it
+-		// The only exception is when it is a directory *and* the file from
+-		// the layer is also a directory. Then we want to merge them (i.e.
+-		// just apply the metadata from the layer).
+-		if fi, err := os.Lstat(path); err == nil {
+-			if fi.IsDir() && hdr.Name == "." {
+-				continue
+-			}
+-			if !(fi.IsDir() && hdr.Typeflag == tar.TypeDir) {
+-				if err := os.RemoveAll(path); err != nil {
+-					return err
+-				}
+-			}
+-		}
+-		trBuf.Reset(tr)
+-		if err := createTarFile(path, dest, hdr, trBuf, !options.NoLchown); err != nil {
+-			return err
+-		}
+-
+-		// Directory mtimes must be handled at the end to avoid further
+-		// file creation in them to modify the directory mtime
+-		if hdr.Typeflag == tar.TypeDir {
+-			dirs = append(dirs, hdr)
+-		}
+-	}
+-
+-	for _, hdr := range dirs {
+-		path := filepath.Join(dest, hdr.Name)
+-		ts := []syscall.Timespec{timeToTimespec(hdr.AccessTime), timeToTimespec(hdr.ModTime)}
+-		if err := syscall.UtimesNano(path, ts); err != nil {
+-			return err
+-		}
+-	}
+-	return nil
+-}
+-
+-// Untar reads a stream of bytes from `archive`, parses it as a tar archive,
+-// and unpacks it into the directory at `dest`.
+-// The archive may be compressed with one of the following algorithms:
+-//  identity (uncompressed), gzip, bzip2, xz.
+-// FIXME: specify behavior when target path exists vs. doesn't exist.
+-func Untar(archive io.Reader, dest string, options *TarOptions) error {
+-	if archive == nil {
+-		return fmt.Errorf("Empty archive")
+-	}
+-	dest = filepath.Clean(dest)
+-	if options == nil {
+-		options = &TarOptions{}
+-	}
+-	if options.Excludes == nil {
+-		options.Excludes = []string{}
+-	}
+-	decompressedArchive, err := DecompressStream(archive)
+-	if err != nil {
+-		return err
+-	}
+-	defer decompressedArchive.Close()
+-	return Unpack(decompressedArchive, dest, options)
+-}
+-
+-func (archiver *Archiver) TarUntar(src, dst string) error {
+-	log.Debugf("TarUntar(%s %s)", src, dst)
+-	archive, err := TarWithOptions(src, &TarOptions{Compression: Uncompressed})
+-	if err != nil {
+-		return err
+-	}
+-	defer archive.Close()
+-	return archiver.Untar(archive, dst, nil)
+-}
+-
+-// TarUntar is a convenience function which calls Tar and Untar, with the output of one piped into the other.
+-// If either Tar or Untar fails, TarUntar aborts and returns the error.
+-func TarUntar(src, dst string) error {
+-	return defaultArchiver.TarUntar(src, dst)
+-}
+-
+-func (archiver *Archiver) UntarPath(src, dst string) error {
+-	archive, err := os.Open(src)
+-	if err != nil {
+-		return err
+-	}
+-	defer archive.Close()
+-	if err := archiver.Untar(archive, dst, nil); err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-// UntarPath is a convenience function which looks for an archive
+-// at filesystem path `src`, and unpacks it at `dst`.
+-func UntarPath(src, dst string) error {
+-	return defaultArchiver.UntarPath(src, dst)
+-}
+-
+-func (archiver *Archiver) CopyWithTar(src, dst string) error {
+-	srcSt, err := os.Stat(src)
+-	if err != nil {
+-		return err
+-	}
+-	if !srcSt.IsDir() {
+-		return archiver.CopyFileWithTar(src, dst)
+-	}
+-	// Create dst, copy src's content into it
+-	log.Debugf("Creating dest directory: %s", dst)
+-	if err := os.MkdirAll(dst, 0755); err != nil && !os.IsExist(err) {
+-		return err
+-	}
+-	log.Debugf("Calling TarUntar(%s, %s)", src, dst)
+-	return archiver.TarUntar(src, dst)
+-}
+-
+-// CopyWithTar creates a tar archive of filesystem path `src`, and
+-// unpacks it at filesystem path `dst`.
+-// The archive is streamed directly with fixed buffering and no
+-// intermediary disk IO.
+-func CopyWithTar(src, dst string) error {
+-	return defaultArchiver.CopyWithTar(src, dst)
+-}
+-
+-func (archiver *Archiver) CopyFileWithTar(src, dst string) (err error) {
+-	log.Debugf("CopyFileWithTar(%s, %s)", src, dst)
+-	srcSt, err := os.Stat(src)
+-	if err != nil {
+-		return err
+-	}
+-	if srcSt.IsDir() {
+-		return fmt.Errorf("Can't copy a directory")
+-	}
+-	// Clean up the trailing /
+-	if dst[len(dst)-1] == '/' {
+-		dst = path.Join(dst, filepath.Base(src))
+-	}
+-	// Create the holding directory if necessary
+-	if err := os.MkdirAll(filepath.Dir(dst), 0700); err != nil && !os.IsExist(err) {
+-		return err
+-	}
+-
+-	r, w := io.Pipe()
+-	errC := promise.Go(func() error {
+-		defer w.Close()
+-
+-		srcF, err := os.Open(src)
+-		if err != nil {
+-			return err
+-		}
+-		defer srcF.Close()
+-
+-		hdr, err := tar.FileInfoHeader(srcSt, "")
+-		if err != nil {
+-			return err
+-		}
+-		hdr.Name = filepath.Base(dst)
+-		tw := tar.NewWriter(w)
+-		defer tw.Close()
+-		if err := tw.WriteHeader(hdr); err != nil {
+-			return err
+-		}
+-		if _, err := io.Copy(tw, srcF); err != nil {
+-			return err
+-		}
+-		return nil
+-	})
+-	defer func() {
+-		if er := <-errC; err != nil {
+-			err = er
+-		}
+-	}()
+-	return archiver.Untar(r, filepath.Dir(dst), nil)
+-}
+-
+-// CopyFileWithTar emulates the behavior of the 'cp' command-line
+-// for a single file. It copies a regular file from path `src` to
+-// path `dst`, and preserves all its metadata.
+-//
+-// If `dst` ends with a trailing slash '/', the final destination path
+-// will be `dst/base(src)`.
+-func CopyFileWithTar(src, dst string) (err error) {
+-	return defaultArchiver.CopyFileWithTar(src, dst)
+-}
+-
+-// CmdStream executes a command, and returns its stdout as a stream.
+-// If the command fails to run or doesn't complete successfully, an error
+-// will be returned, including anything written on stderr.
+-func CmdStream(cmd *exec.Cmd, input io.Reader) (io.ReadCloser, error) {
+-	if input != nil {
+-		stdin, err := cmd.StdinPipe()
+-		if err != nil {
+-			return nil, err
+-		}
+-		// Write stdin if any
+-		go func() {
+-			io.Copy(stdin, input)
+-			stdin.Close()
+-		}()
+-	}
+-	stdout, err := cmd.StdoutPipe()
+-	if err != nil {
+-		return nil, err
+-	}
+-	stderr, err := cmd.StderrPipe()
+-	if err != nil {
+-		return nil, err
+-	}
+-	pipeR, pipeW := io.Pipe()
+-	errChan := make(chan []byte)
+-	// Collect stderr, we will use it in case of an error
+-	go func() {
+-		errText, e := ioutil.ReadAll(stderr)
+-		if e != nil {
+-			errText = []byte("(...couldn't fetch stderr: " + e.Error() + ")")
+-		}
+-		errChan <- errText
+-	}()
+-	// Copy stdout to the returned pipe
+-	go func() {
+-		_, err := io.Copy(pipeW, stdout)
+-		if err != nil {
+-			pipeW.CloseWithError(err)
+-		}
+-		errText := <-errChan
+-		if err := cmd.Wait(); err != nil {
+-			pipeW.CloseWithError(fmt.Errorf("%s: %s", err, errText))
+-		} else {
+-			pipeW.Close()
+-		}
+-	}()
+-	// Run the command and return the pipe
+-	if err := cmd.Start(); err != nil {
+-		return nil, err
+-	}
+-	return pipeR, nil
+-}
+-
+-// NewTempArchive reads the content of src into a temporary file, and returns the contents
+-// of that file as an archive. The archive can only be read once - as soon as reading completes,
+-// the file will be deleted.
+-func NewTempArchive(src Archive, dir string) (*TempArchive, error) {
+-	f, err := ioutil.TempFile(dir, "")
+-	if err != nil {
+-		return nil, err
+-	}
+-	if _, err := io.Copy(f, src); err != nil {
+-		return nil, err
+-	}
+-	if err = f.Sync(); err != nil {
+-		return nil, err
+-	}
+-	if _, err := f.Seek(0, 0); err != nil {
+-		return nil, err
+-	}
+-	st, err := f.Stat()
+-	if err != nil {
+-		return nil, err
+-	}
+-	size := st.Size()
+-	return &TempArchive{File: f, Size: size}, nil
+-}
+-
+-type TempArchive struct {
+-	*os.File
+-	Size   int64 // Pre-computed from Stat().Size() as a convenience
+-	read   int64
+-	closed bool
+-}
+-
+-// Close closes the underlying file if it's still open, or does a no-op
+-// to allow callers to try to close the TempArchive multiple times safely.
+-func (archive *TempArchive) Close() error {
+-	if archive.closed {
+-		return nil
+-	}
+-
+-	archive.closed = true
+-
+-	return archive.File.Close()
+-}
+-
+-func (archive *TempArchive) Read(data []byte) (int, error) {
+-	n, err := archive.File.Read(data)
+-	archive.read += int64(n)
+-	if err != nil || archive.read == archive.Size {
+-		archive.Close()
+-		os.Remove(archive.File.Name())
+-	}
+-	return n, err
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/archive_test.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/archive_test.go
+deleted file mode 100644
+index fdba6fb..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/archive_test.go
++++ /dev/null
+@@ -1,625 +0,0 @@
+-package archive
+-
+-import (
+-	"bytes"
+-	"fmt"
+-	"io"
+-	"io/ioutil"
+-	"os"
+-	"os/exec"
+-	"path"
+-	"path/filepath"
+-	"strings"
+-	"syscall"
+-	"testing"
+-	"time"
+-
+-	"github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar"
+-)
+-
+-func TestCmdStreamLargeStderr(t *testing.T) {
+-	cmd := exec.Command("/bin/sh", "-c", "dd if=/dev/zero bs=1k count=1000 of=/dev/stderr; echo hello")
+-	out, err := CmdStream(cmd, nil)
+-	if err != nil {
+-		t.Fatalf("Failed to start command: %s", err)
+-	}
+-	errCh := make(chan error)
+-	go func() {
+-		_, err := io.Copy(ioutil.Discard, out)
+-		errCh <- err
+-	}()
+-	select {
+-	case err := <-errCh:
+-		if err != nil {
+-			t.Fatalf("Command should not have failed (err=%.100s...)", err)
+-		}
+-	case <-time.After(5 * time.Second):
+-		t.Fatalf("Command did not complete in 5 seconds; probable deadlock")
+-	}
+-}
+-
+-func TestCmdStreamBad(t *testing.T) {
+-	badCmd := exec.Command("/bin/sh", "-c", "echo hello; echo >&2 error couldn\\'t reverse the phase pulser; exit 1")
+-	out, err := CmdStream(badCmd, nil)
+-	if err != nil {
+-		t.Fatalf("Failed to start command: %s", err)
+-	}
+-	if output, err := ioutil.ReadAll(out); err == nil {
+-		t.Fatalf("Command should have failed")
+-	} else if err.Error() != "exit status 1: error couldn't reverse the phase pulser\n" {
+-		t.Fatalf("Wrong error value (%s)", err)
+-	} else if s := string(output); s != "hello\n" {
+-		t.Fatalf("Command output should be '%s', not '%s'", "hello\\n", output)
+-	}
+-}
+-
+-func TestCmdStreamGood(t *testing.T) {
+-	cmd := exec.Command("/bin/sh", "-c", "echo hello; exit 0")
+-	out, err := CmdStream(cmd, nil)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if output, err := ioutil.ReadAll(out); err != nil {
+-		t.Fatalf("Command should not have failed (err=%s)", err)
+-	} else if s := string(output); s != "hello\n" {
+-		t.Fatalf("Command output should be '%s', not '%s'", "hello\\n", output)
+-	}
+-}
+-
+-func TestTarFiles(t *testing.T) {
+-	// try without hardlinks
+-	if err := checkNoChanges(1000, false); err != nil {
+-		t.Fatal(err)
+-	}
+-	// try with hardlinks
+-	if err := checkNoChanges(1000, true); err != nil {
+-		t.Fatal(err)
+-	}
+-}
+-
+-func checkNoChanges(fileNum int, hardlinks bool) error {
+-	srcDir, err := ioutil.TempDir("", "docker-test-srcDir")
+-	if err != nil {
+-		return err
+-	}
+-	defer os.RemoveAll(srcDir)
+-
+-	destDir, err := ioutil.TempDir("", "docker-test-destDir")
+-	if err != nil {
+-		return err
+-	}
+-	defer os.RemoveAll(destDir)
+-
+-	_, err = prepareUntarSourceDirectory(fileNum, srcDir, hardlinks)
+-	if err != nil {
+-		return err
+-	}
+-
+-	err = TarUntar(srcDir, destDir)
+-	if err != nil {
+-		return err
+-	}
+-
+-	changes, err := ChangesDirs(destDir, srcDir)
+-	if err != nil {
+-		return err
+-	}
+-	if len(changes) > 0 {
+-		return fmt.Errorf("with %d files and %v hardlinks: expected 0 changes, got %d", fileNum, hardlinks, len(changes))
+-	}
+-	return nil
+-}
+-
+-func tarUntar(t *testing.T, origin string, options *TarOptions) ([]Change, error) {
+-	archive, err := TarWithOptions(origin, options)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	defer archive.Close()
+-
+-	buf := make([]byte, 10)
+-	if _, err := archive.Read(buf); err != nil {
+-		return nil, err
+-	}
+-	wrap := io.MultiReader(bytes.NewReader(buf), archive)
+-
+-	detectedCompression := DetectCompression(buf)
+-	compression := options.Compression
+-	if detectedCompression.Extension() != compression.Extension() {
+-		return nil, fmt.Errorf("Wrong compression detected. Actual compression: %s, found %s", compression.Extension(), detectedCompression.Extension())
+-	}
+-
+-	tmp, err := ioutil.TempDir("", "docker-test-untar")
+-	if err != nil {
+-		return nil, err
+-	}
+-	defer os.RemoveAll(tmp)
+-	if err := Untar(wrap, tmp, nil); err != nil {
+-		return nil, err
+-	}
+-	if _, err := os.Stat(tmp); err != nil {
+-		return nil, err
+-	}
+-
+-	return ChangesDirs(origin, tmp)
+-}
+-
+-func TestTarUntar(t *testing.T) {
+-	origin, err := ioutil.TempDir("", "docker-test-untar-origin")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	defer os.RemoveAll(origin)
+-	if err := ioutil.WriteFile(path.Join(origin, "1"), []byte("hello world"), 0700); err != nil {
+-		t.Fatal(err)
+-	}
+-	if err := ioutil.WriteFile(path.Join(origin, "2"), []byte("welcome!"), 0700); err != nil {
+-		t.Fatal(err)
+-	}
+-	if err := ioutil.WriteFile(path.Join(origin, "3"), []byte("will be ignored"), 0700); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	for _, c := range []Compression{
+-		Uncompressed,
+-		Gzip,
+-	} {
+-		changes, err := tarUntar(t, origin, &TarOptions{
+-			Compression: c,
+-			Excludes:    []string{"3"},
+-		})
+-
+-		if err != nil {
+-			t.Fatalf("Error tar/untar for compression %s: %s", c.Extension(), err)
+-		}
+-
+-		if len(changes) != 1 || changes[0].Path != "/3" {
+-			t.Fatalf("Unexpected differences after tarUntar: %v", changes)
+-		}
+-	}
+-}
+-
+-func TestTarWithOptions(t *testing.T) {
+-	origin, err := ioutil.TempDir("", "docker-test-untar-origin")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	defer os.RemoveAll(origin)
+-	if err := ioutil.WriteFile(path.Join(origin, "1"), []byte("hello world"), 0700); err != nil {
+-		t.Fatal(err)
+-	}
+-	if err := ioutil.WriteFile(path.Join(origin, "2"), []byte("welcome!"), 0700); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	cases := []struct {
+-		opts       *TarOptions
+-		numChanges int
+-	}{
+-		{&TarOptions{Includes: []string{"1"}}, 1},
+-		{&TarOptions{Excludes: []string{"2"}}, 1},
+-	}
+-	for _, testCase := range cases {
+-		changes, err := tarUntar(t, origin, testCase.opts)
+-		if err != nil {
+-			t.Fatalf("Error tar/untar when testing inclusion/exclusion: %s", err)
+-		}
+-		if len(changes) != testCase.numChanges {
+-			t.Errorf("Expected %d changes, got %d for %+v:",
+-				testCase.numChanges, len(changes), testCase.opts)
+-		}
+-	}
+-}
+-
+-// Some tar archives such as http://haproxy.1wt.eu/download/1.5/src/devel/haproxy-1.5-dev21.tar.gz
+-// use PAX Global Extended Headers.
+-// Failing prevents the archives from being uncompressed during ADD
+-func TestTypeXGlobalHeaderDoesNotFail(t *testing.T) {
+-	hdr := tar.Header{Typeflag: tar.TypeXGlobalHeader}
+-	tmpDir, err := ioutil.TempDir("", "docker-test-archive-pax-test")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	defer os.RemoveAll(tmpDir)
+-	err = createTarFile(filepath.Join(tmpDir, "pax_global_header"), tmpDir, &hdr, nil, true)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-}
+-
+-// Some tar have both GNU specific (huge uid) and Ustar specific (long name) things.
+-// Not supposed to happen (should use PAX instead of Ustar for long name) but it does and it should still work.
+-func TestUntarUstarGnuConflict(t *testing.T) {
+-	f, err := os.Open("testdata/broken.tar")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	found := false
+-	tr := tar.NewReader(f)
+-	// Iterate through the files in the archive.
+-	for {
+-		hdr, err := tr.Next()
+-		if err == io.EOF {
+-			// end of tar archive
+-			break
+-		}
+-		if err != nil {
+-			t.Fatal(err)
+-		}
+-		if hdr.Name == "root/.cpanm/work/1395823785.24209/Plack-1.0030/blib/man3/Plack::Middleware::LighttpdScriptNameFix.3pm" {
+-			found = true
+-			break
+-		}
+-	}
+-	if !found {
+-		t.Fatalf("%s not found in the archive", "root/.cpanm/work/1395823785.24209/Plack-1.0030/blib/man3/Plack::Middleware::LighttpdScriptNameFix.3pm")
+-	}
+-}
+-
+-func TestTarWithHardLink(t *testing.T) {
+-	origin, err := ioutil.TempDir("", "docker-test-tar-hardlink")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	defer os.RemoveAll(origin)
+-	if err := ioutil.WriteFile(path.Join(origin, "1"), []byte("hello world"), 0700); err != nil {
+-		t.Fatal(err)
+-	}
+-	if err := os.Link(path.Join(origin, "1"), path.Join(origin, "2")); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	var i1, i2 uint64
+-	if i1, err = getNlink(path.Join(origin, "1")); err != nil {
+-		t.Fatal(err)
+-	}
+-	// sanity check that we can hardlink
+-	if i1 != 2 {
+-		t.Skipf("skipping since hardlinks don't work here; expected 2 links, got %d", i1)
+-	}
+-
+-	dest, err := ioutil.TempDir("", "docker-test-tar-hardlink-dest")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	defer os.RemoveAll(dest)
+-
+-	// we'll do this in two steps to separate failure
+-	fh, err := Tar(origin, Uncompressed)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	// ensure we can read the whole thing with no error, before writing back out
+-	buf, err := ioutil.ReadAll(fh)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	bRdr := bytes.NewReader(buf)
+-	err = Untar(bRdr, dest, &TarOptions{Compression: Uncompressed})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	if i1, err = getInode(path.Join(dest, "1")); err != nil {
+-		t.Fatal(err)
+-	}
+-	if i2, err = getInode(path.Join(dest, "2")); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	if i1 != i2 {
+-		t.Errorf("expected matching inodes, but got %d and %d", i1, i2)
+-	}
+-}
+-
+-func getNlink(path string) (uint64, error) {
+-	stat, err := os.Stat(path)
+-	if err != nil {
+-		return 0, err
+-	}
+-	statT, ok := stat.Sys().(*syscall.Stat_t)
+-	if !ok {
+-		return 0, fmt.Errorf("expected type *syscall.Stat_t, got %t", stat.Sys())
+-	}
+-	return statT.Nlink, nil
+-}
+-
+-func getInode(path string) (uint64, error) {
+-	stat, err := os.Stat(path)
+-	if err != nil {
+-		return 0, err
+-	}
+-	statT, ok := stat.Sys().(*syscall.Stat_t)
+-	if !ok {
+-		return 0, fmt.Errorf("expected type *syscall.Stat_t, got %t", stat.Sys())
+-	}
+-	return statT.Ino, nil
+-}
+-
+-func prepareUntarSourceDirectory(numberOfFiles int, targetPath string, makeLinks bool) (int, error) {
+-	fileData := []byte("fooo")
+-	for n := 0; n < numberOfFiles; n++ {
+-		fileName := fmt.Sprintf("file-%d", n)
+-		if err := ioutil.WriteFile(path.Join(targetPath, fileName), fileData, 0700); err != nil {
+-			return 0, err
+-		}
+-		if makeLinks {
+-			if err := os.Link(path.Join(targetPath, fileName), path.Join(targetPath, fileName+"-link")); err != nil {
+-				return 0, err
+-			}
+-		}
+-	}
+-	totalSize := numberOfFiles * len(fileData)
+-	return totalSize, nil
+-}
+-
+-func BenchmarkTarUntar(b *testing.B) {
+-	origin, err := ioutil.TempDir("", "docker-test-untar-origin")
+-	if err != nil {
+-		b.Fatal(err)
+-	}
+-	tempDir, err := ioutil.TempDir("", "docker-test-untar-destination")
+-	if err != nil {
+-		b.Fatal(err)
+-	}
+-	target := path.Join(tempDir, "dest")
+-	n, err := prepareUntarSourceDirectory(100, origin, false)
+-	if err != nil {
+-		b.Fatal(err)
+-	}
+-	defer os.RemoveAll(origin)
+-	defer os.RemoveAll(tempDir)
+-
+-	b.ResetTimer()
+-	b.SetBytes(int64(n))
+-	for n := 0; n < b.N; n++ {
+-		err := TarUntar(origin, target)
+-		if err != nil {
+-			b.Fatal(err)
+-		}
+-		os.RemoveAll(target)
+-	}
+-}
+-
+-func BenchmarkTarUntarWithLinks(b *testing.B) {
+-	origin, err := ioutil.TempDir("", "docker-test-untar-origin")
+-	if err != nil {
+-		b.Fatal(err)
+-	}
+-	tempDir, err := ioutil.TempDir("", "docker-test-untar-destination")
+-	if err != nil {
+-		b.Fatal(err)
+-	}
+-	target := path.Join(tempDir, "dest")
+-	n, err := prepareUntarSourceDirectory(100, origin, true)
+-	if err != nil {
+-		b.Fatal(err)
+-	}
+-	defer os.RemoveAll(origin)
+-	defer os.RemoveAll(tempDir)
+-
+-	b.ResetTimer()
+-	b.SetBytes(int64(n))
+-	for n := 0; n < b.N; n++ {
+-		err := TarUntar(origin, target)
+-		if err != nil {
+-			b.Fatal(err)
+-		}
+-		os.RemoveAll(target)
+-	}
+-}
+-
+-func TestUntarInvalidFilenames(t *testing.T) {
+-	for i, headers := range [][]*tar.Header{
+-		{
+-			{
+-				Name:     "../victim/dotdot",
+-				Typeflag: tar.TypeReg,
+-				Mode:     0644,
+-			},
+-		},
+-		{
+-			{
+-				// Note the leading slash
+-				Name:     "/../victim/slash-dotdot",
+-				Typeflag: tar.TypeReg,
+-				Mode:     0644,
+-			},
+-		},
+-	} {
+-		if err := testBreakout("untar", "docker-TestUntarInvalidFilenames", headers); err != nil {
+-			t.Fatalf("i=%d. %v", i, err)
+-		}
+-	}
+-}
+-
+-func TestUntarInvalidHardlink(t *testing.T) {
+-	for i, headers := range [][]*tar.Header{
+-		{ // try reading victim/hello (../)
+-			{
+-				Name:     "dotdot",
+-				Typeflag: tar.TypeLink,
+-				Linkname: "../victim/hello",
+-				Mode:     0644,
+-			},
+-		},
+-		{ // try reading victim/hello (/../)
+-			{
+-				Name:     "slash-dotdot",
+-				Typeflag: tar.TypeLink,
+-				// Note the leading slash
+-				Linkname: "/../victim/hello",
+-				Mode:     0644,
+-			},
+-		},
+-		{ // try writing victim/file
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeLink,
+-				Linkname: "../victim",
+-				Mode:     0755,
+-			},
+-			{
+-				Name:     "loophole-victim/file",
+-				Typeflag: tar.TypeReg,
+-				Mode:     0644,
+-			},
+-		},
+-		{ // try reading victim/hello (hardlink, symlink)
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeLink,
+-				Linkname: "../victim",
+-				Mode:     0755,
+-			},
+-			{
+-				Name:     "symlink",
+-				Typeflag: tar.TypeSymlink,
+-				Linkname: "loophole-victim/hello",
+-				Mode:     0644,
+-			},
+-		},
+-		{ // Try reading victim/hello (hardlink, hardlink)
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeLink,
+-				Linkname: "../victim",
+-				Mode:     0755,
+-			},
+-			{
+-				Name:     "hardlink",
+-				Typeflag: tar.TypeLink,
+-				Linkname: "loophole-victim/hello",
+-				Mode:     0644,
+-			},
+-		},
+-		{ // Try removing victim directory (hardlink)
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeLink,
+-				Linkname: "../victim",
+-				Mode:     0755,
+-			},
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeReg,
+-				Mode:     0644,
+-			},
+-		},
+-	} {
+-		if err := testBreakout("untar", "docker-TestUntarInvalidHardlink", headers); err != nil {
+-			t.Fatalf("i=%d. %v", i, err)
+-		}
+-	}
+-}
+-
+-func TestUntarInvalidSymlink(t *testing.T) {
+-	for i, headers := range [][]*tar.Header{
+-		{ // try reading victim/hello (../)
+-			{
+-				Name:     "dotdot",
+-				Typeflag: tar.TypeSymlink,
+-				Linkname: "../victim/hello",
+-				Mode:     0644,
+-			},
+-		},
+-		{ // try reading victim/hello (/../)
+-			{
+-				Name:     "slash-dotdot",
+-				Typeflag: tar.TypeSymlink,
+-				// Note the leading slash
+-				Linkname: "/../victim/hello",
+-				Mode:     0644,
+-			},
+-		},
+-		{ // try writing victim/file
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeSymlink,
+-				Linkname: "../victim",
+-				Mode:     0755,
+-			},
+-			{
+-				Name:     "loophole-victim/file",
+-				Typeflag: tar.TypeReg,
+-				Mode:     0644,
+-			},
+-		},
+-		{ // try reading victim/hello (symlink, symlink)
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeSymlink,
+-				Linkname: "../victim",
+-				Mode:     0755,
+-			},
+-			{
+-				Name:     "symlink",
+-				Typeflag: tar.TypeSymlink,
+-				Linkname: "loophole-victim/hello",
+-				Mode:     0644,
+-			},
+-		},
+-		{ // try reading victim/hello (symlink, hardlink)
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeSymlink,
+-				Linkname: "../victim",
+-				Mode:     0755,
+-			},
+-			{
+-				Name:     "hardlink",
+-				Typeflag: tar.TypeLink,
+-				Linkname: "loophole-victim/hello",
+-				Mode:     0644,
+-			},
+-		},
+-		{ // try removing victim directory (symlink)
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeSymlink,
+-				Linkname: "../victim",
+-				Mode:     0755,
+-			},
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeReg,
+-				Mode:     0644,
+-			},
+-		},
+-		{ // try writing to victim/newdir/newfile with a symlink in the path
+-			{
+-				// this header needs to be before the next one, or else there is an error
+-				Name:     "dir/loophole",
+-				Typeflag: tar.TypeSymlink,
+-				Linkname: "../../victim",
+-				Mode:     0755,
+-			},
+-			{
+-				Name:     "dir/loophole/newdir/newfile",
+-				Typeflag: tar.TypeReg,
+-				Mode:     0644,
+-			},
+-		},
+-	} {
+-		if err := testBreakout("untar", "docker-TestUntarInvalidSymlink", headers); err != nil {
+-			t.Fatalf("i=%d. %v", i, err)
+-		}
+-	}
+-}
+-
+-func TestTempArchiveCloseMultipleTimes(t *testing.T) {
+-	reader := ioutil.NopCloser(strings.NewReader("hello"))
+-	tempArchive, err := NewTempArchive(reader, "")
+-	buf := make([]byte, 10)
+-	n, err := tempArchive.Read(buf)
+-	if n != 5 {
+-		t.Fatalf("Expected to read 5 bytes. Read %d instead", n)
+-	}
+-	for i := 0; i < 3; i++ {
+-		if err = tempArchive.Close(); err != nil {
+-			t.Fatalf("i=%d. Unexpected error closing temp archive: %v", i, err)
+-		}
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/archive_unix.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/archive_unix.go
+deleted file mode 100644
+index c0e8aee..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/archive_unix.go
++++ /dev/null
+@@ -1,39 +0,0 @@
+-// +build !windows
+-
+-package archive
+-
+-import (
+-	"errors"
+-	"syscall"
+-
+-	"github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar"
+-)
+-
+-func setHeaderForSpecialDevice(hdr *tar.Header, ta *tarAppender, name string, stat interface{}) (nlink uint32, inode uint64, err error) {
+-	s, ok := stat.(*syscall.Stat_t)
+-
+-	if !ok {
+-		err = errors.New("cannot convert stat value to syscall.Stat_t")
+-		return
+-	}
+-
+-	nlink = uint32(s.Nlink)
+-	inode = uint64(s.Ino)
+-
+-	// Currently go does not fil in the major/minors
+-	if s.Mode&syscall.S_IFBLK == syscall.S_IFBLK ||
+-		s.Mode&syscall.S_IFCHR == syscall.S_IFCHR {
+-		hdr.Devmajor = int64(major(uint64(s.Rdev)))
+-		hdr.Devminor = int64(minor(uint64(s.Rdev)))
+-	}
+-
+-	return
+-}
+-
+-func major(device uint64) uint64 {
+-	return (device >> 8) & 0xfff
+-}
+-
+-func minor(device uint64) uint64 {
+-	return (device & 0xff) | ((device >> 12) & 0xfff00)
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/archive_windows.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/archive_windows.go
+deleted file mode 100644
+index 3cc2493..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/archive_windows.go
++++ /dev/null
+@@ -1,12 +0,0 @@
+-// +build windows
+-
+-package archive
+-
+-import (
+-	"github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar"
+-)
+-
+-func setHeaderForSpecialDevice(hdr *tar.Header, ta *tarAppender, name string, stat interface{}) (nlink uint32, inode uint64, err error) {
+-	// do nothing. no notion of Rdev, Inode, Nlink in stat on Windows
+-	return
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/changes.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/changes.go
+deleted file mode 100644
+index 85217f6..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/changes.go
++++ /dev/null
+@@ -1,413 +0,0 @@
+-package archive
+-
+-import (
+-	"bytes"
+-	"fmt"
+-	"io"
+-	"os"
+-	"path/filepath"
+-	"strings"
+-	"syscall"
+-	"time"
+-
+-	"github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar"
+-
+-	log "github.com/Sirupsen/logrus"
+-	"github.com/docker/docker/pkg/pools"
+-	"github.com/docker/docker/pkg/system"
+-)
+-
+-type ChangeType int
+-
+-const (
+-	ChangeModify = iota
+-	ChangeAdd
+-	ChangeDelete
+-)
+-
+-type Change struct {
+-	Path string
+-	Kind ChangeType
+-}
+-
+-func (change *Change) String() string {
+-	var kind string
+-	switch change.Kind {
+-	case ChangeModify:
+-		kind = "C"
+-	case ChangeAdd:
+-		kind = "A"
+-	case ChangeDelete:
+-		kind = "D"
+-	}
+-	return fmt.Sprintf("%s %s", kind, change.Path)
+-}
+-
+-// Gnu tar and the go tar writer don't have sub-second mtime
+-// precision, which is problematic when we apply changes via tar
+-// files, we handle this by comparing for exact times, *or* same
+-// second count and either a or b having exactly 0 nanoseconds
+-func sameFsTime(a, b time.Time) bool {
+-	return a == b ||
+-		(a.Unix() == b.Unix() &&
+-			(a.Nanosecond() == 0 || b.Nanosecond() == 0))
+-}
+-
+-func sameFsTimeSpec(a, b syscall.Timespec) bool {
+-	return a.Sec == b.Sec &&
+-		(a.Nsec == b.Nsec || a.Nsec == 0 || b.Nsec == 0)
+-}
+-
+-// Changes walks the path rw and determines changes for the files in the path,
+-// with respect to the parent layers
+-func Changes(layers []string, rw string) ([]Change, error) {
+-	var changes []Change
+-	err := filepath.Walk(rw, func(path string, f os.FileInfo, err error) error {
+-		if err != nil {
+-			return err
+-		}
+-
+-		// Rebase path
+-		path, err = filepath.Rel(rw, path)
+-		if err != nil {
+-			return err
+-		}
+-		path = filepath.Join("/", path)
+-
+-		// Skip root
+-		if path == "/" {
+-			return nil
+-		}
+-
+-		// Skip AUFS metadata
+-		if matched, err := filepath.Match("/.wh..wh.*", path); err != nil || matched {
+-			return err
+-		}
+-
+-		change := Change{
+-			Path: path,
+-		}
+-
+-		// Find out what kind of modification happened
+-		file := filepath.Base(path)
+-		// If there is a whiteout, then the file was removed
+-		if strings.HasPrefix(file, ".wh.") {
+-			originalFile := file[len(".wh."):]
+-			change.Path = filepath.Join(filepath.Dir(path), originalFile)
+-			change.Kind = ChangeDelete
+-		} else {
+-			// Otherwise, the file was added
+-			change.Kind = ChangeAdd
+-
+-			// ...Unless it already existed in a top layer, in which case, it's a modification
+-			for _, layer := range layers {
+-				stat, err := os.Stat(filepath.Join(layer, path))
+-				if err != nil && !os.IsNotExist(err) {
+-					return err
+-				}
+-				if err == nil {
+-					// The file existed in the top layer, so that's a modification
+-
+-					// However, if it's a directory, maybe it wasn't actually modified.
+-					// If you modify /foo/bar/baz, then /foo will be part of the changed files only because it's the parent of bar
+-					if stat.IsDir() && f.IsDir() {
+-						if f.Size() == stat.Size() && f.Mode() == stat.Mode() && sameFsTime(f.ModTime(), stat.ModTime()) {
+-							// Both directories are the same, don't record the change
+-							return nil
+-						}
+-					}
+-					change.Kind = ChangeModify
+-					break
+-				}
+-			}
+-		}
+-
+-		// Record change
+-		changes = append(changes, change)
+-		return nil
+-	})
+-	if err != nil && !os.IsNotExist(err) {
+-		return nil, err
+-	}
+-	return changes, nil
+-}
+-
+-type FileInfo struct {
+-	parent     *FileInfo
+-	name       string
+-	stat       *system.Stat
+-	children   map[string]*FileInfo
+-	capability []byte
+-	added      bool
+-}
+-
+-func (root *FileInfo) LookUp(path string) *FileInfo {
+-	parent := root
+-	if path == "/" {
+-		return root
+-	}
+-
+-	pathElements := strings.Split(path, "/")
+-	for _, elem := range pathElements {
+-		if elem != "" {
+-			child := parent.children[elem]
+-			if child == nil {
+-				return nil
+-			}
+-			parent = child
+-		}
+-	}
+-	return parent
+-}
+-
+-func (info *FileInfo) path() string {
+-	if info.parent == nil {
+-		return "/"
+-	}
+-	return filepath.Join(info.parent.path(), info.name)
+-}
+-
+-func (info *FileInfo) isDir() bool {
+-	return info.parent == nil || info.stat.Mode()&syscall.S_IFDIR == syscall.S_IFDIR
+-}
+-
+-func (info *FileInfo) addChanges(oldInfo *FileInfo, changes *[]Change) {
+-
+-	sizeAtEntry := len(*changes)
+-
+-	if oldInfo == nil {
+-		// add
+-		change := Change{
+-			Path: info.path(),
+-			Kind: ChangeAdd,
+-		}
+-		*changes = append(*changes, change)
+-		info.added = true
+-	}
+-
+-	// We make a copy so we can modify it to detect additions
+-	// also, we only recurse on the old dir if the new info is a directory
+-	// otherwise any previous delete/change is considered recursive
+-	oldChildren := make(map[string]*FileInfo)
+-	if oldInfo != nil && info.isDir() {
+-		for k, v := range oldInfo.children {
+-			oldChildren[k] = v
+-		}
+-	}
+-
+-	for name, newChild := range info.children {
+-		oldChild, _ := oldChildren[name]
+-		if oldChild != nil {
+-			// change?
+-			oldStat := oldChild.stat
+-			newStat := newChild.stat
+-			// Note: We can't compare inode or ctime or blocksize here, because these change
+-			// when copying a file into a container. However, that is not generally a problem
+-			// because any content change will change mtime, and any status change should
+-			// be visible when actually comparing the stat fields. The only time this
+-			// breaks down is if some code intentionally hides a change by setting
+-			// back mtime
+-			if oldStat.Mode() != newStat.Mode() ||
+-				oldStat.Uid() != newStat.Uid() ||
+-				oldStat.Gid() != newStat.Gid() ||
+-				oldStat.Rdev() != newStat.Rdev() ||
+-				// Don't look at size for dirs, its not a good measure of change
+-				(oldStat.Size() != newStat.Size() && oldStat.Mode()&syscall.S_IFDIR != syscall.S_IFDIR) ||
+-				!sameFsTimeSpec(oldStat.Mtim(), newStat.Mtim()) ||
+-				bytes.Compare(oldChild.capability, newChild.capability) != 0 {
+-				change := Change{
+-					Path: newChild.path(),
+-					Kind: ChangeModify,
+-				}
+-				*changes = append(*changes, change)
+-				newChild.added = true
+-			}
+-
+-			// Remove from copy so we can detect deletions
+-			delete(oldChildren, name)
+-		}
+-
+-		newChild.addChanges(oldChild, changes)
+-	}
+-	for _, oldChild := range oldChildren {
+-		// delete
+-		change := Change{
+-			Path: oldChild.path(),
+-			Kind: ChangeDelete,
+-		}
+-		*changes = append(*changes, change)
+-	}
+-
+-	// If there were changes inside this directory, we need to add it, even if the directory
+-	// itself wasn't changed. This is needed to properly save and restore filesystem permissions.
+-	if len(*changes) > sizeAtEntry && info.isDir() && !info.added && info.path() != "/" {
+-		change := Change{
+-			Path: info.path(),
+-			Kind: ChangeModify,
+-		}
+-		// Let's insert the directory entry before the recently added entries located inside this dir
+-		*changes = append(*changes, change) // just to resize the slice, will be overwritten
+-		copy((*changes)[sizeAtEntry+1:], (*changes)[sizeAtEntry:])
+-		(*changes)[sizeAtEntry] = change
+-	}
+-
+-}
+-
+-func (info *FileInfo) Changes(oldInfo *FileInfo) []Change {
+-	var changes []Change
+-
+-	info.addChanges(oldInfo, &changes)
+-
+-	return changes
+-}
+-
+-func newRootFileInfo() *FileInfo {
+-	root := &FileInfo{
+-		name:     "/",
+-		children: make(map[string]*FileInfo),
+-	}
+-	return root
+-}
+-
+-func collectFileInfo(sourceDir string) (*FileInfo, error) {
+-	root := newRootFileInfo()
+-
+-	err := filepath.Walk(sourceDir, func(path string, f os.FileInfo, err error) error {
+-		if err != nil {
+-			return err
+-		}
+-
+-		// Rebase path
+-		relPath, err := filepath.Rel(sourceDir, path)
+-		if err != nil {
+-			return err
+-		}
+-		relPath = filepath.Join("/", relPath)
+-
+-		if relPath == "/" {
+-			return nil
+-		}
+-
+-		parent := root.LookUp(filepath.Dir(relPath))
+-		if parent == nil {
+-			return fmt.Errorf("collectFileInfo: Unexpectedly no parent for %s", relPath)
+-		}
+-
+-		info := &FileInfo{
+-			name:     filepath.Base(relPath),
+-			children: make(map[string]*FileInfo),
+-			parent:   parent,
+-		}
+-
+-		s, err := system.Lstat(path)
+-		if err != nil {
+-			return err
+-		}
+-		info.stat = s
+-
+-		info.capability, _ = system.Lgetxattr(path, "security.capability")
+-
+-		parent.children[info.name] = info
+-
+-		return nil
+-	})
+-	if err != nil {
+-		return nil, err
+-	}
+-	return root, nil
+-}
+-
+-// ChangesDirs compares two directories and generates an array of Change objects describing the changes.
+-// If oldDir is "", then all files in newDir will be Add-Changes.
+-func ChangesDirs(newDir, oldDir string) ([]Change, error) {
+-	var (
+-		oldRoot, newRoot *FileInfo
+-		err1, err2       error
+-		errs             = make(chan error, 2)
+-	)
+-	go func() {
+-		if oldDir != "" {
+-			oldRoot, err1 = collectFileInfo(oldDir)
+-		}
+-		errs <- err1
+-	}()
+-	go func() {
+-		newRoot, err2 = collectFileInfo(newDir)
+-		errs <- err2
+-	}()
+-
+-	// block until both routines have returned
+-	for i := 0; i < 2; i++ {
+-		if err := <-errs; err != nil {
+-			return nil, err
+-		}
+-	}
+-
+-	return newRoot.Changes(oldRoot), nil
+-}
+-
+-// ChangesSize calculates the size in bytes of the provided changes, based on newDir.
+-func ChangesSize(newDir string, changes []Change) int64 {
+-	var size int64
+-	for _, change := range changes {
+-		if change.Kind == ChangeModify || change.Kind == ChangeAdd {
+-			file := filepath.Join(newDir, change.Path)
+-			fileInfo, _ := os.Lstat(file)
+-			if fileInfo != nil && !fileInfo.IsDir() {
+-				size += fileInfo.Size()
+-			}
+-		}
+-	}
+-	return size
+-}
+-
+-// ExportChanges produces an Archive from the provided changes, relative to dir.
+-func ExportChanges(dir string, changes []Change) (Archive, error) {
+-	reader, writer := io.Pipe()
+-	go func() {
+-		ta := &tarAppender{
+-			TarWriter: tar.NewWriter(writer),
+-			Buffer:    pools.BufioWriter32KPool.Get(nil),
+-			SeenFiles: make(map[uint64]string),
+-		}
+-		// this buffer is needed for the duration of this piped stream
+-		defer pools.BufioWriter32KPool.Put(ta.Buffer)
+-
+-		// In general we log errors here but ignore them because
+-		// during e.g. a diff operation the container can continue
+-		// mutating the filesystem and we can see transient errors
+-		// from this
+-		for _, change := range changes {
+-			if change.Kind == ChangeDelete {
+-				whiteOutDir := filepath.Dir(change.Path)
+-				whiteOutBase := filepath.Base(change.Path)
+-				whiteOut := filepath.Join(whiteOutDir, ".wh."+whiteOutBase)
+-				timestamp := time.Now()
+-				hdr := &tar.Header{
+-					Name:       whiteOut[1:],
+-					Size:       0,
+-					ModTime:    timestamp,
+-					AccessTime: timestamp,
+-					ChangeTime: timestamp,
+-				}
+-				if err := ta.TarWriter.WriteHeader(hdr); err != nil {
+-					log.Debugf("Can't write whiteout header: %s", err)
+-				}
+-			} else {
+-				path := filepath.Join(dir, change.Path)
+-				if err := ta.addTarFile(path, change.Path[1:]); err != nil {
+-					log.Debugf("Can't add file %s to tar: %s", path, err)
+-				}
+-			}
+-		}
+-
+-		// Make sure to check the error on Close.
+-		if err := ta.TarWriter.Close(); err != nil {
+-			log.Debugf("Can't close layer: %s", err)
+-		}
+-		if err := writer.Close(); err != nil {
+-			log.Debugf("failed close Changes writer: %s", err)
+-		}
+-	}()
+-	return reader, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/changes_test.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/changes_test.go
+deleted file mode 100644
+index 34c0f0d..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/changes_test.go
++++ /dev/null
+@@ -1,301 +0,0 @@
+-package archive
+-
+-import (
+-	"io/ioutil"
+-	"os"
+-	"os/exec"
+-	"path"
+-	"sort"
+-	"testing"
+-	"time"
+-)
+-
+-func max(x, y int) int {
+-	if x >= y {
+-		return x
+-	}
+-	return y
+-}
+-
+-func copyDir(src, dst string) error {
+-	cmd := exec.Command("cp", "-a", src, dst)
+-	if err := cmd.Run(); err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-// Helper to sort []Change by path
+-type byPath struct{ changes []Change }
+-
+-func (b byPath) Less(i, j int) bool { return b.changes[i].Path < b.changes[j].Path }
+-func (b byPath) Len() int           { return len(b.changes) }
+-func (b byPath) Swap(i, j int)      { b.changes[i], b.changes[j] = b.changes[j], b.changes[i] }
+-
+-type FileType uint32
+-
+-const (
+-	Regular FileType = iota
+-	Dir
+-	Symlink
+-)
+-
+-type FileData struct {
+-	filetype    FileType
+-	path        string
+-	contents    string
+-	permissions os.FileMode
+-}
+-
+-func createSampleDir(t *testing.T, root string) {
+-	files := []FileData{
+-		{Regular, "file1", "file1\n", 0600},
+-		{Regular, "file2", "file2\n", 0666},
+-		{Regular, "file3", "file3\n", 0404},
+-		{Regular, "file4", "file4\n", 0600},
+-		{Regular, "file5", "file5\n", 0600},
+-		{Regular, "file6", "file6\n", 0600},
+-		{Regular, "file7", "file7\n", 0600},
+-		{Dir, "dir1", "", 0740},
+-		{Regular, "dir1/file1-1", "file1-1\n", 01444},
+-		{Regular, "dir1/file1-2", "file1-2\n", 0666},
+-		{Dir, "dir2", "", 0700},
+-		{Regular, "dir2/file2-1", "file2-1\n", 0666},
+-		{Regular, "dir2/file2-2", "file2-2\n", 0666},
+-		{Dir, "dir3", "", 0700},
+-		{Regular, "dir3/file3-1", "file3-1\n", 0666},
+-		{Regular, "dir3/file3-2", "file3-2\n", 0666},
+-		{Dir, "dir4", "", 0700},
+-		{Regular, "dir4/file3-1", "file4-1\n", 0666},
+-		{Regular, "dir4/file3-2", "file4-2\n", 0666},
+-		{Symlink, "symlink1", "target1", 0666},
+-		{Symlink, "symlink2", "target2", 0666},
+-	}
+-
+-	now := time.Now()
+-	for _, info := range files {
+-		p := path.Join(root, info.path)
+-		if info.filetype == Dir {
+-			if err := os.MkdirAll(p, info.permissions); err != nil {
+-				t.Fatal(err)
+-			}
+-		} else if info.filetype == Regular {
+-			if err := ioutil.WriteFile(p, []byte(info.contents), info.permissions); err != nil {
+-				t.Fatal(err)
+-			}
+-		} else if info.filetype == Symlink {
+-			if err := os.Symlink(info.contents, p); err != nil {
+-				t.Fatal(err)
+-			}
+-		}
+-
+-		if info.filetype != Symlink {
+-			// Set a consistent ctime, atime for all files and dirs
+-			if err := os.Chtimes(p, now, now); err != nil {
+-				t.Fatal(err)
+-			}
+-		}
+-	}
+-}
+-
+-// Create an directory, copy it, make sure we report no changes between the two
+-func TestChangesDirsEmpty(t *testing.T) {
+-	src, err := ioutil.TempDir("", "docker-changes-test")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	createSampleDir(t, src)
+-	dst := src + "-copy"
+-	if err := copyDir(src, dst); err != nil {
+-		t.Fatal(err)
+-	}
+-	changes, err := ChangesDirs(dst, src)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	if len(changes) != 0 {
+-		t.Fatalf("Reported changes for identical dirs: %v", changes)
+-	}
+-	os.RemoveAll(src)
+-	os.RemoveAll(dst)
+-}
+-
+-func mutateSampleDir(t *testing.T, root string) {
+-	// Remove a regular file
+-	if err := os.RemoveAll(path.Join(root, "file1")); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	// Remove a directory
+-	if err := os.RemoveAll(path.Join(root, "dir1")); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	// Remove a symlink
+-	if err := os.RemoveAll(path.Join(root, "symlink1")); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	// Rewrite a file
+-	if err := ioutil.WriteFile(path.Join(root, "file2"), []byte("fileNN\n"), 0777); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	// Replace a file
+-	if err := os.RemoveAll(path.Join(root, "file3")); err != nil {
+-		t.Fatal(err)
+-	}
+-	if err := ioutil.WriteFile(path.Join(root, "file3"), []byte("fileMM\n"), 0404); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	// Touch file
+-	if err := os.Chtimes(path.Join(root, "file4"), time.Now().Add(time.Second), time.Now().Add(time.Second)); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	// Replace file with dir
+-	if err := os.RemoveAll(path.Join(root, "file5")); err != nil {
+-		t.Fatal(err)
+-	}
+-	if err := os.MkdirAll(path.Join(root, "file5"), 0666); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	// Create new file
+-	if err := ioutil.WriteFile(path.Join(root, "filenew"), []byte("filenew\n"), 0777); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	// Create new dir
+-	if err := os.MkdirAll(path.Join(root, "dirnew"), 0766); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	// Create a new symlink
+-	if err := os.Symlink("targetnew", path.Join(root, "symlinknew")); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	// Change a symlink
+-	if err := os.RemoveAll(path.Join(root, "symlink2")); err != nil {
+-		t.Fatal(err)
+-	}
+-	if err := os.Symlink("target2change", path.Join(root, "symlink2")); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	// Replace dir with file
+-	if err := os.RemoveAll(path.Join(root, "dir2")); err != nil {
+-		t.Fatal(err)
+-	}
+-	if err := ioutil.WriteFile(path.Join(root, "dir2"), []byte("dir2\n"), 0777); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	// Touch dir
+-	if err := os.Chtimes(path.Join(root, "dir3"), time.Now().Add(time.Second), time.Now().Add(time.Second)); err != nil {
+-		t.Fatal(err)
+-	}
+-}
+-
+-func TestChangesDirsMutated(t *testing.T) {
+-	src, err := ioutil.TempDir("", "docker-changes-test")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	createSampleDir(t, src)
+-	dst := src + "-copy"
+-	if err := copyDir(src, dst); err != nil {
+-		t.Fatal(err)
+-	}
+-	defer os.RemoveAll(src)
+-	defer os.RemoveAll(dst)
+-
+-	mutateSampleDir(t, dst)
+-
+-	changes, err := ChangesDirs(dst, src)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	sort.Sort(byPath{changes})
+-
+-	expectedChanges := []Change{
+-		{"/dir1", ChangeDelete},
+-		{"/dir2", ChangeModify},
+-		{"/dir3", ChangeModify},
+-		{"/dirnew", ChangeAdd},
+-		{"/file1", ChangeDelete},
+-		{"/file2", ChangeModify},
+-		{"/file3", ChangeModify},
+-		{"/file4", ChangeModify},
+-		{"/file5", ChangeModify},
+-		{"/filenew", ChangeAdd},
+-		{"/symlink1", ChangeDelete},
+-		{"/symlink2", ChangeModify},
+-		{"/symlinknew", ChangeAdd},
+-	}
+-
+-	for i := 0; i < max(len(changes), len(expectedChanges)); i++ {
+-		if i >= len(expectedChanges) {
+-			t.Fatalf("unexpected change %s\n", changes[i].String())
+-		}
+-		if i >= len(changes) {
+-			t.Fatalf("no change for expected change %s\n", expectedChanges[i].String())
+-		}
+-		if changes[i].Path == expectedChanges[i].Path {
+-			if changes[i] != expectedChanges[i] {
+-				t.Fatalf("Wrong change for %s, expected %s, got %s\n", changes[i].Path, changes[i].String(), expectedChanges[i].String())
+-			}
+-		} else if changes[i].Path < expectedChanges[i].Path {
+-			t.Fatalf("unexpected change %s\n", changes[i].String())
+-		} else {
+-			t.Fatalf("no change for expected change %s != %s\n", expectedChanges[i].String(), changes[i].String())
+-		}
+-	}
+-}
+-
+-func TestApplyLayer(t *testing.T) {
+-	src, err := ioutil.TempDir("", "docker-changes-test")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	createSampleDir(t, src)
+-	defer os.RemoveAll(src)
+-	dst := src + "-copy"
+-	if err := copyDir(src, dst); err != nil {
+-		t.Fatal(err)
+-	}
+-	mutateSampleDir(t, dst)
+-	defer os.RemoveAll(dst)
+-
+-	changes, err := ChangesDirs(dst, src)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	layer, err := ExportChanges(dst, changes)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	layerCopy, err := NewTempArchive(layer, "")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	if err := ApplyLayer(src, layerCopy); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	changes2, err := ChangesDirs(src, dst)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	if len(changes2) != 0 {
+-		t.Fatalf("Unexpected differences after reapplying mutation: %v", changes2)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/diff.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/diff.go
+deleted file mode 100644
+index ba22c41..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/diff.go
++++ /dev/null
+@@ -1,165 +0,0 @@
+-package archive
+-
+-import (
+-	"fmt"
+-	"io"
+-	"io/ioutil"
+-	"os"
+-	"path/filepath"
+-	"strings"
+-	"syscall"
+-
+-	"github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar"
+-
+-	"github.com/docker/docker/pkg/pools"
+-	"github.com/docker/docker/pkg/system"
+-)
+-
+-func UnpackLayer(dest string, layer ArchiveReader) error {
+-	tr := tar.NewReader(layer)
+-	trBuf := pools.BufioReader32KPool.Get(tr)
+-	defer pools.BufioReader32KPool.Put(trBuf)
+-
+-	var dirs []*tar.Header
+-
+-	aufsTempdir := ""
+-	aufsHardlinks := make(map[string]*tar.Header)
+-
+-	// Iterate through the files in the archive.
+-	for {
+-		hdr, err := tr.Next()
+-		if err == io.EOF {
+-			// end of tar archive
+-			break
+-		}
+-		if err != nil {
+-			return err
+-		}
+-
+-		// Normalize name, for safety and for a simple is-root check
+-		hdr.Name = filepath.Clean(hdr.Name)
+-
+-		if !strings.HasSuffix(hdr.Name, "/") {
+-			// Not the root directory, ensure that the parent directory exists.
+-			// This happened in some tests where an image had a tarfile without any
+-			// parent directories.
+-			parent := filepath.Dir(hdr.Name)
+-			parentPath := filepath.Join(dest, parent)
+-			if _, err := os.Lstat(parentPath); err != nil && os.IsNotExist(err) {
+-				err = os.MkdirAll(parentPath, 0600)
+-				if err != nil {
+-					return err
+-				}
+-			}
+-		}
+-
+-		// Skip AUFS metadata dirs
+-		if strings.HasPrefix(hdr.Name, ".wh..wh.") {
+-			// Regular files inside /.wh..wh.plnk can be used as hardlink targets
+-			// We don't want this directory, but we need the files in them so that
+-			// such hardlinks can be resolved.
+-			if strings.HasPrefix(hdr.Name, ".wh..wh.plnk") && hdr.Typeflag == tar.TypeReg {
+-				basename := filepath.Base(hdr.Name)
+-				aufsHardlinks[basename] = hdr
+-				if aufsTempdir == "" {
+-					if aufsTempdir, err = ioutil.TempDir("", "dockerplnk"); err != nil {
+-						return err
+-					}
+-					defer os.RemoveAll(aufsTempdir)
+-				}
+-				if err := createTarFile(filepath.Join(aufsTempdir, basename), dest, hdr, tr, true); err != nil {
+-					return err
+-				}
+-			}
+-			continue
+-		}
+-
+-		path := filepath.Join(dest, hdr.Name)
+-		rel, err := filepath.Rel(dest, path)
+-		if err != nil {
+-			return err
+-		}
+-		if strings.HasPrefix(rel, "..") {
+-			return breakoutError(fmt.Errorf("%q is outside of %q", hdr.Name, dest))
+-		}
+-		base := filepath.Base(path)
+-
+-		if strings.HasPrefix(base, ".wh.") {
+-			originalBase := base[len(".wh."):]
+-			originalPath := filepath.Join(filepath.Dir(path), originalBase)
+-			if err := os.RemoveAll(originalPath); err != nil {
+-				return err
+-			}
+-		} else {
+-			// If path exits we almost always just want to remove and replace it.
+-			// The only exception is when it is a directory *and* the file from
+-			// the layer is also a directory. Then we want to merge them (i.e.
+-			// just apply the metadata from the layer).
+-			if fi, err := os.Lstat(path); err == nil {
+-				if !(fi.IsDir() && hdr.Typeflag == tar.TypeDir) {
+-					if err := os.RemoveAll(path); err != nil {
+-						return err
+-					}
+-				}
+-			}
+-
+-			trBuf.Reset(tr)
+-			srcData := io.Reader(trBuf)
+-			srcHdr := hdr
+-
+-			// Hard links into /.wh..wh.plnk don't work, as we don't extract that directory, so
+-			// we manually retarget these into the temporary files we extracted them into
+-			if hdr.Typeflag == tar.TypeLink && strings.HasPrefix(filepath.Clean(hdr.Linkname), ".wh..wh.plnk") {
+-				linkBasename := filepath.Base(hdr.Linkname)
+-				srcHdr = aufsHardlinks[linkBasename]
+-				if srcHdr == nil {
+-					return fmt.Errorf("Invalid aufs hardlink")
+-				}
+-				tmpFile, err := os.Open(filepath.Join(aufsTempdir, linkBasename))
+-				if err != nil {
+-					return err
+-				}
+-				defer tmpFile.Close()
+-				srcData = tmpFile
+-			}
+-
+-			if err := createTarFile(path, dest, srcHdr, srcData, true); err != nil {
+-				return err
+-			}
+-
+-			// Directory mtimes must be handled at the end to avoid further
+-			// file creation in them to modify the directory mtime
+-			if hdr.Typeflag == tar.TypeDir {
+-				dirs = append(dirs, hdr)
+-			}
+-		}
+-	}
+-
+-	for _, hdr := range dirs {
+-		path := filepath.Join(dest, hdr.Name)
+-		ts := []syscall.Timespec{timeToTimespec(hdr.AccessTime), timeToTimespec(hdr.ModTime)}
+-		if err := syscall.UtimesNano(path, ts); err != nil {
+-			return err
+-		}
+-	}
+-	return nil
+-}
+-
+-// ApplyLayer parses a diff in the standard layer format from `layer`, and
+-// applies it to the directory `dest`.
+-func ApplyLayer(dest string, layer ArchiveReader) error {
+-	dest = filepath.Clean(dest)
+-
+-	// We need to be able to set any perms
+-	oldmask, err := system.Umask(0)
+-	if err != nil {
+-		return err
+-	}
+-	defer system.Umask(oldmask) // ignore err, ErrNotSupportedPlatform
+-
+-	layer, err = DecompressStream(layer)
+-	if err != nil {
+-		return err
+-	}
+-	return UnpackLayer(dest, layer)
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/diff_test.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/diff_test.go
+deleted file mode 100644
+index 758c411..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/diff_test.go
++++ /dev/null
+@@ -1,191 +0,0 @@
+-package archive
+-
+-import (
+-	"testing"
+-
+-	"github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar"
+-)
+-
+-func TestApplyLayerInvalidFilenames(t *testing.T) {
+-	for i, headers := range [][]*tar.Header{
+-		{
+-			{
+-				Name:     "../victim/dotdot",
+-				Typeflag: tar.TypeReg,
+-				Mode:     0644,
+-			},
+-		},
+-		{
+-			{
+-				// Note the leading slash
+-				Name:     "/../victim/slash-dotdot",
+-				Typeflag: tar.TypeReg,
+-				Mode:     0644,
+-			},
+-		},
+-	} {
+-		if err := testBreakout("applylayer", "docker-TestApplyLayerInvalidFilenames", headers); err != nil {
+-			t.Fatalf("i=%d. %v", i, err)
+-		}
+-	}
+-}
+-
+-func TestApplyLayerInvalidHardlink(t *testing.T) {
+-	for i, headers := range [][]*tar.Header{
+-		{ // try reading victim/hello (../)
+-			{
+-				Name:     "dotdot",
+-				Typeflag: tar.TypeLink,
+-				Linkname: "../victim/hello",
+-				Mode:     0644,
+-			},
+-		},
+-		{ // try reading victim/hello (/../)
+-			{
+-				Name:     "slash-dotdot",
+-				Typeflag: tar.TypeLink,
+-				// Note the leading slash
+-				Linkname: "/../victim/hello",
+-				Mode:     0644,
+-			},
+-		},
+-		{ // try writing victim/file
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeLink,
+-				Linkname: "../victim",
+-				Mode:     0755,
+-			},
+-			{
+-				Name:     "loophole-victim/file",
+-				Typeflag: tar.TypeReg,
+-				Mode:     0644,
+-			},
+-		},
+-		{ // try reading victim/hello (hardlink, symlink)
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeLink,
+-				Linkname: "../victim",
+-				Mode:     0755,
+-			},
+-			{
+-				Name:     "symlink",
+-				Typeflag: tar.TypeSymlink,
+-				Linkname: "loophole-victim/hello",
+-				Mode:     0644,
+-			},
+-		},
+-		{ // Try reading victim/hello (hardlink, hardlink)
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeLink,
+-				Linkname: "../victim",
+-				Mode:     0755,
+-			},
+-			{
+-				Name:     "hardlink",
+-				Typeflag: tar.TypeLink,
+-				Linkname: "loophole-victim/hello",
+-				Mode:     0644,
+-			},
+-		},
+-		{ // Try removing victim directory (hardlink)
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeLink,
+-				Linkname: "../victim",
+-				Mode:     0755,
+-			},
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeReg,
+-				Mode:     0644,
+-			},
+-		},
+-	} {
+-		if err := testBreakout("applylayer", "docker-TestApplyLayerInvalidHardlink", headers); err != nil {
+-			t.Fatalf("i=%d. %v", i, err)
+-		}
+-	}
+-}
+-
+-func TestApplyLayerInvalidSymlink(t *testing.T) {
+-	for i, headers := range [][]*tar.Header{
+-		{ // try reading victim/hello (../)
+-			{
+-				Name:     "dotdot",
+-				Typeflag: tar.TypeSymlink,
+-				Linkname: "../victim/hello",
+-				Mode:     0644,
+-			},
+-		},
+-		{ // try reading victim/hello (/../)
+-			{
+-				Name:     "slash-dotdot",
+-				Typeflag: tar.TypeSymlink,
+-				// Note the leading slash
+-				Linkname: "/../victim/hello",
+-				Mode:     0644,
+-			},
+-		},
+-		{ // try writing victim/file
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeSymlink,
+-				Linkname: "../victim",
+-				Mode:     0755,
+-			},
+-			{
+-				Name:     "loophole-victim/file",
+-				Typeflag: tar.TypeReg,
+-				Mode:     0644,
+-			},
+-		},
+-		{ // try reading victim/hello (symlink, symlink)
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeSymlink,
+-				Linkname: "../victim",
+-				Mode:     0755,
+-			},
+-			{
+-				Name:     "symlink",
+-				Typeflag: tar.TypeSymlink,
+-				Linkname: "loophole-victim/hello",
+-				Mode:     0644,
+-			},
+-		},
+-		{ // try reading victim/hello (symlink, hardlink)
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeSymlink,
+-				Linkname: "../victim",
+-				Mode:     0755,
+-			},
+-			{
+-				Name:     "hardlink",
+-				Typeflag: tar.TypeLink,
+-				Linkname: "loophole-victim/hello",
+-				Mode:     0644,
+-			},
+-		},
+-		{ // try removing victim directory (symlink)
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeSymlink,
+-				Linkname: "../victim",
+-				Mode:     0755,
+-			},
+-			{
+-				Name:     "loophole-victim",
+-				Typeflag: tar.TypeReg,
+-				Mode:     0644,
+-			},
+-		},
+-	} {
+-		if err := testBreakout("applylayer", "docker-TestApplyLayerInvalidSymlink", headers); err != nil {
+-			t.Fatalf("i=%d. %v", i, err)
+-		}
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/example_changes.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/example_changes.go
+deleted file mode 100644
+index cedd46a..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/example_changes.go
++++ /dev/null
+@@ -1,97 +0,0 @@
+-// +build ignore
+-
+-// Simple tool to create an archive stream from an old and new directory
+-//
+-// By default it will stream the comparison of two temporary directories with junk files
+-package main
+-
+-import (
+-	"flag"
+-	"fmt"
+-	"io"
+-	"io/ioutil"
+-	"os"
+-	"path"
+-
+-	"github.com/Sirupsen/logrus"
+-	"github.com/docker/docker/pkg/archive"
+-)
+-
+-var (
+-	flDebug  = flag.Bool("D", false, "debugging output")
+-	flNewDir = flag.String("newdir", "", "")
+-	flOldDir = flag.String("olddir", "", "")
+-	log      = logrus.New()
+-)
+-
+-func main() {
+-	flag.Usage = func() {
+-		fmt.Println("Produce a tar from comparing two directory paths. By default a demo tar is created of around 200 files (including hardlinks)")
+-		fmt.Printf("%s [OPTIONS]\n", os.Args[0])
+-		flag.PrintDefaults()
+-	}
+-	flag.Parse()
+-	log.Out = os.Stderr
+-	if (len(os.Getenv("DEBUG")) > 0) || *flDebug {
+-		logrus.SetLevel(logrus.DebugLevel)
+-	}
+-	var newDir, oldDir string
+-
+-	if len(*flNewDir) == 0 {
+-		var err error
+-		newDir, err = ioutil.TempDir("", "docker-test-newDir")
+-		if err != nil {
+-			log.Fatal(err)
+-		}
+-		defer os.RemoveAll(newDir)
+-		if _, err := prepareUntarSourceDirectory(100, newDir, true); err != nil {
+-			log.Fatal(err)
+-		}
+-	} else {
+-		newDir = *flNewDir
+-	}
+-
+-	if len(*flOldDir) == 0 {
+-		oldDir, err := ioutil.TempDir("", "docker-test-oldDir")
+-		if err != nil {
+-			log.Fatal(err)
+-		}
+-		defer os.RemoveAll(oldDir)
+-	} else {
+-		oldDir = *flOldDir
+-	}
+-
+-	changes, err := archive.ChangesDirs(newDir, oldDir)
+-	if err != nil {
+-		log.Fatal(err)
+-	}
+-
+-	a, err := archive.ExportChanges(newDir, changes)
+-	if err != nil {
+-		log.Fatal(err)
+-	}
+-	defer a.Close()
+-
+-	i, err := io.Copy(os.Stdout, a)
+-	if err != nil && err != io.EOF {
+-		log.Fatal(err)
+-	}
+-	fmt.Fprintf(os.Stderr, "wrote archive of %d bytes", i)
+-}
+-
+-func prepareUntarSourceDirectory(numberOfFiles int, targetPath string, makeLinks bool) (int, error) {
+-	fileData := []byte("fooo")
+-	for n := 0; n < numberOfFiles; n++ {
+-		fileName := fmt.Sprintf("file-%d", n)
+-		if err := ioutil.WriteFile(path.Join(targetPath, fileName), fileData, 0700); err != nil {
+-			return 0, err
+-		}
+-		if makeLinks {
+-			if err := os.Link(path.Join(targetPath, fileName), path.Join(targetPath, fileName+"-link")); err != nil {
+-				return 0, err
+-			}
+-		}
+-	}
+-	totalSize := numberOfFiles * len(fileData)
+-	return totalSize, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/testdata/broken.tar b/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/testdata/broken.tar
+deleted file mode 100644
+index 8f10ea6b87d3eb4fed572349dfe87695603b10a5..0000000000000000000000000000000000000000
+GIT binary patch
+literal 0
+HcmV?d00001
+
+literal 13824
+zcmeHN>rxv>7UtLfn5Q@^l8gXrG&7O_li)0oQBai)6v9rjo&-ixOPXbFo(r;aaqT1Q
+zi|o_vJM6y3ey8Um2^?(fm~vH66==Hq^tqqYr_U$~f~3CkaX-4=)VFkfMbAE0zj=1W
+zFdGeXOK)!KtrgwSO|!8=t&huAhCPiFI|54|O6#g{AByje_D5`gZ4lbN_tD%y+P?+6
+zW}mCyJbT6dM$<6v?SB_8uxS5j5M6u>C%C=+&BoS!{NIK7SFYLLXgq9fL;u??&1{<b
+z!#}_wZg2ml(Q4ku|6Mr1+wI?RTv6*d{;+nE;z`#Uja&M}?d`v1Y;E1!|I at Yq)BV#u
+zZRWY}#v$rCeY4qI`6s}QfBo-2{9XIYzyF)p1BPLmD~7SzXl<ICn<)Hr)7Wg8EA+uN
+z8R)$ABkMn+x5B**AQz at AZr%p}iLBRZHCp{)@9C2rL(>)C_QVb?f0pB4xfD_C1pX2f
+z=LE&>$4O)llEszRik&8tAi~^>9~IXb2tQsXkop&XF!hz8gWXO)O at R9>nS~7H1w&*U
+zWf1ryXPidjED|qMClc|F!YuB;N}eT-8}IBqwJ!w!F&$m$r;a;(N7!YIEb7h<=ej}&
+zT~f;Cd!ZOC&mX2<A4GTBffw2lvz)=7iZ}sRft- at sEaqQf{#!Tbmv}UNOYws<kQA>n
+zv4)UvkOa{z8}jxVC6bTq+3^R;Sok8c6EQsN&k9^`&<Ew#qD`%}b*8rzPb79NW<eyv
+zG;;IZlOzdu>h(<JHK{@^4$^2KMnN<dnlF+%N4?x!yEL?>Hc32JVwt-Hrj<{`vG3V<
+zCk?#){6BW>!9 at +(L2u}{Jos}CZh!u_HaA;$dH(--^ZzaF-*=t<t)1ZZ_TOx6-P`}2
+z;`c*=-pBr)?ceGOaC`f2H5+$&|NryGzs&BaRh;3_6;m!^cAhw6t_Fs^LF9zVAxgrI
+z^Ga)k-uwDmQU6~pk+ZSU)Y0=r|JP`?471rlpV-_&ANVfo{}p;)*~)!ag?rz?DiPkz
+zgJxA|FHHi^PMm at 5x-%+EOX|<)I2dwy?USjQTU3?9p5ukCpoV5{uPNBif7DBCe`rTT
+z3L{~Aebmu%diM|dDB4g^FC<WUE+WY)#i2bARGm(QPg6ky+gB4xV?o;SF&J}3l#mvO
+zq_r;P$mfxwX%g4-KI8gEj2)kg<UYjrC=ss`MH?m5{!Y>S5&i^O)@Me!3BwBQ`@=VE
+zIl)Fp0<ty)I0-2ZJn%KK`C23*!u80HT~G at An4m7!)liHaUkr(FKmIt at h^+N0?qpNP
+zb)^Q!&ZPh_rG6ipy|AHL8rt#X0RtX)B_K(l(2;XbDhqQqxncyFz|$~DdGE_KNW=q4
+z9tcjBfg=w6CCH4S_Qq9)$j4<aqV~oHAli25B(_TscWjdrvlWJv1i*BSZy`mO93>MG
+z@%2K`G+^8HA?T&;xGZB%_q<@Vt&(_!w-gfXxk at mb9|fb)1BuBGk_ptuvx%G~pq0Kb
+zb&?6Szj_3#ClOiI_3vu1e+<T{ZC$E0&A3#piCQy4)rxE8M*h5E#X6Q3R^dW|e6oJA
+z6!1m_957RkFrR=qLihlW;C)rguWARo&2;UHs^RULcpxU7Z<CbFRAm&!bB*ofK>mOX
+z9k`Og<ag2OH>2B5RmN7LGZ)c;3%E%Ip__9KKUf&G&zD9jkJNr-{ibNby{ds<t*Y>>
+zUrSU_0z^Wf<)}gE{Jb22kgArW_I#nO79{eFvL6rZP*4oJ7H%7}fn5i&1ZT at 5hDK4~
+z(U`5S#`Fws86Z{2P=gP6usiI=mKaOr at 4W<f_DdFo`NM}zf>|(?6Ye5$Oayf(LUxEb
+zaN*HO8gZBg{sZJ1)pg4>36^kmC*dQ2;oE@^#)cw_*aI^!cM=y1Rqga(?Ey`Mja44@
+zco?Vs7`J_y5ir%m6vXp*y&Gb{4lfBvR0R>wjxNBA^zHAzdc;~eK6(s=AB|{$OM8p}
+zp9LwiIkAyG5Q$+F3`7h$CPJbL(j-h1h61!ZViYo4dBXOg at lop12w4V<L4&zs_AUbl
+zRPBf%7W7VbALtP2MKUWDr*_mV-FCm1snL%p>Yz!&$vL+Po-n0lE6B8Y;6$Ar89(FQ
+zU43m0VVC)g+}A0GY(H3=vGXH;5|6sFnZk+NN-WF&+)64KnDBNmlR?P<{j247c6ZGs
+zY`hF!K4&Hi(0r~#=6sH0f#>;~|6uT_GuPArovwt~PT&t2-pNh;x9aMe7i;!lK!(<$
+z?d`g5*7a at bJ?(y(Y4ln98)|Cinp8V=gdKs-N$TT&k8N344C6y&*H}a~{9Pg&%cB8(
+zs3gwCMEH-=;aI?u+)#>TQj}R!`jyO-QsK*KZS|lK9+9#7oV0B(la+ at sRbyfJf~*mY
+z#+u;OA2B at 66aq^nOW6`=t5qYdRV{oFkE8T+GhJI-*NldT<GMfrdYcObq_-4np!UTa
+z62ven4N*a=kcA193+2D7wCW<x^TokWivt|3bJDNrb;(Bkcf<u=>tcr!I|PQf({z2i
+zZs;`}x~m6ks)bXh at +($$(s>pJ`5X6~16{Ufo<hOp)jft at H;jVNPjA=*VXp3B-qzFy
+zZvcLM4LC!MqtjbcU%z2T{o0OY(SNq8vAei$!G_W)rF&L~wiC~4DDQ;3mL2w#n^vCS
+zJ2z3;0CO9x>JC(mW1b(MtJcpN$ZBT3r1B`&Cx9{-iF=!{A}z(ob033DW~d!*9$cfm
+zVNC%z6l$8Qz0L<amlq9R;(1{~=%L_}f at kJr!Pk!x=@7-loMt$bG^groHAiH&Jk=VR
+zR&_E%j4>iPv&`A!8a*yd3zi-in+*e-!2$MiQNyE>1xX!65{vsnGKkf9!|0+OGBAb=
+z5*&U!Rl91sZq^%6Di#9<<87G)rv;99!{p6oE&}gq)LXeeJT)kYlsjz{ehkbMY(O`q
+zGvc6vviAh-6>EFt+I|*)$Z&%o;(ob2LAmI=<VrwhwM%)lUw7a2hl_E at e5S9hA!K2O
+z%kV<}$`HIQz@&<rp86Auh3`cqoVYj(gD*FjqM(QaSH9xFslX{4=lmc_q`SLelwDdl
+zSsXkv8&n*U&mS2N$x;^Ut{sAM@~pT`aa;}pvdd?9l=LD4t~s7hOCN!<d3rJ{q1gih
+zwI9wi3)?eLpB&F;*iLi8Y#G==o_-#!zTotaB##pVr$ieI75am2f4huK(YoK$DHl^z
+zdDpH5p=*JSrw4SK9aJ%OqftW+H5;glLlL=j+0u+{&BX8-j$3L6T<_s^70R$<UVj`6
+zQV++DyxoB$gzv!W*&Rhzj|9J at f8ceaGr~=q9TpbcbEoz!t1jjGWESE&D_6fnC5Q^*
+zLcqGf1~}Al0cQLed8kWyh0C@?3?`_0Q4tSw9{Bu+`{KT94+*zOAD4*U0aXt7p6*wa
+zch-beqmlCpM5a-Idau_$=^me+F%s#p$9ty-XWhfj5o$_1L0O)4jVKlgIA(gi9}bU>
+zd);1Ux&vAHF3sW+ZYtInM5`<aS2kpap%%ttM^5u)K4<qEeyJy-FEKBd<Qpm&;ukq0
+z)ZeoFsl2gyRpD(ME}sE?_WWCkX_byptn(#;tNuaYLBmiRZsl at Q$ge+em$zy$b=u$J
+za#O>7V!gWe@@A3}gzBN4OzKHcFXhsnBZ62vkM}c;c8?C16|}T)I>F_`E4y<`7O_Uv
+z_IIGuK3}j6k8x0(NE^)|N^6ztuoF5wcqyCPP4-b>1H5)kQM(q_kYzo37tjs2w1@@5
+z)pou5q*BNKlggS#-4TOxF*--bZwQgZIP>8>Wh4R6qJg1trGj7P+M9C-U$bgV0-Bbc
+zM}8SyaI1`5o3Hn=gK~dij~yq2v7>PXETRIqq!En36W>+P9az*N;)5;FK054lzkPPH
+zcY4hR*Orc{l5us$Y*nZ!(@__9wdDn6|B~BL+;v!B^Cr<A%tOZ-b&(!im(9mvgsY|#
+z4dI4!RPSSH<bvyV#mjh^W(ct>(N`)UtH54-56s#rGO&e at Q}~KNY<cNr8n?O<R`Hz0
+z1w9pD6oj1ckgHrbR at j#oTzZ0&5jRwv;^>PdQ94MZxA|gP9PSIqe at Ff$9bNNvws)xH
+zUYfZ#^MIJly?f4ly_CL`QQoB~o&>3jKAlL=*#tHX$;*%#;^sVnJHGU0={L0dh$?du
+z$V*u|2o=sbG6HQV;$?~-5Xh?Gjf~m#{@1wY+1 at T!Us<#xZ;2Rn{Y@!B=|jZ;TY#GL
+zQet9G=4h_z5?#7$NWf6BJyZ3f$1aFp02S_lpyVtB;|niLX54VbZP`xU1YMSiGnf#!
+zBhWBJBLfCg3eCtIG~av^x3Yo4twnBx#0a&E><Z1 at 4Ne^joS+N^P7<8_aH#Xax|s6v
+zl(F~h^x){^%86D^{*Xp9`a61<=;bQtLMx|s5~maABA}<v%pTiQlwtB at +~23YC%vQP
+z#NR7t^F!|d+`Ie(6Fzv9ukzn$jFDW at z6LAQ<>6G9&~+z{;Wn%CtG>DYD1(pjqYiYL
+oJsf9Rk?Q4-IWqA2mih3}{ZBUT=3UD at m3s}`Yv5i3pOOat4?XSI`2YX_
+
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/time_linux.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/time_linux.go
+deleted file mode 100644
+index 3448569..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/time_linux.go
++++ /dev/null
+@@ -1,16 +0,0 @@
+-package archive
+-
+-import (
+-	"syscall"
+-	"time"
+-)
+-
+-func timeToTimespec(time time.Time) (ts syscall.Timespec) {
+-	if time.IsZero() {
+-		// Return UTIME_OMIT special value
+-		ts.Sec = 0
+-		ts.Nsec = ((1 << 30) - 2)
+-		return
+-	}
+-	return syscall.NsecToTimespec(time.UnixNano())
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/time_unsupported.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/time_unsupported.go
+deleted file mode 100644
+index e85aac0..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/time_unsupported.go
++++ /dev/null
+@@ -1,16 +0,0 @@
+-// +build !linux
+-
+-package archive
+-
+-import (
+-	"syscall"
+-	"time"
+-)
+-
+-func timeToTimespec(time time.Time) (ts syscall.Timespec) {
+-	nsec := int64(0)
+-	if !time.IsZero() {
+-		nsec = time.UnixNano()
+-	}
+-	return syscall.NsecToTimespec(nsec)
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/utils_test.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/utils_test.go
+deleted file mode 100644
+index 3624fe5..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/utils_test.go
++++ /dev/null
+@@ -1,166 +0,0 @@
+-package archive
+-
+-import (
+-	"bytes"
+-	"fmt"
+-	"io"
+-	"io/ioutil"
+-	"os"
+-	"path/filepath"
+-	"time"
+-
+-	"github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar"
+-)
+-
+-var testUntarFns = map[string]func(string, io.Reader) error{
+-	"untar": func(dest string, r io.Reader) error {
+-		return Untar(r, dest, nil)
+-	},
+-	"applylayer": func(dest string, r io.Reader) error {
+-		return ApplyLayer(dest, ArchiveReader(r))
+-	},
+-}
+-
+-// testBreakout is a helper function that, within the provided `tmpdir` directory,
+-// creates a `victim` folder with a generated `hello` file in it.
+-// `untar` extracts to a directory named `dest`, the tar file created from `headers`.
+-//
+-// Here are the tested scenarios:
+-// - removed `victim` folder				(write)
+-// - removed files from `victim` folder			(write)
+-// - new files in `victim` folder			(write)
+-// - modified files in `victim` folder			(write)
+-// - file in `dest` with same content as `victim/hello` (read)
+-//
+-// When using testBreakout make sure you cover one of the scenarios listed above.
+-func testBreakout(untarFn string, tmpdir string, headers []*tar.Header) error {
+-	tmpdir, err := ioutil.TempDir("", tmpdir)
+-	if err != nil {
+-		return err
+-	}
+-	defer os.RemoveAll(tmpdir)
+-
+-	dest := filepath.Join(tmpdir, "dest")
+-	if err := os.Mkdir(dest, 0755); err != nil {
+-		return err
+-	}
+-
+-	victim := filepath.Join(tmpdir, "victim")
+-	if err := os.Mkdir(victim, 0755); err != nil {
+-		return err
+-	}
+-	hello := filepath.Join(victim, "hello")
+-	helloData, err := time.Now().MarshalText()
+-	if err != nil {
+-		return err
+-	}
+-	if err := ioutil.WriteFile(hello, helloData, 0644); err != nil {
+-		return err
+-	}
+-	helloStat, err := os.Stat(hello)
+-	if err != nil {
+-		return err
+-	}
+-
+-	reader, writer := io.Pipe()
+-	go func() {
+-		t := tar.NewWriter(writer)
+-		for _, hdr := range headers {
+-			t.WriteHeader(hdr)
+-		}
+-		t.Close()
+-	}()
+-
+-	untar := testUntarFns[untarFn]
+-	if untar == nil {
+-		return fmt.Errorf("could not find untar function %q in testUntarFns", untarFn)
+-	}
+-	if err := untar(dest, reader); err != nil {
+-		if _, ok := err.(breakoutError); !ok {
+-			// If untar returns an error unrelated to an archive breakout,
+-			// then consider this an unexpected error and abort.
+-			return err
+-		}
+-		// Here, untar detected the breakout.
+-		// Let's move on verifying that indeed there was no breakout.
+-		fmt.Printf("breakoutError: %v\n", err)
+-	}
+-
+-	// Check victim folder
+-	f, err := os.Open(victim)
+-	if err != nil {
+-		// codepath taken if victim folder was removed
+-		return fmt.Errorf("archive breakout: error reading %q: %v", victim, err)
+-	}
+-	defer f.Close()
+-
+-	// Check contents of victim folder
+-	//
+-	// We are only interested in getting 2 files from the victim folder, because if all is well
+-	// we expect only one result, the `hello` file. If there is a second result, it cannot
+-	// hold the same name `hello` and we assume that a new file got created in the victim folder.
+-	// That is enough to detect an archive breakout.
+-	names, err := f.Readdirnames(2)
+-	if err != nil {
+-		// codepath taken if victim is not a folder
+-		return fmt.Errorf("archive breakout: error reading directory content of %q: %v", victim, err)
+-	}
+-	for _, name := range names {
+-		if name != "hello" {
+-			// codepath taken if new file was created in victim folder
+-			return fmt.Errorf("archive breakout: new file %q", name)
+-		}
+-	}
+-
+-	// Check victim/hello
+-	f, err = os.Open(hello)
+-	if err != nil {
+-		// codepath taken if read permissions were removed
+-		return fmt.Errorf("archive breakout: could not lstat %q: %v", hello, err)
+-	}
+-	defer f.Close()
+-	b, err := ioutil.ReadAll(f)
+-	if err != nil {
+-		return err
+-	}
+-	fi, err := f.Stat()
+-	if err != nil {
+-		return err
+-	}
+-	if helloStat.IsDir() != fi.IsDir() ||
+-		// TODO: cannot check for fi.ModTime() change
+-		helloStat.Mode() != fi.Mode() ||
+-		helloStat.Size() != fi.Size() ||
+-		!bytes.Equal(helloData, b) {
+-		// codepath taken if hello has been modified
+-		return fmt.Errorf("archive breakout: file %q has been modified. Contents: expected=%q, got=%q. FileInfo: expected=%#v, got=%#v.", hello, helloData, b, helloStat, fi)
+-	}
+-
+-	// Check that nothing in dest/ has the same content as victim/hello.
+-	// Since victim/hello was generated with time.Now(), it is safe to assume
+-	// that any file whose content matches exactly victim/hello, managed somehow
+-	// to access victim/hello.
+-	return filepath.Walk(dest, func(path string, info os.FileInfo, err error) error {
+-		if info.IsDir() {
+-			if err != nil {
+-				// skip directory if error
+-				return filepath.SkipDir
+-			}
+-			// enter directory
+-			return nil
+-		}
+-		if err != nil {
+-			// skip file if error
+-			return nil
+-		}
+-		b, err := ioutil.ReadFile(path)
+-		if err != nil {
+-			// Houston, we have a problem. Aborting (space)walk.
+-			return err
+-		}
+-		if bytes.Equal(helloData, b) {
+-			return fmt.Errorf("archive breakout: file %q has been accessed via %q", hello, path)
+-		}
+-		return nil
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/wrap.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/wrap.go
+deleted file mode 100644
+index b8b6019..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/archive/wrap.go
++++ /dev/null
+@@ -1,59 +0,0 @@
+-package archive
+-
+-import (
+-	"bytes"
+-	"github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar"
+-	"io/ioutil"
+-)
+-
+-// Generate generates a new archive from the content provided
+-// as input.
+-//
+-// `files` is a sequence of path/content pairs. A new file is
+-// added to the archive for each pair.
+-// If the last pair is incomplete, the file is created with an
+-// empty content. For example:
+-//
+-// Generate("foo.txt", "hello world", "emptyfile")
+-//
+-// The above call will return an archive with 2 files:
+-//  * ./foo.txt with content "hello world"
+-//  * ./empty with empty content
+-//
+-// FIXME: stream content instead of buffering
+-// FIXME: specify permissions and other archive metadata
+-func Generate(input ...string) (Archive, error) {
+-	files := parseStringPairs(input...)
+-	buf := new(bytes.Buffer)
+-	tw := tar.NewWriter(buf)
+-	for _, file := range files {
+-		name, content := file[0], file[1]
+-		hdr := &tar.Header{
+-			Name: name,
+-			Size: int64(len(content)),
+-		}
+-		if err := tw.WriteHeader(hdr); err != nil {
+-			return nil, err
+-		}
+-		if _, err := tw.Write([]byte(content)); err != nil {
+-			return nil, err
+-		}
+-	}
+-	if err := tw.Close(); err != nil {
+-		return nil, err
+-	}
+-	return ioutil.NopCloser(buf), nil
+-}
+-
+-func parseStringPairs(input ...string) (output [][2]string) {
+-	output = make([][2]string, 0, len(input)/2+1)
+-	for i := 0; i < len(input); i += 2 {
+-		var pair [2]string
+-		pair[0] = input[i]
+-		if i+1 < len(input) {
+-			pair[1] = input[i+1]
+-		}
+-		output = append(output, pair)
+-	}
+-	return
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/fileutils/fileutils.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/fileutils/fileutils.go
+deleted file mode 100644
+index 4e4a91b..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/fileutils/fileutils.go
++++ /dev/null
+@@ -1,26 +0,0 @@
+-package fileutils
+-
+-import (
+-	log "github.com/Sirupsen/logrus"
+-	"path/filepath"
+-)
+-
+-// Matches returns true if relFilePath matches any of the patterns
+-func Matches(relFilePath string, patterns []string) (bool, error) {
+-	for _, exclude := range patterns {
+-		matched, err := filepath.Match(exclude, relFilePath)
+-		if err != nil {
+-			log.Errorf("Error matching: %s (pattern: %s)", relFilePath, exclude)
+-			return false, err
+-		}
+-		if matched {
+-			if filepath.Clean(relFilePath) == "." {
+-				log.Errorf("Can't exclude whole path, excluding pattern: %s", exclude)
+-				continue
+-			}
+-			log.Debugf("Skipping excluded path: %s", relFilePath)
+-			return true, nil
+-		}
+-	}
+-	return false, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/ioutils/readers.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/ioutils/readers.go
+deleted file mode 100644
+index 22f46fb..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/ioutils/readers.go
++++ /dev/null
+@@ -1,114 +0,0 @@
+-package ioutils
+-
+-import (
+-	"bytes"
+-	"io"
+-	"sync"
+-)
+-
+-type readCloserWrapper struct {
+-	io.Reader
+-	closer func() error
+-}
+-
+-func (r *readCloserWrapper) Close() error {
+-	return r.closer()
+-}
+-
+-func NewReadCloserWrapper(r io.Reader, closer func() error) io.ReadCloser {
+-	return &readCloserWrapper{
+-		Reader: r,
+-		closer: closer,
+-	}
+-}
+-
+-type readerErrWrapper struct {
+-	reader io.Reader
+-	closer func()
+-}
+-
+-func (r *readerErrWrapper) Read(p []byte) (int, error) {
+-	n, err := r.reader.Read(p)
+-	if err != nil {
+-		r.closer()
+-	}
+-	return n, err
+-}
+-
+-func NewReaderErrWrapper(r io.Reader, closer func()) io.Reader {
+-	return &readerErrWrapper{
+-		reader: r,
+-		closer: closer,
+-	}
+-}
+-
+-type bufReader struct {
+-	sync.Mutex
+-	buf      *bytes.Buffer
+-	reader   io.Reader
+-	err      error
+-	wait     sync.Cond
+-	drainBuf []byte
+-}
+-
+-func NewBufReader(r io.Reader) *bufReader {
+-	reader := &bufReader{
+-		buf:      &bytes.Buffer{},
+-		drainBuf: make([]byte, 1024),
+-		reader:   r,
+-	}
+-	reader.wait.L = &reader.Mutex
+-	go reader.drain()
+-	return reader
+-}
+-
+-func NewBufReaderWithDrainbufAndBuffer(r io.Reader, drainBuffer []byte, buffer *bytes.Buffer) *bufReader {
+-	reader := &bufReader{
+-		buf:      buffer,
+-		drainBuf: drainBuffer,
+-		reader:   r,
+-	}
+-	reader.wait.L = &reader.Mutex
+-	go reader.drain()
+-	return reader
+-}
+-
+-func (r *bufReader) drain() {
+-	for {
+-		n, err := r.reader.Read(r.drainBuf)
+-		r.Lock()
+-		if err != nil {
+-			r.err = err
+-		} else {
+-			r.buf.Write(r.drainBuf[0:n])
+-		}
+-		r.wait.Signal()
+-		r.Unlock()
+-		if err != nil {
+-			break
+-		}
+-	}
+-}
+-
+-func (r *bufReader) Read(p []byte) (n int, err error) {
+-	r.Lock()
+-	defer r.Unlock()
+-	for {
+-		n, err = r.buf.Read(p)
+-		if n > 0 {
+-			return n, err
+-		}
+-		if r.err != nil {
+-			return 0, r.err
+-		}
+-		r.wait.Wait()
+-	}
+-}
+-
+-func (r *bufReader) Close() error {
+-	closer, ok := r.reader.(io.ReadCloser)
+-	if !ok {
+-		return nil
+-	}
+-	return closer.Close()
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/ioutils/readers_test.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/ioutils/readers_test.go
+deleted file mode 100644
+index a7a2dad..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/ioutils/readers_test.go
++++ /dev/null
+@@ -1,34 +0,0 @@
+-package ioutils
+-
+-import (
+-	"bytes"
+-	"io"
+-	"io/ioutil"
+-	"testing"
+-)
+-
+-func TestBufReader(t *testing.T) {
+-	reader, writer := io.Pipe()
+-	bufreader := NewBufReader(reader)
+-
+-	// Write everything down to a Pipe
+-	// Usually, a pipe should block but because of the buffered reader,
+-	// the writes will go through
+-	done := make(chan bool)
+-	go func() {
+-		writer.Write([]byte("hello world"))
+-		writer.Close()
+-		done <- true
+-	}()
+-
+-	// Drain the reader *after* everything has been written, just to verify
+-	// it is indeed buffering
+-	<-done
+-	output, err := ioutil.ReadAll(bufreader)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !bytes.Equal(output, []byte("hello world")) {
+-		t.Error(string(output))
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/ioutils/writers.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/ioutils/writers.go
+deleted file mode 100644
+index c0b3608..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/ioutils/writers.go
++++ /dev/null
+@@ -1,39 +0,0 @@
+-package ioutils
+-
+-import "io"
+-
+-type NopWriter struct{}
+-
+-func (*NopWriter) Write(buf []byte) (int, error) {
+-	return len(buf), nil
+-}
+-
+-type nopWriteCloser struct {
+-	io.Writer
+-}
+-
+-func (w *nopWriteCloser) Close() error { return nil }
+-
+-func NopWriteCloser(w io.Writer) io.WriteCloser {
+-	return &nopWriteCloser{w}
+-}
+-
+-type NopFlusher struct{}
+-
+-func (f *NopFlusher) Flush() {}
+-
+-type writeCloserWrapper struct {
+-	io.Writer
+-	closer func() error
+-}
+-
+-func (r *writeCloserWrapper) Close() error {
+-	return r.closer()
+-}
+-
+-func NewWriteCloserWrapper(r io.Writer, closer func() error) io.WriteCloser {
+-	return &writeCloserWrapper{
+-		Writer: r,
+-		closer: closer,
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/pools/pools.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/pools/pools.go
+deleted file mode 100644
+index 5338a0c..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/pools/pools.go
++++ /dev/null
+@@ -1,111 +0,0 @@
+-// +build go1.3
+-
+-// Package pools provides a collection of pools which provide various
+-// data types with buffers. These can be used to lower the number of
+-// memory allocations and reuse buffers.
+-//
+-// New pools should be added to this package to allow them to be
+-// shared across packages.
+-//
+-// Utility functions which operate on pools should be added to this
+-// package to allow them to be reused.
+-package pools
+-
+-import (
+-	"bufio"
+-	"io"
+-	"sync"
+-
+-	"github.com/docker/docker/pkg/ioutils"
+-)
+-
+-var (
+-	// Pool which returns bufio.Reader with a 32K buffer
+-	BufioReader32KPool *BufioReaderPool
+-	// Pool which returns bufio.Writer with a 32K buffer
+-	BufioWriter32KPool *BufioWriterPool
+-)
+-
+-const buffer32K = 32 * 1024
+-
+-type BufioReaderPool struct {
+-	pool sync.Pool
+-}
+-
+-func init() {
+-	BufioReader32KPool = newBufioReaderPoolWithSize(buffer32K)
+-	BufioWriter32KPool = newBufioWriterPoolWithSize(buffer32K)
+-}
+-
+-// newBufioReaderPoolWithSize is unexported because new pools should be
+-// added here to be shared where required.
+-func newBufioReaderPoolWithSize(size int) *BufioReaderPool {
+-	pool := sync.Pool{
+-		New: func() interface{} { return bufio.NewReaderSize(nil, size) },
+-	}
+-	return &BufioReaderPool{pool: pool}
+-}
+-
+-// Get returns a bufio.Reader which reads from r. The buffer size is that of the pool.
+-func (bufPool *BufioReaderPool) Get(r io.Reader) *bufio.Reader {
+-	buf := bufPool.pool.Get().(*bufio.Reader)
+-	buf.Reset(r)
+-	return buf
+-}
+-
+-// Put puts the bufio.Reader back into the pool.
+-func (bufPool *BufioReaderPool) Put(b *bufio.Reader) {
+-	b.Reset(nil)
+-	bufPool.pool.Put(b)
+-}
+-
+-// NewReadCloserWrapper returns a wrapper which puts the bufio.Reader back
+-// into the pool and closes the reader if it's an io.ReadCloser.
+-func (bufPool *BufioReaderPool) NewReadCloserWrapper(buf *bufio.Reader, r io.Reader) io.ReadCloser {
+-	return ioutils.NewReadCloserWrapper(r, func() error {
+-		if readCloser, ok := r.(io.ReadCloser); ok {
+-			readCloser.Close()
+-		}
+-		bufPool.Put(buf)
+-		return nil
+-	})
+-}
+-
+-type BufioWriterPool struct {
+-	pool sync.Pool
+-}
+-
+-// newBufioWriterPoolWithSize is unexported because new pools should be
+-// added here to be shared where required.
+-func newBufioWriterPoolWithSize(size int) *BufioWriterPool {
+-	pool := sync.Pool{
+-		New: func() interface{} { return bufio.NewWriterSize(nil, size) },
+-	}
+-	return &BufioWriterPool{pool: pool}
+-}
+-
+-// Get returns a bufio.Writer which writes to w. The buffer size is that of the pool.
+-func (bufPool *BufioWriterPool) Get(w io.Writer) *bufio.Writer {
+-	buf := bufPool.pool.Get().(*bufio.Writer)
+-	buf.Reset(w)
+-	return buf
+-}
+-
+-// Put puts the bufio.Writer back into the pool.
+-func (bufPool *BufioWriterPool) Put(b *bufio.Writer) {
+-	b.Reset(nil)
+-	bufPool.pool.Put(b)
+-}
+-
+-// NewWriteCloserWrapper returns a wrapper which puts the bufio.Writer back
+-// into the pool and closes the writer if it's an io.Writecloser.
+-func (bufPool *BufioWriterPool) NewWriteCloserWrapper(buf *bufio.Writer, w io.Writer) io.WriteCloser {
+-	return ioutils.NewWriteCloserWrapper(w, func() error {
+-		buf.Flush()
+-		if writeCloser, ok := w.(io.WriteCloser); ok {
+-			writeCloser.Close()
+-		}
+-		bufPool.Put(buf)
+-		return nil
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/pools/pools_nopool.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/pools/pools_nopool.go
+deleted file mode 100644
+index 48903c2..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/pools/pools_nopool.go
++++ /dev/null
+@@ -1,73 +0,0 @@
+-// +build !go1.3
+-
+-package pools
+-
+-import (
+-	"bufio"
+-	"io"
+-
+-	"github.com/docker/docker/pkg/ioutils"
+-)
+-
+-var (
+-	BufioReader32KPool *BufioReaderPool
+-	BufioWriter32KPool *BufioWriterPool
+-)
+-
+-const buffer32K = 32 * 1024
+-
+-type BufioReaderPool struct {
+-	size int
+-}
+-
+-func init() {
+-	BufioReader32KPool = newBufioReaderPoolWithSize(buffer32K)
+-	BufioWriter32KPool = newBufioWriterPoolWithSize(buffer32K)
+-}
+-
+-func newBufioReaderPoolWithSize(size int) *BufioReaderPool {
+-	return &BufioReaderPool{size: size}
+-}
+-
+-func (bufPool *BufioReaderPool) Get(r io.Reader) *bufio.Reader {
+-	return bufio.NewReaderSize(r, bufPool.size)
+-}
+-
+-func (bufPool *BufioReaderPool) Put(b *bufio.Reader) {
+-	b.Reset(nil)
+-}
+-
+-func (bufPool *BufioReaderPool) NewReadCloserWrapper(buf *bufio.Reader, r io.Reader) io.ReadCloser {
+-	return ioutils.NewReadCloserWrapper(r, func() error {
+-		if readCloser, ok := r.(io.ReadCloser); ok {
+-			return readCloser.Close()
+-		}
+-		return nil
+-	})
+-}
+-
+-type BufioWriterPool struct {
+-	size int
+-}
+-
+-func newBufioWriterPoolWithSize(size int) *BufioWriterPool {
+-	return &BufioWriterPool{size: size}
+-}
+-
+-func (bufPool *BufioWriterPool) Get(w io.Writer) *bufio.Writer {
+-	return bufio.NewWriterSize(w, bufPool.size)
+-}
+-
+-func (bufPool *BufioWriterPool) Put(b *bufio.Writer) {
+-	b.Reset(nil)
+-}
+-
+-func (bufPool *BufioWriterPool) NewWriteCloserWrapper(buf *bufio.Writer, w io.Writer) io.WriteCloser {
+-	return ioutils.NewWriteCloserWrapper(w, func() error {
+-		buf.Flush()
+-		if writeCloser, ok := w.(io.WriteCloser); ok {
+-			return writeCloser.Close()
+-		}
+-		return nil
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/promise/promise.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/promise/promise.go
+deleted file mode 100644
+index dd52b90..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/promise/promise.go
++++ /dev/null
+@@ -1,11 +0,0 @@
+-package promise
+-
+-// Go is a basic promise implementation: it wraps calls a function in a goroutine,
+-// and returns a channel which will later return the function's return value.
+-func Go(f func() error) chan error {
+-	ch := make(chan error, 1)
+-	go func() {
+-		ch <- f()
+-	}()
+-	return ch
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/MAINTAINERS b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/MAINTAINERS
+deleted file mode 100644
+index 68a97d2..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/MAINTAINERS
++++ /dev/null
+@@ -1,2 +0,0 @@
+-Michael Crosby <michael at crosbymichael.com> (@crosbymichael)
+-Victor Vieux <vieux at docker.com> (@vieux)
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/errors.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/errors.go
+deleted file mode 100644
+index 6304518..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/errors.go
++++ /dev/null
+@@ -1,9 +0,0 @@
+-package system
+-
+-import (
+-	"errors"
+-)
+-
+-var (
+-	ErrNotSupportedPlatform = errors.New("platform and architecture is not supported")
+-)
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/lstat.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/lstat.go
+deleted file mode 100644
+index 9ef82d5..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/lstat.go
++++ /dev/null
+@@ -1,16 +0,0 @@
+-// +build !windows
+-
+-package system
+-
+-import (
+-	"syscall"
+-)
+-
+-func Lstat(path string) (*Stat, error) {
+-	s := &syscall.Stat_t{}
+-	err := syscall.Lstat(path, s)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return fromStatT(s)
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/lstat_test.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/lstat_test.go
+deleted file mode 100644
+index 9bab4d7..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/lstat_test.go
++++ /dev/null
+@@ -1,27 +0,0 @@
+-package system
+-
+-import (
+-	"os"
+-	"testing"
+-)
+-
+-func TestLstat(t *testing.T) {
+-	file, invalid, _, dir := prepareFiles(t)
+-	defer os.RemoveAll(dir)
+-
+-	statFile, err := Lstat(file)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if statFile == nil {
+-		t.Fatal("returned empty stat for existing file")
+-	}
+-
+-	statInvalid, err := Lstat(invalid)
+-	if err == nil {
+-		t.Fatal("did not return error for non-existing file")
+-	}
+-	if statInvalid != nil {
+-		t.Fatal("returned non-nil stat for non-existing file")
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/lstat_windows.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/lstat_windows.go
+deleted file mode 100644
+index 213a7c7..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/lstat_windows.go
++++ /dev/null
+@@ -1,8 +0,0 @@
+-// +build windows
+-
+-package system
+-
+-func Lstat(path string) (*Stat, error) {
+-	// should not be called on cli code path
+-	return nil, ErrNotSupportedPlatform
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/meminfo.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/meminfo.go
+deleted file mode 100644
+index 3b6e947..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/meminfo.go
++++ /dev/null
+@@ -1,17 +0,0 @@
+-package system
+-
+-// MemInfo contains memory statistics of the host system.
+-type MemInfo struct {
+-	// Total usable RAM (i.e. physical RAM minus a few reserved bits and the
+-	// kernel binary code).
+-	MemTotal int64
+-
+-	// Amount of free memory.
+-	MemFree int64
+-
+-	// Total amount of swap space available.
+-	SwapTotal int64
+-
+-	// Amount of swap space that is currently unused.
+-	SwapFree int64
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/meminfo_linux.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/meminfo_linux.go
+deleted file mode 100644
+index b7de3ff..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/meminfo_linux.go
++++ /dev/null
+@@ -1,67 +0,0 @@
+-package system
+-
+-import (
+-	"bufio"
+-	"errors"
+-	"io"
+-	"os"
+-	"strconv"
+-	"strings"
+-
+-	"github.com/docker/docker/pkg/units"
+-)
+-
+-var (
+-	ErrMalformed = errors.New("malformed file")
+-)
+-
+-// Retrieve memory statistics of the host system and parse them into a MemInfo
+-// type.
+-func ReadMemInfo() (*MemInfo, error) {
+-	file, err := os.Open("/proc/meminfo")
+-	if err != nil {
+-		return nil, err
+-	}
+-	defer file.Close()
+-	return parseMemInfo(file)
+-}
+-
+-func parseMemInfo(reader io.Reader) (*MemInfo, error) {
+-	meminfo := &MemInfo{}
+-	scanner := bufio.NewScanner(reader)
+-	for scanner.Scan() {
+-		// Expected format: ["MemTotal:", "1234", "kB"]
+-		parts := strings.Fields(scanner.Text())
+-
+-		// Sanity checks: Skip malformed entries.
+-		if len(parts) < 3 || parts[2] != "kB" {
+-			continue
+-		}
+-
+-		// Convert to bytes.
+-		size, err := strconv.Atoi(parts[1])
+-		if err != nil {
+-			continue
+-		}
+-		bytes := int64(size) * units.KiB
+-
+-		switch parts[0] {
+-		case "MemTotal:":
+-			meminfo.MemTotal = bytes
+-		case "MemFree:":
+-			meminfo.MemFree = bytes
+-		case "SwapTotal:":
+-			meminfo.SwapTotal = bytes
+-		case "SwapFree:":
+-			meminfo.SwapFree = bytes
+-		}
+-
+-	}
+-
+-	// Handle errors that may have occurred during the reading of the file.
+-	if err := scanner.Err(); err != nil {
+-		return nil, err
+-	}
+-
+-	return meminfo, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/meminfo_linux_test.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/meminfo_linux_test.go
+deleted file mode 100644
+index 377405e..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/meminfo_linux_test.go
++++ /dev/null
+@@ -1,37 +0,0 @@
+-package system
+-
+-import (
+-	"strings"
+-	"testing"
+-
+-	"github.com/docker/docker/pkg/units"
+-)
+-
+-func TestMemInfo(t *testing.T) {
+-	const input = `
+-	MemTotal:      1 kB
+-	MemFree:       2 kB
+-	SwapTotal:     3 kB
+-	SwapFree:      4 kB
+-	Malformed1:
+-	Malformed2:    1
+-	Malformed3:    2 MB
+-	Malformed4:    X kB
+-	`
+-	meminfo, err := parseMemInfo(strings.NewReader(input))
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if meminfo.MemTotal != 1*units.KiB {
+-		t.Fatalf("Unexpected MemTotal: %d", meminfo.MemTotal)
+-	}
+-	if meminfo.MemFree != 2*units.KiB {
+-		t.Fatalf("Unexpected MemFree: %d", meminfo.MemFree)
+-	}
+-	if meminfo.SwapTotal != 3*units.KiB {
+-		t.Fatalf("Unexpected SwapTotal: %d", meminfo.SwapTotal)
+-	}
+-	if meminfo.SwapFree != 4*units.KiB {
+-		t.Fatalf("Unexpected SwapFree: %d", meminfo.SwapFree)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/meminfo_unsupported.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/meminfo_unsupported.go
+deleted file mode 100644
+index 63b8b16..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/meminfo_unsupported.go
++++ /dev/null
+@@ -1,7 +0,0 @@
+-// +build !linux
+-
+-package system
+-
+-func ReadMemInfo() (*MemInfo, error) {
+-	return nil, ErrNotSupportedPlatform
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/mknod.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/mknod.go
+deleted file mode 100644
+index 06f9c6a..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/mknod.go
++++ /dev/null
+@@ -1,18 +0,0 @@
+-// +build !windows
+-
+-package system
+-
+-import (
+-	"syscall"
+-)
+-
+-func Mknod(path string, mode uint32, dev int) error {
+-	return syscall.Mknod(path, mode, dev)
+-}
+-
+-// Linux device nodes are a bit weird due to backwards compat with 16 bit device nodes.
+-// They are, from low to high: the lower 8 bits of the minor, then 12 bits of the major,
+-// then the top 12 bits of the minor
+-func Mkdev(major int64, minor int64) uint32 {
+-	return uint32(((minor & 0xfff00) << 12) | ((major & 0xfff) << 8) | (minor & 0xff))
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/mknod_windows.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/mknod_windows.go
+deleted file mode 100644
+index b4020c1..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/mknod_windows.go
++++ /dev/null
+@@ -1,12 +0,0 @@
+-// +build windows
+-
+-package system
+-
+-func Mknod(path string, mode uint32, dev int) error {
+-	// should not be called on cli code path
+-	return ErrNotSupportedPlatform
+-}
+-
+-func Mkdev(major int64, minor int64) uint32 {
+-	panic("Mkdev not implemented on windows, should not be called on cli code")
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat.go
+deleted file mode 100644
+index 5d47494..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat.go
++++ /dev/null
+@@ -1,42 +0,0 @@
+-package system
+-
+-import (
+-	"syscall"
+-)
+-
+-type Stat struct {
+-	mode uint32
+-	uid  uint32
+-	gid  uint32
+-	rdev uint64
+-	size int64
+-	mtim syscall.Timespec
+-}
+-
+-func (s Stat) Mode() uint32 {
+-	return s.mode
+-}
+-
+-func (s Stat) Uid() uint32 {
+-	return s.uid
+-}
+-
+-func (s Stat) Gid() uint32 {
+-	return s.gid
+-}
+-
+-func (s Stat) Rdev() uint64 {
+-	return s.rdev
+-}
+-
+-func (s Stat) Size() int64 {
+-	return s.size
+-}
+-
+-func (s Stat) Mtim() syscall.Timespec {
+-	return s.mtim
+-}
+-
+-func (s Stat) GetLastModification() syscall.Timespec {
+-	return s.Mtim()
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat_linux.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat_linux.go
+deleted file mode 100644
+index 47cebef..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat_linux.go
++++ /dev/null
+@@ -1,14 +0,0 @@
+-package system
+-
+-import (
+-	"syscall"
+-)
+-
+-func fromStatT(s *syscall.Stat_t) (*Stat, error) {
+-	return &Stat{size: s.Size,
+-		mode: s.Mode,
+-		uid:  s.Uid,
+-		gid:  s.Gid,
+-		rdev: s.Rdev,
+-		mtim: s.Mtim}, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat_test.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat_test.go
+deleted file mode 100644
+index abcc8ea..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat_test.go
++++ /dev/null
+@@ -1,36 +0,0 @@
+-package system
+-
+-import (
+-	"os"
+-	"syscall"
+-	"testing"
+-)
+-
+-func TestFromStatT(t *testing.T) {
+-	file, _, _, dir := prepareFiles(t)
+-	defer os.RemoveAll(dir)
+-
+-	stat := &syscall.Stat_t{}
+-	err := syscall.Lstat(file, stat)
+-
+-	s, err := fromStatT(stat)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	if stat.Mode != s.Mode() {
+-		t.Fatal("got invalid mode")
+-	}
+-	if stat.Uid != s.Uid() {
+-		t.Fatal("got invalid uid")
+-	}
+-	if stat.Gid != s.Gid() {
+-		t.Fatal("got invalid gid")
+-	}
+-	if stat.Rdev != s.Rdev() {
+-		t.Fatal("got invalid rdev")
+-	}
+-	if stat.Mtim != s.Mtim() {
+-		t.Fatal("got invalid mtim")
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat_unsupported.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat_unsupported.go
+deleted file mode 100644
+index c4d53e6..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat_unsupported.go
++++ /dev/null
+@@ -1,16 +0,0 @@
+-// +build !linux,!windows
+-
+-package system
+-
+-import (
+-	"syscall"
+-)
+-
+-func fromStatT(s *syscall.Stat_t) (*Stat, error) {
+-	return &Stat{size: s.Size,
+-		mode: uint32(s.Mode),
+-		uid:  s.Uid,
+-		gid:  s.Gid,
+-		rdev: uint64(s.Rdev),
+-		mtim: s.Mtimespec}, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat_windows.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat_windows.go
+deleted file mode 100644
+index 584e894..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/stat_windows.go
++++ /dev/null
+@@ -1,12 +0,0 @@
+-// +build windows
+-
+-package system
+-
+-import (
+-	"errors"
+-	"syscall"
+-)
+-
+-func fromStatT(s *syscall.Win32FileAttributeData) (*Stat, error) {
+-	return nil, errors.New("fromStatT should not be called on windows path")
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/umask.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/umask.go
+deleted file mode 100644
+index fddbecd..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/umask.go
++++ /dev/null
+@@ -1,11 +0,0 @@
+-// +build !windows
+-
+-package system
+-
+-import (
+-	"syscall"
+-)
+-
+-func Umask(newmask int) (oldmask int, err error) {
+-	return syscall.Umask(newmask), nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/umask_windows.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/umask_windows.go
+deleted file mode 100644
+index 3be563f..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/umask_windows.go
++++ /dev/null
+@@ -1,8 +0,0 @@
+-// +build windows
+-
+-package system
+-
+-func Umask(newmask int) (oldmask int, err error) {
+-	// should not be called on cli code path
+-	return 0, ErrNotSupportedPlatform
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_darwin.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_darwin.go
+deleted file mode 100644
+index 4c6002f..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_darwin.go
++++ /dev/null
+@@ -1,11 +0,0 @@
+-package system
+-
+-import "syscall"
+-
+-func LUtimesNano(path string, ts []syscall.Timespec) error {
+-	return ErrNotSupportedPlatform
+-}
+-
+-func UtimesNano(path string, ts []syscall.Timespec) error {
+-	return syscall.UtimesNano(path, ts)
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_freebsd.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_freebsd.go
+deleted file mode 100644
+index ceaa044..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_freebsd.go
++++ /dev/null
+@@ -1,24 +0,0 @@
+-package system
+-
+-import (
+-	"syscall"
+-	"unsafe"
+-)
+-
+-func LUtimesNano(path string, ts []syscall.Timespec) error {
+-	var _path *byte
+-	_path, err := syscall.BytePtrFromString(path)
+-	if err != nil {
+-		return err
+-	}
+-
+-	if _, _, err := syscall.Syscall(syscall.SYS_LUTIMES, uintptr(unsafe.Pointer(_path)), uintptr(unsafe.Pointer(&ts[0])), 0); err != 0 && err != syscall.ENOSYS {
+-		return err
+-	}
+-
+-	return nil
+-}
+-
+-func UtimesNano(path string, ts []syscall.Timespec) error {
+-	return syscall.UtimesNano(path, ts)
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_linux.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_linux.go
+deleted file mode 100644
+index 8f90298..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_linux.go
++++ /dev/null
+@@ -1,28 +0,0 @@
+-package system
+-
+-import (
+-	"syscall"
+-	"unsafe"
+-)
+-
+-func LUtimesNano(path string, ts []syscall.Timespec) error {
+-	// These are not currently available in syscall
+-	AT_FDCWD := -100
+-	AT_SYMLINK_NOFOLLOW := 0x100
+-
+-	var _path *byte
+-	_path, err := syscall.BytePtrFromString(path)
+-	if err != nil {
+-		return err
+-	}
+-
+-	if _, _, err := syscall.Syscall6(syscall.SYS_UTIMENSAT, uintptr(AT_FDCWD), uintptr(unsafe.Pointer(_path)), uintptr(unsafe.Pointer(&ts[0])), uintptr(AT_SYMLINK_NOFOLLOW), 0, 0); err != 0 && err != syscall.ENOSYS {
+-		return err
+-	}
+-
+-	return nil
+-}
+-
+-func UtimesNano(path string, ts []syscall.Timespec) error {
+-	return syscall.UtimesNano(path, ts)
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_test.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_test.go
+deleted file mode 100644
+index 1dea47c..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_test.go
++++ /dev/null
+@@ -1,65 +0,0 @@
+-package system
+-
+-import (
+-	"io/ioutil"
+-	"os"
+-	"path/filepath"
+-	"syscall"
+-	"testing"
+-)
+-
+-func prepareFiles(t *testing.T) (string, string, string, string) {
+-	dir, err := ioutil.TempDir("", "docker-system-test")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	file := filepath.Join(dir, "exist")
+-	if err := ioutil.WriteFile(file, []byte("hello"), 0644); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	invalid := filepath.Join(dir, "doesnt-exist")
+-
+-	symlink := filepath.Join(dir, "symlink")
+-	if err := os.Symlink(file, symlink); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	return file, invalid, symlink, dir
+-}
+-
+-func TestLUtimesNano(t *testing.T) {
+-	file, invalid, symlink, dir := prepareFiles(t)
+-	defer os.RemoveAll(dir)
+-
+-	before, err := os.Stat(file)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	ts := []syscall.Timespec{{0, 0}, {0, 0}}
+-	if err := LUtimesNano(symlink, ts); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	symlinkInfo, err := os.Lstat(symlink)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if before.ModTime().Unix() == symlinkInfo.ModTime().Unix() {
+-		t.Fatal("The modification time of the symlink should be different")
+-	}
+-
+-	fileInfo, err := os.Stat(file)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if before.ModTime().Unix() != fileInfo.ModTime().Unix() {
+-		t.Fatal("The modification time of the file should be same")
+-	}
+-
+-	if err := LUtimesNano(invalid, ts); err == nil {
+-		t.Fatal("Doesn't return an error on a non-existing file")
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_unsupported.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_unsupported.go
+deleted file mode 100644
+index adf2734..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/utimes_unsupported.go
++++ /dev/null
+@@ -1,13 +0,0 @@
+-// +build !linux,!freebsd,!darwin
+-
+-package system
+-
+-import "syscall"
+-
+-func LUtimesNano(path string, ts []syscall.Timespec) error {
+-	return ErrNotSupportedPlatform
+-}
+-
+-func UtimesNano(path string, ts []syscall.Timespec) error {
+-	return ErrNotSupportedPlatform
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/xattrs_linux.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/xattrs_linux.go
+deleted file mode 100644
+index 00edb20..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/xattrs_linux.go
++++ /dev/null
+@@ -1,59 +0,0 @@
+-package system
+-
+-import (
+-	"syscall"
+-	"unsafe"
+-)
+-
+-// Returns a nil slice and nil error if the xattr is not set
+-func Lgetxattr(path string, attr string) ([]byte, error) {
+-	pathBytes, err := syscall.BytePtrFromString(path)
+-	if err != nil {
+-		return nil, err
+-	}
+-	attrBytes, err := syscall.BytePtrFromString(attr)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	dest := make([]byte, 128)
+-	destBytes := unsafe.Pointer(&dest[0])
+-	sz, _, errno := syscall.Syscall6(syscall.SYS_LGETXATTR, uintptr(unsafe.Pointer(pathBytes)), uintptr(unsafe.Pointer(attrBytes)), uintptr(destBytes), uintptr(len(dest)), 0, 0)
+-	if errno == syscall.ENODATA {
+-		return nil, nil
+-	}
+-	if errno == syscall.ERANGE {
+-		dest = make([]byte, sz)
+-		destBytes := unsafe.Pointer(&dest[0])
+-		sz, _, errno = syscall.Syscall6(syscall.SYS_LGETXATTR, uintptr(unsafe.Pointer(pathBytes)), uintptr(unsafe.Pointer(attrBytes)), uintptr(destBytes), uintptr(len(dest)), 0, 0)
+-	}
+-	if errno != 0 {
+-		return nil, errno
+-	}
+-
+-	return dest[:sz], nil
+-}
+-
+-var _zero uintptr
+-
+-func Lsetxattr(path string, attr string, data []byte, flags int) error {
+-	pathBytes, err := syscall.BytePtrFromString(path)
+-	if err != nil {
+-		return err
+-	}
+-	attrBytes, err := syscall.BytePtrFromString(attr)
+-	if err != nil {
+-		return err
+-	}
+-	var dataBytes unsafe.Pointer
+-	if len(data) > 0 {
+-		dataBytes = unsafe.Pointer(&data[0])
+-	} else {
+-		dataBytes = unsafe.Pointer(&_zero)
+-	}
+-	_, _, errno := syscall.Syscall6(syscall.SYS_LSETXATTR, uintptr(unsafe.Pointer(pathBytes)), uintptr(unsafe.Pointer(attrBytes)), uintptr(dataBytes), uintptr(len(data)), uintptr(flags), 0)
+-	if errno != 0 {
+-		return errno
+-	}
+-	return nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/xattrs_unsupported.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/system/xattrs_unsupported.go
+deleted file mode 100644
+index 0060c16..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/system/xattrs_unsupported.go
++++ /dev/null
+@@ -1,11 +0,0 @@
+-// +build !linux
+-
+-package system
+-
+-func Lgetxattr(path string, attr string) ([]byte, error) {
+-	return nil, ErrNotSupportedPlatform
+-}
+-
+-func Lsetxattr(path string, attr string, data []byte, flags int) error {
+-	return ErrNotSupportedPlatform
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/units/MAINTAINERS b/Godeps/_workspace/src/github.com/docker/docker/pkg/units/MAINTAINERS
+deleted file mode 100644
+index 96abeae..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/units/MAINTAINERS
++++ /dev/null
+@@ -1,2 +0,0 @@
+-Victor Vieux <vieux at docker.com> (@vieux)
+-Jessie Frazelle <jess at docker.com> (@jfrazelle)
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/units/duration.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/units/duration.go
+deleted file mode 100644
+index cd33121..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/units/duration.go
++++ /dev/null
+@@ -1,31 +0,0 @@
+-package units
+-
+-import (
+-	"fmt"
+-	"time"
+-)
+-
+-// HumanDuration returns a human-readable approximation of a duration
+-// (eg. "About a minute", "4 hours ago", etc.)
+-func HumanDuration(d time.Duration) string {
+-	if seconds := int(d.Seconds()); seconds < 1 {
+-		return "Less than a second"
+-	} else if seconds < 60 {
+-		return fmt.Sprintf("%d seconds", seconds)
+-	} else if minutes := int(d.Minutes()); minutes == 1 {
+-		return "About a minute"
+-	} else if minutes < 60 {
+-		return fmt.Sprintf("%d minutes", minutes)
+-	} else if hours := int(d.Hours()); hours == 1 {
+-		return "About an hour"
+-	} else if hours < 48 {
+-		return fmt.Sprintf("%d hours", hours)
+-	} else if hours < 24*7*2 {
+-		return fmt.Sprintf("%d days", hours/24)
+-	} else if hours < 24*30*3 {
+-		return fmt.Sprintf("%d weeks", hours/24/7)
+-	} else if hours < 24*365*2 {
+-		return fmt.Sprintf("%d months", hours/24/30)
+-	}
+-	return fmt.Sprintf("%f years", d.Hours()/24/365)
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/units/duration_test.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/units/duration_test.go
+deleted file mode 100644
+index a229474..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/units/duration_test.go
++++ /dev/null
+@@ -1,46 +0,0 @@
+-package units
+-
+-import (
+-	"testing"
+-	"time"
+-)
+-
+-func TestHumanDuration(t *testing.T) {
+-	// Useful duration abstractions
+-	day := 24 * time.Hour
+-	week := 7 * day
+-	month := 30 * day
+-	year := 365 * day
+-
+-	assertEquals(t, "Less than a second", HumanDuration(450*time.Millisecond))
+-	assertEquals(t, "47 seconds", HumanDuration(47*time.Second))
+-	assertEquals(t, "About a minute", HumanDuration(1*time.Minute))
+-	assertEquals(t, "3 minutes", HumanDuration(3*time.Minute))
+-	assertEquals(t, "35 minutes", HumanDuration(35*time.Minute))
+-	assertEquals(t, "35 minutes", HumanDuration(35*time.Minute+40*time.Second))
+-	assertEquals(t, "About an hour", HumanDuration(1*time.Hour))
+-	assertEquals(t, "About an hour", HumanDuration(1*time.Hour+45*time.Minute))
+-	assertEquals(t, "3 hours", HumanDuration(3*time.Hour))
+-	assertEquals(t, "3 hours", HumanDuration(3*time.Hour+59*time.Minute))
+-	assertEquals(t, "4 hours", HumanDuration(3*time.Hour+60*time.Minute))
+-	assertEquals(t, "24 hours", HumanDuration(24*time.Hour))
+-	assertEquals(t, "36 hours", HumanDuration(1*day+12*time.Hour))
+-	assertEquals(t, "2 days", HumanDuration(2*day))
+-	assertEquals(t, "7 days", HumanDuration(7*day))
+-	assertEquals(t, "13 days", HumanDuration(13*day+5*time.Hour))
+-	assertEquals(t, "2 weeks", HumanDuration(2*week))
+-	assertEquals(t, "2 weeks", HumanDuration(2*week+4*day))
+-	assertEquals(t, "3 weeks", HumanDuration(3*week))
+-	assertEquals(t, "4 weeks", HumanDuration(4*week))
+-	assertEquals(t, "4 weeks", HumanDuration(4*week+3*day))
+-	assertEquals(t, "4 weeks", HumanDuration(1*month))
+-	assertEquals(t, "6 weeks", HumanDuration(1*month+2*week))
+-	assertEquals(t, "8 weeks", HumanDuration(2*month))
+-	assertEquals(t, "3 months", HumanDuration(3*month+1*week))
+-	assertEquals(t, "5 months", HumanDuration(5*month+2*week))
+-	assertEquals(t, "13 months", HumanDuration(13*month))
+-	assertEquals(t, "23 months", HumanDuration(23*month))
+-	assertEquals(t, "24 months", HumanDuration(24*month))
+-	assertEquals(t, "2.010959 years", HumanDuration(24*month+2*week))
+-	assertEquals(t, "3.164384 years", HumanDuration(3*year+2*month))
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/units/size.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/units/size.go
+deleted file mode 100644
+index 264f388..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/units/size.go
++++ /dev/null
+@@ -1,91 +0,0 @@
+-package units
+-
+-import (
+-	"fmt"
+-	"regexp"
+-	"strconv"
+-	"strings"
+-)
+-
+-// See: http://en.wikipedia.org/wiki/Binary_prefix
+-const (
+-	// Decimal
+-
+-	KB = 1000
+-	MB = 1000 * KB
+-	GB = 1000 * MB
+-	TB = 1000 * GB
+-	PB = 1000 * TB
+-
+-	// Binary
+-
+-	KiB = 1024
+-	MiB = 1024 * KiB
+-	GiB = 1024 * MiB
+-	TiB = 1024 * GiB
+-	PiB = 1024 * TiB
+-)
+-
+-type unitMap map[string]int64
+-
+-var (
+-	decimalMap = unitMap{"k": KB, "m": MB, "g": GB, "t": TB, "p": PB}
+-	binaryMap  = unitMap{"k": KiB, "m": MiB, "g": GiB, "t": TiB, "p": PiB}
+-	sizeRegex  = regexp.MustCompile(`^(\d+)([kKmMgGtTpP])?[bB]?$`)
+-)
+-
+-var decimapAbbrs = []string{"B", "kB", "MB", "GB", "TB", "PB", "EB", "ZB", "YB"}
+-var binaryAbbrs = []string{"B", "KiB", "MiB", "GiB", "TiB", "PiB", "EiB", "ZiB", "YiB"}
+-
+-// HumanSize returns a human-readable approximation of a size
+-// using SI standard (eg. "44kB", "17MB")
+-func HumanSize(size int64) string {
+-	return intToString(float64(size), 1000.0, decimapAbbrs)
+-}
+-
+-func BytesSize(size float64) string {
+-	return intToString(size, 1024.0, binaryAbbrs)
+-}
+-
+-func intToString(size, unit float64, _map []string) string {
+-	i := 0
+-	for size >= unit {
+-		size = size / unit
+-		i++
+-	}
+-	return fmt.Sprintf("%.4g %s", size, _map[i])
+-}
+-
+-// FromHumanSize returns an integer from a human-readable specification of a
+-// size using SI standard (eg. "44kB", "17MB")
+-func FromHumanSize(size string) (int64, error) {
+-	return parseSize(size, decimalMap)
+-}
+-
+-// RAMInBytes parses a human-readable string representing an amount of RAM
+-// in bytes, kibibytes, mebibytes, gibibytes, or tebibytes and
+-// returns the number of bytes, or -1 if the string is unparseable.
+-// Units are case-insensitive, and the 'b' suffix is optional.
+-func RAMInBytes(size string) (int64, error) {
+-	return parseSize(size, binaryMap)
+-}
+-
+-// Parses the human-readable size string into the amount it represents
+-func parseSize(sizeStr string, uMap unitMap) (int64, error) {
+-	matches := sizeRegex.FindStringSubmatch(sizeStr)
+-	if len(matches) != 3 {
+-		return -1, fmt.Errorf("invalid size: '%s'", sizeStr)
+-	}
+-
+-	size, err := strconv.ParseInt(matches[1], 10, 0)
+-	if err != nil {
+-		return -1, err
+-	}
+-
+-	unitPrefix := strings.ToLower(matches[2])
+-	if mul, ok := uMap[unitPrefix]; ok {
+-		size *= mul
+-	}
+-
+-	return size, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/pkg/units/size_test.go b/Godeps/_workspace/src/github.com/docker/docker/pkg/units/size_test.go
+deleted file mode 100644
+index 3e410b0..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/pkg/units/size_test.go
++++ /dev/null
+@@ -1,108 +0,0 @@
+-package units
+-
+-import (
+-	"reflect"
+-	"runtime"
+-	"strings"
+-	"testing"
+-)
+-
+-func TestBytesSize(t *testing.T) {
+-	assertEquals(t, "1 KiB", BytesSize(1024))
+-	assertEquals(t, "1 MiB", BytesSize(1024*1024))
+-	assertEquals(t, "1 MiB", BytesSize(1048576))
+-	assertEquals(t, "2 MiB", BytesSize(2*MiB))
+-	assertEquals(t, "3.42 GiB", BytesSize(3.42*GiB))
+-	assertEquals(t, "5.372 TiB", BytesSize(5.372*TiB))
+-	assertEquals(t, "2.22 PiB", BytesSize(2.22*PiB))
+-}
+-
+-func TestHumanSize(t *testing.T) {
+-	assertEquals(t, "1 kB", HumanSize(1000))
+-	assertEquals(t, "1.024 kB", HumanSize(1024))
+-	assertEquals(t, "1 MB", HumanSize(1000000))
+-	assertEquals(t, "1.049 MB", HumanSize(1048576))
+-	assertEquals(t, "2 MB", HumanSize(2*MB))
+-	assertEquals(t, "3.42 GB", HumanSize(int64(float64(3.42*GB))))
+-	assertEquals(t, "5.372 TB", HumanSize(int64(float64(5.372*TB))))
+-	assertEquals(t, "2.22 PB", HumanSize(int64(float64(2.22*PB))))
+-}
+-
+-func TestFromHumanSize(t *testing.T) {
+-	assertSuccessEquals(t, 32, FromHumanSize, "32")
+-	assertSuccessEquals(t, 32, FromHumanSize, "32b")
+-	assertSuccessEquals(t, 32, FromHumanSize, "32B")
+-	assertSuccessEquals(t, 32*KB, FromHumanSize, "32k")
+-	assertSuccessEquals(t, 32*KB, FromHumanSize, "32K")
+-	assertSuccessEquals(t, 32*KB, FromHumanSize, "32kb")
+-	assertSuccessEquals(t, 32*KB, FromHumanSize, "32Kb")
+-	assertSuccessEquals(t, 32*MB, FromHumanSize, "32Mb")
+-	assertSuccessEquals(t, 32*GB, FromHumanSize, "32Gb")
+-	assertSuccessEquals(t, 32*TB, FromHumanSize, "32Tb")
+-	assertSuccessEquals(t, 32*PB, FromHumanSize, "32Pb")
+-
+-	assertError(t, FromHumanSize, "")
+-	assertError(t, FromHumanSize, "hello")
+-	assertError(t, FromHumanSize, "-32")
+-	assertError(t, FromHumanSize, "32.3")
+-	assertError(t, FromHumanSize, " 32 ")
+-	assertError(t, FromHumanSize, "32.3Kb")
+-	assertError(t, FromHumanSize, "32 mb")
+-	assertError(t, FromHumanSize, "32m b")
+-	assertError(t, FromHumanSize, "32bm")
+-}
+-
+-func TestRAMInBytes(t *testing.T) {
+-	assertSuccessEquals(t, 32, RAMInBytes, "32")
+-	assertSuccessEquals(t, 32, RAMInBytes, "32b")
+-	assertSuccessEquals(t, 32, RAMInBytes, "32B")
+-	assertSuccessEquals(t, 32*KiB, RAMInBytes, "32k")
+-	assertSuccessEquals(t, 32*KiB, RAMInBytes, "32K")
+-	assertSuccessEquals(t, 32*KiB, RAMInBytes, "32kb")
+-	assertSuccessEquals(t, 32*KiB, RAMInBytes, "32Kb")
+-	assertSuccessEquals(t, 32*MiB, RAMInBytes, "32Mb")
+-	assertSuccessEquals(t, 32*GiB, RAMInBytes, "32Gb")
+-	assertSuccessEquals(t, 32*TiB, RAMInBytes, "32Tb")
+-	assertSuccessEquals(t, 32*PiB, RAMInBytes, "32Pb")
+-	assertSuccessEquals(t, 32*PiB, RAMInBytes, "32PB")
+-	assertSuccessEquals(t, 32*PiB, RAMInBytes, "32P")
+-
+-	assertError(t, RAMInBytes, "")
+-	assertError(t, RAMInBytes, "hello")
+-	assertError(t, RAMInBytes, "-32")
+-	assertError(t, RAMInBytes, "32.3")
+-	assertError(t, RAMInBytes, " 32 ")
+-	assertError(t, RAMInBytes, "32.3Kb")
+-	assertError(t, RAMInBytes, "32 mb")
+-	assertError(t, RAMInBytes, "32m b")
+-	assertError(t, RAMInBytes, "32bm")
+-}
+-
+-func assertEquals(t *testing.T, expected, actual interface{}) {
+-	if expected != actual {
+-		t.Errorf("Expected '%v' but got '%v'", expected, actual)
+-	}
+-}
+-
+-// func that maps to the parse function signatures as testing abstraction
+-type parseFn func(string) (int64, error)
+-
+-// Define 'String()' for pretty-print
+-func (fn parseFn) String() string {
+-	fnName := runtime.FuncForPC(reflect.ValueOf(fn).Pointer()).Name()
+-	return fnName[strings.LastIndex(fnName, ".")+1:]
+-}
+-
+-func assertSuccessEquals(t *testing.T, expected int64, fn parseFn, arg string) {
+-	res, err := fn(arg)
+-	if err != nil || res != expected {
+-		t.Errorf("%s(\"%s\") -> expected '%d' but got '%d' with error '%v'", fn, arg, expected, res, err)
+-	}
+-}
+-
+-func assertError(t *testing.T, fn parseFn, arg string) {
+-	res, err := fn(arg)
+-	if err == nil && res != -1 {
+-		t.Errorf("%s(\"%s\") -> expected error but got '%d'", fn, arg, res)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/common.go b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/common.go
+deleted file mode 100644
+index e363aa7..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/common.go
++++ /dev/null
+@@ -1,305 +0,0 @@
+-// Copyright 2009 The Go 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 tar implements access to tar archives.
+-// It aims to cover most of the variations, including those produced
+-// by GNU and BSD tars.
+-//
+-// References:
+-//   http://www.freebsd.org/cgi/man.cgi?query=tar&sektion=5
+-//   http://www.gnu.org/software/tar/manual/html_node/Standard.html
+-//   http://pubs.opengroup.org/onlinepubs/9699919799/utilities/pax.html
+-package tar
+-
+-import (
+-	"bytes"
+-	"errors"
+-	"fmt"
+-	"os"
+-	"path"
+-	"time"
+-)
+-
+-const (
+-	blockSize = 512
+-
+-	// Types
+-	TypeReg           = '0'    // regular file
+-	TypeRegA          = '\x00' // regular file
+-	TypeLink          = '1'    // hard link
+-	TypeSymlink       = '2'    // symbolic link
+-	TypeChar          = '3'    // character device node
+-	TypeBlock         = '4'    // block device node
+-	TypeDir           = '5'    // directory
+-	TypeFifo          = '6'    // fifo node
+-	TypeCont          = '7'    // reserved
+-	TypeXHeader       = 'x'    // extended header
+-	TypeXGlobalHeader = 'g'    // global extended header
+-	TypeGNULongName   = 'L'    // Next file has a long name
+-	TypeGNULongLink   = 'K'    // Next file symlinks to a file w/ a long name
+-	TypeGNUSparse     = 'S'    // sparse file
+-)
+-
+-// A Header represents a single header in a tar archive.
+-// Some fields may not be populated.
+-type Header struct {
+-	Name       string    // name of header file entry
+-	Mode       int64     // permission and mode bits
+-	Uid        int       // user id of owner
+-	Gid        int       // group id of owner
+-	Size       int64     // length in bytes
+-	ModTime    time.Time // modified time
+-	Typeflag   byte      // type of header entry
+-	Linkname   string    // target name of link
+-	Uname      string    // user name of owner
+-	Gname      string    // group name of owner
+-	Devmajor   int64     // major number of character or block device
+-	Devminor   int64     // minor number of character or block device
+-	AccessTime time.Time // access time
+-	ChangeTime time.Time // status change time
+-	Xattrs     map[string]string
+-}
+-
+-// File name constants from the tar spec.
+-const (
+-	fileNameSize       = 100 // Maximum number of bytes in a standard tar name.
+-	fileNamePrefixSize = 155 // Maximum number of ustar extension bytes.
+-)
+-
+-// FileInfo returns an os.FileInfo for the Header.
+-func (h *Header) FileInfo() os.FileInfo {
+-	return headerFileInfo{h}
+-}
+-
+-// headerFileInfo implements os.FileInfo.
+-type headerFileInfo struct {
+-	h *Header
+-}
+-
+-func (fi headerFileInfo) Size() int64        { return fi.h.Size }
+-func (fi headerFileInfo) IsDir() bool        { return fi.Mode().IsDir() }
+-func (fi headerFileInfo) ModTime() time.Time { return fi.h.ModTime }
+-func (fi headerFileInfo) Sys() interface{}   { return fi.h }
+-
+-// Name returns the base name of the file.
+-func (fi headerFileInfo) Name() string {
+-	if fi.IsDir() {
+-		return path.Base(path.Clean(fi.h.Name))
+-	}
+-	return path.Base(fi.h.Name)
+-}
+-
+-// Mode returns the permission and mode bits for the headerFileInfo.
+-func (fi headerFileInfo) Mode() (mode os.FileMode) {
+-	// Set file permission bits.
+-	mode = os.FileMode(fi.h.Mode).Perm()
+-
+-	// Set setuid, setgid and sticky bits.
+-	if fi.h.Mode&c_ISUID != 0 {
+-		// setuid
+-		mode |= os.ModeSetuid
+-	}
+-	if fi.h.Mode&c_ISGID != 0 {
+-		// setgid
+-		mode |= os.ModeSetgid
+-	}
+-	if fi.h.Mode&c_ISVTX != 0 {
+-		// sticky
+-		mode |= os.ModeSticky
+-	}
+-
+-	// Set file mode bits.
+-	// clear perm, setuid, setgid and sticky bits.
+-	m := os.FileMode(fi.h.Mode) &^ 07777
+-	if m == c_ISDIR {
+-		// directory
+-		mode |= os.ModeDir
+-	}
+-	if m == c_ISFIFO {
+-		// named pipe (FIFO)
+-		mode |= os.ModeNamedPipe
+-	}
+-	if m == c_ISLNK {
+-		// symbolic link
+-		mode |= os.ModeSymlink
+-	}
+-	if m == c_ISBLK {
+-		// device file
+-		mode |= os.ModeDevice
+-	}
+-	if m == c_ISCHR {
+-		// Unix character device
+-		mode |= os.ModeDevice
+-		mode |= os.ModeCharDevice
+-	}
+-	if m == c_ISSOCK {
+-		// Unix domain socket
+-		mode |= os.ModeSocket
+-	}
+-
+-	switch fi.h.Typeflag {
+-	case TypeLink, TypeSymlink:
+-		// hard link, symbolic link
+-		mode |= os.ModeSymlink
+-	case TypeChar:
+-		// character device node
+-		mode |= os.ModeDevice
+-		mode |= os.ModeCharDevice
+-	case TypeBlock:
+-		// block device node
+-		mode |= os.ModeDevice
+-	case TypeDir:
+-		// directory
+-		mode |= os.ModeDir
+-	case TypeFifo:
+-		// fifo node
+-		mode |= os.ModeNamedPipe
+-	}
+-
+-	return mode
+-}
+-
+-// sysStat, if non-nil, populates h from system-dependent fields of fi.
+-var sysStat func(fi os.FileInfo, h *Header) error
+-
+-// Mode constants from the tar spec.
+-const (
+-	c_ISUID  = 04000   // Set uid
+-	c_ISGID  = 02000   // Set gid
+-	c_ISVTX  = 01000   // Save text (sticky bit)
+-	c_ISDIR  = 040000  // Directory
+-	c_ISFIFO = 010000  // FIFO
+-	c_ISREG  = 0100000 // Regular file
+-	c_ISLNK  = 0120000 // Symbolic link
+-	c_ISBLK  = 060000  // Block special file
+-	c_ISCHR  = 020000  // Character special file
+-	c_ISSOCK = 0140000 // Socket
+-)
+-
+-// Keywords for the PAX Extended Header
+-const (
+-	paxAtime    = "atime"
+-	paxCharset  = "charset"
+-	paxComment  = "comment"
+-	paxCtime    = "ctime" // please note that ctime is not a valid pax header.
+-	paxGid      = "gid"
+-	paxGname    = "gname"
+-	paxLinkpath = "linkpath"
+-	paxMtime    = "mtime"
+-	paxPath     = "path"
+-	paxSize     = "size"
+-	paxUid      = "uid"
+-	paxUname    = "uname"
+-	paxXattr    = "SCHILY.xattr."
+-	paxNone     = ""
+-)
+-
+-// FileInfoHeader creates a partially-populated Header from fi.
+-// If fi describes a symlink, FileInfoHeader records link as the link target.
+-// If fi describes a directory, a slash is appended to the name.
+-// Because os.FileInfo's Name method returns only the base name of
+-// the file it describes, it may be necessary to modify the Name field
+-// of the returned header to provide the full path name of the file.
+-func FileInfoHeader(fi os.FileInfo, link string) (*Header, error) {
+-	if fi == nil {
+-		return nil, errors.New("tar: FileInfo is nil")
+-	}
+-	fm := fi.Mode()
+-	h := &Header{
+-		Name:    fi.Name(),
+-		ModTime: fi.ModTime(),
+-		Mode:    int64(fm.Perm()), // or'd with c_IS* constants later
+-	}
+-	switch {
+-	case fm.IsRegular():
+-		h.Mode |= c_ISREG
+-		h.Typeflag = TypeReg
+-		h.Size = fi.Size()
+-	case fi.IsDir():
+-		h.Typeflag = TypeDir
+-		h.Mode |= c_ISDIR
+-		h.Name += "/"
+-	case fm&os.ModeSymlink != 0:
+-		h.Typeflag = TypeSymlink
+-		h.Mode |= c_ISLNK
+-		h.Linkname = link
+-	case fm&os.ModeDevice != 0:
+-		if fm&os.ModeCharDevice != 0 {
+-			h.Mode |= c_ISCHR
+-			h.Typeflag = TypeChar
+-		} else {
+-			h.Mode |= c_ISBLK
+-			h.Typeflag = TypeBlock
+-		}
+-	case fm&os.ModeNamedPipe != 0:
+-		h.Typeflag = TypeFifo
+-		h.Mode |= c_ISFIFO
+-	case fm&os.ModeSocket != 0:
+-		h.Mode |= c_ISSOCK
+-	default:
+-		return nil, fmt.Errorf("archive/tar: unknown file mode %v", fm)
+-	}
+-	if fm&os.ModeSetuid != 0 {
+-		h.Mode |= c_ISUID
+-	}
+-	if fm&os.ModeSetgid != 0 {
+-		h.Mode |= c_ISGID
+-	}
+-	if fm&os.ModeSticky != 0 {
+-		h.Mode |= c_ISVTX
+-	}
+-	if sysStat != nil {
+-		return h, sysStat(fi, h)
+-	}
+-	return h, nil
+-}
+-
+-var zeroBlock = make([]byte, blockSize)
+-
+-// POSIX specifies a sum of the unsigned byte values, but the Sun tar uses signed byte values.
+-// We compute and return both.
+-func checksum(header []byte) (unsigned int64, signed int64) {
+-	for i := 0; i < len(header); i++ {
+-		if i == 148 {
+-			// The chksum field (header[148:156]) is special: it should be treated as space bytes.
+-			unsigned += ' ' * 8
+-			signed += ' ' * 8
+-			i += 7
+-			continue
+-		}
+-		unsigned += int64(header[i])
+-		signed += int64(int8(header[i]))
+-	}
+-	return
+-}
+-
+-type slicer []byte
+-
+-func (sp *slicer) next(n int) (b []byte) {
+-	s := *sp
+-	b, *sp = s[0:n], s[n:]
+-	return
+-}
+-
+-func isASCII(s string) bool {
+-	for _, c := range s {
+-		if c >= 0x80 {
+-			return false
+-		}
+-	}
+-	return true
+-}
+-
+-func toASCII(s string) string {
+-	if isASCII(s) {
+-		return s
+-	}
+-	var buf bytes.Buffer
+-	for _, c := range s {
+-		if c < 0x80 {
+-			buf.WriteByte(byte(c))
+-		}
+-	}
+-	return buf.String()
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/example_test.go b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/example_test.go
+deleted file mode 100644
+index 351eaa0..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/example_test.go
++++ /dev/null
+@@ -1,79 +0,0 @@
+-// Copyright 2013 The Go 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 tar_test
+-
+-import (
+-	"archive/tar"
+-	"bytes"
+-	"fmt"
+-	"io"
+-	"log"
+-	"os"
+-)
+-
+-func Example() {
+-	// Create a buffer to write our archive to.
+-	buf := new(bytes.Buffer)
+-
+-	// Create a new tar archive.
+-	tw := tar.NewWriter(buf)
+-
+-	// Add some files to the archive.
+-	var files = []struct {
+-		Name, Body string
+-	}{
+-		{"readme.txt", "This archive contains some text files."},
+-		{"gopher.txt", "Gopher names:\nGeorge\nGeoffrey\nGonzo"},
+-		{"todo.txt", "Get animal handling licence."},
+-	}
+-	for _, file := range files {
+-		hdr := &tar.Header{
+-			Name: file.Name,
+-			Size: int64(len(file.Body)),
+-		}
+-		if err := tw.WriteHeader(hdr); err != nil {
+-			log.Fatalln(err)
+-		}
+-		if _, err := tw.Write([]byte(file.Body)); err != nil {
+-			log.Fatalln(err)
+-		}
+-	}
+-	// Make sure to check the error on Close.
+-	if err := tw.Close(); err != nil {
+-		log.Fatalln(err)
+-	}
+-
+-	// Open the tar archive for reading.
+-	r := bytes.NewReader(buf.Bytes())
+-	tr := tar.NewReader(r)
+-
+-	// Iterate through the files in the archive.
+-	for {
+-		hdr, err := tr.Next()
+-		if err == io.EOF {
+-			// end of tar archive
+-			break
+-		}
+-		if err != nil {
+-			log.Fatalln(err)
+-		}
+-		fmt.Printf("Contents of %s:\n", hdr.Name)
+-		if _, err := io.Copy(os.Stdout, tr); err != nil {
+-			log.Fatalln(err)
+-		}
+-		fmt.Println()
+-	}
+-
+-	// Output:
+-	// Contents of readme.txt:
+-	// This archive contains some text files.
+-	// Contents of gopher.txt:
+-	// Gopher names:
+-	// George
+-	// Geoffrey
+-	// Gonzo
+-	// Contents of todo.txt:
+-	// Get animal handling licence.
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/reader.go b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/reader.go
+deleted file mode 100644
+index a27559d..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/reader.go
++++ /dev/null
+@@ -1,820 +0,0 @@
+-// Copyright 2009 The Go 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 tar
+-
+-// TODO(dsymonds):
+-//   - pax extensions
+-
+-import (
+-	"bytes"
+-	"errors"
+-	"io"
+-	"io/ioutil"
+-	"os"
+-	"strconv"
+-	"strings"
+-	"time"
+-)
+-
+-var (
+-	ErrHeader = errors.New("archive/tar: invalid tar header")
+-)
+-
+-const maxNanoSecondIntSize = 9
+-
+-// A Reader provides sequential access to the contents of a tar archive.
+-// A tar archive consists of a sequence of files.
+-// The Next method advances to the next file in the archive (including the first),
+-// and then it can be treated as an io.Reader to access the file's data.
+-type Reader struct {
+-	r       io.Reader
+-	err     error
+-	pad     int64           // amount of padding (ignored) after current file entry
+-	curr    numBytesReader  // reader for current file entry
+-	hdrBuff [blockSize]byte // buffer to use in readHeader
+-}
+-
+-// A numBytesReader is an io.Reader with a numBytes method, returning the number
+-// of bytes remaining in the underlying encoded data.
+-type numBytesReader interface {
+-	io.Reader
+-	numBytes() int64
+-}
+-
+-// A regFileReader is a numBytesReader for reading file data from a tar archive.
+-type regFileReader struct {
+-	r  io.Reader // underlying reader
+-	nb int64     // number of unread bytes for current file entry
+-}
+-
+-// A sparseFileReader is a numBytesReader for reading sparse file data from a tar archive.
+-type sparseFileReader struct {
+-	rfr *regFileReader // reads the sparse-encoded file data
+-	sp  []sparseEntry  // the sparse map for the file
+-	pos int64          // keeps track of file position
+-	tot int64          // total size of the file
+-}
+-
+-// Keywords for GNU sparse files in a PAX extended header
+-const (
+-	paxGNUSparseNumBlocks = "GNU.sparse.numblocks"
+-	paxGNUSparseOffset    = "GNU.sparse.offset"
+-	paxGNUSparseNumBytes  = "GNU.sparse.numbytes"
+-	paxGNUSparseMap       = "GNU.sparse.map"
+-	paxGNUSparseName      = "GNU.sparse.name"
+-	paxGNUSparseMajor     = "GNU.sparse.major"
+-	paxGNUSparseMinor     = "GNU.sparse.minor"
+-	paxGNUSparseSize      = "GNU.sparse.size"
+-	paxGNUSparseRealSize  = "GNU.sparse.realsize"
+-)
+-
+-// Keywords for old GNU sparse headers
+-const (
+-	oldGNUSparseMainHeaderOffset               = 386
+-	oldGNUSparseMainHeaderIsExtendedOffset     = 482
+-	oldGNUSparseMainHeaderNumEntries           = 4
+-	oldGNUSparseExtendedHeaderIsExtendedOffset = 504
+-	oldGNUSparseExtendedHeaderNumEntries       = 21
+-	oldGNUSparseOffsetSize                     = 12
+-	oldGNUSparseNumBytesSize                   = 12
+-)
+-
+-// NewReader creates a new Reader reading from r.
+-func NewReader(r io.Reader) *Reader { return &Reader{r: r} }
+-
+-// Next advances to the next entry in the tar archive.
+-func (tr *Reader) Next() (*Header, error) {
+-	var hdr *Header
+-	if tr.err == nil {
+-		tr.skipUnread()
+-	}
+-	if tr.err != nil {
+-		return hdr, tr.err
+-	}
+-	hdr = tr.readHeader()
+-	if hdr == nil {
+-		return hdr, tr.err
+-	}
+-	// Check for PAX/GNU header.
+-	switch hdr.Typeflag {
+-	case TypeXHeader:
+-		//  PAX extended header
+-		headers, err := parsePAX(tr)
+-		if err != nil {
+-			return nil, err
+-		}
+-		// We actually read the whole file,
+-		// but this skips alignment padding
+-		tr.skipUnread()
+-		hdr = tr.readHeader()
+-		mergePAX(hdr, headers)
+-
+-		// Check for a PAX format sparse file
+-		sp, err := tr.checkForGNUSparsePAXHeaders(hdr, headers)
+-		if err != nil {
+-			tr.err = err
+-			return nil, err
+-		}
+-		if sp != nil {
+-			// Current file is a PAX format GNU sparse file.
+-			// Set the current file reader to a sparse file reader.
+-			tr.curr = &sparseFileReader{rfr: tr.curr.(*regFileReader), sp: sp, tot: hdr.Size}
+-		}
+-		return hdr, nil
+-	case TypeGNULongName:
+-		// We have a GNU long name header. Its contents are the real file name.
+-		realname, err := ioutil.ReadAll(tr)
+-		if err != nil {
+-			return nil, err
+-		}
+-		hdr, err := tr.Next()
+-		hdr.Name = cString(realname)
+-		return hdr, err
+-	case TypeGNULongLink:
+-		// We have a GNU long link header.
+-		realname, err := ioutil.ReadAll(tr)
+-		if err != nil {
+-			return nil, err
+-		}
+-		hdr, err := tr.Next()
+-		hdr.Linkname = cString(realname)
+-		return hdr, err
+-	}
+-	return hdr, tr.err
+-}
+-
+-// checkForGNUSparsePAXHeaders checks the PAX headers for GNU sparse headers. If they are found, then
+-// this function reads the sparse map and returns it. Unknown sparse formats are ignored, causing the file to
+-// be treated as a regular file.
+-func (tr *Reader) checkForGNUSparsePAXHeaders(hdr *Header, headers map[string]string) ([]sparseEntry, error) {
+-	var sparseFormat string
+-
+-	// Check for sparse format indicators
+-	major, majorOk := headers[paxGNUSparseMajor]
+-	minor, minorOk := headers[paxGNUSparseMinor]
+-	sparseName, sparseNameOk := headers[paxGNUSparseName]
+-	_, sparseMapOk := headers[paxGNUSparseMap]
+-	sparseSize, sparseSizeOk := headers[paxGNUSparseSize]
+-	sparseRealSize, sparseRealSizeOk := headers[paxGNUSparseRealSize]
+-
+-	// Identify which, if any, sparse format applies from which PAX headers are set
+-	if majorOk && minorOk {
+-		sparseFormat = major + "." + minor
+-	} else if sparseNameOk && sparseMapOk {
+-		sparseFormat = "0.1"
+-	} else if sparseSizeOk {
+-		sparseFormat = "0.0"
+-	} else {
+-		// Not a PAX format GNU sparse file.
+-		return nil, nil
+-	}
+-
+-	// Check for unknown sparse format
+-	if sparseFormat != "0.0" && sparseFormat != "0.1" && sparseFormat != "1.0" {
+-		return nil, nil
+-	}
+-
+-	// Update hdr from GNU sparse PAX headers
+-	if sparseNameOk {
+-		hdr.Name = sparseName
+-	}
+-	if sparseSizeOk {
+-		realSize, err := strconv.ParseInt(sparseSize, 10, 0)
+-		if err != nil {
+-			return nil, ErrHeader
+-		}
+-		hdr.Size = realSize
+-	} else if sparseRealSizeOk {
+-		realSize, err := strconv.ParseInt(sparseRealSize, 10, 0)
+-		if err != nil {
+-			return nil, ErrHeader
+-		}
+-		hdr.Size = realSize
+-	}
+-
+-	// Set up the sparse map, according to the particular sparse format in use
+-	var sp []sparseEntry
+-	var err error
+-	switch sparseFormat {
+-	case "0.0", "0.1":
+-		sp, err = readGNUSparseMap0x1(headers)
+-	case "1.0":
+-		sp, err = readGNUSparseMap1x0(tr.curr)
+-	}
+-	return sp, err
+-}
+-
+-// mergePAX merges well known headers according to PAX standard.
+-// In general headers with the same name as those found
+-// in the header struct overwrite those found in the header
+-// struct with higher precision or longer values. Esp. useful
+-// for name and linkname fields.
+-func mergePAX(hdr *Header, headers map[string]string) error {
+-	for k, v := range headers {
+-		switch k {
+-		case paxPath:
+-			hdr.Name = v
+-		case paxLinkpath:
+-			hdr.Linkname = v
+-		case paxGname:
+-			hdr.Gname = v
+-		case paxUname:
+-			hdr.Uname = v
+-		case paxUid:
+-			uid, err := strconv.ParseInt(v, 10, 0)
+-			if err != nil {
+-				return err
+-			}
+-			hdr.Uid = int(uid)
+-		case paxGid:
+-			gid, err := strconv.ParseInt(v, 10, 0)
+-			if err != nil {
+-				return err
+-			}
+-			hdr.Gid = int(gid)
+-		case paxAtime:
+-			t, err := parsePAXTime(v)
+-			if err != nil {
+-				return err
+-			}
+-			hdr.AccessTime = t
+-		case paxMtime:
+-			t, err := parsePAXTime(v)
+-			if err != nil {
+-				return err
+-			}
+-			hdr.ModTime = t
+-		case paxCtime:
+-			t, err := parsePAXTime(v)
+-			if err != nil {
+-				return err
+-			}
+-			hdr.ChangeTime = t
+-		case paxSize:
+-			size, err := strconv.ParseInt(v, 10, 0)
+-			if err != nil {
+-				return err
+-			}
+-			hdr.Size = int64(size)
+-		default:
+-			if strings.HasPrefix(k, paxXattr) {
+-				if hdr.Xattrs == nil {
+-					hdr.Xattrs = make(map[string]string)
+-				}
+-				hdr.Xattrs[k[len(paxXattr):]] = v
+-			}
+-		}
+-	}
+-	return nil
+-}
+-
+-// parsePAXTime takes a string of the form %d.%d as described in
+-// the PAX specification.
+-func parsePAXTime(t string) (time.Time, error) {
+-	buf := []byte(t)
+-	pos := bytes.IndexByte(buf, '.')
+-	var seconds, nanoseconds int64
+-	var err error
+-	if pos == -1 {
+-		seconds, err = strconv.ParseInt(t, 10, 0)
+-		if err != nil {
+-			return time.Time{}, err
+-		}
+-	} else {
+-		seconds, err = strconv.ParseInt(string(buf[:pos]), 10, 0)
+-		if err != nil {
+-			return time.Time{}, err
+-		}
+-		nano_buf := string(buf[pos+1:])
+-		// Pad as needed before converting to a decimal.
+-		// For example .030 -> .030000000 -> 30000000 nanoseconds
+-		if len(nano_buf) < maxNanoSecondIntSize {
+-			// Right pad
+-			nano_buf += strings.Repeat("0", maxNanoSecondIntSize-len(nano_buf))
+-		} else if len(nano_buf) > maxNanoSecondIntSize {
+-			// Right truncate
+-			nano_buf = nano_buf[:maxNanoSecondIntSize]
+-		}
+-		nanoseconds, err = strconv.ParseInt(string(nano_buf), 10, 0)
+-		if err != nil {
+-			return time.Time{}, err
+-		}
+-	}
+-	ts := time.Unix(seconds, nanoseconds)
+-	return ts, nil
+-}
+-
+-// parsePAX parses PAX headers.
+-// If an extended header (type 'x') is invalid, ErrHeader is returned
+-func parsePAX(r io.Reader) (map[string]string, error) {
+-	buf, err := ioutil.ReadAll(r)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	// For GNU PAX sparse format 0.0 support.
+-	// This function transforms the sparse format 0.0 headers into sparse format 0.1 headers.
+-	var sparseMap bytes.Buffer
+-
+-	headers := make(map[string]string)
+-	// Each record is constructed as
+-	//     "%d %s=%s\n", length, keyword, value
+-	for len(buf) > 0 {
+-		// or the header was empty to start with.
+-		var sp int
+-		// The size field ends at the first space.
+-		sp = bytes.IndexByte(buf, ' ')
+-		if sp == -1 {
+-			return nil, ErrHeader
+-		}
+-		// Parse the first token as a decimal integer.
+-		n, err := strconv.ParseInt(string(buf[:sp]), 10, 0)
+-		if err != nil {
+-			return nil, ErrHeader
+-		}
+-		// Extract everything between the decimal and the n -1 on the
+-		// beginning to eat the ' ', -1 on the end to skip the newline.
+-		var record []byte
+-		record, buf = buf[sp+1:n-1], buf[n:]
+-		// The first equals is guaranteed to mark the end of the key.
+-		// Everything else is value.
+-		eq := bytes.IndexByte(record, '=')
+-		if eq == -1 {
+-			return nil, ErrHeader
+-		}
+-		key, value := record[:eq], record[eq+1:]
+-
+-		keyStr := string(key)
+-		if keyStr == paxGNUSparseOffset || keyStr == paxGNUSparseNumBytes {
+-			// GNU sparse format 0.0 special key. Write to sparseMap instead of using the headers map.
+-			sparseMap.Write(value)
+-			sparseMap.Write([]byte{','})
+-		} else {
+-			// Normal key. Set the value in the headers map.
+-			headers[keyStr] = string(value)
+-		}
+-	}
+-	if sparseMap.Len() != 0 {
+-		// Add sparse info to headers, chopping off the extra comma
+-		sparseMap.Truncate(sparseMap.Len() - 1)
+-		headers[paxGNUSparseMap] = sparseMap.String()
+-	}
+-	return headers, nil
+-}
+-
+-// cString parses bytes as a NUL-terminated C-style string.
+-// If a NUL byte is not found then the whole slice is returned as a string.
+-func cString(b []byte) string {
+-	n := 0
+-	for n < len(b) && b[n] != 0 {
+-		n++
+-	}
+-	return string(b[0:n])
+-}
+-
+-func (tr *Reader) octal(b []byte) int64 {
+-	// Check for binary format first.
+-	if len(b) > 0 && b[0]&0x80 != 0 {
+-		var x int64
+-		for i, c := range b {
+-			if i == 0 {
+-				c &= 0x7f // ignore signal bit in first byte
+-			}
+-			x = x<<8 | int64(c)
+-		}
+-		return x
+-	}
+-
+-	// Because unused fields are filled with NULs, we need
+-	// to skip leading NULs. Fields may also be padded with
+-	// spaces or NULs.
+-	// So we remove leading and trailing NULs and spaces to
+-	// be sure.
+-	b = bytes.Trim(b, " \x00")
+-
+-	if len(b) == 0 {
+-		return 0
+-	}
+-	x, err := strconv.ParseUint(cString(b), 8, 64)
+-	if err != nil {
+-		tr.err = err
+-	}
+-	return int64(x)
+-}
+-
+-// skipUnread skips any unread bytes in the existing file entry, as well as any alignment padding.
+-func (tr *Reader) skipUnread() {
+-	nr := tr.numBytes() + tr.pad // number of bytes to skip
+-	tr.curr, tr.pad = nil, 0
+-	if sr, ok := tr.r.(io.Seeker); ok {
+-		if _, err := sr.Seek(nr, os.SEEK_CUR); err == nil {
+-			return
+-		}
+-	}
+-	_, tr.err = io.CopyN(ioutil.Discard, tr.r, nr)
+-}
+-
+-func (tr *Reader) verifyChecksum(header []byte) bool {
+-	if tr.err != nil {
+-		return false
+-	}
+-
+-	given := tr.octal(header[148:156])
+-	unsigned, signed := checksum(header)
+-	return given == unsigned || given == signed
+-}
+-
+-func (tr *Reader) readHeader() *Header {
+-	header := tr.hdrBuff[:]
+-	copy(header, zeroBlock)
+-
+-	if _, tr.err = io.ReadFull(tr.r, header); tr.err != nil {
+-		return nil
+-	}
+-
+-	// Two blocks of zero bytes marks the end of the archive.
+-	if bytes.Equal(header, zeroBlock[0:blockSize]) {
+-		if _, tr.err = io.ReadFull(tr.r, header); tr.err != nil {
+-			return nil
+-		}
+-		if bytes.Equal(header, zeroBlock[0:blockSize]) {
+-			tr.err = io.EOF
+-		} else {
+-			tr.err = ErrHeader // zero block and then non-zero block
+-		}
+-		return nil
+-	}
+-
+-	if !tr.verifyChecksum(header) {
+-		tr.err = ErrHeader
+-		return nil
+-	}
+-
+-	// Unpack
+-	hdr := new(Header)
+-	s := slicer(header)
+-
+-	hdr.Name = cString(s.next(100))
+-	hdr.Mode = tr.octal(s.next(8))
+-	hdr.Uid = int(tr.octal(s.next(8)))
+-	hdr.Gid = int(tr.octal(s.next(8)))
+-	hdr.Size = tr.octal(s.next(12))
+-	hdr.ModTime = time.Unix(tr.octal(s.next(12)), 0)
+-	s.next(8) // chksum
+-	hdr.Typeflag = s.next(1)[0]
+-	hdr.Linkname = cString(s.next(100))
+-
+-	// The remainder of the header depends on the value of magic.
+-	// The original (v7) version of tar had no explicit magic field,
+-	// so its magic bytes, like the rest of the block, are NULs.
+-	magic := string(s.next(8)) // contains version field as well.
+-	var format string
+-	switch {
+-	case magic[:6] == "ustar\x00": // POSIX tar (1003.1-1988)
+-		if string(header[508:512]) == "tar\x00" {
+-			format = "star"
+-		} else {
+-			format = "posix"
+-		}
+-	case magic == "ustar  \x00": // old GNU tar
+-		format = "gnu"
+-	}
+-
+-	switch format {
+-	case "posix", "gnu", "star":
+-		hdr.Uname = cString(s.next(32))
+-		hdr.Gname = cString(s.next(32))
+-		devmajor := s.next(8)
+-		devminor := s.next(8)
+-		if hdr.Typeflag == TypeChar || hdr.Typeflag == TypeBlock {
+-			hdr.Devmajor = tr.octal(devmajor)
+-			hdr.Devminor = tr.octal(devminor)
+-		}
+-		var prefix string
+-		switch format {
+-		case "posix", "gnu":
+-			prefix = cString(s.next(155))
+-		case "star":
+-			prefix = cString(s.next(131))
+-			hdr.AccessTime = time.Unix(tr.octal(s.next(12)), 0)
+-			hdr.ChangeTime = time.Unix(tr.octal(s.next(12)), 0)
+-		}
+-		if len(prefix) > 0 {
+-			hdr.Name = prefix + "/" + hdr.Name
+-		}
+-	}
+-
+-	if tr.err != nil {
+-		tr.err = ErrHeader
+-		return nil
+-	}
+-
+-	// Maximum value of hdr.Size is 64 GB (12 octal digits),
+-	// so there's no risk of int64 overflowing.
+-	nb := int64(hdr.Size)
+-	tr.pad = -nb & (blockSize - 1) // blockSize is a power of two
+-
+-	// Set the current file reader.
+-	tr.curr = &regFileReader{r: tr.r, nb: nb}
+-
+-	// Check for old GNU sparse format entry.
+-	if hdr.Typeflag == TypeGNUSparse {
+-		// Get the real size of the file.
+-		hdr.Size = tr.octal(header[483:495])
+-
+-		// Read the sparse map.
+-		sp := tr.readOldGNUSparseMap(header)
+-		if tr.err != nil {
+-			return nil
+-		}
+-		// Current file is a GNU sparse file. Update the current file reader.
+-		tr.curr = &sparseFileReader{rfr: tr.curr.(*regFileReader), sp: sp, tot: hdr.Size}
+-	}
+-
+-	return hdr
+-}
+-
+-// A sparseEntry holds a single entry in a sparse file's sparse map.
+-// A sparse entry indicates the offset and size in a sparse file of a
+-// block of data.
+-type sparseEntry struct {
+-	offset   int64
+-	numBytes int64
+-}
+-
+-// readOldGNUSparseMap reads the sparse map as stored in the old GNU sparse format.
+-// The sparse map is stored in the tar header if it's small enough. If it's larger than four entries,
+-// then one or more extension headers are used to store the rest of the sparse map.
+-func (tr *Reader) readOldGNUSparseMap(header []byte) []sparseEntry {
+-	isExtended := header[oldGNUSparseMainHeaderIsExtendedOffset] != 0
+-	spCap := oldGNUSparseMainHeaderNumEntries
+-	if isExtended {
+-		spCap += oldGNUSparseExtendedHeaderNumEntries
+-	}
+-	sp := make([]sparseEntry, 0, spCap)
+-	s := slicer(header[oldGNUSparseMainHeaderOffset:])
+-
+-	// Read the four entries from the main tar header
+-	for i := 0; i < oldGNUSparseMainHeaderNumEntries; i++ {
+-		offset := tr.octal(s.next(oldGNUSparseOffsetSize))
+-		numBytes := tr.octal(s.next(oldGNUSparseNumBytesSize))
+-		if tr.err != nil {
+-			tr.err = ErrHeader
+-			return nil
+-		}
+-		if offset == 0 && numBytes == 0 {
+-			break
+-		}
+-		sp = append(sp, sparseEntry{offset: offset, numBytes: numBytes})
+-	}
+-
+-	for isExtended {
+-		// There are more entries. Read an extension header and parse its entries.
+-		sparseHeader := make([]byte, blockSize)
+-		if _, tr.err = io.ReadFull(tr.r, sparseHeader); tr.err != nil {
+-			return nil
+-		}
+-		isExtended = sparseHeader[oldGNUSparseExtendedHeaderIsExtendedOffset] != 0
+-		s = slicer(sparseHeader)
+-		for i := 0; i < oldGNUSparseExtendedHeaderNumEntries; i++ {
+-			offset := tr.octal(s.next(oldGNUSparseOffsetSize))
+-			numBytes := tr.octal(s.next(oldGNUSparseNumBytesSize))
+-			if tr.err != nil {
+-				tr.err = ErrHeader
+-				return nil
+-			}
+-			if offset == 0 && numBytes == 0 {
+-				break
+-			}
+-			sp = append(sp, sparseEntry{offset: offset, numBytes: numBytes})
+-		}
+-	}
+-	return sp
+-}
+-
+-// readGNUSparseMap1x0 reads the sparse map as stored in GNU's PAX sparse format version 1.0.
+-// The sparse map is stored just before the file data and padded out to the nearest block boundary.
+-func readGNUSparseMap1x0(r io.Reader) ([]sparseEntry, error) {
+-	buf := make([]byte, 2*blockSize)
+-	sparseHeader := buf[:blockSize]
+-
+-	// readDecimal is a helper function to read a decimal integer from the sparse map
+-	// while making sure to read from the file in blocks of size blockSize
+-	readDecimal := func() (int64, error) {
+-		// Look for newline
+-		nl := bytes.IndexByte(sparseHeader, '\n')
+-		if nl == -1 {
+-			if len(sparseHeader) >= blockSize {
+-				// This is an error
+-				return 0, ErrHeader
+-			}
+-			oldLen := len(sparseHeader)
+-			newLen := oldLen + blockSize
+-			if cap(sparseHeader) < newLen {
+-				// There's more header, but we need to make room for the next block
+-				copy(buf, sparseHeader)
+-				sparseHeader = buf[:newLen]
+-			} else {
+-				// There's more header, and we can just reslice
+-				sparseHeader = sparseHeader[:newLen]
+-			}
+-
+-			// Now that sparseHeader is large enough, read next block
+-			if _, err := io.ReadFull(r, sparseHeader[oldLen:newLen]); err != nil {
+-				return 0, err
+-			}
+-
+-			// Look for a newline in the new data
+-			nl = bytes.IndexByte(sparseHeader[oldLen:newLen], '\n')
+-			if nl == -1 {
+-				// This is an error
+-				return 0, ErrHeader
+-			}
+-			nl += oldLen // We want the position from the beginning
+-		}
+-		// Now that we've found a newline, read a number
+-		n, err := strconv.ParseInt(string(sparseHeader[:nl]), 10, 0)
+-		if err != nil {
+-			return 0, ErrHeader
+-		}
+-
+-		// Update sparseHeader to consume this number
+-		sparseHeader = sparseHeader[nl+1:]
+-		return n, nil
+-	}
+-
+-	// Read the first block
+-	if _, err := io.ReadFull(r, sparseHeader); err != nil {
+-		return nil, err
+-	}
+-
+-	// The first line contains the number of entries
+-	numEntries, err := readDecimal()
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	// Read all the entries
+-	sp := make([]sparseEntry, 0, numEntries)
+-	for i := int64(0); i < numEntries; i++ {
+-		// Read the offset
+-		offset, err := readDecimal()
+-		if err != nil {
+-			return nil, err
+-		}
+-		// Read numBytes
+-		numBytes, err := readDecimal()
+-		if err != nil {
+-			return nil, err
+-		}
+-
+-		sp = append(sp, sparseEntry{offset: offset, numBytes: numBytes})
+-	}
+-
+-	return sp, nil
+-}
+-
+-// readGNUSparseMap0x1 reads the sparse map as stored in GNU's PAX sparse format version 0.1.
+-// The sparse map is stored in the PAX headers.
+-func readGNUSparseMap0x1(headers map[string]string) ([]sparseEntry, error) {
+-	// Get number of entries
+-	numEntriesStr, ok := headers[paxGNUSparseNumBlocks]
+-	if !ok {
+-		return nil, ErrHeader
+-	}
+-	numEntries, err := strconv.ParseInt(numEntriesStr, 10, 0)
+-	if err != nil {
+-		return nil, ErrHeader
+-	}
+-
+-	sparseMap := strings.Split(headers[paxGNUSparseMap], ",")
+-
+-	// There should be two numbers in sparseMap for each entry
+-	if int64(len(sparseMap)) != 2*numEntries {
+-		return nil, ErrHeader
+-	}
+-
+-	// Loop through the entries in the sparse map
+-	sp := make([]sparseEntry, 0, numEntries)
+-	for i := int64(0); i < numEntries; i++ {
+-		offset, err := strconv.ParseInt(sparseMap[2*i], 10, 0)
+-		if err != nil {
+-			return nil, ErrHeader
+-		}
+-		numBytes, err := strconv.ParseInt(sparseMap[2*i+1], 10, 0)
+-		if err != nil {
+-			return nil, ErrHeader
+-		}
+-		sp = append(sp, sparseEntry{offset: offset, numBytes: numBytes})
+-	}
+-
+-	return sp, nil
+-}
+-
+-// numBytes returns the number of bytes left to read in the current file's entry
+-// in the tar archive, or 0 if there is no current file.
+-func (tr *Reader) numBytes() int64 {
+-	if tr.curr == nil {
+-		// No current file, so no bytes
+-		return 0
+-	}
+-	return tr.curr.numBytes()
+-}
+-
+-// Read reads from the current entry in the tar archive.
+-// It returns 0, io.EOF when it reaches the end of that entry,
+-// until Next is called to advance to the next entry.
+-func (tr *Reader) Read(b []byte) (n int, err error) {
+-	if tr.curr == nil {
+-		return 0, io.EOF
+-	}
+-	n, err = tr.curr.Read(b)
+-	if err != nil && err != io.EOF {
+-		tr.err = err
+-	}
+-	return
+-}
+-
+-func (rfr *regFileReader) Read(b []byte) (n int, err error) {
+-	if rfr.nb == 0 {
+-		// file consumed
+-		return 0, io.EOF
+-	}
+-	if int64(len(b)) > rfr.nb {
+-		b = b[0:rfr.nb]
+-	}
+-	n, err = rfr.r.Read(b)
+-	rfr.nb -= int64(n)
+-
+-	if err == io.EOF && rfr.nb > 0 {
+-		err = io.ErrUnexpectedEOF
+-	}
+-	return
+-}
+-
+-// numBytes returns the number of bytes left to read in the file's data in the tar archive.
+-func (rfr *regFileReader) numBytes() int64 {
+-	return rfr.nb
+-}
+-
+-// readHole reads a sparse file hole ending at offset toOffset
+-func (sfr *sparseFileReader) readHole(b []byte, toOffset int64) int {
+-	n64 := toOffset - sfr.pos
+-	if n64 > int64(len(b)) {
+-		n64 = int64(len(b))
+-	}
+-	n := int(n64)
+-	for i := 0; i < n; i++ {
+-		b[i] = 0
+-	}
+-	sfr.pos += n64
+-	return n
+-}
+-
+-// Read reads the sparse file data in expanded form.
+-func (sfr *sparseFileReader) Read(b []byte) (n int, err error) {
+-	if len(sfr.sp) == 0 {
+-		// No more data fragments to read from.
+-		if sfr.pos < sfr.tot {
+-			// We're in the last hole
+-			n = sfr.readHole(b, sfr.tot)
+-			return
+-		}
+-		// Otherwise, we're at the end of the file
+-		return 0, io.EOF
+-	}
+-	if sfr.pos < sfr.sp[0].offset {
+-		// We're in a hole
+-		n = sfr.readHole(b, sfr.sp[0].offset)
+-		return
+-	}
+-
+-	// We're not in a hole, so we'll read from the next data fragment
+-	posInFragment := sfr.pos - sfr.sp[0].offset
+-	bytesLeft := sfr.sp[0].numBytes - posInFragment
+-	if int64(len(b)) > bytesLeft {
+-		b = b[0:bytesLeft]
+-	}
+-
+-	n, err = sfr.rfr.Read(b)
+-	sfr.pos += int64(n)
+-
+-	if int64(n) == bytesLeft {
+-		// We're done with this fragment
+-		sfr.sp = sfr.sp[1:]
+-	}
+-
+-	if err == io.EOF && sfr.pos < sfr.tot {
+-		// We reached the end of the last fragment's data, but there's a final hole
+-		err = nil
+-	}
+-	return
+-}
+-
+-// numBytes returns the number of bytes left to read in the sparse file's
+-// sparse-encoded data in the tar archive.
+-func (sfr *sparseFileReader) numBytes() int64 {
+-	return sfr.rfr.nb
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/reader_test.go b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/reader_test.go
+deleted file mode 100644
+index 9601ffe..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/reader_test.go
++++ /dev/null
+@@ -1,743 +0,0 @@
+-// Copyright 2009 The Go 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 tar
+-
+-import (
+-	"bytes"
+-	"crypto/md5"
+-	"fmt"
+-	"io"
+-	"io/ioutil"
+-	"os"
+-	"reflect"
+-	"strings"
+-	"testing"
+-	"time"
+-)
+-
+-type untarTest struct {
+-	file    string
+-	headers []*Header
+-	cksums  []string
+-}
+-
+-var gnuTarTest = &untarTest{
+-	file: "testdata/gnu.tar",
+-	headers: []*Header{
+-		{
+-			Name:     "small.txt",
+-			Mode:     0640,
+-			Uid:      73025,
+-			Gid:      5000,
+-			Size:     5,
+-			ModTime:  time.Unix(1244428340, 0),
+-			Typeflag: '0',
+-			Uname:    "dsymonds",
+-			Gname:    "eng",
+-		},
+-		{
+-			Name:     "small2.txt",
+-			Mode:     0640,
+-			Uid:      73025,
+-			Gid:      5000,
+-			Size:     11,
+-			ModTime:  time.Unix(1244436044, 0),
+-			Typeflag: '0',
+-			Uname:    "dsymonds",
+-			Gname:    "eng",
+-		},
+-	},
+-	cksums: []string{
+-		"e38b27eaccb4391bdec553a7f3ae6b2f",
+-		"c65bd2e50a56a2138bf1716f2fd56fe9",
+-	},
+-}
+-
+-var sparseTarTest = &untarTest{
+-	file: "testdata/sparse-formats.tar",
+-	headers: []*Header{
+-		{
+-			Name:     "sparse-gnu",
+-			Mode:     420,
+-			Uid:      1000,
+-			Gid:      1000,
+-			Size:     200,
+-			ModTime:  time.Unix(1392395740, 0),
+-			Typeflag: 0x53,
+-			Linkname: "",
+-			Uname:    "david",
+-			Gname:    "david",
+-			Devmajor: 0,
+-			Devminor: 0,
+-		},
+-		{
+-			Name:     "sparse-posix-0.0",
+-			Mode:     420,
+-			Uid:      1000,
+-			Gid:      1000,
+-			Size:     200,
+-			ModTime:  time.Unix(1392342187, 0),
+-			Typeflag: 0x30,
+-			Linkname: "",
+-			Uname:    "david",
+-			Gname:    "david",
+-			Devmajor: 0,
+-			Devminor: 0,
+-		},
+-		{
+-			Name:     "sparse-posix-0.1",
+-			Mode:     420,
+-			Uid:      1000,
+-			Gid:      1000,
+-			Size:     200,
+-			ModTime:  time.Unix(1392340456, 0),
+-			Typeflag: 0x30,
+-			Linkname: "",
+-			Uname:    "david",
+-			Gname:    "david",
+-			Devmajor: 0,
+-			Devminor: 0,
+-		},
+-		{
+-			Name:     "sparse-posix-1.0",
+-			Mode:     420,
+-			Uid:      1000,
+-			Gid:      1000,
+-			Size:     200,
+-			ModTime:  time.Unix(1392337404, 0),
+-			Typeflag: 0x30,
+-			Linkname: "",
+-			Uname:    "david",
+-			Gname:    "david",
+-			Devmajor: 0,
+-			Devminor: 0,
+-		},
+-		{
+-			Name:     "end",
+-			Mode:     420,
+-			Uid:      1000,
+-			Gid:      1000,
+-			Size:     4,
+-			ModTime:  time.Unix(1392398319, 0),
+-			Typeflag: 0x30,
+-			Linkname: "",
+-			Uname:    "david",
+-			Gname:    "david",
+-			Devmajor: 0,
+-			Devminor: 0,
+-		},
+-	},
+-	cksums: []string{
+-		"6f53234398c2449fe67c1812d993012f",
+-		"6f53234398c2449fe67c1812d993012f",
+-		"6f53234398c2449fe67c1812d993012f",
+-		"6f53234398c2449fe67c1812d993012f",
+-		"b0061974914468de549a2af8ced10316",
+-	},
+-}
+-
+-var untarTests = []*untarTest{
+-	gnuTarTest,
+-	sparseTarTest,
+-	{
+-		file: "testdata/star.tar",
+-		headers: []*Header{
+-			{
+-				Name:       "small.txt",
+-				Mode:       0640,
+-				Uid:        73025,
+-				Gid:        5000,
+-				Size:       5,
+-				ModTime:    time.Unix(1244592783, 0),
+-				Typeflag:   '0',
+-				Uname:      "dsymonds",
+-				Gname:      "eng",
+-				AccessTime: time.Unix(1244592783, 0),
+-				ChangeTime: time.Unix(1244592783, 0),
+-			},
+-			{
+-				Name:       "small2.txt",
+-				Mode:       0640,
+-				Uid:        73025,
+-				Gid:        5000,
+-				Size:       11,
+-				ModTime:    time.Unix(1244592783, 0),
+-				Typeflag:   '0',
+-				Uname:      "dsymonds",
+-				Gname:      "eng",
+-				AccessTime: time.Unix(1244592783, 0),
+-				ChangeTime: time.Unix(1244592783, 0),
+-			},
+-		},
+-	},
+-	{
+-		file: "testdata/v7.tar",
+-		headers: []*Header{
+-			{
+-				Name:     "small.txt",
+-				Mode:     0444,
+-				Uid:      73025,
+-				Gid:      5000,
+-				Size:     5,
+-				ModTime:  time.Unix(1244593104, 0),
+-				Typeflag: '\x00',
+-			},
+-			{
+-				Name:     "small2.txt",
+-				Mode:     0444,
+-				Uid:      73025,
+-				Gid:      5000,
+-				Size:     11,
+-				ModTime:  time.Unix(1244593104, 0),
+-				Typeflag: '\x00',
+-			},
+-		},
+-	},
+-	{
+-		file: "testdata/pax.tar",
+-		headers: []*Header{
+-			{
+-				Name:       "a/123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100",
+-				Mode:       0664,
+-				Uid:        1000,
+-				Gid:        1000,
+-				Uname:      "shane",
+-				Gname:      "shane",
+-				Size:       7,
+-				ModTime:    time.Unix(1350244992, 23960108),
+-				ChangeTime: time.Unix(1350244992, 23960108),
+-				AccessTime: time.Unix(1350244992, 23960108),
+-				Typeflag:   TypeReg,
+-			},
+-			{
+-				Name:       "a/b",
+-				Mode:       0777,
+-				Uid:        1000,
+-				Gid:        1000,
+-				Uname:      "shane",
+-				Gname:      "shane",
+-				Size:       0,
+-				ModTime:    time.Unix(1350266320, 910238425),
+-				ChangeTime: time.Unix(1350266320, 910238425),
+-				AccessTime: time.Unix(1350266320, 910238425),
+-				Typeflag:   TypeSymlink,
+-				Linkname:   "123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100",
+-			},
+-		},
+-	},
+-	{
+-		file: "testdata/nil-uid.tar", // golang.org/issue/5290
+-		headers: []*Header{
+-			{
+-				Name:     "P1050238.JPG.log",
+-				Mode:     0664,
+-				Uid:      0,
+-				Gid:      0,
+-				Size:     14,
+-				ModTime:  time.Unix(1365454838, 0),
+-				Typeflag: TypeReg,
+-				Linkname: "",
+-				Uname:    "eyefi",
+-				Gname:    "eyefi",
+-				Devmajor: 0,
+-				Devminor: 0,
+-			},
+-		},
+-	},
+-	{
+-		file: "testdata/xattrs.tar",
+-		headers: []*Header{
+-			{
+-				Name:       "small.txt",
+-				Mode:       0644,
+-				Uid:        1000,
+-				Gid:        10,
+-				Size:       5,
+-				ModTime:    time.Unix(1386065770, 448252320),
+-				Typeflag:   '0',
+-				Uname:      "alex",
+-				Gname:      "wheel",
+-				AccessTime: time.Unix(1389782991, 419875220),
+-				ChangeTime: time.Unix(1389782956, 794414986),
+-				Xattrs: map[string]string{
+-					"user.key":  "value",
+-					"user.key2": "value2",
+-					// Interestingly, selinux encodes the terminating null inside the xattr
+-					"security.selinux": "unconfined_u:object_r:default_t:s0\x00",
+-				},
+-			},
+-			{
+-				Name:       "small2.txt",
+-				Mode:       0644,
+-				Uid:        1000,
+-				Gid:        10,
+-				Size:       11,
+-				ModTime:    time.Unix(1386065770, 449252304),
+-				Typeflag:   '0',
+-				Uname:      "alex",
+-				Gname:      "wheel",
+-				AccessTime: time.Unix(1389782991, 419875220),
+-				ChangeTime: time.Unix(1386065770, 449252304),
+-				Xattrs: map[string]string{
+-					"security.selinux": "unconfined_u:object_r:default_t:s0\x00",
+-				},
+-			},
+-		},
+-	},
+-}
+-
+-func TestReader(t *testing.T) {
+-testLoop:
+-	for i, test := range untarTests {
+-		f, err := os.Open(test.file)
+-		if err != nil {
+-			t.Errorf("test %d: Unexpected error: %v", i, err)
+-			continue
+-		}
+-		defer f.Close()
+-		tr := NewReader(f)
+-		for j, header := range test.headers {
+-			hdr, err := tr.Next()
+-			if err != nil || hdr == nil {
+-				t.Errorf("test %d, entry %d: Didn't get entry: %v", i, j, err)
+-				f.Close()
+-				continue testLoop
+-			}
+-			if !reflect.DeepEqual(*hdr, *header) {
+-				t.Errorf("test %d, entry %d: Incorrect header:\nhave %+v\nwant %+v",
+-					i, j, *hdr, *header)
+-			}
+-		}
+-		hdr, err := tr.Next()
+-		if err == io.EOF {
+-			continue testLoop
+-		}
+-		if hdr != nil || err != nil {
+-			t.Errorf("test %d: Unexpected entry or error: hdr=%v err=%v", i, hdr, err)
+-		}
+-	}
+-}
+-
+-func TestPartialRead(t *testing.T) {
+-	f, err := os.Open("testdata/gnu.tar")
+-	if err != nil {
+-		t.Fatalf("Unexpected error: %v", err)
+-	}
+-	defer f.Close()
+-
+-	tr := NewReader(f)
+-
+-	// Read the first four bytes; Next() should skip the last byte.
+-	hdr, err := tr.Next()
+-	if err != nil || hdr == nil {
+-		t.Fatalf("Didn't get first file: %v", err)
+-	}
+-	buf := make([]byte, 4)
+-	if _, err := io.ReadFull(tr, buf); err != nil {
+-		t.Fatalf("Unexpected error: %v", err)
+-	}
+-	if expected := []byte("Kilt"); !bytes.Equal(buf, expected) {
+-		t.Errorf("Contents = %v, want %v", buf, expected)
+-	}
+-
+-	// Second file
+-	hdr, err = tr.Next()
+-	if err != nil || hdr == nil {
+-		t.Fatalf("Didn't get second file: %v", err)
+-	}
+-	buf = make([]byte, 6)
+-	if _, err := io.ReadFull(tr, buf); err != nil {
+-		t.Fatalf("Unexpected error: %v", err)
+-	}
+-	if expected := []byte("Google"); !bytes.Equal(buf, expected) {
+-		t.Errorf("Contents = %v, want %v", buf, expected)
+-	}
+-}
+-
+-func TestIncrementalRead(t *testing.T) {
+-	test := gnuTarTest
+-	f, err := os.Open(test.file)
+-	if err != nil {
+-		t.Fatalf("Unexpected error: %v", err)
+-	}
+-	defer f.Close()
+-
+-	tr := NewReader(f)
+-
+-	headers := test.headers
+-	cksums := test.cksums
+-	nread := 0
+-
+-	// loop over all files
+-	for ; ; nread++ {
+-		hdr, err := tr.Next()
+-		if hdr == nil || err == io.EOF {
+-			break
+-		}
+-
+-		// check the header
+-		if !reflect.DeepEqual(*hdr, *headers[nread]) {
+-			t.Errorf("Incorrect header:\nhave %+v\nwant %+v",
+-				*hdr, headers[nread])
+-		}
+-
+-		// read file contents in little chunks EOF,
+-		// checksumming all the way
+-		h := md5.New()
+-		rdbuf := make([]uint8, 8)
+-		for {
+-			nr, err := tr.Read(rdbuf)
+-			if err == io.EOF {
+-				break
+-			}
+-			if err != nil {
+-				t.Errorf("Read: unexpected error %v\n", err)
+-				break
+-			}
+-			h.Write(rdbuf[0:nr])
+-		}
+-		// verify checksum
+-		have := fmt.Sprintf("%x", h.Sum(nil))
+-		want := cksums[nread]
+-		if want != have {
+-			t.Errorf("Bad checksum on file %s:\nhave %+v\nwant %+v", hdr.Name, have, want)
+-		}
+-	}
+-	if nread != len(headers) {
+-		t.Errorf("Didn't process all files\nexpected: %d\nprocessed %d\n", len(headers), nread)
+-	}
+-}
+-
+-func TestNonSeekable(t *testing.T) {
+-	test := gnuTarTest
+-	f, err := os.Open(test.file)
+-	if err != nil {
+-		t.Fatalf("Unexpected error: %v", err)
+-	}
+-	defer f.Close()
+-
+-	type readerOnly struct {
+-		io.Reader
+-	}
+-	tr := NewReader(readerOnly{f})
+-	nread := 0
+-
+-	for ; ; nread++ {
+-		_, err := tr.Next()
+-		if err == io.EOF {
+-			break
+-		}
+-		if err != nil {
+-			t.Fatalf("Unexpected error: %v", err)
+-		}
+-	}
+-
+-	if nread != len(test.headers) {
+-		t.Errorf("Didn't process all files\nexpected: %d\nprocessed %d\n", len(test.headers), nread)
+-	}
+-}
+-
+-func TestParsePAXHeader(t *testing.T) {
+-	paxTests := [][3]string{
+-		{"a", "a=name", "10 a=name\n"}, // Test case involving multiple acceptable lengths
+-		{"a", "a=name", "9 a=name\n"},  // Test case involving multiple acceptable length
+-		{"mtime", "mtime=1350244992.023960108", "30 mtime=1350244992.023960108\n"}}
+-	for _, test := range paxTests {
+-		key, expected, raw := test[0], test[1], test[2]
+-		reader := bytes.NewReader([]byte(raw))
+-		headers, err := parsePAX(reader)
+-		if err != nil {
+-			t.Errorf("Couldn't parse correctly formatted headers: %v", err)
+-			continue
+-		}
+-		if strings.EqualFold(headers[key], expected) {
+-			t.Errorf("mtime header incorrectly parsed: got %s, wanted %s", headers[key], expected)
+-			continue
+-		}
+-		trailer := make([]byte, 100)
+-		n, err := reader.Read(trailer)
+-		if err != io.EOF || n != 0 {
+-			t.Error("Buffer wasn't consumed")
+-		}
+-	}
+-	badHeader := bytes.NewReader([]byte("3 somelongkey="))
+-	if _, err := parsePAX(badHeader); err != ErrHeader {
+-		t.Fatal("Unexpected success when parsing bad header")
+-	}
+-}
+-
+-func TestParsePAXTime(t *testing.T) {
+-	// Some valid PAX time values
+-	timestamps := map[string]time.Time{
+-		"1350244992.023960108":  time.Unix(1350244992, 23960108), // The common case
+-		"1350244992.02396010":   time.Unix(1350244992, 23960100), // Lower precision value
+-		"1350244992.0239601089": time.Unix(1350244992, 23960108), // Higher precision value
+-		"1350244992":            time.Unix(1350244992, 0),        // Low precision value
+-	}
+-	for input, expected := range timestamps {
+-		ts, err := parsePAXTime(input)
+-		if err != nil {
+-			t.Fatal(err)
+-		}
+-		if !ts.Equal(expected) {
+-			t.Fatalf("Time parsing failure %s %s", ts, expected)
+-		}
+-	}
+-}
+-
+-func TestMergePAX(t *testing.T) {
+-	hdr := new(Header)
+-	// Test a string, integer, and time based value.
+-	headers := map[string]string{
+-		"path":  "a/b/c",
+-		"uid":   "1000",
+-		"mtime": "1350244992.023960108",
+-	}
+-	err := mergePAX(hdr, headers)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	want := &Header{
+-		Name:    "a/b/c",
+-		Uid:     1000,
+-		ModTime: time.Unix(1350244992, 23960108),
+-	}
+-	if !reflect.DeepEqual(hdr, want) {
+-		t.Errorf("incorrect merge: got %+v, want %+v", hdr, want)
+-	}
+-}
+-
+-func TestSparseEndToEnd(t *testing.T) {
+-	test := sparseTarTest
+-	f, err := os.Open(test.file)
+-	if err != nil {
+-		t.Fatalf("Unexpected error: %v", err)
+-	}
+-	defer f.Close()
+-
+-	tr := NewReader(f)
+-
+-	headers := test.headers
+-	cksums := test.cksums
+-	nread := 0
+-
+-	// loop over all files
+-	for ; ; nread++ {
+-		hdr, err := tr.Next()
+-		if hdr == nil || err == io.EOF {
+-			break
+-		}
+-
+-		// check the header
+-		if !reflect.DeepEqual(*hdr, *headers[nread]) {
+-			t.Errorf("Incorrect header:\nhave %+v\nwant %+v",
+-				*hdr, headers[nread])
+-		}
+-
+-		// read and checksum the file data
+-		h := md5.New()
+-		_, err = io.Copy(h, tr)
+-		if err != nil {
+-			t.Fatalf("Unexpected error: %v", err)
+-		}
+-
+-		// verify checksum
+-		have := fmt.Sprintf("%x", h.Sum(nil))
+-		want := cksums[nread]
+-		if want != have {
+-			t.Errorf("Bad checksum on file %s:\nhave %+v\nwant %+v", hdr.Name, have, want)
+-		}
+-	}
+-	if nread != len(headers) {
+-		t.Errorf("Didn't process all files\nexpected: %d\nprocessed %d\n", len(headers), nread)
+-	}
+-}
+-
+-type sparseFileReadTest struct {
+-	sparseData []byte
+-	sparseMap  []sparseEntry
+-	realSize   int64
+-	expected   []byte
+-}
+-
+-var sparseFileReadTests = []sparseFileReadTest{
+-	{
+-		sparseData: []byte("abcde"),
+-		sparseMap: []sparseEntry{
+-			{offset: 0, numBytes: 2},
+-			{offset: 5, numBytes: 3},
+-		},
+-		realSize: 8,
+-		expected: []byte("ab\x00\x00\x00cde"),
+-	},
+-	{
+-		sparseData: []byte("abcde"),
+-		sparseMap: []sparseEntry{
+-			{offset: 0, numBytes: 2},
+-			{offset: 5, numBytes: 3},
+-		},
+-		realSize: 10,
+-		expected: []byte("ab\x00\x00\x00cde\x00\x00"),
+-	},
+-	{
+-		sparseData: []byte("abcde"),
+-		sparseMap: []sparseEntry{
+-			{offset: 1, numBytes: 3},
+-			{offset: 6, numBytes: 2},
+-		},
+-		realSize: 8,
+-		expected: []byte("\x00abc\x00\x00de"),
+-	},
+-	{
+-		sparseData: []byte("abcde"),
+-		sparseMap: []sparseEntry{
+-			{offset: 1, numBytes: 3},
+-			{offset: 6, numBytes: 2},
+-		},
+-		realSize: 10,
+-		expected: []byte("\x00abc\x00\x00de\x00\x00"),
+-	},
+-	{
+-		sparseData: []byte(""),
+-		sparseMap:  nil,
+-		realSize:   2,
+-		expected:   []byte("\x00\x00"),
+-	},
+-}
+-
+-func TestSparseFileReader(t *testing.T) {
+-	for i, test := range sparseFileReadTests {
+-		r := bytes.NewReader(test.sparseData)
+-		nb := int64(r.Len())
+-		sfr := &sparseFileReader{
+-			rfr: &regFileReader{r: r, nb: nb},
+-			sp:  test.sparseMap,
+-			pos: 0,
+-			tot: test.realSize,
+-		}
+-		if sfr.numBytes() != nb {
+-			t.Errorf("test %d: Before reading, sfr.numBytes() = %d, want %d", i, sfr.numBytes(), nb)
+-		}
+-		buf, err := ioutil.ReadAll(sfr)
+-		if err != nil {
+-			t.Errorf("test %d: Unexpected error: %v", i, err)
+-		}
+-		if e := test.expected; !bytes.Equal(buf, e) {
+-			t.Errorf("test %d: Contents = %v, want %v", i, buf, e)
+-		}
+-		if sfr.numBytes() != 0 {
+-			t.Errorf("test %d: After draining the reader, numBytes() was nonzero", i)
+-		}
+-	}
+-}
+-
+-func TestSparseIncrementalRead(t *testing.T) {
+-	sparseMap := []sparseEntry{{10, 2}}
+-	sparseData := []byte("Go")
+-	expected := "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00Go\x00\x00\x00\x00\x00\x00\x00\x00"
+-
+-	r := bytes.NewReader(sparseData)
+-	nb := int64(r.Len())
+-	sfr := &sparseFileReader{
+-		rfr: &regFileReader{r: r, nb: nb},
+-		sp:  sparseMap,
+-		pos: 0,
+-		tot: int64(len(expected)),
+-	}
+-
+-	// We'll read the data 6 bytes at a time, with a hole of size 10 at
+-	// the beginning and one of size 8 at the end.
+-	var outputBuf bytes.Buffer
+-	buf := make([]byte, 6)
+-	for {
+-		n, err := sfr.Read(buf)
+-		if err == io.EOF {
+-			break
+-		}
+-		if err != nil {
+-			t.Errorf("Read: unexpected error %v\n", err)
+-		}
+-		if n > 0 {
+-			_, err := outputBuf.Write(buf[:n])
+-			if err != nil {
+-				t.Errorf("Write: unexpected error %v\n", err)
+-			}
+-		}
+-	}
+-	got := outputBuf.String()
+-	if got != expected {
+-		t.Errorf("Contents = %v, want %v", got, expected)
+-	}
+-}
+-
+-func TestReadGNUSparseMap0x1(t *testing.T) {
+-	headers := map[string]string{
+-		paxGNUSparseNumBlocks: "4",
+-		paxGNUSparseMap:       "0,5,10,5,20,5,30,5",
+-	}
+-	expected := []sparseEntry{
+-		{offset: 0, numBytes: 5},
+-		{offset: 10, numBytes: 5},
+-		{offset: 20, numBytes: 5},
+-		{offset: 30, numBytes: 5},
+-	}
+-
+-	sp, err := readGNUSparseMap0x1(headers)
+-	if err != nil {
+-		t.Errorf("Unexpected error: %v", err)
+-	}
+-	if !reflect.DeepEqual(sp, expected) {
+-		t.Errorf("Incorrect sparse map: got %v, wanted %v", sp, expected)
+-	}
+-}
+-
+-func TestReadGNUSparseMap1x0(t *testing.T) {
+-	// This test uses lots of holes so the sparse header takes up more than two blocks
+-	numEntries := 100
+-	expected := make([]sparseEntry, 0, numEntries)
+-	sparseMap := new(bytes.Buffer)
+-
+-	fmt.Fprintf(sparseMap, "%d\n", numEntries)
+-	for i := 0; i < numEntries; i++ {
+-		offset := int64(2048 * i)
+-		numBytes := int64(1024)
+-		expected = append(expected, sparseEntry{offset: offset, numBytes: numBytes})
+-		fmt.Fprintf(sparseMap, "%d\n%d\n", offset, numBytes)
+-	}
+-
+-	// Make the header the smallest multiple of blockSize that fits the sparseMap
+-	headerBlocks := (sparseMap.Len() + blockSize - 1) / blockSize
+-	bufLen := blockSize * headerBlocks
+-	buf := make([]byte, bufLen)
+-	copy(buf, sparseMap.Bytes())
+-
+-	// Get an reader to read the sparse map
+-	r := bytes.NewReader(buf)
+-
+-	// Read the sparse map
+-	sp, err := readGNUSparseMap1x0(r)
+-	if err != nil {
+-		t.Errorf("Unexpected error: %v", err)
+-	}
+-	if !reflect.DeepEqual(sp, expected) {
+-		t.Errorf("Incorrect sparse map: got %v, wanted %v", sp, expected)
+-	}
+-}
+-
+-func TestUninitializedRead(t *testing.T) {
+-	test := gnuTarTest
+-	f, err := os.Open(test.file)
+-	if err != nil {
+-		t.Fatalf("Unexpected error: %v", err)
+-	}
+-	defer f.Close()
+-
+-	tr := NewReader(f)
+-	_, err = tr.Read([]byte{})
+-	if err == nil || err != io.EOF {
+-		t.Errorf("Unexpected error: %v, wanted %v", err, io.EOF)
+-	}
+-
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/stat_atim.go b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/stat_atim.go
+deleted file mode 100644
+index cf9cc79..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/stat_atim.go
++++ /dev/null
+@@ -1,20 +0,0 @@
+-// Copyright 2012 The Go Authors. All rights reserved.
+-// Use of this source code is governed by a BSD-style
+-// license that can be found in the LICENSE file.
+-
+-// +build linux dragonfly openbsd solaris
+-
+-package tar
+-
+-import (
+-	"syscall"
+-	"time"
+-)
+-
+-func statAtime(st *syscall.Stat_t) time.Time {
+-	return time.Unix(st.Atim.Unix())
+-}
+-
+-func statCtime(st *syscall.Stat_t) time.Time {
+-	return time.Unix(st.Ctim.Unix())
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/stat_atimespec.go b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/stat_atimespec.go
+deleted file mode 100644
+index 6f17dbe..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/stat_atimespec.go
++++ /dev/null
+@@ -1,20 +0,0 @@
+-// Copyright 2012 The Go Authors. All rights reserved.
+-// Use of this source code is governed by a BSD-style
+-// license that can be found in the LICENSE file.
+-
+-// +build darwin freebsd netbsd
+-
+-package tar
+-
+-import (
+-	"syscall"
+-	"time"
+-)
+-
+-func statAtime(st *syscall.Stat_t) time.Time {
+-	return time.Unix(st.Atimespec.Unix())
+-}
+-
+-func statCtime(st *syscall.Stat_t) time.Time {
+-	return time.Unix(st.Ctimespec.Unix())
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/stat_unix.go b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/stat_unix.go
+deleted file mode 100644
+index cb843db..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/stat_unix.go
++++ /dev/null
+@@ -1,32 +0,0 @@
+-// Copyright 2012 The Go Authors. All rights reserved.
+-// Use of this source code is governed by a BSD-style
+-// license that can be found in the LICENSE file.
+-
+-// +build linux darwin dragonfly freebsd openbsd netbsd solaris
+-
+-package tar
+-
+-import (
+-	"os"
+-	"syscall"
+-)
+-
+-func init() {
+-	sysStat = statUnix
+-}
+-
+-func statUnix(fi os.FileInfo, h *Header) error {
+-	sys, ok := fi.Sys().(*syscall.Stat_t)
+-	if !ok {
+-		return nil
+-	}
+-	h.Uid = int(sys.Uid)
+-	h.Gid = int(sys.Gid)
+-	// TODO(bradfitz): populate username & group.  os/user
+-	// doesn't cache LookupId lookups, and lacks group
+-	// lookup functions.
+-	h.AccessTime = statAtime(sys)
+-	h.ChangeTime = statCtime(sys)
+-	// TODO(bradfitz): major/minor device numbers?
+-	return nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/tar_test.go b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/tar_test.go
+deleted file mode 100644
+index ed333f3..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/tar_test.go
++++ /dev/null
+@@ -1,284 +0,0 @@
+-// Copyright 2012 The Go 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 tar
+-
+-import (
+-	"bytes"
+-	"io/ioutil"
+-	"os"
+-	"path"
+-	"reflect"
+-	"strings"
+-	"testing"
+-	"time"
+-)
+-
+-func TestFileInfoHeader(t *testing.T) {
+-	fi, err := os.Stat("testdata/small.txt")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	h, err := FileInfoHeader(fi, "")
+-	if err != nil {
+-		t.Fatalf("FileInfoHeader: %v", err)
+-	}
+-	if g, e := h.Name, "small.txt"; g != e {
+-		t.Errorf("Name = %q; want %q", g, e)
+-	}
+-	if g, e := h.Mode, int64(fi.Mode().Perm())|c_ISREG; g != e {
+-		t.Errorf("Mode = %#o; want %#o", g, e)
+-	}
+-	if g, e := h.Size, int64(5); g != e {
+-		t.Errorf("Size = %v; want %v", g, e)
+-	}
+-	if g, e := h.ModTime, fi.ModTime(); !g.Equal(e) {
+-		t.Errorf("ModTime = %v; want %v", g, e)
+-	}
+-	// FileInfoHeader should error when passing nil FileInfo
+-	if _, err := FileInfoHeader(nil, ""); err == nil {
+-		t.Fatalf("Expected error when passing nil to FileInfoHeader")
+-	}
+-}
+-
+-func TestFileInfoHeaderDir(t *testing.T) {
+-	fi, err := os.Stat("testdata")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	h, err := FileInfoHeader(fi, "")
+-	if err != nil {
+-		t.Fatalf("FileInfoHeader: %v", err)
+-	}
+-	if g, e := h.Name, "testdata/"; g != e {
+-		t.Errorf("Name = %q; want %q", g, e)
+-	}
+-	// Ignoring c_ISGID for golang.org/issue/4867
+-	if g, e := h.Mode&^c_ISGID, int64(fi.Mode().Perm())|c_ISDIR; g != e {
+-		t.Errorf("Mode = %#o; want %#o", g, e)
+-	}
+-	if g, e := h.Size, int64(0); g != e {
+-		t.Errorf("Size = %v; want %v", g, e)
+-	}
+-	if g, e := h.ModTime, fi.ModTime(); !g.Equal(e) {
+-		t.Errorf("ModTime = %v; want %v", g, e)
+-	}
+-}
+-
+-func TestFileInfoHeaderSymlink(t *testing.T) {
+-	h, err := FileInfoHeader(symlink{}, "some-target")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if g, e := h.Name, "some-symlink"; g != e {
+-		t.Errorf("Name = %q; want %q", g, e)
+-	}
+-	if g, e := h.Linkname, "some-target"; g != e {
+-		t.Errorf("Linkname = %q; want %q", g, e)
+-	}
+-}
+-
+-type symlink struct{}
+-
+-func (symlink) Name() string       { return "some-symlink" }
+-func (symlink) Size() int64        { return 0 }
+-func (symlink) Mode() os.FileMode  { return os.ModeSymlink }
+-func (symlink) ModTime() time.Time { return time.Time{} }
+-func (symlink) IsDir() bool        { return false }
+-func (symlink) Sys() interface{}   { return nil }
+-
+-func TestRoundTrip(t *testing.T) {
+-	data := []byte("some file contents")
+-
+-	var b bytes.Buffer
+-	tw := NewWriter(&b)
+-	hdr := &Header{
+-		Name:    "file.txt",
+-		Uid:     1 << 21, // too big for 8 octal digits
+-		Size:    int64(len(data)),
+-		ModTime: time.Now(),
+-	}
+-	// tar only supports second precision.
+-	hdr.ModTime = hdr.ModTime.Add(-time.Duration(hdr.ModTime.Nanosecond()) * time.Nanosecond)
+-	if err := tw.WriteHeader(hdr); err != nil {
+-		t.Fatalf("tw.WriteHeader: %v", err)
+-	}
+-	if _, err := tw.Write(data); err != nil {
+-		t.Fatalf("tw.Write: %v", err)
+-	}
+-	if err := tw.Close(); err != nil {
+-		t.Fatalf("tw.Close: %v", err)
+-	}
+-
+-	// Read it back.
+-	tr := NewReader(&b)
+-	rHdr, err := tr.Next()
+-	if err != nil {
+-		t.Fatalf("tr.Next: %v", err)
+-	}
+-	if !reflect.DeepEqual(rHdr, hdr) {
+-		t.Errorf("Header mismatch.\n got %+v\nwant %+v", rHdr, hdr)
+-	}
+-	rData, err := ioutil.ReadAll(tr)
+-	if err != nil {
+-		t.Fatalf("Read: %v", err)
+-	}
+-	if !bytes.Equal(rData, data) {
+-		t.Errorf("Data mismatch.\n got %q\nwant %q", rData, data)
+-	}
+-}
+-
+-type headerRoundTripTest struct {
+-	h  *Header
+-	fm os.FileMode
+-}
+-
+-func TestHeaderRoundTrip(t *testing.T) {
+-	golden := []headerRoundTripTest{
+-		// regular file.
+-		{
+-			h: &Header{
+-				Name:     "test.txt",
+-				Mode:     0644 | c_ISREG,
+-				Size:     12,
+-				ModTime:  time.Unix(1360600916, 0),
+-				Typeflag: TypeReg,
+-			},
+-			fm: 0644,
+-		},
+-		// hard link.
+-		{
+-			h: &Header{
+-				Name:     "hard.txt",
+-				Mode:     0644 | c_ISLNK,
+-				Size:     0,
+-				ModTime:  time.Unix(1360600916, 0),
+-				Typeflag: TypeLink,
+-			},
+-			fm: 0644 | os.ModeSymlink,
+-		},
+-		// symbolic link.
+-		{
+-			h: &Header{
+-				Name:     "link.txt",
+-				Mode:     0777 | c_ISLNK,
+-				Size:     0,
+-				ModTime:  time.Unix(1360600852, 0),
+-				Typeflag: TypeSymlink,
+-			},
+-			fm: 0777 | os.ModeSymlink,
+-		},
+-		// character device node.
+-		{
+-			h: &Header{
+-				Name:     "dev/null",
+-				Mode:     0666 | c_ISCHR,
+-				Size:     0,
+-				ModTime:  time.Unix(1360578951, 0),
+-				Typeflag: TypeChar,
+-			},
+-			fm: 0666 | os.ModeDevice | os.ModeCharDevice,
+-		},
+-		// block device node.
+-		{
+-			h: &Header{
+-				Name:     "dev/sda",
+-				Mode:     0660 | c_ISBLK,
+-				Size:     0,
+-				ModTime:  time.Unix(1360578954, 0),
+-				Typeflag: TypeBlock,
+-			},
+-			fm: 0660 | os.ModeDevice,
+-		},
+-		// directory.
+-		{
+-			h: &Header{
+-				Name:     "dir/",
+-				Mode:     0755 | c_ISDIR,
+-				Size:     0,
+-				ModTime:  time.Unix(1360601116, 0),
+-				Typeflag: TypeDir,
+-			},
+-			fm: 0755 | os.ModeDir,
+-		},
+-		// fifo node.
+-		{
+-			h: &Header{
+-				Name:     "dev/initctl",
+-				Mode:     0600 | c_ISFIFO,
+-				Size:     0,
+-				ModTime:  time.Unix(1360578949, 0),
+-				Typeflag: TypeFifo,
+-			},
+-			fm: 0600 | os.ModeNamedPipe,
+-		},
+-		// setuid.
+-		{
+-			h: &Header{
+-				Name:     "bin/su",
+-				Mode:     0755 | c_ISREG | c_ISUID,
+-				Size:     23232,
+-				ModTime:  time.Unix(1355405093, 0),
+-				Typeflag: TypeReg,
+-			},
+-			fm: 0755 | os.ModeSetuid,
+-		},
+-		// setguid.
+-		{
+-			h: &Header{
+-				Name:     "group.txt",
+-				Mode:     0750 | c_ISREG | c_ISGID,
+-				Size:     0,
+-				ModTime:  time.Unix(1360602346, 0),
+-				Typeflag: TypeReg,
+-			},
+-			fm: 0750 | os.ModeSetgid,
+-		},
+-		// sticky.
+-		{
+-			h: &Header{
+-				Name:     "sticky.txt",
+-				Mode:     0600 | c_ISREG | c_ISVTX,
+-				Size:     7,
+-				ModTime:  time.Unix(1360602540, 0),
+-				Typeflag: TypeReg,
+-			},
+-			fm: 0600 | os.ModeSticky,
+-		},
+-	}
+-
+-	for i, g := range golden {
+-		fi := g.h.FileInfo()
+-		h2, err := FileInfoHeader(fi, "")
+-		if err != nil {
+-			t.Error(err)
+-			continue
+-		}
+-		if strings.Contains(fi.Name(), "/") {
+-			t.Errorf("FileInfo of %q contains slash: %q", g.h.Name, fi.Name())
+-		}
+-		name := path.Base(g.h.Name)
+-		if fi.IsDir() {
+-			name += "/"
+-		}
+-		if got, want := h2.Name, name; got != want {
+-			t.Errorf("i=%d: Name: got %v, want %v", i, got, want)
+-		}
+-		if got, want := h2.Size, g.h.Size; got != want {
+-			t.Errorf("i=%d: Size: got %v, want %v", i, got, want)
+-		}
+-		if got, want := h2.Mode, g.h.Mode; got != want {
+-			t.Errorf("i=%d: Mode: got %o, want %o", i, got, want)
+-		}
+-		if got, want := fi.Mode(), g.fm; got != want {
+-			t.Errorf("i=%d: fi.Mode: got %o, want %o", i, got, want)
+-		}
+-		if got, want := h2.ModTime, g.h.ModTime; got != want {
+-			t.Errorf("i=%d: ModTime: got %v, want %v", i, got, want)
+-		}
+-		if sysh, ok := fi.Sys().(*Header); !ok || sysh != g.h {
+-			t.Errorf("i=%d: Sys didn't return original *Header", i)
+-		}
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/gnu.tar b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/gnu.tar
+deleted file mode 100644
+index fc899dc8dc2ad9952f5c5f67a0c76ca2d87249e9..0000000000000000000000000000000000000000
+GIT binary patch
+literal 0
+HcmV?d00001
+
+literal 3072
+zcmeHH%L>9U5Ztq0(Jv at FdDKtv;8zq|ijXv5BIw^6DOh^2UK)_HbK1>@VQ0c5`qsHR
+zJrb1zXEcV16&lMRW}rdtKd=NSXg->JkvP|Esp4`g&CK_h+FMmo7oR?iU7RP&svn2t
+z!9Ke4)upeR_aRYKtT+(g`B!B>fS>t?p7IZ9V9LKWlK+)w+iY|SVQ_tY3I4Ddrx1w)
+M;($0H4*b6ZFWOBnBLDyZ
+
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/nil-uid.tar b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/nil-uid.tar
+deleted file mode 100644
+index cc9cfaa33cc5de0a28b4183c1705d801f788c96a..0000000000000000000000000000000000000000
+GIT binary patch
+literal 0
+HcmV?d00001
+
+literal 1024
+zcmWGAG%z(VGPcn33UJrU$xmmX0WbgpGcywmlR at HOU}(l*Xk=(?U}j`)Zf3?{U<jnm
+z859gKbkIPcw74X(NI`)iwK6p=6OZ|X<nd at 7C@FB5ni!ZE85p31FS2_~Omu)Kz(3qI
+O$lniHVw621LI421e;KL(
+
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/pax.tar b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/pax.tar
+deleted file mode 100644
+index 9bc24b6587d726c7fca4e533d9c61a3801a34688..0000000000000000000000000000000000000000
+GIT binary patch
+literal 0
+HcmV?d00001
+
+literal 10240
+zcmeH~&u-H|5XOD(Q}_vz`9HIV-Z}CL1|qeBRwxNlAD?kbq{vMJQj94uds*3I at 2-Ed
+zpXb|Q{eF0Qw;4Wdw!4)@_!@~t&7&b8A|a!oqM>78BOoLqCLtvwr=Z5b$i&RT%Er#Y
+zO+ZjcSVUAHn~8MUp(~vBV+cg7LjpEKCCE6D7<T<rw?O;0+Yj4Z(zR0^zGPhdbGvr9
+zrQRoy{_C*6yB&T*;!Rvanu2Cxl~q*L)HSpj7#bOyn3|beSaWc6a&~cbbNBET5Ev93
+z5*ijB5v at VXo!D}hwH&DBLoGKe+%WVH`}>E at EwTcMv_>l+&bbg`j1Cv0A776ym5t at +
+zSt9MDBFtXbKY&m4pMN0f`l~hhD>#q(-`x$5n+q at eEPmAevA;0XTM8XMYkTvSmQ-t5
+zkihVw{(qQ#_JjT})&KMa&-FhG0c8or{CPvw|Jf69W<Ub#zuZ55K6rrnt=}JY0A at _E
+zN^3xAA4n$-;7s(y0ZgN3(ESs)hV}e<pMn|npKk8d_aDyzKdR+K|CC3Dtp9n`nENR5
+zazFm(^?#bHx-J4mpa>L!B2Wa1KoKYcMW6^2fg(@@ia-%40!5$*6oDd81d2cr_`3;w
+E2V3|JA^-pY
+
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/small.txt b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/small.txt
+deleted file mode 100644
+index b249bfc..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/small.txt
++++ /dev/null
+@@ -1 +0,0 @@
+-Kilts
+\ No newline at end of file
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/small2.txt b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/small2.txt
+deleted file mode 100644
+index 394ee3e..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/small2.txt
++++ /dev/null
+@@ -1 +0,0 @@
+-Google.com
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/sparse-formats.tar b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/sparse-formats.tar
+deleted file mode 100644
+index 8bd4e74d50f9c8961f80a887ab7d6449e032048b..0000000000000000000000000000000000000000
+GIT binary patch
+literal 0
+HcmV?d00001
+
+literal 17920
+zcmeHO!BXQ!5M{6a3g^xmb&sU64qQV{sZ?#{1DvdPiv%!*Aw}}_dEEjdi|Nre#)hpG
+zE{}(KnjXC;wbY|&t*;k1>*dF<S9eEy`z!EQm*o+DC{{)HSD=DIJR;^8%aUWjb{s-g
+zA5A~)ZI3#J at 7A}Ao9XoE^WvZL&z<&ubqMco|IPoa1g#FD%)=jb>Y-EbwpT`b+-m>u
+zXfjaoe5W44g1VMFbuvaLV|3acePf?HHj7T34f|}^XTyHz*zDR5hW%jJ$GN!K=dPX7
+zuwNSXOT&I?*sl!xm0`a!>{o{UdfWbohf`t0wKm47jd5yYoVY#C#(p&HN5g(h+o$d^
+z>C~x6+ovLJp9;gi;Rj^+0U3Tkh98jO2W0pG8Gb;9ACTb()boS>@h8I{<l4MBhF!f4
+ze;~sj$nXa;{DBOAAj2QX at CP#dfqMS%$dL>`Aj1#H at B=dZfDAvtjWMmW;RoC~7Py0M
+z`m*5%-1CF}@n^#y*zgB7{DBRBV8b8S at CP>hfen8^_^{DnOAo^z5MmhHr;h_0e!zww
+zu;B-6_yHS!z=j{N;RkH^0r&ji+3`30fen9P!ynl22R8fx0blw!^!(v@<TAFrh5~1+
+zeSUs=ja?jV>`{T)$#0AMUzUr{%bWEKK}dPBZfAtotM&Q)$6}V4GkAAL?ydIxj}Q`3
+zJOATY>UD~$8khO$y?3COY_Ib_T!Mz?cSHC~#(oEVI84ue{e9LR^x69SzvU?x#e`$G
+z`ReZSkBilxf3HuQYO>v9_2tWYd3#C|uKGRxy<M&a*c#zs`{3Lj!@BH8=k`rz`?5>y
+zk#CN0vO|t>vO|t?vO|t at vV)g2dr7mGG<!+2mo$4x2QTU1B^|t^gO_yhk}kcZOE2lt
+zOS<%uF1 at 5HFX_rly7H2)yre5H>Do)W_L8o>q-!tf+DkfmNk=c~=p`M!q@$Pg+)H}y
+zB|Z0&o_k5py`&p2>BdW1A|f+1N!@lEFX<*ndTZ#%;H1d0PWQ;sPWQ<1PWQ+WPxo*$
+zCpU9)GbcB5ax*74^K5XIR5u%)rF*!UXXCT<7;fg-2rW5AHbhJJa5K*aY3VWC%(G!y
+za*S-8mhRzZo{iMfW4M`TW3}WM*<dZ*!_7P!uBFFtGtUNW$uY7KTe^pvc{XNCkKtyX
+zjoOl9WW%;}4>$8{;Fcc4%{&{rCCA9dZs{Iw=Go{iJw}H4J9rlMBkscMKka?4V*dGW
+zC;x{dmiMq8gvD(vpG{xk(ev}2>9_pg&wuy1`g67#*MIt_+k5+eaQ%mN-{S%QM+!~(
+zxc)<2*YN+U4#l|sv%B)c7PePszGeL<)ZO)vtHtH=w09GsNfox9d|WQBPwAMB1HKi$
+z5#I)1l17qNl4g>25`gi0%mT0gEC34-1PB5I0fGQQfKq@`fKq@`fKq@;fJ%T$fJ%T$
+zfLefBfLefBfLeekKolSf5Cw<=%mtVWFc)Ahz+8YvfJT5ufJT5u0A#CaDG)Nzv=opE
+zMO*%@0IdS81gZg+MP*A>0a;*L*S;zQ^1P%)r9keM))iGXNaa8-mb9xN$g|SAj;op=
+zlS*1t6=X?iT~QSVc~H`#(jdo4>x!y6$YPQf)rV9dQiVt*BGrggBvO?~WSR`0jpG)F
+zR$z95<=;=b<p1;e#WI-!u<I>g;QIfR|BZ{k=7%FW59w-S{C9wpVT}I{Ao4pNVj%vb
+z{pbH+{)aiAzW>2BZdt7HACK|hLCzZHZZvnf_-l0|IXl~}=T~SgCPR at QPL^Kc(9Lpj
+zv56 at U!e<=Br at -+2fA>qk!2KVo<PYzEab4ggF!(?2|8czk`;O$xw#M=`;S=zcTEw@(
+z7wf3_NGn!5QAj)1BynZHFH-uX5CH3YC<MSN90~!D&xAq%<Q>rji&Q8CK+X>e0g#)6
+z at dUuK3<?3Tc!ELzEODR^0J$S51VD}l_D%pi)JGuz9=)Rw01wDf2!I>}6apYu09*vX
+znm!5vu=b8Z0L;v^6bQklmI7jCCS}XN6`)n1l|VJX%uKdX6)-c?y7pBeFf)@Dl>##}
+ztt+Z(U}h#Qst0CfT31vh!CNoVqM~4CrgcSC7r2GAs4|$DX<bnj2XCB6i^_wUnbs9m
+zg)lRd7S#wdGp#GCGQI5F8GC*I3XJjp_kRp`VX(Z)z4W|`<)^*__kX|-&wtA at MtM&O
+o7i7H7b-?-m^bOzte$weJYB>JmbGf$=ejIaDU{qjK;EfgdABYgg9smFU
+
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/star.tar b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/star.tar
+deleted file mode 100644
+index 59e2d4e604611eeac3e2a0f3d6f71d2623c50449..0000000000000000000000000000000000000000
+GIT binary patch
+literal 0
+HcmV?d00001
+
+literal 3072
+zcmeHHT?)e>4DRzz;R#BjQ;)ERouag*479>@u-$$NbG3!-WyoMlUh?xvNIv}HZD&jy
+zuA!-C5KZlY0Y at bP833Zfm_JQ2M2<pg$x$a<X%X>yBQ2dTK6K{>VDLBV=D{z>IvVF`
+zUD#xgUGh?F1AikeIW6NnOIrMRGU4UU`62nAWxyx>^STEhN#m{lQEc_E<B1^sfB5T4
+f&6ja*oAiHhZZc!rJG;we^27i!KnxHAf55;UI$1)v
+
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/ustar.tar b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/ustar.tar
+deleted file mode 100644
+index 29679d9a305fc0293f31212541335af824ab32c7..0000000000000000000000000000000000000000
+GIT binary patch
+literal 0
+HcmV?d00001
+
+literal 2048
+zcmYex%t_TNsVHHfAus>}GZPaA5N&Q|3Z at N=AbgM*P?o{a$k4#V#K6eR)QrKv#MIE(
+zgh9c8hHiozU0Pg{SOj!ZaYkZZDqIwk0aTWjhA9jefq29K;yD8YhMfGo^t{B}RQ&;E
+gz at 3MSk&&8{lh1`qc2s;c1V%$(Gz3ONV7P_=0F<Om%m4rY
+
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/v7.tar b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/v7.tar
+deleted file mode 100644
+index eb65fc9410721efd98cb7c5e274f547ec530252d..0000000000000000000000000000000000000000
+GIT binary patch
+literal 0
+HcmV?d00001
+
+literal 3584
+zcmeHH&ubGw6n?3{z(^13q0owB at t_Dbv)OD<qP9W<=F*#Zu|<OsHb$B#MLfilBFeB(
+zSoNT!67<$TAs)OG!JCj{H}PP>Tf|dgec!sXT^AK{$jKc at -kWdUe(&uh-&e0L+xARj
+zwLzm>LI~3|1sT#R<fI at Wr6qG5qg7zYkom%FVb;hoYUM10#ONkUne`1^zGXM+dP9_X
+zf9{!k@}lkT-^GT?E=~8;_J-Sfc*0X(rakp_A<JKLSzr#wwI)%K`MZ;SC3bqMH1Ip|
+z1{<-><Eg%KV|%16{)~l~IM!EAm?y(W(^K-Ur`8VhORW=CxX-71o<d*Dpz-3wx&t1}
+zqB**~o+=Lf%pnHMS44X_c9{pYsHyN=;KOss!Fho3#oJp!j+%FT{yE&EUz{K3SbKkk
+z===U0_xa&>&XkBIzWbfCPrYEK7fr^Q at 7vXO;&pw$QCTT3-?&yO+jq(<{6qS`FS_vP
+zIBhMBjnmsnS~{|C9LMN8#r!W{zj5l&zcE?^U_t*||1zJ{zqInH{-Zy}2$O|c?WSFx
+zxn8RtM3-UpAJiW`Z at Zar#$ojz)NjtWBfnULUzD=jj5!>iG>O2k{o(=ZAg=$-urC7q
+zVm{n!{kK`S at p|Vk`q%aFg#nw)bMB-40yAj*%7=F37m at ziFINBH7pTSD@Cfil^^9T6
+zxL-iu+Aq)#ev#CF(l2&S at A^eC<`;^e4{ZQ#s9$Y4r}$iP3;;e3V;a&MNN*s$f%FFc
+H(;N5+1FUK9
+
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/writer-big-long.tar b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/writer-big-long.tar
+deleted file mode 100644
+index 5960ee824784ffeacb976a9c648be41b0281508b..0000000000000000000000000000000000000000
+GIT binary patch
+literal 0
+HcmV?d00001
+
+literal 4096
+zcmeIuJqp7x3<Y2fJ%~?`%0IEr;~|)U<3MUd#~!^lfo!2u=#cjYOIU- at r+u8`P~L^E
+z3%7XZs1+?EAN8}ZeDtD?wMK+T7Gmew2r1s@*S_^t!lo3(I;RxsGM%jZHSb5Z^y7Lc
+jtvTkfOwYeIC&%C$0uX=z1Rwwb2tWV=5P$##?k4aBT?$NV
+
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/writer-big.tar b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/writer-big.tar
+deleted file mode 100644
+index 753e883cebf52ac1291f1b7bf1b7a37ae517b2d9..0000000000000000000000000000000000000000
+GIT binary patch
+literal 0
+HcmV?d00001
+
+literal 4096
+zcmeIuF%E+;3<XdRJxET_`a8w<L86KnpjDGf?Z(j?V1^B*|A$1fEm?kLc-`QsPuKD-
+za!j<w?<#8WMj@(zLuFdmUFHukH;d4w&LP601YP^bzMov$cL>tu-|!r}ytVByrmfae
+ipO37m$1T~NWs?FFpa2CZKmiI+fC3bt00k&;vcMnFf)<_t
+
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/writer.tar b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/writer.tar
+deleted file mode 100644
+index e6d816ad0775d56d09242d6f5d1dbe56af310a32..0000000000000000000000000000000000000000
+GIT binary patch
+literal 0
+HcmV?d00001
+
+literal 3584
+zcmeHIK at P$o5ajGDd_l9j6nKIMUt!cVjT92WM1L<dt&JwF9!gRh_Cl9!$n3!ExaOdB
+z;qRWM3kV at gU_dAZAOk>@81h#LhDgML6Bon)c?rO_kPgyt^3D0fH9$GJM`O*&4VCw=
+zv#H)UKC-TtzNwGuV$*%C{b<jNMV*1o#ej?Yr?dkgN at G(0$fN$_Oh8U$tAC-g{^z>m
+zsdIMLR{C5VZL^vBE!S4cfUeCYt@>GOiAt%sq7tp|_iN{x5cDreh9ME=K+wOCQm`$x
+j!znSk-v6Dy)}|V_!f*AilYjI7l|Jj-R%ReG at B;%+QQ}au
+
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/xattrs.tar b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/testdata/xattrs.tar
+deleted file mode 100644
+index 9701950edd1f0dc82858b7117136b37391be0b08..0000000000000000000000000000000000000000
+GIT binary patch
+literal 0
+HcmV?d00001
+
+literal 5120
+zcmeHJv2KGf5M|~o_yWg1+khiw>d;i}P^nX=$R$ooYd`|ilD{uBAv6g^kxC>6-(uu<
+zHg^v_-l5r}td>fyRbC(vfcdOQq}Iq(#u+Ja9X?}Dv(|CCVoJF~09ZgF;2a!G7^%~|
+zYNYoMUQ-rE=5<MfNf&^--n!;4I5LG45ME;9L at fvneeClfz=*LBI8bnFP`025LJ)!=
+zMno8J0GDDfIs&<m0>KzzBJ^EKyr-Mx-NQ4gq%k=v3zee}wOxElT`HH-ei(K*xV|_}
+zC{$GDvDu<R={PN`MVUrfx`|V at UX}Cg<y}Q)mCx5|BTH>oW?o>&odUrVuVHkt_w?IH
+zW3PV_ at V!Jxt at A^i>Yrj(>;K=H?5X8!tJS~MYVd#a^`?|QJKb&Uduf~MfN4M7$J!Lr
+zF40zZMF!9x{tqJ#0F5+;{2!=)=Knre|G(mAKU`hAc#r>!#{V(9d;sW1hxVv7 at B_zF
+ze)#eKF~#1~>@WTI`#+&4`lkel_5U6!N8h^5vRAE8lqGgr9-Ul!p=H1_U>TS&1K)l2
+B)fNB%
+
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/writer.go b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/writer.go
+deleted file mode 100644
+index dafb2ca..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/writer.go
++++ /dev/null
+@@ -1,396 +0,0 @@
+-// Copyright 2009 The Go 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 tar
+-
+-// TODO(dsymonds):
+-// - catch more errors (no first header, etc.)
+-
+-import (
+-	"bytes"
+-	"errors"
+-	"fmt"
+-	"io"
+-	"os"
+-	"path"
+-	"strconv"
+-	"strings"
+-	"time"
+-)
+-
+-var (
+-	ErrWriteTooLong    = errors.New("archive/tar: write too long")
+-	ErrFieldTooLong    = errors.New("archive/tar: header field too long")
+-	ErrWriteAfterClose = errors.New("archive/tar: write after close")
+-	errNameTooLong     = errors.New("archive/tar: name too long")
+-	errInvalidHeader   = errors.New("archive/tar: header field too long or contains invalid values")
+-)
+-
+-// A Writer provides sequential writing of a tar archive in POSIX.1 format.
+-// A tar archive consists of a sequence of files.
+-// Call WriteHeader to begin a new file, and then call Write to supply that file's data,
+-// writing at most hdr.Size bytes in total.
+-type Writer struct {
+-	w          io.Writer
+-	err        error
+-	nb         int64 // number of unwritten bytes for current file entry
+-	pad        int64 // amount of padding to write after current file entry
+-	closed     bool
+-	usedBinary bool            // whether the binary numeric field extension was used
+-	preferPax  bool            // use pax header instead of binary numeric header
+-	hdrBuff    [blockSize]byte // buffer to use in writeHeader when writing a regular header
+-	paxHdrBuff [blockSize]byte // buffer to use in writeHeader when writing a pax header
+-}
+-
+-// NewWriter creates a new Writer writing to w.
+-func NewWriter(w io.Writer) *Writer { return &Writer{w: w} }
+-
+-// Flush finishes writing the current file (optional).
+-func (tw *Writer) Flush() error {
+-	if tw.nb > 0 {
+-		tw.err = fmt.Errorf("archive/tar: missed writing %d bytes", tw.nb)
+-		return tw.err
+-	}
+-
+-	n := tw.nb + tw.pad
+-	for n > 0 && tw.err == nil {
+-		nr := n
+-		if nr > blockSize {
+-			nr = blockSize
+-		}
+-		var nw int
+-		nw, tw.err = tw.w.Write(zeroBlock[0:nr])
+-		n -= int64(nw)
+-	}
+-	tw.nb = 0
+-	tw.pad = 0
+-	return tw.err
+-}
+-
+-// Write s into b, terminating it with a NUL if there is room.
+-// If the value is too long for the field and allowPax is true add a paxheader record instead
+-func (tw *Writer) cString(b []byte, s string, allowPax bool, paxKeyword string, paxHeaders map[string]string) {
+-	needsPaxHeader := allowPax && len(s) > len(b) || !isASCII(s)
+-	if needsPaxHeader {
+-		paxHeaders[paxKeyword] = s
+-		return
+-	}
+-	if len(s) > len(b) {
+-		if tw.err == nil {
+-			tw.err = ErrFieldTooLong
+-		}
+-		return
+-	}
+-	ascii := toASCII(s)
+-	copy(b, ascii)
+-	if len(ascii) < len(b) {
+-		b[len(ascii)] = 0
+-	}
+-}
+-
+-// Encode x as an octal ASCII string and write it into b with leading zeros.
+-func (tw *Writer) octal(b []byte, x int64) {
+-	s := strconv.FormatInt(x, 8)
+-	// leading zeros, but leave room for a NUL.
+-	for len(s)+1 < len(b) {
+-		s = "0" + s
+-	}
+-	tw.cString(b, s, false, paxNone, nil)
+-}
+-
+-// Write x into b, either as octal or as binary (GNUtar/star extension).
+-// If the value is too long for the field and writingPax is enabled both for the field and the add a paxheader record instead
+-func (tw *Writer) numeric(b []byte, x int64, allowPax bool, paxKeyword string, paxHeaders map[string]string) {
+-	// Try octal first.
+-	s := strconv.FormatInt(x, 8)
+-	if len(s) < len(b) {
+-		tw.octal(b, x)
+-		return
+-	}
+-
+-	// If it is too long for octal, and pax is preferred, use a pax header
+-	if allowPax && tw.preferPax {
+-		tw.octal(b, 0)
+-		s := strconv.FormatInt(x, 10)
+-		paxHeaders[paxKeyword] = s
+-		return
+-	}
+-
+-	// Too big: use binary (big-endian).
+-	tw.usedBinary = true
+-	for i := len(b) - 1; x > 0 && i >= 0; i-- {
+-		b[i] = byte(x)
+-		x >>= 8
+-	}
+-	b[0] |= 0x80 // highest bit indicates binary format
+-}
+-
+-var (
+-	minTime = time.Unix(0, 0)
+-	// There is room for 11 octal digits (33 bits) of mtime.
+-	maxTime = minTime.Add((1<<33 - 1) * time.Second)
+-)
+-
+-// WriteHeader writes hdr and prepares to accept the file's contents.
+-// WriteHeader calls Flush if it is not the first header.
+-// Calling after a Close will return ErrWriteAfterClose.
+-func (tw *Writer) WriteHeader(hdr *Header) error {
+-	return tw.writeHeader(hdr, true)
+-}
+-
+-// WriteHeader writes hdr and prepares to accept the file's contents.
+-// WriteHeader calls Flush if it is not the first header.
+-// Calling after a Close will return ErrWriteAfterClose.
+-// As this method is called internally by writePax header to allow it to
+-// suppress writing the pax header.
+-func (tw *Writer) writeHeader(hdr *Header, allowPax bool) error {
+-	if tw.closed {
+-		return ErrWriteAfterClose
+-	}
+-	if tw.err == nil {
+-		tw.Flush()
+-	}
+-	if tw.err != nil {
+-		return tw.err
+-	}
+-
+-	// a map to hold pax header records, if any are needed
+-	paxHeaders := make(map[string]string)
+-
+-	// TODO(shanemhansen): we might want to use PAX headers for
+-	// subsecond time resolution, but for now let's just capture
+-	// too long fields or non ascii characters
+-
+-	var header []byte
+-
+-	// We need to select which scratch buffer to use carefully,
+-	// since this method is called recursively to write PAX headers.
+-	// If allowPax is true, this is the non-recursive call, and we will use hdrBuff.
+-	// If allowPax is false, we are being called by writePAXHeader, and hdrBuff is
+-	// already being used by the non-recursive call, so we must use paxHdrBuff.
+-	header = tw.hdrBuff[:]
+-	if !allowPax {
+-		header = tw.paxHdrBuff[:]
+-	}
+-	copy(header, zeroBlock)
+-	s := slicer(header)
+-
+-	// keep a reference to the filename to allow to overwrite it later if we detect that we can use ustar longnames instead of pax
+-	pathHeaderBytes := s.next(fileNameSize)
+-
+-	tw.cString(pathHeaderBytes, hdr.Name, true, paxPath, paxHeaders)
+-
+-	// Handle out of range ModTime carefully.
+-	var modTime int64
+-	if !hdr.ModTime.Before(minTime) && !hdr.ModTime.After(maxTime) {
+-		modTime = hdr.ModTime.Unix()
+-	}
+-
+-	tw.octal(s.next(8), hdr.Mode)                                   // 100:108
+-	tw.numeric(s.next(8), int64(hdr.Uid), true, paxUid, paxHeaders) // 108:116
+-	tw.numeric(s.next(8), int64(hdr.Gid), true, paxGid, paxHeaders) // 116:124
+-	tw.numeric(s.next(12), hdr.Size, true, paxSize, paxHeaders)     // 124:136
+-	tw.numeric(s.next(12), modTime, false, paxNone, nil)            // 136:148 --- consider using pax for finer granularity
+-	s.next(8)                                                       // chksum (148:156)
+-	s.next(1)[0] = hdr.Typeflag                                     // 156:157
+-
+-	tw.cString(s.next(100), hdr.Linkname, true, paxLinkpath, paxHeaders)
+-
+-	copy(s.next(8), []byte("ustar\x0000"))                        // 257:265
+-	tw.cString(s.next(32), hdr.Uname, true, paxUname, paxHeaders) // 265:297
+-	tw.cString(s.next(32), hdr.Gname, true, paxGname, paxHeaders) // 297:329
+-	tw.numeric(s.next(8), hdr.Devmajor, false, paxNone, nil)      // 329:337
+-	tw.numeric(s.next(8), hdr.Devminor, false, paxNone, nil)      // 337:345
+-
+-	// keep a reference to the prefix to allow to overwrite it later if we detect that we can use ustar longnames instead of pax
+-	prefixHeaderBytes := s.next(155)
+-	tw.cString(prefixHeaderBytes, "", false, paxNone, nil) // 345:500  prefix
+-
+-	// Use the GNU magic instead of POSIX magic if we used any GNU extensions.
+-	if tw.usedBinary {
+-		copy(header[257:265], []byte("ustar  \x00"))
+-	}
+-
+-	_, paxPathUsed := paxHeaders[paxPath]
+-	// try to use a ustar header when only the name is too long
+-	if !tw.preferPax && len(paxHeaders) == 1 && paxPathUsed {
+-		suffix := hdr.Name
+-		prefix := ""
+-		if len(hdr.Name) > fileNameSize && isASCII(hdr.Name) {
+-			var err error
+-			prefix, suffix, err = tw.splitUSTARLongName(hdr.Name)
+-			if err == nil {
+-				// ok we can use a ustar long name instead of pax, now correct the fields
+-
+-				// remove the path field from the pax header. this will suppress the pax header
+-				delete(paxHeaders, paxPath)
+-
+-				// update the path fields
+-				tw.cString(pathHeaderBytes, suffix, false, paxNone, nil)
+-				tw.cString(prefixHeaderBytes, prefix, false, paxNone, nil)
+-
+-				// Use the ustar magic if we used ustar long names.
+-				if len(prefix) > 0 && !tw.usedBinary {
+-					copy(header[257:265], []byte("ustar\x00"))
+-				}
+-			}
+-		}
+-	}
+-
+-	// The chksum field is terminated by a NUL and a space.
+-	// This is different from the other octal fields.
+-	chksum, _ := checksum(header)
+-	tw.octal(header[148:155], chksum)
+-	header[155] = ' '
+-
+-	if tw.err != nil {
+-		// problem with header; probably integer too big for a field.
+-		return tw.err
+-	}
+-
+-	if allowPax {
+-		for k, v := range hdr.Xattrs {
+-			paxHeaders[paxXattr+k] = v
+-		}
+-	}
+-
+-	if len(paxHeaders) > 0 {
+-		if !allowPax {
+-			return errInvalidHeader
+-		}
+-		if err := tw.writePAXHeader(hdr, paxHeaders); err != nil {
+-			return err
+-		}
+-	}
+-	tw.nb = int64(hdr.Size)
+-	tw.pad = (blockSize - (tw.nb % blockSize)) % blockSize
+-
+-	_, tw.err = tw.w.Write(header)
+-	return tw.err
+-}
+-
+-// writeUSTARLongName splits a USTAR long name hdr.Name.
+-// name must be < 256 characters. errNameTooLong is returned
+-// if hdr.Name can't be split. The splitting heuristic
+-// is compatible with gnu tar.
+-func (tw *Writer) splitUSTARLongName(name string) (prefix, suffix string, err error) {
+-	length := len(name)
+-	if length > fileNamePrefixSize+1 {
+-		length = fileNamePrefixSize + 1
+-	} else if name[length-1] == '/' {
+-		length--
+-	}
+-	i := strings.LastIndex(name[:length], "/")
+-	// nlen contains the resulting length in the name field.
+-	// plen contains the resulting length in the prefix field.
+-	nlen := len(name) - i - 1
+-	plen := i
+-	if i <= 0 || nlen > fileNameSize || nlen == 0 || plen > fileNamePrefixSize {
+-		err = errNameTooLong
+-		return
+-	}
+-	prefix, suffix = name[:i], name[i+1:]
+-	return
+-}
+-
+-// writePaxHeader writes an extended pax header to the
+-// archive.
+-func (tw *Writer) writePAXHeader(hdr *Header, paxHeaders map[string]string) error {
+-	// Prepare extended header
+-	ext := new(Header)
+-	ext.Typeflag = TypeXHeader
+-	// Setting ModTime is required for reader parsing to
+-	// succeed, and seems harmless enough.
+-	ext.ModTime = hdr.ModTime
+-	// The spec asks that we namespace our pseudo files
+-	// with the current pid.
+-	pid := os.Getpid()
+-	dir, file := path.Split(hdr.Name)
+-	fullName := path.Join(dir,
+-		fmt.Sprintf("PaxHeaders.%d", pid), file)
+-
+-	ascii := toASCII(fullName)
+-	if len(ascii) > 100 {
+-		ascii = ascii[:100]
+-	}
+-	ext.Name = ascii
+-	// Construct the body
+-	var buf bytes.Buffer
+-
+-	for k, v := range paxHeaders {
+-		fmt.Fprint(&buf, paxHeader(k+"="+v))
+-	}
+-
+-	ext.Size = int64(len(buf.Bytes()))
+-	if err := tw.writeHeader(ext, false); err != nil {
+-		return err
+-	}
+-	if _, err := tw.Write(buf.Bytes()); err != nil {
+-		return err
+-	}
+-	if err := tw.Flush(); err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-// paxHeader formats a single pax record, prefixing it with the appropriate length
+-func paxHeader(msg string) string {
+-	const padding = 2 // Extra padding for space and newline
+-	size := len(msg) + padding
+-	size += len(strconv.Itoa(size))
+-	record := fmt.Sprintf("%d %s\n", size, msg)
+-	if len(record) != size {
+-		// Final adjustment if adding size increased
+-		// the number of digits in size
+-		size = len(record)
+-		record = fmt.Sprintf("%d %s\n", size, msg)
+-	}
+-	return record
+-}
+-
+-// Write writes to the current entry in the tar archive.
+-// Write returns the error ErrWriteTooLong if more than
+-// hdr.Size bytes are written after WriteHeader.
+-func (tw *Writer) Write(b []byte) (n int, err error) {
+-	if tw.closed {
+-		err = ErrWriteTooLong
+-		return
+-	}
+-	overwrite := false
+-	if int64(len(b)) > tw.nb {
+-		b = b[0:tw.nb]
+-		overwrite = true
+-	}
+-	n, err = tw.w.Write(b)
+-	tw.nb -= int64(n)
+-	if err == nil && overwrite {
+-		err = ErrWriteTooLong
+-		return
+-	}
+-	tw.err = err
+-	return
+-}
+-
+-// Close closes the tar archive, flushing any unwritten
+-// data to the underlying writer.
+-func (tw *Writer) Close() error {
+-	if tw.err != nil || tw.closed {
+-		return tw.err
+-	}
+-	tw.Flush()
+-	tw.closed = true
+-	if tw.err != nil {
+-		return tw.err
+-	}
+-
+-	// trailer: two zero blocks
+-	for i := 0; i < 2; i++ {
+-		_, tw.err = tw.w.Write(zeroBlock)
+-		if tw.err != nil {
+-			break
+-		}
+-	}
+-	return tw.err
+-}
+diff --git a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/writer_test.go b/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/writer_test.go
+deleted file mode 100644
+index 5e42e32..0000000
+--- a/Godeps/_workspace/src/github.com/docker/docker/vendor/src/code.google.com/p/go/src/pkg/archive/tar/writer_test.go
++++ /dev/null
+@@ -1,491 +0,0 @@
+-// Copyright 2009 The Go 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 tar
+-
+-import (
+-	"bytes"
+-	"fmt"
+-	"io"
+-	"io/ioutil"
+-	"os"
+-	"reflect"
+-	"strings"
+-	"testing"
+-	"testing/iotest"
+-	"time"
+-)
+-
+-type writerTestEntry struct {
+-	header   *Header
+-	contents string
+-}
+-
+-type writerTest struct {
+-	file    string // filename of expected output
+-	entries []*writerTestEntry
+-}
+-
+-var writerTests = []*writerTest{
+-	// The writer test file was produced with this command:
+-	// tar (GNU tar) 1.26
+-	//   ln -s small.txt link.txt
+-	//   tar -b 1 --format=ustar -c -f writer.tar small.txt small2.txt link.txt
+-	{
+-		file: "testdata/writer.tar",
+-		entries: []*writerTestEntry{
+-			{
+-				header: &Header{
+-					Name:     "small.txt",
+-					Mode:     0640,
+-					Uid:      73025,
+-					Gid:      5000,
+-					Size:     5,
+-					ModTime:  time.Unix(1246508266, 0),
+-					Typeflag: '0',
+-					Uname:    "dsymonds",
+-					Gname:    "eng",
+-				},
+-				contents: "Kilts",
+-			},
+-			{
+-				header: &Header{
+-					Name:     "small2.txt",
+-					Mode:     0640,
+-					Uid:      73025,
+-					Gid:      5000,
+-					Size:     11,
+-					ModTime:  time.Unix(1245217492, 0),
+-					Typeflag: '0',
+-					Uname:    "dsymonds",
+-					Gname:    "eng",
+-				},
+-				contents: "Google.com\n",
+-			},
+-			{
+-				header: &Header{
+-					Name:     "link.txt",
+-					Mode:     0777,
+-					Uid:      1000,
+-					Gid:      1000,
+-					Size:     0,
+-					ModTime:  time.Unix(1314603082, 0),
+-					Typeflag: '2',
+-					Linkname: "small.txt",
+-					Uname:    "strings",
+-					Gname:    "strings",
+-				},
+-				// no contents
+-			},
+-		},
+-	},
+-	// The truncated test file was produced using these commands:
+-	//   dd if=/dev/zero bs=1048576 count=16384 > /tmp/16gig.txt
+-	//   tar -b 1 -c -f- /tmp/16gig.txt | dd bs=512 count=8 > writer-big.tar
+-	{
+-		file: "testdata/writer-big.tar",
+-		entries: []*writerTestEntry{
+-			{
+-				header: &Header{
+-					Name:     "tmp/16gig.txt",
+-					Mode:     0640,
+-					Uid:      73025,
+-					Gid:      5000,
+-					Size:     16 << 30,
+-					ModTime:  time.Unix(1254699560, 0),
+-					Typeflag: '0',
+-					Uname:    "dsymonds",
+-					Gname:    "eng",
+-				},
+-				// fake contents
+-				contents: strings.Repeat("\x00", 4<<10),
+-			},
+-		},
+-	},
+-	// The truncated test file was produced using these commands:
+-	//   dd if=/dev/zero bs=1048576 count=16384 > (longname/)*15 /16gig.txt
+-	//   tar -b 1 -c -f- (longname/)*15 /16gig.txt | dd bs=512 count=8 > writer-big-long.tar
+-	{
+-		file: "testdata/writer-big-long.tar",
+-		entries: []*writerTestEntry{
+-			{
+-				header: &Header{
+-					Name:     strings.Repeat("longname/", 15) + "16gig.txt",
+-					Mode:     0644,
+-					Uid:      1000,
+-					Gid:      1000,
+-					Size:     16 << 30,
+-					ModTime:  time.Unix(1399583047, 0),
+-					Typeflag: '0',
+-					Uname:    "guillaume",
+-					Gname:    "guillaume",
+-				},
+-				// fake contents
+-				contents: strings.Repeat("\x00", 4<<10),
+-			},
+-		},
+-	},
+-	// This file was produced using gnu tar 1.17
+-	// gnutar  -b 4 --format=ustar (longname/)*15 + file.txt
+-	{
+-		file: "testdata/ustar.tar",
+-		entries: []*writerTestEntry{
+-			{
+-				header: &Header{
+-					Name:     strings.Repeat("longname/", 15) + "file.txt",
+-					Mode:     0644,
+-					Uid:      0765,
+-					Gid:      024,
+-					Size:     06,
+-					ModTime:  time.Unix(1360135598, 0),
+-					Typeflag: '0',
+-					Uname:    "shane",
+-					Gname:    "staff",
+-				},
+-				contents: "hello\n",
+-			},
+-		},
+-	},
+-}
+-
+-// Render byte array in a two-character hexadecimal string, spaced for easy visual inspection.
+-func bytestr(offset int, b []byte) string {
+-	const rowLen = 32
+-	s := fmt.Sprintf("%04x ", offset)
+-	for _, ch := range b {
+-		switch {
+-		case '0' <= ch && ch <= '9', 'A' <= ch && ch <= 'Z', 'a' <= ch && ch <= 'z':
+-			s += fmt.Sprintf("  %c", ch)
+-		default:
+-			s += fmt.Sprintf(" %02x", ch)
+-		}
+-	}
+-	return s
+-}
+-
+-// Render a pseudo-diff between two blocks of bytes.
+-func bytediff(a []byte, b []byte) string {
+-	const rowLen = 32
+-	s := fmt.Sprintf("(%d bytes vs. %d bytes)\n", len(a), len(b))
+-	for offset := 0; len(a)+len(b) > 0; offset += rowLen {
+-		na, nb := rowLen, rowLen
+-		if na > len(a) {
+-			na = len(a)
+-		}
+-		if nb > len(b) {
+-			nb = len(b)
+-		}
+-		sa := bytestr(offset, a[0:na])
+-		sb := bytestr(offset, b[0:nb])
+-		if sa != sb {
+-			s += fmt.Sprintf("-%v\n+%v\n", sa, sb)
+-		}
+-		a = a[na:]
+-		b = b[nb:]
+-	}
+-	return s
+-}
+-
+-func TestWriter(t *testing.T) {
+-testLoop:
+-	for i, test := range writerTests {
+-		expected, err := ioutil.ReadFile(test.file)
+-		if err != nil {
+-			t.Errorf("test %d: Unexpected error: %v", i, err)
+-			continue
+-		}
+-
+-		buf := new(bytes.Buffer)
+-		tw := NewWriter(iotest.TruncateWriter(buf, 4<<10)) // only catch the first 4 KB
+-		big := false
+-		for j, entry := range test.entries {
+-			big = big || entry.header.Size > 1<<10
+-			if err := tw.WriteHeader(entry.header); err != nil {
+-				t.Errorf("test %d, entry %d: Failed writing header: %v", i, j, err)
+-				continue testLoop
+-			}
+-			if _, err := io.WriteString(tw, entry.contents); err != nil {
+-				t.Errorf("test %d, entry %d: Failed writing contents: %v", i, j, err)
+-				continue testLoop
+-			}
+-		}
+-		// Only interested in Close failures for the small tests.
+-		if err := tw.Close(); err != nil && !big {
+-			t.Errorf("test %d: Failed closing archive: %v", i, err)
+-			continue testLoop
+-		}
+-
+-		actual := buf.Bytes()
+-		if !bytes.Equal(expected, actual) {
+-			t.Errorf("test %d: Incorrect result: (-=expected, +=actual)\n%v",
+-				i, bytediff(expected, actual))
+-		}
+-		if testing.Short() { // The second test is expensive.
+-			break
+-		}
+-	}
+-}
+-
+-func TestPax(t *testing.T) {
+-	// Create an archive with a large name
+-	fileinfo, err := os.Stat("testdata/small.txt")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	hdr, err := FileInfoHeader(fileinfo, "")
+-	if err != nil {
+-		t.Fatalf("os.Stat: %v", err)
+-	}
+-	// Force a PAX long name to be written
+-	longName := strings.Repeat("ab", 100)
+-	contents := strings.Repeat(" ", int(hdr.Size))
+-	hdr.Name = longName
+-	var buf bytes.Buffer
+-	writer := NewWriter(&buf)
+-	if err := writer.WriteHeader(hdr); err != nil {
+-		t.Fatal(err)
+-	}
+-	if _, err = writer.Write([]byte(contents)); err != nil {
+-		t.Fatal(err)
+-	}
+-	if err := writer.Close(); err != nil {
+-		t.Fatal(err)
+-	}
+-	// Simple test to make sure PAX extensions are in effect
+-	if !bytes.Contains(buf.Bytes(), []byte("PaxHeaders.")) {
+-		t.Fatal("Expected at least one PAX header to be written.")
+-	}
+-	// Test that we can get a long name back out of the archive.
+-	reader := NewReader(&buf)
+-	hdr, err = reader.Next()
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if hdr.Name != longName {
+-		t.Fatal("Couldn't recover long file name")
+-	}
+-}
+-
+-func TestPaxSymlink(t *testing.T) {
+-	// Create an archive with a large linkname
+-	fileinfo, err := os.Stat("testdata/small.txt")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	hdr, err := FileInfoHeader(fileinfo, "")
+-	hdr.Typeflag = TypeSymlink
+-	if err != nil {
+-		t.Fatalf("os.Stat:1 %v", err)
+-	}
+-	// Force a PAX long linkname to be written
+-	longLinkname := strings.Repeat("1234567890/1234567890", 10)
+-	hdr.Linkname = longLinkname
+-
+-	hdr.Size = 0
+-	var buf bytes.Buffer
+-	writer := NewWriter(&buf)
+-	if err := writer.WriteHeader(hdr); err != nil {
+-		t.Fatal(err)
+-	}
+-	if err := writer.Close(); err != nil {
+-		t.Fatal(err)
+-	}
+-	// Simple test to make sure PAX extensions are in effect
+-	if !bytes.Contains(buf.Bytes(), []byte("PaxHeaders.")) {
+-		t.Fatal("Expected at least one PAX header to be written.")
+-	}
+-	// Test that we can get a long name back out of the archive.
+-	reader := NewReader(&buf)
+-	hdr, err = reader.Next()
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if hdr.Linkname != longLinkname {
+-		t.Fatal("Couldn't recover long link name")
+-	}
+-}
+-
+-func TestPaxNonAscii(t *testing.T) {
+-	// Create an archive with non ascii. These should trigger a pax header
+-	// because pax headers have a defined utf-8 encoding.
+-	fileinfo, err := os.Stat("testdata/small.txt")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	hdr, err := FileInfoHeader(fileinfo, "")
+-	if err != nil {
+-		t.Fatalf("os.Stat:1 %v", err)
+-	}
+-
+-	// some sample data
+-	chineseFilename := "文件名"
+-	chineseGroupname := "組"
+-	chineseUsername := "用戶名"
+-
+-	hdr.Name = chineseFilename
+-	hdr.Gname = chineseGroupname
+-	hdr.Uname = chineseUsername
+-
+-	contents := strings.Repeat(" ", int(hdr.Size))
+-
+-	var buf bytes.Buffer
+-	writer := NewWriter(&buf)
+-	if err := writer.WriteHeader(hdr); err != nil {
+-		t.Fatal(err)
+-	}
+-	if _, err = writer.Write([]byte(contents)); err != nil {
+-		t.Fatal(err)
+-	}
+-	if err := writer.Close(); err != nil {
+-		t.Fatal(err)
+-	}
+-	// Simple test to make sure PAX extensions are in effect
+-	if !bytes.Contains(buf.Bytes(), []byte("PaxHeaders.")) {
+-		t.Fatal("Expected at least one PAX header to be written.")
+-	}
+-	// Test that we can get a long name back out of the archive.
+-	reader := NewReader(&buf)
+-	hdr, err = reader.Next()
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if hdr.Name != chineseFilename {
+-		t.Fatal("Couldn't recover unicode name")
+-	}
+-	if hdr.Gname != chineseGroupname {
+-		t.Fatal("Couldn't recover unicode group")
+-	}
+-	if hdr.Uname != chineseUsername {
+-		t.Fatal("Couldn't recover unicode user")
+-	}
+-}
+-
+-func TestPaxXattrs(t *testing.T) {
+-	xattrs := map[string]string{
+-		"user.key": "value",
+-	}
+-
+-	// Create an archive with an xattr
+-	fileinfo, err := os.Stat("testdata/small.txt")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	hdr, err := FileInfoHeader(fileinfo, "")
+-	if err != nil {
+-		t.Fatalf("os.Stat: %v", err)
+-	}
+-	contents := "Kilts"
+-	hdr.Xattrs = xattrs
+-	var buf bytes.Buffer
+-	writer := NewWriter(&buf)
+-	if err := writer.WriteHeader(hdr); err != nil {
+-		t.Fatal(err)
+-	}
+-	if _, err = writer.Write([]byte(contents)); err != nil {
+-		t.Fatal(err)
+-	}
+-	if err := writer.Close(); err != nil {
+-		t.Fatal(err)
+-	}
+-	// Test that we can get the xattrs back out of the archive.
+-	reader := NewReader(&buf)
+-	hdr, err = reader.Next()
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !reflect.DeepEqual(hdr.Xattrs, xattrs) {
+-		t.Fatalf("xattrs did not survive round trip: got %+v, want %+v",
+-			hdr.Xattrs, xattrs)
+-	}
+-}
+-
+-func TestPAXHeader(t *testing.T) {
+-	medName := strings.Repeat("CD", 50)
+-	longName := strings.Repeat("AB", 100)
+-	paxTests := [][2]string{
+-		{paxPath + "=/etc/hosts", "19 path=/etc/hosts\n"},
+-		{"a=b", "6 a=b\n"},          // Single digit length
+-		{"a=names", "11 a=names\n"}, // Test case involving carries
+-		{paxPath + "=" + longName, fmt.Sprintf("210 path=%s\n", longName)},
+-		{paxPath + "=" + medName, fmt.Sprintf("110 path=%s\n", medName)}}
+-
+-	for _, test := range paxTests {
+-		key, expected := test[0], test[1]
+-		if result := paxHeader(key); result != expected {
+-			t.Fatalf("paxHeader: got %s, expected %s", result, expected)
+-		}
+-	}
+-}
+-
+-func TestUSTARLongName(t *testing.T) {
+-	// Create an archive with a path that failed to split with USTAR extension in previous versions.
+-	fileinfo, err := os.Stat("testdata/small.txt")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	hdr, err := FileInfoHeader(fileinfo, "")
+-	hdr.Typeflag = TypeDir
+-	if err != nil {
+-		t.Fatalf("os.Stat:1 %v", err)
+-	}
+-	// Force a PAX long name to be written. The name was taken from a practical example
+-	// that fails and replaced ever char through numbers to anonymize the sample.
+-	longName := "/0000_0000000/00000-000000000/0000_0000000/00000-0000000000000/0000_0000000/00000-0000000-00000000/0000_0000000/00000000/0000_0000000/000/0000_0000000/00000000v00/0000_0000000/000000/0000_0000000/0000000/0000_0000000/00000y-00/0000/0000/00000000/0x000000/"
+-	hdr.Name = longName
+-
+-	hdr.Size = 0
+-	var buf bytes.Buffer
+-	writer := NewWriter(&buf)
+-	if err := writer.WriteHeader(hdr); err != nil {
+-		t.Fatal(err)
+-	}
+-	if err := writer.Close(); err != nil {
+-		t.Fatal(err)
+-	}
+-	// Test that we can get a long name back out of the archive.
+-	reader := NewReader(&buf)
+-	hdr, err = reader.Next()
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if hdr.Name != longName {
+-		t.Fatal("Couldn't recover long name")
+-	}
+-}
+-
+-func TestValidTypeflagWithPAXHeader(t *testing.T) {
+-	var buffer bytes.Buffer
+-	tw := NewWriter(&buffer)
+-
+-	fileName := strings.Repeat("ab", 100)
+-
+-	hdr := &Header{
+-		Name:     fileName,
+-		Size:     4,
+-		Typeflag: 0,
+-	}
+-	if err := tw.WriteHeader(hdr); err != nil {
+-		t.Fatalf("Failed to write header: %s", err)
+-	}
+-	if _, err := tw.Write([]byte("fooo")); err != nil {
+-		t.Fatalf("Failed to write the file's data: %s", err)
+-	}
+-	tw.Close()
+-
+-	tr := NewReader(&buffer)
+-
+-	for {
+-		header, err := tr.Next()
+-		if err == io.EOF {
+-			break
+-		}
+-		if err != nil {
+-			t.Fatalf("Failed to read header: %s", err)
+-		}
+-		if header.Typeflag != 0 {
+-			t.Fatalf("Typeflag should've been 0, found %d", header.Typeflag)
+-		}
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/LICENSE b/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/LICENSE
+deleted file mode 100644
+index 5782c72..0000000
+--- a/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/LICENSE
++++ /dev/null
+@@ -1,23 +0,0 @@
+-Copyright (c) 2014, Elazar Leibovich
+-All rights reserved.
+-
+-Redistribution and use in source and binary forms, with or without
+-modification, are permitted provided that the following conditions are met:
+-
+-* Redistributions of source code must retain the above copyright notice, this
+-  list of conditions and the following disclaimer.
+-
+-* Redistributions in binary form must reproduce the above copyright notice,
+-  this list of conditions and the following disclaimer in the documentation
+-  and/or other materials provided with the distribution.
+-
+-THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+-AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+-IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+-DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
+-FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+-DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+-SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+-CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+-OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+-OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+diff --git a/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/README.md b/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/README.md
+deleted file mode 100644
+index a3929a8..0000000
+--- a/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/README.md
++++ /dev/null
+@@ -1,18 +0,0 @@
+-go-bindata-http
+-===============
+-
+-Serve embedded files from [jteeuwen/go-bindata](https://github.com/jteeuwen/go-bindata) with `net/http`.
+-
+-[GoDoc](http://godoc.org/github.com/elazarl/go-bindata-assetfs)
+-
+-After running
+-
+-    $ go-bindata data/...
+-
+-Use
+-
+-     http.Handle("/",
+-        http.FileServer(
+-        &assetfs.AssetFS{Asset: Asset, AssetDir: AssetDir, Prefix: "data"}))
+-
+-to serve files embedded from the `data` directory.
+diff --git a/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/assetfs.go b/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/assetfs.go
+deleted file mode 100644
+index 83cd94d..0000000
+--- a/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/assetfs.go
++++ /dev/null
+@@ -1,141 +0,0 @@
+-package assetfs
+-
+-import (
+-	"bytes"
+-	"errors"
+-	"fmt"
+-	"io"
+-	"io/ioutil"
+-	"net/http"
+-	"os"
+-	"path"
+-	"path/filepath"
+-	"time"
+-)
+-
+-// FakeFile implements os.FileInfo interface for a given path and size
+-type FakeFile struct {
+-	// Path is the path of this file
+-	Path string
+-	// Dir marks of the path is a directory
+-	Dir bool
+-	// Len is the length of the fake file, zero if it is a directory
+-	Len int64
+-}
+-
+-func (f *FakeFile) Name() string {
+-	_, name := filepath.Split(f.Path)
+-	return name
+-}
+-
+-func (f *FakeFile) Mode() os.FileMode {
+-	mode := os.FileMode(0644)
+-	if f.Dir {
+-		return mode | os.ModeDir
+-	}
+-	return mode
+-}
+-
+-func (f *FakeFile) ModTime() time.Time {
+-	return time.Unix(0, 0)
+-}
+-
+-func (f *FakeFile) Size() int64 {
+-	return f.Len
+-}
+-
+-func (f *FakeFile) IsDir() bool {
+-	return f.Mode().IsDir()
+-}
+-
+-func (f *FakeFile) Sys() interface{} {
+-	return nil
+-}
+-
+-// AssetFile implements http.File interface for a no-directory file with content
+-type AssetFile struct {
+-	*bytes.Reader
+-	io.Closer
+-	FakeFile
+-}
+-
+-func NewAssetFile(name string, content []byte) *AssetFile {
+-	return &AssetFile{
+-		bytes.NewReader(content),
+-		ioutil.NopCloser(nil),
+-		FakeFile{name, false, int64(len(content))}}
+-}
+-
+-func (f *AssetFile) Readdir(count int) ([]os.FileInfo, error) {
+-	return nil, errors.New("not a directory")
+-}
+-
+-func (f *AssetFile) Stat() (os.FileInfo, error) {
+-	return f, nil
+-}
+-
+-// AssetDirectory implements http.File interface for a directory
+-type AssetDirectory struct {
+-	AssetFile
+-	ChildrenRead int
+-	Children     []os.FileInfo
+-}
+-
+-func NewAssetDirectory(name string, children []string, fs *AssetFS) *AssetDirectory {
+-	fileinfos := make([]os.FileInfo, 0, len(children))
+-	for _, child := range children {
+-		_, err := fs.AssetDir(filepath.Join(name, child))
+-		fileinfos = append(fileinfos, &FakeFile{child, err == nil, 0})
+-	}
+-	return &AssetDirectory{
+-		AssetFile{
+-			bytes.NewReader(nil),
+-			ioutil.NopCloser(nil),
+-			FakeFile{name, true, 0},
+-		},
+-		0,
+-		fileinfos}
+-}
+-
+-func (f *AssetDirectory) Readdir(count int) ([]os.FileInfo, error) {
+-	fmt.Println(f, count)
+-	if count <= 0 {
+-		return f.Children, nil
+-	}
+-	if f.ChildrenRead+count > len(f.Children) {
+-		count = len(f.Children) - f.ChildrenRead
+-	}
+-	rv := f.Children[f.ChildrenRead : f.ChildrenRead+count]
+-	f.ChildrenRead += count
+-	return rv, nil
+-}
+-
+-func (f *AssetDirectory) Stat() (os.FileInfo, error) {
+-	return f, nil
+-}
+-
+-// AssetFS implements http.FileSystem, allowing
+-// embedded files to be served from net/http package.
+-type AssetFS struct {
+-	// Asset should return content of file in path if exists
+-	Asset func(path string) ([]byte, error)
+-	// AssetDir should return list of files in the path
+-	AssetDir func(path string) ([]string, error)
+-	// Prefix would be prepended to http requests
+-	Prefix string
+-}
+-
+-func (fs *AssetFS) Open(name string) (http.File, error) {
+-	name = path.Join(fs.Prefix, name)
+-	if len(name) > 0 && name[0] == '/' {
+-		name = name[1:]
+-	}
+-	if children, err := fs.AssetDir(name); err == nil {
+-		return NewAssetDirectory(name, children, fs), nil
+-	}
+-	b, err := fs.Asset(name)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return NewAssetFile(name, b), nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/doc.go b/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/doc.go
+deleted file mode 100644
+index a664249..0000000
+--- a/Godeps/_workspace/src/github.com/elazarl/go-bindata-assetfs/doc.go
++++ /dev/null
+@@ -1,13 +0,0 @@
+-// assetfs allows packages to serve static content embedded
+-// with the go-bindata tool with the standard net/http package.
+-//
+-// See https://github.com/jteeuwen/go-bindata for more information
+-// about embedding binary data with go-bindata.
+-//
+-// Usage example, after running
+-//    $ go-bindata data/...
+-// use:
+-//     http.Handle("/",
+-//        http.FileServer(
+-//        &assetfs.AssetFS{Asset: Asset, AssetDir: AssetDir, Prefix: "data"}))
+-package assetfs
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/.gitignore b/Godeps/_workspace/src/github.com/emicklei/go-restful/.gitignore
+deleted file mode 100644
+index cece7be..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/.gitignore
++++ /dev/null
+@@ -1,70 +0,0 @@
+-# Compiled Object files, Static and Dynamic libs (Shared Objects)
+-*.o
+-*.a
+-*.so
+-
+-# Folders
+-_obj
+-_test
+-
+-# Architecture specific extensions/prefixes
+-*.[568vq]
+-[568vq].out
+-
+-*.cgo1.go
+-*.cgo2.c
+-_cgo_defun.c
+-_cgo_gotypes.go
+-_cgo_export.*
+-
+-_testmain.go
+-
+-*.exe
+-
+-restful.html
+-
+-*.out
+-
+-tmp.prof
+-
+-go-restful.test
+-
+-examples/restful-basic-authentication
+-
+-examples/restful-encoding-filter
+-
+-examples/restful-filters
+-
+-examples/restful-hello-world
+-
+-examples/restful-resource-functions
+-
+-examples/restful-serve-static
+-
+-examples/restful-user-service
+-
+-*.DS_Store
+-examples/restful-user-resource
+-
+-examples/restful-multi-containers
+-
+-examples/restful-form-handling
+-
+-examples/restful-CORS-filter
+-
+-examples/restful-options-filter
+-
+-examples/restful-curly-router
+-
+-examples/restful-cpuprofiler-service
+-
+-examples/restful-pre-post-filters
+-
+-curly.prof
+-
+-examples/restful-NCSA-logging
+-
+-examples/restful-html-template
+-
+-s.html
+-restful-path-tail
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/CHANGES.md b/Godeps/_workspace/src/github.com/emicklei/go-restful/CHANGES.md
+deleted file mode 100644
+index 9c6de61..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/CHANGES.md
++++ /dev/null
+@@ -1,130 +0,0 @@
+-Change history of go-restful
+-=
+-2014-11-27
+-- (api add) PrettyPrint per response. (as proposed in #167)
+-
+-2014-11-12
+-- (api add) ApiVersion(.) for documentation in Swagger UI
+-
+-2014-11-10
+-- (api change) struct fields tagged with "description" show up in Swagger UI
+-
+-2014-10-31
+-- (api change) ReturnsError -> Returns
+-- (api add)    RouteBuilder.Do(aBuilder) for DRY use of RouteBuilder
+-- fix swagger nested structs
+-- sort Swagger response messages by code
+-
+-2014-10-23
+-- (api add) ReturnsError allows you to document Http codes in swagger
+-- fixed problem with greedy CurlyRouter
+-- (api add) Access-Control-Max-Age in CORS
+-- add tracing functionality (injectable) for debugging purposes
+-- support JSON parse 64bit int 
+-- fix empty parameters for swagger
+-- WebServicesUrl is now optional for swagger
+-- fixed duplicate AccessControlAllowOrigin in CORS
+-- (api change) expose ServeMux in container
+-- (api add) added AllowedDomains in CORS
+-- (api add) ParameterNamed for detailed documentation
+-
+-2014-04-16
+-- (api add) expose constructor of Request for testing.
+-
+-2014-06-27
+-- (api add) ParameterNamed gives access to a Parameter definition and its data (for further specification).
+-- (api add) SetCacheReadEntity allow scontrol over whether or not the request body is being cached (default true for compatibility reasons).
+-
+-2014-07-03
+-- (api add) CORS can be configured with a list of allowed domains
+-
+-2014-03-12
+-- (api add) Route path parameters can use wildcard or regular expressions. (requires CurlyRouter)
+-
+-2014-02-26
+-- (api add) Request now provides information about the matched Route, see method SelectedRoutePath 
+-
+-2014-02-17
+-- (api change) renamed parameter constants (go-lint checks)
+-
+-2014-01-10
+- - (api add) support for CloseNotify, see http://golang.org/pkg/net/http/#CloseNotifier
+-
+-2014-01-07
+- - (api change) Write* methods in Response now return the error or nil.
+- - added example of serving HTML from a Go template.
+- - fixed comparing Allowed headers in CORS (is now case-insensitive)
+-
+-2013-11-13
+- - (api add) Response knows how many bytes are written to the response body.
+-
+-2013-10-29
+- - (api add) RecoverHandler(handler RecoverHandleFunction) to change how panic recovery is handled. Default behavior is to log and return a stacktrace. This may be a security issue as it exposes sourcecode information.
+-
+-2013-10-04
+- - (api add) Response knows what HTTP status has been written
+- - (api add) Request can have attributes (map of string->interface, also called request-scoped variables
+-
+-2013-09-12
+- - (api change) Router interface simplified
+- - Implemented CurlyRouter, a Router that does not use|allow regular expressions in paths
+-
+-2013-08-05
+- - add OPTIONS support
+- - add CORS support
+-
+-2013-08-27
+- - fixed some reported issues (see github)
+- - (api change) deprecated use of WriteError; use WriteErrorString instead
+-
+-2014-04-15
+- - (fix) v1.0.1 tag: fix Issue 111: WriteErrorString
+-
+-2013-08-08
+- - (api add) Added implementation Container: a WebServices collection with its own http.ServeMux allowing multiple endpoints per program. Existing uses of go-restful will register their services to the DefaultContainer.
+- - (api add) the swagger package has be extended to have a UI per container.
+- - if panic is detected then a small stack trace is printed (thanks to runner-mei)
+- - (api add) WriteErrorString to Response
+-
+-Important API changes:
+-
+- - (api remove) package variable DoNotRecover no longer works ; use restful.DefaultContainer.DoNotRecover(true) instead.
+- - (api remove) package variable EnableContentEncoding no longer works ; use restful.DefaultContainer.EnableContentEncoding(true) instead.
+- 
+- 
+-2013-07-06
+-
+- - (api add) Added support for response encoding (gzip and deflate(zlib)). This feature is disabled on default (for backwards compatibility). Use restful.EnableContentEncoding = true in your initialization to enable this feature.
+-
+-2013-06-19
+-
+- - (improve) DoNotRecover option, moved request body closer, improved ReadEntity
+-
+-2013-06-03
+-
+- - (api change) removed Dispatcher interface, hide PathExpression
+- - changed receiver names of type functions to be more idiomatic Go
+-
+-2013-06-02
+-
+- - (optimize) Cache the RegExp compilation of Paths.
+-
+-2013-05-22
+-	
+- - (api add) Added support for request/response filter functions
+-
+-2013-05-18
+-
+-
+- - (api add) Added feature to change the default Http Request Dispatch function (travis cline)
+- - (api change) Moved Swagger Webservice to swagger package (see example restful-user)
+-
+-[2012-11-14 .. 2013-05-18>
+- 
+- - See https://github.com/emicklei/go-restful/commits
+-
+-2012-11-14
+-
+- - Initial commit
+-
+-
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/LICENSE b/Godeps/_workspace/src/github.com/emicklei/go-restful/LICENSE
+deleted file mode 100644
+index ece7ec6..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/LICENSE
++++ /dev/null
+@@ -1,22 +0,0 @@
+-Copyright (c) 2012,2013 Ernest Micklei
+-
+-MIT License
+-
+-Permission is hereby granted, free of charge, to any person obtaining
+-a copy of this software and associated documentation files (the
+-"Software"), to deal in the Software without restriction, including
+-without limitation the rights to use, copy, modify, merge, publish,
+-distribute, sublicense, and/or sell copies of the Software, and to
+-permit persons to whom the Software is furnished to do so, subject to
+-the following conditions:
+-
+-The above copyright notice and this permission notice shall be
+-included in all copies or substantial portions of the Software.
+-
+-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+-EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+-MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+-NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+-LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+-OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+-WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+\ No newline at end of file
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/README.md b/Godeps/_workspace/src/github.com/emicklei/go-restful/README.md
+deleted file mode 100644
+index 8af137d..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/README.md
++++ /dev/null
+@@ -1,70 +0,0 @@
+-go-restful
+-==========
+-
+-package for building REST-style Web Services using Google Go
+-
+-REST asks developers to use HTTP methods explicitly and in a way that's consistent with the protocol definition. This basic REST design principle establishes a one-to-one mapping between create, read, update, and delete (CRUD) operations and HTTP methods. According to this mapping:
+-
+-- GET = Retrieve a representation of a resource
+-- POST = Create if you are sending content to the server to create a subordinate of the specified resource collection, using some server-side algorithm.
+-- PUT = Create if you are sending the full content of the specified resource (URI).
+-- PUT = Update if you are updating the full content of the specified resource.
+-- DELETE = Delete if you are requesting the server to delete the resource
+-- PATCH = Update partial content of a resource
+-- OPTIONS = Get information about the communication options for the request URI
+-    
+-### Example
+-
+-```Go
+-ws := new(restful.WebService)
+-ws.
+-	Path("/users").
+-	Consumes(restful.MIME_XML, restful.MIME_JSON).
+-	Produces(restful.MIME_JSON, restful.MIME_XML)
+-
+-ws.Route(ws.GET("/{user-id}").To(u.findUser).
+-	Doc("get a user").
+-	Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")).
+-	Writes(User{}))		
+-...
+-	
+-func (u UserResource) findUser(request *restful.Request, response *restful.Response) {
+-	id := request.PathParameter("user-id")
+-	...
+-}
+-```
+-	
+-[Full API of a UserResource](https://github.com/emicklei/go-restful/tree/master/examples/restful-user-resource.go) 
+-		
+-### Features
+-
+-- Routes for request &#8594; function mapping with path parameter (e.g. {id}) support
+-- Configurable router:
+-	- Routing algorithm after [JSR311](http://jsr311.java.net/nonav/releases/1.1/spec/spec.html) that is implemented using (but doest **not** accept) regular expressions (See RouterJSR311 which is used by default)
+-	- Fast routing algorithm that allows static elements, regular expressions and dynamic parameters in the URL path (e.g. /meetings/{id} or /static/{subpath:*}, See CurlyRouter)
+-- Request API for reading structs from JSON/XML and accesing parameters (path,query,header)
+-- Response API for writing structs to JSON/XML and setting headers
+-- Filters for intercepting the request &#8594; response flow on Service or Route level
+-- Request-scoped variables using attributes
+-- Containers for WebServices on different HTTP endpoints
+-- Content encoding (gzip,deflate) of responses
+-- Automatic responses on OPTIONS (using a filter)
+-- Automatic CORS request handling (using a filter)
+-- API declaration for Swagger UI (see swagger package)
+-- Panic recovery to produce HTTP 500, customizable using RecoverHandler(...)
+-	
+-### Resources
+-
+-- [Documentation on godoc.org](http://godoc.org/github.com/emicklei/go-restful)
+-- [Code examples](https://github.com/emicklei/go-restful/tree/master/examples)
+-- [Example posted on blog](http://ernestmicklei.com/2012/11/24/go-restful-first-working-example/)
+-- [Design explained on blog](http://ernestmicklei.com/2012/11/11/go-restful-api-design/)
+-- [sourcegraph](https://sourcegraph.com/github.com/emicklei/go-restful)
+-- [gopkg.in](https://gopkg.in/emicklei/go-restful.v1)
+-- [showcase: Mora - MongoDB REST Api server](https://github.com/emicklei/mora)
+-
+-[![Build Status](https://drone.io/github.com/emicklei/go-restful/status.png)](https://drone.io/github.com/emicklei/go-restful/latest)[![library users](https://sourcegraph.com/api/repos/github.com/emicklei/go-restful/badges/library-users.png)](https://sourcegraph.com/github.com/emicklei/go-restful) [![authors](https://sourcegraph.com/api/repos/github.com/emicklei/go-restful/badges/authors.png)](https://sourcegraph.com/github.com/emicklei/go-restful) [![xrefs](https://sourcegraph.com/api/repos/github.com/emicklei/go-restful/badges/xrefs.png)](https://sourcegraph.com/github.com/emicklei/go-restful)
+-
+-(c) 2012 - 2014, http://ernestmicklei.com. MIT License
+-
+-Type ```git shortlog -s``` for a full list of contributors.
+\ No newline at end of file
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/Srcfile b/Godeps/_workspace/src/github.com/emicklei/go-restful/Srcfile
+deleted file mode 100644
+index 16fd186..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/Srcfile
++++ /dev/null
+@@ -1 +0,0 @@
+-{"SkipDirs": ["examples"]}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/bench_curly_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/bench_curly_test.go
+deleted file mode 100644
+index db6a1a7..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/bench_curly_test.go
++++ /dev/null
+@@ -1,51 +0,0 @@
+-package restful
+-
+-import (
+-	"fmt"
+-	"net/http"
+-	"net/http/httptest"
+-	"testing"
+-)
+-
+-func setupCurly(container *Container) []string {
+-	wsCount := 26
+-	rtCount := 26
+-	urisCurly := []string{}
+-
+-	container.Router(CurlyRouter{})
+-	for i := 0; i < wsCount; i++ {
+-		root := fmt.Sprintf("/%s/{%s}/", string(i+97), string(i+97))
+-		ws := new(WebService).Path(root)
+-		for j := 0; j < rtCount; j++ {
+-			sub := fmt.Sprintf("/%s2/{%s2}", string(j+97), string(j+97))
+-			ws.Route(ws.GET(sub).Consumes("application/xml").Produces("application/xml").To(echoCurly))
+-		}
+-		container.Add(ws)
+-		for _, each := range ws.Routes() {
+-			urisCurly = append(urisCurly, "http://bench.com"+each.Path)
+-		}
+-	}
+-	return urisCurly
+-}
+-
+-func echoCurly(req *Request, resp *Response) {}
+-
+-func BenchmarkManyCurly(b *testing.B) {
+-	container := NewContainer()
+-	urisCurly := setupCurly(container)
+-	b.ResetTimer()
+-	for t := 0; t < b.N; t++ {
+-		for r := 0; r < 1000; r++ {
+-			for _, each := range urisCurly {
+-				sendNoReturnTo(each, container, t)
+-			}
+-		}
+-	}
+-}
+-
+-func sendNoReturnTo(address string, container *Container, t int) {
+-	httpRequest, _ := http.NewRequest("GET", address, nil)
+-	httpRequest.Header.Set("Accept", "application/xml")
+-	httpWriter := httptest.NewRecorder()
+-	container.dispatch(httpWriter, httpRequest)
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/bench_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/bench_test.go
+deleted file mode 100644
+index 3e77c2d..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/bench_test.go
++++ /dev/null
+@@ -1,43 +0,0 @@
+-package restful
+-
+-import (
+-	"fmt"
+-	"io"
+-	"testing"
+-)
+-
+-var uris = []string{}
+-
+-func setup(container *Container) {
+-	wsCount := 26
+-	rtCount := 26
+-
+-	for i := 0; i < wsCount; i++ {
+-		root := fmt.Sprintf("/%s/{%s}/", string(i+97), string(i+97))
+-		ws := new(WebService).Path(root)
+-		for j := 0; j < rtCount; j++ {
+-			sub := fmt.Sprintf("/%s2/{%s2}", string(j+97), string(j+97))
+-			ws.Route(ws.GET(sub).To(echo))
+-		}
+-		container.Add(ws)
+-		for _, each := range ws.Routes() {
+-			uris = append(uris, "http://bench.com"+each.Path)
+-		}
+-	}
+-}
+-
+-func echo(req *Request, resp *Response) {
+-	io.WriteString(resp.ResponseWriter, "echo")
+-}
+-
+-func BenchmarkMany(b *testing.B) {
+-	container := NewContainer()
+-	setup(container)
+-	b.ResetTimer()
+-	for t := 0; t < b.N; t++ {
+-		for _, each := range uris {
+-			// println(each)
+-			sendItTo(each, container)
+-		}
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/bench_test.sh b/Godeps/_workspace/src/github.com/emicklei/go-restful/bench_test.sh
+deleted file mode 100644
+index 47ffbe4..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/bench_test.sh
++++ /dev/null
+@@ -1,10 +0,0 @@
+-#go test -run=none -file bench_test.go -test.bench . -cpuprofile=bench_test.out
+-
+-go test -c
+-./go-restful.test -test.run=none -test.cpuprofile=tmp.prof -test.bench=BenchmarkMany
+-./go-restful.test -test.run=none -test.cpuprofile=curly.prof -test.bench=BenchmarkManyCurly
+-
+-#go tool pprof go-restful.test tmp.prof
+-go tool pprof go-restful.test curly.prof
+-
+-
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/compress.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/compress.go
+deleted file mode 100644
+index c4dcca0..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/compress.go
++++ /dev/null
+@@ -1,89 +0,0 @@
+-package restful
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-import (
+-	"compress/gzip"
+-	"compress/zlib"
+-	"errors"
+-	"io"
+-	"net/http"
+-	"strings"
+-)
+-
+-// OBSOLETE : use restful.DefaultContainer.EnableContentEncoding(true) to change this setting.
+-var EnableContentEncoding = false
+-
+-// CompressingResponseWriter is a http.ResponseWriter that can perform content encoding (gzip and zlib)
+-type CompressingResponseWriter struct {
+-	writer     http.ResponseWriter
+-	compressor io.WriteCloser
+-}
+-
+-// Header is part of http.ResponseWriter interface
+-func (c *CompressingResponseWriter) Header() http.Header {
+-	return c.writer.Header()
+-}
+-
+-// WriteHeader is part of http.ResponseWriter interface
+-func (c *CompressingResponseWriter) WriteHeader(status int) {
+-	c.writer.WriteHeader(status)
+-}
+-
+-// Write is part of http.ResponseWriter interface
+-// It is passed through the compressor
+-func (c *CompressingResponseWriter) Write(bytes []byte) (int, error) {
+-	return c.compressor.Write(bytes)
+-}
+-
+-// CloseNotify is part of http.CloseNotifier interface
+-func (c *CompressingResponseWriter) CloseNotify() <-chan bool {
+-	return c.writer.(http.CloseNotifier).CloseNotify()
+-}
+-
+-// Close the underlying compressor
+-func (c *CompressingResponseWriter) Close() {
+-	c.compressor.Close()
+-}
+-
+-// WantsCompressedResponse reads the Accept-Encoding header to see if and which encoding is requested.
+-func wantsCompressedResponse(httpRequest *http.Request) (bool, string) {
+-	header := httpRequest.Header.Get(HEADER_AcceptEncoding)
+-	gi := strings.Index(header, ENCODING_GZIP)
+-	zi := strings.Index(header, ENCODING_DEFLATE)
+-	// use in order of appearance
+-	if gi == -1 {
+-		return zi != -1, ENCODING_DEFLATE
+-	} else if zi == -1 {
+-		return gi != -1, ENCODING_GZIP
+-	} else {
+-		if gi < zi {
+-			return true, ENCODING_GZIP
+-		}
+-		return true, ENCODING_DEFLATE
+-	}
+-}
+-
+-// NewCompressingResponseWriter create a CompressingResponseWriter for a known encoding = {gzip,deflate}
+-func NewCompressingResponseWriter(httpWriter http.ResponseWriter, encoding string) (*CompressingResponseWriter, error) {
+-	httpWriter.Header().Set(HEADER_ContentEncoding, encoding)
+-	c := new(CompressingResponseWriter)
+-	c.writer = httpWriter
+-	var err error
+-	if ENCODING_GZIP == encoding {
+-		c.compressor, err = gzip.NewWriterLevel(httpWriter, gzip.BestSpeed)
+-		if err != nil {
+-			return nil, err
+-		}
+-	} else if ENCODING_DEFLATE == encoding {
+-		c.compressor, err = zlib.NewWriterLevel(httpWriter, zlib.BestSpeed)
+-		if err != nil {
+-			return nil, err
+-		}
+-	} else {
+-		return nil, errors.New("Unknown encoding:" + encoding)
+-	}
+-	return c, err
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/compress_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/compress_test.go
+deleted file mode 100644
+index 332fb22..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/compress_test.go
++++ /dev/null
+@@ -1,53 +0,0 @@
+-package restful
+-
+-import (
+-	"net/http"
+-	"net/http/httptest"
+-	"testing"
+-)
+-
+-func TestGzip(t *testing.T) {
+-	EnableContentEncoding = true
+-	httpRequest, _ := http.NewRequest("GET", "/test", nil)
+-	httpRequest.Header.Set("Accept-Encoding", "gzip,deflate")
+-	httpWriter := httptest.NewRecorder()
+-	wanted, encoding := wantsCompressedResponse(httpRequest)
+-	if !wanted {
+-		t.Fatal("should accept gzip")
+-	}
+-	if encoding != "gzip" {
+-		t.Fatal("expected gzip")
+-	}
+-	c, err := NewCompressingResponseWriter(httpWriter, encoding)
+-	if err != nil {
+-		t.Fatal(err.Error())
+-	}
+-	c.Write([]byte("Hello World"))
+-	c.Close()
+-	if httpWriter.Header().Get("Content-Encoding") != "gzip" {
+-		t.Fatal("Missing gzip header")
+-	}
+-}
+-
+-func TestDeflate(t *testing.T) {
+-	EnableContentEncoding = true
+-	httpRequest, _ := http.NewRequest("GET", "/test", nil)
+-	httpRequest.Header.Set("Accept-Encoding", "deflate,gzip")
+-	httpWriter := httptest.NewRecorder()
+-	wanted, encoding := wantsCompressedResponse(httpRequest)
+-	if !wanted {
+-		t.Fatal("should accept deflate")
+-	}
+-	if encoding != "deflate" {
+-		t.Fatal("expected deflate")
+-	}
+-	c, err := NewCompressingResponseWriter(httpWriter, encoding)
+-	if err != nil {
+-		t.Fatal(err.Error())
+-	}
+-	c.Write([]byte("Hello World"))
+-	c.Close()
+-	if httpWriter.Header().Get("Content-Encoding") != "deflate" {
+-		t.Fatal("Missing deflate header")
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/constants.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/constants.go
+deleted file mode 100644
+index 5e564d0..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/constants.go
++++ /dev/null
+@@ -1,29 +0,0 @@
+-package restful
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-const (
+-	MIME_XML  = "application/xml"  // Accept or Content-Type used in Consumes() and/or Produces()
+-	MIME_JSON = "application/json" // Accept or Content-Type used in Consumes() and/or Produces()
+-
+-	HEADER_Allow                         = "Allow"
+-	HEADER_Accept                        = "Accept"
+-	HEADER_Origin                        = "Origin"
+-	HEADER_ContentType                   = "Content-Type"
+-	HEADER_LastModified                  = "Last-Modified"
+-	HEADER_AcceptEncoding                = "Accept-Encoding"
+-	HEADER_ContentEncoding               = "Content-Encoding"
+-	HEADER_AccessControlExposeHeaders    = "Access-Control-Expose-Headers"
+-	HEADER_AccessControlRequestMethod    = "Access-Control-Request-Method"
+-	HEADER_AccessControlRequestHeaders   = "Access-Control-Request-Headers"
+-	HEADER_AccessControlAllowMethods     = "Access-Control-Allow-Methods"
+-	HEADER_AccessControlAllowOrigin      = "Access-Control-Allow-Origin"
+-	HEADER_AccessControlAllowCredentials = "Access-Control-Allow-Credentials"
+-	HEADER_AccessControlAllowHeaders     = "Access-Control-Allow-Headers"
+-	HEADER_AccessControlMaxAge           = "Access-Control-Max-Age"
+-
+-	ENCODING_GZIP    = "gzip"
+-	ENCODING_DEFLATE = "deflate"
+-)
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/container.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/container.go
+deleted file mode 100644
+index 7aae565..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/container.go
++++ /dev/null
+@@ -1,261 +0,0 @@
+-package restful
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-import (
+-	"bytes"
+-	"fmt"
+-	"log"
+-	"net/http"
+-	"runtime"
+-	"strings"
+-)
+-
+-// Container holds a collection of WebServices and a http.ServeMux to dispatch http requests.
+-// The requests are further dispatched to routes of WebServices using a RouteSelector
+-type Container struct {
+-	webServices            []*WebService
+-	ServeMux               *http.ServeMux
+-	isRegisteredOnRoot     bool
+-	containerFilters       []FilterFunction
+-	doNotRecover           bool // default is false
+-	recoverHandleFunc      RecoverHandleFunction
+-	router                 RouteSelector // default is a RouterJSR311, CurlyRouter is the faster alternative
+-	contentEncodingEnabled bool          // default is false
+-}
+-
+-// NewContainer creates a new Container using a new ServeMux and default router (RouterJSR311)
+-func NewContainer() *Container {
+-	return &Container{
+-		webServices:            []*WebService{},
+-		ServeMux:               http.NewServeMux(),
+-		isRegisteredOnRoot:     false,
+-		containerFilters:       []FilterFunction{},
+-		doNotRecover:           false,
+-		recoverHandleFunc:      logStackOnRecover,
+-		router:                 RouterJSR311{},
+-		contentEncodingEnabled: false}
+-}
+-
+-// RecoverHandleFunction declares functions that can be used to handle a panic situation.
+-// The first argument is what recover() returns. The second must be used to communicate an error response.
+-type RecoverHandleFunction func(interface{}, http.ResponseWriter)
+-
+-// RecoverHandler changes the default function (logStackOnRecover) to be called
+-// when a panic is detected. DoNotRecover must be have its default value (=false).
+-func (c *Container) RecoverHandler(handler RecoverHandleFunction) {
+-	c.recoverHandleFunc = handler
+-}
+-
+-// DoNotRecover controls whether panics will be caught to return HTTP 500.
+-// If set to true, Route functions are responsible for handling any error situation.
+-// Default value is false = recover from panics. This has performance implications.
+-func (c *Container) DoNotRecover(doNot bool) {
+-	c.doNotRecover = doNot
+-}
+-
+-// Router changes the default Router (currently RouterJSR311)
+-func (c *Container) Router(aRouter RouteSelector) {
+-	c.router = aRouter
+-}
+-
+-// EnableContentEncoding (default=false) allows for GZIP or DEFLATE encoding of responses.
+-func (c *Container) EnableContentEncoding(enabled bool) {
+-	c.contentEncodingEnabled = enabled
+-}
+-
+-// Add a WebService to the Container. It will detect duplicate root paths and panic in that case.
+-func (c *Container) Add(service *WebService) *Container {
+-	// If registered on root then no additional specific mapping is needed
+-	if !c.isRegisteredOnRoot {
+-		pattern := c.fixedPrefixPath(service.RootPath())
+-		// check if root path registration is needed
+-		if "/" == pattern || "" == pattern {
+-			c.ServeMux.HandleFunc("/", c.dispatch)
+-			c.isRegisteredOnRoot = true
+-		} else {
+-			// detect if registration already exists
+-			alreadyMapped := false
+-			for _, each := range c.webServices {
+-				if each.RootPath() == service.RootPath() {
+-					alreadyMapped = true
+-					break
+-				}
+-			}
+-			if !alreadyMapped {
+-				c.ServeMux.HandleFunc(pattern, c.dispatch)
+-				if !strings.HasSuffix(pattern, "/") {
+-					c.ServeMux.HandleFunc(pattern+"/", c.dispatch)
+-				}
+-			}
+-		}
+-	}
+-	// cannot have duplicate root paths
+-	for _, each := range c.webServices {
+-		if each.RootPath() == service.RootPath() {
+-			log.Fatalf("[restful] WebService with duplicate root path detected:['%v']", each)
+-		}
+-	}
+-	// if rootPath was not set then lazy initialize it
+-	if len(service.rootPath) == 0 {
+-		service.Path("/")
+-	}
+-	c.webServices = append(c.webServices, service)
+-	return c
+-}
+-
+-// logStackOnRecover is the default RecoverHandleFunction and is called
+-// when DoNotRecover is false and the recoverHandleFunc is not set for the container.
+-// Default implementation logs the stacktrace and writes the stacktrace on the response.
+-// This may be a security issue as it exposes sourcecode information.
+-func logStackOnRecover(panicReason interface{}, httpWriter http.ResponseWriter) {
+-	var buffer bytes.Buffer
+-	buffer.WriteString(fmt.Sprintf("[restful] recover from panic situation: - %v\r\n", panicReason))
+-	for i := 2; ; i += 1 {
+-		_, file, line, ok := runtime.Caller(i)
+-		if !ok {
+-			break
+-		}
+-		buffer.WriteString(fmt.Sprintf("    %s:%d\r\n", file, line))
+-	}
+-	log.Println(buffer.String())
+-	httpWriter.WriteHeader(http.StatusInternalServerError)
+-	httpWriter.Write(buffer.Bytes())
+-}
+-
+-// Dispatch the incoming Http Request to a matching WebService.
+-func (c *Container) dispatch(httpWriter http.ResponseWriter, httpRequest *http.Request) {
+-	// Instal panic recovery unless told otherwise
+-	if !c.doNotRecover { // catch all for 500 response
+-		defer func() {
+-			if r := recover(); r != nil {
+-				c.recoverHandleFunc(r, httpWriter)
+-				return
+-			}
+-		}()
+-	}
+-	// Install closing the request body (if any)
+-	defer func() {
+-		if nil != httpRequest.Body {
+-			httpRequest.Body.Close()
+-		}
+-	}()
+-
+-	// Detect if compression is needed
+-	// assume without compression, test for override
+-	writer := httpWriter
+-	if c.contentEncodingEnabled {
+-		doCompress, encoding := wantsCompressedResponse(httpRequest)
+-		if doCompress {
+-			var err error
+-			writer, err = NewCompressingResponseWriter(httpWriter, encoding)
+-			if err != nil {
+-				log.Println("[restful] unable to install compressor:", err)
+-				httpWriter.WriteHeader(http.StatusInternalServerError)
+-				return
+-			}
+-			defer func() {
+-				writer.(*CompressingResponseWriter).Close()
+-			}()
+-		}
+-	}
+-	// Find best match Route ; err is non nil if no match was found
+-	webService, route, err := c.router.SelectRoute(
+-		c.webServices,
+-		httpRequest)
+-	if err != nil {
+-		// a non-200 response has already been written
+-		// run container filters anyway ; they should not touch the response...
+-		chain := FilterChain{Filters: c.containerFilters, Target: func(req *Request, resp *Response) {
+-			switch err.(type) {
+-			case ServiceError:
+-				ser := err.(ServiceError)
+-				resp.WriteErrorString(ser.Code, ser.Message)
+-			}
+-			// TODO
+-		}}
+-		chain.ProcessFilter(NewRequest(httpRequest), NewResponse(writer))
+-		return
+-	}
+-	wrappedRequest, wrappedResponse := route.wrapRequestResponse(writer, httpRequest)
+-	// pass through filters (if any)
+-	if len(c.containerFilters)+len(webService.filters)+len(route.Filters) > 0 {
+-		// compose filter chain
+-		allFilters := []FilterFunction{}
+-		allFilters = append(allFilters, c.containerFilters...)
+-		allFilters = append(allFilters, webService.filters...)
+-		allFilters = append(allFilters, route.Filters...)
+-		chain := FilterChain{Filters: allFilters, Target: func(req *Request, resp *Response) {
+-			// handle request by route after passing all filters
+-			route.Function(wrappedRequest, wrappedResponse)
+-		}}
+-		chain.ProcessFilter(wrappedRequest, wrappedResponse)
+-	} else {
+-		// no filters, handle request by route
+-		route.Function(wrappedRequest, wrappedResponse)
+-	}
+-}
+-
+-// fixedPrefixPath returns the fixed part of the partspec ; it may include template vars {}
+-func (c Container) fixedPrefixPath(pathspec string) string {
+-	varBegin := strings.Index(pathspec, "{")
+-	if -1 == varBegin {
+-		return pathspec
+-	}
+-	return pathspec[:varBegin]
+-}
+-
+-// ServeHTTP implements net/http.Handler therefore a Container can be a Handler in a http.Server
+-func (c Container) ServeHTTP(httpwriter http.ResponseWriter, httpRequest *http.Request) {
+-	c.ServeMux.ServeHTTP(httpwriter, httpRequest)
+-}
+-
+-// Handle registers the handler for the given pattern. If a handler already exists for pattern, Handle panics.
+-func (c Container) Handle(pattern string, handler http.Handler) {
+-	c.ServeMux.Handle(pattern, handler)
+-}
+-
+-// Filter appends a container FilterFunction. These are called before dispatching
+-// a http.Request to a WebService from the container
+-func (c *Container) Filter(filter FilterFunction) {
+-	c.containerFilters = append(c.containerFilters, filter)
+-}
+-
+-// RegisteredWebServices returns the collections of added WebServices
+-func (c Container) RegisteredWebServices() []*WebService {
+-	return c.webServices
+-}
+-
+-// computeAllowedMethods returns a list of HTTP methods that are valid for a Request
+-func (c Container) computeAllowedMethods(req *Request) []string {
+-	// Go through all RegisteredWebServices() and all its Routes to collect the options
+-	methods := []string{}
+-	requestPath := req.Request.URL.Path
+-	for _, ws := range c.RegisteredWebServices() {
+-		matches := ws.pathExpr.Matcher.FindStringSubmatch(requestPath)
+-		if matches != nil {
+-			finalMatch := matches[len(matches)-1]
+-			for _, rt := range ws.Routes() {
+-				matches := rt.pathExpr.Matcher.FindStringSubmatch(finalMatch)
+-				if matches != nil {
+-					lastMatch := matches[len(matches)-1]
+-					if lastMatch == "" || lastMatch == "/" { // do not include if value is neither empty nor ‘/’.
+-						methods = append(methods, rt.Method)
+-					}
+-				}
+-			}
+-		}
+-	}
+-	// methods = append(methods, "OPTIONS")  not sure about this
+-	return methods
+-}
+-
+-// newBasicRequestResponse creates a pair of Request,Response from its http versions.
+-// It is basic because no parameter or (produces) content-type information is given.
+-func newBasicRequestResponse(httpWriter http.ResponseWriter, httpRequest *http.Request) (*Request, *Response) {
+-	resp := NewResponse(httpWriter)
+-	resp.requestAccept = httpRequest.Header.Get(HEADER_Accept)
+-	return NewRequest(httpRequest), resp
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/cors_filter.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/cors_filter.go
+deleted file mode 100644
+index ae166b6..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/cors_filter.go
++++ /dev/null
+@@ -1,170 +0,0 @@
+-package restful
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-import (
+-	"strconv"
+-	"strings"
+-)
+-
+-// CrossOriginResourceSharing is used to create a Container Filter that implements CORS.
+-// Cross-origin resource sharing (CORS) is a mechanism that allows JavaScript on a web page
+-// to make XMLHttpRequests to another domain, not the domain the JavaScript originated from.
+-//
+-// http://en.wikipedia.org/wiki/Cross-origin_resource_sharing
+-// http://enable-cors.org/server.html
+-// http://www.html5rocks.com/en/tutorials/cors/#toc-handling-a-not-so-simple-request
+-type CrossOriginResourceSharing struct {
+-	ExposeHeaders  []string // list of Header names
+-	AllowedHeaders []string // list of Header names
+-	AllowedDomains []string // list of allowed values for Http Origin. If empty all are allowed.
+-	AllowedMethods []string
+-	MaxAge         int // number of seconds before requiring new Options request
+-	CookiesAllowed bool
+-	Container      *Container
+-}
+-
+-// Filter is a filter function that implements the CORS flow as documented on http://enable-cors.org/server.html
+-// and http://www.html5rocks.com/static/images/cors_server_flowchart.png
+-func (c CrossOriginResourceSharing) Filter(req *Request, resp *Response, chain *FilterChain) {
+-	origin := req.Request.Header.Get(HEADER_Origin)
+-	if len(origin) == 0 {
+-		if trace {
+-			traceLogger.Println("no Http header Origin set")
+-		}
+-		chain.ProcessFilter(req, resp)
+-		return
+-	}
+-	if len(c.AllowedDomains) > 0 { // if provided then origin must be included
+-		included := false
+-		for _, each := range c.AllowedDomains {
+-			if each == origin {
+-				included = true
+-				break
+-			}
+-		}
+-		if !included {
+-			if trace {
+-				traceLogger.Println("HTTP Origin:%s is not part of %v", origin, c.AllowedDomains)
+-			}
+-			chain.ProcessFilter(req, resp)
+-			return
+-		}
+-	}
+-	if req.Request.Method != "OPTIONS" {
+-		c.doActualRequest(req, resp)
+-		chain.ProcessFilter(req, resp)
+-		return
+-	}
+-	if acrm := req.Request.Header.Get(HEADER_AccessControlRequestMethod); acrm != "" {
+-		c.doPreflightRequest(req, resp)
+-	} else {
+-		c.doActualRequest(req, resp)
+-	}
+-}
+-
+-func (c CrossOriginResourceSharing) doActualRequest(req *Request, resp *Response) {
+-	c.setOptionsHeaders(req, resp)
+-	// continue processing the response
+-}
+-
+-func (c CrossOriginResourceSharing) doPreflightRequest(req *Request, resp *Response) {
+-	if len(c.AllowedMethods) == 0 {
+-		c.AllowedMethods = c.Container.computeAllowedMethods(req)
+-	}
+-
+-	acrm := req.Request.Header.Get(HEADER_AccessControlRequestMethod)
+-	if !c.isValidAccessControlRequestMethod(acrm, c.AllowedMethods) {
+-		if trace {
+-			traceLogger.Printf("Http header %s:%s is not in %v",
+-				HEADER_AccessControlRequestMethod,
+-				acrm,
+-				c.AllowedMethods)
+-		}
+-		return
+-	}
+-	acrhs := req.Request.Header.Get(HEADER_AccessControlRequestHeaders)
+-	if len(acrhs) > 0 {
+-		for _, each := range strings.Split(acrhs, ",") {
+-			if !c.isValidAccessControlRequestHeader(strings.Trim(each, " ")) {
+-				if trace {
+-					traceLogger.Printf("Http header %s:%s is not in %v",
+-						HEADER_AccessControlRequestHeaders,
+-						acrhs,
+-						c.AllowedHeaders)
+-				}
+-				return
+-			}
+-		}
+-	}
+-	resp.AddHeader(HEADER_AccessControlAllowMethods, strings.Join(c.AllowedMethods, ","))
+-	resp.AddHeader(HEADER_AccessControlAllowHeaders, acrhs)
+-	c.setOptionsHeaders(req, resp)
+-
+-	// return http 200 response, no body
+-}
+-
+-func (c CrossOriginResourceSharing) setOptionsHeaders(req *Request, resp *Response) {
+-	c.checkAndSetExposeHeaders(resp)
+-	c.setAllowOriginHeader(req, resp)
+-	c.checkAndSetAllowCredentials(resp)
+-	if c.MaxAge > 0 {
+-		resp.AddHeader(HEADER_AccessControlMaxAge, strconv.Itoa(c.MaxAge))
+-	}
+-}
+-
+-func (c CrossOriginResourceSharing) isOriginAllowed(origin string) bool {
+-	if len(origin) == 0 {
+-		return false
+-	}
+-	if len(c.AllowedDomains) == 0 {
+-		return true
+-	}
+-	allowed := false
+-	for _, each := range c.AllowedDomains {
+-		if each == origin {
+-			allowed = true
+-			break
+-		}
+-	}
+-	return allowed
+-}
+-
+-func (c CrossOriginResourceSharing) setAllowOriginHeader(req *Request, resp *Response) {
+-	origin := req.Request.Header.Get(HEADER_Origin)
+-	if c.isOriginAllowed(origin) {
+-		resp.AddHeader(HEADER_AccessControlAllowOrigin, origin)
+-	}
+-}
+-
+-func (c CrossOriginResourceSharing) checkAndSetExposeHeaders(resp *Response) {
+-	if len(c.ExposeHeaders) > 0 {
+-		resp.AddHeader(HEADER_AccessControlExposeHeaders, strings.Join(c.ExposeHeaders, ","))
+-	}
+-}
+-
+-func (c CrossOriginResourceSharing) checkAndSetAllowCredentials(resp *Response) {
+-	if c.CookiesAllowed {
+-		resp.AddHeader(HEADER_AccessControlAllowCredentials, "true")
+-	}
+-}
+-
+-func (c CrossOriginResourceSharing) isValidAccessControlRequestMethod(method string, allowedMethods []string) bool {
+-	for _, each := range allowedMethods {
+-		if each == method {
+-			return true
+-		}
+-	}
+-	return false
+-}
+-
+-func (c CrossOriginResourceSharing) isValidAccessControlRequestHeader(header string) bool {
+-	for _, each := range c.AllowedHeaders {
+-		if strings.ToLower(each) == strings.ToLower(header) {
+-			return true
+-		}
+-	}
+-	return false
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/cors_filter_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/cors_filter_test.go
+deleted file mode 100644
+index 9b47230..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/cors_filter_test.go
++++ /dev/null
+@@ -1,125 +0,0 @@
+-package restful
+-
+-import (
+-	"net/http"
+-	"net/http/httptest"
+-	"testing"
+-)
+-
+-// go test -v -test.run TestCORSFilter_Preflight ...restful
+-// http://www.html5rocks.com/en/tutorials/cors/#toc-handling-a-not-so-simple-request
+-func TestCORSFilter_Preflight(t *testing.T) {
+-	tearDown()
+-	ws := new(WebService)
+-	ws.Route(ws.PUT("/cors").To(dummy))
+-	Add(ws)
+-
+-	cors := CrossOriginResourceSharing{
+-		ExposeHeaders:  []string{"X-Custom-Header"},
+-		AllowedHeaders: []string{"X-Custom-Header", "X-Additional-Header"},
+-		CookiesAllowed: true,
+-		Container:      DefaultContainer}
+-	Filter(cors.Filter)
+-
+-	// Preflight
+-	httpRequest, _ := http.NewRequest("OPTIONS", "http://api.alice.com/cors", nil)
+-	httpRequest.Method = "OPTIONS"
+-	httpRequest.Header.Set(HEADER_Origin, "http://api.bob.com")
+-	httpRequest.Header.Set(HEADER_AccessControlRequestMethod, "PUT")
+-	httpRequest.Header.Set(HEADER_AccessControlRequestHeaders, "X-Custom-Header, X-Additional-Header")
+-
+-	httpWriter := httptest.NewRecorder()
+-	DefaultContainer.dispatch(httpWriter, httpRequest)
+-
+-	actual := httpWriter.Header().Get(HEADER_AccessControlAllowOrigin)
+-	if "http://api.bob.com" != actual {
+-		t.Fatal("expected: http://api.bob.com but got:" + actual)
+-	}
+-	actual = httpWriter.Header().Get(HEADER_AccessControlAllowMethods)
+-	if "PUT" != actual {
+-		t.Fatal("expected: PUT but got:" + actual)
+-	}
+-	actual = httpWriter.Header().Get(HEADER_AccessControlAllowHeaders)
+-	if "X-Custom-Header, X-Additional-Header" != actual {
+-		t.Fatal("expected: X-Custom-Header, X-Additional-Header but got:" + actual)
+-	}
+-
+-	if !cors.isOriginAllowed("somewhere") {
+-		t.Fatal("origin expected to be allowed")
+-	}
+-	cors.AllowedDomains = []string{"overthere.com"}
+-	if cors.isOriginAllowed("somewhere") {
+-		t.Fatal("origin [somewhere] expected NOT to be allowed")
+-	}
+-	if !cors.isOriginAllowed("overthere.com") {
+-		t.Fatal("origin [overthere] expected to be allowed")
+-	}
+-
+-}
+-
+-// go test -v -test.run TestCORSFilter_Actual ...restful
+-// http://www.html5rocks.com/en/tutorials/cors/#toc-handling-a-not-so-simple-request
+-func TestCORSFilter_Actual(t *testing.T) {
+-	tearDown()
+-	ws := new(WebService)
+-	ws.Route(ws.PUT("/cors").To(dummy))
+-	Add(ws)
+-
+-	cors := CrossOriginResourceSharing{
+-		ExposeHeaders:  []string{"X-Custom-Header"},
+-		AllowedHeaders: []string{"X-Custom-Header", "X-Additional-Header"},
+-		CookiesAllowed: true,
+-		Container:      DefaultContainer}
+-	Filter(cors.Filter)
+-
+-	// Actual
+-	httpRequest, _ := http.NewRequest("PUT", "http://api.alice.com/cors", nil)
+-	httpRequest.Header.Set(HEADER_Origin, "http://api.bob.com")
+-	httpRequest.Header.Set("X-Custom-Header", "value")
+-
+-	httpWriter := httptest.NewRecorder()
+-	DefaultContainer.dispatch(httpWriter, httpRequest)
+-	actual := httpWriter.Header().Get(HEADER_AccessControlAllowOrigin)
+-	if "http://api.bob.com" != actual {
+-		t.Fatal("expected: http://api.bob.com but got:" + actual)
+-	}
+-	if httpWriter.Body.String() != "dummy" {
+-		t.Fatal("expected: dummy but got:" + httpWriter.Body.String())
+-	}
+-}
+-
+-var allowedDomainInput = []struct {
+-	domains  []string
+-	origin   string
+-	accepted bool
+-}{
+-	{[]string{}, "http://anything.com", true},
+-}
+-
+-// go test -v -test.run TestCORSFilter_AllowedDomains ...restful
+-func TestCORSFilter_AllowedDomains(t *testing.T) {
+-	for _, each := range allowedDomainInput {
+-		tearDown()
+-		ws := new(WebService)
+-		ws.Route(ws.PUT("/cors").To(dummy))
+-		Add(ws)
+-
+-		cors := CrossOriginResourceSharing{
+-			AllowedDomains: each.domains,
+-			CookiesAllowed: true,
+-			Container:      DefaultContainer}
+-		Filter(cors.Filter)
+-
+-		httpRequest, _ := http.NewRequest("PUT", "http://api.his.com/cors", nil)
+-		httpRequest.Header.Set(HEADER_Origin, each.origin)
+-		httpWriter := httptest.NewRecorder()
+-		DefaultContainer.dispatch(httpWriter, httpRequest)
+-		actual := httpWriter.Header().Get(HEADER_AccessControlAllowOrigin)
+-		if actual != each.origin && each.accepted {
+-			t.Fatal("expected to be accepted")
+-		}
+-		if actual == each.origin && !each.accepted {
+-			t.Fatal("did not expect to be accepted")
+-		}
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/coverage.sh b/Godeps/_workspace/src/github.com/emicklei/go-restful/coverage.sh
+deleted file mode 100644
+index e27dbf1..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/coverage.sh
++++ /dev/null
+@@ -1,2 +0,0 @@
+-go test -coverprofile=coverage.out
+-go tool cover -html=coverage.out
+\ No newline at end of file
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/curly.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/curly.go
+deleted file mode 100644
+index ce284f7..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/curly.go
++++ /dev/null
+@@ -1,162 +0,0 @@
+-package restful
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-import (
+-	"net/http"
+-	"regexp"
+-	"sort"
+-	"strings"
+-)
+-
+-// CurlyRouter expects Routes with paths that contain zero or more parameters in curly brackets.
+-type CurlyRouter struct{}
+-
+-// SelectRoute is part of the Router interface and returns the best match
+-// for the WebService and its Route for the given Request.
+-func (c CurlyRouter) SelectRoute(
+-	webServices []*WebService,
+-	httpRequest *http.Request) (selectedService *WebService, selected *Route, err error) {
+-
+-	requestTokens := tokenizePath(httpRequest.URL.Path)
+-
+-	detectedService := c.detectWebService(requestTokens, webServices)
+-	if detectedService == nil {
+-		if trace {
+-			traceLogger.Printf("no WebService was found to match URL path:%s\n", httpRequest.URL.Path)
+-		}
+-		return nil, nil, NewError(http.StatusNotFound, "404: Page Not Found")
+-	}
+-	candidateRoutes := c.selectRoutes(detectedService, requestTokens)
+-	if len(candidateRoutes) == 0 {
+-		if trace {
+-			traceLogger.Printf("no Route in WebService with path %s was found to match URL path:%s\n", detectedService.rootPath, httpRequest.URL.Path)
+-		}
+-		return detectedService, nil, NewError(http.StatusNotFound, "404: Page Not Found")
+-	}
+-	selectedRoute, err := c.detectRoute(candidateRoutes, httpRequest)
+-	if selectedRoute == nil {
+-		return detectedService, nil, err
+-	}
+-	return detectedService, selectedRoute, nil
+-}
+-
+-// selectRoutes return a collection of Route from a WebService that matches the path tokens from the request.
+-func (c CurlyRouter) selectRoutes(ws *WebService, requestTokens []string) []Route {
+-	candidates := &sortableCurlyRoutes{[]*curlyRoute{}}
+-	for _, each := range ws.routes {
+-		matches, paramCount, staticCount := c.matchesRouteByPathTokens(each.pathParts, requestTokens)
+-		if matches {
+-			candidates.add(&curlyRoute{each, paramCount, staticCount}) // TODO make sure Routes() return pointers?
+-		}
+-	}
+-	sort.Sort(sort.Reverse(candidates))
+-	return candidates.routes()
+-}
+-
+-// matchesRouteByPathTokens computes whether it matches, howmany parameters do match and what the number of static path elements are.
+-func (c CurlyRouter) matchesRouteByPathTokens(routeTokens, requestTokens []string) (matches bool, paramCount int, staticCount int) {
+-	if len(routeTokens) < len(requestTokens) {
+-		// proceed in matching only if last routeToken is wildcard
+-		count := len(routeTokens)
+-		if count == 0 || !strings.HasSuffix(routeTokens[count-1], "*}") {
+-			return false, 0, 0
+-		}
+-		// proceed
+-	}
+-	for i, routeToken := range routeTokens {
+-		if i == len(requestTokens) {
+-			// reached end of request path
+-			return false, 0, 0
+-		}
+-		requestToken := requestTokens[i]
+-		if strings.HasPrefix(routeToken, "{") {
+-			paramCount++
+-			if colon := strings.Index(routeToken, ":"); colon != -1 {
+-				// match by regex
+-				matchesToken, matchesRemainder := c.regularMatchesPathToken(routeToken, colon, requestToken)
+-				if !matchesToken {
+-					return false, 0, 0
+-				}
+-				if matchesRemainder {
+-					break
+-				}
+-			}
+-		} else { // no { prefix
+-			if requestToken != routeToken {
+-				return false, 0, 0
+-			}
+-			staticCount++
+-		}
+-	}
+-	return true, paramCount, staticCount
+-}
+-
+-// regularMatchesPathToken tests whether the regular expression part of routeToken matches the requestToken or all remaining tokens
+-// format routeToken is {someVar:someExpression}, e.g. {zipcode:[\d][\d][\d][\d][A-Z][A-Z]}
+-func (c CurlyRouter) regularMatchesPathToken(routeToken string, colon int, requestToken string) (matchesToken bool, matchesRemainder bool) {
+-	regPart := routeToken[colon+1 : len(routeToken)-1]
+-	if regPart == "*" {
+-		if trace {
+-			traceLogger.Printf("wildcard parameter detected in route token %s that matches %s\n", routeToken, requestToken)
+-		}
+-		return true, true
+-	}
+-	matched, err := regexp.MatchString(regPart, requestToken)
+-	return (matched && err == nil), false
+-}
+-
+-// detectRoute selectes from a list of Route the first match by inspecting both the Accept and Content-Type
+-// headers of the Request. See also RouterJSR311 in jsr311.go
+-func (c CurlyRouter) detectRoute(candidateRoutes []Route, httpRequest *http.Request) (*Route, error) {
+-	// tracing is done inside detectRoute
+-	return RouterJSR311{}.detectRoute(candidateRoutes, httpRequest)
+-}
+-
+-// detectWebService returns the best matching webService given the list of path tokens.
+-// see also computeWebserviceScore
+-func (c CurlyRouter) detectWebService(requestTokens []string, webServices []*WebService) *WebService {
+-	var best *WebService
+-	score := -1
+-	for _, each := range webServices {
+-		matches, eachScore := c.computeWebserviceScore(requestTokens, each.pathExpr.tokens)
+-		if matches && (eachScore > score) {
+-			best = each
+-			score = eachScore
+-		}
+-	}
+-	return best
+-}
+-
+-// computeWebserviceScore returns whether tokens match and
+-// the weighted score of the longest matching consecutive tokens from the beginning.
+-func (c CurlyRouter) computeWebserviceScore(requestTokens []string, tokens []string) (bool, int) {
+-	if len(tokens) > len(requestTokens) {
+-		return false, 0
+-	}
+-	score := 0
+-	for i := 0; i < len(tokens); i++ {
+-		each := requestTokens[i]
+-		other := tokens[i]
+-		if len(each) == 0 && len(other) == 0 {
+-			score++
+-			continue
+-		}
+-		if len(other) > 0 && strings.HasPrefix(other, "{") {
+-			// no empty match
+-			if len(each) == 0 {
+-				return false, score
+-			}
+-			score += 1
+-		} else {
+-			// not a parameter
+-			if each != other {
+-				return false, score
+-			}
+-			score += (len(tokens) - i) * 10 //fuzzy
+-		}
+-	}
+-	return true, score
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/curly_route.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/curly_route.go
+deleted file mode 100644
+index 3edab72..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/curly_route.go
++++ /dev/null
+@@ -1,54 +0,0 @@
+-package restful
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-// curlyRoute exits for sorting Routes by the CurlyRouter based on number of parameters and number of static path elements.
+-type curlyRoute struct {
+-	route       Route
+-	paramCount  int
+-	staticCount int
+-}
+-
+-type sortableCurlyRoutes struct {
+-	candidates []*curlyRoute
+-}
+-
+-func (s *sortableCurlyRoutes) add(route *curlyRoute) {
+-	s.candidates = append(s.candidates, route)
+-}
+-
+-func (s *sortableCurlyRoutes) routes() (routes []Route) {
+-	for _, each := range s.candidates {
+-		routes = append(routes, each.route) // TODO change return type
+-	}
+-	return routes
+-}
+-
+-func (s *sortableCurlyRoutes) Len() int {
+-	return len(s.candidates)
+-}
+-func (s *sortableCurlyRoutes) Swap(i, j int) {
+-	s.candidates[i], s.candidates[j] = s.candidates[j], s.candidates[i]
+-}
+-func (s *sortableCurlyRoutes) Less(i, j int) bool {
+-	ci := s.candidates[i]
+-	cj := s.candidates[j]
+-
+-	// primary key
+-	if ci.staticCount < cj.staticCount {
+-		return true
+-	}
+-	if ci.staticCount > cj.staticCount {
+-		return false
+-	}
+-	// secundary key
+-	if ci.paramCount < cj.paramCount {
+-		return true
+-	}
+-	if ci.paramCount > cj.paramCount {
+-		return false
+-	}
+-	return ci.route.Path < cj.route.Path
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/curly_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/curly_test.go
+deleted file mode 100644
+index 31d66dc..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/curly_test.go
++++ /dev/null
+@@ -1,231 +0,0 @@
+-package restful
+-
+-import (
+-	"io"
+-	"net/http"
+-	"testing"
+-)
+-
+-var requestPaths = []struct {
+-	// url with path (1) is handled by service with root (2) and remainder has value final (3)
+-	path, root string
+-}{
+-	{"/", "/"},
+-	{"/p", "/p"},
+-	{"/p/x", "/p/{q}"},
+-	{"/q/x", "/q"},
+-	{"/p/x/", "/p/{q}"},
+-	{"/p/x/y", "/p/{q}"},
+-	{"/q/x/y", "/q"},
+-	{"/z/q", "/{p}/q"},
+-	{"/a/b/c/q", "/"},
+-}
+-
+-// go test -v -test.run TestCurlyDetectWebService ...restful
+-func TestCurlyDetectWebService(t *testing.T) {
+-	ws1 := new(WebService).Path("/")
+-	ws2 := new(WebService).Path("/p")
+-	ws3 := new(WebService).Path("/q")
+-	ws4 := new(WebService).Path("/p/q")
+-	ws5 := new(WebService).Path("/p/{q}")
+-	ws7 := new(WebService).Path("/{p}/q")
+-	var wss = []*WebService{ws1, ws2, ws3, ws4, ws5, ws7}
+-
+-	for _, each := range wss {
+-		t.Logf("path=%s,toks=%v\n", each.pathExpr.Source, each.pathExpr.tokens)
+-	}
+-
+-	router := CurlyRouter{}
+-
+-	ok := true
+-	for i, fixture := range requestPaths {
+-		requestTokens := tokenizePath(fixture.path)
+-		who := router.detectWebService(requestTokens, wss)
+-		if who != nil && who.RootPath() != fixture.root {
+-			t.Logf("[line:%v] Unexpected dispatcher, expected:%v, actual:%v", i, fixture.root, who.RootPath())
+-			ok = false
+-		}
+-	}
+-	if !ok {
+-		t.Fail()
+-	}
+-}
+-
+-var serviceDetects = []struct {
+-	path  string
+-	found bool
+-	root  string
+-}{
+-	{"/a/b", true, "/{p}/{q}/{r}"},
+-	{"/p/q", true, "/p/q"},
+-	{"/q/p", true, "/q"},
+-	{"/", true, "/"},
+-	{"/p/q/r", true, "/p/q"},
+-}
+-
+-// go test -v -test.run Test_detectWebService ...restful
+-func Test_detectWebService(t *testing.T) {
+-	router := CurlyRouter{}
+-	ws1 := new(WebService).Path("/")
+-	ws2 := new(WebService).Path("/p")
+-	ws3 := new(WebService).Path("/q")
+-	ws4 := new(WebService).Path("/p/q")
+-	ws5 := new(WebService).Path("/p/{q}")
+-	ws6 := new(WebService).Path("/p/{q}/")
+-	ws7 := new(WebService).Path("/{p}/q")
+-	ws8 := new(WebService).Path("/{p}/{q}/{r}")
+-	var wss = []*WebService{ws8, ws7, ws6, ws5, ws4, ws3, ws2, ws1}
+-	for _, fix := range serviceDetects {
+-		requestPath := fix.path
+-		requestTokens := tokenizePath(requestPath)
+-		for _, ws := range wss {
+-			serviceTokens := ws.pathExpr.tokens
+-			matches, score := router.computeWebserviceScore(requestTokens, serviceTokens)
+-			t.Logf("req=%s,toks:%v,ws=%s,toks:%v,score=%d,matches=%v", requestPath, requestTokens, ws.RootPath(), serviceTokens, score, matches)
+-		}
+-		best := router.detectWebService(requestTokens, wss)
+-		if best != nil {
+-			if fix.found {
+-				t.Logf("best=%s", best.RootPath())
+-			} else {
+-				t.Fatalf("should have found:%s", fix.root)
+-			}
+-		}
+-	}
+-}
+-
+-var routeMatchers = []struct {
+-	route       string
+-	path        string
+-	matches     bool
+-	paramCount  int
+-	staticCount int
+-}{
+-	// route, request-path
+-	{"/a", "/a", true, 0, 1},
+-	{"/a", "/b", false, 0, 0},
+-	{"/a", "/b", false, 0, 0},
+-	{"/a/{b}/c/", "/a/2/c", true, 1, 2},
+-	{"/{a}/{b}/{c}/", "/a/b", false, 0, 0},
+-	{"/{x:*}", "/", false, 0, 0},
+-	{"/{x:*}", "/a", true, 1, 0},
+-	{"/{x:*}", "/a/b", true, 1, 0},
+-	{"/a/{x:*}", "/a/b", true, 1, 1},
+-	{"/a/{x:[A-Z][A-Z]}", "/a/ZX", true, 1, 1},
+-	{"/basepath/{resource:*}", "/basepath/some/other/location/test.xml", true, 1, 1},
+-}
+-
+-// clear && go test -v -test.run Test_matchesRouteByPathTokens ...restful
+-func Test_matchesRouteByPathTokens(t *testing.T) {
+-	router := CurlyRouter{}
+-	for i, each := range routeMatchers {
+-		routeToks := tokenizePath(each.route)
+-		reqToks := tokenizePath(each.path)
+-		matches, pCount, sCount := router.matchesRouteByPathTokens(routeToks, reqToks)
+-		if matches != each.matches {
+-			t.Fatalf("[%d] unexpected matches outcome route:%s, path:%s, matches:%v", i, each.route, each.path, matches)
+-		}
+-		if pCount != each.paramCount {
+-			t.Fatalf("[%d] unexpected paramCount got:%d want:%d ", i, pCount, each.paramCount)
+-		}
+-		if sCount != each.staticCount {
+-			t.Fatalf("[%d] unexpected staticCount got:%d want:%d ", i, sCount, each.staticCount)
+-		}
+-	}
+-}
+-
+-// clear && go test -v -test.run TestExtractParameters_Wildcard1 ...restful
+-func TestExtractParameters_Wildcard1(t *testing.T) {
+-	params := doExtractParams("/fixed/{var:*}", 2, "/fixed/remainder", t)
+-	if params["var"] != "remainder" {
+-		t.Errorf("parameter mismatch var: %s", params["var"])
+-	}
+-}
+-
+-// clear && go test -v -test.run TestExtractParameters_Wildcard2 ...restful
+-func TestExtractParameters_Wildcard2(t *testing.T) {
+-	params := doExtractParams("/fixed/{var:*}", 2, "/fixed/remain/der", t)
+-	if params["var"] != "remain/der" {
+-		t.Errorf("parameter mismatch var: %s", params["var"])
+-	}
+-}
+-
+-// clear && go test -v -test.run TestExtractParameters_Wildcard3 ...restful
+-func TestExtractParameters_Wildcard3(t *testing.T) {
+-	params := doExtractParams("/static/{var:*}", 2, "/static/test/sub/hi.html", t)
+-	if params["var"] != "test/sub/hi.html" {
+-		t.Errorf("parameter mismatch var: %s", params["var"])
+-	}
+-}
+-
+-// clear && go test -v -test.run TestCurly_ISSUE_34 ...restful
+-func TestCurly_ISSUE_34(t *testing.T) {
+-	ws1 := new(WebService).Path("/")
+-	ws1.Route(ws1.GET("/{type}/{id}").To(curlyDummy))
+-	ws1.Route(ws1.GET("/network/{id}").To(curlyDummy))
+-	routes := CurlyRouter{}.selectRoutes(ws1, tokenizePath("/network/12"))
+-	if len(routes) != 2 {
+-		t.Fatal("expected 2 routes")
+-	}
+-	if routes[0].Path != "/network/{id}" {
+-		t.Error("first is", routes[0].Path)
+-	}
+-}
+-
+-// clear && go test -v -test.run TestCurly_ISSUE_34_2 ...restful
+-func TestCurly_ISSUE_34_2(t *testing.T) {
+-	ws1 := new(WebService)
+-	ws1.Route(ws1.GET("/network/{id}").To(curlyDummy))
+-	ws1.Route(ws1.GET("/{type}/{id}").To(curlyDummy))
+-	routes := CurlyRouter{}.selectRoutes(ws1, tokenizePath("/network/12"))
+-	if len(routes) != 2 {
+-		t.Fatal("expected 2 routes")
+-	}
+-	if routes[0].Path != "/network/{id}" {
+-		t.Error("first is", routes[0].Path)
+-	}
+-}
+-
+-// clear && go test -v -test.run TestCurly_JsonHtml ...restful
+-func TestCurly_JsonHtml(t *testing.T) {
+-	ws1 := new(WebService)
+-	ws1.Path("/")
+-	ws1.Route(ws1.GET("/some.html").To(curlyDummy).Consumes("*/*").Produces("text/html"))
+-	req, _ := http.NewRequest("GET", "/some.html", nil)
+-	req.Header.Set("Accept", "application/json")
+-	_, route, err := CurlyRouter{}.SelectRoute([]*WebService{ws1}, req)
+-	if err == nil {
+-		t.Error("error expected")
+-	}
+-	if route != nil {
+-		t.Error("no route expected")
+-	}
+-}
+-
+-// go test -v -test.run TestCurly_ISSUE_137 ...restful
+-func TestCurly_ISSUE_137(t *testing.T) {
+-	ws1 := new(WebService)
+-	ws1.Route(ws1.GET("/hello").To(curlyDummy))
+-	ws1.Path("/")
+-	req, _ := http.NewRequest("GET", "/", nil)
+-	_, route, _ := CurlyRouter{}.SelectRoute([]*WebService{ws1}, req)
+-	t.Log(route)
+-	if route != nil {
+-		t.Error("no route expected")
+-	}
+-}
+-
+-// go test -v -test.run TestCurly_ISSUE_137_2 ...restful
+-func TestCurly_ISSUE_137_2(t *testing.T) {
+-	ws1 := new(WebService)
+-	ws1.Route(ws1.GET("/hello").To(curlyDummy))
+-	ws1.Path("/")
+-	req, _ := http.NewRequest("GET", "/hello/bob", nil)
+-	_, route, _ := CurlyRouter{}.SelectRoute([]*WebService{ws1}, req)
+-	t.Log(route)
+-	if route != nil {
+-		t.Errorf("no route expected, got %v", route)
+-	}
+-}
+-
+-func curlyDummy(req *Request, resp *Response) { io.WriteString(resp.ResponseWriter, "curlyDummy") }
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/doc.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/doc.go
+deleted file mode 100644
+index c095566..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/doc.go
++++ /dev/null
+@@ -1,184 +0,0 @@
+-/*
+-Package restful, a lean package for creating REST-style WebServices without magic.
+-
+-WebServices and Routes
+-
+-A WebService has a collection of Route objects that dispatch incoming Http Requests to a function calls.
+-Typically, a WebService has a root path (e.g. /users) and defines common MIME types for its routes.
+-WebServices must be added to a container (see below) in order to handler Http requests from a server.
+-
+-A Route is defined by a HTTP method, an URL path and (optionally) the MIME types it consumes (Content-Type) and produces (Accept).
+-This package has the logic to find the best matching Route and if found, call its Function.
+-
+-	ws := new(restful.WebService)
+-	ws.
+-		Path("/users").
+-		Consumes(restful.MIME_JSON, restful.MIME_XML).
+-		Produces(restful.MIME_JSON, restful.MIME_XML)
+-
+-	ws.Route(ws.GET("/{user-id}").To(u.findUser))  // u is a UserResource
+-
+-	...
+-
+-	// GET http://localhost:8080/users/1
+-	func (u UserResource) findUser(request *restful.Request, response *restful.Response) {
+-		id := request.PathParameter("user-id")
+-		...
+-	}
+-
+-The (*Request, *Response) arguments provide functions for reading information from the request and writing information back to the response.
+-
+-See the example https://github.com/emicklei/go-restful/blob/master/examples/restful-user-resource.go with a full implementation.
+-
+-Regular expression matching Routes
+-
+-A Route parameter can be specified using the format "uri/{var[:regexp]}" or the special version "uri/{var:*}" for matching the tail of the path.
+-For example, /persons/{name:[A-Z][A-Z]} can be used to restrict values for the parameter "name" to only contain capital alphabetic characters.
+-Regular expressions must use the standard Go syntax as described in the regexp package. (https://code.google.com/p/re2/wiki/Syntax)
+-This feature requires the use of a CurlyRouter.
+-
+-Containers
+-
+-A Container holds a collection of WebServices, Filters and a http.ServeMux for multiplexing http requests.
+-Using the statements "restful.Add(...) and restful.Filter(...)" will register WebServices and Filters to the Default Container.
+-The Default container of go-restful uses the http.DefaultServeMux.
+-You can create your own Container and create a new http.Server for that particular container.
+-
+-	container := restful.NewContainer()
+-	server := &http.Server{Addr: ":8081", Handler: container}
+-
+-Filters
+-
+-A filter dynamically intercepts requests and responses to transform or use the information contained in the requests or responses.
+-You can use filters to perform generic logging, measurement, authentication, redirect, set response headers etc.
+-In the restful package there are three hooks into the request,response flow where filters can be added.
+-Each filter must define a FilterFunction:
+-
+-	func (req *restful.Request, resp *restful.Response, chain *restful.FilterChain)
+-
+-Use the following statement to pass the request,response pair to the next filter or RouteFunction
+-
+-	chain.ProcessFilter(req, resp)
+-
+-Container Filters
+-
+-These are processed before any registered WebService.
+-
+-	// install a (global) filter for the default container (processed before any webservice)
+-	restful.Filter(globalLogging)
+-
+-WebService Filters
+-
+-These are processed before any Route of a WebService.
+-
+-	// install a webservice filter (processed before any route)
+-	ws.Filter(webserviceLogging).Filter(measureTime)
+-
+-
+-Route Filters
+-
+-These are processed before calling the function associated with the Route.
+-
+-	// install 2 chained route filters (processed before calling findUser)
+-	ws.Route(ws.GET("/{user-id}").Filter(routeLogging).Filter(NewCountFilter().routeCounter).To(findUser))
+-
+-See the example https://github.com/emicklei/go-restful/blob/master/examples/restful-filters.go with full implementations.
+-
+-Response Encoding
+-
+-Two encodings are supported: gzip and deflate. To enable this for all responses:
+-
+-	restful.DefaultContainer.EnableContentEncoding(true)
+-
+-If a Http request includes the Accept-Encoding header then the response content will be compressed using the specified encoding.
+-Alternatively, you can create a Filter that performs the encoding and install it per WebService or Route.
+-
+-See the example https://github.com/emicklei/go-restful/blob/master/examples/restful-encoding-filter.go
+-
+-OPTIONS support
+-
+-By installing a pre-defined container filter, your Webservice(s) can respond to the OPTIONS Http request.
+-
+-	Filter(OPTIONSFilter())
+-
+-CORS
+-
+-By installing the filter of a CrossOriginResourceSharing (CORS), your WebService(s) can handle CORS requests.
+-
+-	cors := CrossOriginResourceSharing{ExposeHeaders: []string{"X-My-Header"}, CookiesAllowed: false, Container: DefaultContainer}
+-	Filter(cors.Filter)
+-
+-Error Handling
+-
+-Unexpected things happen. If a request cannot be processed because of a failure, your service needs to tell via the response what happened and why.
+-For this reason HTTP status codes exist and it is important to use the correct code in every exceptional situation.
+-
+-	400: Bad Request
+-
+-If path or query parameters are not valid (content or type) then use http.StatusBadRequest.
+-
+-	404: Not Found
+-
+-Despite a valid URI, the resource requested may not be available
+-
+-	500: Internal Server Error
+-
+-If the application logic could not process the request (or write the response) then use http.StatusInternalServerError.
+-
+-	405: Method Not Allowed
+-
+-The request has a valid URL but the method (GET,PUT,POST,...) is not allowed.
+-
+-	406: Not Acceptable
+-
+-The request does not have or has an unknown Accept Header set for this operation.
+-
+-	415: Unsupported Media Type
+-
+-The request does not have or has an unknown Content-Type Header set for this operation.
+-
+-ServiceError
+-
+-In addition to setting the correct (error) Http status code, you can choose to write a ServiceError message on the response.
+-
+-Performance options
+-
+-This package has several options that affect the performance of your service. It is important to understand them and how you can change it.
+-
+-	restful.DefaultContainer.Router(CurlyRouter{})
+-
+-The default router is the RouterJSR311 which is an implementation of its spec (http://jsr311.java.net/nonav/releases/1.1/spec/spec.html).
+-However, it uses regular expressions for all its routes which, depending on your usecase, may consume a significant amount of time.
+-The CurlyRouter implementation is more lightweight that also allows you to use wildcards and expressions, but only if needed.
+-
+-	restful.DefaultContainer.DoNotRecover(true)
+-
+-DoNotRecover controls whether panics will be caught to return HTTP 500.
+-If set to true, Route functions are responsible for handling any error situation.
+-Default value is false; it will recover from panics. This has performance implications.
+-
+-	restful.SetCacheReadEntity(false)
+-
+-SetCacheReadEntity controls whether the response data ([]byte) is cached such that ReadEntity is repeatable.
+-If you expect to read large amounts of payload data, and you do not use this feature, you should set it to false.
+-
+-Trouble shooting
+-
+-This package has the means to produce detail logging of the complete Http request matching process and filter invocation.
+-Enabling this feature requires you to set a log.Logger instance such as:
+-
+-	restful.TraceLogger(log.New(os.Stdout, "[restful] ", log.LstdFlags|log.Lshortfile))
+-
+-Resources
+-
+-[project]: https://github.com/emicklei/go-restful
+-
+-[examples]: https://github.com/emicklei/go-restful/blob/master/examples
+-
+-[design]:  http://ernestmicklei.com/2012/11/11/go-restful-api-design/
+-
+-[showcases]: https://github.com/emicklei/mora, https://github.com/emicklei/landskape
+-
+-(c) 2012-2014, http://ernestmicklei.com. MIT License
+-*/
+-package restful
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/doc_examples_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/doc_examples_test.go
+deleted file mode 100644
+index e1a2f3b..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/doc_examples_test.go
++++ /dev/null
+@@ -1,35 +0,0 @@
+-package restful
+-
+-import "net/http"
+-
+-func ExampleOPTIONSFilter() {
+-	// Install the OPTIONS filter on the default Container
+-	Filter(OPTIONSFilter())
+-}
+-func ExampleContainer_OPTIONSFilter() {
+-	// Install the OPTIONS filter on a Container
+-	myContainer := new(Container)
+-	myContainer.Filter(myContainer.OPTIONSFilter)
+-}
+-
+-func ExampleContainer() {
+-	// The Default container of go-restful uses the http.DefaultServeMux.
+-	// You can create your own Container using restful.NewContainer() and create a new http.Server for that particular container
+-
+-	ws := new(WebService)
+-	wsContainer := NewContainer()
+-	wsContainer.Add(ws)
+-	server := &http.Server{Addr: ":8080", Handler: wsContainer}
+-	server.ListenAndServe()
+-}
+-
+-func ExampleCrossOriginResourceSharing() {
+-	// To install this filter on the Default Container use:
+-	cors := CrossOriginResourceSharing{ExposeHeaders: []string{"X-My-Header"}, CookiesAllowed: false, Container: DefaultContainer}
+-	Filter(cors.Filter)
+-}
+-
+-func ExampleServiceError() {
+-	resp := new(Response)
+-	resp.WriteEntity(NewError(http.StatusBadRequest, "Non-integer {id} path parameter"))
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/.goconvey b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/.goconvey
+deleted file mode 100644
+index 8485e98..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/.goconvey
++++ /dev/null
+@@ -1 +0,0 @@
+-ignore
+\ No newline at end of file
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/.goconvey b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/.goconvey
+deleted file mode 100644
+index 8485e98..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/.goconvey
++++ /dev/null
+@@ -1 +0,0 @@
+-ignore
+\ No newline at end of file
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/app.yaml b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/app.yaml
+deleted file mode 100644
+index 362db6b..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/app.yaml
++++ /dev/null
+@@ -1,20 +0,0 @@
+-#
+-# Include your application ID here
+-#
+-application: <your_app_id>
+-version: 1
+-runtime: go
+-api_version: go1
+-
+-handlers:
+-#
+-# Regex for all swagger files to make as static content.
+-# You should create the folder static/swagger and copy
+-# swagger-ui into it.
+-#
+-- url: /apidocs/(.*?)/(.*\.(js|html|css))
+-  static_files: static/swagger/\1/\2
+-  upload: static/swagger/(.*?)/(.*\.(js|html|css))
+-
+-- url: /.*
+-  script: _go_app
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/datastore/.goconvey b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/datastore/.goconvey
+deleted file mode 100644
+index 8485e98..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/datastore/.goconvey
++++ /dev/null
+@@ -1 +0,0 @@
+-ignore
+\ No newline at end of file
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/datastore/app.yaml b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/datastore/app.yaml
+deleted file mode 100644
+index 33883d1..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/datastore/app.yaml
++++ /dev/null
+@@ -1,18 +0,0 @@
+-application: datastore-example
+-version: 1
+-runtime: go
+-api_version: go1
+-
+-handlers:
+-# Regex for all swagger files to make as static content.
+-# You should create the folder static/swagger and copy
+-# swagger-ui into it.
+-#
+-- url: /apidocs/(.*?)/(.*\.(js|html|css))
+-  static_files: static/swagger/\1/\2
+-  upload: static/swagger/(.*?)/(.*\.(js|html|css))
+-
+-# Catch all.
+-- url: /.*
+-  script: _go_app
+-  login: required
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/datastore/main.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/datastore/main.go
+deleted file mode 100644
+index cf832ef..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/datastore/main.go
++++ /dev/null
+@@ -1,266 +0,0 @@
+-package main
+-
+-import (
+-	"appengine"
+-	"appengine/datastore"
+-	"appengine/user"
+-	"github.com/emicklei/go-restful"
+-	"github.com/emicklei/go-restful/swagger"
+-	"net/http"
+-	"time"
+-)
+-
+-// This example demonstrates a reasonably complete suite of RESTful operations backed
+-// by DataStore on Google App Engine.
+-
+-// Our simple example struct.
+-type Profile struct {
+-	LastModified time.Time `json:"-" xml:"-"`
+-	Email        string    `json:"-" xml:"-"`
+-	FirstName    string    `json:"first_name" xml:"first-name"`
+-	NickName     string    `json:"nick_name" xml:"nick-name"`
+-	LastName     string    `json:"last_name" xml:"last-name"`
+-}
+-
+-type ProfileApi struct {
+-	Path string
+-}
+-
+-func gaeUrl() string {
+-	if appengine.IsDevAppServer() {
+-		return "http://localhost:8080"
+-	} else {
+-		// Include your URL on App Engine here.
+-		// I found no way to get AppID without appengine.Context and this always
+-		// based on a http.Request.
+-		return "http://federatedservices.appspot.com"
+-	}
+-}
+-
+-func init() {
+-	u := ProfileApi{Path: "/profiles"}
+-	u.register()
+-
+-	// Optionally, you can install the Swagger Service which provides a nice Web UI on your REST API
+-	// You need to download the Swagger HTML5 assets and change the FilePath location in the config below.
+-	// Open <your_app_id>.appspot.com/apidocs and enter
+-	// Place the Swagger UI files into a folder called static/swagger if you wish to use Swagger
+-	// http://<your_app_id>.appspot.com/apidocs.json in the api input field.
+-	// For testing, you can use http://localhost:8080/apidocs.json
+-	config := swagger.Config{
+-		// You control what services are visible
+-		WebServices:    restful.RegisteredWebServices(),
+-		WebServicesUrl: gaeUrl(),
+-		ApiPath:        "/apidocs.json",
+-
+-		// Optionally, specifiy where the UI is located
+-		SwaggerPath: "/apidocs/",
+-
+-		// GAE support static content which is configured in your app.yaml.
+-		// This example expect the swagger-ui in static/swagger so you should place it there :)
+-		SwaggerFilePath: "static/swagger"}
+-	swagger.InstallSwaggerService(config)
+-}
+-
+-func (u ProfileApi) register() {
+-	ws := new(restful.WebService)
+-
+-	ws.
+-		Path(u.Path).
+-		// You can specify consumes and produces per route as well.
+-		Consumes(restful.MIME_JSON, restful.MIME_XML).
+-		Produces(restful.MIME_JSON, restful.MIME_XML)
+-
+-	ws.Route(ws.POST("").To(u.insert).
+-		// Swagger documentation.
+-		Doc("insert a new profile").
+-		Param(ws.BodyParameter("Profile", "representation of a profile").DataType("main.Profile")).
+-		Reads(Profile{}))
+-
+-	ws.Route(ws.GET("/{profile-id}").To(u.read).
+-		// Swagger documentation.
+-		Doc("read a profile").
+-		Param(ws.PathParameter("profile-id", "identifier for a profile").DataType("string")).
+-		Writes(Profile{}))
+-
+-	ws.Route(ws.PUT("/{profile-id}").To(u.update).
+-		// Swagger documentation.
+-		Doc("update an existing profile").
+-		Param(ws.PathParameter("profile-id", "identifier for a profile").DataType("string")).
+-		Param(ws.BodyParameter("Profile", "representation of a profile").DataType("main.Profile")).
+-		Reads(Profile{}))
+-
+-	ws.Route(ws.DELETE("/{profile-id}").To(u.remove).
+-		// Swagger documentation.
+-		Doc("remove a profile").
+-		Param(ws.PathParameter("profile-id", "identifier for a profile").DataType("string")))
+-
+-	restful.Add(ws)
+-}
+-
+-// POST http://localhost:8080/profiles
+-// {"first_name": "Ivan", "nick_name": "Socks", "last_name": "Hawkes"}
+-//
+-func (u *ProfileApi) insert(r *restful.Request, w *restful.Response) {
+-	c := appengine.NewContext(r.Request)
+-
+-	// Marshall the entity from the request into a struct.
+-	p := new(Profile)
+-	err := r.ReadEntity(&p)
+-	if err != nil {
+-		w.WriteError(http.StatusNotAcceptable, err)
+-		return
+-	}
+-
+-	// Ensure we start with a sensible value for this field.
+-	p.LastModified = time.Now()
+-
+-	// The profile belongs to this user.
+-	p.Email = user.Current(c).String()
+-
+-	k, err := datastore.Put(c, datastore.NewIncompleteKey(c, "profiles", nil), p)
+-	if err != nil {
+-		http.Error(w, err.Error(), http.StatusInternalServerError)
+-		return
+-	}
+-
+-	// Let them know the location of the newly created resource.
+-	// TODO: Use a safe Url path append function.
+-	w.AddHeader("Location", u.Path+"/"+k.Encode())
+-
+-	// Return the resultant entity.
+-	w.WriteHeader(http.StatusCreated)
+-	w.WriteEntity(p)
+-}
+-
+-// GET http://localhost:8080/profiles/ahdkZXZ-ZmVkZXJhdGlvbi1zZXJ2aWNlc3IVCxIIcHJvZmlsZXMYgICAgICAgAoM
+-//
+-func (u ProfileApi) read(r *restful.Request, w *restful.Response) {
+-	c := appengine.NewContext(r.Request)
+-
+-	// Decode the request parameter to determine the key for the entity.
+-	k, err := datastore.DecodeKey(r.PathParameter("profile-id"))
+-	if err != nil {
+-		http.Error(w, err.Error(), http.StatusBadRequest)
+-		return
+-	}
+-
+-	// Retrieve the entity from the datastore.
+-	p := Profile{}
+-	if err := datastore.Get(c, k, &p); err != nil {
+-		if err.Error() == "datastore: no such entity" {
+-			http.Error(w, err.Error(), http.StatusNotFound)
+-		} else {
+-			http.Error(w, err.Error(), http.StatusInternalServerError)
+-		}
+-		return
+-	}
+-
+-	// Check we own the profile before allowing them to view it.
+-	// Optionally, return a 404 instead to help prevent guessing ids.
+-	// TODO: Allow admins access.
+-	if p.Email != user.Current(c).String() {
+-		http.Error(w, "You do not have access to this resource", http.StatusForbidden)
+-		return
+-	}
+-
+-	w.WriteEntity(p)
+-}
+-
+-// PUT http://localhost:8080/profiles/ahdkZXZ-ZmVkZXJhdGlvbi1zZXJ2aWNlc3IVCxIIcHJvZmlsZXMYgICAgICAgAoM
+-// {"first_name": "Ivan", "nick_name": "Socks", "last_name": "Hawkes"}
+-//
+-func (u *ProfileApi) update(r *restful.Request, w *restful.Response) {
+-	c := appengine.NewContext(r.Request)
+-
+-	// Decode the request parameter to determine the key for the entity.
+-	k, err := datastore.DecodeKey(r.PathParameter("profile-id"))
+-	if err != nil {
+-		http.Error(w, err.Error(), http.StatusBadRequest)
+-		return
+-	}
+-
+-	// Marshall the entity from the request into a struct.
+-	p := new(Profile)
+-	err = r.ReadEntity(&p)
+-	if err != nil {
+-		w.WriteError(http.StatusNotAcceptable, err)
+-		return
+-	}
+-
+-	// Retrieve the old entity from the datastore.
+-	old := Profile{}
+-	if err := datastore.Get(c, k, &old); err != nil {
+-		if err.Error() == "datastore: no such entity" {
+-			http.Error(w, err.Error(), http.StatusNotFound)
+-		} else {
+-			http.Error(w, err.Error(), http.StatusInternalServerError)
+-		}
+-		return
+-	}
+-
+-	// Check we own the profile before allowing them to update it.
+-	// Optionally, return a 404 instead to help prevent guessing ids.
+-	// TODO: Allow admins access.
+-	if old.Email != user.Current(c).String() {
+-		http.Error(w, "You do not have access to this resource", http.StatusForbidden)
+-		return
+-	}
+-
+-	// Since the whole entity is re-written, we need to assign any invariant fields again
+-	// e.g. the owner of the entity.
+-	p.Email = user.Current(c).String()
+-
+-	// Keep track of the last modification date.
+-	p.LastModified = time.Now()
+-
+-	// Attempt to overwrite the old entity.
+-	_, err = datastore.Put(c, k, p)
+-	if err != nil {
+-		http.Error(w, err.Error(), http.StatusInternalServerError)
+-		return
+-	}
+-
+-	// Let them know it succeeded.
+-	w.WriteHeader(http.StatusNoContent)
+-}
+-
+-// DELETE http://localhost:8080/profiles/ahdkZXZ-ZmVkZXJhdGlvbi1zZXJ2aWNlc3IVCxIIcHJvZmlsZXMYgICAgICAgAoM
+-//
+-func (u *ProfileApi) remove(r *restful.Request, w *restful.Response) {
+-	c := appengine.NewContext(r.Request)
+-
+-	// Decode the request parameter to determine the key for the entity.
+-	k, err := datastore.DecodeKey(r.PathParameter("profile-id"))
+-	if err != nil {
+-		http.Error(w, err.Error(), http.StatusBadRequest)
+-		return
+-	}
+-
+-	// Retrieve the old entity from the datastore.
+-	old := Profile{}
+-	if err := datastore.Get(c, k, &old); err != nil {
+-		if err.Error() == "datastore: no such entity" {
+-			http.Error(w, err.Error(), http.StatusNotFound)
+-		} else {
+-			http.Error(w, err.Error(), http.StatusInternalServerError)
+-		}
+-		return
+-	}
+-
+-	// Check we own the profile before allowing them to delete it.
+-	// Optionally, return a 404 instead to help prevent guessing ids.
+-	// TODO: Allow admins access.
+-	if old.Email != user.Current(c).String() {
+-		http.Error(w, "You do not have access to this resource", http.StatusForbidden)
+-		return
+-	}
+-
+-	// Delete the entity.
+-	if err := datastore.Delete(c, k); err != nil {
+-		http.Error(w, err.Error(), http.StatusInternalServerError)
+-	}
+-
+-	// Success notification.
+-	w.WriteHeader(http.StatusNoContent)
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/restful-appstats-integration.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/restful-appstats-integration.go
+deleted file mode 100644
+index b3261ee..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/restful-appstats-integration.go
++++ /dev/null
+@@ -1,13 +0,0 @@
+-package main
+-
+-import (
+-	"github.com/mjibson/appstats"
+-)
+-
+-
+-func stats(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
+-	c := appstats.NewContext(req.Request)
+-	chain.ProcessFilter(req, resp)
+-	c.Stats.Status = resp.StatusCode()
+-	c.Save()
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/restful-user-service.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/restful-user-service.go
+deleted file mode 100644
+index e97ba2e..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/restful-user-service.go
++++ /dev/null
+@@ -1,161 +0,0 @@
+-package main
+-
+-import (
+-	"appengine"
+-	"appengine/memcache"
+-	"github.com/emicklei/go-restful"
+-	"github.com/emicklei/go-restful/swagger"
+-	"net/http"
+-)
+-
+-// This example is functionally the same as ../restful-user-service.go
+-// but it`s supposed to run on Goole App Engine (GAE)
+-//
+-// contributed by ivanhawkes
+-
+-type User struct {
+-	Id, Name string
+-}
+-
+-type UserService struct {
+-	// normally one would use DAO (data access object)
+-	// but in this example we simple use memcache.
+-}
+-
+-func (u UserService) Register() {
+-	ws := new(restful.WebService)
+-
+-	ws.
+-		Path("/users").
+-		Consumes(restful.MIME_XML, restful.MIME_JSON).
+-		Produces(restful.MIME_JSON, restful.MIME_XML) // you can specify this per route as well
+-
+-	ws.Route(ws.GET("/{user-id}").To(u.findUser).
+-		// docs
+-		Doc("get a user").
+-		Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")).
+-		Writes(User{})) // on the response
+-
+-	ws.Route(ws.PATCH("").To(u.updateUser).
+-		// docs
+-		Doc("update a user").
+-		Reads(User{})) // from the request
+-
+-	ws.Route(ws.PUT("/{user-id}").To(u.createUser).
+-		// docs
+-		Doc("create a user").
+-		Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")).
+-		Reads(User{})) // from the request
+-
+-	ws.Route(ws.DELETE("/{user-id}").To(u.removeUser).
+-		// docs
+-		Doc("delete a user").
+-		Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")))
+-
+-	restful.Add(ws)
+-}
+-
+-// GET http://localhost:8080/users/1
+-//
+-func (u UserService) findUser(request *restful.Request, response *restful.Response) {
+-	c := appengine.NewContext(request.Request)
+-	id := request.PathParameter("user-id")
+-	usr := new(User)
+-	_, err := memcache.Gob.Get(c, id, &usr)
+-	if err != nil || len(usr.Id) == 0 {
+-		response.WriteErrorString(http.StatusNotFound, "User could not be found.")
+-	} else {
+-		response.WriteEntity(usr)
+-	}
+-}
+-
+-// PATCH http://localhost:8080/users
+-// <User><Id>1</Id><Name>Melissa Raspberry</Name></User>
+-//
+-func (u *UserService) updateUser(request *restful.Request, response *restful.Response) {
+-	c := appengine.NewContext(request.Request)
+-	usr := new(User)
+-	err := request.ReadEntity(&usr)
+-	if err == nil {
+-		item := &memcache.Item{
+-			Key:    usr.Id,
+-			Object: &usr,
+-		}
+-		err = memcache.Gob.Set(c, item)
+-		if err != nil {
+-			response.WriteError(http.StatusInternalServerError, err)
+-			return
+-		}
+-		response.WriteEntity(usr)
+-	} else {
+-		response.WriteError(http.StatusInternalServerError, err)
+-	}
+-}
+-
+-// PUT http://localhost:8080/users/1
+-// <User><Id>1</Id><Name>Melissa</Name></User>
+-//
+-func (u *UserService) createUser(request *restful.Request, response *restful.Response) {
+-	c := appengine.NewContext(request.Request)
+-	usr := User{Id: request.PathParameter("user-id")}
+-	err := request.ReadEntity(&usr)
+-	if err == nil {
+-		item := &memcache.Item{
+-			Key:    usr.Id,
+-			Object: &usr,
+-		}
+-		err = memcache.Gob.Add(c, item)
+-		if err != nil {
+-			response.WriteError(http.StatusInternalServerError, err)
+-			return
+-		}
+-		response.WriteHeader(http.StatusCreated)
+-		response.WriteEntity(usr)
+-	} else {
+-		response.WriteError(http.StatusInternalServerError, err)
+-	}
+-}
+-
+-// DELETE http://localhost:8080/users/1
+-//
+-func (u *UserService) removeUser(request *restful.Request, response *restful.Response) {
+-	c := appengine.NewContext(request.Request)
+-	id := request.PathParameter("user-id")
+-	err := memcache.Delete(c, id)
+-	if err != nil {
+-		response.WriteError(http.StatusInternalServerError, err)
+-	}
+-}
+-
+-func getGaeURL() string {
+-	if appengine.IsDevAppServer() {
+-		return "http://localhost:8080"
+-	} else {
+-		/**
+-		 * Include your URL on App Engine here.
+-		 * I found no way to get AppID without appengine.Context and this always
+-		 * based on a http.Request.
+-		 */
+-		return "http://<your_app_id>.appspot.com"
+-	}
+-}
+-
+-func init() {
+-	u := UserService{}
+-	u.Register()
+-
+-	// Optionally, you can install the Swagger Service which provides a nice Web UI on your REST API
+-	// You need to download the Swagger HTML5 assets and change the FilePath location in the config below.
+-	// Open <your_app_id>.appspot.com/apidocs and enter http://<your_app_id>.appspot.com/apidocs.json in the api input field.
+-	config := swagger.Config{
+-		WebServices:    restful.RegisteredWebServices(), // you control what services are visible
+-		WebServicesUrl: getGaeURL(),
+-		ApiPath:        "/apidocs.json",
+-
+-		// Optionally, specifiy where the UI is located
+-		SwaggerPath: "/apidocs/",
+-		// GAE support static content which is configured in your app.yaml.
+-		// This example expect the swagger-ui in static/swagger so you should place it there :)
+-		SwaggerFilePath: "static/swagger"}
+-	swagger.InstallSwaggerService(config)
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/home.html b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/home.html
+deleted file mode 100644
+index e5d49b4..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/home.html
++++ /dev/null
+@@ -1,7 +0,0 @@
+-<!DOCTYPE html>
+-
+-<html>
+-<body>
+-	<h1>{{.Text}}</h1>
+-</body>
+-</html>
+\ No newline at end of file
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-CORS-filter.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-CORS-filter.go
+deleted file mode 100644
+index aacaa3d..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-CORS-filter.go
++++ /dev/null
+@@ -1,67 +0,0 @@
+-package main
+-
+-import (
+-	"io"
+-	"log"
+-	"net/http"
+-
+-	"github.com/emicklei/go-restful"
+-)
+-
+-// Cross-origin resource sharing (CORS) is a mechanism that allows JavaScript on a web page
+-// to make XMLHttpRequests to another domain, not the domain the JavaScript originated from.
+-//
+-// http://en.wikipedia.org/wiki/Cross-origin_resource_sharing
+-// http://enable-cors.org/server.html
+-//
+-// GET http://localhost:8080/users
+-//
+-// GET http://localhost:8080/users/1
+-//
+-// PUT http://localhost:8080/users/1
+-//
+-// DELETE http://localhost:8080/users/1
+-//
+-// OPTIONS http://localhost:8080/users/1  with Header "Origin" set to some domain and
+-
+-type UserResource struct{}
+-
+-func (u UserResource) RegisterTo(container *restful.Container) {
+-	ws := new(restful.WebService)
+-	ws.
+-		Path("/users").
+-		Consumes("*/*").
+-		Produces("*/*")
+-
+-	ws.Route(ws.GET("/{user-id}").To(u.nop))
+-	ws.Route(ws.POST("").To(u.nop))
+-	ws.Route(ws.PUT("/{user-id}").To(u.nop))
+-	ws.Route(ws.DELETE("/{user-id}").To(u.nop))
+-
+-	container.Add(ws)
+-}
+-
+-func (u UserResource) nop(request *restful.Request, response *restful.Response) {
+-	io.WriteString(response.ResponseWriter, "this would be a normal response")
+-}
+-
+-func main() {
+-	wsContainer := restful.NewContainer()
+-	u := UserResource{}
+-	u.RegisterTo(wsContainer)
+-
+-	// Add container filter to enable CORS
+-	cors := restful.CrossOriginResourceSharing{
+-		ExposeHeaders:  []string{"X-My-Header"},
+-		AllowedHeaders: []string{"Content-Type"},
+-		CookiesAllowed: false,
+-		Container:      wsContainer}
+-	wsContainer.Filter(cors.Filter)
+-
+-	// Add container filter to respond to OPTIONS
+-	wsContainer.Filter(wsContainer.OPTIONSFilter)
+-
+-	log.Printf("start listening on localhost:8080")
+-	server := &http.Server{Addr: ":8080", Handler: wsContainer}
+-	log.Fatal(server.ListenAndServe())
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-NCSA-logging.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-NCSA-logging.go
+deleted file mode 100644
+index 0cda50d..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-NCSA-logging.go
++++ /dev/null
+@@ -1,54 +0,0 @@
+-package main
+-
+-import (
+-	"github.com/emicklei/go-restful"
+-	"io"
+-	"log"
+-	"net/http"
+-	"os"
+-	"strings"
+-	"time"
+-)
+-
+-// This example shows how to create a filter that produces log lines
+-// according to the Common Log Format, also known as the NCSA standard.
+-//
+-// kindly contributed by leehambley
+-//
+-// GET http://localhost:8080/ping
+-
+-var logger *log.Logger = log.New(os.Stdout, "", 0)
+-
+-func NCSACommonLogFormatLogger() restful.FilterFunction {
+-	return func(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
+-		var username = "-"
+-		if req.Request.URL.User != nil {
+-			if name := req.Request.URL.User.Username(); name != "" {
+-				username = name
+-			}
+-		}
+-		chain.ProcessFilter(req, resp)
+-		logger.Printf("%s - %s [%s] \"%s %s %s\" %d %d",
+-			strings.Split(req.Request.RemoteAddr, ":")[0],
+-			username,
+-			time.Now().Format("02/Jan/2006:15:04:05 -0700"),
+-			req.Request.Method,
+-			req.Request.URL.RequestURI(),
+-			req.Request.Proto,
+-			resp.StatusCode(),
+-			resp.ContentLength(),
+-		)
+-	}
+-}
+-
+-func main() {
+-	ws := new(restful.WebService)
+-	ws.Filter(NCSACommonLogFormatLogger())
+-	ws.Route(ws.GET("/ping").To(hello))
+-	restful.Add(ws)
+-	http.ListenAndServe(":8080", nil)
+-}
+-
+-func hello(req *restful.Request, resp *restful.Response) {
+-	io.WriteString(resp, "pong")
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-basic-authentication.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-basic-authentication.go
+deleted file mode 100644
+index 5dd3067..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-basic-authentication.go
++++ /dev/null
+@@ -1,35 +0,0 @@
+-package main
+-
+-import (
+-	"github.com/emicklei/go-restful"
+-	"io"
+-	"net/http"
+-)
+-
+-// This example shows how to create a (Route) Filter that performs Basic Authentication on the Http request.
+-//
+-// GET http://localhost:8080/secret
+-// and use admin,admin for the credentials
+-
+-func main() {
+-	ws := new(restful.WebService)
+-	ws.Route(ws.GET("/secret").Filter(basicAuthenticate).To(secret))
+-	restful.Add(ws)
+-	http.ListenAndServe(":8080", nil)
+-}
+-
+-func basicAuthenticate(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
+-	encoded := req.Request.Header.Get("Authorization")
+-	// usr/pwd = admin/admin
+-	// real code does some decoding
+-	if len(encoded) == 0 || "Basic YWRtaW46YWRtaW4=" != encoded {
+-		resp.AddHeader("WWW-Authenticate", "Basic realm=Protected Area")
+-		resp.WriteErrorString(401, "401: Not Authorized")
+-		return
+-	}
+-	chain.ProcessFilter(req, resp)
+-}
+-
+-func secret(req *restful.Request, resp *restful.Response) {
+-	io.WriteString(resp, "42")
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-cpuprofiler-service.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-cpuprofiler-service.go
+deleted file mode 100644
+index 9148213..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-cpuprofiler-service.go
++++ /dev/null
+@@ -1,65 +0,0 @@
+-package main
+-
+-import (
+-	"github.com/emicklei/go-restful"
+-	"io"
+-	"log"
+-	"os"
+-	"runtime/pprof"
+-)
+-
+-// ProfilingService is a WebService that can start/stop a CPU profile and write results to a file
+-// 	GET /{rootPath}/start will activate CPU profiling
+-//	GET /{rootPath}/stop will stop profiling
+-//
+-// NewProfileService("/profiler", "ace.prof").AddWebServiceTo(restful.DefaultContainer)
+-//
+-type ProfilingService struct {
+-	rootPath   string   // the base (root) of the service, e.g. /profiler
+-	cpuprofile string   // the output filename to write profile results, e.g. myservice.prof
+-	cpufile    *os.File // if not nil, then profiling is active
+-}
+-
+-func NewProfileService(rootPath string, outputFilename string) *ProfilingService {
+-	ps := new(ProfilingService)
+-	ps.rootPath = rootPath
+-	ps.cpuprofile = outputFilename
+-	return ps
+-}
+-
+-// Add this ProfileService to a restful Container
+-func (p ProfilingService) AddWebServiceTo(container *restful.Container) {
+-	ws := new(restful.WebService)
+-	ws.Path(p.rootPath).Consumes("*/*").Produces(restful.MIME_JSON)
+-	ws.Route(ws.GET("/start").To(p.startProfiler))
+-	ws.Route(ws.GET("/stop").To(p.stopProfiler))
+-	container.Add(ws)
+-}
+-
+-func (p *ProfilingService) startProfiler(req *restful.Request, resp *restful.Response) {
+-	if p.cpufile != nil {
+-		io.WriteString(resp.ResponseWriter, "[restful] CPU profiling already running")
+-		return // error?
+-	}
+-	cpufile, err := os.Create(p.cpuprofile)
+-	if err != nil {
+-		log.Fatal(err)
+-	}
+-	// remember for close
+-	p.cpufile = cpufile
+-	pprof.StartCPUProfile(cpufile)
+-	io.WriteString(resp.ResponseWriter, "[restful] CPU profiling started, writing on:"+p.cpuprofile)
+-}
+-
+-func (p *ProfilingService) stopProfiler(req *restful.Request, resp *restful.Response) {
+-	if p.cpufile == nil {
+-		io.WriteString(resp.ResponseWriter, "[restful] CPU profiling not active")
+-		return // error?
+-	}
+-	pprof.StopCPUProfile()
+-	p.cpufile.Close()
+-	p.cpufile = nil
+-	io.WriteString(resp.ResponseWriter, "[restful] CPU profiling stopped, closing:"+p.cpuprofile)
+-}
+-
+-func main() {} // exists for example compilation only
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-curly-router.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-curly-router.go
+deleted file mode 100644
+index 1b95dd0..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-curly-router.go
++++ /dev/null
+@@ -1,107 +0,0 @@
+-package main
+-
+-import (
+-	"github.com/emicklei/go-restful"
+-	"log"
+-	"net/http"
+-)
+-
+-// This example has the same service definition as restful-user-resource
+-// but uses a different router (CurlyRouter) that does not use regular expressions
+-//
+-// POST http://localhost:8080/users
+-// <User><Id>1</Id><Name>Melissa Raspberry</Name></User>
+-//
+-// GET http://localhost:8080/users/1
+-//
+-// PUT http://localhost:8080/users/1
+-// <User><Id>1</Id><Name>Melissa</Name></User>
+-//
+-// DELETE http://localhost:8080/users/1
+-//
+-
+-type User struct {
+-	Id, Name string
+-}
+-
+-type UserResource struct {
+-	// normally one would use DAO (data access object)
+-	users map[string]User
+-}
+-
+-func (u UserResource) Register(container *restful.Container) {
+-	ws := new(restful.WebService)
+-	ws.
+-		Path("/users").
+-		Consumes(restful.MIME_XML, restful.MIME_JSON).
+-		Produces(restful.MIME_JSON, restful.MIME_XML) // you can specify this per route as well
+-
+-	ws.Route(ws.GET("/{user-id}").To(u.findUser))
+-	ws.Route(ws.POST("").To(u.updateUser))
+-	ws.Route(ws.PUT("/{user-id}").To(u.createUser))
+-	ws.Route(ws.DELETE("/{user-id}").To(u.removeUser))
+-
+-	container.Add(ws)
+-}
+-
+-// GET http://localhost:8080/users/1
+-//
+-func (u UserResource) findUser(request *restful.Request, response *restful.Response) {
+-	id := request.PathParameter("user-id")
+-	usr := u.users[id]
+-	if len(usr.Id) == 0 {
+-		response.AddHeader("Content-Type", "text/plain")
+-		response.WriteErrorString(http.StatusNotFound, "User could not be found.")
+-	} else {
+-		response.WriteEntity(usr)
+-	}
+-}
+-
+-// POST http://localhost:8080/users
+-// <User><Id>1</Id><Name>Melissa Raspberry</Name></User>
+-//
+-func (u *UserResource) updateUser(request *restful.Request, response *restful.Response) {
+-	usr := new(User)
+-	err := request.ReadEntity(&usr)
+-	if err == nil {
+-		u.users[usr.Id] = *usr
+-		response.WriteEntity(usr)
+-	} else {
+-		response.AddHeader("Content-Type", "text/plain")
+-		response.WriteErrorString(http.StatusInternalServerError, err.Error())
+-	}
+-}
+-
+-// PUT http://localhost:8080/users/1
+-// <User><Id>1</Id><Name>Melissa</Name></User>
+-//
+-func (u *UserResource) createUser(request *restful.Request, response *restful.Response) {
+-	usr := User{Id: request.PathParameter("user-id")}
+-	err := request.ReadEntity(&usr)
+-	if err == nil {
+-		u.users[usr.Id] = usr
+-		response.WriteHeader(http.StatusCreated)
+-		response.WriteEntity(usr)
+-	} else {
+-		response.AddHeader("Content-Type", "text/plain")
+-		response.WriteErrorString(http.StatusInternalServerError, err.Error())
+-	}
+-}
+-
+-// DELETE http://localhost:8080/users/1
+-//
+-func (u *UserResource) removeUser(request *restful.Request, response *restful.Response) {
+-	id := request.PathParameter("user-id")
+-	delete(u.users, id)
+-}
+-
+-func main() {
+-	wsContainer := restful.NewContainer()
+-	wsContainer.Router(restful.CurlyRouter{})
+-	u := UserResource{map[string]User{}}
+-	u.Register(wsContainer)
+-
+-	log.Printf("start listening on localhost:8080")
+-	server := &http.Server{Addr: ":8080", Handler: wsContainer}
+-	log.Fatal(server.ListenAndServe())
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-encoding-filter.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-encoding-filter.go
+deleted file mode 100644
+index 6094c49..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-encoding-filter.go
++++ /dev/null
+@@ -1,61 +0,0 @@
+-package main
+-
+-import (
+-	"github.com/emicklei/go-restful"
+-	"log"
+-	"net/http"
+-)
+-
+-type User struct {
+-	Id, Name string
+-}
+-
+-type UserList struct {
+-	Users []User
+-}
+-
+-//
+-// This example shows how to use the CompressingResponseWriter by a Filter
+-// such that encoding can be enabled per WebService or per Route (instead of per container)
+-// Using restful.DefaultContainer.EnableContentEncoding(true) will encode all responses served by WebServices in the DefaultContainer.
+-//
+-// Set Accept-Encoding to gzip or deflate
+-// GET http://localhost:8080/users/42
+-// and look at the response headers
+-
+-func main() {
+-	restful.Add(NewUserService())
+-	log.Printf("start listening on localhost:8080")
+-	log.Fatal(http.ListenAndServe(":8080", nil))
+-}
+-
+-func NewUserService() *restful.WebService {
+-	ws := new(restful.WebService)
+-	ws.
+-		Path("/users").
+-		Consumes(restful.MIME_XML, restful.MIME_JSON).
+-		Produces(restful.MIME_JSON, restful.MIME_XML)
+-
+-	// install a response encoding filter
+-	ws.Route(ws.GET("/{user-id}").Filter(encodingFilter).To(findUser))
+-	return ws
+-}
+-
+-// Route Filter (defines FilterFunction)
+-func encodingFilter(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
+-	log.Printf("[encoding-filter] %s,%s\n", req.Request.Method, req.Request.URL)
+-	// wrap responseWriter into a compressing one
+-	compress, _ := restful.NewCompressingResponseWriter(resp.ResponseWriter, restful.ENCODING_GZIP)
+-	resp.ResponseWriter = compress
+-	defer func() {
+-		compress.Close()
+-	}()
+-	chain.ProcessFilter(req, resp)
+-}
+-
+-// GET http://localhost:8080/users/42
+-//
+-func findUser(request *restful.Request, response *restful.Response) {
+-	log.Printf("findUser")
+-	response.WriteEntity(User{"42", "Gandalf"})
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-filters.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-filters.go
+deleted file mode 100644
+index 47e1146..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-filters.go
++++ /dev/null
+@@ -1,114 +0,0 @@
+-package main
+-
+-import (
+-	"github.com/emicklei/go-restful"
+-	"log"
+-	"net/http"
+-	"time"
+-)
+-
+-type User struct {
+-	Id, Name string
+-}
+-
+-type UserList struct {
+-	Users []User
+-}
+-
+-// This example show how to create and use the three different Filters (Container,WebService and Route)
+-// When applied to the restful.DefaultContainer, we refer to them as a global filter.
+-//
+-// GET  http://locahost:8080/users/42
+-// and see the logging per filter (try repeating this request)
+-
+-func main() {
+-	// install a global (=DefaultContainer) filter (processed before any webservice in the DefaultContainer)
+-	restful.Filter(globalLogging)
+-
+-	restful.Add(NewUserService())
+-	log.Printf("start listening on localhost:8080")
+-	log.Fatal(http.ListenAndServe(":8080", nil))
+-}
+-
+-func NewUserService() *restful.WebService {
+-	ws := new(restful.WebService)
+-	ws.
+-		Path("/users").
+-		Consumes(restful.MIME_XML, restful.MIME_JSON).
+-		Produces(restful.MIME_JSON, restful.MIME_XML)
+-
+-	// install a webservice filter (processed before any route)
+-	ws.Filter(webserviceLogging).Filter(measureTime)
+-
+-	// install a counter filter
+-	ws.Route(ws.GET("").Filter(NewCountFilter().routeCounter).To(getAllUsers))
+-
+-	// install 2 chained route filters (processed before calling findUser)
+-	ws.Route(ws.GET("/{user-id}").Filter(routeLogging).Filter(NewCountFilter().routeCounter).To(findUser))
+-	return ws
+-}
+-
+-// Global Filter
+-func globalLogging(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
+-	log.Printf("[global-filter (logger)] %s,%s\n", req.Request.Method, req.Request.URL)
+-	chain.ProcessFilter(req, resp)
+-}
+-
+-// WebService Filter
+-func webserviceLogging(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
+-	log.Printf("[webservice-filter (logger)] %s,%s\n", req.Request.Method, req.Request.URL)
+-	chain.ProcessFilter(req, resp)
+-}
+-
+-// WebService (post-process) Filter (as a struct that defines a FilterFunction)
+-func measureTime(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
+-	now := time.Now()
+-	chain.ProcessFilter(req, resp)
+-	log.Printf("[webservice-filter (timer)] %v\n", time.Now().Sub(now))
+-}
+-
+-// Route Filter (defines FilterFunction)
+-func routeLogging(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
+-	log.Printf("[route-filter (logger)] %s,%s\n", req.Request.Method, req.Request.URL)
+-	chain.ProcessFilter(req, resp)
+-}
+-
+-// Route Filter (as a struct that defines a FilterFunction)
+-// CountFilter implements a FilterFunction for counting requests.
+-type CountFilter struct {
+-	count   int
+-	counter chan int // for go-routine safe count increments
+-}
+-
+-// NewCountFilter creates and initializes a new CountFilter.
+-func NewCountFilter() *CountFilter {
+-	c := new(CountFilter)
+-	c.counter = make(chan int)
+-	go func() {
+-		for {
+-			c.count += <-c.counter
+-		}
+-	}()
+-	return c
+-}
+-
+-// routeCounter increments the count of the filter (through a channel)
+-func (c *CountFilter) routeCounter(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
+-	c.counter <- 1
+-	log.Printf("[route-filter (counter)] count:%d", c.count)
+-	chain.ProcessFilter(req, resp)
+-}
+-
+-// GET http://localhost:8080/users
+-//
+-func getAllUsers(request *restful.Request, response *restful.Response) {
+-	log.Printf("getAllUsers")
+-	response.WriteEntity(UserList{[]User{User{"42", "Gandalf"}, User{"3.14", "Pi"}}})
+-}
+-
+-// GET http://localhost:8080/users/42
+-//
+-func findUser(request *restful.Request, response *restful.Response) {
+-	log.Printf("findUser")
+-	response.WriteEntity(User{"42", "Gandalf"})
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-form-handling.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-form-handling.go
+deleted file mode 100644
+index a83db44..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-form-handling.go
++++ /dev/null
+@@ -1,62 +0,0 @@
+-package main
+-
+-import (
+-	"fmt"
+-	"github.com/emicklei/go-restful"
+-	"github.com/gorilla/schema"
+-	"io"
+-	"net/http"
+-)
+-
+-// This example shows how to handle a POST of a HTML form that uses the standard x-www-form-urlencoded content-type.
+-// It uses the gorilla web tool kit schema package to decode the form data into a struct.
+-//
+-// GET http://localhost:8080/profiles
+-//
+-
+-type Profile struct {
+-	Name string
+-	Age  int
+-}
+-
+-var decoder *schema.Decoder
+-
+-func main() {
+-	decoder = schema.NewDecoder()
+-	ws := new(restful.WebService)
+-	ws.Route(ws.POST("/profiles").Consumes("application/x-www-form-urlencoded").To(postAdddress))
+-	ws.Route(ws.GET("/profiles").To(addresssForm))
+-	restful.Add(ws)
+-	http.ListenAndServe(":8080", nil)
+-}
+-
+-func postAdddress(req *restful.Request, resp *restful.Response) {
+-	err := req.Request.ParseForm()
+-	if err != nil {
+-		resp.WriteErrorString(http.StatusBadRequest, err.Error())
+-		return
+-	}
+-	p := new(Profile)
+-	err = decoder.Decode(p, req.Request.PostForm)
+-	if err != nil {
+-		resp.WriteErrorString(http.StatusBadRequest, err.Error())
+-		return
+-	}
+-	io.WriteString(resp.ResponseWriter, fmt.Sprintf("<html><body>Name=%s, Age=%d</body></html>", p.Name, p.Age))
+-}
+-
+-func addresssForm(req *restful.Request, resp *restful.Response) {
+-	io.WriteString(resp.ResponseWriter,
+-		`<html>
+-		<body>
+-		<h1>Enter Profile</h1>
+-		<form method="post">
+-		    <label>Name:</label>
+-			<input type="text" name="Name"/>
+-			<label>Age:</label>
+-		    <input type="text" name="Age"/>
+-			<input type="Submit" />
+-		</form>
+-		</body>
+-		</html>`)
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-hello-world.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-hello-world.go
+deleted file mode 100644
+index a21c2a6..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-hello-world.go
++++ /dev/null
+@@ -1,22 +0,0 @@
+-package main
+-
+-import (
+-	"github.com/emicklei/go-restful"
+-	"io"
+-	"net/http"
+-)
+-
+-// This example shows the minimal code needed to get a restful.WebService working.
+-//
+-// GET http://localhost:8080/hello
+-
+-func main() {
+-	ws := new(restful.WebService)
+-	ws.Route(ws.GET("/hello").To(hello))
+-	restful.Add(ws)
+-	http.ListenAndServe(":8080", nil)
+-}
+-
+-func hello(req *restful.Request, resp *restful.Response) {
+-	io.WriteString(resp, "world")
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-html-template.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-html-template.go
+deleted file mode 100644
+index de51c59..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-html-template.go
++++ /dev/null
+@@ -1,35 +0,0 @@
+-package main
+-
+-import (
+-	"log"
+-	"net/http"
+-	"text/template"
+-
+-	"github.com/emicklei/go-restful"
+-)
+-
+-// This example shows how to serve a HTML page using the standard Go template engine.
+-//
+-// GET http://localhost:8080/
+-
+-func main() {
+-	ws := new(restful.WebService)
+-	ws.Route(ws.GET("/").To(home))
+-	restful.Add(ws)
+-	print("open browser on http://localhost:8080/\n")
+-	http.ListenAndServe(":8080", nil)
+-}
+-
+-type Message struct {
+-	Text string
+-}
+-
+-func home(req *restful.Request, resp *restful.Response) {
+-	p := &Message{"restful-html-template demo"}
+-	// you might want to cache compiled templates
+-	t, err := template.ParseFiles("home.html")
+-	if err != nil {
+-		log.Fatalf("Template gave: %s", err)
+-	}
+-	t.Execute(resp.ResponseWriter, p)
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-multi-containers.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-multi-containers.go
+deleted file mode 100644
+index 3f1650b..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-multi-containers.go
++++ /dev/null
+@@ -1,43 +0,0 @@
+-package main
+-
+-import (
+-	"github.com/emicklei/go-restful"
+-	"io"
+-	"log"
+-	"net/http"
+-)
+-
+-// This example shows how to have a program with 2 WebServices containers
+-// each having a http server listening on its own port.
+-//
+-// The first "hello" is added to the restful.DefaultContainer (and uses DefaultServeMux)
+-// For the second "hello", a new container and ServeMux is created
+-// and requires a new http.Server with the container being the Handler.
+-// This first server is spawn in its own go-routine such that the program proceeds to create the second.
+-//
+-// GET http://localhost:8080/hello
+-// GET http://localhost:8081/hello
+-
+-func main() {
+-	ws := new(restful.WebService)
+-	ws.Route(ws.GET("/hello").To(hello))
+-	restful.Add(ws)
+-	go func() {
+-		http.ListenAndServe(":8080", nil)
+-	}()
+-
+-	container2 := restful.NewContainer()
+-	ws2 := new(restful.WebService)
+-	ws2.Route(ws2.GET("/hello").To(hello2))
+-	container2.Add(ws2)
+-	server := &http.Server{Addr: ":8081", Handler: container2}
+-	log.Fatal(server.ListenAndServe())
+-}
+-
+-func hello(req *restful.Request, resp *restful.Response) {
+-	io.WriteString(resp, "default world")
+-}
+-
+-func hello2(req *restful.Request, resp *restful.Response) {
+-	io.WriteString(resp, "second world")
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-options-filter.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-options-filter.go
+deleted file mode 100644
+index 73dc3cf..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-options-filter.go
++++ /dev/null
+@@ -1,51 +0,0 @@
+-package main
+-
+-import (
+-	"github.com/emicklei/go-restful"
+-	"io"
+-	"log"
+-	"net/http"
+-)
+-
+-// This example shows how to use the OPTIONSFilter on a Container
+-//
+-// OPTIONS http://localhost:8080/users
+-//
+-// OPTIONS http://localhost:8080/users/1
+-
+-type UserResource struct{}
+-
+-func (u UserResource) RegisterTo(container *restful.Container) {
+-	ws := new(restful.WebService)
+-	ws.
+-		Path("/users").
+-		Consumes("*/*").
+-		Produces("*/*")
+-
+-	ws.Route(ws.GET("/{user-id}").To(u.nop))
+-	ws.Route(ws.POST("").To(u.nop))
+-	ws.Route(ws.PUT("/{user-id}").To(u.nop))
+-	ws.Route(ws.DELETE("/{user-id}").To(u.nop))
+-
+-	container.Add(ws)
+-}
+-
+-func (u UserResource) nop(request *restful.Request, response *restful.Response) {
+-	io.WriteString(response.ResponseWriter, "this would be a normal response")
+-}
+-
+-func main() {
+-	wsContainer := restful.NewContainer()
+-	u := UserResource{}
+-	u.RegisterTo(wsContainer)
+-
+-	// Add container filter to respond to OPTIONS
+-	wsContainer.Filter(wsContainer.OPTIONSFilter)
+-
+-	// For use on the default container, you can write
+-	// restful.Filter(restful.OPTIONSFilter())
+-
+-	log.Printf("start listening on localhost:8080")
+-	server := &http.Server{Addr: ":8080", Handler: wsContainer}
+-	log.Fatal(server.ListenAndServe())
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-path-tail.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-path-tail.go
+deleted file mode 100644
+index 8488a23..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-path-tail.go
++++ /dev/null
+@@ -1,26 +0,0 @@
+-package main
+-
+-import (
+-	"io"
+-	"net/http"
+-	. "github.com/emicklei/go-restful"
+-)
+-
+-// This example shows how to a Route that matches the "tail" of a path.
+-// Requires the use of a CurlyRouter and the star "*" path parameter pattern.
+-//
+-// GET http://localhost:8080/basepath/some/other/location/test.xml
+-
+-func main() {
+-	DefaultContainer.Router(CurlyRouter{})
+-	ws := new(WebService)
+-	ws.Route(ws.GET("/basepath/{resource:*}").To(staticFromPathParam))
+-	Add(ws)
+-
+-	println("[go-restful] serve path tails from http://localhost:8080/basepath")
+-	http.ListenAndServe(":8080", nil)
+-}
+-
+-func staticFromPathParam(req *Request, resp *Response) {
+-	io.WriteString(resp, "Tail="+req.PathParameter("resource"))
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-pre-post-filters.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-pre-post-filters.go
+deleted file mode 100644
+index 0b55f14..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-pre-post-filters.go
++++ /dev/null
+@@ -1,98 +0,0 @@
+-package main
+-
+-import (
+-	"github.com/emicklei/go-restful"
+-	"io"
+-	"log"
+-	"net/http"
+-)
+-
+-// This example shows how the different types of filters are called in the request-response flow.
+-// The call chain is logged on the console when sending an http request.
+-//
+-// GET http://localhost:8080/1
+-// GET http://localhost:8080/2
+-
+-var indentLevel int
+-
+-func container_filter_A(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
+-	log.Printf("url path:%v\n", req.Request.URL)
+-	trace("container_filter_A: before", 1)
+-	chain.ProcessFilter(req, resp)
+-	trace("container_filter_A: after", -1)
+-}
+-
+-func container_filter_B(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
+-	trace("container_filter_B: before", 1)
+-	chain.ProcessFilter(req, resp)
+-	trace("container_filter_B: after", -1)
+-}
+-
+-func service_filter_A(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
+-	trace("service_filter_A: before", 1)
+-	chain.ProcessFilter(req, resp)
+-	trace("service_filter_A: after", -1)
+-}
+-
+-func service_filter_B(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
+-	trace("service_filter_B: before", 1)
+-	chain.ProcessFilter(req, resp)
+-	trace("service_filter_B: after", -1)
+-}
+-
+-func route_filter_A(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
+-	trace("route_filter_A: before", 1)
+-	chain.ProcessFilter(req, resp)
+-	trace("route_filter_A: after", -1)
+-}
+-
+-func route_filter_B(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
+-	trace("route_filter_B: before", 1)
+-	chain.ProcessFilter(req, resp)
+-	trace("route_filter_B: after", -1)
+-}
+-
+-func trace(what string, delta int) {
+-	indented := what
+-	if delta < 0 {
+-		indentLevel += delta
+-	}
+-	for t := 0; t < indentLevel; t++ {
+-		indented = "." + indented
+-	}
+-	log.Printf("%s", indented)
+-	if delta > 0 {
+-		indentLevel += delta
+-	}
+-}
+-
+-func main() {
+-	restful.Filter(container_filter_A)
+-	restful.Filter(container_filter_B)
+-
+-	ws1 := new(restful.WebService)
+-	ws1.Path("/1")
+-	ws1.Filter(service_filter_A)
+-	ws1.Filter(service_filter_B)
+-	ws1.Route(ws1.GET("").To(doit1).Filter(route_filter_A).Filter(route_filter_B))
+-
+-	ws2 := new(restful.WebService)
+-	ws2.Path("/2")
+-	ws2.Filter(service_filter_A)
+-	ws2.Filter(service_filter_B)
+-	ws2.Route(ws2.GET("").To(doit2).Filter(route_filter_A).Filter(route_filter_B))
+-
+-	restful.Add(ws1)
+-	restful.Add(ws2)
+-
+-	log.Print("go-restful example listing on http://localhost:8080/1 and http://localhost:8080/2")
+-	log.Fatal(http.ListenAndServe(":8080", nil))
+-}
+-
+-func doit1(req *restful.Request, resp *restful.Response) {
+-	io.WriteString(resp, "nothing to see in 1")
+-}
+-
+-func doit2(req *restful.Request, resp *restful.Response) {
+-	io.WriteString(resp, "nothing to see in 2")
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-resource-functions.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-resource-functions.go
+deleted file mode 100644
+index fb1012a..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-resource-functions.go
++++ /dev/null
+@@ -1,63 +0,0 @@
+-package main
+-
+-import (
+-	"github.com/emicklei/go-restful"
+-	"log"
+-	"net/http"
+-)
+-
+-// This example shows how to use methods as RouteFunctions for WebServices.
+-// The ProductResource has a Register() method that creates and initializes
+-// a WebService to expose its methods as REST operations.
+-// The WebService is added to the restful.DefaultContainer.
+-// A ProductResource is typically created using some data access object.
+-//
+-// GET http://localhost:8080/products/1
+-// POST http://localhost:8080/products
+-// <Product><Id>1</Id><Title>The First</Title></Product>
+-
+-type Product struct {
+-	Id, Title string
+-}
+-
+-type ProductResource struct {
+-	// typically reference a DAO (data-access-object)
+-}
+-
+-func (p ProductResource) getOne(req *restful.Request, resp *restful.Response) {
+-	id := req.PathParameter("id")
+-	log.Println("getting product with id:" + id)
+-	resp.WriteEntity(Product{Id: id, Title: "test"})
+-}
+-
+-func (p ProductResource) postOne(req *restful.Request, resp *restful.Response) {
+-	updatedProduct := new(Product)
+-	err := req.ReadEntity(updatedProduct)
+-	if err != nil { // bad request
+-		resp.WriteErrorString(http.StatusBadRequest, err.Error())
+-		return
+-	}
+-	log.Println("updating product with id:" + updatedProduct.Id)
+-}
+-
+-func (p ProductResource) Register() {
+-	ws := new(restful.WebService)
+-	ws.Path("/products")
+-	ws.Consumes(restful.MIME_XML)
+-	ws.Produces(restful.MIME_XML)
+-
+-	ws.Route(ws.GET("/{id}").To(p.getOne).
+-		Doc("get the product by its id").
+-		Param(ws.PathParameter("id", "identifier of the product").DataType("string")))
+-
+-	ws.Route(ws.POST("").To(p.postOne).
+-		Doc("update or create a product").
+-		Param(ws.BodyParameter("Product", "a Product (XML)").DataType("main.Product")))
+-
+-	restful.Add(ws)
+-}
+-
+-func main() {
+-	ProductResource{}.Register()
+-	http.ListenAndServe(":8080", nil)
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-route_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-route_test.go
+deleted file mode 100644
+index 20c366b..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-route_test.go
++++ /dev/null
+@@ -1,39 +0,0 @@
+-package main
+-
+-import (
+-	"net/http"
+-	"net/http/httptest"
+-	"strings"
+-	"testing"
+-
+-	"github.com/emicklei/go-restful"
+-)
+-
+-var (
+-	Result string
+-)
+-
+-func TestRouteExtractParameter(t *testing.T) {
+-	// setup service
+-	ws := new(restful.WebService)
+-	ws.Consumes(restful.MIME_XML)
+-	ws.Route(ws.GET("/test/{param}").To(DummyHandler))
+-	restful.Add(ws)
+-
+-	// setup request + writer
+-	bodyReader := strings.NewReader("<Sample><Value>42</Value></Sample>")
+-	httpRequest, _ := http.NewRequest("GET", "/test/THIS", bodyReader)
+-	httpRequest.Header.Set("Content-Type", restful.MIME_XML)
+-	httpWriter := httptest.NewRecorder()
+-
+-	// run
+-	restful.DefaultContainer.ServeHTTP(httpWriter, httpRequest)
+-
+-	if Result != "THIS" {
+-		t.Fatalf("Result is actually: %s", Result)
+-	}
+-}
+-
+-func DummyHandler(rq *restful.Request, rp *restful.Response) {
+-	Result = rq.PathParameter("param")
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-routefunction_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-routefunction_test.go
+deleted file mode 100644
+index 6d61c5c..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-routefunction_test.go
++++ /dev/null
+@@ -1,29 +0,0 @@
+-package main
+-
+-import (
+-	"net/http"
+-	"net/http/httptest"
+-	"testing"
+-
+-	"github.com/emicklei/go-restful"
+-)
+-
+-// This example show how to test one particular RouteFunction (getIt)
+-// It uses the httptest.ResponseRecorder to capture output
+-
+-func getIt(req *restful.Request, resp *restful.Response) {
+-	resp.WriteHeader(404)
+-}
+-
+-func TestCallFunction(t *testing.T) {
+-	httpReq, _ := http.NewRequest("GET", "/", nil)
+-	req := restful.NewRequest(httpReq)
+-
+-	recorder := new(httptest.ResponseRecorder)
+-	resp := restful.NewResponse(recoder)
+-
+-	getIt(req, resp)
+-	if recorder.Code != 404 {
+-		t.Logf("Missing or wrong status code:%d", recorder.Code)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-serve-static.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-serve-static.go
+deleted file mode 100644
+index 8cb7848..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-serve-static.go
++++ /dev/null
+@@ -1,47 +0,0 @@
+-package main
+-
+-import (
+-	"fmt"
+-	"net/http"
+-	"path"
+-
+-	"github.com/emicklei/go-restful"
+-)
+-
+-// This example shows how to define methods that serve static files
+-// It uses the standard http.ServeFile method
+-//
+-// GET http://localhost:8080/static/test.xml
+-// GET http://localhost:8080/static/
+-//
+-// GET http://localhost:8080/static?resource=subdir/test.xml
+-
+-var rootdir = "/tmp"
+-
+-func main() {
+-	restful.DefaultContainer.Router(restful.CurlyRouter{})
+-
+-	ws := new(restful.WebService)
+-	ws.Route(ws.GET("/static/{subpath:*}").To(staticFromPathParam))
+-	ws.Route(ws.GET("/static").To(staticFromQueryParam))
+-	restful.Add(ws)
+-
+-	println("[go-restful] serving files on http://localhost:8080/static from local /tmp")
+-	http.ListenAndServe(":8080", nil)
+-}
+-
+-func staticFromPathParam(req *restful.Request, resp *restful.Response) {
+-	actual := path.Join(rootdir, req.PathParameter("subpath"))
+-	fmt.Printf("serving %s ... (from %s)\n", actual, req.PathParameter("subpath"))
+-	http.ServeFile(
+-		resp.ResponseWriter,
+-		req.Request,
+-		actual)
+-}
+-
+-func staticFromQueryParam(req *restful.Request, resp *restful.Response) {
+-	http.ServeFile(
+-		resp.ResponseWriter,
+-		req.Request,
+-		path.Join(rootdir, req.QueryParameter("resource")))
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-user-resource.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-user-resource.go
+deleted file mode 100644
+index f6ec988..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-user-resource.go
++++ /dev/null
+@@ -1,153 +0,0 @@
+-package main
+-
+-import (
+-	"log"
+-	"net/http"
+-	"strconv"
+-
+-	"github.com/emicklei/go-restful"
+-	"github.com/emicklei/go-restful/swagger"
+-)
+-
+-// This example show a complete (GET,PUT,POST,DELETE) conventional example of
+-// a REST Resource including documentation to be served by e.g. a Swagger UI
+-// It is recommended to create a Resource struct (UserResource) that can encapsulate
+-// an object that provide domain access (a DAO)
+-// It has a Register method including the complete Route mapping to methods together
+-// with all the appropriate documentation
+-//
+-// POST http://localhost:8080/users
+-// <User><Id>1</Id><Name>Melissa Raspberry</Name></User>
+-//
+-// GET http://localhost:8080/users/1
+-//
+-// PUT http://localhost:8080/users/1
+-// <User><Id>1</Id><Name>Melissa</Name></User>
+-//
+-// DELETE http://localhost:8080/users/1
+-//
+-
+-type User struct {
+-	Id, Name string
+-}
+-
+-type UserResource struct {
+-	// normally one would use DAO (data access object)
+-	users map[string]User
+-}
+-
+-func (u UserResource) Register(container *restful.Container) {
+-	ws := new(restful.WebService)
+-	ws.
+-		Path("/users").
+-		Doc("Manage Users").
+-		Consumes(restful.MIME_XML, restful.MIME_JSON).
+-		Produces(restful.MIME_JSON, restful.MIME_XML) // you can specify this per route as well
+-
+-	ws.Route(ws.GET("/{user-id}").To(u.findUser).
+-		// docs
+-		Doc("get a user").
+-		Operation("findUser").
+-		Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")).
+-		Writes(User{})) // on the response
+-
+-	ws.Route(ws.PUT("/{user-id}").To(u.updateUser).
+-		// docs
+-		Doc("update a user").
+-		Operation("updateUser").
+-		Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")).
+-		ReturnsError(409, "duplicate user-id", nil).
+-		Reads(User{})) // from the request
+-
+-	ws.Route(ws.POST("").To(u.createUser).
+-		// docs
+-		Doc("create a user").
+-		Operation("createUser").
+-		Reads(User{})) // from the request
+-
+-	ws.Route(ws.DELETE("/{user-id}").To(u.removeUser).
+-		// docs
+-		Doc("delete a user").
+-		Operation("removeUser").
+-		Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")))
+-
+-	container.Add(ws)
+-}
+-
+-// GET http://localhost:8080/users/1
+-//
+-func (u UserResource) findUser(request *restful.Request, response *restful.Response) {
+-	id := request.PathParameter("user-id")
+-	usr := u.users[id]
+-	if len(usr.Id) == 0 {
+-		response.AddHeader("Content-Type", "text/plain")
+-		response.WriteErrorString(http.StatusNotFound, "404: User could not be found.")
+-		return
+-	}
+-	response.WriteEntity(usr)
+-}
+-
+-// POST http://localhost:8080/users
+-// <User><Name>Melissa</Name></User>
+-//
+-func (u *UserResource) createUser(request *restful.Request, response *restful.Response) {
+-	usr := new(User)
+-	err := request.ReadEntity(usr)
+-	if err != nil {
+-		response.AddHeader("Content-Type", "text/plain")
+-		response.WriteErrorString(http.StatusInternalServerError, err.Error())
+-		return
+-	}
+-	usr.Id = strconv.Itoa(len(u.users) + 1) // simple id generation
+-	u.users[usr.Id] = *usr
+-	response.WriteHeader(http.StatusCreated)
+-	response.WriteEntity(usr)
+-}
+-
+-// PUT http://localhost:8080/users/1
+-// <User><Id>1</Id><Name>Melissa Raspberry</Name></User>
+-//
+-func (u *UserResource) updateUser(request *restful.Request, response *restful.Response) {
+-	usr := new(User)
+-	err := request.ReadEntity(&usr)
+-	if err != nil {
+-		response.AddHeader("Content-Type", "text/plain")
+-		response.WriteErrorString(http.StatusInternalServerError, err.Error())
+-		return
+-	}
+-	u.users[usr.Id] = *usr
+-	response.WriteEntity(usr)
+-}
+-
+-// DELETE http://localhost:8080/users/1
+-//
+-func (u *UserResource) removeUser(request *restful.Request, response *restful.Response) {
+-	id := request.PathParameter("user-id")
+-	delete(u.users, id)
+-}
+-
+-func main() {
+-	// to see what happens in the package, uncomment the following
+-	//restful.TraceLogger(log.New(os.Stdout, "[restful] ", log.LstdFlags|log.Lshortfile))
+-
+-	wsContainer := restful.NewContainer()
+-	u := UserResource{map[string]User{}}
+-	u.Register(wsContainer)
+-
+-	// Optionally, you can install the Swagger Service which provides a nice Web UI on your REST API
+-	// You need to download the Swagger HTML5 assets and change the FilePath location in the config below.
+-	// Open http://localhost:8080/apidocs and enter http://localhost:8080/apidocs.json in the api input field.
+-	config := swagger.Config{
+-		WebServices:    wsContainer.RegisteredWebServices(), // you control what services are visible
+-		WebServicesUrl: "http://localhost:8080",
+-		ApiPath:        "/apidocs.json",
+-
+-		// Optionally, specifiy where the UI is located
+-		SwaggerPath:     "/apidocs/",
+-		SwaggerFilePath: "/Users/emicklei/xProjects/swagger-ui/dist"}
+-	swagger.RegisterSwaggerService(config, wsContainer)
+-
+-	log.Printf("start listening on localhost:8080")
+-	server := &http.Server{Addr: ":8080", Handler: wsContainer}
+-	log.Fatal(server.ListenAndServe())
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-user-service.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-user-service.go
+deleted file mode 100644
+index d0d9872..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-user-service.go
++++ /dev/null
+@@ -1,138 +0,0 @@
+-package main
+-
+-import (
+-	"log"
+-	"net/http"
+-
+-	"github.com/emicklei/go-restful"
+-	"github.com/emicklei/go-restful/swagger"
+-)
+-
+-// This example is functionally the same as the example in restful-user-resource.go
+-// with the only difference that is served using the restful.DefaultContainer
+-
+-type User struct {
+-	Id, Name string
+-}
+-
+-type UserService struct {
+-	// normally one would use DAO (data access object)
+-	users map[string]User
+-}
+-
+-func (u UserService) Register() {
+-	ws := new(restful.WebService)
+-	ws.
+-		Path("/users").
+-		Consumes(restful.MIME_XML, restful.MIME_JSON).
+-		Produces(restful.MIME_JSON, restful.MIME_XML) // you can specify this per route as well
+-
+-	ws.Route(ws.GET("/").To(u.findAllUsers).
+-		// docs
+-		Doc("get all users").
+-		Operation("findAllUsers").
+-		Returns(200, "OK", []User{}))
+-
+-	ws.Route(ws.GET("/{user-id}").To(u.findUser).
+-		// docs
+-		Doc("get a user").
+-		Operation("findUser").
+-		Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")).
+-		Writes(User{})) // on the response
+-
+-	ws.Route(ws.PUT("/{user-id}").To(u.updateUser).
+-		// docs
+-		Doc("update a user").
+-		Operation("updateUser").
+-		Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")).
+-		Reads(User{})) // from the request
+-
+-	ws.Route(ws.PUT("").To(u.createUser).
+-		// docs
+-		Doc("create a user").
+-		Operation("createUser").
+-		Reads(User{})) // from the request
+-
+-	ws.Route(ws.DELETE("/{user-id}").To(u.removeUser).
+-		// docs
+-		Doc("delete a user").
+-		Operation("removeUser").
+-		Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")))
+-
+-	restful.Add(ws)
+-}
+-
+-// GET http://localhost:8080/users
+-//
+-func (u UserService) findAllUsers(request *restful.Request, response *restful.Response) {
+-	response.WriteEntity(u.users)
+-}
+-
+-// GET http://localhost:8080/users/1
+-//
+-func (u UserService) findUser(request *restful.Request, response *restful.Response) {
+-	id := request.PathParameter("user-id")
+-	usr := u.users[id]
+-	if len(usr.Id) == 0 {
+-		response.WriteErrorString(http.StatusNotFound, "User could not be found.")
+-	} else {
+-		response.WriteEntity(usr)
+-	}
+-}
+-
+-// PUT http://localhost:8080/users/1
+-// <User><Id>1</Id><Name>Melissa Raspberry</Name></User>
+-//
+-func (u *UserService) updateUser(request *restful.Request, response *restful.Response) {
+-	usr := new(User)
+-	err := request.ReadEntity(&usr)
+-	if err == nil {
+-		u.users[usr.Id] = *usr
+-		response.WriteEntity(usr)
+-	} else {
+-		response.WriteError(http.StatusInternalServerError, err)
+-	}
+-}
+-
+-// PUT http://localhost:8080/users/1
+-// <User><Id>1</Id><Name>Melissa</Name></User>
+-//
+-func (u *UserService) createUser(request *restful.Request, response *restful.Response) {
+-	usr := User{Id: request.PathParameter("user-id")}
+-	err := request.ReadEntity(&usr)
+-	if err == nil {
+-		u.users[usr.Id] = usr
+-		response.WriteHeader(http.StatusCreated)
+-		response.WriteEntity(usr)
+-	} else {
+-		response.WriteError(http.StatusInternalServerError, err)
+-	}
+-}
+-
+-// DELETE http://localhost:8080/users/1
+-//
+-func (u *UserService) removeUser(request *restful.Request, response *restful.Response) {
+-	id := request.PathParameter("user-id")
+-	delete(u.users, id)
+-}
+-
+-func main() {
+-	u := UserService{map[string]User{}}
+-	u.Register()
+-
+-	// Optionally, you can install the Swagger Service which provides a nice Web UI on your REST API
+-	// You need to download the Swagger HTML5 assets and change the FilePath location in the config below.
+-	// Open http://localhost:8080/apidocs and enter http://localhost:8080/apidocs.json in the api input field.
+-	config := swagger.Config{
+-		WebServices:    restful.RegisteredWebServices(), // you control what services are visible
+-		WebServicesUrl: "http://localhost:8080",
+-		ApiPath:        "/apidocs.json",
+-
+-		// Optionally, specifiy where the UI is located
+-		SwaggerPath:     "/apidocs/",
+-		SwaggerFilePath: "/Users/emicklei/Projects/swagger-ui/dist"}
+-	swagger.InstallSwaggerService(config)
+-
+-	log.Printf("start listening on localhost:8080")
+-	log.Fatal(http.ListenAndServe(":8080", nil))
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/filter.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/filter.go
+deleted file mode 100644
+index 4b86656..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/filter.go
++++ /dev/null
+@@ -1,26 +0,0 @@
+-package restful
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-// FilterChain is a request scoped object to process one or more filters before calling the target RouteFunction.
+-type FilterChain struct {
+-	Filters []FilterFunction // ordered list of FilterFunction
+-	Index   int              // index into filters that is currently in progress
+-	Target  RouteFunction    // function to call after passing all filters
+-}
+-
+-// ProcessFilter passes the request,response pair through the next of Filters.
+-// Each filter can decide to proceed to the next Filter or handle the Response itself.
+-func (f *FilterChain) ProcessFilter(request *Request, response *Response) {
+-	if f.Index < len(f.Filters) {
+-		f.Index++
+-		f.Filters[f.Index-1](request, response, f)
+-	} else {
+-		f.Target(request, response)
+-	}
+-}
+-
+-// FilterFunction definitions must call ProcessFilter on the FilterChain to pass on the control and eventually call the RouteFunction
+-type FilterFunction func(*Request, *Response, *FilterChain)
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/filter_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/filter_test.go
+deleted file mode 100644
+index fadfb57..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/filter_test.go
++++ /dev/null
+@@ -1,141 +0,0 @@
+-package restful
+-
+-import (
+-	"io"
+-	"net/http"
+-	"net/http/httptest"
+-	"testing"
+-)
+-
+-func setupServices(addGlobalFilter bool, addServiceFilter bool, addRouteFilter bool) {
+-	if addGlobalFilter {
+-		Filter(globalFilter)
+-	}
+-	Add(newTestService(addServiceFilter, addRouteFilter))
+-}
+-
+-func tearDown() {
+-	DefaultContainer.webServices = []*WebService{}
+-	DefaultContainer.isRegisteredOnRoot = true // this allows for setupServices multiple times
+-	DefaultContainer.containerFilters = []FilterFunction{}
+-}
+-
+-func newTestService(addServiceFilter bool, addRouteFilter bool) *WebService {
+-	ws := new(WebService).Path("")
+-	if addServiceFilter {
+-		ws.Filter(serviceFilter)
+-	}
+-	rb := ws.GET("/foo").To(foo)
+-	if addRouteFilter {
+-		rb.Filter(routeFilter)
+-	}
+-	ws.Route(rb)
+-	ws.Route(ws.GET("/bar").To(bar))
+-	return ws
+-}
+-
+-func foo(req *Request, resp *Response) {
+-	io.WriteString(resp.ResponseWriter, "foo")
+-}
+-
+-func bar(req *Request, resp *Response) {
+-	io.WriteString(resp.ResponseWriter, "bar")
+-}
+-
+-func fail(req *Request, resp *Response) {
+-	http.Error(resp.ResponseWriter, "something failed", http.StatusInternalServerError)
+-}
+-
+-func globalFilter(req *Request, resp *Response, chain *FilterChain) {
+-	io.WriteString(resp.ResponseWriter, "global-")
+-	chain.ProcessFilter(req, resp)
+-}
+-
+-func serviceFilter(req *Request, resp *Response, chain *FilterChain) {
+-	io.WriteString(resp.ResponseWriter, "service-")
+-	chain.ProcessFilter(req, resp)
+-}
+-
+-func routeFilter(req *Request, resp *Response, chain *FilterChain) {
+-	io.WriteString(resp.ResponseWriter, "route-")
+-	chain.ProcessFilter(req, resp)
+-}
+-
+-func TestNoFilter(t *testing.T) {
+-	tearDown()
+-	setupServices(false, false, false)
+-	actual := sendIt("http://example.com/foo")
+-	if "foo" != actual {
+-		t.Fatal("expected: foo but got:" + actual)
+-	}
+-}
+-
+-func TestGlobalFilter(t *testing.T) {
+-	tearDown()
+-	setupServices(true, false, false)
+-	actual := sendIt("http://example.com/foo")
+-	if "global-foo" != actual {
+-		t.Fatal("expected: global-foo but got:" + actual)
+-	}
+-}
+-
+-func TestWebServiceFilter(t *testing.T) {
+-	tearDown()
+-	setupServices(true, true, false)
+-	actual := sendIt("http://example.com/foo")
+-	if "global-service-foo" != actual {
+-		t.Fatal("expected: global-service-foo but got:" + actual)
+-	}
+-}
+-
+-func TestRouteFilter(t *testing.T) {
+-	tearDown()
+-	setupServices(true, true, true)
+-	actual := sendIt("http://example.com/foo")
+-	if "global-service-route-foo" != actual {
+-		t.Fatal("expected: global-service-route-foo but got:" + actual)
+-	}
+-}
+-
+-func TestRouteFilterOnly(t *testing.T) {
+-	tearDown()
+-	setupServices(false, false, true)
+-	actual := sendIt("http://example.com/foo")
+-	if "route-foo" != actual {
+-		t.Fatal("expected: route-foo but got:" + actual)
+-	}
+-}
+-
+-func TestBar(t *testing.T) {
+-	tearDown()
+-	setupServices(false, true, false)
+-	actual := sendIt("http://example.com/bar")
+-	if "service-bar" != actual {
+-		t.Fatal("expected: service-bar but got:" + actual)
+-	}
+-}
+-
+-func TestAllFiltersBar(t *testing.T) {
+-	tearDown()
+-	setupServices(true, true, true)
+-	actual := sendIt("http://example.com/bar")
+-	if "global-service-bar" != actual {
+-		t.Fatal("expected: global-service-bar but got:" + actual)
+-	}
+-}
+-
+-func sendIt(address string) string {
+-	httpRequest, _ := http.NewRequest("GET", address, nil)
+-	httpRequest.Header.Set("Accept", "*/*")
+-	httpWriter := httptest.NewRecorder()
+-	DefaultContainer.dispatch(httpWriter, httpRequest)
+-	return httpWriter.Body.String()
+-}
+-
+-func sendItTo(address string, container *Container) string {
+-	httpRequest, _ := http.NewRequest("GET", address, nil)
+-	httpRequest.Header.Set("Accept", "*/*")
+-	httpWriter := httptest.NewRecorder()
+-	container.dispatch(httpWriter, httpRequest)
+-	return httpWriter.Body.String()
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/install.sh b/Godeps/_workspace/src/github.com/emicklei/go-restful/install.sh
+deleted file mode 100644
+index b5de8a2..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/install.sh
++++ /dev/null
+@@ -1,9 +0,0 @@
+-cd examples
+-	ls *.go | xargs -I {} go build {}
+-	cd ..
+-go fmt ...swagger && \
+-go test -test.v ...swagger && \
+-go install ...swagger && \
+-go fmt ...restful && \
+-go test -test.v ...restful && \
+-go install ...restful
+\ No newline at end of file
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/jsr311.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/jsr311.go
+deleted file mode 100644
+index 3d9d7d8..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/jsr311.go
++++ /dev/null
+@@ -1,247 +0,0 @@
+-package restful
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-import (
+-	"errors"
+-	"fmt"
+-	"net/http"
+-	"sort"
+-)
+-
+-// RouterJSR311 implements the flow for matching Requests to Routes (and consequently Resource Functions)
+-// as specified by the JSR311 http://jsr311.java.net/nonav/releases/1.1/spec/spec.html.
+-// RouterJSR311 implements the Router interface.
+-// Concept of locators is not implemented.
+-type RouterJSR311 struct{}
+-
+-// SelectRoute is part of the Router interface and returns the best match
+-// for the WebService and its Route for the given Request.
+-func (r RouterJSR311) SelectRoute(
+-	webServices []*WebService,
+-	httpRequest *http.Request) (selectedService *WebService, selectedRoute *Route, err error) {
+-
+-	// Identify the root resource class (WebService)
+-	dispatcher, finalMatch, err := r.detectDispatcher(httpRequest.URL.Path, webServices)
+-	if err != nil {
+-		return nil, nil, NewError(http.StatusNotFound, "")
+-	}
+-	// Obtain the set of candidate methods (Routes)
+-	routes := r.selectRoutes(dispatcher, finalMatch)
+-	if len(routes) == 0 {
+-		return dispatcher, nil, NewError(http.StatusNotFound, "404: Page Not Found")
+-	}
+-
+-	// Identify the method (Route) that will handle the request
+-	route, ok := r.detectRoute(routes, httpRequest)
+-	return dispatcher, route, ok
+-}
+-
+-// http://jsr311.java.net/nonav/releases/1.1/spec/spec3.html#x3-360003.7.2
+-func (r RouterJSR311) detectRoute(routes []Route, httpRequest *http.Request) (*Route, error) {
+-	// http method
+-	methodOk := []Route{}
+-	for _, each := range routes {
+-		if httpRequest.Method == each.Method {
+-			methodOk = append(methodOk, each)
+-		}
+-	}
+-	if len(methodOk) == 0 {
+-		if trace {
+-			traceLogger.Printf("no Route found (in %d routes) that matches HTTP method %s\n", len(routes), httpRequest.Method)
+-		}
+-		return nil, NewError(http.StatusMethodNotAllowed, "405: Method Not Allowed")
+-	}
+-	inputMediaOk := methodOk
+-	// content-type
+-	contentType := httpRequest.Header.Get(HEADER_ContentType)
+-	if httpRequest.ContentLength > 0 {
+-		inputMediaOk = []Route{}
+-		for _, each := range methodOk {
+-			if each.matchesContentType(contentType) {
+-				inputMediaOk = append(inputMediaOk, each)
+-			}
+-		}
+-		if len(inputMediaOk) == 0 {
+-			if trace {
+-				traceLogger.Printf("no Route found (from %d) that matches HTTP Content-Type: %s\n", len(methodOk), contentType)
+-			}
+-			return nil, NewError(http.StatusUnsupportedMediaType, "415: Unsupported Media Type")
+-		}
+-	}
+-	// accept
+-	outputMediaOk := []Route{}
+-	accept := httpRequest.Header.Get(HEADER_Accept)
+-	if accept == "" {
+-		accept = "*/*"
+-	}
+-	for _, each := range inputMediaOk {
+-		if each.matchesAccept(accept) {
+-			outputMediaOk = append(outputMediaOk, each)
+-		}
+-	}
+-	if len(outputMediaOk) == 0 {
+-		if trace {
+-			traceLogger.Printf("no Route found (from %d) that matches HTTP Accept: %s\n", len(inputMediaOk), accept)
+-		}
+-		return nil, NewError(http.StatusNotAcceptable, "406: Not Acceptable")
+-	}
+-	return r.bestMatchByMedia(outputMediaOk, contentType, accept), nil
+-}
+-
+-// http://jsr311.java.net/nonav/releases/1.1/spec/spec3.html#x3-360003.7.2
+-// n/m > n/* > */*
+-func (r RouterJSR311) bestMatchByMedia(routes []Route, contentType string, accept string) *Route {
+-	// TODO
+-	return &routes[0]
+-}
+-
+-// http://jsr311.java.net/nonav/releases/1.1/spec/spec3.html#x3-360003.7.2  (step 2)
+-func (r RouterJSR311) selectRoutes(dispatcher *WebService, pathRemainder string) []Route {
+-	filtered := &sortableRouteCandidates{}
+-	for _, each := range dispatcher.Routes() {
+-		pathExpr := each.pathExpr
+-		matches := pathExpr.Matcher.FindStringSubmatch(pathRemainder)
+-		if matches != nil {
+-			lastMatch := matches[len(matches)-1]
+-			if len(lastMatch) == 0 || lastMatch == "/" { // do not include if value is neither empty nor ‘/’.
+-				filtered.candidates = append(filtered.candidates,
+-					routeCandidate{each, len(matches) - 1, pathExpr.LiteralCount, pathExpr.VarCount})
+-			}
+-		}
+-	}
+-	if len(filtered.candidates) == 0 {
+-		if trace {
+-			traceLogger.Printf("WebService on path %s has no routes that match URL path remainder:%s\n", dispatcher.rootPath, pathRemainder)
+-		}
+-		return []Route{}
+-	}
+-	sort.Sort(sort.Reverse(filtered))
+-
+-	// select other routes from candidates whoes expression matches rmatch
+-	matchingRoutes := []Route{filtered.candidates[0].route}
+-	for c := 1; c < len(filtered.candidates); c++ {
+-		each := filtered.candidates[c]
+-		if each.route.pathExpr.Matcher.MatchString(pathRemainder) {
+-			matchingRoutes = append(matchingRoutes, each.route)
+-		}
+-	}
+-	return matchingRoutes
+-}
+-
+-// http://jsr311.java.net/nonav/releases/1.1/spec/spec3.html#x3-360003.7.2 (step 1)
+-func (r RouterJSR311) detectDispatcher(requestPath string, dispatchers []*WebService) (*WebService, string, error) {
+-	filtered := &sortableDispatcherCandidates{}
+-	for _, each := range dispatchers {
+-		matches := each.pathExpr.Matcher.FindStringSubmatch(requestPath)
+-		if matches != nil {
+-			filtered.candidates = append(filtered.candidates,
+-				dispatcherCandidate{each, matches[len(matches)-1], len(matches), each.pathExpr.LiteralCount, each.pathExpr.VarCount})
+-		}
+-	}
+-	if len(filtered.candidates) == 0 {
+-		if trace {
+-			traceLogger.Printf("no WebService was found to match URL path:%s\n", requestPath)
+-		}
+-		return nil, "", errors.New("not found")
+-	}
+-	sort.Sort(sort.Reverse(filtered))
+-	return filtered.candidates[0].dispatcher, filtered.candidates[0].finalMatch, nil
+-}
+-
+-// Types and functions to support the sorting of Routes
+-
+-type routeCandidate struct {
+-	route           Route
+-	matchesCount    int // the number of capturing groups
+-	literalCount    int // the number of literal characters (means those not resulting from template variable substitution)
+-	nonDefaultCount int // the number of capturing groups with non-default regular expressions (i.e. not ‘([^  /]+?)’)
+-}
+-
+-func (r routeCandidate) expressionToMatch() string {
+-	return r.route.pathExpr.Source
+-}
+-
+-func (r routeCandidate) String() string {
+-	return fmt.Sprintf("(m=%d,l=%d,n=%d)", r.matchesCount, r.literalCount, r.nonDefaultCount)
+-}
+-
+-type sortableRouteCandidates struct {
+-	candidates []routeCandidate
+-}
+-
+-func (rcs *sortableRouteCandidates) Len() int {
+-	return len(rcs.candidates)
+-}
+-func (rcs *sortableRouteCandidates) Swap(i, j int) {
+-	rcs.candidates[i], rcs.candidates[j] = rcs.candidates[j], rcs.candidates[i]
+-}
+-func (rcs *sortableRouteCandidates) Less(i, j int) bool {
+-	ci := rcs.candidates[i]
+-	cj := rcs.candidates[j]
+-	// primary key
+-	if ci.literalCount < cj.literalCount {
+-		return true
+-	}
+-	if ci.literalCount > cj.literalCount {
+-		return false
+-	}
+-	// secundary key
+-	if ci.matchesCount < cj.matchesCount {
+-		return true
+-	}
+-	if ci.matchesCount > cj.matchesCount {
+-		return false
+-	}
+-	// tertiary key
+-	if ci.nonDefaultCount < cj.nonDefaultCount {
+-		return true
+-	}
+-	if ci.nonDefaultCount > cj.nonDefaultCount {
+-		return false
+-	}
+-	// quaternary key ("source" is interpreted as Path)
+-	return ci.route.Path < cj.route.Path
+-}
+-
+-// Types and functions to support the sorting of Dispatchers
+-
+-type dispatcherCandidate struct {
+-	dispatcher      *WebService
+-	finalMatch      string
+-	matchesCount    int // the number of capturing groups
+-	literalCount    int // the number of literal characters (means those not resulting from template variable substitution)
+-	nonDefaultCount int // the number of capturing groups with non-default regular expressions (i.e. not ‘([^  /]+?)’)
+-}
+-type sortableDispatcherCandidates struct {
+-	candidates []dispatcherCandidate
+-}
+-
+-func (dc *sortableDispatcherCandidates) Len() int {
+-	return len(dc.candidates)
+-}
+-func (dc *sortableDispatcherCandidates) Swap(i, j int) {
+-	dc.candidates[i], dc.candidates[j] = dc.candidates[j], dc.candidates[i]
+-}
+-func (dc *sortableDispatcherCandidates) Less(i, j int) bool {
+-	ci := dc.candidates[i]
+-	cj := dc.candidates[j]
+-	// primary key
+-	if ci.matchesCount < cj.matchesCount {
+-		return true
+-	}
+-	if ci.matchesCount > cj.matchesCount {
+-		return false
+-	}
+-	// secundary key
+-	if ci.literalCount < cj.literalCount {
+-		return true
+-	}
+-	if ci.literalCount > cj.literalCount {
+-		return false
+-	}
+-	// tertiary key
+-	return ci.nonDefaultCount < cj.nonDefaultCount
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/jsr311_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/jsr311_test.go
+deleted file mode 100644
+index b531b7f..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/jsr311_test.go
++++ /dev/null
+@@ -1,236 +0,0 @@
+-package restful
+-
+-import (
+-	"io"
+-	"sort"
+-	"testing"
+-)
+-
+-//
+-// Step 1 tests
+-//
+-var paths = []struct {
+-	// url with path (1) is handled by service with root (2) and last capturing group has value final (3)
+-	path, root, final string
+-}{
+-	{"/", "/", "/"},
+-	{"/p", "/p", ""},
+-	{"/p/x", "/p/{q}", ""},
+-	{"/q/x", "/q", "/x"},
+-	{"/p/x/", "/p/{q}", "/"},
+-	{"/p/x/y", "/p/{q}", "/y"},
+-	{"/q/x/y", "/q", "/x/y"},
+-	{"/z/q", "/{p}/q", ""},
+-	{"/a/b/c/q", "/", "/a/b/c/q"},
+-}
+-
+-func TestDetectDispatcher(t *testing.T) {
+-	ws1 := new(WebService).Path("/")
+-	ws2 := new(WebService).Path("/p")
+-	ws3 := new(WebService).Path("/q")
+-	ws4 := new(WebService).Path("/p/q")
+-	ws5 := new(WebService).Path("/p/{q}")
+-	ws6 := new(WebService).Path("/p/{q}/")
+-	ws7 := new(WebService).Path("/{p}/q")
+-	var dispatchers = []*WebService{ws1, ws2, ws3, ws4, ws5, ws6, ws7}
+-
+-	wc := NewContainer()
+-	for _, each := range dispatchers {
+-		wc.Add(each)
+-	}
+-
+-	router := RouterJSR311{}
+-
+-	ok := true
+-	for i, fixture := range paths {
+-		who, final, err := router.detectDispatcher(fixture.path, dispatchers)
+-		if err != nil {
+-			t.Logf("error in detection:%v", err)
+-			ok = false
+-		}
+-		if who.RootPath() != fixture.root {
+-			t.Logf("[line:%v] Unexpected dispatcher, expected:%v, actual:%v", i, fixture.root, who.RootPath())
+-			ok = false
+-		}
+-		if final != fixture.final {
+-			t.Logf("[line:%v] Unexpected final, expected:%v, actual:%v", i, fixture.final, final)
+-			ok = false
+-		}
+-	}
+-	if !ok {
+-		t.Fail()
+-	}
+-}
+-
+-//
+-// Step 2 tests
+-//
+-
+-// go test -v -test.run TestISSUE_30 ...restful
+-func TestISSUE_30(t *testing.T) {
+-	ws1 := new(WebService).Path("/users")
+-	ws1.Route(ws1.GET("/{id}").To(dummy))
+-	ws1.Route(ws1.POST("/login").To(dummy))
+-	routes := RouterJSR311{}.selectRoutes(ws1, "/login")
+-	if len(routes) != 2 {
+-		t.Fatal("expected 2 routes")
+-	}
+-	if routes[0].Path != "/users/login" {
+-		t.Error("first is", routes[0].Path)
+-		t.Logf("routes:%v", routes)
+-	}
+-}
+-
+-// go test -v -test.run TestISSUE_34 ...restful
+-func TestISSUE_34(t *testing.T) {
+-	ws1 := new(WebService).Path("/")
+-	ws1.Route(ws1.GET("/{type}/{id}").To(dummy))
+-	ws1.Route(ws1.GET("/network/{id}").To(dummy))
+-	routes := RouterJSR311{}.selectRoutes(ws1, "/network/12")
+-	if len(routes) != 2 {
+-		t.Fatal("expected 2 routes")
+-	}
+-	if routes[0].Path != "/network/{id}" {
+-		t.Error("first is", routes[0].Path)
+-		t.Logf("routes:%v", routes)
+-	}
+-}
+-
+-// go test -v -test.run TestISSUE_34_2 ...restful
+-func TestISSUE_34_2(t *testing.T) {
+-	ws1 := new(WebService).Path("/")
+-	// change the registration order
+-	ws1.Route(ws1.GET("/network/{id}").To(dummy))
+-	ws1.Route(ws1.GET("/{type}/{id}").To(dummy))
+-	routes := RouterJSR311{}.selectRoutes(ws1, "/network/12")
+-	if len(routes) != 2 {
+-		t.Fatal("expected 2 routes")
+-	}
+-	if routes[0].Path != "/network/{id}" {
+-		t.Error("first is", routes[0].Path)
+-	}
+-}
+-
+-// go test -v -test.run TestISSUE_137 ...restful
+-func TestISSUE_137(t *testing.T) {
+-	ws1 := new(WebService)
+-	ws1.Route(ws1.GET("/hello").To(dummy))
+-	routes := RouterJSR311{}.selectRoutes(ws1, "/")
+-	t.Log(routes)
+-	if len(routes) > 0 {
+-		t.Error("no route expected")
+-	}
+-}
+-
+-func TestSelectRoutesSlash(t *testing.T) {
+-	ws1 := new(WebService).Path("/")
+-	ws1.Route(ws1.GET("").To(dummy))
+-	ws1.Route(ws1.GET("/").To(dummy))
+-	ws1.Route(ws1.GET("/u").To(dummy))
+-	ws1.Route(ws1.POST("/u").To(dummy))
+-	ws1.Route(ws1.POST("/u/v").To(dummy))
+-	ws1.Route(ws1.POST("/u/{w}").To(dummy))
+-	ws1.Route(ws1.POST("/u/{w}/z").To(dummy))
+-	routes := RouterJSR311{}.selectRoutes(ws1, "/u")
+-	checkRoutesContains(routes, "/u", t)
+-	checkRoutesContainsNo(routes, "/u/v", t)
+-	checkRoutesContainsNo(routes, "/", t)
+-	checkRoutesContainsNo(routes, "/u/{w}/z", t)
+-}
+-func TestSelectRoutesU(t *testing.T) {
+-	ws1 := new(WebService).Path("/u")
+-	ws1.Route(ws1.GET("").To(dummy))
+-	ws1.Route(ws1.GET("/").To(dummy))
+-	ws1.Route(ws1.GET("/v").To(dummy))
+-	ws1.Route(ws1.POST("/{w}").To(dummy))
+-	ws1.Route(ws1.POST("/{w}/z").To(dummy))          // so full path = /u/{w}/z
+-	routes := RouterJSR311{}.selectRoutes(ws1, "/v") // test against /u/v
+-	checkRoutesContains(routes, "/u/{w}", t)
+-}
+-
+-func TestSelectRoutesUsers1(t *testing.T) {
+-	ws1 := new(WebService).Path("/users")
+-	ws1.Route(ws1.POST("").To(dummy))
+-	ws1.Route(ws1.POST("/").To(dummy))
+-	ws1.Route(ws1.PUT("/{id}").To(dummy))
+-	routes := RouterJSR311{}.selectRoutes(ws1, "/1")
+-	checkRoutesContains(routes, "/users/{id}", t)
+-}
+-func checkRoutesContains(routes []Route, path string, t *testing.T) {
+-	if !containsRoutePath(routes, path, t) {
+-		for _, r := range routes {
+-			t.Logf("route %v %v", r.Method, r.Path)
+-		}
+-		t.Fatalf("routes should include [%v]:", path)
+-	}
+-}
+-func checkRoutesContainsNo(routes []Route, path string, t *testing.T) {
+-	if containsRoutePath(routes, path, t) {
+-		for _, r := range routes {
+-			t.Logf("route %v %v", r.Method, r.Path)
+-		}
+-		t.Fatalf("routes should not include [%v]:", path)
+-	}
+-}
+-func containsRoutePath(routes []Route, path string, t *testing.T) bool {
+-	for _, each := range routes {
+-		if each.Path == path {
+-			return true
+-		}
+-	}
+-	return false
+-}
+-
+-var tempregexs = []struct {
+-	template, regex        string
+-	literalCount, varCount int
+-}{
+-	{"", "^(/.*)?$", 0, 0},
+-	{"/a/{b}/c/", "^/a/([^/]+?)/c(/.*)?$", 2, 1},
+-	{"/{a}/{b}/{c-d-e}/", "^/([^/]+?)/([^/]+?)/([^/]+?)(/.*)?$", 0, 3},
+-	{"/{p}/abcde", "^/([^/]+?)/abcde(/.*)?$", 5, 1},
+-}
+-
+-func TestTemplateToRegularExpression(t *testing.T) {
+-	ok := true
+-	for i, fixture := range tempregexs {
+-		actual, lCount, vCount, _ := templateToRegularExpression(fixture.template)
+-		if actual != fixture.regex {
+-			t.Logf("regex mismatch, expected:%v , actual:%v, line:%v\n", fixture.regex, actual, i) // 11 = where the data starts
+-			ok = false
+-		}
+-		if lCount != fixture.literalCount {
+-			t.Logf("literal count mismatch, expected:%v , actual:%v, line:%v\n", fixture.literalCount, lCount, i)
+-			ok = false
+-		}
+-		if vCount != fixture.varCount {
+-			t.Logf("variable count mismatch, expected:%v , actual:%v, line:%v\n", fixture.varCount, vCount, i)
+-			ok = false
+-		}
+-	}
+-	if !ok {
+-		t.Fatal("one or more expression did not match")
+-	}
+-}
+-
+-// go test -v -test.run TestSortableRouteCandidates ...restful
+-func TestSortableRouteCandidates(t *testing.T) {
+-	fixture := &sortableRouteCandidates{}
+-	r1 := routeCandidate{matchesCount: 0, literalCount: 0, nonDefaultCount: 0}
+-	r2 := routeCandidate{matchesCount: 0, literalCount: 0, nonDefaultCount: 1}
+-	r3 := routeCandidate{matchesCount: 0, literalCount: 1, nonDefaultCount: 1}
+-	r4 := routeCandidate{matchesCount: 1, literalCount: 1, nonDefaultCount: 0}
+-	r5 := routeCandidate{matchesCount: 1, literalCount: 0, nonDefaultCount: 0}
+-	fixture.candidates = append(fixture.candidates, r5, r4, r3, r2, r1)
+-	sort.Sort(sort.Reverse(fixture))
+-	first := fixture.candidates[0]
+-	if first.matchesCount != 1 && first.literalCount != 1 && first.nonDefaultCount != 0 {
+-		t.Fatal("expected r4")
+-	}
+-	last := fixture.candidates[len(fixture.candidates)-1]
+-	if last.matchesCount != 0 && last.literalCount != 0 && last.nonDefaultCount != 0 {
+-		t.Fatal("expected r1")
+-	}
+-}
+-
+-func dummy(req *Request, resp *Response) { io.WriteString(resp.ResponseWriter, "dummy") }
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/logger.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/logger.go
+deleted file mode 100644
+index 25d6a8e..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/logger.go
++++ /dev/null
+@@ -1,16 +0,0 @@
+-package restful
+-
+-import "log"
+-
+-// Copyright 2014 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-var trace bool = false
+-var traceLogger *log.Logger
+-
+-// TraceLogger enables detailed logging of Http request matching and filter invocation. Default no logger is set.
+-func TraceLogger(logger *log.Logger) {
+-	traceLogger = logger
+-	trace = logger != nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/options_filter.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/options_filter.go
+deleted file mode 100644
+index bd5d0c2..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/options_filter.go
++++ /dev/null
+@@ -1,24 +0,0 @@
+-package restful
+-
+-import "strings"
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-// OPTIONSFilter is a filter function that inspects the Http Request for the OPTIONS method
+-// and provides the response with a set of allowed methods for the request URL Path.
+-// As for any filter, you can also install it for a particular WebService within a Container
+-func (c Container) OPTIONSFilter(req *Request, resp *Response, chain *FilterChain) {
+-	if "OPTIONS" != req.Request.Method {
+-		chain.ProcessFilter(req, resp)
+-		return
+-	}
+-	resp.AddHeader(HEADER_Allow, strings.Join(c.computeAllowedMethods(req), ","))
+-}
+-
+-// OPTIONSFilter is a filter function that inspects the Http Request for the OPTIONS method
+-// and provides the response with a set of allowed methods for the request URL Path.
+-func OPTIONSFilter() FilterFunction {
+-	return DefaultContainer.OPTIONSFilter
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/options_filter_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/options_filter_test.go
+deleted file mode 100644
+index f0fceb8..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/options_filter_test.go
++++ /dev/null
+@@ -1,34 +0,0 @@
+-package restful
+-
+-import (
+-	"net/http"
+-	"net/http/httptest"
+-	"testing"
+-)
+-
+-// go test -v -test.run TestOptionsFilter ...restful
+-func TestOptionsFilter(t *testing.T) {
+-	tearDown()
+-	ws := new(WebService)
+-	ws.Route(ws.GET("/candy/{kind}").To(dummy))
+-	ws.Route(ws.DELETE("/candy/{kind}").To(dummy))
+-	ws.Route(ws.POST("/candies").To(dummy))
+-	Add(ws)
+-	Filter(OPTIONSFilter())
+-
+-	httpRequest, _ := http.NewRequest("OPTIONS", "http://here.io/candy/gum", nil)
+-	httpWriter := httptest.NewRecorder()
+-	DefaultContainer.dispatch(httpWriter, httpRequest)
+-	actual := httpWriter.Header().Get(HEADER_Allow)
+-	if "GET,DELETE" != actual {
+-		t.Fatal("expected: GET,DELETE but got:" + actual)
+-	}
+-
+-	httpRequest, _ = http.NewRequest("OPTIONS", "http://here.io/candies", nil)
+-	httpWriter = httptest.NewRecorder()
+-	DefaultContainer.dispatch(httpWriter, httpRequest)
+-	actual = httpWriter.Header().Get(HEADER_Allow)
+-	if "POST" != actual {
+-		t.Fatal("expected: POST but got:" + actual)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/parameter.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/parameter.go
+deleted file mode 100644
+index 7f38a0a..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/parameter.go
++++ /dev/null
+@@ -1,95 +0,0 @@
+-package restful
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-const (
+-	// PathParameterKind = indicator of Request parameter type "path"
+-	PathParameterKind = iota
+-
+-	// QueryParameterKind = indicator of Request parameter type "query"
+-	QueryParameterKind
+-
+-	// BodyParameterKind = indicator of Request parameter type "body"
+-	BodyParameterKind
+-
+-	// HeaderParameterKind = indicator of Request parameter type "header"
+-	HeaderParameterKind
+-
+-	// FormParameterKind = indicator of Request parameter type "form"
+-	FormParameterKind
+-)
+-
+-// Parameter is for documententing the parameter used in a Http Request
+-// ParameterData kinds are Path,Query and Body
+-type Parameter struct {
+-	data *ParameterData
+-}
+-
+-// ParameterData represents the state of a Parameter.
+-// It is made public to make it accessible to e.g. the Swagger package.
+-type ParameterData struct {
+-	Name, Description, DataType string
+-	Kind                        int
+-	Required                    bool
+-	AllowableValues             map[string]string
+-	AllowMultiple               bool
+-}
+-
+-// Data returns the state of the Parameter
+-func (p *Parameter) Data() ParameterData {
+-	return *p.data
+-}
+-
+-// Kind returns the parameter type indicator (see const for valid values)
+-func (p *Parameter) Kind() int {
+-	return p.data.Kind
+-}
+-
+-func (p *Parameter) bePath() *Parameter {
+-	p.data.Kind = PathParameterKind
+-	return p
+-}
+-func (p *Parameter) beQuery() *Parameter {
+-	p.data.Kind = QueryParameterKind
+-	return p
+-}
+-func (p *Parameter) beBody() *Parameter {
+-	p.data.Kind = BodyParameterKind
+-	return p
+-}
+-
+-func (p *Parameter) beHeader() *Parameter {
+-	p.data.Kind = HeaderParameterKind
+-	return p
+-}
+-
+-func (p *Parameter) beForm() *Parameter {
+-	p.data.Kind = FormParameterKind
+-	return p
+-}
+-
+-// Required sets the required field and return the receiver
+-func (p *Parameter) Required(required bool) *Parameter {
+-	p.data.Required = required
+-	return p
+-}
+-
+-// AllowMultiple sets the allowMultiple field and return the receiver
+-func (p *Parameter) AllowMultiple(multiple bool) *Parameter {
+-	p.data.AllowMultiple = multiple
+-	return p
+-}
+-
+-// AllowableValues sets the allowableValues field and return the receiver
+-func (p *Parameter) AllowableValues(values map[string]string) *Parameter {
+-	p.data.AllowableValues = values
+-	return p
+-}
+-
+-// DataType sets the dataType field and return the receiver
+-func (p *Parameter) DataType(typeName string) *Parameter {
+-	p.data.DataType = typeName
+-	return p
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/path_expression.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/path_expression.go
+deleted file mode 100644
+index 8749cb5..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/path_expression.go
++++ /dev/null
+@@ -1,56 +0,0 @@
+-package restful
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-import (
+-	"bytes"
+-	"regexp"
+-	"strings"
+-)
+-
+-// PathExpression holds a compiled path expression (RegExp) needed to match against
+-// Http request paths and to extract path parameter values.
+-type pathExpression struct {
+-	LiteralCount int // the number of literal characters (means those not resulting from template variable substitution)
+-	VarCount     int // the number of named parameters (enclosed by {}) in the path
+-	Matcher      *regexp.Regexp
+-	Source       string // Path as defined by the RouteBuilder
+-	tokens       []string
+-}
+-
+-// NewPathExpression creates a PathExpression from the input URL path.
+-// Returns an error if the path is invalid.
+-func newPathExpression(path string) (*pathExpression, error) {
+-	expression, literalCount, varCount, tokens := templateToRegularExpression(path)
+-	compiled, err := regexp.Compile(expression)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return &pathExpression{literalCount, varCount, compiled, expression, tokens}, nil
+-}
+-
+-// http://jsr311.java.net/nonav/releases/1.1/spec/spec3.html#x3-370003.7.3
+-func templateToRegularExpression(template string) (expression string, literalCount int, varCount int, tokens []string) {
+-	var buffer bytes.Buffer
+-	buffer.WriteString("^")
+-	//tokens = strings.Split(template, "/")
+-	tokens = tokenizePath(template)
+-	for _, each := range tokens {
+-		if each == "" {
+-			continue
+-		}
+-		buffer.WriteString("/")
+-		if strings.HasPrefix(each, "{") {
+-			// ignore var spec
+-			varCount += 1
+-			buffer.WriteString("([^/]+?)")
+-		} else {
+-			literalCount += len(each)
+-			encoded := each // TODO URI encode
+-			buffer.WriteString(regexp.QuoteMeta(encoded))
+-		}
+-	}
+-	return strings.TrimRight(buffer.String(), "/") + "(/.*)?$", literalCount, varCount, tokens
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/request.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/request.go
+deleted file mode 100644
+index 00a069f..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/request.go
++++ /dev/null
+@@ -1,135 +0,0 @@
+-package restful
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-import (
+-	"bytes"
+-	"encoding/json"
+-	"encoding/xml"
+-	"io"
+-	"io/ioutil"
+-	"net/http"
+-	"strings"
+-)
+-
+-var defaultRequestContentType string
+-
+-var doCacheReadEntityBytes = true
+-
+-// Request is a wrapper for a http Request that provides convenience methods
+-type Request struct {
+-	Request           *http.Request
+-	bodyContent       *[]byte // to cache the request body for multiple reads of ReadEntity
+-	pathParameters    map[string]string
+-	attributes        map[string]interface{} // for storing request-scoped values
+-	selectedRoutePath string                 // root path + route path that matched the request, e.g. /meetings/{id}/attendees
+-}
+-
+-func NewRequest(httpRequest *http.Request) *Request {
+-	return &Request{
+-		Request:        httpRequest,
+-		pathParameters: map[string]string{},
+-		attributes:     map[string]interface{}{},
+-	} // empty parameters, attributes
+-}
+-
+-// If ContentType is missing or */* is given then fall back to this type, otherwise
+-// a "Unable to unmarshal content of type:" response is returned.
+-// Valid values are restful.MIME_JSON and restful.MIME_XML
+-// Example:
+-// 	restful.DefaultRequestContentType(restful.MIME_JSON)
+-func DefaultRequestContentType(mime string) {
+-	defaultRequestContentType = mime
+-}
+-
+-// SetCacheReadEntity controls whether the response data ([]byte) is cached such that ReadEntity is repeatable.
+-// Default is true (due to backwardcompatibility). For better performance, you should set it to false if you don't need it.
+-func SetCacheReadEntity(doCache bool) {
+-	doCacheReadEntityBytes = doCache
+-}
+-
+-// PathParameter accesses the Path parameter value by its name
+-func (r *Request) PathParameter(name string) string {
+-	return r.pathParameters[name]
+-}
+-
+-// PathParameters accesses the Path parameter values
+-func (r *Request) PathParameters() map[string]string {
+-	return r.pathParameters
+-}
+-
+-// QueryParameter returns the (first) Query parameter value by its name
+-func (r *Request) QueryParameter(name string) string {
+-	return r.Request.FormValue(name)
+-}
+-
+-// BodyParameter parses the body of the request (once for typically a POST or a PUT) and returns the value of the given name or an error.
+-func (r *Request) BodyParameter(name string) (string, error) {
+-	err := r.Request.ParseForm()
+-	if err != nil {
+-		return "", err
+-	}
+-	return r.Request.PostFormValue(name), nil
+-}
+-
+-// HeaderParameter returns the HTTP Header value of a Header name or empty if missing
+-func (r *Request) HeaderParameter(name string) string {
+-	return r.Request.Header.Get(name)
+-}
+-
+-// ReadEntity checks the Accept header and reads the content into the entityPointer
+-// May be called multiple times in the request-response flow
+-func (r *Request) ReadEntity(entityPointer interface{}) (err error) {
+-	contentType := r.Request.Header.Get(HEADER_ContentType)
+-	if doCacheReadEntityBytes {
+-		return r.cachingReadEntity(contentType, entityPointer)
+-	}
+-	// unmarshall directly from request Body
+-	return r.decodeEntity(r.Request.Body, contentType, entityPointer)
+-}
+-
+-func (r *Request) cachingReadEntity(contentType string, entityPointer interface{}) (err error) {
+-	var buffer []byte
+-	if r.bodyContent != nil {
+-		buffer = *r.bodyContent
+-	} else {
+-		buffer, err = ioutil.ReadAll(r.Request.Body)
+-		if err != nil {
+-			return err
+-		}
+-		r.bodyContent = &buffer
+-	}
+-	return r.decodeEntity(bytes.NewReader(buffer), contentType, entityPointer)
+-}
+-
+-func (r *Request) decodeEntity(reader io.Reader, contentType string, entityPointer interface{}) (err error) {
+-	if strings.Contains(contentType, MIME_XML) {
+-		return xml.NewDecoder(reader).Decode(entityPointer)
+-	}
+-	if strings.Contains(contentType, MIME_JSON) || MIME_JSON == defaultRequestContentType {
+-		decoder := json.NewDecoder(reader)
+-		decoder.UseNumber()
+-		return decoder.Decode(entityPointer)
+-	}
+-	if MIME_XML == defaultRequestContentType {
+-		return xml.NewDecoder(reader).Decode(entityPointer)
+-	}
+-	return NewError(400, "Unable to unmarshal content of type:"+contentType)
+-}
+-
+-// SetAttribute adds or replaces the attribute with the given value.
+-func (r *Request) SetAttribute(name string, value interface{}) {
+-	r.attributes[name] = value
+-}
+-
+-// Attribute returns the value associated to the given name. Returns nil if absent.
+-func (r Request) Attribute(name string) interface{} {
+-	return r.attributes[name]
+-}
+-
+-// SelectedRoutePath root path + route path that matched the request, e.g. /meetings/{id}/attendees
+-func (r Request) SelectedRoutePath() string {
+-	return r.selectedRoutePath
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/request_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/request_test.go
+deleted file mode 100644
+index 6e7c55b..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/request_test.go
++++ /dev/null
+@@ -1,204 +0,0 @@
+-package restful
+-
+-import (
+-	"encoding/json"
+-	"net/http"
+-	"net/url"
+-	"strconv"
+-	"strings"
+-	"testing"
+-)
+-
+-func TestQueryParameter(t *testing.T) {
+-	hreq := http.Request{Method: "GET"}
+-	hreq.URL, _ = url.Parse("http://www.google.com/search?q=foo&q=bar")
+-	rreq := Request{Request: &hreq}
+-	if rreq.QueryParameter("q") != "foo" {
+-		t.Errorf("q!=foo %#v", rreq)
+-	}
+-}
+-
+-type Anything map[string]interface{}
+-
+-type Number struct {
+-	ValueFloat float64
+-	ValueInt   int64
+-}
+-
+-type Sample struct {
+-	Value string
+-}
+-
+-func TestReadEntityXml(t *testing.T) {
+-	SetCacheReadEntity(true)
+-	bodyReader := strings.NewReader("<Sample><Value>42</Value></Sample>")
+-	httpRequest, _ := http.NewRequest("GET", "/test", bodyReader)
+-	httpRequest.Header.Set("Content-Type", "application/xml")
+-	request := &Request{Request: httpRequest}
+-	sam := new(Sample)
+-	request.ReadEntity(sam)
+-	if sam.Value != "42" {
+-		t.Fatal("read failed")
+-	}
+-	if request.bodyContent == nil {
+-		t.Fatal("no expected cached bytes found")
+-	}
+-}
+-
+-func TestReadEntityXmlNonCached(t *testing.T) {
+-	SetCacheReadEntity(false)
+-	bodyReader := strings.NewReader("<Sample><Value>42</Value></Sample>")
+-	httpRequest, _ := http.NewRequest("GET", "/test", bodyReader)
+-	httpRequest.Header.Set("Content-Type", "application/xml")
+-	request := &Request{Request: httpRequest}
+-	sam := new(Sample)
+-	request.ReadEntity(sam)
+-	if sam.Value != "42" {
+-		t.Fatal("read failed")
+-	}
+-	if request.bodyContent != nil {
+-		t.Fatal("unexpected cached bytes found")
+-	}
+-}
+-
+-func TestReadEntityJson(t *testing.T) {
+-	bodyReader := strings.NewReader(`{"Value" : "42"}`)
+-	httpRequest, _ := http.NewRequest("GET", "/test", bodyReader)
+-	httpRequest.Header.Set("Content-Type", "application/json")
+-	request := &Request{Request: httpRequest}
+-	sam := new(Sample)
+-	request.ReadEntity(sam)
+-	if sam.Value != "42" {
+-		t.Fatal("read failed")
+-	}
+-}
+-
+-func TestReadEntityJsonCharset(t *testing.T) {
+-	bodyReader := strings.NewReader(`{"Value" : "42"}`)
+-	httpRequest, _ := http.NewRequest("GET", "/test", bodyReader)
+-	httpRequest.Header.Set("Content-Type", "application/json; charset=UTF-8")
+-	request := NewRequest(httpRequest)
+-	sam := new(Sample)
+-	request.ReadEntity(sam)
+-	if sam.Value != "42" {
+-		t.Fatal("read failed")
+-	}
+-}
+-
+-func TestReadEntityJsonNumber(t *testing.T) {
+-	SetCacheReadEntity(true)
+-	bodyReader := strings.NewReader(`{"Value" : 4899710515899924123}`)
+-	httpRequest, _ := http.NewRequest("GET", "/test", bodyReader)
+-	httpRequest.Header.Set("Content-Type", "application/json")
+-	request := &Request{Request: httpRequest}
+-	any := make(Anything)
+-	request.ReadEntity(&any)
+-	number, ok := any["Value"].(json.Number)
+-	if !ok {
+-		t.Fatal("read failed")
+-	}
+-	vint, err := number.Int64()
+-	if err != nil {
+-		t.Fatal("convert failed")
+-	}
+-	if vint != 4899710515899924123 {
+-		t.Fatal("read failed")
+-	}
+-	vfloat, err := number.Float64()
+-	if err != nil {
+-		t.Fatal("convert failed")
+-	}
+-	// match the default behaviour
+-	vstring := strconv.FormatFloat(vfloat, 'e', 15, 64)
+-	if vstring != "4.899710515899924e+18" {
+-		t.Fatal("convert float64 failed")
+-	}
+-}
+-
+-func TestReadEntityJsonNumberNonCached(t *testing.T) {
+-	SetCacheReadEntity(false)
+-	bodyReader := strings.NewReader(`{"Value" : 4899710515899924123}`)
+-	httpRequest, _ := http.NewRequest("GET", "/test", bodyReader)
+-	httpRequest.Header.Set("Content-Type", "application/json")
+-	request := &Request{Request: httpRequest}
+-	any := make(Anything)
+-	request.ReadEntity(&any)
+-	number, ok := any["Value"].(json.Number)
+-	if !ok {
+-		t.Fatal("read failed")
+-	}
+-	vint, err := number.Int64()
+-	if err != nil {
+-		t.Fatal("convert failed")
+-	}
+-	if vint != 4899710515899924123 {
+-		t.Fatal("read failed")
+-	}
+-	vfloat, err := number.Float64()
+-	if err != nil {
+-		t.Fatal("convert failed")
+-	}
+-	// match the default behaviour
+-	vstring := strconv.FormatFloat(vfloat, 'e', 15, 64)
+-	if vstring != "4.899710515899924e+18" {
+-		t.Fatal("convert float64 failed")
+-	}
+-}
+-
+-func TestReadEntityJsonLong(t *testing.T) {
+-	bodyReader := strings.NewReader(`{"ValueFloat" : 4899710515899924123, "ValueInt": 4899710515899924123}`)
+-	httpRequest, _ := http.NewRequest("GET", "/test", bodyReader)
+-	httpRequest.Header.Set("Content-Type", "application/json")
+-	request := &Request{Request: httpRequest}
+-	number := new(Number)
+-	request.ReadEntity(&number)
+-	if number.ValueInt != 4899710515899924123 {
+-		t.Fatal("read failed")
+-	}
+-	// match the default behaviour
+-	vstring := strconv.FormatFloat(number.ValueFloat, 'e', 15, 64)
+-	if vstring != "4.899710515899924e+18" {
+-		t.Fatal("convert float64 failed")
+-	}
+-}
+-
+-func TestBodyParameter(t *testing.T) {
+-	bodyReader := strings.NewReader(`value1=42&value2=43`)
+-	httpRequest, _ := http.NewRequest("POST", "/test?value1=44", bodyReader) // POST and PUT body parameters take precedence over URL query string
+-	httpRequest.Header.Set("Content-Type", "application/x-www-form-urlencoded; charset=UTF-8")
+-	request := NewRequest(httpRequest)
+-	v1, err := request.BodyParameter("value1")
+-	if err != nil {
+-		t.Error(err)
+-	}
+-	v2, err := request.BodyParameter("value2")
+-	if err != nil {
+-		t.Error(err)
+-	}
+-	if v1 != "42" || v2 != "43" {
+-		t.Fatal("read failed")
+-	}
+-}
+-
+-func TestReadEntityUnkown(t *testing.T) {
+-	bodyReader := strings.NewReader("?")
+-	httpRequest, _ := http.NewRequest("GET", "/test", bodyReader)
+-	httpRequest.Header.Set("Content-Type", "application/rubbish")
+-	request := NewRequest(httpRequest)
+-	sam := new(Sample)
+-	err := request.ReadEntity(sam)
+-	if err == nil {
+-		t.Fatal("read should be in error")
+-	}
+-}
+-
+-func TestSetAttribute(t *testing.T) {
+-	bodyReader := strings.NewReader("?")
+-	httpRequest, _ := http.NewRequest("GET", "/test", bodyReader)
+-	request := NewRequest(httpRequest)
+-	request.SetAttribute("go", "there")
+-	there := request.Attribute("go")
+-	if there != "there" {
+-		t.Fatalf("missing request attribute:%v", there)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/response.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/response.go
+deleted file mode 100644
+index 0a3cbd5..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/response.go
++++ /dev/null
+@@ -1,241 +0,0 @@
+-package restful
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-import (
+-	"encoding/json"
+-	"encoding/xml"
+-	"net/http"
+-	"strings"
+-)
+-
+-// DEPRECATED, use DefaultResponseContentType(mime)
+-var DefaultResponseMimeType string
+-
+-//PrettyPrintResponses controls the indentation feature of XML and JSON
+-//serialization in the response methods WriteEntity, WriteAsJson, and
+-//WriteAsXml.
+-var PrettyPrintResponses = true
+-
+-// Response is a wrapper on the actual http ResponseWriter
+-// It provides several convenience methods to prepare and write response content.
+-type Response struct {
+-	http.ResponseWriter
+-	requestAccept string   // mime-type what the Http Request says it wants to receive
+-	routeProduces []string // mime-types what the Route says it can produce
+-	statusCode    int      // HTTP status code that has been written explicity (if zero then net/http has written 200)
+-	contentLength int      // number of bytes written for the response body
+-	prettyPrint   bool     // controls the indentation feature of XML and JSON serialization. It is initialized using var PrettyPrintResponses.
+-}
+-
+-// Creates a new response based on a http ResponseWriter.
+-func NewResponse(httpWriter http.ResponseWriter) *Response {
+-	return &Response{httpWriter, "", []string{}, http.StatusOK, 0, PrettyPrintResponses} // empty content-types
+-}
+-
+-// If Accept header matching fails, fall back to this type, otherwise
+-// a "406: Not Acceptable" response is returned.
+-// Valid values are restful.MIME_JSON and restful.MIME_XML
+-// Example:
+-// 	restful.DefaultResponseContentType(restful.MIME_JSON)
+-func DefaultResponseContentType(mime string) {
+-	DefaultResponseMimeType = mime
+-}
+-
+-// InternalServerError writes the StatusInternalServerError header.
+-// DEPRECATED, use WriteErrorString(http.StatusInternalServerError,reason)
+-func (r Response) InternalServerError() Response {
+-	r.WriteHeader(http.StatusInternalServerError)
+-	return r
+-}
+-
+-// PrettyPrint changes whether this response must produce pretty (line-by-line, indented) JSON or XML output.
+-func (r *Response) PrettyPrint(bePretty bool) {
+-	r.prettyPrint = bePretty
+-}
+-
+-// AddHeader is a shortcut for .Header().Add(header,value)
+-func (r Response) AddHeader(header string, value string) Response {
+-	r.Header().Add(header, value)
+-	return r
+-}
+-
+-// SetRequestAccepts tells the response what Mime-type(s) the HTTP request said it wants to accept. Exposed for testing.
+-func (r *Response) SetRequestAccepts(mime string) {
+-	r.requestAccept = mime
+-}
+-
+-// WriteEntity marshals the value using the representation denoted by the Accept Header (XML or JSON)
+-// If no Accept header is specified (or */*) then return the Content-Type as specified by the first in the Route.Produces.
+-// If an Accept header is specified then return the Content-Type as specified by the first in the Route.Produces that is matched with the Accept header.
+-// If the value is nil then nothing is written. You may want to call WriteHeader(http.StatusNotFound) instead.
+-// Current implementation ignores any q-parameters in the Accept Header.
+-func (r *Response) WriteEntity(value interface{}) error {
+-	if value == nil { // do not write a nil representation
+-		return nil
+-	}
+-	for _, qualifiedMime := range strings.Split(r.requestAccept, ",") {
+-		mime := strings.Trim(strings.Split(qualifiedMime, ";")[0], " ")
+-		if 0 == len(mime) || mime == "*/*" {
+-			for _, each := range r.routeProduces {
+-				if MIME_JSON == each {
+-					return r.WriteAsJson(value)
+-				}
+-				if MIME_XML == each {
+-					return r.WriteAsXml(value)
+-				}
+-			}
+-		} else { // mime is not blank; see if we have a match in Produces
+-			for _, each := range r.routeProduces {
+-				if mime == each {
+-					if MIME_JSON == each {
+-						return r.WriteAsJson(value)
+-					}
+-					if MIME_XML == each {
+-						return r.WriteAsXml(value)
+-					}
+-				}
+-			}
+-		}
+-	}
+-	if DefaultResponseMimeType == MIME_JSON {
+-		return r.WriteAsJson(value)
+-	} else if DefaultResponseMimeType == MIME_XML {
+-		return r.WriteAsXml(value)
+-	} else {
+-		if trace {
+-			traceLogger.Printf("mismatch in mime-types and no defaults; (http)Accept=%v,(route)Produces=%v\n", r.requestAccept, r.routeProduces)
+-		}
+-		r.WriteHeader(http.StatusNotAcceptable) // for recording only
+-		r.ResponseWriter.WriteHeader(http.StatusNotAcceptable)
+-		if _, err := r.Write([]byte("406: Not Acceptable")); err != nil {
+-			return err
+-		}
+-	}
+-	return nil
+-}
+-
+-// WriteAsXml is a convenience method for writing a value in xml (requires Xml tags on the value)
+-func (r *Response) WriteAsXml(value interface{}) error {
+-	var output []byte
+-	var err error
+-
+-	if value == nil { // do not write a nil representation
+-		return nil
+-	}
+-	if r.prettyPrint {
+-		output, err = xml.MarshalIndent(value, " ", " ")
+-	} else {
+-		output, err = xml.Marshal(value)
+-	}
+-
+-	if err != nil {
+-		return r.WriteError(http.StatusInternalServerError, err)
+-	}
+-	r.Header().Set(HEADER_ContentType, MIME_XML)
+-	if r.statusCode > 0 { // a WriteHeader was intercepted
+-		r.ResponseWriter.WriteHeader(r.statusCode)
+-	}
+-	_, err = r.Write([]byte(xml.Header))
+-	if err != nil {
+-		return err
+-	}
+-	if _, err = r.Write(output); err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-// WriteAsJson is a convenience method for writing a value in json
+-func (r *Response) WriteAsJson(value interface{}) error {
+-	var output []byte
+-	var err error
+-
+-	if value == nil { // do not write a nil representation
+-		return nil
+-	}
+-	if r.prettyPrint {
+-		output, err = json.MarshalIndent(value, " ", " ")
+-	} else {
+-		output, err = json.Marshal(value)
+-	}
+-
+-	if err != nil {
+-		return r.WriteErrorString(http.StatusInternalServerError, err.Error())
+-	}
+-	r.Header().Set(HEADER_ContentType, MIME_JSON)
+-	if r.statusCode > 0 { // a WriteHeader was intercepted
+-		r.ResponseWriter.WriteHeader(r.statusCode)
+-	}
+-	if _, err = r.Write(output); err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-// WriteError write the http status and the error string on the response.
+-func (r *Response) WriteError(httpStatus int, err error) error {
+-	return r.WriteErrorString(httpStatus, err.Error())
+-}
+-
+-// WriteServiceError is a convenience method for a responding with a ServiceError and a status
+-func (r *Response) WriteServiceError(httpStatus int, err ServiceError) error {
+-	r.WriteHeader(httpStatus) // for recording only
+-	return r.WriteEntity(err)
+-}
+-
+-// WriteErrorString is a convenience method for an error status with the actual error
+-func (r *Response) WriteErrorString(status int, errorReason string) error {
+-	r.statusCode = status // for recording only
+-	r.ResponseWriter.WriteHeader(status)
+-	if _, err := r.Write([]byte(errorReason)); err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-// WriteHeader is overridden to remember the Status Code that has been written.
+-// Note that using this method, the status value is only written when
+-// - calling WriteEntity,
+-// - or directly calling WriteAsXml or WriteAsJson,
+-// - or if the status is one for which no response is allowed (i.e.,
+-//   204 (http.StatusNoContent) or 304 (http.StatusNotModified))
+-func (r *Response) WriteHeader(httpStatus int) {
+-	r.statusCode = httpStatus
+-	// if 204 then WriteEntity will not be called so we need to pass this code
+-	if http.StatusNoContent == httpStatus ||
+-		http.StatusNotModified == httpStatus {
+-		r.ResponseWriter.WriteHeader(httpStatus)
+-	}
+-}
+-
+-// StatusCode returns the code that has been written using WriteHeader.
+-func (r Response) StatusCode() int {
+-	if 0 == r.statusCode {
+-		// no status code has been written yet; assume OK
+-		return http.StatusOK
+-	}
+-	return r.statusCode
+-}
+-
+-// Write writes the data to the connection as part of an HTTP reply.
+-// Write is part of http.ResponseWriter interface.
+-func (r *Response) Write(bytes []byte) (int, error) {
+-	written, err := r.ResponseWriter.Write(bytes)
+-	r.contentLength += written
+-	return written, err
+-}
+-
+-// ContentLength returns the number of bytes written for the response content.
+-// Note that this value is only correct if all data is written through the Response using its Write* methods.
+-// Data written directly using the underlying http.ResponseWriter is not accounted for.
+-func (r Response) ContentLength() int {
+-	return r.contentLength
+-}
+-
+-// CloseNotify is part of http.CloseNotifier interface
+-func (r Response) CloseNotify() <-chan bool {
+-	return r.ResponseWriter.(http.CloseNotifier).CloseNotify()
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/response_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/response_test.go
+deleted file mode 100644
+index ee9a74f..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/response_test.go
++++ /dev/null
+@@ -1,157 +0,0 @@
+-package restful
+-
+-import (
+-	"errors"
+-	"net/http"
+-	"net/http/httptest"
+-	"testing"
+-)
+-
+-func TestWriteHeader(t *testing.T) {
+-	httpWriter := httptest.NewRecorder()
+-	resp := Response{httpWriter, "*/*", []string{"*/*"}, 0, 0, true}
+-	resp.WriteHeader(123)
+-	if resp.StatusCode() != 123 {
+-		t.Errorf("Unexpected status code:%d", resp.StatusCode())
+-	}
+-}
+-
+-func TestNoWriteHeader(t *testing.T) {
+-	httpWriter := httptest.NewRecorder()
+-	resp := Response{httpWriter, "*/*", []string{"*/*"}, 0, 0, true}
+-	if resp.StatusCode() != http.StatusOK {
+-		t.Errorf("Unexpected status code:%d", resp.StatusCode())
+-	}
+-}
+-
+-type food struct {
+-	Kind string
+-}
+-
+-// go test -v -test.run TestMeasureContentLengthXml ...restful
+-func TestMeasureContentLengthXml(t *testing.T) {
+-	httpWriter := httptest.NewRecorder()
+-	resp := Response{httpWriter, "*/*", []string{"*/*"}, 0, 0, true}
+-	resp.WriteAsXml(food{"apple"})
+-	if resp.ContentLength() != 76 {
+-		t.Errorf("Incorrect measured length:%d", resp.ContentLength())
+-	}
+-}
+-
+-// go test -v -test.run TestMeasureContentLengthJson ...restful
+-func TestMeasureContentLengthJson(t *testing.T) {
+-	httpWriter := httptest.NewRecorder()
+-	resp := Response{httpWriter, "*/*", []string{"*/*"}, 0, 0, true}
+-	resp.WriteAsJson(food{"apple"})
+-	if resp.ContentLength() != 22 {
+-		t.Errorf("Incorrect measured length:%d", resp.ContentLength())
+-	}
+-}
+-
+-// go test -v -test.run TestMeasureContentLengthJsonNotPretty ...restful
+-func TestMeasureContentLengthJsonNotPretty(t *testing.T) {
+-	httpWriter := httptest.NewRecorder()
+-	resp := Response{httpWriter, "*/*", []string{"*/*"}, 0, 0, false}
+-	resp.WriteAsJson(food{"apple"})
+-	if resp.ContentLength() != 16 {
+-		t.Errorf("Incorrect measured length:%d", resp.ContentLength())
+-	}
+-}
+-
+-// go test -v -test.run TestMeasureContentLengthWriteErrorString ...restful
+-func TestMeasureContentLengthWriteErrorString(t *testing.T) {
+-	httpWriter := httptest.NewRecorder()
+-	resp := Response{httpWriter, "*/*", []string{"*/*"}, 0, 0, true}
+-	resp.WriteErrorString(404, "Invalid")
+-	if resp.ContentLength() != len("Invalid") {
+-		t.Errorf("Incorrect measured length:%d", resp.ContentLength())
+-	}
+-}
+-
+-// go test -v -test.run TestStatusCreatedAndContentTypeJson_Issue54 ...restful
+-func TestStatusCreatedAndContentTypeJson_Issue54(t *testing.T) {
+-	httpWriter := httptest.NewRecorder()
+-	resp := Response{httpWriter, "application/json", []string{"application/json"}, 0, 0, true}
+-	resp.WriteHeader(201)
+-	resp.WriteAsJson(food{"Juicy"})
+-	if httpWriter.HeaderMap.Get("Content-Type") != "application/json" {
+-		t.Errorf("Expected content type json but got:%d", httpWriter.HeaderMap.Get("Content-Type"))
+-	}
+-	if httpWriter.Code != 201 {
+-		t.Errorf("Expected status 201 but got:%d", httpWriter.Code)
+-	}
+-}
+-
+-type errorOnWriteRecorder struct {
+-	*httptest.ResponseRecorder
+-}
+-
+-func (e errorOnWriteRecorder) Write(bytes []byte) (int, error) {
+-	return 0, errors.New("fail")
+-}
+-
+-// go test -v -test.run TestLastWriteErrorCaught ...restful
+-func TestLastWriteErrorCaught(t *testing.T) {
+-	httpWriter := errorOnWriteRecorder{httptest.NewRecorder()}
+-	resp := Response{httpWriter, "application/json", []string{"application/json"}, 0, 0, true}
+-	err := resp.WriteAsJson(food{"Juicy"})
+-	if err.Error() != "fail" {
+-		t.Errorf("Unexpected error message:%v", err)
+-	}
+-}
+-
+-// go test -v -test.run TestAcceptStarStar_Issue83 ...restful
+-func TestAcceptStarStar_Issue83(t *testing.T) {
+-	httpWriter := httptest.NewRecorder()
+-	//								Accept									Produces
+-	resp := Response{httpWriter, "application/bogus,*/*;q=0.8", []string{"application/json"}, 0, 0, true}
+-	resp.WriteEntity(food{"Juicy"})
+-	ct := httpWriter.Header().Get("Content-Type")
+-	if "application/json" != ct {
+-		t.Errorf("Unexpected content type:%s", ct)
+-	}
+-}
+-
+-// go test -v -test.run TestAcceptSkipStarStar_Issue83 ...restful
+-func TestAcceptSkipStarStar_Issue83(t *testing.T) {
+-	httpWriter := httptest.NewRecorder()
+-	//								Accept									Produces
+-	resp := Response{httpWriter, " application/xml ,*/* ; q=0.8", []string{"application/json", "application/xml"}, 0, 0, true}
+-	resp.WriteEntity(food{"Juicy"})
+-	ct := httpWriter.Header().Get("Content-Type")
+-	if "application/xml" != ct {
+-		t.Errorf("Unexpected content type:%s", ct)
+-	}
+-}
+-
+-// go test -v -test.run TestAcceptXmlBeforeStarStar_Issue83 ...restful
+-func TestAcceptXmlBeforeStarStar_Issue83(t *testing.T) {
+-	httpWriter := httptest.NewRecorder()
+-	//								Accept									Produces
+-	resp := Response{httpWriter, "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8", []string{"application/json"}, 0, 0, true}
+-	resp.WriteEntity(food{"Juicy"})
+-	ct := httpWriter.Header().Get("Content-Type")
+-	if "application/json" != ct {
+-		t.Errorf("Unexpected content type:%s", ct)
+-	}
+-}
+-
+-// go test -v -test.run TestWriteHeaderNoContent_Issue124 ...restful
+-func TestWriteHeaderNoContent_Issue124(t *testing.T) {
+-	httpWriter := httptest.NewRecorder()
+-	resp := Response{httpWriter, "text/plain", []string{"text/plain"}, 0, 0, true}
+-	resp.WriteHeader(http.StatusNoContent)
+-	if httpWriter.Code != http.StatusNoContent {
+-		t.Errorf("got %d want %d", httpWriter.Code, http.StatusNoContent)
+-	}
+-}
+-
+-// go test -v -test.run TestStatusCreatedAndContentTypeJson_Issue163 ...restful
+-func TestStatusCreatedAndContentTypeJson_Issue163(t *testing.T) {
+-	httpWriter := httptest.NewRecorder()
+-	resp := Response{httpWriter, "application/json", []string{"application/json"}, 0, 0, true}
+-	resp.WriteHeader(http.StatusNotModified)
+-	if httpWriter.Code != http.StatusNotModified {
+-		t.Errorf("Got %d want %d", httpWriter.Code, http.StatusNotModified)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/route.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/route.go
+deleted file mode 100644
+index 59d6e23..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/route.go
++++ /dev/null
+@@ -1,166 +0,0 @@
+-package restful
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-import (
+-	"bytes"
+-	"net/http"
+-	"strings"
+-)
+-
+-// RouteFunction declares the signature of a function that can be bound to a Route.
+-type RouteFunction func(*Request, *Response)
+-
+-// Route binds a HTTP Method,Path,Consumes combination to a RouteFunction.
+-type Route struct {
+-	Method   string
+-	Produces []string
+-	Consumes []string
+-	Path     string // webservice root path + described path
+-	Function RouteFunction
+-	Filters  []FilterFunction
+-
+-	// cached values for dispatching
+-	relativePath string
+-	pathParts    []string
+-	pathExpr     *pathExpression // cached compilation of relativePath as RegExp
+-
+-	// documentation
+-	Doc                     string
+-	Operation               string
+-	ParameterDocs           []*Parameter
+-	ResponseErrors          map[int]ResponseError
+-	ReadSample, WriteSample interface{} // structs that model an example request or response payload
+-}
+-
+-// Initialize for Route
+-func (r *Route) postBuild() {
+-	r.pathParts = tokenizePath(r.Path)
+-}
+-
+-// Create Request and Response from their http versions
+-func (r *Route) wrapRequestResponse(httpWriter http.ResponseWriter, httpRequest *http.Request) (*Request, *Response) {
+-	params := r.extractParameters(httpRequest.URL.Path)
+-	wrappedRequest := NewRequest(httpRequest)
+-	wrappedRequest.pathParameters = params
+-	wrappedRequest.selectedRoutePath = r.Path
+-	wrappedResponse := NewResponse(httpWriter)
+-	wrappedResponse.requestAccept = httpRequest.Header.Get(HEADER_Accept)
+-	wrappedResponse.routeProduces = r.Produces
+-	return wrappedRequest, wrappedResponse
+-}
+-
+-// dispatchWithFilters call the function after passing through its own filters
+-func (r *Route) dispatchWithFilters(wrappedRequest *Request, wrappedResponse *Response) {
+-	if len(r.Filters) > 0 {
+-		chain := FilterChain{Filters: r.Filters, Target: r.Function}
+-		chain.ProcessFilter(wrappedRequest, wrappedResponse)
+-	} else {
+-		// unfiltered
+-		r.Function(wrappedRequest, wrappedResponse)
+-	}
+-}
+-
+-// Return whether the mimeType matches to what this Route can produce.
+-func (r Route) matchesAccept(mimeTypesWithQuality string) bool {
+-	parts := strings.Split(mimeTypesWithQuality, ",")
+-	for _, each := range parts {
+-		var withoutQuality string
+-		if strings.Contains(each, ";") {
+-			withoutQuality = strings.Split(each, ";")[0]
+-		} else {
+-			withoutQuality = each
+-		}
+-		// trim before compare
+-		withoutQuality = strings.Trim(withoutQuality, " ")
+-		if withoutQuality == "*/*" {
+-			return true
+-		}
+-		for _, other := range r.Produces {
+-			if other == withoutQuality {
+-				return true
+-			}
+-		}
+-	}
+-	return false
+-}
+-
+-// Return whether the mimeType matches to what this Route can consume.
+-func (r Route) matchesContentType(mimeTypes string) bool {
+-	parts := strings.Split(mimeTypes, ",")
+-	for _, each := range parts {
+-		var contentType string
+-		if strings.Contains(each, ";") {
+-			contentType = strings.Split(each, ";")[0]
+-		} else {
+-			contentType = each
+-		}
+-		// trim before compare
+-		contentType = strings.Trim(contentType, " ")
+-		for _, other := range r.Consumes {
+-			if other == "*/*" || other == contentType {
+-				return true
+-			}
+-		}
+-	}
+-	return false
+-}
+-
+-// Extract the parameters from the request url path
+-func (r Route) extractParameters(urlPath string) map[string]string {
+-	urlParts := tokenizePath(urlPath)
+-	pathParameters := map[string]string{}
+-	for i, key := range r.pathParts {
+-		var value string
+-		if i >= len(urlParts) {
+-			value = ""
+-		} else {
+-			value = urlParts[i]
+-		}
+-		if strings.HasPrefix(key, "{") { // path-parameter
+-			if colon := strings.Index(key, ":"); colon != -1 {
+-				// extract by regex
+-				regPart := key[colon+1 : len(key)-1]
+-				keyPart := key[1:colon]
+-				if regPart == "*" {
+-					pathParameters[keyPart] = untokenizePath(i, urlParts)
+-					break
+-				} else {
+-					pathParameters[keyPart] = value
+-				}
+-			} else {
+-				// without enclosing {}
+-				pathParameters[key[1:len(key)-1]] = value
+-			}
+-		}
+-	}
+-	return pathParameters
+-}
+-
+-// Untokenize back into an URL path using the slash separator
+-func untokenizePath(offset int, parts []string) string {
+-	var buffer bytes.Buffer
+-	for p := offset; p < len(parts); p++ {
+-		buffer.WriteString(parts[p])
+-		// do not end
+-		if p < len(parts)-1 {
+-			buffer.WriteString("/")
+-		}
+-	}
+-	return buffer.String()
+-}
+-
+-// Tokenize an URL path using the slash separator ; the result does not have empty tokens
+-func tokenizePath(path string) []string {
+-	if "/" == path {
+-		return []string{}
+-	}
+-	return strings.Split(strings.Trim(path, "/"), "/")
+-}
+-
+-// for debugging
+-func (r Route) String() string {
+-	return r.Method + " " + r.Path
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/route_builder.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/route_builder.go
+deleted file mode 100644
+index 8f46619..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/route_builder.go
++++ /dev/null
+@@ -1,208 +0,0 @@
+-package restful
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-import (
+-	"log"
+-	"reflect"
+-	"strings"
+-)
+-
+-// RouteBuilder is a helper to construct Routes.
+-type RouteBuilder struct {
+-	rootPath    string
+-	currentPath string
+-	produces    []string
+-	consumes    []string
+-	httpMethod  string        // required
+-	function    RouteFunction // required
+-	filters     []FilterFunction
+-	// documentation
+-	doc                     string
+-	operation               string
+-	readSample, writeSample interface{}
+-	parameters              []*Parameter
+-	errorMap                map[int]ResponseError
+-}
+-
+-// Do evaluates each argument with the RouteBuilder itself.
+-// This allows you to follow DRY principles without breaking the fluent programming style.
+-// Example:
+-// 		ws.Route(ws.DELETE("/{name}").To(t.deletePerson).Do(Returns200, Returns500))
+-//
+-//		func Returns500(b *RouteBuilder) {
+-//			b.Returns(500, "Internal Server Error", restful.ServiceError{})
+-//		}
+-func (b *RouteBuilder) Do(oneArgBlocks ...func(*RouteBuilder)) *RouteBuilder {
+-	for _, each := range oneArgBlocks {
+-		each(b)
+-	}
+-	return b
+-}
+-
+-// To bind the route to a function.
+-// If this route is matched with the incoming Http Request then call this function with the *Request,*Response pair. Required.
+-func (b *RouteBuilder) To(function RouteFunction) *RouteBuilder {
+-	b.function = function
+-	return b
+-}
+-
+-// Method specifies what HTTP method to match. Required.
+-func (b *RouteBuilder) Method(method string) *RouteBuilder {
+-	b.httpMethod = method
+-	return b
+-}
+-
+-// Produces specifies what MIME types can be produced ; the matched one will appear in the Content-Type Http header.
+-func (b *RouteBuilder) Produces(mimeTypes ...string) *RouteBuilder {
+-	b.produces = mimeTypes
+-	return b
+-}
+-
+-// Consumes specifies what MIME types can be consumes ; the Accept Http header must matched any of these
+-func (b *RouteBuilder) Consumes(mimeTypes ...string) *RouteBuilder {
+-	b.consumes = mimeTypes
+-	return b
+-}
+-
+-// Path specifies the relative (w.r.t WebService root path) URL path to match. Default is "/".
+-func (b *RouteBuilder) Path(subPath string) *RouteBuilder {
+-	b.currentPath = subPath
+-	return b
+-}
+-
+-// Doc tells what this route is all about. Optional.
+-func (b *RouteBuilder) Doc(documentation string) *RouteBuilder {
+-	b.doc = documentation
+-	return b
+-}
+-
+-// Reads tells what resource type will be read from the request payload. Optional.
+-// A parameter of type "body" is added ,required is set to true and the dataType is set to the qualified name of the sample's type.
+-func (b *RouteBuilder) Reads(sample interface{}) *RouteBuilder {
+-	b.readSample = sample
+-	typeAsName := reflect.TypeOf(sample).String()
+-	bodyParameter := &Parameter{&ParameterData{Name: "body"}}
+-	bodyParameter.beBody()
+-	bodyParameter.Required(true)
+-	bodyParameter.DataType(typeAsName)
+-	b.Param(bodyParameter)
+-	return b
+-}
+-
+-// ParameterNamed returns a Parameter already known to the RouteBuilder. Returns nil if not.
+-// Use this to modify or extend information for the Parameter (through its Data()).
+-func (b RouteBuilder) ParameterNamed(name string) (p *Parameter) {
+-	for _, each := range b.parameters {
+-		if each.Data().Name == name {
+-			return each
+-		}
+-	}
+-	return p
+-}
+-
+-// Writes tells what resource type will be written as the response payload. Optional.
+-func (b *RouteBuilder) Writes(sample interface{}) *RouteBuilder {
+-	b.writeSample = sample
+-	return b
+-}
+-
+-// Param allows you to document the parameters of the Route. It adds a new Parameter (does not check for duplicates).
+-func (b *RouteBuilder) Param(parameter *Parameter) *RouteBuilder {
+-	if b.parameters == nil {
+-		b.parameters = []*Parameter{}
+-	}
+-	b.parameters = append(b.parameters, parameter)
+-	return b
+-}
+-
+-// Operation allows you to document what the acutal method/function call is of the Route.
+-func (b *RouteBuilder) Operation(name string) *RouteBuilder {
+-	b.operation = name
+-	return b
+-}
+-
+-// ReturnsError is deprecated, use Returns instead.
+-func (b *RouteBuilder) ReturnsError(code int, message string, model interface{}) *RouteBuilder {
+-	log.Println("ReturnsError is deprecated, use Returns instead.")
+-	return b.Returns(code, message, model)
+-}
+-
+-// Returns allows you to document what responses (errors or regular) can be expected.
+-// The model parameter is optional ; either pass a struct instance or use nil if not applicable.
+-func (b *RouteBuilder) Returns(code int, message string, model interface{}) *RouteBuilder {
+-	err := ResponseError{
+-		Code:    code,
+-		Message: message,
+-		Model:   model,
+-	}
+-	// lazy init because there is no NewRouteBuilder (yet)
+-	if b.errorMap == nil {
+-		b.errorMap = map[int]ResponseError{}
+-	}
+-	b.errorMap[code] = err
+-	return b
+-}
+-
+-type ResponseError struct {
+-	Code    int
+-	Message string
+-	Model   interface{}
+-}
+-
+-func (b *RouteBuilder) servicePath(path string) *RouteBuilder {
+-	b.rootPath = path
+-	return b
+-}
+-
+-// Filter appends a FilterFunction to the end of filters for this Route to build.
+-func (b *RouteBuilder) Filter(filter FilterFunction) *RouteBuilder {
+-	b.filters = append(b.filters, filter)
+-	return b
+-}
+-
+-// If no specific Route path then set to rootPath
+-// If no specific Produces then set to rootProduces
+-// If no specific Consumes then set to rootConsumes
+-func (b *RouteBuilder) copyDefaults(rootProduces, rootConsumes []string) {
+-	if len(b.produces) == 0 {
+-		b.produces = rootProduces
+-	}
+-	if len(b.consumes) == 0 {
+-		b.consumes = rootConsumes
+-	}
+-}
+-
+-// Build creates a new Route using the specification details collected by the RouteBuilder
+-func (b *RouteBuilder) Build() Route {
+-	pathExpr, err := newPathExpression(b.currentPath)
+-	if err != nil {
+-		log.Fatalf("[restful] Invalid path:%s because:%v", b.currentPath, err)
+-	}
+-	if b.function == nil {
+-		log.Fatalf("[restful] No function specified for route:" + b.currentPath)
+-	}
+-	route := Route{
+-		Method:         b.httpMethod,
+-		Path:           concatPath(b.rootPath, b.currentPath),
+-		Produces:       b.produces,
+-		Consumes:       b.consumes,
+-		Function:       b.function,
+-		Filters:        b.filters,
+-		relativePath:   b.currentPath,
+-		pathExpr:       pathExpr,
+-		Doc:            b.doc,
+-		Operation:      b.operation,
+-		ParameterDocs:  b.parameters,
+-		ResponseErrors: b.errorMap,
+-		ReadSample:     b.readSample,
+-		WriteSample:    b.writeSample}
+-	route.postBuild()
+-	return route
+-}
+-
+-func concatPath(path1, path2 string) string {
+-	return strings.TrimRight(path1, "/") + "/" + strings.TrimLeft(path2, "/")
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/route_builder_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/route_builder_test.go
+deleted file mode 100644
+index 42ec689..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/route_builder_test.go
++++ /dev/null
+@@ -1,55 +0,0 @@
+-package restful
+-
+-import (
+-	"testing"
+-)
+-
+-func TestRouteBuilder_PathParameter(t *testing.T) {
+-	p := &Parameter{&ParameterData{Name: "name", Description: "desc"}}
+-	p.AllowMultiple(true)
+-	p.DataType("int")
+-	p.Required(true)
+-	values := map[string]string{"a": "b"}
+-	p.AllowableValues(values)
+-	p.bePath()
+-
+-	b := new(RouteBuilder)
+-	b.function = dummy
+-	b.Param(p)
+-	r := b.Build()
+-	if !r.ParameterDocs[0].Data().AllowMultiple {
+-		t.Error("AllowMultiple invalid")
+-	}
+-	if r.ParameterDocs[0].Data().DataType != "int" {
+-		t.Error("dataType invalid")
+-	}
+-	if !r.ParameterDocs[0].Data().Required {
+-		t.Error("required invalid")
+-	}
+-	if r.ParameterDocs[0].Data().Kind != PathParameterKind {
+-		t.Error("kind invalid")
+-	}
+-	if r.ParameterDocs[0].Data().AllowableValues["a"] != "b" {
+-		t.Error("allowableValues invalid")
+-	}
+-	if b.ParameterNamed("name") == nil {
+-		t.Error("access to parameter failed")
+-	}
+-}
+-
+-func TestRouteBuilder(t *testing.T) {
+-	json := "application/json"
+-	b := new(RouteBuilder)
+-	b.To(dummy)
+-	b.Path("/routes").Method("HEAD").Consumes(json).Produces(json)
+-	r := b.Build()
+-	if r.Path != "/routes" {
+-		t.Error("path invalid")
+-	}
+-	if r.Produces[0] != json {
+-		t.Error("produces invalid")
+-	}
+-	if r.Consumes[0] != json {
+-		t.Error("consumes invalid")
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/route_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/route_test.go
+deleted file mode 100644
+index a416576..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/route_test.go
++++ /dev/null
+@@ -1,108 +0,0 @@
+-package restful
+-
+-import (
+-	"testing"
+-)
+-
+-// accept should match produces
+-func TestMatchesAcceptStar(t *testing.T) {
+-	r := Route{Produces: []string{"application/xml"}}
+-	if !r.matchesAccept("*/*") {
+-		t.Errorf("accept should match star")
+-	}
+-}
+-
+-// accept should match produces
+-func TestMatchesAcceptIE(t *testing.T) {
+-	r := Route{Produces: []string{"application/xml"}}
+-	if !r.matchesAccept("text/html, application/xhtml+xml, */*") {
+-		t.Errorf("accept should match star")
+-	}
+-}
+-
+-// accept should match produces
+-func TestMatchesAcceptXml(t *testing.T) {
+-	r := Route{Produces: []string{"application/xml"}}
+-	if r.matchesAccept("application/json") {
+-		t.Errorf("accept should not match json")
+-	}
+-	if !r.matchesAccept("application/xml") {
+-		t.Errorf("accept should match xml")
+-	}
+-}
+-
+-// content type should match consumes
+-func TestMatchesContentTypeXml(t *testing.T) {
+-	r := Route{Consumes: []string{"application/xml"}}
+-	if r.matchesContentType("application/json") {
+-		t.Errorf("accept should not match json")
+-	}
+-	if !r.matchesContentType("application/xml") {
+-		t.Errorf("accept should match xml")
+-	}
+-}
+-
+-// content type should match consumes
+-func TestMatchesContentTypeCharsetInformation(t *testing.T) {
+-	r := Route{Consumes: []string{"application/json"}}
+-	if !r.matchesContentType("application/json; charset=UTF-8") {
+-		t.Errorf("matchesContentType should ignore charset information")
+-	}
+-}
+-
+-func TestMatchesPath_OneParam(t *testing.T) {
+-	params := doExtractParams("/from/{source}", 2, "/from/here", t)
+-	if params["source"] != "here" {
+-		t.Errorf("parameter mismatch here")
+-	}
+-}
+-
+-func TestMatchesPath_Slash(t *testing.T) {
+-	params := doExtractParams("/", 0, "/", t)
+-	if len(params) != 0 {
+-		t.Errorf("expected empty parameters")
+-	}
+-}
+-
+-func TestMatchesPath_SlashNonVar(t *testing.T) {
+-	params := doExtractParams("/any", 1, "/any", t)
+-	if len(params) != 0 {
+-		t.Errorf("expected empty parameters")
+-	}
+-}
+-
+-func TestMatchesPath_TwoVars(t *testing.T) {
+-	params := doExtractParams("/from/{source}/to/{destination}", 4, "/from/AMS/to/NY", t)
+-	if params["source"] != "AMS" {
+-		t.Errorf("parameter mismatch AMS")
+-	}
+-}
+-
+-func TestMatchesPath_VarOnFront(t *testing.T) {
+-	params := doExtractParams("{what}/from/{source}/", 3, "who/from/SOS/", t)
+-	if params["source"] != "SOS" {
+-		t.Errorf("parameter mismatch SOS")
+-	}
+-}
+-
+-func TestExtractParameters_EmptyValue(t *testing.T) {
+-	params := doExtractParams("/fixed/{var}", 2, "/fixed/", t)
+-	if params["var"] != "" {
+-		t.Errorf("parameter mismatch var")
+-	}
+-}
+-
+-func TestTokenizePath(t *testing.T) {
+-	if len(tokenizePath("/")) != 0 {
+-		t.Errorf("not empty path tokens")
+-	}
+-}
+-
+-func doExtractParams(routePath string, size int, urlPath string, t *testing.T) map[string]string {
+-	r := Route{Path: routePath}
+-	r.postBuild()
+-	if len(r.pathParts) != size {
+-		t.Fatalf("len not %v %v, but %v", size, r.pathParts, len(r.pathParts))
+-	}
+-	return r.extractParameters(urlPath)
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/router.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/router.go
+deleted file mode 100644
+index 9b32fb6..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/router.go
++++ /dev/null
+@@ -1,18 +0,0 @@
+-package restful
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-import "net/http"
+-
+-// A RouteSelector finds the best matching Route given the input HTTP Request
+-type RouteSelector interface {
+-
+-	// SelectRoute finds a Route given the input HTTP Request and a list of WebServices.
+-	// It returns a selected Route and its containing WebService or an error indicating
+-	// a problem.
+-	SelectRoute(
+-		webServices []*WebService,
+-		httpRequest *http.Request) (selectedService *WebService, selected *Route, err error)
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/service_error.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/service_error.go
+deleted file mode 100644
+index 62d1108..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/service_error.go
++++ /dev/null
+@@ -1,23 +0,0 @@
+-package restful
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-import "fmt"
+-
+-// ServiceError is a transport object to pass information about a non-Http error occurred in a WebService while processing a request.
+-type ServiceError struct {
+-	Code    int
+-	Message string
+-}
+-
+-// NewError returns a ServiceError using the code and reason
+-func NewError(code int, message string) ServiceError {
+-	return ServiceError{Code: code, Message: message}
+-}
+-
+-// Error returns a text representation of the service error
+-func (s ServiceError) Error() string {
+-	return fmt.Sprintf("[ServiceError:%v] %v", s.Code, s.Message)
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/CHANGES.md b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/CHANGES.md
+deleted file mode 100644
+index 9980f2f..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/CHANGES.md
++++ /dev/null
+@@ -1,27 +0,0 @@
+-Change history of swagger
+-=
+-
+-2014-11-14
+-- operation parameters are now sorted using ordering path,query,form,header,body
+-
+-2014-11-12
+-- respect omitempty tag value for embedded structs
+-- expose ApiVersion of WebService to Swagger ApiDeclaration
+-
+-2014-05-29
+-- (api add) Ability to define custom http.Handler to serve swagger-ui static files
+-
+-2014-05-04
+-- (fix) include model for array element type of response
+-
+-2014-01-03
+-- (fix) do not add primitive type to the Api models
+-
+-2013-11-27
+-- (fix) make Swagger work for WebServices with root ("/" or "") paths
+-
+-2013-10-29
+-- (api add) package variable LogInfo to customize logging function
+-
+-2013-10-15
+-- upgraded to spec version 1.2 (https://github.com/wordnik/swagger-core/wiki/1.2-transition)
+\ No newline at end of file
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/README.md b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/README.md
+deleted file mode 100644
+index 2efe8f3..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/README.md
++++ /dev/null
+@@ -1,28 +0,0 @@
+-How to use Swagger UI with go-restful
+-=
+-
+-Get the Swagger UI sources (version 1.2 only)
+-
+-	git clone https://github.com/wordnik/swagger-ui.git
+-	
+-The project contains a "dist" folder.
+-Its contents has all the Swagger UI files you need.
+-
+-The `index.html` has an `url` set to `http://petstore.swagger.wordnik.com/api/api-docs`.
+-You need to change that to match your WebService JSON endpoint  e.g. `http://localhost:8080/apidocs.json`
+-
+-Now, you can install the Swagger WebService for serving the Swagger specification in JSON.
+-
+-	config := swagger.Config{
+-		WebServices:    restful.RegisteredWebServices(),
+-		ApiPath:        "/apidocs.json",
+-		SwaggerPath:     "/apidocs/",
+-		SwaggerFilePath: "/Users/emicklei/Projects/swagger-ui/dist"}
+-	swagger.InstallSwaggerService(config)		
+-	
+-	
+-Notes
+---
+-- Use RouteBuilder.Operation(..) to set the Nickname field of the API spec
+-- The WebServices field of swagger.Config can be used to control which service you want to expose and document ; you can have multiple configs and therefore multiple endpoints.
+-- Use tag "description" to annotate a struct field with a description to show in the UI
+\ No newline at end of file
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/config.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/config.go
+deleted file mode 100644
+index 4fca0fa..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/config.go
++++ /dev/null
+@@ -1,25 +0,0 @@
+-package swagger
+-
+-import (
+-	"net/http"
+-
+-	"github.com/emicklei/go-restful"
+-)
+-
+-type Config struct {
+-	// url where the services are available, e.g. http://localhost:8080
+-	// if left empty then the basePath of Swagger is taken from the actual request
+-	WebServicesUrl string
+-	// path where the JSON api is avaiable , e.g. /apidocs
+-	ApiPath string
+-	// [optional] path where the swagger UI will be served, e.g. /swagger
+-	SwaggerPath string
+-	// [optional] location of folder containing Swagger HTML5 application index.html
+-	SwaggerFilePath string
+-	// api listing is constructed from this list of restful WebServices.
+-	WebServices []*restful.WebService
+-	// will serve all static content (scripts,pages,images)
+-	StaticHandler http.Handler
+-	// [optional] on default CORS (Cross-Origin-Resource-Sharing) is enabled.
+-	DisableCORS bool
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/model_builder.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/model_builder.go
+deleted file mode 100644
+index 68524ec..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/model_builder.go
++++ /dev/null
+@@ -1,277 +0,0 @@
+-package swagger
+-
+-import (
+-	"encoding/json"
+-	"reflect"
+-	"strings"
+-)
+-
+-type modelBuilder struct {
+-	Models map[string]Model
+-}
+-
+-func (b modelBuilder) addModel(st reflect.Type, nameOverride string) {
+-	modelName := b.keyFrom(st)
+-	if nameOverride != "" {
+-		modelName = nameOverride
+-	}
+-	// no models needed for primitive types
+-	if b.isPrimitiveType(modelName) {
+-		return
+-	}
+-	// see if we already have visited this model
+-	if _, ok := b.Models[modelName]; ok {
+-		return
+-	}
+-	sm := Model{
+-		Id:         modelName,
+-		Required:   []string{},
+-		Properties: map[string]ModelProperty{}}
+-
+-	// reference the model before further initializing (enables recursive structs)
+-	b.Models[modelName] = sm
+-
+-	// check for slice or array
+-	if st.Kind() == reflect.Slice || st.Kind() == reflect.Array {
+-		b.addModel(st.Elem(), "")
+-		return
+-	}
+-	// check for structure or primitive type
+-	if st.Kind() != reflect.Struct {
+-		return
+-	}
+-	for i := 0; i < st.NumField(); i++ {
+-		field := st.Field(i)
+-		jsonName, prop := b.buildProperty(field, &sm, modelName)
+-		if descTag := field.Tag.Get("description"); descTag != "" {
+-			prop.Description = descTag
+-		}
+-		// add if not ommitted
+-		if len(jsonName) != 0 {
+-			// update Required
+-			if b.isPropertyRequired(field) {
+-				sm.Required = append(sm.Required, jsonName)
+-			}
+-			sm.Properties[jsonName] = prop
+-		}
+-	}
+-
+-	// update model builder with completed model
+-	b.Models[modelName] = sm
+-}
+-
+-func (b modelBuilder) isPropertyRequired(field reflect.StructField) bool {
+-	required := true
+-	if jsonTag := field.Tag.Get("json"); jsonTag != "" {
+-		s := strings.Split(jsonTag, ",")
+-		if len(s) > 1 && s[1] == "omitempty" {
+-			return false
+-		}
+-	}
+-	return required
+-}
+-
+-func (b modelBuilder) buildProperty(field reflect.StructField, model *Model, modelName string) (jsonName string, prop ModelProperty) {
+-	jsonName = b.jsonNameOfField(field)
+-	if len(jsonName) == 0 {
+-		// empty name signals skip property
+-		return "", prop
+-	}
+-	fieldType := field.Type
+-	fieldKind := fieldType.Kind()
+-
+-	if jsonTag := field.Tag.Get("json"); jsonTag != "" {
+-		s := strings.Split(jsonTag, ",")
+-		if len(s) > 1 && s[1] == "string" {
+-			fieldType = reflect.TypeOf("")
+-		}
+-	}
+-
+-	var pType = b.jsonSchemaType(fieldType.String()) // may include pkg path
+-	prop.Type = &pType
+-	if b.isPrimitiveType(fieldType.String()) {
+-		prop.Format = b.jsonSchemaFormat(fieldType.String())
+-		return jsonName, prop
+-	}
+-
+-	marshalerType := reflect.TypeOf((*json.Marshaler)(nil)).Elem()
+-	if fieldType.Implements(marshalerType) {
+-		var pType = "string"
+-		prop.Type = &pType
+-		return jsonName, prop
+-	}
+-
+-	if fieldKind == reflect.Struct {
+-		return b.buildStructTypeProperty(field, jsonName, model)
+-	}
+-
+-	if fieldKind == reflect.Slice || fieldKind == reflect.Array {
+-		return b.buildArrayTypeProperty(field, jsonName, modelName)
+-	}
+-
+-	if fieldKind == reflect.Ptr {
+-		return b.buildPointerTypeProperty(field, jsonName, modelName)
+-	}
+-
+-	if fieldType.Name() == "" { // override type of anonymous structs
+-		nestedTypeName := modelName + "." + jsonName
+-		var pType = nestedTypeName
+-		prop.Type = &pType
+-		b.addModel(fieldType, nestedTypeName)
+-	}
+-	return jsonName, prop
+-}
+-
+-func (b modelBuilder) buildStructTypeProperty(field reflect.StructField, jsonName string, model *Model) (nameJson string, prop ModelProperty) {
+-	fieldType := field.Type
+-	// check for anonymous
+-	if len(fieldType.Name()) == 0 {
+-		// anonymous
+-		anonType := model.Id + "." + jsonName
+-		b.addModel(fieldType, anonType)
+-		prop.Type = &anonType
+-		return jsonName, prop
+-	}
+-	if field.Name == fieldType.Name() && field.Anonymous {
+-		// embedded struct
+-		sub := modelBuilder{map[string]Model{}}
+-		sub.addModel(fieldType, "")
+-		subKey := sub.keyFrom(fieldType)
+-		// merge properties from sub
+-		subModel := sub.Models[subKey]
+-		for k, v := range subModel.Properties {
+-			model.Properties[k] = v
+-			// if subModel says this property is required then include it
+-			required := false
+-			for _, each := range subModel.Required {
+-				if k == each {
+-					required = true
+-					break
+-				}
+-			}
+-			if required {
+-				model.Required = append(model.Required, k)
+-			}
+-		}
+-		// empty name signals skip property
+-		return "", prop
+-	}
+-	// simple struct
+-	b.addModel(fieldType, "")
+-	var pType = fieldType.String()
+-	prop.Type = &pType
+-	return jsonName, prop
+-}
+-
+-func (b modelBuilder) buildArrayTypeProperty(field reflect.StructField, jsonName, modelName string) (nameJson string, prop ModelProperty) {
+-	fieldType := field.Type
+-	var pType = "array"
+-	prop.Type = &pType
+-	elemName := b.getElementTypeName(modelName, jsonName, fieldType.Elem())
+-	prop.Items = []Item{Item{Ref: &elemName}}
+-	// add|overwrite model for element type
+-	b.addModel(fieldType.Elem(), elemName)
+-	return jsonName, prop
+-}
+-
+-func (b modelBuilder) buildPointerTypeProperty(field reflect.StructField, jsonName, modelName string) (nameJson string, prop ModelProperty) {
+-	fieldType := field.Type
+-
+-	// override type of pointer to list-likes
+-	if fieldType.Elem().Kind() == reflect.Slice || fieldType.Elem().Kind() == reflect.Array {
+-		var pType = "array"
+-		prop.Type = &pType
+-		elemName := b.getElementTypeName(modelName, jsonName, fieldType.Elem().Elem())
+-		prop.Items = []Item{Item{Ref: &elemName}}
+-		// add|overwrite model for element type
+-		b.addModel(fieldType.Elem().Elem(), elemName)
+-	} else {
+-		// non-array, pointer type
+-		var pType = fieldType.String()[1:] // no star, include pkg path
+-		prop.Type = &pType
+-		elemName := ""
+-		if fieldType.Elem().Name() == "" {
+-			elemName = modelName + "." + jsonName
+-			prop.Type = &elemName
+-		}
+-		b.addModel(fieldType.Elem(), elemName)
+-	}
+-	return jsonName, prop
+-}
+-
+-func (b modelBuilder) getElementTypeName(modelName, jsonName string, t reflect.Type) string {
+-	if t.Name() == "" {
+-		return modelName + "." + jsonName
+-	}
+-	if b.isPrimitiveType(t.Name()) {
+-		return b.jsonSchemaType(t.Name())
+-	}
+-	return b.keyFrom(t)
+-}
+-
+-func (b modelBuilder) keyFrom(st reflect.Type) string {
+-	key := st.String()
+-	if len(st.Name()) == 0 { // unnamed type
+-		// Swagger UI has special meaning for [
+-		key = strings.Replace(key, "[]", "||", -1)
+-	}
+-	return key
+-}
+-
+-func (b modelBuilder) isPrimitiveType(modelName string) bool {
+-	return strings.Contains("uint8 int int32 int64 float32 float64 bool string byte time.Time", modelName)
+-}
+-
+-// jsonNameOfField returns the name of the field as it should appear in JSON format
+-// An empty string indicates that this field is not part of the JSON representation
+-func (b modelBuilder) jsonNameOfField(field reflect.StructField) string {
+-	if jsonTag := field.Tag.Get("json"); jsonTag != "" {
+-		s := strings.Split(jsonTag, ",")
+-		if s[0] == "-" {
+-			// empty name signals skip property
+-			return ""
+-		} else if s[0] != "" {
+-			return s[0]
+-		}
+-	}
+-	return field.Name
+-}
+-
+-func (b modelBuilder) jsonSchemaType(modelName string) string {
+-	schemaMap := map[string]string{
+-		"uint8":     "integer",
+-		"int":       "integer",
+-		"int32":     "integer",
+-		"int64":     "integer",
+-		"byte":      "string",
+-		"float64":   "number",
+-		"float32":   "number",
+-		"bool":      "boolean",
+-		"time.Time": "string",
+-	}
+-	mapped, ok := schemaMap[modelName]
+-	if ok {
+-		return mapped
+-	} else {
+-		return modelName // use as is (custom or struct)
+-	}
+-}
+-
+-func (b modelBuilder) jsonSchemaFormat(modelName string) string {
+-	schemaMap := map[string]string{
+-		"int":       "int32",
+-		"int32":     "int32",
+-		"int64":     "int64",
+-		"byte":      "byte",
+-		"uint8":     "byte",
+-		"float64":   "double",
+-		"float32":   "float",
+-		"time.Time": "date-time",
+-	}
+-	mapped, ok := schemaMap[modelName]
+-	if ok {
+-		return mapped
+-	} else {
+-		return "" // no format
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/model_builder_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/model_builder_test.go
+deleted file mode 100644
+index dd966bd..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/model_builder_test.go
++++ /dev/null
+@@ -1,729 +0,0 @@
+-package swagger
+-
+-import (
+-	"testing"
+-	"time"
+-)
+-
+-type YesNo bool
+-
+-func (y YesNo) MarshalJSON() ([]byte, error) {
+-	if y {
+-		return []byte("yes"), nil
+-	}
+-	return []byte("no"), nil
+-}
+-
+-// clear && go test -v -test.run TestCustomMarshaller_Issue96 ...swagger
+-func TestCustomMarshaller_Issue96(t *testing.T) {
+-	type Vote struct {
+-		What YesNo
+-	}
+-	testJsonFromStruct(t, Vote{}, `{
+-  "swagger.Vote": {
+-   "id": "swagger.Vote",
+-   "required": [
+-    "What"
+-   ],
+-   "properties": {
+-    "What": {
+-     "type": "string"
+-    }
+-   }
+-  }
+- }`)
+-}
+-
+-// clear && go test -v -test.run TestPrimitiveTypes ...swagger
+-func TestPrimitiveTypes(t *testing.T) {
+-	type Prims struct {
+-		f float64
+-		t time.Time
+-	}
+-	testJsonFromStruct(t, Prims{}, `{
+-  "swagger.Prims": {
+-   "id": "swagger.Prims",
+-   "required": [
+-    "f",
+-    "t"
+-   ],
+-   "properties": {
+-    "f": {
+-     "type": "number",
+-     "format": "double"
+-    },
+-    "t": {
+-     "type": "string",
+-     "format": "date-time"
+-    }
+-   }
+-  }
+- }`)
+-}
+-
+-// clear && go test -v -test.run TestS1 ...swagger
+-func TestS1(t *testing.T) {
+-	type S1 struct {
+-		Id string
+-	}
+-	testJsonFromStruct(t, S1{}, `{
+-  "swagger.S1": {
+-   "id": "swagger.S1",
+-   "required": [
+-    "Id"
+-   ],
+-   "properties": {
+-    "Id": {
+-     "type": "string"
+-    }
+-   }
+-  }
+- }`)
+-}
+-
+-// clear && go test -v -test.run TestS2 ...swagger
+-func TestS2(t *testing.T) {
+-	type S2 struct {
+-		Ids []string
+-	}
+-	testJsonFromStruct(t, S2{}, `{
+-  "swagger.S2": {
+-   "id": "swagger.S2",
+-   "required": [
+-    "Ids"
+-   ],
+-   "properties": {
+-    "Ids": {
+-     "type": "array",
+-     "items": [
+-      {
+-       "$ref": "string"
+-      }
+-     ]
+-    }
+-   }
+-  }
+- }`)
+-}
+-
+-// clear && go test -v -test.run TestS3 ...swagger
+-func TestS3(t *testing.T) {
+-	type NestedS3 struct {
+-		Id string
+-	}
+-	type S3 struct {
+-		Nested NestedS3
+-	}
+-	testJsonFromStruct(t, S3{}, `{
+-  "swagger.NestedS3": {
+-   "id": "swagger.NestedS3",
+-   "required": [
+-    "Id"
+-   ],
+-   "properties": {
+-    "Id": {
+-     "type": "string"
+-    }
+-   }
+-  },
+-  "swagger.S3": {
+-   "id": "swagger.S3",
+-   "required": [
+-    "Nested"
+-   ],
+-   "properties": {
+-    "Nested": {
+-     "type": "swagger.NestedS3"
+-    }
+-   }
+-  }
+- }`)
+-}
+-
+-type sample struct {
+-	id       string `swagger:"required"` // TODO
+-	items    []item
+-	rootItem item `json:"root" description:"root desc"`
+-}
+-
+-type item struct {
+-	itemName string `json:"name"`
+-}
+-
+-// clear && go test -v -test.run TestSampleToModelAsJson ...swagger
+-func TestSampleToModelAsJson(t *testing.T) {
+-	testJsonFromStruct(t, sample{items: []item{}}, `{
+-  "swagger.item": {
+-   "id": "swagger.item",
+-   "required": [
+-    "name"
+-   ],
+-   "properties": {
+-    "name": {
+-     "type": "string"
+-    }
+-   }
+-  },
+-  "swagger.sample": {
+-   "id": "swagger.sample",
+-   "required": [
+-    "id",
+-    "items",
+-    "root"
+-   ],
+-   "properties": {
+-    "id": {
+-     "type": "string"
+-    },
+-    "items": {
+-     "type": "array",
+-     "items": [
+-      {
+-       "$ref": "swagger.item"
+-      }
+-     ]
+-    },
+-    "root": {
+-     "type": "swagger.item",
+-     "description": "root desc"
+-    }
+-   }
+-  }
+- }`)
+-}
+-
+-func TestJsonTags(t *testing.T) {
+-	type X struct {
+-		A string
+-		B string `json:"-"`
+-		C int    `json:",string"`
+-		D int    `json:","`
+-	}
+-
+-	expected := `{
+-  "swagger.X": {
+-   "id": "swagger.X",
+-   "required": [
+-    "A",
+-    "C",
+-    "D"
+-   ],
+-   "properties": {
+-    "A": {
+-     "type": "string"
+-    },
+-    "C": {
+-     "type": "string"
+-    },
+-    "D": {
+-     "type": "integer",
+-     "format": "int32"
+-    }
+-   }
+-  }
+- }`
+-
+-	testJsonFromStruct(t, X{}, expected)
+-}
+-
+-func TestJsonTagOmitempty(t *testing.T) {
+-	type X struct {
+-		A int `json:",omitempty"`
+-		B int `json:"C,omitempty"`
+-	}
+-
+-	expected := `{
+-  "swagger.X": {
+-   "id": "swagger.X",
+-   "properties": {
+-    "A": {
+-     "type": "integer",
+-     "format": "int32"
+-    },
+-    "C": {
+-     "type": "integer",
+-     "format": "int32"
+-    }
+-   }
+-  }
+- }`
+-
+-	testJsonFromStruct(t, X{}, expected)
+-}
+-
+-func TestJsonTagName(t *testing.T) {
+-	type X struct {
+-		A string `json:"B"`
+-	}
+-
+-	expected := `{
+-  "swagger.X": {
+-   "id": "swagger.X",
+-   "required": [
+-    "B"
+-   ],
+-   "properties": {
+-    "B": {
+-     "type": "string"
+-    }
+-   }
+-  }
+- }`
+-
+-	testJsonFromStruct(t, X{}, expected)
+-}
+-
+-func TestAnonymousStruct(t *testing.T) {
+-	type X struct {
+-		A struct {
+-			B int
+-		}
+-	}
+-
+-	expected := `{
+-  "swagger.X": {
+-   "id": "swagger.X",
+-   "required": [
+-    "A"
+-   ],
+-   "properties": {
+-    "A": {
+-     "type": "swagger.X.A"
+-    }
+-   }
+-  },
+-  "swagger.X.A": {
+-   "id": "swagger.X.A",
+-   "required": [
+-    "B"
+-   ],
+-   "properties": {
+-    "B": {
+-     "type": "integer",
+-     "format": "int32"
+-    }
+-   }
+-  }
+- }`
+-
+-	testJsonFromStruct(t, X{}, expected)
+-}
+-
+-func TestAnonymousPtrStruct(t *testing.T) {
+-	type X struct {
+-		A *struct {
+-			B int
+-		}
+-	}
+-
+-	expected := `{
+-  "swagger.X": {
+-   "id": "swagger.X",
+-   "required": [
+-    "A"
+-   ],
+-   "properties": {
+-    "A": {
+-     "type": "swagger.X.A"
+-    }
+-   }
+-  },
+-  "swagger.X.A": {
+-   "id": "swagger.X.A",
+-   "required": [
+-    "B"
+-   ],
+-   "properties": {
+-    "B": {
+-     "type": "integer",
+-     "format": "int32"
+-    }
+-   }
+-  }
+- }`
+-
+-	testJsonFromStruct(t, X{}, expected)
+-}
+-
+-func TestAnonymousArrayStruct(t *testing.T) {
+-	type X struct {
+-		A []struct {
+-			B int
+-		}
+-	}
+-
+-	expected := `{
+-  "swagger.X": {
+-   "id": "swagger.X",
+-   "required": [
+-    "A"
+-   ],
+-   "properties": {
+-    "A": {
+-     "type": "array",
+-     "items": [
+-      {
+-       "$ref": "swagger.X.A"
+-      }
+-     ]
+-    }
+-   }
+-  },
+-  "swagger.X.A": {
+-   "id": "swagger.X.A",
+-   "required": [
+-    "B"
+-   ],
+-   "properties": {
+-    "B": {
+-     "type": "integer",
+-     "format": "int32"
+-    }
+-   }
+-  }
+- }`
+-
+-	testJsonFromStruct(t, X{}, expected)
+-}
+-
+-func TestAnonymousPtrArrayStruct(t *testing.T) {
+-	type X struct {
+-		A *[]struct {
+-			B int
+-		}
+-	}
+-
+-	expected := `{
+-  "swagger.X": {
+-   "id": "swagger.X",
+-   "required": [
+-    "A"
+-   ],
+-   "properties": {
+-    "A": {
+-     "type": "array",
+-     "items": [
+-      {
+-       "$ref": "swagger.X.A"
+-      }
+-     ]
+-    }
+-   }
+-  },
+-  "swagger.X.A": {
+-   "id": "swagger.X.A",
+-   "required": [
+-    "B"
+-   ],
+-   "properties": {
+-    "B": {
+-     "type": "integer",
+-     "format": "int32"
+-    }
+-   }
+-  }
+- }`
+-
+-	testJsonFromStruct(t, X{}, expected)
+-}
+-
+-// go test -v -test.run TestEmbeddedStruct_Issue98 ...swagger
+-func TestEmbeddedStruct_Issue98(t *testing.T) {
+-	type Y struct {
+-		A int
+-	}
+-	type X struct {
+-		Y
+-	}
+-	testJsonFromStruct(t, X{}, `{
+-  "swagger.X": {
+-   "id": "swagger.X",
+-   "required": [
+-    "A"
+-   ],
+-   "properties": {
+-    "A": {
+-     "type": "integer",
+-     "format": "int32"
+-    }
+-   }
+-  }
+- }`)
+-}
+-
+-type Dataset struct {
+-	Names []string
+-}
+-
+-// clear && go test -v -test.run TestIssue85 ...swagger
+-func TestIssue85(t *testing.T) {
+-	anon := struct{ Datasets []Dataset }{}
+-	testJsonFromStruct(t, anon, `{
+-  "struct { Datasets ||swagger.Dataset }": {
+-   "id": "struct { Datasets ||swagger.Dataset }",
+-   "required": [
+-    "Datasets"
+-   ],
+-   "properties": {
+-    "Datasets": {
+-     "type": "array",
+-     "items": [
+-      {
+-       "$ref": "swagger.Dataset"
+-      }
+-     ]
+-    }
+-   }
+-  },
+-  "swagger.Dataset": {
+-   "id": "swagger.Dataset",
+-   "required": [
+-    "Names"
+-   ],
+-   "properties": {
+-    "Names": {
+-     "type": "array",
+-     "items": [
+-      {
+-       "$ref": "string"
+-      }
+-     ]
+-    }
+-   }
+-  }
+- }`)
+-}
+-
+-type File struct {
+-	History     []File
+-	HistoryPtrs []*File
+-}
+-
+-// go test -v -test.run TestRecursiveStructure ...swagger
+-func TestRecursiveStructure(t *testing.T) {
+-	testJsonFromStruct(t, File{}, `{
+-  "swagger.File": {
+-   "id": "swagger.File",
+-   "required": [
+-    "History",
+-    "HistoryPtrs"
+-   ],
+-   "properties": {
+-    "History": {
+-     "type": "array",
+-     "items": [
+-      {
+-       "$ref": "swagger.File"
+-      }
+-     ]
+-    },
+-    "HistoryPtrs": {
+-     "type": "array",
+-     "items": [
+-      {
+-       "$ref": "swagger.File.HistoryPtrs"
+-      }
+-     ]
+-    }
+-   }
+-  },
+-  "swagger.File.HistoryPtrs": {
+-   "id": "swagger.File.HistoryPtrs",
+-   "properties": {}
+-  }
+- }`)
+-}
+-
+-type A1 struct {
+-	B struct {
+-		Id      int
+-		Comment string `json:"comment,omitempty"`
+-	}
+-}
+-
+-// go test -v -test.run TestEmbeddedStructA1 ...swagger
+-func TestEmbeddedStructA1(t *testing.T) {
+-	testJsonFromStruct(t, A1{}, `{
+-  "swagger.A1": {
+-   "id": "swagger.A1",
+-   "required": [
+-    "B"
+-   ],
+-   "properties": {
+-    "B": {
+-     "type": "swagger.A1.B"
+-    }
+-   }
+-  },
+-  "swagger.A1.B": {
+-   "id": "swagger.A1.B",
+-   "required": [
+-    "Id"
+-   ],
+-   "properties": {
+-    "Id": {
+-     "type": "integer",
+-     "format": "int32"
+-    },
+-    "comment": {
+-     "type": "string"
+-    }
+-   }
+-  }
+- }`)
+-}
+-
+-type A2 struct {
+-	C
+-}
+-type C struct {
+-	Id      int    `json:"B"`
+-	Comment string `json:"comment,omitempty"`
+-	Secure  bool   `json:"secure"`
+-}
+-
+-// go test -v -test.run TestEmbeddedStructA2 ...swagger
+-func TestEmbeddedStructA2(t *testing.T) {
+-	testJsonFromStruct(t, A2{}, `{
+-  "swagger.A2": {
+-   "id": "swagger.A2",
+-   "required": [
+-    "B",
+-    "secure"
+-   ],
+-   "properties": {
+-    "B": {
+-     "type": "integer",
+-     "format": "int32"
+-    },
+-    "comment": {
+-     "type": "string"
+-    },
+-    "secure": {
+-     "type": "boolean"
+-    }
+-   }
+-  }
+- }`)
+-}
+-
+-type A3 struct {
+-	B D
+-}
+-
+-type D struct {
+-	Id int
+-}
+-
+-// clear && go test -v -test.run TestStructA3 ...swagger
+-func TestStructA3(t *testing.T) {
+-	testJsonFromStruct(t, A3{}, `{
+-  "swagger.A3": {
+-   "id": "swagger.A3",
+-   "required": [
+-    "B"
+-   ],
+-   "properties": {
+-    "B": {
+-     "type": "swagger.D"
+-    }
+-   }
+-  },
+-  "swagger.D": {
+-   "id": "swagger.D",
+-   "required": [
+-    "Id"
+-   ],
+-   "properties": {
+-    "Id": {
+-     "type": "integer",
+-     "format": "int32"
+-    }
+-   }
+-  }
+- }`)
+-}
+-
+-type ObjectId []byte
+-
+-type Region struct {
+-	Id   ObjectId `bson:"_id" json:"id"`
+-	Name string   `bson:"name" json:"name"`
+-	Type string   `bson:"type" json:"type"`
+-}
+-
+-// clear && go test -v -test.run TestRegion_Issue113 ...swagger
+-func TestRegion_Issue113(t *testing.T) {
+-	testJsonFromStruct(t, []Region{}, `{
+-  "integer": {
+-   "id": "integer",
+-   "properties": {}
+-  },
+-  "swagger.Region": {
+-   "id": "swagger.Region",
+-   "required": [
+-    "id",
+-    "name",
+-    "type"
+-   ],
+-   "properties": {
+-    "id": {
+-     "type": "array",
+-     "items": [
+-      {
+-       "$ref": "integer"
+-      }
+-     ]
+-    },
+-    "name": {
+-     "type": "string"
+-    },
+-    "type": {
+-     "type": "string"
+-    }
+-   }
+-  },
+-  "||swagger.Region": {
+-   "id": "||swagger.Region",
+-   "properties": {}
+-  }
+- }`)
+-}
+-
+-// clear && go test -v -test.run TestIssue158 ...swagger
+-func TestIssue158(t *testing.T) {
+-	type Address struct {
+-		Country string `json:"country,omitempty"`
+-	}
+-
+-	type Customer struct {
+-		Name    string  `json:"name"`
+-		Address Address `json:"address"`
+-	}
+-	expected := `{
+-  "swagger.Address": {
+-   "id": "swagger.Address",
+-   "properties": {
+-    "country": {
+-     "type": "string"
+-    }
+-   }
+-  },
+-  "swagger.Customer": {
+-   "id": "swagger.Customer",
+-   "required": [
+-    "name",
+-    "address"
+-   ],
+-   "properties": {
+-    "address": {
+-     "type": "swagger.Address"
+-    },
+-    "name": {
+-     "type": "string"
+-    }
+-   }
+-  }
+- }`
+-	testJsonFromStruct(t, Customer{}, expected)
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/param_sorter.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/param_sorter.go
+deleted file mode 100644
+index 813007b..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/param_sorter.go
++++ /dev/null
+@@ -1,29 +0,0 @@
+-package swagger
+-
+-// Copyright 2014 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-type ParameterSorter []Parameter
+-
+-func (s ParameterSorter) Len() int {
+-	return len(s)
+-}
+-func (s ParameterSorter) Swap(i, j int) {
+-	s[i], s[j] = s[j], s[i]
+-}
+-
+-var typeToSortKey = map[string]string{
+-	"path":   "A",
+-	"query":  "B",
+-	"form":   "C",
+-	"header": "D",
+-	"body":   "E",
+-}
+-
+-func (s ParameterSorter) Less(i, j int) bool {
+-	// use ordering path,query,form,header,body
+-	pi := s[i]
+-	pj := s[j]
+-	return typeToSortKey[pi.ParamType]+pi.Name < typeToSortKey[pj.ParamType]+pj.Name
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/param_sorter_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/param_sorter_test.go
+deleted file mode 100644
+index ef6d9eb..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/param_sorter_test.go
++++ /dev/null
+@@ -1,52 +0,0 @@
+-package swagger
+-
+-import (
+-	"bytes"
+-	"sort"
+-	"testing"
+-)
+-
+-func TestSortParameters(t *testing.T) {
+-	unsorted := []Parameter{
+-		Parameter{
+-			Name:      "form2",
+-			ParamType: "form",
+-		},
+-		Parameter{
+-			Name:      "header1",
+-			ParamType: "header",
+-		},
+-		Parameter{
+-			Name:      "path2",
+-			ParamType: "path",
+-		},
+-		Parameter{
+-			Name:      "body",
+-			ParamType: "body",
+-		},
+-		Parameter{
+-			Name:      "path1",
+-			ParamType: "path",
+-		},
+-		Parameter{
+-			Name:      "form1",
+-			ParamType: "form",
+-		},
+-		Parameter{
+-			Name:      "query2",
+-			ParamType: "query",
+-		},
+-		Parameter{
+-			Name:      "query1",
+-			ParamType: "query",
+-		},
+-	}
+-	sort.Sort(ParameterSorter(unsorted))
+-	var b bytes.Buffer
+-	for _, p := range unsorted {
+-		b.WriteString(p.Name + ".")
+-	}
+-	if "path1.path2.query1.query2.form1.form2.header1.body." != b.String() {
+-		t.Fatal("sorting has changed:" + b.String())
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/swagger.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/swagger.go
+deleted file mode 100644
+index 9f2fe4b..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/swagger.go
++++ /dev/null
+@@ -1,184 +0,0 @@
+-// Package swagger implements the structures of the Swagger
+-// https://github.com/wordnik/swagger-spec/blob/master/versions/1.2.md
+-package swagger
+-
+-const swaggerVersion = "1.2"
+-
+-// 4.3.3 Data Type Fields
+-type DataTypeFields struct {
+-	Type         *string  `json:"type,omitempty"` // if Ref not used
+-	Ref          *string  `json:"$ref,omitempty"` // if Type not used
+-	Format       string   `json:"format,omitempty"`
+-	DefaultValue Special  `json:"defaultValue,omitempty"`
+-	Enum         []string `json:"enum,omitempty"`
+-	Minimum      string   `json:"minimum,omitempty"`
+-	Maximum      string   `json:"maximum,omitempty"`
+-	Items        []Item   `json:"items,omitempty"`
+-	UniqueItems  *bool    `json:"uniqueItems,omitempty"`
+-}
+-
+-type Special string
+-
+-// 4.3.4 Items Object
+-type Item struct {
+-	Type   *string `json:"type,omitempty"`
+-	Ref    *string `json:"$ref,omitempty"`
+-	Format string  `json:"format,omitempty"`
+-}
+-
+-// 5.1 Resource Listing
+-type ResourceListing struct {
+-	SwaggerVersion string          `json:"swaggerVersion"` // e.g 1.2
+-	Apis           []Resource      `json:"apis"`
+-	ApiVersion     string          `json:"apiVersion"`
+-	Info           Info            `json:"info"`
+-	Authorizations []Authorization `json:"authorizations,omitempty"`
+-}
+-
+-// 5.1.2 Resource Object
+-type Resource struct {
+-	Path        string `json:"path"` // relative or absolute, must start with /
+-	Description string `json:"description"`
+-}
+-
+-// 5.1.3 Info Object
+-type Info struct {
+-	Title             string `json:"title"`
+-	Description       string `json:"description"`
+-	TermsOfServiceUrl string `json:"termsOfServiceUrl,omitempty"`
+-	Contact           string `json:"contact,omitempty"`
+-	License           string `json:"license,omitempty"`
+-	LicensUrl         string `json:"licensUrl,omitempty"`
+-}
+-
+-// 5.1.5
+-type Authorization struct {
+-	Type       string      `json:"type"`
+-	PassAs     string      `json:"passAs"`
+-	Keyname    string      `json:"keyname"`
+-	Scopes     []Scope     `json:"scopes"`
+-	GrantTypes []GrantType `json:"grandTypes"`
+-}
+-
+-// 5.1.6, 5.2.11
+-type Scope struct {
+-	// Required. The name of the scope.
+-	Scope string `json:"scope"`
+-	// Recommended. A short description of the scope.
+-	Description string `json:"description"`
+-}
+-
+-// 5.1.7
+-type GrantType struct {
+-	Implicit          Implicit          `json:"implicit"`
+-	AuthorizationCode AuthorizationCode `json:"authorization_code"`
+-}
+-
+-// 5.1.8 Implicit Object
+-type Implicit struct {
+-	// Required. The login endpoint definition.
+-	loginEndpoint LoginEndpoint `json:"loginEndpoint"`
+-	// An optional alternative name to standard "access_token" OAuth2 parameter.
+-	TokenName string `json:"tokenName"`
+-}
+-
+-// 5.1.9 Authorization Code Object
+-type AuthorizationCode struct {
+-	TokenRequestEndpoint TokenRequestEndpoint `json:"tokenRequestEndpoint"`
+-	TokenEndpoint        TokenEndpoint        `json:"tokenEndpoint"`
+-}
+-
+-// 5.1.10 Login Endpoint Object
+-type LoginEndpoint struct {
+-	// Required. The URL of the authorization endpoint for the implicit grant flow. The value SHOULD be in a URL format.
+-	Url string `json:"url"`
+-}
+-
+-// 5.1.11 Token Request Endpoint Object
+-type TokenRequestEndpoint struct {
+-	// Required. The URL of the authorization endpoint for the authentication code grant flow. The value SHOULD be in a URL format.
+-	Url string `json:"url"`
+-	// An optional alternative name to standard "client_id" OAuth2 parameter.
+-	ClientIdName string `json:"clientIdName"`
+-	// An optional alternative name to the standard "client_secret" OAuth2 parameter.
+-	ClientSecretName string `json:"clientSecretName"`
+-}
+-
+-// 5.1.12 Token Endpoint Object
+-type TokenEndpoint struct {
+-	// Required. The URL of the token endpoint for the authentication code grant flow. The value SHOULD be in a URL format.
+-	Url string `json:"url"`
+-	// An optional alternative name to standard "access_token" OAuth2 parameter.
+-	TokenName string `json:"tokenName"`
+-}
+-
+-// 5.2 API Declaration
+-type ApiDeclaration struct {
+-	SwaggerVersion string           `json:"swaggerVersion"`
+-	ApiVersion     string           `json:"apiVersion"`
+-	BasePath       string           `json:"basePath"`
+-	ResourcePath   string           `json:"resourcePath"` // must start with /
+-	Apis           []Api            `json:"apis,omitempty"`
+-	Models         map[string]Model `json:"models,omitempty"`
+-	Produces       []string         `json:"produces,omitempty"`
+-	Consumes       []string         `json:"consumes,omitempty"`
+-	Authorizations []Authorization  `json:"authorizations,omitempty"`
+-}
+-
+-// 5.2.2 API Object
+-type Api struct {
+-	Path        string      `json:"path"` // relative or absolute, must start with /
+-	Description string      `json:"description"`
+-	Operations  []Operation `json:"operations,omitempty"`
+-}
+-
+-// 5.2.3 Operation Object
+-type Operation struct {
+-	Type             string            `json:"type"`
+-	Method           string            `json:"method"`
+-	Summary          string            `json:"summary,omitempty"`
+-	Notes            string            `json:"notes,omitempty"`
+-	Nickname         string            `json:"nickname"`
+-	Authorizations   []Authorization   `json:"authorizations,omitempty"`
+-	Parameters       []Parameter       `json:"parameters"`
+-	ResponseMessages []ResponseMessage `json:"responseMessages,omitempty"` // optional
+-	Produces         []string          `json:"produces,omitempty"`
+-	Consumes         []string          `json:"consumes,omitempty"`
+-	Deprecated       string            `json:"deprecated,omitempty"`
+-}
+-
+-// 5.2.4 Parameter Object
+-type Parameter struct {
+-	DataTypeFields
+-	ParamType     string `json:"paramType"` // path,query,body,header,form
+-	Name          string `json:"name"`
+-	Description   string `json:"description"`
+-	Required      bool   `json:"required"`
+-	AllowMultiple bool   `json:"allowMultiple"`
+-}
+-
+-// 5.2.5 Response Message Object
+-type ResponseMessage struct {
+-	Code          int    `json:"code"`
+-	Message       string `json:"message"`
+-	ResponseModel string `json:"responseModel,omitempty"`
+-}
+-
+-// 5.2.6, 5.2.7 Models Object
+-type Model struct {
+-	Id            string                   `json:"id"`
+-	Description   string                   `json:"description,omitempty"`
+-	Required      []string                 `json:"required,omitempty"`
+-	Properties    map[string]ModelProperty `json:"properties"`
+-	SubTypes      []string                 `json:"subTypes,omitempty"`
+-	Discriminator string                   `json:"discriminator,omitempty"`
+-}
+-
+-// 5.2.8 Properties Object
+-type ModelProperty struct {
+-	DataTypeFields
+-	Description string `json:"description,omitempty"`
+-}
+-
+-// 5.2.10
+-type Authorizations map[string]Authorization
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/swagger_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/swagger_test.go
+deleted file mode 100644
+index 81e72f6..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/swagger_test.go
++++ /dev/null
+@@ -1,116 +0,0 @@
+-package swagger
+-
+-import (
+-	"encoding/json"
+-	"fmt"
+-	"testing"
+-
+-	"github.com/emicklei/go-restful"
+-)
+-
+-// go test -v -test.run TestApi ...swagger
+-func TestApi(t *testing.T) {
+-	value := Api{Path: "/", Description: "Some Path", Operations: []Operation{}}
+-	compareJson(t, true, value, `{"path":"/","description":"Some Path"}`)
+-}
+-
+-// go test -v -test.run TestServiceToApi ...swagger
+-func TestServiceToApi(t *testing.T) {
+-	ws := new(restful.WebService)
+-	ws.Path("/tests")
+-	ws.Consumes(restful.MIME_JSON)
+-	ws.Produces(restful.MIME_XML)
+-	ws.Route(ws.GET("/all").To(dummy).Writes(sample{}))
+-	ws.ApiVersion("1.2.3")
+-	cfg := Config{
+-		WebServicesUrl: "http://here.com",
+-		ApiPath:        "/apipath",
+-		WebServices:    []*restful.WebService{ws}}
+-	sws := newSwaggerService(cfg)
+-	decl := sws.composeDeclaration(ws, "/tests")
+-	data, err := json.MarshalIndent(decl, " ", " ")
+-	if err != nil {
+-		t.Fatal(err.Error())
+-	}
+-	// for visual inspection only
+-	fmt.Println(string(data))
+-}
+-
+-func dummy(i *restful.Request, o *restful.Response) {}
+-
+-// go test -v -test.run TestIssue78 ...swagger
+-type Response struct {
+-	Code  int
+-	Users *[]User
+-	Items *[]TestItem
+-}
+-type User struct {
+-	Id, Name string
+-}
+-type TestItem struct {
+-	Id, Name string
+-}
+-
+-// clear && go test -v -test.run TestComposeResponseMessages ...swagger
+-func TestComposeResponseMessages(t *testing.T) {
+-	responseErrors := map[int]restful.ResponseError{}
+-	responseErrors[400] = restful.ResponseError{Code: 400, Message: "Bad Request", Model: TestItem{}}
+-	route := restful.Route{ResponseErrors: responseErrors}
+-	decl := new(ApiDeclaration)
+-	decl.Models = map[string]Model{}
+-	msgs := composeResponseMessages(route, decl)
+-	if msgs[0].ResponseModel != "swagger.TestItem" {
+-		t.Errorf("got %s want swagger.TestItem", msgs[0].ResponseModel)
+-	}
+-}
+-
+-// clear && go test -v -test.run TestComposeResponseMessageArray ...swagger
+-func TestComposeResponseMessageArray(t *testing.T) {
+-	responseErrors := map[int]restful.ResponseError{}
+-	responseErrors[400] = restful.ResponseError{Code: 400, Message: "Bad Request", Model: []TestItem{}}
+-	route := restful.Route{ResponseErrors: responseErrors}
+-	decl := new(ApiDeclaration)
+-	decl.Models = map[string]Model{}
+-	msgs := composeResponseMessages(route, decl)
+-	if msgs[0].ResponseModel != "array[swagger.TestItem]" {
+-		t.Errorf("got %s want swagger.TestItem", msgs[0].ResponseModel)
+-	}
+-}
+-
+-func TestIssue78(t *testing.T) {
+-	sws := newSwaggerService(Config{})
+-	models := map[string]Model{}
+-	sws.addModelFromSampleTo(&Operation{}, true, Response{Items: &[]TestItem{}}, models)
+-	model, ok := models["swagger.Response"]
+-	if !ok {
+-		t.Fatal("missing response model")
+-	}
+-	if "swagger.Response" != model.Id {
+-		t.Fatal("wrong model id:" + model.Id)
+-	}
+-	code, ok := model.Properties["Code"]
+-	if !ok {
+-		t.Fatal("missing code")
+-	}
+-	if "integer" != *code.Type {
+-		t.Fatal("wrong code type:" + *code.Type)
+-	}
+-	items, ok := model.Properties["Items"]
+-	if !ok {
+-		t.Fatal("missing items")
+-	}
+-	if "array" != *items.Type {
+-		t.Fatal("wrong items type:" + *items.Type)
+-	}
+-	items_items := items.Items
+-	if len(items_items) == 0 {
+-		t.Fatal("missing items->items")
+-	}
+-	ref := items_items[0].Ref
+-	if ref == nil {
+-		t.Fatal("missing $ref")
+-	}
+-	if *ref != "swagger.TestItem" {
+-		t.Fatal("wrong $ref:" + *ref)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/swagger_webservice.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/swagger_webservice.go
+deleted file mode 100644
+index 04da0a1..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/swagger_webservice.go
++++ /dev/null
+@@ -1,353 +0,0 @@
+-package swagger
+-
+-import (
+-	"fmt"
+-	"github.com/emicklei/go-restful"
+-	// "github.com/emicklei/hopwatch"
+-	"log"
+-	"net/http"
+-	"reflect"
+-	"sort"
+-	"strings"
+-)
+-
+-type SwaggerService struct {
+-	config            Config
+-	apiDeclarationMap map[string]ApiDeclaration
+-}
+-
+-func newSwaggerService(config Config) *SwaggerService {
+-	return &SwaggerService{
+-		config:            config,
+-		apiDeclarationMap: map[string]ApiDeclaration{}}
+-}
+-
+-// LogInfo is the function that is called when this package needs to log. It defaults to log.Printf
+-var LogInfo = log.Printf
+-
+-// InstallSwaggerService add the WebService that provides the API documentation of all services
+-// conform the Swagger documentation specifcation. (https://github.com/wordnik/swagger-core/wiki).
+-func InstallSwaggerService(aSwaggerConfig Config) {
+-	RegisterSwaggerService(aSwaggerConfig, restful.DefaultContainer)
+-}
+-
+-// RegisterSwaggerService add the WebService that provides the API documentation of all services
+-// conform the Swagger documentation specifcation. (https://github.com/wordnik/swagger-core/wiki).
+-func RegisterSwaggerService(config Config, wsContainer *restful.Container) {
+-	sws := newSwaggerService(config)
+-	ws := new(restful.WebService)
+-	ws.Path(config.ApiPath)
+-	ws.Produces(restful.MIME_JSON)
+-	if config.DisableCORS {
+-		ws.Filter(enableCORS)
+-	}
+-	ws.Route(ws.GET("/").To(sws.getListing))
+-	ws.Route(ws.GET("/{a}").To(sws.getDeclarations))
+-	ws.Route(ws.GET("/{a}/{b}").To(sws.getDeclarations))
+-	ws.Route(ws.GET("/{a}/{b}/{c}").To(sws.getDeclarations))
+-	ws.Route(ws.GET("/{a}/{b}/{c}/{d}").To(sws.getDeclarations))
+-	ws.Route(ws.GET("/{a}/{b}/{c}/{d}/{e}").To(sws.getDeclarations))
+-	ws.Route(ws.GET("/{a}/{b}/{c}/{d}/{e}/{f}").To(sws.getDeclarations))
+-	ws.Route(ws.GET("/{a}/{b}/{c}/{d}/{e}/{f}/{g}").To(sws.getDeclarations))
+-	LogInfo("[restful/swagger] listing is available at %v%v", config.WebServicesUrl, config.ApiPath)
+-	wsContainer.Add(ws)
+-
+-	// Build all ApiDeclarations
+-	for _, each := range config.WebServices {
+-		rootPath := each.RootPath()
+-		// skip the api service itself
+-		if rootPath != config.ApiPath {
+-			if rootPath == "" || rootPath == "/" {
+-				// use routes
+-				for _, route := range each.Routes() {
+-					entry := staticPathFromRoute(route)
+-					_, exists := sws.apiDeclarationMap[entry]
+-					if !exists {
+-						sws.apiDeclarationMap[entry] = sws.composeDeclaration(each, entry)
+-					}
+-				}
+-			} else { // use root path
+-				sws.apiDeclarationMap[each.RootPath()] = sws.composeDeclaration(each, each.RootPath())
+-			}
+-		}
+-	}
+-
+-	// Check paths for UI serving
+-	if config.StaticHandler == nil && config.SwaggerFilePath != "" && config.SwaggerPath != "" {
+-		swaggerPathSlash := config.SwaggerPath
+-		// path must end with slash /
+-		if "/" != config.SwaggerPath[len(config.SwaggerPath)-1:] {
+-			LogInfo("[restful/swagger] use corrected SwaggerPath ; must end with slash (/)")
+-			swaggerPathSlash += "/"
+-		}
+-
+-		LogInfo("[restful/swagger] %v%v is mapped to folder %v", config.WebServicesUrl, swaggerPathSlash, config.SwaggerFilePath)
+-		wsContainer.Handle(swaggerPathSlash, http.StripPrefix(swaggerPathSlash, http.FileServer(http.Dir(config.SwaggerFilePath))))
+-
+-		//if we define a custom static handler use it
+-	} else if config.StaticHandler != nil && config.SwaggerPath != "" {
+-		swaggerPathSlash := config.SwaggerPath
+-		// path must end with slash /
+-		if "/" != config.SwaggerPath[len(config.SwaggerPath)-1:] {
+-			LogInfo("[restful/swagger] use corrected SwaggerFilePath ; must end with slash (/)")
+-			swaggerPathSlash += "/"
+-
+-		}
+-		LogInfo("[restful/swagger] %v%v is mapped to custom Handler %T", config.WebServicesUrl, swaggerPathSlash, config.StaticHandler)
+-		wsContainer.Handle(swaggerPathSlash, config.StaticHandler)
+-
+-	} else {
+-		LogInfo("[restful/swagger] Swagger(File)Path is empty ; no UI is served")
+-	}
+-}
+-
+-func staticPathFromRoute(r restful.Route) string {
+-	static := r.Path
+-	bracket := strings.Index(static, "{")
+-	if bracket <= 1 { // result cannot be empty
+-		return static
+-	}
+-	if bracket != -1 {
+-		static = r.Path[:bracket]
+-	}
+-	if strings.HasSuffix(static, "/") {
+-		return static[:len(static)-1]
+-	} else {
+-		return static
+-	}
+-}
+-
+-func enableCORS(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
+-	if origin := req.HeaderParameter(restful.HEADER_Origin); origin != "" {
+-		// prevent duplicate header
+-		if len(resp.Header().Get(restful.HEADER_AccessControlAllowOrigin)) == 0 {
+-			resp.AddHeader(restful.HEADER_AccessControlAllowOrigin, origin)
+-		}
+-	}
+-	chain.ProcessFilter(req, resp)
+-}
+-
+-func (sws SwaggerService) getListing(req *restful.Request, resp *restful.Response) {
+-	listing := ResourceListing{SwaggerVersion: swaggerVersion}
+-	for k, v := range sws.apiDeclarationMap {
+-		ref := Resource{Path: k}
+-		if len(v.Apis) > 0 { // use description of first (could still be empty)
+-			ref.Description = v.Apis[0].Description
+-		}
+-		listing.Apis = append(listing.Apis, ref)
+-	}
+-	resp.WriteAsJson(listing)
+-}
+-
+-func (sws SwaggerService) getDeclarations(req *restful.Request, resp *restful.Response) {
+-	decl := sws.apiDeclarationMap[composeRootPath(req)]
+-	// unless WebServicesUrl is given
+-	if len(sws.config.WebServicesUrl) == 0 {
+-		// update base path from the actual request
+-		// TODO how to detect https? assume http for now
+-		(&decl).BasePath = fmt.Sprintf("http://%s", req.Request.Host)
+-	}
+-	resp.WriteAsJson(decl)
+-}
+-
+-func (sws SwaggerService) composeDeclaration(ws *restful.WebService, pathPrefix string) ApiDeclaration {
+-	decl := ApiDeclaration{
+-		SwaggerVersion: swaggerVersion,
+-		BasePath:       sws.config.WebServicesUrl,
+-		ResourcePath:   ws.RootPath(),
+-		Models:         map[string]Model{},
+-		ApiVersion:     ws.Version()}
+-
+-	// collect any path parameters
+-	rootParams := []Parameter{}
+-	for _, param := range ws.PathParameters() {
+-		rootParams = append(rootParams, asSwaggerParameter(param.Data()))
+-	}
+-	// aggregate by path
+-	pathToRoutes := map[string][]restful.Route{}
+-	for _, other := range ws.Routes() {
+-		if strings.HasPrefix(other.Path, pathPrefix) {
+-			routes := pathToRoutes[other.Path]
+-			pathToRoutes[other.Path] = append(routes, other)
+-		}
+-	}
+-	for path, routes := range pathToRoutes {
+-		api := Api{Path: strings.TrimSuffix(path, "/"), Description: ws.Documentation()}
+-		for _, route := range routes {
+-			operation := Operation{
+-				Method:           route.Method,
+-				Summary:          route.Doc,
+-				Type:             asDataType(route.WriteSample),
+-				Parameters:       []Parameter{},
+-				Nickname:         route.Operation,
+-				ResponseMessages: composeResponseMessages(route, &decl)}
+-
+-			operation.Consumes = route.Consumes
+-			operation.Produces = route.Produces
+-
+-			// share root params if any
+-			for _, swparam := range rootParams {
+-				operation.Parameters = append(operation.Parameters, swparam)
+-			}
+-			// route specific params
+-			for _, param := range route.ParameterDocs {
+-				operation.Parameters = append(operation.Parameters, asSwaggerParameter(param.Data()))
+-			}
+-			// sort parameters
+-			sort.Sort(ParameterSorter(operation.Parameters))
+-
+-			sws.addModelsFromRouteTo(&operation, route, &decl)
+-			api.Operations = append(api.Operations, operation)
+-		}
+-		decl.Apis = append(decl.Apis, api)
+-	}
+-	return decl
+-}
+-
+-// composeResponseMessages takes the ResponseErrors (if any) and creates ResponseMessages from them.
+-func composeResponseMessages(route restful.Route, decl *ApiDeclaration) (messages []ResponseMessage) {
+-	if route.ResponseErrors == nil {
+-		return messages
+-	}
+-	// sort by code
+-	codes := sort.IntSlice{}
+-	for code, _ := range route.ResponseErrors {
+-		codes = append(codes, code)
+-	}
+-	codes.Sort()
+-	for _, code := range codes {
+-		each := route.ResponseErrors[code]
+-		message := ResponseMessage{
+-			Code:    code,
+-			Message: each.Message,
+-		}
+-		if each.Model != nil {
+-			st := reflect.TypeOf(each.Model)
+-			isCollection, st := detectCollectionType(st)
+-			modelName := modelBuilder{}.keyFrom(st)
+-			if isCollection {
+-				modelName = "array[" + modelName + "]"
+-			}
+-			modelBuilder{decl.Models}.addModel(st, "")
+-			// reference the model
+-			message.ResponseModel = modelName
+-		}
+-		messages = append(messages, message)
+-	}
+-	return
+-}
+-
+-// addModelsFromRoute takes any read or write sample from the Route and creates a Swagger model from it.
+-func (sws SwaggerService) addModelsFromRouteTo(operation *Operation, route restful.Route, decl *ApiDeclaration) {
+-	if route.ReadSample != nil {
+-		sws.addModelFromSampleTo(operation, false, route.ReadSample, decl.Models)
+-	}
+-	if route.WriteSample != nil {
+-		sws.addModelFromSampleTo(operation, true, route.WriteSample, decl.Models)
+-	}
+-}
+-
+-func detectCollectionType(st reflect.Type) (bool, reflect.Type) {
+-	isCollection := false
+-	if st.Kind() == reflect.Slice || st.Kind() == reflect.Array {
+-		st = st.Elem()
+-		isCollection = true
+-	} else {
+-		if st.Kind() == reflect.Ptr {
+-			if st.Elem().Kind() == reflect.Slice || st.Elem().Kind() == reflect.Array {
+-				st = st.Elem().Elem()
+-				isCollection = true
+-			}
+-		}
+-	}
+-	return isCollection, st
+-}
+-
+-// addModelFromSample creates and adds (or overwrites) a Model from a sample resource
+-func (sws SwaggerService) addModelFromSampleTo(operation *Operation, isResponse bool, sample interface{}, models map[string]Model) {
+-	st := reflect.TypeOf(sample)
+-	isCollection, st := detectCollectionType(st)
+-	modelName := modelBuilder{}.keyFrom(st)
+-	if isResponse {
+-		if isCollection {
+-			modelName = "array[" + modelName + "]"
+-		}
+-		operation.Type = modelName
+-	}
+-	modelBuilder{models}.addModel(reflect.TypeOf(sample), "")
+-}
+-
+-func asSwaggerParameter(param restful.ParameterData) Parameter {
+-	return Parameter{
+-		DataTypeFields: DataTypeFields{
+-			Type:   &param.DataType,
+-			Format: asFormat(param.DataType),
+-		},
+-		Name:        param.Name,
+-		Description: param.Description,
+-		ParamType:   asParamType(param.Kind),
+-
+-		Required: param.Required}
+-}
+-
+-// Between 1..7 path parameters is supported
+-func composeRootPath(req *restful.Request) string {
+-	path := "/" + req.PathParameter("a")
+-	b := req.PathParameter("b")
+-	if b == "" {
+-		return path
+-	}
+-	path = path + "/" + b
+-	c := req.PathParameter("c")
+-	if c == "" {
+-		return path
+-	}
+-	path = path + "/" + c
+-	d := req.PathParameter("d")
+-	if d == "" {
+-		return path
+-	}
+-	path = path + "/" + d
+-	e := req.PathParameter("e")
+-	if e == "" {
+-		return path
+-	}
+-	path = path + "/" + e
+-	f := req.PathParameter("f")
+-	if f == "" {
+-		return path
+-	}
+-	path = path + "/" + f
+-	g := req.PathParameter("g")
+-	if g == "" {
+-		return path
+-	}
+-	return path + "/" + g
+-}
+-
+-func asFormat(name string) string {
+-	return "" // TODO
+-}
+-
+-func asParamType(kind int) string {
+-	switch {
+-	case kind == restful.PathParameterKind:
+-		return "path"
+-	case kind == restful.QueryParameterKind:
+-		return "query"
+-	case kind == restful.BodyParameterKind:
+-		return "body"
+-	case kind == restful.HeaderParameterKind:
+-		return "header"
+-	case kind == restful.FormParameterKind:
+-		return "form"
+-	}
+-	return ""
+-}
+-
+-func asDataType(any interface{}) string {
+-	if any == nil {
+-		return "void"
+-	}
+-	return reflect.TypeOf(any).Name()
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/utils_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/utils_test.go
+deleted file mode 100644
+index 6127bd5..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/utils_test.go
++++ /dev/null
+@@ -1,70 +0,0 @@
+-package swagger
+-
+-import (
+-	"bytes"
+-	"encoding/json"
+-	"fmt"
+-	"reflect"
+-	"strings"
+-	"testing"
+-)
+-
+-func testJsonFromStruct(t *testing.T, sample interface{}, expectedJson string) {
+-	compareJson(t, false, modelsFromStruct(sample), expectedJson)
+-}
+-
+-func modelsFromStruct(sample interface{}) map[string]Model {
+-	models := map[string]Model{}
+-	builder := modelBuilder{models}
+-	builder.addModel(reflect.TypeOf(sample), "")
+-	return models
+-}
+-
+-func compareJson(t *testing.T, flatCompare bool, value interface{}, expectedJsonAsString string) {
+-	var output []byte
+-	var err error
+-	if flatCompare {
+-		output, err = json.Marshal(value)
+-	} else {
+-		output, err = json.MarshalIndent(value, " ", " ")
+-	}
+-	if err != nil {
+-		t.Error(err.Error())
+-		return
+-	}
+-	actual := string(output)
+-	if actual != expectedJsonAsString {
+-		t.Errorf("First mismatch JSON doc at line:%d", indexOfNonMatchingLine(actual, expectedJsonAsString))
+-		// Use simple fmt to create a pastable output :-)
+-		fmt.Println("---- expected -----")
+-		fmt.Println(withLineNumbers(expectedJsonAsString))
+-		fmt.Println("---- actual -----")
+-		fmt.Println(withLineNumbers(actual))
+-		fmt.Println("---- raw -----")
+-		fmt.Println(actual)
+-	}
+-}
+-
+-func indexOfNonMatchingLine(actual, expected string) int {
+-	a := strings.Split(actual, "\n")
+-	e := strings.Split(expected, "\n")
+-	size := len(a)
+-	if len(e) < len(a) {
+-		size = len(e)
+-	}
+-	for i := 0; i < size; i++ {
+-		if a[i] != e[i] {
+-			return i
+-		}
+-	}
+-	return -1
+-}
+-
+-func withLineNumbers(content string) string {
+-	var buffer bytes.Buffer
+-	lines := strings.Split(content, "\n")
+-	for i, each := range lines {
+-		buffer.WriteString(fmt.Sprintf("%d:%s\n", i, each))
+-	}
+-	return buffer.String()
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/web_service.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/web_service.go
+deleted file mode 100644
+index f3c10e0..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/web_service.go
++++ /dev/null
+@@ -1,190 +0,0 @@
+-package restful
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-import "log"
+-
+-// WebService holds a collection of Route values that bind a Http Method + URL Path to a function.
+-type WebService struct {
+-	rootPath       string
+-	pathExpr       *pathExpression // cached compilation of rootPath as RegExp
+-	routes         []Route
+-	produces       []string
+-	consumes       []string
+-	pathParameters []*Parameter
+-	filters        []FilterFunction
+-	documentation  string
+-	apiVersion     string
+-}
+-
+-// compilePathExpression ensures that the path is compiled into a RegEx for those routers that need it.
+-func (w *WebService) compilePathExpression() {
+-	if len(w.rootPath) == 0 {
+-		w.Path("/") // lazy initialize path
+-	}
+-	compiled, err := newPathExpression(w.rootPath)
+-	if err != nil {
+-		log.Fatalf("[restful] invalid path:%s because:%v", w.rootPath, err)
+-	}
+-	w.pathExpr = compiled
+-}
+-
+-// ApiVersion sets the API version for documentation purposes.
+-func (w *WebService) ApiVersion(apiVersion string) *WebService {
+-	w.apiVersion = apiVersion
+-	return w
+-}
+-
+-// Version returns the API version for documentation purposes.
+-func (w WebService) Version() string { return w.apiVersion }
+-
+-// Path specifies the root URL template path of the WebService.
+-// All Routes will be relative to this path.
+-func (w *WebService) Path(root string) *WebService {
+-	w.rootPath = root
+-	w.compilePathExpression()
+-	return w
+-}
+-
+-// Param adds a PathParameter to document parameters used in the root path.
+-func (w *WebService) Param(parameter *Parameter) *WebService {
+-	if w.pathParameters == nil {
+-		w.pathParameters = []*Parameter{}
+-	}
+-	w.pathParameters = append(w.pathParameters, parameter)
+-	return w
+-}
+-
+-// PathParameter creates a new Parameter of kind Path for documentation purposes.
+-// It is initialized as required with string as its DataType.
+-func (w *WebService) PathParameter(name, description string) *Parameter {
+-	p := &Parameter{&ParameterData{Name: name, Description: description, Required: true, DataType: "string"}}
+-	p.bePath()
+-	return p
+-}
+-
+-// QueryParameter creates a new Parameter of kind Query for documentation purposes.
+-// It is initialized as not required with string as its DataType.
+-func (w *WebService) QueryParameter(name, description string) *Parameter {
+-	p := &Parameter{&ParameterData{Name: name, Description: description, Required: false, DataType: "string"}}
+-	p.beQuery()
+-	return p
+-}
+-
+-// BodyParameter creates a new Parameter of kind Body for documentation purposes.
+-// It is initialized as required without a DataType.
+-func (w *WebService) BodyParameter(name, description string) *Parameter {
+-	p := &Parameter{&ParameterData{Name: name, Description: description, Required: true}}
+-	p.beBody()
+-	return p
+-}
+-
+-// HeaderParameter creates a new Parameter of kind (Http) Header for documentation purposes.
+-// It is initialized as not required with string as its DataType.
+-func (w *WebService) HeaderParameter(name, description string) *Parameter {
+-	p := &Parameter{&ParameterData{Name: name, Description: description, Required: false, DataType: "string"}}
+-	p.beHeader()
+-	return p
+-}
+-
+-// FormParameter creates a new Parameter of kind Form (using application/x-www-form-urlencoded) for documentation purposes.
+-// It is initialized as required with string as its DataType.
+-func (w *WebService) FormParameter(name, description string) *Parameter {
+-	p := &Parameter{&ParameterData{Name: name, Description: description, Required: false, DataType: "string"}}
+-	p.beForm()
+-	return p
+-}
+-
+-// Route creates a new Route using the RouteBuilder and add to the ordered list of Routes.
+-func (w *WebService) Route(builder *RouteBuilder) *WebService {
+-	builder.copyDefaults(w.produces, w.consumes)
+-	w.routes = append(w.routes, builder.Build())
+-	return w
+-}
+-
+-// Method creates a new RouteBuilder and initialize its http method
+-func (w *WebService) Method(httpMethod string) *RouteBuilder {
+-	return new(RouteBuilder).servicePath(w.rootPath).Method(httpMethod)
+-}
+-
+-// Produces specifies that this WebService can produce one or more MIME types.
+-// Http requests must have one of these values set for the Accept header.
+-func (w *WebService) Produces(contentTypes ...string) *WebService {
+-	w.produces = contentTypes
+-	return w
+-}
+-
+-// Consumes specifies that this WebService can consume one or more MIME types.
+-// Http requests must have one of these values set for the Content-Type header.
+-func (w *WebService) Consumes(accepts ...string) *WebService {
+-	w.consumes = accepts
+-	return w
+-}
+-
+-// Routes returns the Routes associated with this WebService
+-func (w WebService) Routes() []Route {
+-	return w.routes
+-}
+-
+-// RootPath returns the RootPath associated with this WebService. Default "/"
+-func (w WebService) RootPath() string {
+-	return w.rootPath
+-}
+-
+-// PathParameters return the path parameter names for (shared amoung its Routes)
+-func (w WebService) PathParameters() []*Parameter {
+-	return w.pathParameters
+-}
+-
+-// Filter adds a filter function to the chain of filters applicable to all its Routes
+-func (w *WebService) Filter(filter FilterFunction) *WebService {
+-	w.filters = append(w.filters, filter)
+-	return w
+-}
+-
+-// Doc is used to set the documentation of this service.
+-func (w *WebService) Doc(plainText string) *WebService {
+-	w.documentation = plainText
+-	return w
+-}
+-
+-// Documentation returns it.
+-func (w WebService) Documentation() string {
+-	return w.documentation
+-}
+-
+-/*
+-	Convenience methods
+-*/
+-
+-// HEAD is a shortcut for .Method("HEAD").Path(subPath)
+-func (w *WebService) HEAD(subPath string) *RouteBuilder {
+-	return new(RouteBuilder).servicePath(w.rootPath).Method("HEAD").Path(subPath)
+-}
+-
+-// GET is a shortcut for .Method("GET").Path(subPath)
+-func (w *WebService) GET(subPath string) *RouteBuilder {
+-	return new(RouteBuilder).servicePath(w.rootPath).Method("GET").Path(subPath)
+-}
+-
+-// POST is a shortcut for .Method("POST").Path(subPath)
+-func (w *WebService) POST(subPath string) *RouteBuilder {
+-	return new(RouteBuilder).servicePath(w.rootPath).Method("POST").Path(subPath)
+-}
+-
+-// PUT is a shortcut for .Method("PUT").Path(subPath)
+-func (w *WebService) PUT(subPath string) *RouteBuilder {
+-	return new(RouteBuilder).servicePath(w.rootPath).Method("PUT").Path(subPath)
+-}
+-
+-// PATCH is a shortcut for .Method("PATCH").Path(subPath)
+-func (w *WebService) PATCH(subPath string) *RouteBuilder {
+-	return new(RouteBuilder).servicePath(w.rootPath).Method("PATCH").Path(subPath)
+-}
+-
+-// DELETE is a shortcut for .Method("DELETE").Path(subPath)
+-func (w *WebService) DELETE(subPath string) *RouteBuilder {
+-	return new(RouteBuilder).servicePath(w.rootPath).Method("DELETE").Path(subPath)
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/web_service_container.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/web_service_container.go
+deleted file mode 100644
+index c9d31b0..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/web_service_container.go
++++ /dev/null
+@@ -1,39 +0,0 @@
+-package restful
+-
+-// Copyright 2013 Ernest Micklei. All rights reserved.
+-// Use of this source code is governed by a license
+-// that can be found in the LICENSE file.
+-
+-import (
+-	"net/http"
+-)
+-
+-// DefaultContainer is a restful.Container that uses http.DefaultServeMux
+-var DefaultContainer *Container
+-
+-func init() {
+-	DefaultContainer = NewContainer()
+-	DefaultContainer.ServeMux = http.DefaultServeMux
+-}
+-
+-// If set the true then panics will not be caught to return HTTP 500.
+-// In that case, Route functions are responsible for handling any error situation.
+-// Default value is false = recover from panics. This has performance implications.
+-// OBSOLETE ; use restful.DefaultContainer.DoNotRecover(true)
+-var DoNotRecover = false
+-
+-// Add registers a new WebService add it to the DefaultContainer.
+-func Add(service *WebService) {
+-	DefaultContainer.Add(service)
+-}
+-
+-// Filter appends a container FilterFunction from the DefaultContainer.
+-// These are called before dispatching a http.Request to a WebService.
+-func Filter(filter FilterFunction) {
+-	DefaultContainer.Filter(filter)
+-}
+-
+-// RegisteredWebServices returns the collections of WebServices from the DefaultContainer
+-func RegisteredWebServices() []*WebService {
+-	return DefaultContainer.RegisteredWebServices()
+-}
+diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/web_service_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/web_service_test.go
+deleted file mode 100644
+index e200979..0000000
+--- a/Godeps/_workspace/src/github.com/emicklei/go-restful/web_service_test.go
++++ /dev/null
+@@ -1,115 +0,0 @@
+-package restful
+-
+-import (
+-	"net/http"
+-	"net/http/httptest"
+-	"testing"
+-)
+-
+-const (
+-	pathGetFriends = "/get/{userId}/friends"
+-)
+-
+-func TestParameter(t *testing.T) {
+-	p := &Parameter{&ParameterData{Name: "name", Description: "desc"}}
+-	p.AllowMultiple(true)
+-	p.DataType("int")
+-	p.Required(true)
+-	values := map[string]string{"a": "b"}
+-	p.AllowableValues(values)
+-	p.bePath()
+-
+-	ws := new(WebService)
+-	ws.Param(p)
+-	if ws.pathParameters[0].Data().Name != "name" {
+-		t.Error("path parameter (or name) invalid")
+-	}
+-}
+-func TestWebService_CanCreateParameterKinds(t *testing.T) {
+-	ws := new(WebService)
+-	if ws.BodyParameter("b", "b").Kind() != BodyParameterKind {
+-		t.Error("body parameter expected")
+-	}
+-	if ws.PathParameter("p", "p").Kind() != PathParameterKind {
+-		t.Error("path parameter expected")
+-	}
+-	if ws.QueryParameter("q", "q").Kind() != QueryParameterKind {
+-		t.Error("query parameter expected")
+-	}
+-}
+-
+-func TestCapturePanic(t *testing.T) {
+-	tearDown()
+-	Add(newPanicingService())
+-	httpRequest, _ := http.NewRequest("GET", "http://here.com/fire", nil)
+-	httpRequest.Header.Set("Accept", "*/*")
+-	httpWriter := httptest.NewRecorder()
+-	DefaultContainer.dispatch(httpWriter, httpRequest)
+-	if 500 != httpWriter.Code {
+-		t.Error("500 expected on fire")
+-	}
+-}
+-
+-func TestNotFound(t *testing.T) {
+-	tearDown()
+-	httpRequest, _ := http.NewRequest("GET", "http://here.com/missing", nil)
+-	httpRequest.Header.Set("Accept", "*/*")
+-	httpWriter := httptest.NewRecorder()
+-	DefaultContainer.dispatch(httpWriter, httpRequest)
+-	if 404 != httpWriter.Code {
+-		t.Error("404 expected on missing")
+-	}
+-}
+-
+-func TestMethodNotAllowed(t *testing.T) {
+-	tearDown()
+-	Add(newGetOnlyService())
+-	httpRequest, _ := http.NewRequest("POST", "http://here.com/get", nil)
+-	httpRequest.Header.Set("Accept", "*/*")
+-	httpWriter := httptest.NewRecorder()
+-	DefaultContainer.dispatch(httpWriter, httpRequest)
+-	if 405 != httpWriter.Code {
+-		t.Error("405 expected method not allowed")
+-	}
+-}
+-
+-func TestSelectedRoutePath_Issue100(t *testing.T) {
+-	tearDown()
+-	Add(newSelectedRouteTestingService())
+-	httpRequest, _ := http.NewRequest("GET", "http://here.com/get/232452/friends", nil)
+-	httpRequest.Header.Set("Accept", "*/*")
+-	httpWriter := httptest.NewRecorder()
+-	DefaultContainer.dispatch(httpWriter, httpRequest)
+-	if http.StatusOK != httpWriter.Code {
+-		t.Error(http.StatusOK, "expected,", httpWriter.Code, "received.")
+-	}
+-}
+-
+-func newPanicingService() *WebService {
+-	ws := new(WebService).Path("")
+-	ws.Route(ws.GET("/fire").To(doPanic))
+-	return ws
+-}
+-
+-func newGetOnlyService() *WebService {
+-	ws := new(WebService).Path("")
+-	ws.Route(ws.GET("/get").To(doPanic))
+-	return ws
+-}
+-
+-func newSelectedRouteTestingService() *WebService {
+-	ws := new(WebService).Path("")
+-	ws.Route(ws.GET(pathGetFriends).To(selectedRouteChecker))
+-	return ws
+-}
+-
+-func selectedRouteChecker(req *Request, resp *Response) {
+-	if req.SelectedRoutePath() != pathGetFriends {
+-		resp.InternalServerError()
+-	}
+-}
+-
+-func doPanic(req *Request, resp *Response) {
+-	println("lightning...")
+-	panic("fire")
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/.travis.yml b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/.travis.yml
+deleted file mode 100644
+index 5a19fae..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/.travis.yml
++++ /dev/null
+@@ -1,13 +0,0 @@
+-language: go
+-go:
+-  - 1.2.2
+-  - 1.3.1
+-  - tip
+-env:
+-  - GOARCH=amd64
+-  - GOARCH=386
+-install:
+-  - go get -d ./...
+-script:
+-  - go test ./...
+-  - ./testing/bin/fmtpolice
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/AUTHORS b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/AUTHORS
+deleted file mode 100644
+index 1470c64..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/AUTHORS
++++ /dev/null
+@@ -1,50 +0,0 @@
+-# This is the official list of go-dockerclient authors for copyright purposes.
+-
+-Aldrin Leal <aldrin at leal.eng.br>
+-Andreas Jaekle <andreas at jaekle.net>
+-Andrews Medina <andrewsmedina at gmail.com>
+-Andy Goldstein <andy.goldstein at redhat.com>
+-Ben McCann <benmccann.com>
+-Carlos Diaz-Padron <cpadron at mozilla.com>
+-Cezar Sa Espinola <cezar.sa at corp.globo.com>
+-Cheah Chu Yeow <chuyeow at gmail.com>
+-cheneydeng <cheneydeng at qq.com>
+-CMGS <ilskdw at gmail.com>
+-Daniel, Dao Quang Minh <dqminh89 at gmail.com>
+-David Huie <dahuie at gmail.com>
+-Dawn Chen <dawnchen at google.com>
+-Ed <edrocksit at gmail.com>
+-Eric Anderson <anderson at copperegg.com>
+-Fabio Rehm <fgrehm at gmail.com>
+-Flavia Missi <flaviamissi at gmail.com>
+-Francisco Souza <f at souza.cc>
+-Jari Kolehmainen <jari.kolehmainen at digia.com>
+-Jason Wilder <jwilder at litl.com>
+-Jawher Moussa <jawher.moussa at gmail.com>
+-Jean-Baptiste Dalido <jeanbaptiste at appgratis.com>
+-Jeff Mitchell <jeffrey.mitchell at gmail.com>
+-Jeffrey Hulten <jhulten at gmail.com>
+-Johan Euphrosine <proppy at google.com>
+-Karan Misra <kidoman at gmail.com>
+-Kim, Hirokuni <hirokuni.kim at kvh.co.jp>
+-Lucas Clemente <lucas at clemente.io>
+-Máximo Cuadros Ortiz <mcuadros at gmail.com>
+-Mike Dillon <mike.dillon at synctree.com>
+-Omeid Matten <public at omeid.me>
+-Paul Morie <pmorie at gmail.com>
+-Peter Jihoon Kim <raingrove at gmail.com>
+-Philippe Lafoucrière <philippe.lafoucriere at tech-angels.com>
+-Rafe Colton <rafael.colton at gmail.com>
+-Rob Miller <rob at kalistra.com>
+-Robert Williamson <williamson.robert at gmail.com>
+-Salvador Gironès <salvadorgirones at gmail.com>
+-Simon Eskildsen <sirup at sirupsen.com>
+-Simon Menke <simon.menke at gmail.com>
+-Skolos <skolos at gopherlab.com>
+-Soulou <leo at unbekandt.eu>
+-Sridhar Ratnakumar <sridharr at activestate.com>
+-Summer Mousa <smousa at zenoss.com>
+-Tarsis Azevedo <tarsis at corp.globo.com>
+-Tim Schindler <tim at catalyst-zero.com>
+-Wiliam Souza <wiliamsouza83 at gmail.com>
+-Ye Yin <eyniy at qq.com>
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/DOCKER-LICENSE b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/DOCKER-LICENSE
+deleted file mode 100644
+index f4130a5..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/DOCKER-LICENSE
++++ /dev/null
+@@ -1,6 +0,0 @@
+-                                 Apache License
+-                           Version 2.0, January 2004
+-                        http://www.apache.org/licenses/
+-
+-You can find the Docker license int the following link:
+-https://raw2.github.com/dotcloud/docker/master/LICENSE
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/LICENSE b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/LICENSE
+deleted file mode 100644
+index 7a6d8bb..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/LICENSE
++++ /dev/null
+@@ -1,22 +0,0 @@
+-Copyright (c) 2014, go-dockerclient authors
+-All rights reserved.
+-
+-Redistribution and use in source and binary forms, with or without
+-modification, are permitted provided that the following conditions are met:
+-
+-  * Redistributions of source code must retain the above copyright notice,
+-this list of conditions and the following disclaimer.
+-  * Redistributions in binary form must reproduce the above copyright notice,
+-this list of conditions and the following disclaimer in the documentation
+-and/or other materials provided with the distribution.
+-
+-THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
+-ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+-WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+-DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
+-FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+-DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+-SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+-CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+-OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+-OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/README.markdown b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/README.markdown
+deleted file mode 100644
+index 0f95d1f..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/README.markdown
++++ /dev/null
+@@ -1,42 +0,0 @@
+-#go-dockerclient
+-
+-[![Build Status](https://drone.io/github.com/fsouza/go-dockerclient/status.png)](https://drone.io/github.com/fsouza/go-dockerclient/latest)
+-[![Build Status](https://travis-ci.org/fsouza/go-dockerclient.png)](https://travis-ci.org/fsouza/go-dockerclient)
+-
+-[![GoDoc](http://godoc.org/github.com/fsouza/go-dockerclient?status.png)](http://godoc.org/github.com/fsouza/go-dockerclient)
+-
+-This package presents a client for the Docker remote API.
+-
+-For more details, check the [remote API documentation](http://docs.docker.io/en/latest/reference/api/docker_remote_api/).
+-
+-## Example
+-
+-```go
+-package main
+-
+-import (
+-        "fmt"
+-        "github.com/fsouza/go-dockerclient"
+-)
+-
+-func main() {
+-        endpoint := "unix:///var/run/docker.sock"
+-        client, _ := docker.NewClient(endpoint)
+-        imgs, _ := client.ListImages(true)
+-        for _, img := range imgs {
+-                fmt.Println("ID: ", img.ID)
+-                fmt.Println("RepoTags: ", img.RepoTags)
+-                fmt.Println("Created: ", img.Created)
+-                fmt.Println("Size: ", img.Size)
+-                fmt.Println("VirtualSize: ", img.VirtualSize)
+-                fmt.Println("ParentId: ", img.ParentID)
+-        }
+-}
+-```
+-
+-## Developing
+-
+-You can run the tests with:
+-
+-    go get -d ./...
+-    go test ./...
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/build_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/build_test.go
+deleted file mode 100644
+index ecd9885..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/build_test.go
++++ /dev/null
+@@ -1,144 +0,0 @@
+-package docker
+-
+-import (
+-	"bytes"
+-	"io"
+-	"io/ioutil"
+-	"net/http"
+-	"os"
+-	"reflect"
+-	"testing"
+-
+-	"github.com/docker/docker/pkg/archive"
+-)
+-
+-func TestBuildImageMultipleContextsError(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-	opts := BuildImageOptions{
+-		Name:                "testImage",
+-		NoCache:             true,
+-		SuppressOutput:      true,
+-		RmTmpContainer:      true,
+-		ForceRmTmpContainer: true,
+-		InputStream:         &buf,
+-		OutputStream:        &buf,
+-		ContextDir:          "testing/data",
+-	}
+-	err := client.BuildImage(opts)
+-	if err != ErrMultipleContexts {
+-		t.Errorf("BuildImage: providing both InputStream and ContextDir should produce an error")
+-	}
+-}
+-
+-func TestBuildImageContextDirDockerignoreParsing(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-	opts := BuildImageOptions{
+-		Name:                "testImage",
+-		NoCache:             true,
+-		SuppressOutput:      true,
+-		RmTmpContainer:      true,
+-		ForceRmTmpContainer: true,
+-		OutputStream:        &buf,
+-		ContextDir:          "testing/data",
+-	}
+-	err := client.BuildImage(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	reqBody := fakeRT.requests[0].Body
+-	tmpdir, err := unpackBodyTarball(reqBody)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	defer func() {
+-		if err := os.RemoveAll(tmpdir); err != nil {
+-			t.Fatal(err)
+-		}
+-	}()
+-
+-	files, err := ioutil.ReadDir(tmpdir)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	foundFiles := []string{}
+-	for _, file := range files {
+-		foundFiles = append(foundFiles, file.Name())
+-	}
+-
+-	expectedFiles := []string{
+-		".dockerignore",
+-		"Dockerfile",
+-		"barfile",
+-		"ca.pem",
+-		"cert.pem",
+-		"key.pem",
+-		"server.pem",
+-		"serverkey.pem",
+-		"symlink",
+-	}
+-
+-	if !reflect.DeepEqual(expectedFiles, foundFiles) {
+-		t.Errorf(
+-			"BuildImage: incorrect files sent in tarball to docker server\nexpected %+v, found %+v",
+-			expectedFiles, foundFiles,
+-		)
+-	}
+-}
+-
+-func TestBuildImageSendXRegistryConfig(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-	opts := BuildImageOptions{
+-		Name:                "testImage",
+-		NoCache:             true,
+-		SuppressOutput:      true,
+-		RmTmpContainer:      true,
+-		ForceRmTmpContainer: true,
+-		OutputStream:        &buf,
+-		ContextDir:          "testing/data",
+-		AuthConfigs: AuthConfigurations{
+-			Configs: map[string]AuthConfiguration{
+-				"quay.io": {
+-					Username:      "foo",
+-					Password:      "bar",
+-					Email:         "baz",
+-					ServerAddress: "quay.io",
+-				},
+-			},
+-		},
+-	}
+-
+-	encodedConfig := "eyJjb25maWdzIjp7InF1YXkuaW8iOnsidXNlcm5hbWUiOiJmb28iLCJwYXNzd29yZCI6ImJhciIsImVtYWlsIjoiYmF6Iiwic2VydmVyYWRkcmVzcyI6InF1YXkuaW8ifX19Cg=="
+-
+-	if err := client.BuildImage(opts); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	xRegistryConfig := fakeRT.requests[0].Header["X-Registry-Config"][0]
+-	if xRegistryConfig != encodedConfig {
+-		t.Errorf(
+-			"BuildImage: X-Registry-Config not set currectly: expected %q, got %q",
+-			encodedConfig,
+-			xRegistryConfig,
+-		)
+-	}
+-}
+-
+-func unpackBodyTarball(req io.ReadCloser) (tmpdir string, err error) {
+-	tmpdir, err = ioutil.TempDir("", "go-dockerclient-test")
+-	if err != nil {
+-		return
+-	}
+-	err = archive.Untar(req, tmpdir, &archive.TarOptions{
+-		Compression: archive.Uncompressed,
+-		NoLchown:    true,
+-	})
+-	return
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/change.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/change.go
+deleted file mode 100644
+index e7b056c..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/change.go
++++ /dev/null
+@@ -1,43 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 docker
+-
+-import "fmt"
+-
+-// ChangeType is a type for constants indicating the type of change
+-// in a container
+-type ChangeType int
+-
+-const (
+-	// ChangeModify is the ChangeType for container modifications
+-	ChangeModify ChangeType = iota
+-
+-	// ChangeAdd is the ChangeType for additions to a container
+-	ChangeAdd
+-
+-	// ChangeDelete is the ChangeType for deletions from a container
+-	ChangeDelete
+-)
+-
+-// Change represents a change in a container.
+-//
+-// See http://goo.gl/QkW9sH for more details.
+-type Change struct {
+-	Path string
+-	Kind ChangeType
+-}
+-
+-func (change *Change) String() string {
+-	var kind string
+-	switch change.Kind {
+-	case ChangeModify:
+-		kind = "C"
+-	case ChangeAdd:
+-		kind = "A"
+-	case ChangeDelete:
+-		kind = "D"
+-	}
+-	return fmt.Sprintf("%s %s", kind, change.Path)
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/change_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/change_test.go
+deleted file mode 100644
+index 7c2ec30..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/change_test.go
++++ /dev/null
+@@ -1,26 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 docker
+-
+-import (
+-	"testing"
+-)
+-
+-func TestChangeString(t *testing.T) {
+-	var tests = []struct {
+-		change   Change
+-		expected string
+-	}{
+-		{Change{"/etc/passwd", ChangeModify}, "C /etc/passwd"},
+-		{Change{"/etc/passwd", ChangeAdd}, "A /etc/passwd"},
+-		{Change{"/etc/passwd", ChangeDelete}, "D /etc/passwd"},
+-		{Change{"/etc/passwd", 33}, " /etc/passwd"},
+-	}
+-	for _, tt := range tests {
+-		if got := tt.change.String(); got != tt.expected {
+-			t.Errorf("Change.String(): want %q. Got %q.", tt.expected, got)
+-		}
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/client.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/client.go
+deleted file mode 100644
+index 3d86ff2..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/client.go
++++ /dev/null
+@@ -1,636 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 docker provides a client for the Docker remote API.
+-//
+-// See http://goo.gl/G3plxW for more details on the remote API.
+-package docker
+-
+-import (
+-	"bytes"
+-	"crypto/tls"
+-	"crypto/x509"
+-	"encoding/json"
+-	"errors"
+-	"fmt"
+-	"io"
+-	"io/ioutil"
+-	"net"
+-	"net/http"
+-	"net/http/httputil"
+-	"net/url"
+-	"reflect"
+-	"strconv"
+-	"strings"
+-)
+-
+-const userAgent = "go-dockerclient"
+-
+-var (
+-	// ErrInvalidEndpoint is returned when the endpoint is not a valid HTTP URL.
+-	ErrInvalidEndpoint = errors.New("invalid endpoint")
+-
+-	// ErrConnectionRefused is returned when the client cannot connect to the given endpoint.
+-	ErrConnectionRefused = errors.New("cannot connect to Docker endpoint")
+-
+-	apiVersion1_12, _ = NewAPIVersion("1.12")
+-)
+-
+-// APIVersion is an internal representation of a version of the Remote API.
+-type APIVersion []int
+-
+-// NewAPIVersion returns an instance of APIVersion for the given string.
+-//
+-// The given string must be in the form <major>.<minor>.<patch>, where <major>,
+-// <minor> and <patch> are integer numbers.
+-func NewAPIVersion(input string) (APIVersion, error) {
+-	if !strings.Contains(input, ".") {
+-		return nil, fmt.Errorf("Unable to parse version %q", input)
+-	}
+-	arr := strings.Split(input, ".")
+-	ret := make(APIVersion, len(arr))
+-	var err error
+-	for i, val := range arr {
+-		ret[i], err = strconv.Atoi(val)
+-		if err != nil {
+-			return nil, fmt.Errorf("Unable to parse version %q: %q is not an integer", input, val)
+-		}
+-	}
+-	return ret, nil
+-}
+-
+-func (version APIVersion) String() string {
+-	var str string
+-	for i, val := range version {
+-		str += strconv.Itoa(val)
+-		if i < len(version)-1 {
+-			str += "."
+-		}
+-	}
+-	return str
+-}
+-
+-// LessThan is a function for comparing APIVersion structs
+-func (version APIVersion) LessThan(other APIVersion) bool {
+-	return version.compare(other) < 0
+-}
+-
+-// LessThanOrEqualTo is a function for comparing APIVersion structs
+-func (version APIVersion) LessThanOrEqualTo(other APIVersion) bool {
+-	return version.compare(other) <= 0
+-}
+-
+-// GreaterThan is a function for comparing APIVersion structs
+-func (version APIVersion) GreaterThan(other APIVersion) bool {
+-	return version.compare(other) > 0
+-}
+-
+-// GreaterThanOrEqualTo is a function for comparing APIVersion structs
+-func (version APIVersion) GreaterThanOrEqualTo(other APIVersion) bool {
+-	return version.compare(other) >= 0
+-}
+-
+-func (version APIVersion) compare(other APIVersion) int {
+-	for i, v := range version {
+-		if i <= len(other)-1 {
+-			otherVersion := other[i]
+-
+-			if v < otherVersion {
+-				return -1
+-			} else if v > otherVersion {
+-				return 1
+-			}
+-		}
+-	}
+-	if len(version) > len(other) {
+-		return 1
+-	}
+-	if len(version) < len(other) {
+-		return -1
+-	}
+-	return 0
+-}
+-
+-// Client is the basic type of this package. It provides methods for
+-// interaction with the API.
+-type Client struct {
+-	SkipServerVersionCheck bool
+-	HTTPClient             *http.Client
+-	TLSConfig              *tls.Config
+-
+-	endpoint            string
+-	endpointURL         *url.URL
+-	eventMonitor        *eventMonitoringState
+-	requestedAPIVersion APIVersion
+-	serverAPIVersion    APIVersion
+-	expectedAPIVersion  APIVersion
+-}
+-
+-// NewClient returns a Client instance ready for communication with the given
+-// server endpoint. It will use the latest remote API version available in the
+-// server.
+-func NewClient(endpoint string) (*Client, error) {
+-	client, err := NewVersionedClient(endpoint, "")
+-	if err != nil {
+-		return nil, err
+-	}
+-	client.SkipServerVersionCheck = true
+-	return client, nil
+-}
+-
+-// NewTLSClient returns a Client instance ready for TLS communications with the givens
+-// server endpoint, key and certificates . It will use the latest remote API version
+-// available in the server.
+-func NewTLSClient(endpoint string, cert, key, ca string) (*Client, error) {
+-	client, err := NewVersionnedTLSClient(endpoint, cert, key, ca, "")
+-	if err != nil {
+-		return nil, err
+-	}
+-	client.SkipServerVersionCheck = true
+-	return client, nil
+-}
+-
+-// NewVersionedClient returns a Client instance ready for communication with
+-// the given server endpoint, using a specific remote API version.
+-func NewVersionedClient(endpoint string, apiVersionString string) (*Client, error) {
+-	u, err := parseEndpoint(endpoint)
+-	if err != nil {
+-		return nil, err
+-	}
+-	var requestedAPIVersion APIVersion
+-	if strings.Contains(apiVersionString, ".") {
+-		requestedAPIVersion, err = NewAPIVersion(apiVersionString)
+-		if err != nil {
+-			return nil, err
+-		}
+-	}
+-	return &Client{
+-		HTTPClient:          http.DefaultClient,
+-		endpoint:            endpoint,
+-		endpointURL:         u,
+-		eventMonitor:        new(eventMonitoringState),
+-		requestedAPIVersion: requestedAPIVersion,
+-	}, nil
+-}
+-
+-// NewVersionnedTLSClient returns a Client instance ready for TLS communications with the givens
+-// server endpoint, key and certificates, using a specific remote API version.
+-func NewVersionnedTLSClient(endpoint string, cert, key, ca, apiVersionString string) (*Client, error) {
+-	u, err := parseEndpoint(endpoint)
+-	if err != nil {
+-		return nil, err
+-	}
+-	var requestedAPIVersion APIVersion
+-	if strings.Contains(apiVersionString, ".") {
+-		requestedAPIVersion, err = NewAPIVersion(apiVersionString)
+-		if err != nil {
+-			return nil, err
+-		}
+-	}
+-	if cert == "" || key == "" {
+-		return nil, errors.New("Both cert and key path are required")
+-	}
+-	tlsCert, err := tls.LoadX509KeyPair(cert, key)
+-	if err != nil {
+-		return nil, err
+-	}
+-	tlsConfig := &tls.Config{Certificates: []tls.Certificate{tlsCert}}
+-	if ca == "" {
+-		tlsConfig.InsecureSkipVerify = true
+-	} else {
+-		cert, err := ioutil.ReadFile(ca)
+-		if err != nil {
+-			return nil, err
+-		}
+-		caPool := x509.NewCertPool()
+-		if !caPool.AppendCertsFromPEM(cert) {
+-			return nil, errors.New("Could not add RootCA pem")
+-		}
+-		tlsConfig.RootCAs = caPool
+-	}
+-	tr := &http.Transport{
+-		TLSClientConfig: tlsConfig,
+-	}
+-	if err != nil {
+-		return nil, err
+-	}
+-	return &Client{
+-		HTTPClient:          &http.Client{Transport: tr},
+-		TLSConfig:           tlsConfig,
+-		endpoint:            endpoint,
+-		endpointURL:         u,
+-		eventMonitor:        new(eventMonitoringState),
+-		requestedAPIVersion: requestedAPIVersion,
+-	}, nil
+-}
+-
+-func (c *Client) checkAPIVersion() error {
+-	serverAPIVersionString, err := c.getServerAPIVersionString()
+-	if err != nil {
+-		return err
+-	}
+-	c.serverAPIVersion, err = NewAPIVersion(serverAPIVersionString)
+-	if err != nil {
+-		return err
+-	}
+-	if c.requestedAPIVersion == nil {
+-		c.expectedAPIVersion = c.serverAPIVersion
+-	} else {
+-		c.expectedAPIVersion = c.requestedAPIVersion
+-	}
+-	return nil
+-}
+-
+-// Ping pings the docker server
+-//
+-// See http://goo.gl/stJENm for more details.
+-func (c *Client) Ping() error {
+-	path := "/_ping"
+-	body, status, err := c.do("GET", path, nil)
+-	if err != nil {
+-		return err
+-	}
+-	if status != http.StatusOK {
+-		return newError(status, body)
+-	}
+-	return nil
+-}
+-
+-func (c *Client) getServerAPIVersionString() (version string, err error) {
+-	body, status, err := c.do("GET", "/version", nil)
+-	if err != nil {
+-		return "", err
+-	}
+-	if status != http.StatusOK {
+-		return "", fmt.Errorf("Received unexpected status %d while trying to retrieve the server version", status)
+-	}
+-	var versionResponse map[string]string
+-	err = json.Unmarshal(body, &versionResponse)
+-	if err != nil {
+-		return "", err
+-	}
+-	version = versionResponse["ApiVersion"]
+-	return version, nil
+-}
+-
+-func (c *Client) do(method, path string, data interface{}) ([]byte, int, error) {
+-	var params io.Reader
+-	if data != nil {
+-		buf, err := json.Marshal(data)
+-		if err != nil {
+-			return nil, -1, err
+-		}
+-		params = bytes.NewBuffer(buf)
+-	}
+-	if path != "/version" && !c.SkipServerVersionCheck && c.expectedAPIVersion == nil {
+-		err := c.checkAPIVersion()
+-		if err != nil {
+-			return nil, -1, err
+-		}
+-	}
+-	req, err := http.NewRequest(method, c.getURL(path), params)
+-	if err != nil {
+-		return nil, -1, err
+-	}
+-	req.Header.Set("User-Agent", userAgent)
+-	if data != nil {
+-		req.Header.Set("Content-Type", "application/json")
+-	} else if method == "POST" {
+-		req.Header.Set("Content-Type", "plain/text")
+-	}
+-	var resp *http.Response
+-	protocol := c.endpointURL.Scheme
+-	address := c.endpointURL.Path
+-	if protocol == "unix" {
+-		dial, err := net.Dial(protocol, address)
+-		if err != nil {
+-			return nil, -1, err
+-		}
+-		defer dial.Close()
+-		clientconn := httputil.NewClientConn(dial, nil)
+-		resp, err = clientconn.Do(req)
+-		if err != nil {
+-			return nil, -1, err
+-		}
+-		defer clientconn.Close()
+-	} else {
+-		resp, err = c.HTTPClient.Do(req)
+-	}
+-	if err != nil {
+-		if strings.Contains(err.Error(), "connection refused") {
+-			return nil, -1, ErrConnectionRefused
+-		}
+-		return nil, -1, err
+-	}
+-	defer resp.Body.Close()
+-	body, err := ioutil.ReadAll(resp.Body)
+-	if err != nil {
+-		return nil, -1, err
+-	}
+-	if resp.StatusCode < 200 || resp.StatusCode >= 400 {
+-		return nil, resp.StatusCode, newError(resp.StatusCode, body)
+-	}
+-	return body, resp.StatusCode, nil
+-}
+-
+-func (c *Client) stream(method, path string, setRawTerminal, rawJSONStream bool, headers map[string]string, in io.Reader, stdout, stderr io.Writer) error {
+-	if (method == "POST" || method == "PUT") && in == nil {
+-		in = bytes.NewReader(nil)
+-	}
+-	if path != "/version" && !c.SkipServerVersionCheck && c.expectedAPIVersion == nil {
+-		err := c.checkAPIVersion()
+-		if err != nil {
+-			return err
+-		}
+-	}
+-	req, err := http.NewRequest(method, c.getURL(path), in)
+-	if err != nil {
+-		return err
+-	}
+-	req.Header.Set("User-Agent", userAgent)
+-	if method == "POST" {
+-		req.Header.Set("Content-Type", "plain/text")
+-	}
+-	for key, val := range headers {
+-		req.Header.Set(key, val)
+-	}
+-	var resp *http.Response
+-	protocol := c.endpointURL.Scheme
+-	address := c.endpointURL.Path
+-	if stdout == nil {
+-		stdout = ioutil.Discard
+-	}
+-	if stderr == nil {
+-		stderr = ioutil.Discard
+-	}
+-	if protocol == "unix" {
+-		dial, err := net.Dial(protocol, address)
+-		if err != nil {
+-			return err
+-		}
+-		clientconn := httputil.NewClientConn(dial, nil)
+-		resp, err = clientconn.Do(req)
+-		defer clientconn.Close()
+-	} else {
+-		resp, err = c.HTTPClient.Do(req)
+-	}
+-	if err != nil {
+-		if strings.Contains(err.Error(), "connection refused") {
+-			return ErrConnectionRefused
+-		}
+-		return err
+-	}
+-	defer resp.Body.Close()
+-	if resp.StatusCode < 200 || resp.StatusCode >= 400 {
+-		body, err := ioutil.ReadAll(resp.Body)
+-		if err != nil {
+-			return err
+-		}
+-		return newError(resp.StatusCode, body)
+-	}
+-	if resp.Header.Get("Content-Type") == "application/json" {
+-		// if we want to get raw json stream, just copy it back to output
+-		// without decoding it
+-		if rawJSONStream {
+-			_, err = io.Copy(stdout, resp.Body)
+-			return err
+-		}
+-		dec := json.NewDecoder(resp.Body)
+-		for {
+-			var m jsonMessage
+-			if err := dec.Decode(&m); err == io.EOF {
+-				break
+-			} else if err != nil {
+-				return err
+-			}
+-			if m.Stream != "" {
+-				fmt.Fprint(stdout, m.Stream)
+-			} else if m.Progress != "" {
+-				fmt.Fprintf(stdout, "%s %s\r", m.Status, m.Progress)
+-			} else if m.Error != "" {
+-				return errors.New(m.Error)
+-			}
+-			if m.Status != "" {
+-				fmt.Fprintln(stdout, m.Status)
+-			}
+-		}
+-	} else {
+-		if setRawTerminal {
+-			_, err = io.Copy(stdout, resp.Body)
+-		} else {
+-			_, err = stdCopy(stdout, stderr, resp.Body)
+-		}
+-		return err
+-	}
+-	return nil
+-}
+-
+-func (c *Client) hijack(method, path string, success chan struct{}, setRawTerminal bool, in io.Reader, stderr, stdout io.Writer, data interface{}) error {
+-	if path != "/version" && !c.SkipServerVersionCheck && c.expectedAPIVersion == nil {
+-		err := c.checkAPIVersion()
+-		if err != nil {
+-			return err
+-		}
+-	}
+-
+-	var params io.Reader
+-	if data != nil {
+-		buf, err := json.Marshal(data)
+-		if err != nil {
+-			return err
+-		}
+-		params = bytes.NewBuffer(buf)
+-	}
+-
+-	if stdout == nil {
+-		stdout = ioutil.Discard
+-	}
+-	if stderr == nil {
+-		stderr = ioutil.Discard
+-	}
+-	req, err := http.NewRequest(method, c.getURL(path), params)
+-	if err != nil {
+-		return err
+-	}
+-	req.Header.Set("Content-Type", "plain/text")
+-	protocol := c.endpointURL.Scheme
+-	address := c.endpointURL.Path
+-	if protocol != "unix" {
+-		protocol = "tcp"
+-		address = c.endpointURL.Host
+-	}
+-	dial, err := net.Dial(protocol, address)
+-	if err != nil {
+-		return err
+-	}
+-	defer dial.Close()
+-	clientconn := httputil.NewClientConn(dial, nil)
+-	clientconn.Do(req)
+-	if success != nil {
+-		success <- struct{}{}
+-		<-success
+-	}
+-	rwc, br := clientconn.Hijack()
+-	errs := make(chan error, 2)
+-	exit := make(chan bool)
+-	go func() {
+-		defer close(exit)
+-		var err error
+-		if setRawTerminal {
+-			_, err = io.Copy(stdout, br)
+-		} else {
+-			_, err = stdCopy(stdout, stderr, br)
+-		}
+-		errs <- err
+-	}()
+-	go func() {
+-		var err error
+-		if in != nil {
+-			_, err = io.Copy(rwc, in)
+-		}
+-		rwc.(interface {
+-			CloseWrite() error
+-		}).CloseWrite()
+-		errs <- err
+-	}()
+-	<-exit
+-	return <-errs
+-}
+-
+-func (c *Client) getURL(path string) string {
+-	urlStr := strings.TrimRight(c.endpointURL.String(), "/")
+-	if c.endpointURL.Scheme == "unix" {
+-		urlStr = ""
+-	}
+-
+-	if c.requestedAPIVersion != nil {
+-		return fmt.Sprintf("%s/v%s%s", urlStr, c.requestedAPIVersion, path)
+-	}
+-	return fmt.Sprintf("%s%s", urlStr, path)
+-}
+-
+-type jsonMessage struct {
+-	Status   string `json:"status,omitempty"`
+-	Progress string `json:"progress,omitempty"`
+-	Error    string `json:"error,omitempty"`
+-	Stream   string `json:"stream,omitempty"`
+-}
+-
+-func queryString(opts interface{}) string {
+-	if opts == nil {
+-		return ""
+-	}
+-	value := reflect.ValueOf(opts)
+-	if value.Kind() == reflect.Ptr {
+-		value = value.Elem()
+-	}
+-	if value.Kind() != reflect.Struct {
+-		return ""
+-	}
+-	items := url.Values(map[string][]string{})
+-	for i := 0; i < value.NumField(); i++ {
+-		field := value.Type().Field(i)
+-		if field.PkgPath != "" {
+-			continue
+-		}
+-		key := field.Tag.Get("qs")
+-		if key == "" {
+-			key = strings.ToLower(field.Name)
+-		} else if key == "-" {
+-			continue
+-		}
+-		v := value.Field(i)
+-		switch v.Kind() {
+-		case reflect.Bool:
+-			if v.Bool() {
+-				items.Add(key, "1")
+-			}
+-		case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
+-			if v.Int() > 0 {
+-				items.Add(key, strconv.FormatInt(v.Int(), 10))
+-			}
+-		case reflect.Float32, reflect.Float64:
+-			if v.Float() > 0 {
+-				items.Add(key, strconv.FormatFloat(v.Float(), 'f', -1, 64))
+-			}
+-		case reflect.String:
+-			if v.String() != "" {
+-				items.Add(key, v.String())
+-			}
+-		case reflect.Ptr:
+-			if !v.IsNil() {
+-				if b, err := json.Marshal(v.Interface()); err == nil {
+-					items.Add(key, string(b))
+-				}
+-			}
+-		case reflect.Map:
+-			if len(v.MapKeys()) > 0 {
+-				if b, err := json.Marshal(v.Interface()); err == nil {
+-					items.Add(key, string(b))
+-				}
+-			}
+-		}
+-	}
+-	return items.Encode()
+-}
+-
+-// Error represents failures in the API. It represents a failure from the API.
+-type Error struct {
+-	Status  int
+-	Message string
+-}
+-
+-func newError(status int, body []byte) *Error {
+-	return &Error{Status: status, Message: string(body)}
+-}
+-
+-func (e *Error) Error() string {
+-	return fmt.Sprintf("API error (%d): %s", e.Status, e.Message)
+-}
+-
+-func parseEndpoint(endpoint string) (*url.URL, error) {
+-	u, err := url.Parse(endpoint)
+-	if err != nil {
+-		return nil, ErrInvalidEndpoint
+-	}
+-	if u.Scheme == "tcp" {
+-		_, port, err := net.SplitHostPort(u.Host)
+-		if err != nil {
+-			if e, ok := err.(*net.AddrError); ok {
+-				if e.Err == "missing port in address" {
+-					return u, nil
+-				}
+-			}
+-			return nil, ErrInvalidEndpoint
+-		}
+-
+-		number, err := strconv.ParseInt(port, 10, 64)
+-		if err == nil && number == 2376 {
+-			u.Scheme = "https"
+-		} else {
+-			u.Scheme = "http"
+-		}
+-	}
+-	if u.Scheme != "http" && u.Scheme != "https" && u.Scheme != "unix" {
+-		return nil, ErrInvalidEndpoint
+-	}
+-	if u.Scheme != "unix" {
+-		_, port, err := net.SplitHostPort(u.Host)
+-		if err != nil {
+-			if e, ok := err.(*net.AddrError); ok {
+-				if e.Err == "missing port in address" {
+-					return u, nil
+-				}
+-			}
+-			return nil, ErrInvalidEndpoint
+-		}
+-		number, err := strconv.ParseInt(port, 10, 64)
+-		if err == nil && number > 0 && number < 65536 {
+-			return u, nil
+-		}
+-	} else {
+-		return u, nil // we don't need port when using a unix socket
+-	}
+-	return nil, ErrInvalidEndpoint
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/client_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/client_test.go
+deleted file mode 100644
+index 34543b4..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/client_test.go
++++ /dev/null
+@@ -1,368 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 docker
+-
+-import (
+-	"fmt"
+-	"io/ioutil"
+-	"net/http"
+-	"net/url"
+-	"reflect"
+-	"strconv"
+-	"strings"
+-	"testing"
+-)
+-
+-func TestNewAPIClient(t *testing.T) {
+-	endpoint := "http://localhost:4243"
+-	client, err := NewClient(endpoint)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if client.endpoint != endpoint {
+-		t.Errorf("Expected endpoint %s. Got %s.", endpoint, client.endpoint)
+-	}
+-	if client.HTTPClient != http.DefaultClient {
+-		t.Errorf("Expected http.Client %#v. Got %#v.", http.DefaultClient, client.HTTPClient)
+-	}
+-	// test unix socket endpoints
+-	endpoint = "unix:///var/run/docker.sock"
+-	client, err = NewClient(endpoint)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if client.endpoint != endpoint {
+-		t.Errorf("Expected endpoint %s. Got %s.", endpoint, client.endpoint)
+-	}
+-	if !client.SkipServerVersionCheck {
+-		t.Error("Expected SkipServerVersionCheck to be true, got false")
+-	}
+-	if client.requestedAPIVersion != nil {
+-		t.Errorf("Expected requestedAPIVersion to be nil, got %#v.", client.requestedAPIVersion)
+-	}
+-}
+-
+-func newTLSClient(endpoint string) (*Client, error) {
+-	return NewTLSClient(endpoint,
+-		"testing/data/cert.pem",
+-		"testing/data/key.pem",
+-		"testing/data/ca.pem")
+-}
+-
+-func TestNewTSLAPIClient(t *testing.T) {
+-	endpoint := "https://localhost:4243"
+-	client, err := newTLSClient(endpoint)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if client.endpoint != endpoint {
+-		t.Errorf("Expected endpoint %s. Got %s.", endpoint, client.endpoint)
+-	}
+-	if !client.SkipServerVersionCheck {
+-		t.Error("Expected SkipServerVersionCheck to be true, got false")
+-	}
+-	if client.requestedAPIVersion != nil {
+-		t.Errorf("Expected requestedAPIVersion to be nil, got %#v.", client.requestedAPIVersion)
+-	}
+-}
+-
+-func TestNewVersionedClient(t *testing.T) {
+-	endpoint := "http://localhost:4243"
+-	client, err := NewVersionedClient(endpoint, "1.12")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if client.endpoint != endpoint {
+-		t.Errorf("Expected endpoint %s. Got %s.", endpoint, client.endpoint)
+-	}
+-	if client.HTTPClient != http.DefaultClient {
+-		t.Errorf("Expected http.Client %#v. Got %#v.", http.DefaultClient, client.HTTPClient)
+-	}
+-	if reqVersion := client.requestedAPIVersion.String(); reqVersion != "1.12" {
+-		t.Errorf("Wrong requestAPIVersion. Want %q. Got %q.", "1.12", reqVersion)
+-	}
+-	if client.SkipServerVersionCheck {
+-		t.Error("Expected SkipServerVersionCheck to be false, got true")
+-	}
+-}
+-
+-func TestNewTLSVersionedClient(t *testing.T) {
+-	certPath := "testing/data/cert.pem"
+-	keyPath := "testing/data/key.pem"
+-	caPath := "testing/data/ca.pem"
+-	endpoint := "https://localhost:4243"
+-	client, err := NewVersionnedTLSClient(endpoint, certPath, keyPath, caPath, "1.14")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if client.endpoint != endpoint {
+-		t.Errorf("Expected endpoint %s. Got %s.", endpoint, client.endpoint)
+-	}
+-	if reqVersion := client.requestedAPIVersion.String(); reqVersion != "1.14" {
+-		t.Errorf("Wrong requestAPIVersion. Want %q. Got %q.", "1.14", reqVersion)
+-	}
+-	if client.SkipServerVersionCheck {
+-		t.Error("Expected SkipServerVersionCheck to be false, got true")
+-	}
+-}
+-
+-func TestNewTLSVersionedClientInvalidCA(t *testing.T) {
+-	certPath := "testing/data/cert.pem"
+-	keyPath := "testing/data/key.pem"
+-	caPath := "testing/data/key.pem"
+-	endpoint := "https://localhost:4243"
+-	_, err := NewVersionnedTLSClient(endpoint, certPath, keyPath, caPath, "1.14")
+-	if err == nil {
+-		t.Errorf("Expected invalid ca at %s", caPath)
+-	}
+-}
+-
+-func TestNewClientInvalidEndpoint(t *testing.T) {
+-	cases := []string{
+-		"htp://localhost:3243", "http://localhost:a", "localhost:8080",
+-		"", "localhost", "http://localhost:8080:8383", "http://localhost:65536",
+-		"https://localhost:-20",
+-	}
+-	for _, c := range cases {
+-		client, err := NewClient(c)
+-		if client != nil {
+-			t.Errorf("Want <nil> client for invalid endpoint, got %#v.", client)
+-		}
+-		if !reflect.DeepEqual(err, ErrInvalidEndpoint) {
+-			t.Errorf("NewClient(%q): Got invalid error for invalid endpoint. Want %#v. Got %#v.", c, ErrInvalidEndpoint, err)
+-		}
+-	}
+-}
+-
+-func TestNewTLSClient2376(t *testing.T) {
+-	var tests = []struct {
+-		endpoint string
+-		expected string
+-	}{
+-		{"tcp://localhost:2376", "https"},
+-		{"tcp://localhost:2375", "http"},
+-		{"tcp://localhost:4000", "http"},
+-	}
+-
+-	for _, tt := range tests {
+-		client, err := newTLSClient(tt.endpoint)
+-		if err != nil {
+-			t.Error(err)
+-		}
+-		got := client.endpointURL.Scheme
+-		if got != tt.expected {
+-			t.Errorf("endpointURL.Scheme: Got %s. Want %s.", got, tt.expected)
+-		}
+-	}
+-}
+-
+-func TestGetURL(t *testing.T) {
+-	var tests = []struct {
+-		endpoint string
+-		path     string
+-		expected string
+-	}{
+-		{"http://localhost:4243/", "/", "http://localhost:4243/"},
+-		{"http://localhost:4243", "/", "http://localhost:4243/"},
+-		{"http://localhost:4243", "/containers/ps", "http://localhost:4243/containers/ps"},
+-		{"tcp://localhost:4243", "/containers/ps", "http://localhost:4243/containers/ps"},
+-		{"http://localhost:4243/////", "/", "http://localhost:4243/"},
+-		{"unix:///var/run/docker.socket", "/containers", "/containers"},
+-	}
+-	for _, tt := range tests {
+-		client, _ := NewClient(tt.endpoint)
+-		client.endpoint = tt.endpoint
+-		client.SkipServerVersionCheck = true
+-		got := client.getURL(tt.path)
+-		if got != tt.expected {
+-			t.Errorf("getURL(%q): Got %s. Want %s.", tt.path, got, tt.expected)
+-		}
+-	}
+-}
+-
+-func TestError(t *testing.T) {
+-	err := newError(400, []byte("bad parameter"))
+-	expected := Error{Status: 400, Message: "bad parameter"}
+-	if !reflect.DeepEqual(expected, *err) {
+-		t.Errorf("Wrong error type. Want %#v. Got %#v.", expected, *err)
+-	}
+-	message := "API error (400): bad parameter"
+-	if err.Error() != message {
+-		t.Errorf("Wrong error message. Want %q. Got %q.", message, err.Error())
+-	}
+-}
+-
+-func TestQueryString(t *testing.T) {
+-	v := float32(2.4)
+-	f32QueryString := fmt.Sprintf("w=%s&x=10&y=10.35", strconv.FormatFloat(float64(v), 'f', -1, 64))
+-	jsonPerson := url.QueryEscape(`{"Name":"gopher","age":4}`)
+-	var tests = []struct {
+-		input interface{}
+-		want  string
+-	}{
+-		{&ListContainersOptions{All: true}, "all=1"},
+-		{ListContainersOptions{All: true}, "all=1"},
+-		{ListContainersOptions{Before: "something"}, "before=something"},
+-		{ListContainersOptions{Before: "something", Since: "other"}, "before=something&since=other"},
+-		{ListContainersOptions{Filters: map[string][]string{"status": {"paused", "running"}}}, "filters=%7B%22status%22%3A%5B%22paused%22%2C%22running%22%5D%7D"},
+-		{dumb{X: 10, Y: 10.35000}, "x=10&y=10.35"},
+-		{dumb{W: v, X: 10, Y: 10.35000}, f32QueryString},
+-		{dumb{X: 10, Y: 10.35000, Z: 10}, "x=10&y=10.35&zee=10"},
+-		{dumb{v: 4, X: 10, Y: 10.35000}, "x=10&y=10.35"},
+-		{dumb{T: 10, Y: 10.35000}, "y=10.35"},
+-		{dumb{Person: &person{Name: "gopher", Age: 4}}, "p=" + jsonPerson},
+-		{nil, ""},
+-		{10, ""},
+-		{"not_a_struct", ""},
+-	}
+-	for _, tt := range tests {
+-		got := queryString(tt.input)
+-		if got != tt.want {
+-			t.Errorf("queryString(%v). Want %q. Got %q.", tt.input, tt.want, got)
+-		}
+-	}
+-}
+-
+-func TestNewAPIVersionFailures(t *testing.T) {
+-	var tests = []struct {
+-		input         string
+-		expectedError string
+-	}{
+-		{"1-0", `Unable to parse version "1-0"`},
+-		{"1.0-beta", `Unable to parse version "1.0-beta": "0-beta" is not an integer`},
+-	}
+-	for _, tt := range tests {
+-		v, err := NewAPIVersion(tt.input)
+-		if v != nil {
+-			t.Errorf("Expected <nil> version, got %v.", v)
+-		}
+-		if err.Error() != tt.expectedError {
+-			t.Errorf("NewAPIVersion(%q): wrong error. Want %q. Got %q", tt.input, tt.expectedError, err.Error())
+-		}
+-	}
+-}
+-
+-func TestAPIVersions(t *testing.T) {
+-	var tests = []struct {
+-		a                              string
+-		b                              string
+-		expectedALessThanB             bool
+-		expectedALessThanOrEqualToB    bool
+-		expectedAGreaterThanB          bool
+-		expectedAGreaterThanOrEqualToB bool
+-	}{
+-		{"1.11", "1.11", false, true, false, true},
+-		{"1.10", "1.11", true, true, false, false},
+-		{"1.11", "1.10", false, false, true, true},
+-
+-		{"1.9", "1.11", true, true, false, false},
+-		{"1.11", "1.9", false, false, true, true},
+-
+-		{"1.1.1", "1.1", false, false, true, true},
+-		{"1.1", "1.1.1", true, true, false, false},
+-
+-		{"2.1", "1.1.1", false, false, true, true},
+-		{"2.1", "1.3.1", false, false, true, true},
+-		{"1.1.1", "2.1", true, true, false, false},
+-		{"1.3.1", "2.1", true, true, false, false},
+-	}
+-
+-	for _, tt := range tests {
+-		a, _ := NewAPIVersion(tt.a)
+-		b, _ := NewAPIVersion(tt.b)
+-
+-		if tt.expectedALessThanB && !a.LessThan(b) {
+-			t.Errorf("Expected %#v < %#v", a, b)
+-		}
+-		if tt.expectedALessThanOrEqualToB && !a.LessThanOrEqualTo(b) {
+-			t.Errorf("Expected %#v <= %#v", a, b)
+-		}
+-		if tt.expectedAGreaterThanB && !a.GreaterThan(b) {
+-			t.Errorf("Expected %#v > %#v", a, b)
+-		}
+-		if tt.expectedAGreaterThanOrEqualToB && !a.GreaterThanOrEqualTo(b) {
+-			t.Errorf("Expected %#v >= %#v", a, b)
+-		}
+-	}
+-}
+-
+-func TestPing(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	err := client.Ping()
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-}
+-
+-func TestPingFailing(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusInternalServerError}
+-	client := newTestClient(fakeRT)
+-	err := client.Ping()
+-	if err == nil {
+-		t.Fatal("Expected non nil error, got nil")
+-	}
+-	expectedErrMsg := "API error (500): "
+-	if err.Error() != expectedErrMsg {
+-		t.Fatalf("Expected error to be %q, got: %q", expectedErrMsg, err.Error())
+-	}
+-}
+-
+-func TestPingFailingWrongStatus(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusAccepted}
+-	client := newTestClient(fakeRT)
+-	err := client.Ping()
+-	if err == nil {
+-		t.Fatal("Expected non nil error, got nil")
+-	}
+-	expectedErrMsg := "API error (202): "
+-	if err.Error() != expectedErrMsg {
+-		t.Fatalf("Expected error to be %q, got: %q", expectedErrMsg, err.Error())
+-	}
+-}
+-
+-type FakeRoundTripper struct {
+-	message  string
+-	status   int
+-	header   map[string]string
+-	requests []*http.Request
+-}
+-
+-func (rt *FakeRoundTripper) RoundTrip(r *http.Request) (*http.Response, error) {
+-	body := strings.NewReader(rt.message)
+-	rt.requests = append(rt.requests, r)
+-	res := &http.Response{
+-		StatusCode: rt.status,
+-		Body:       ioutil.NopCloser(body),
+-		Header:     make(http.Header),
+-	}
+-	for k, v := range rt.header {
+-		res.Header.Set(k, v)
+-	}
+-	return res, nil
+-}
+-
+-func (rt *FakeRoundTripper) Reset() {
+-	rt.requests = nil
+-}
+-
+-type person struct {
+-	Name string
+-	Age  int `json:"age"`
+-}
+-
+-type dumb struct {
+-	T      int `qs:"-"`
+-	v      int
+-	W      float32
+-	X      int
+-	Y      float64
+-	Z      int     `qs:"zee"`
+-	Person *person `qs:"p"`
+-}
+-
+-type fakeEndpointURL struct {
+-	Scheme string
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/container.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/container.go
+deleted file mode 100644
+index c600c84..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/container.go
++++ /dev/null
+@@ -1,760 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 docker
+-
+-import (
+-	"bytes"
+-	"encoding/json"
+-	"fmt"
+-	"io"
+-	"net/http"
+-	"net/url"
+-	"strconv"
+-	"strings"
+-	"time"
+-)
+-
+-// ListContainersOptions specify parameters to the ListContainers function.
+-//
+-// See http://goo.gl/6Y4Gz7 for more details.
+-type ListContainersOptions struct {
+-	All     bool
+-	Size    bool
+-	Limit   int
+-	Since   string
+-	Before  string
+-	Filters map[string][]string
+-}
+-
+-// APIPort is a type that represents a port mapping returned by the Docker API
+-type APIPort struct {
+-	PrivatePort int64  `json:"PrivatePort,omitempty" yaml:"PrivatePort,omitempty"`
+-	PublicPort  int64  `json:"PublicPort,omitempty" yaml:"PublicPort,omitempty"`
+-	Type        string `json:"Type,omitempty" yaml:"Type,omitempty"`
+-	IP          string `json:"IP,omitempty" yaml:"IP,omitempty"`
+-}
+-
+-// APIContainers represents a container.
+-//
+-// See http://goo.gl/QeFH7U for more details.
+-type APIContainers struct {
+-	ID         string    `json:"Id" yaml:"Id"`
+-	Image      string    `json:"Image,omitempty" yaml:"Image,omitempty"`
+-	Command    string    `json:"Command,omitempty" yaml:"Command,omitempty"`
+-	Created    int64     `json:"Created,omitempty" yaml:"Created,omitempty"`
+-	Status     string    `json:"Status,omitempty" yaml:"Status,omitempty"`
+-	Ports      []APIPort `json:"Ports,omitempty" yaml:"Ports,omitempty"`
+-	SizeRw     int64     `json:"SizeRw,omitempty" yaml:"SizeRw,omitempty"`
+-	SizeRootFs int64     `json:"SizeRootFs,omitempty" yaml:"SizeRootFs,omitempty"`
+-	Names      []string  `json:"Names,omitempty" yaml:"Names,omitempty"`
+-}
+-
+-// ListContainers returns a slice of containers matching the given criteria.
+-//
+-// See http://goo.gl/6Y4Gz7 for more details.
+-func (c *Client) ListContainers(opts ListContainersOptions) ([]APIContainers, error) {
+-	path := "/containers/json?" + queryString(opts)
+-	body, _, err := c.do("GET", path, nil)
+-	if err != nil {
+-		return nil, err
+-	}
+-	var containers []APIContainers
+-	err = json.Unmarshal(body, &containers)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return containers, nil
+-}
+-
+-// Port represents the port number and the protocol, in the form
+-// <number>/<protocol>. For example: 80/tcp.
+-type Port string
+-
+-// Port returns the number of the port.
+-func (p Port) Port() string {
+-	return strings.Split(string(p), "/")[0]
+-}
+-
+-// Proto returns the name of the protocol.
+-func (p Port) Proto() string {
+-	parts := strings.Split(string(p), "/")
+-	if len(parts) == 1 {
+-		return "tcp"
+-	}
+-	return parts[1]
+-}
+-
+-// State represents the state of a container.
+-type State struct {
+-	Running    bool      `json:"Running,omitempty" yaml:"Running,omitempty"`
+-	Paused     bool      `json:"Paused,omitempty" yaml:"Paused,omitempty"`
+-	OOMKilled  bool      `json:"OOMKilled,omitempty" yaml:"OOMKilled,omitempty"`
+-	Pid        int       `json:"Pid,omitempty" yaml:"Pid,omitempty"`
+-	ExitCode   int       `json:"ExitCode,omitempty" yaml:"ExitCode,omitempty"`
+-	Error      string    `json:"Error,omitempty" yaml:"Error,omitempty"`
+-	StartedAt  time.Time `json:"StartedAt,omitempty" yaml:"StartedAt,omitempty"`
+-	FinishedAt time.Time `json:"FinishedAt,omitempty" yaml:"FinishedAt,omitempty"`
+-}
+-
+-// String returns the string representation of a state.
+-func (s *State) String() string {
+-	if s.Running {
+-		if s.Paused {
+-			return "paused"
+-		}
+-		return fmt.Sprintf("Up %s", time.Now().UTC().Sub(s.StartedAt))
+-	}
+-	return fmt.Sprintf("Exit %d", s.ExitCode)
+-}
+-
+-// PortBinding represents the host/container port mapping as returned in the
+-// `docker inspect` json
+-type PortBinding struct {
+-	HostIP   string `json:"HostIP,omitempty" yaml:"HostIP,omitempty"`
+-	HostPort string `json:"HostPort,omitempty" yaml:"HostPort,omitempty"`
+-}
+-
+-// PortMapping represents a deprecated field in the `docker inspect` output,
+-// and its value as found in NetworkSettings should always be nil
+-type PortMapping map[string]string
+-
+-// NetworkSettings contains network-related information about a container
+-type NetworkSettings struct {
+-	IPAddress   string                 `json:"IPAddress,omitempty" yaml:"IPAddress,omitempty"`
+-	IPPrefixLen int                    `json:"IPPrefixLen,omitempty" yaml:"IPPrefixLen,omitempty"`
+-	Gateway     string                 `json:"Gateway,omitempty" yaml:"Gateway,omitempty"`
+-	Bridge      string                 `json:"Bridge,omitempty" yaml:"Bridge,omitempty"`
+-	PortMapping map[string]PortMapping `json:"PortMapping,omitempty" yaml:"PortMapping,omitempty"`
+-	Ports       map[Port][]PortBinding `json:"Ports,omitempty" yaml:"Ports,omitempty"`
+-}
+-
+-// PortMappingAPI translates the port mappings as contained in NetworkSettings
+-// into the format in which they would appear when returned by the API
+-func (settings *NetworkSettings) PortMappingAPI() []APIPort {
+-	var mapping []APIPort
+-	for port, bindings := range settings.Ports {
+-		p, _ := parsePort(port.Port())
+-		if len(bindings) == 0 {
+-			mapping = append(mapping, APIPort{
+-				PublicPort: int64(p),
+-				Type:       port.Proto(),
+-			})
+-			continue
+-		}
+-		for _, binding := range bindings {
+-			p, _ := parsePort(port.Port())
+-			h, _ := parsePort(binding.HostPort)
+-			mapping = append(mapping, APIPort{
+-				PrivatePort: int64(p),
+-				PublicPort:  int64(h),
+-				Type:        port.Proto(),
+-				IP:          binding.HostIP,
+-			})
+-		}
+-	}
+-	return mapping
+-}
+-
+-func parsePort(rawPort string) (int, error) {
+-	port, err := strconv.ParseUint(rawPort, 10, 16)
+-	if err != nil {
+-		return 0, err
+-	}
+-	return int(port), nil
+-}
+-
+-// Config is the list of configuration options used when creating a container.
+-// Config does not the options that are specific to starting a container on a
+-// given host.  Those are contained in HostConfig
+-type Config struct {
+-	Hostname        string              `json:"Hostname,omitempty" yaml:"Hostname,omitempty"`
+-	Domainname      string              `json:"Domainname,omitempty" yaml:"Domainname,omitempty"`
+-	User            string              `json:"User,omitempty" yaml:"User,omitempty"`
+-	Memory          int64               `json:"Memory,omitempty" yaml:"Memory,omitempty"`
+-	MemorySwap      int64               `json:"MemorySwap,omitempty" yaml:"MemorySwap,omitempty"`
+-	CPUShares       int64               `json:"CpuShares,omitempty" yaml:"CpuShares,omitempty"`
+-	CPUSet          string              `json:"Cpuset,omitempty" yaml:"Cpuset,omitempty"`
+-	AttachStdin     bool                `json:"AttachStdin,omitempty" yaml:"AttachStdin,omitempty"`
+-	AttachStdout    bool                `json:"AttachStdout,omitempty" yaml:"AttachStdout,omitempty"`
+-	AttachStderr    bool                `json:"AttachStderr,omitempty" yaml:"AttachStderr,omitempty"`
+-	PortSpecs       []string            `json:"PortSpecs,omitempty" yaml:"PortSpecs,omitempty"`
+-	ExposedPorts    map[Port]struct{}   `json:"ExposedPorts,omitempty" yaml:"ExposedPorts,omitempty"`
+-	Tty             bool                `json:"Tty,omitempty" yaml:"Tty,omitempty"`
+-	OpenStdin       bool                `json:"OpenStdin,omitempty" yaml:"OpenStdin,omitempty"`
+-	StdinOnce       bool                `json:"StdinOnce,omitempty" yaml:"StdinOnce,omitempty"`
+-	Env             []string            `json:"Env,omitempty" yaml:"Env,omitempty"`
+-	Cmd             []string            `json:"Cmd,omitempty" yaml:"Cmd,omitempty"`
+-	DNS             []string            `json:"Dns,omitempty" yaml:"Dns,omitempty"` // For Docker API v1.9 and below only
+-	Image           string              `json:"Image,omitempty" yaml:"Image,omitempty"`
+-	Volumes         map[string]struct{} `json:"Volumes,omitempty" yaml:"Volumes,omitempty"`
+-	VolumesFrom     string              `json:"VolumesFrom,omitempty" yaml:"VolumesFrom,omitempty"`
+-	WorkingDir      string              `json:"WorkingDir,omitempty" yaml:"WorkingDir,omitempty"`
+-	Entrypoint      []string            `json:"Entrypoint,omitempty" yaml:"Entrypoint,omitempty"`
+-	NetworkDisabled bool                `json:"NetworkDisabled,omitempty" yaml:"NetworkDisabled,omitempty"`
+-}
+-
+-// Container is the type encompasing everything about a container - its config,
+-// hostconfig, etc.
+-type Container struct {
+-	ID string `json:"Id" yaml:"Id"`
+-
+-	Created time.Time `json:"Created,omitempty" yaml:"Created,omitempty"`
+-
+-	Path string   `json:"Path,omitempty" yaml:"Path,omitempty"`
+-	Args []string `json:"Args,omitempty" yaml:"Args,omitempty"`
+-
+-	Config *Config `json:"Config,omitempty" yaml:"Config,omitempty"`
+-	State  State   `json:"State,omitempty" yaml:"State,omitempty"`
+-	Image  string  `json:"Image,omitempty" yaml:"Image,omitempty"`
+-
+-	NetworkSettings *NetworkSettings `json:"NetworkSettings,omitempty" yaml:"NetworkSettings,omitempty"`
+-
+-	SysInitPath    string `json:"SysInitPath,omitempty" yaml:"SysInitPath,omitempty"`
+-	ResolvConfPath string `json:"ResolvConfPath,omitempty" yaml:"ResolvConfPath,omitempty"`
+-	HostnamePath   string `json:"HostnamePath,omitempty" yaml:"HostnamePath,omitempty"`
+-	HostsPath      string `json:"HostsPath,omitempty" yaml:"HostsPath,omitempty"`
+-	Name           string `json:"Name,omitempty" yaml:"Name,omitempty"`
+-	Driver         string `json:"Driver,omitempty" yaml:"Driver,omitempty"`
+-
+-	Volumes    map[string]string `json:"Volumes,omitempty" yaml:"Volumes,omitempty"`
+-	VolumesRW  map[string]bool   `json:"VolumesRW,omitempty" yaml:"VolumesRW,omitempty"`
+-	HostConfig *HostConfig       `json:"HostConfig,omitempty" yaml:"HostConfig,omitempty"`
+-}
+-
+-// InspectContainer returns information about a container by its ID.
+-//
+-// See http://goo.gl/CxVuJ5 for more details.
+-func (c *Client) InspectContainer(id string) (*Container, error) {
+-	path := "/containers/" + id + "/json"
+-	body, status, err := c.do("GET", path, nil)
+-	if status == http.StatusNotFound {
+-		return nil, &NoSuchContainer{ID: id}
+-	}
+-	if err != nil {
+-		return nil, err
+-	}
+-	var container Container
+-	err = json.Unmarshal(body, &container)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return &container, nil
+-}
+-
+-// ContainerChanges returns changes in the filesystem of the given container.
+-//
+-// See http://goo.gl/QkW9sH for more details.
+-func (c *Client) ContainerChanges(id string) ([]Change, error) {
+-	path := "/containers/" + id + "/changes"
+-	body, status, err := c.do("GET", path, nil)
+-	if status == http.StatusNotFound {
+-		return nil, &NoSuchContainer{ID: id}
+-	}
+-	if err != nil {
+-		return nil, err
+-	}
+-	var changes []Change
+-	err = json.Unmarshal(body, &changes)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return changes, nil
+-}
+-
+-// CreateContainerOptions specify parameters to the CreateContainer function.
+-//
+-// See http://goo.gl/2xxQQK for more details.
+-type CreateContainerOptions struct {
+-	Name       string
+-	Config     *Config `qs:"-"`
+-	HostConfig *HostConfig
+-}
+-
+-// CreateContainer creates a new container, returning the container instance,
+-// or an error in case of failure.
+-//
+-// See http://goo.gl/mErxNp for more details.
+-func (c *Client) CreateContainer(opts CreateContainerOptions) (*Container, error) {
+-	path := "/containers/create?" + queryString(opts)
+-	body, status, err := c.do("POST", path, struct {
+-		*Config
+-		HostConfig *HostConfig `json:"HostConfig,omitempty" yaml:"HostConfig,omitempty"`
+-	}{
+-		opts.Config,
+-		opts.HostConfig,
+-	})
+-
+-	if status == http.StatusNotFound {
+-		return nil, ErrNoSuchImage
+-	}
+-	if err != nil {
+-		return nil, err
+-	}
+-	var container Container
+-	err = json.Unmarshal(body, &container)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	container.Name = opts.Name
+-
+-	return &container, nil
+-}
+-
+-// KeyValuePair is a type for generic key/value pairs as used in the Lxc
+-// configuration
+-type KeyValuePair struct {
+-	Key   string `json:"Key,omitempty" yaml:"Key,omitempty"`
+-	Value string `json:"Value,omitempty" yaml:"Value,omitempty"`
+-}
+-
+-// RestartPolicy represents the policy for automatically restarting a container.
+-//
+-// Possible values are:
+-//
+-//   - always: the docker daemon will always restart the container
+-//   - on-failure: the docker daemon will restart the container on failures, at
+-//                 most MaximumRetryCount times
+-//   - no: the docker daemon will not restart the container automatically
+-type RestartPolicy struct {
+-	Name              string `json:"Name,omitempty" yaml:"Name,omitempty"`
+-	MaximumRetryCount int    `json:"MaximumRetryCount,omitempty" yaml:"MaximumRetryCount,omitempty"`
+-}
+-
+-// AlwaysRestart returns a restart policy that tells the Docker daemon to
+-// always restart the container.
+-func AlwaysRestart() RestartPolicy {
+-	return RestartPolicy{Name: "always"}
+-}
+-
+-// RestartOnFailure returns a restart policy that tells the Docker daemon to
+-// restart the container on failures, trying at most maxRetry times.
+-func RestartOnFailure(maxRetry int) RestartPolicy {
+-	return RestartPolicy{Name: "on-failure", MaximumRetryCount: maxRetry}
+-}
+-
+-// NeverRestart returns a restart policy that tells the Docker daemon to never
+-// restart the container on failures.
+-func NeverRestart() RestartPolicy {
+-	return RestartPolicy{Name: "no"}
+-}
+-
+-// HostConfig contains the container options related to starting a container on
+-// a given host
+-type HostConfig struct {
+-	Binds           []string               `json:"Binds,omitempty" yaml:"Binds,omitempty"`
+-	CapAdd          []string               `json:"CapAdd,omitempty" yaml:"CapAdd,omitempty"`
+-	CapDrop         []string               `json:"CapDrop,omitempty" yaml:"CapDrop,omitempty"`
+-	ContainerIDFile string                 `json:"ContainerIDFile,omitempty" yaml:"ContainerIDFile,omitempty"`
+-	LxcConf         []KeyValuePair         `json:"LxcConf,omitempty" yaml:"LxcConf,omitempty"`
+-	Privileged      bool                   `json:"Privileged,omitempty" yaml:"Privileged,omitempty"`
+-	PortBindings    map[Port][]PortBinding `json:"PortBindings,omitempty" yaml:"PortBindings,omitempty"`
+-	Links           []string               `json:"Links,omitempty" yaml:"Links,omitempty"`
+-	PublishAllPorts bool                   `json:"PublishAllPorts,omitempty" yaml:"PublishAllPorts,omitempty"`
+-	DNS             []string               `json:"Dns,omitempty" yaml:"Dns,omitempty"` // For Docker API v1.10 and above only
+-	DNSSearch       []string               `json:"DnsSearch,omitempty" yaml:"DnsSearch,omitempty"`
+-	ExtraHosts      []string               `json:"ExtraHosts,omitempty" yaml:"ExtraHosts,omitempty"`
+-	VolumesFrom     []string               `json:"VolumesFrom,omitempty" yaml:"VolumesFrom,omitempty"`
+-	NetworkMode     string                 `json:"NetworkMode,omitempty" yaml:"NetworkMode,omitempty"`
+-	RestartPolicy   RestartPolicy          `json:"RestartPolicy,omitempty" yaml:"RestartPolicy,omitempty"`
+-}
+-
+-// StartContainer starts a container, returning an error in case of failure.
+-//
+-// See http://goo.gl/iM5GYs for more details.
+-func (c *Client) StartContainer(id string, hostConfig *HostConfig) error {
+-	if hostConfig == nil {
+-		hostConfig = &HostConfig{}
+-	}
+-	path := "/containers/" + id + "/start"
+-	_, status, err := c.do("POST", path, hostConfig)
+-	if status == http.StatusNotFound {
+-		return &NoSuchContainer{ID: id}
+-	}
+-	if status == http.StatusNotModified {
+-		return &ContainerAlreadyRunning{ID: id}
+-	}
+-	if err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-// StopContainer stops a container, killing it after the given timeout (in
+-// seconds).
+-//
+-// See http://goo.gl/EbcpXt for more details.
+-func (c *Client) StopContainer(id string, timeout uint) error {
+-	path := fmt.Sprintf("/containers/%s/stop?t=%d", id, timeout)
+-	_, status, err := c.do("POST", path, nil)
+-	if status == http.StatusNotFound {
+-		return &NoSuchContainer{ID: id}
+-	}
+-	if status == http.StatusNotModified {
+-		return &ContainerNotRunning{ID: id}
+-	}
+-	if err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-// RestartContainer stops a container, killing it after the given timeout (in
+-// seconds), during the stop process.
+-//
+-// See http://goo.gl/VOzR2n for more details.
+-func (c *Client) RestartContainer(id string, timeout uint) error {
+-	path := fmt.Sprintf("/containers/%s/restart?t=%d", id, timeout)
+-	_, status, err := c.do("POST", path, nil)
+-	if status == http.StatusNotFound {
+-		return &NoSuchContainer{ID: id}
+-	}
+-	if err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-// PauseContainer pauses the given container.
+-//
+-// See http://goo.gl/AM5t42 for more details.
+-func (c *Client) PauseContainer(id string) error {
+-	path := fmt.Sprintf("/containers/%s/pause", id)
+-	_, status, err := c.do("POST", path, nil)
+-	if status == http.StatusNotFound {
+-		return &NoSuchContainer{ID: id}
+-	}
+-	if err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-// UnpauseContainer pauses the given container.
+-//
+-// See http://goo.gl/eBrNSL for more details.
+-func (c *Client) UnpauseContainer(id string) error {
+-	path := fmt.Sprintf("/containers/%s/unpause", id)
+-	_, status, err := c.do("POST", path, nil)
+-	if status == http.StatusNotFound {
+-		return &NoSuchContainer{ID: id}
+-	}
+-	if err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-// TopResult represents the list of processes running in a container, as
+-// returned by /containers/<id>/top.
+-//
+-// See http://goo.gl/qu4gse for more details.
+-type TopResult struct {
+-	Titles    []string
+-	Processes [][]string
+-}
+-
+-// TopContainer returns processes running inside a container
+-//
+-// See http://goo.gl/qu4gse for more details.
+-func (c *Client) TopContainer(id string, psArgs string) (TopResult, error) {
+-	var args string
+-	var result TopResult
+-	if psArgs != "" {
+-		args = fmt.Sprintf("?ps_args=%s", psArgs)
+-	}
+-	path := fmt.Sprintf("/containers/%s/top%s", id, args)
+-	body, status, err := c.do("GET", path, nil)
+-	if status == http.StatusNotFound {
+-		return result, &NoSuchContainer{ID: id}
+-	}
+-	if err != nil {
+-		return result, err
+-	}
+-	err = json.Unmarshal(body, &result)
+-	if err != nil {
+-		return result, err
+-	}
+-	return result, nil
+-}
+-
+-// KillContainerOptions represents the set of options that can be used in a
+-// call to KillContainer.
+-//
+-// See http://goo.gl/TFkECx for more details.
+-type KillContainerOptions struct {
+-	// The ID of the container.
+-	ID string `qs:"-"`
+-
+-	// The signal to send to the container. When omitted, Docker server
+-	// will assume SIGKILL.
+-	Signal Signal
+-}
+-
+-// KillContainer kills a container, returning an error in case of failure.
+-//
+-// See http://goo.gl/TFkECx for more details.
+-func (c *Client) KillContainer(opts KillContainerOptions) error {
+-	path := "/containers/" + opts.ID + "/kill" + "?" + queryString(opts)
+-	_, status, err := c.do("POST", path, nil)
+-	if status == http.StatusNotFound {
+-		return &NoSuchContainer{ID: opts.ID}
+-	}
+-	if err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-// RemoveContainerOptions encapsulates options to remove a container.
+-//
+-// See http://goo.gl/ZB83ji for more details.
+-type RemoveContainerOptions struct {
+-	// The ID of the container.
+-	ID string `qs:"-"`
+-
+-	// A flag that indicates whether Docker should remove the volumes
+-	// associated to the container.
+-	RemoveVolumes bool `qs:"v"`
+-
+-	// A flag that indicates whether Docker should remove the container
+-	// even if it is currently running.
+-	Force bool
+-}
+-
+-// RemoveContainer removes a container, returning an error in case of failure.
+-//
+-// See http://goo.gl/ZB83ji for more details.
+-func (c *Client) RemoveContainer(opts RemoveContainerOptions) error {
+-	path := "/containers/" + opts.ID + "?" + queryString(opts)
+-	_, status, err := c.do("DELETE", path, nil)
+-	if status == http.StatusNotFound {
+-		return &NoSuchContainer{ID: opts.ID}
+-	}
+-	if err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-// CopyFromContainerOptions is the set of options that can be used when copying
+-// files or folders from a container.
+-//
+-// See http://goo.gl/rINMlw for more details.
+-type CopyFromContainerOptions struct {
+-	OutputStream io.Writer `json:"-"`
+-	Container    string    `json:"-"`
+-	Resource     string
+-}
+-
+-// CopyFromContainer copy files or folders from a container, using a given
+-// resource.
+-//
+-// See http://goo.gl/rINMlw for more details.
+-func (c *Client) CopyFromContainer(opts CopyFromContainerOptions) error {
+-	if opts.Container == "" {
+-		return &NoSuchContainer{ID: opts.Container}
+-	}
+-	url := fmt.Sprintf("/containers/%s/copy", opts.Container)
+-	body, status, err := c.do("POST", url, opts)
+-	if status == http.StatusNotFound {
+-		return &NoSuchContainer{ID: opts.Container}
+-	}
+-	if err != nil {
+-		return err
+-	}
+-	io.Copy(opts.OutputStream, bytes.NewBuffer(body))
+-	return nil
+-}
+-
+-// WaitContainer blocks until the given container stops, return the exit code
+-// of the container status.
+-//
+-// See http://goo.gl/J88DHU for more details.
+-func (c *Client) WaitContainer(id string) (int, error) {
+-	body, status, err := c.do("POST", "/containers/"+id+"/wait", nil)
+-	if status == http.StatusNotFound {
+-		return 0, &NoSuchContainer{ID: id}
+-	}
+-	if err != nil {
+-		return 0, err
+-	}
+-	var r struct{ StatusCode int }
+-	err = json.Unmarshal(body, &r)
+-	if err != nil {
+-		return 0, err
+-	}
+-	return r.StatusCode, nil
+-}
+-
+-// CommitContainerOptions aggregates parameters to the CommitContainer method.
+-//
+-// See http://goo.gl/Jn8pe8 for more details.
+-type CommitContainerOptions struct {
+-	Container  string
+-	Repository string `qs:"repo"`
+-	Tag        string
+-	Message    string `qs:"m"`
+-	Author     string
+-	Run        *Config `qs:"-"`
+-}
+-
+-// CommitContainer creates a new image from a container's changes.
+-//
+-// See http://goo.gl/Jn8pe8 for more details.
+-func (c *Client) CommitContainer(opts CommitContainerOptions) (*Image, error) {
+-	path := "/commit?" + queryString(opts)
+-	body, status, err := c.do("POST", path, opts.Run)
+-	if status == http.StatusNotFound {
+-		return nil, &NoSuchContainer{ID: opts.Container}
+-	}
+-	if err != nil {
+-		return nil, err
+-	}
+-	var image Image
+-	err = json.Unmarshal(body, &image)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return &image, nil
+-}
+-
+-// AttachToContainerOptions is the set of options that can be used when
+-// attaching to a container.
+-//
+-// See http://goo.gl/RRAhws for more details.
+-type AttachToContainerOptions struct {
+-	Container    string    `qs:"-"`
+-	InputStream  io.Reader `qs:"-"`
+-	OutputStream io.Writer `qs:"-"`
+-	ErrorStream  io.Writer `qs:"-"`
+-
+-	// Get container logs, sending it to OutputStream.
+-	Logs bool
+-
+-	// Stream the response?
+-	Stream bool
+-
+-	// Attach to stdin, and use InputStream.
+-	Stdin bool
+-
+-	// Attach to stdout, and use OutputStream.
+-	Stdout bool
+-
+-	// Attach to stderr, and use ErrorStream.
+-	Stderr bool
+-
+-	// If set, after a successful connect, a sentinel will be sent and then the
+-	// client will block on receive before continuing.
+-	//
+-	// It must be an unbuffered channel. Using a buffered channel can lead
+-	// to unexpected behavior.
+-	Success chan struct{}
+-
+-	// Use raw terminal? Usually true when the container contains a TTY.
+-	RawTerminal bool `qs:"-"`
+-}
+-
+-// AttachToContainer attaches to a container, using the given options.
+-//
+-// See http://goo.gl/RRAhws for more details.
+-func (c *Client) AttachToContainer(opts AttachToContainerOptions) error {
+-	if opts.Container == "" {
+-		return &NoSuchContainer{ID: opts.Container}
+-	}
+-	path := "/containers/" + opts.Container + "/attach?" + queryString(opts)
+-	return c.hijack("POST", path, opts.Success, opts.RawTerminal, opts.InputStream, opts.ErrorStream, opts.OutputStream, nil)
+-}
+-
+-// LogsOptions represents the set of options used when getting logs from a
+-// container.
+-//
+-// See http://goo.gl/rLhKSU for more details.
+-type LogsOptions struct {
+-	Container    string    `qs:"-"`
+-	OutputStream io.Writer `qs:"-"`
+-	ErrorStream  io.Writer `qs:"-"`
+-	Follow       bool
+-	Stdout       bool
+-	Stderr       bool
+-	Timestamps   bool
+-	Tail         string
+-
+-	// Use raw terminal? Usually true when the container contains a TTY.
+-	RawTerminal bool `qs:"-"`
+-}
+-
+-// Logs gets stdout and stderr logs from the specified container.
+-//
+-// See http://goo.gl/rLhKSU for more details.
+-func (c *Client) Logs(opts LogsOptions) error {
+-	if opts.Container == "" {
+-		return &NoSuchContainer{ID: opts.Container}
+-	}
+-	if opts.Tail == "" {
+-		opts.Tail = "all"
+-	}
+-	path := "/containers/" + opts.Container + "/logs?" + queryString(opts)
+-	return c.stream("GET", path, opts.RawTerminal, false, nil, nil, opts.OutputStream, opts.ErrorStream)
+-}
+-
+-// ResizeContainerTTY resizes the terminal to the given height and width.
+-func (c *Client) ResizeContainerTTY(id string, height, width int) error {
+-	params := make(url.Values)
+-	params.Set("h", strconv.Itoa(height))
+-	params.Set("w", strconv.Itoa(width))
+-	_, _, err := c.do("POST", "/containers/"+id+"/resize?"+params.Encode(), nil)
+-	return err
+-}
+-
+-// ExportContainerOptions is the set of parameters to the ExportContainer
+-// method.
+-//
+-// See http://goo.gl/hnzE62 for more details.
+-type ExportContainerOptions struct {
+-	ID           string
+-	OutputStream io.Writer
+-}
+-
+-// ExportContainer export the contents of container id as tar archive
+-// and prints the exported contents to stdout.
+-//
+-// See http://goo.gl/hnzE62 for more details.
+-func (c *Client) ExportContainer(opts ExportContainerOptions) error {
+-	if opts.ID == "" {
+-		return &NoSuchContainer{ID: opts.ID}
+-	}
+-	url := fmt.Sprintf("/containers/%s/export", opts.ID)
+-	return c.stream("GET", url, true, false, nil, nil, opts.OutputStream, nil)
+-}
+-
+-// NoSuchContainer is the error returned when a given container does not exist.
+-type NoSuchContainer struct {
+-	ID string
+-}
+-
+-func (err *NoSuchContainer) Error() string {
+-	return "No such container: " + err.ID
+-}
+-
+-// ContainerAlreadyRunning is the error returned when a given container is
+-// already running.
+-type ContainerAlreadyRunning struct {
+-	ID string
+-}
+-
+-func (err *ContainerAlreadyRunning) Error() string {
+-	return "Container already running: " + err.ID
+-}
+-
+-// ContainerNotRunning is the error returned when a given container is not
+-// running.
+-type ContainerNotRunning struct {
+-	ID string
+-}
+-
+-func (err *ContainerNotRunning) Error() string {
+-	return "Container not running: " + err.ID
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/container_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/container_test.go
+deleted file mode 100644
+index bfb1119..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/container_test.go
++++ /dev/null
+@@ -1,1524 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 docker
+-
+-import (
+-	"bytes"
+-	"encoding/json"
+-	"io/ioutil"
+-	"net"
+-	"net/http"
+-	"net/http/httptest"
+-	"net/url"
+-	"os"
+-	"reflect"
+-	"regexp"
+-	"runtime"
+-	"strconv"
+-	"strings"
+-	"testing"
+-	"time"
+-)
+-
+-func TestStateString(t *testing.T) {
+-	started := time.Now().Add(-3 * time.Hour)
+-	var tests = []struct {
+-		input    State
+-		expected string
+-	}{
+-		{State{Running: true, Paused: true}, "^paused$"},
+-		{State{Running: true, StartedAt: started}, "^Up 3h.*$"},
+-		{State{Running: false, ExitCode: 7}, "^Exit 7$"},
+-	}
+-	for _, tt := range tests {
+-		re := regexp.MustCompile(tt.expected)
+-		if got := tt.input.String(); !re.MatchString(got) {
+-			t.Errorf("State.String(): wrong result. Want %q. Got %q.", tt.expected, got)
+-		}
+-	}
+-}
+-
+-func TestListContainers(t *testing.T) {
+-	jsonContainers := `[
+-     {
+-             "Id": "8dfafdbc3a40",
+-             "Image": "base:latest",
+-             "Command": "echo 1",
+-             "Created": 1367854155,
+-             "Ports":[{"PrivatePort": 2222, "PublicPort": 3333, "Type": "tcp"}],
+-             "Status": "Exit 0"
+-     },
+-     {
+-             "Id": "9cd87474be90",
+-             "Image": "base:latest",
+-             "Command": "echo 222222",
+-             "Created": 1367854155,
+-             "Ports":[{"PrivatePort": 2222, "PublicPort": 3333, "Type": "tcp"}],
+-             "Status": "Exit 0"
+-     },
+-     {
+-             "Id": "3176a2479c92",
+-             "Image": "base:latest",
+-             "Command": "echo 3333333333333333",
+-             "Created": 1367854154,
+-             "Ports":[{"PrivatePort": 2221, "PublicPort": 3331, "Type": "tcp"}],
+-             "Status": "Exit 0"
+-     },
+-     {
+-             "Id": "4cb07b47f9fb",
+-             "Image": "base:latest",
+-             "Command": "echo 444444444444444444444444444444444",
+-             "Ports":[{"PrivatePort": 2223, "PublicPort": 3332, "Type": "tcp"}],
+-             "Created": 1367854152,
+-             "Status": "Exit 0"
+-     }
+-]`
+-	var expected []APIContainers
+-	err := json.Unmarshal([]byte(jsonContainers), &expected)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	client := newTestClient(&FakeRoundTripper{message: jsonContainers, status: http.StatusOK})
+-	containers, err := client.ListContainers(ListContainersOptions{})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !reflect.DeepEqual(containers, expected) {
+-		t.Errorf("ListContainers: Expected %#v. Got %#v.", expected, containers)
+-	}
+-}
+-
+-func TestListContainersParams(t *testing.T) {
+-	var tests = []struct {
+-		input  ListContainersOptions
+-		params map[string][]string
+-	}{
+-		{ListContainersOptions{}, map[string][]string{}},
+-		{ListContainersOptions{All: true}, map[string][]string{"all": {"1"}}},
+-		{ListContainersOptions{All: true, Limit: 10}, map[string][]string{"all": {"1"}, "limit": {"10"}}},
+-		{
+-			ListContainersOptions{All: true, Limit: 10, Since: "adf9983", Before: "abdeef"},
+-			map[string][]string{"all": {"1"}, "limit": {"10"}, "since": {"adf9983"}, "before": {"abdeef"}},
+-		},
+-		{
+-			ListContainersOptions{Filters: map[string][]string{"status": {"paused", "running"}}},
+-			map[string][]string{"filters": {"{\"status\":[\"paused\",\"running\"]}"}},
+-		},
+-		{
+-			ListContainersOptions{All: true, Filters: map[string][]string{"exited": {"0"}, "status": {"exited"}}},
+-			map[string][]string{"all": {"1"}, "filters": {"{\"exited\":[\"0\"],\"status\":[\"exited\"]}"}},
+-		},
+-	}
+-	fakeRT := &FakeRoundTripper{message: "[]", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	u, _ := url.Parse(client.getURL("/containers/json"))
+-	for _, tt := range tests {
+-		client.ListContainers(tt.input)
+-		got := map[string][]string(fakeRT.requests[0].URL.Query())
+-		if !reflect.DeepEqual(got, tt.params) {
+-			t.Errorf("Expected %#v, got %#v.", tt.params, got)
+-		}
+-		if path := fakeRT.requests[0].URL.Path; path != u.Path {
+-			t.Errorf("Wrong path on request. Want %q. Got %q.", u.Path, path)
+-		}
+-		if meth := fakeRT.requests[0].Method; meth != "GET" {
+-			t.Errorf("Wrong HTTP method. Want GET. Got %s.", meth)
+-		}
+-		fakeRT.Reset()
+-	}
+-}
+-
+-func TestListContainersFailure(t *testing.T) {
+-	var tests = []struct {
+-		status  int
+-		message string
+-	}{
+-		{400, "bad parameter"},
+-		{500, "internal server error"},
+-	}
+-	for _, tt := range tests {
+-		client := newTestClient(&FakeRoundTripper{message: tt.message, status: tt.status})
+-		expected := Error{Status: tt.status, Message: tt.message}
+-		containers, err := client.ListContainers(ListContainersOptions{})
+-		if !reflect.DeepEqual(expected, *err.(*Error)) {
+-			t.Errorf("Wrong error in ListContainers. Want %#v. Got %#v.", expected, err)
+-		}
+-		if len(containers) > 0 {
+-			t.Errorf("ListContainers failure. Expected empty list. Got %#v.", containers)
+-		}
+-	}
+-}
+-
+-func TestInspectContainer(t *testing.T) {
+-	jsonContainer := `{
+-             "Id": "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2",
+-             "Created": "2013-05-07T14:51:42.087658+02:00",
+-             "Path": "date",
+-             "Args": [],
+-             "Config": {
+-                     "Hostname": "4fa6e0f0c678",
+-                     "User": "",
+-                     "Memory": 17179869184,
+-                     "MemorySwap": 34359738368,
+-                     "AttachStdin": false,
+-                     "AttachStdout": true,
+-                     "AttachStderr": true,
+-                     "PortSpecs": null,
+-                     "Tty": false,
+-                     "OpenStdin": false,
+-                     "StdinOnce": false,
+-                     "Env": null,
+-                     "Cmd": [
+-                             "date"
+-                     ],
+-                     "Image": "base",
+-                     "Volumes": {},
+-                     "VolumesFrom": ""
+-             },
+-             "State": {
+-                     "Running": false,
+-                     "Pid": 0,
+-                     "ExitCode": 0,
+-                     "StartedAt": "2013-05-07T14:51:42.087658+02:00",
+-                     "Ghost": false
+-             },
+-             "Image": "b750fe79269d2ec9a3c593ef05b4332b1d1a02a62b4accb2c21d589ff2f5f2dc",
+-             "NetworkSettings": {
+-                     "IpAddress": "",
+-                     "IpPrefixLen": 0,
+-                     "Gateway": "",
+-                     "Bridge": "",
+-                     "PortMapping": null
+-             },
+-             "SysInitPath": "/home/kitty/go/src/github.com/dotcloud/docker/bin/docker",
+-             "ResolvConfPath": "/etc/resolv.conf",
+-             "Volumes": {},
+-             "HostConfig": {
+-               "Binds": null,
+-               "ContainerIDFile": "",
+-               "LxcConf": [],
+-               "Privileged": false,
+-               "PortBindings": {
+-                 "80/tcp": [
+-                   {
+-                     "HostIp": "0.0.0.0",
+-                     "HostPort": "49153"
+-                   }
+-                 ]
+-               },
+-               "Links": null,
+-               "PublishAllPorts": false
+-             }
+-}`
+-	var expected Container
+-	err := json.Unmarshal([]byte(jsonContainer), &expected)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	fakeRT := &FakeRoundTripper{message: jsonContainer, status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	id := "4fa6e0f0c678"
+-	container, err := client.InspectContainer(id)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !reflect.DeepEqual(*container, expected) {
+-		t.Errorf("InspectContainer(%q): Expected %#v. Got %#v.", id, expected, container)
+-	}
+-	expectedURL, _ := url.Parse(client.getURL("/containers/4fa6e0f0c678/json"))
+-	if gotPath := fakeRT.requests[0].URL.Path; gotPath != expectedURL.Path {
+-		t.Errorf("InspectContainer(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
+-	}
+-}
+-
+-func TestInspectContainerNegativeSwap(t *testing.T) {
+-	jsonContainer := `{
+-             "Id": "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2",
+-             "Created": "2013-05-07T14:51:42.087658+02:00",
+-             "Path": "date",
+-             "Args": [],
+-             "Config": {
+-                     "Hostname": "4fa6e0f0c678",
+-                     "User": "",
+-                     "Memory": 17179869184,
+-                     "MemorySwap": -1,
+-                     "AttachStdin": false,
+-                     "AttachStdout": true,
+-                     "AttachStderr": true,
+-                     "PortSpecs": null,
+-                     "Tty": false,
+-                     "OpenStdin": false,
+-                     "StdinOnce": false,
+-                     "Env": null,
+-                     "Cmd": [
+-                             "date"
+-                     ],
+-                     "Image": "base",
+-                     "Volumes": {},
+-                     "VolumesFrom": ""
+-             },
+-             "State": {
+-                     "Running": false,
+-                     "Pid": 0,
+-                     "ExitCode": 0,
+-                     "StartedAt": "2013-05-07T14:51:42.087658+02:00",
+-                     "Ghost": false
+-             },
+-             "Image": "b750fe79269d2ec9a3c593ef05b4332b1d1a02a62b4accb2c21d589ff2f5f2dc",
+-             "NetworkSettings": {
+-                     "IpAddress": "",
+-                     "IpPrefixLen": 0,
+-                     "Gateway": "",
+-                     "Bridge": "",
+-                     "PortMapping": null
+-             },
+-             "SysInitPath": "/home/kitty/go/src/github.com/dotcloud/docker/bin/docker",
+-             "ResolvConfPath": "/etc/resolv.conf",
+-             "Volumes": {},
+-             "HostConfig": {
+-               "Binds": null,
+-               "ContainerIDFile": "",
+-               "LxcConf": [],
+-               "Privileged": false,
+-               "PortBindings": {
+-                 "80/tcp": [
+-                   {
+-                     "HostIp": "0.0.0.0",
+-                     "HostPort": "49153"
+-                   }
+-                 ]
+-               },
+-               "Links": null,
+-               "PublishAllPorts": false
+-             }
+-}`
+-	var expected Container
+-	err := json.Unmarshal([]byte(jsonContainer), &expected)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	fakeRT := &FakeRoundTripper{message: jsonContainer, status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	id := "4fa6e0f0c678"
+-	container, err := client.InspectContainer(id)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !reflect.DeepEqual(*container, expected) {
+-		t.Errorf("InspectContainer(%q): Expected %#v. Got %#v.", id, expected, container)
+-	}
+-	expectedURL, _ := url.Parse(client.getURL("/containers/4fa6e0f0c678/json"))
+-	if gotPath := fakeRT.requests[0].URL.Path; gotPath != expectedURL.Path {
+-		t.Errorf("InspectContainer(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
+-	}
+-}
+-
+-func TestInspectContainerFailure(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "server error", status: 500})
+-	expected := Error{Status: 500, Message: "server error"}
+-	container, err := client.InspectContainer("abe033")
+-	if container != nil {
+-		t.Errorf("InspectContainer: Expected <nil> container, got %#v", container)
+-	}
+-	if !reflect.DeepEqual(expected, *err.(*Error)) {
+-		t.Errorf("InspectContainer: Wrong error information. Want %#v. Got %#v.", expected, err)
+-	}
+-}
+-
+-func TestInspectContainerNotFound(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "no such container", status: 404})
+-	container, err := client.InspectContainer("abe033")
+-	if container != nil {
+-		t.Errorf("InspectContainer: Expected <nil> container, got %#v", container)
+-	}
+-	expected := &NoSuchContainer{ID: "abe033"}
+-	if !reflect.DeepEqual(err, expected) {
+-		t.Errorf("InspectContainer: Wrong error information. Want %#v. Got %#v.", expected, err)
+-	}
+-}
+-
+-func TestContainerChanges(t *testing.T) {
+-	jsonChanges := `[
+-     {
+-             "Path":"/dev",
+-             "Kind":0
+-     },
+-     {
+-             "Path":"/dev/kmsg",
+-             "Kind":1
+-     },
+-     {
+-             "Path":"/test",
+-             "Kind":1
+-     }
+-]`
+-	var expected []Change
+-	err := json.Unmarshal([]byte(jsonChanges), &expected)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	fakeRT := &FakeRoundTripper{message: jsonChanges, status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	id := "4fa6e0f0c678"
+-	changes, err := client.ContainerChanges(id)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !reflect.DeepEqual(changes, expected) {
+-		t.Errorf("ContainerChanges(%q): Expected %#v. Got %#v.", id, expected, changes)
+-	}
+-	expectedURL, _ := url.Parse(client.getURL("/containers/4fa6e0f0c678/changes"))
+-	if gotPath := fakeRT.requests[0].URL.Path; gotPath != expectedURL.Path {
+-		t.Errorf("ContainerChanges(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
+-	}
+-}
+-
+-func TestContainerChangesFailure(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "server error", status: 500})
+-	expected := Error{Status: 500, Message: "server error"}
+-	changes, err := client.ContainerChanges("abe033")
+-	if changes != nil {
+-		t.Errorf("ContainerChanges: Expected <nil> changes, got %#v", changes)
+-	}
+-	if !reflect.DeepEqual(expected, *err.(*Error)) {
+-		t.Errorf("ContainerChanges: Wrong error information. Want %#v. Got %#v.", expected, err)
+-	}
+-}
+-
+-func TestContainerChangesNotFound(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "no such container", status: 404})
+-	changes, err := client.ContainerChanges("abe033")
+-	if changes != nil {
+-		t.Errorf("ContainerChanges: Expected <nil> changes, got %#v", changes)
+-	}
+-	expected := &NoSuchContainer{ID: "abe033"}
+-	if !reflect.DeepEqual(err, expected) {
+-		t.Errorf("ContainerChanges: Wrong error information. Want %#v. Got %#v.", expected, err)
+-	}
+-}
+-
+-func TestCreateContainer(t *testing.T) {
+-	jsonContainer := `{
+-             "Id": "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2",
+-	     "Warnings": []
+-}`
+-	var expected Container
+-	err := json.Unmarshal([]byte(jsonContainer), &expected)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	fakeRT := &FakeRoundTripper{message: jsonContainer, status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	config := Config{AttachStdout: true, AttachStdin: true}
+-	opts := CreateContainerOptions{Name: "TestCreateContainer", Config: &config}
+-	container, err := client.CreateContainer(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
+-	if container.ID != id {
+-		t.Errorf("CreateContainer: wrong ID. Want %q. Got %q.", id, container.ID)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "POST" {
+-		t.Errorf("CreateContainer: wrong HTTP method. Want %q. Got %q.", "POST", req.Method)
+-	}
+-	expectedURL, _ := url.Parse(client.getURL("/containers/create"))
+-	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
+-		t.Errorf("CreateContainer: Wrong path in request. Want %q. Got %q.", expectedURL.Path, gotPath)
+-	}
+-	var gotBody Config
+-	err = json.NewDecoder(req.Body).Decode(&gotBody)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-}
+-
+-func TestCreateContainerImageNotFound(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "No such image", status: http.StatusNotFound})
+-	config := Config{AttachStdout: true, AttachStdin: true}
+-	container, err := client.CreateContainer(CreateContainerOptions{Config: &config})
+-	if container != nil {
+-		t.Errorf("CreateContainer: expected <nil> container, got %#v.", container)
+-	}
+-	if !reflect.DeepEqual(err, ErrNoSuchImage) {
+-		t.Errorf("CreateContainer: Wrong error type. Want %#v. Got %#v.", ErrNoSuchImage, err)
+-	}
+-}
+-
+-func TestCreateContainerWithHostConfig(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "{}", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	config := Config{}
+-	hostConfig := HostConfig{PublishAllPorts: true}
+-	opts := CreateContainerOptions{Name: "TestCreateContainerWithHostConfig", Config: &config, HostConfig: &hostConfig}
+-	_, err := client.CreateContainer(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	var gotBody map[string]interface{}
+-	err = json.NewDecoder(req.Body).Decode(&gotBody)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if _, ok := gotBody["HostConfig"]; !ok {
+-		t.Errorf("CreateContainer: wrong body. HostConfig was not serialized")
+-	}
+-}
+-
+-func TestStartContainer(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
+-	err := client.StartContainer(id, &HostConfig{})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "POST" {
+-		t.Errorf("StartContainer(%q): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
+-	}
+-	expectedURL, _ := url.Parse(client.getURL("/containers/" + id + "/start"))
+-	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
+-		t.Errorf("StartContainer(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
+-	}
+-	expectedContentType := "application/json"
+-	if contentType := req.Header.Get("Content-Type"); contentType != expectedContentType {
+-		t.Errorf("StartContainer(%q): Wrong content-type in request. Want %q. Got %q.", id, expectedContentType, contentType)
+-	}
+-}
+-
+-func TestStartContainerNilHostConfig(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
+-	err := client.StartContainer(id, nil)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "POST" {
+-		t.Errorf("StartContainer(%q): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
+-	}
+-	expectedURL, _ := url.Parse(client.getURL("/containers/" + id + "/start"))
+-	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
+-		t.Errorf("StartContainer(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
+-	}
+-	expectedContentType := "application/json"
+-	if contentType := req.Header.Get("Content-Type"); contentType != expectedContentType {
+-		t.Errorf("StartContainer(%q): Wrong content-type in request. Want %q. Got %q.", id, expectedContentType, contentType)
+-	}
+-}
+-
+-func TestStartContainerNotFound(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
+-	err := client.StartContainer("a2344", &HostConfig{})
+-	expected := &NoSuchContainer{ID: "a2344"}
+-	if !reflect.DeepEqual(err, expected) {
+-		t.Errorf("StartContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
+-	}
+-}
+-
+-func TestStartContainerAlreadyRunning(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "container already running", status: http.StatusNotModified})
+-	err := client.StartContainer("a2334", &HostConfig{})
+-	expected := &ContainerAlreadyRunning{ID: "a2334"}
+-	if !reflect.DeepEqual(err, expected) {
+-		t.Errorf("StartContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
+-	}
+-}
+-
+-func TestStopContainer(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusNoContent}
+-	client := newTestClient(fakeRT)
+-	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
+-	err := client.StopContainer(id, 10)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "POST" {
+-		t.Errorf("StopContainer(%q, 10): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
+-	}
+-	expectedURL, _ := url.Parse(client.getURL("/containers/" + id + "/stop"))
+-	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
+-		t.Errorf("StopContainer(%q, 10): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
+-	}
+-}
+-
+-func TestStopContainerNotFound(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
+-	err := client.StopContainer("a2334", 10)
+-	expected := &NoSuchContainer{ID: "a2334"}
+-	if !reflect.DeepEqual(err, expected) {
+-		t.Errorf("StopContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
+-	}
+-}
+-
+-func TestStopContainerNotRunning(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "container not running", status: http.StatusNotModified})
+-	err := client.StopContainer("a2334", 10)
+-	expected := &ContainerNotRunning{ID: "a2334"}
+-	if !reflect.DeepEqual(err, expected) {
+-		t.Errorf("StopContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
+-	}
+-}
+-
+-func TestRestartContainer(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusNoContent}
+-	client := newTestClient(fakeRT)
+-	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
+-	err := client.RestartContainer(id, 10)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "POST" {
+-		t.Errorf("RestartContainer(%q, 10): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
+-	}
+-	expectedURL, _ := url.Parse(client.getURL("/containers/" + id + "/restart"))
+-	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
+-		t.Errorf("RestartContainer(%q, 10): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
+-	}
+-}
+-
+-func TestRestartContainerNotFound(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
+-	err := client.RestartContainer("a2334", 10)
+-	expected := &NoSuchContainer{ID: "a2334"}
+-	if !reflect.DeepEqual(err, expected) {
+-		t.Errorf("RestartContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
+-	}
+-}
+-
+-func TestPauseContainer(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusNoContent}
+-	client := newTestClient(fakeRT)
+-	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
+-	err := client.PauseContainer(id)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "POST" {
+-		t.Errorf("PauseContainer(%q): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
+-	}
+-	expectedURL, _ := url.Parse(client.getURL("/containers/" + id + "/pause"))
+-	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
+-		t.Errorf("PauseContainer(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
+-	}
+-}
+-
+-func TestPauseContainerNotFound(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
+-	err := client.PauseContainer("a2334")
+-	expected := &NoSuchContainer{ID: "a2334"}
+-	if !reflect.DeepEqual(err, expected) {
+-		t.Errorf("PauseContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
+-	}
+-}
+-
+-func TestUnpauseContainer(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusNoContent}
+-	client := newTestClient(fakeRT)
+-	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
+-	err := client.UnpauseContainer(id)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "POST" {
+-		t.Errorf("PauseContainer(%q): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
+-	}
+-	expectedURL, _ := url.Parse(client.getURL("/containers/" + id + "/unpause"))
+-	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
+-		t.Errorf("PauseContainer(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
+-	}
+-}
+-
+-func TestUnpauseContainerNotFound(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
+-	err := client.UnpauseContainer("a2334")
+-	expected := &NoSuchContainer{ID: "a2334"}
+-	if !reflect.DeepEqual(err, expected) {
+-		t.Errorf("PauseContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
+-	}
+-}
+-
+-func TestKillContainer(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusNoContent}
+-	client := newTestClient(fakeRT)
+-	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
+-	err := client.KillContainer(KillContainerOptions{ID: id})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "POST" {
+-		t.Errorf("KillContainer(%q): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
+-	}
+-	expectedURL, _ := url.Parse(client.getURL("/containers/" + id + "/kill"))
+-	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
+-		t.Errorf("KillContainer(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
+-	}
+-}
+-
+-func TestKillContainerSignal(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusNoContent}
+-	client := newTestClient(fakeRT)
+-	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
+-	err := client.KillContainer(KillContainerOptions{ID: id, Signal: SIGTERM})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "POST" {
+-		t.Errorf("KillContainer(%q): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
+-	}
+-	if signal := req.URL.Query().Get("signal"); signal != "15" {
+-		t.Errorf("KillContainer(%q): Wrong query string in request. Want %q. Got %q.", id, "15", signal)
+-	}
+-}
+-
+-func TestKillContainerNotFound(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
+-	err := client.KillContainer(KillContainerOptions{ID: "a2334"})
+-	expected := &NoSuchContainer{ID: "a2334"}
+-	if !reflect.DeepEqual(err, expected) {
+-		t.Errorf("KillContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
+-	}
+-}
+-
+-func TestRemoveContainer(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
+-	opts := RemoveContainerOptions{ID: id}
+-	err := client.RemoveContainer(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "DELETE" {
+-		t.Errorf("RemoveContainer(%q): wrong HTTP method. Want %q. Got %q.", id, "DELETE", req.Method)
+-	}
+-	expectedURL, _ := url.Parse(client.getURL("/containers/" + id))
+-	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
+-		t.Errorf("RemoveContainer(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
+-	}
+-}
+-
+-func TestRemoveContainerRemoveVolumes(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
+-	opts := RemoveContainerOptions{ID: id, RemoveVolumes: true}
+-	err := client.RemoveContainer(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	params := map[string][]string(req.URL.Query())
+-	expected := map[string][]string{"v": {"1"}}
+-	if !reflect.DeepEqual(params, expected) {
+-		t.Errorf("RemoveContainer(%q): wrong parameters. Want %#v. Got %#v.", id, expected, params)
+-	}
+-}
+-
+-func TestRemoveContainerNotFound(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
+-	err := client.RemoveContainer(RemoveContainerOptions{ID: "a2334"})
+-	expected := &NoSuchContainer{ID: "a2334"}
+-	if !reflect.DeepEqual(err, expected) {
+-		t.Errorf("RemoveContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
+-	}
+-}
+-
+-func TestResizeContainerTTY(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
+-	err := client.ResizeContainerTTY(id, 40, 80)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "POST" {
+-		t.Errorf("ResizeContainerTTY(%q): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
+-	}
+-	expectedURL, _ := url.Parse(client.getURL("/containers/" + id + "/resize"))
+-	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
+-		t.Errorf("ResizeContainerTTY(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
+-	}
+-	got := map[string][]string(req.URL.Query())
+-	expectedParams := map[string][]string{
+-		"w": {"80"},
+-		"h": {"40"},
+-	}
+-	if !reflect.DeepEqual(got, expectedParams) {
+-		t.Errorf("Expected %#v, got %#v.", expectedParams, got)
+-	}
+-}
+-
+-func TestWaitContainer(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: `{"StatusCode": 56}`, status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
+-	status, err := client.WaitContainer(id)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if status != 56 {
+-		t.Errorf("WaitContainer(%q): wrong return. Want 56. Got %d.", id, status)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "POST" {
+-		t.Errorf("WaitContainer(%q): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
+-	}
+-	expectedURL, _ := url.Parse(client.getURL("/containers/" + id + "/wait"))
+-	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
+-		t.Errorf("WaitContainer(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
+-	}
+-}
+-
+-func TestWaitContainerNotFound(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
+-	_, err := client.WaitContainer("a2334")
+-	expected := &NoSuchContainer{ID: "a2334"}
+-	if !reflect.DeepEqual(err, expected) {
+-		t.Errorf("WaitContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
+-	}
+-}
+-
+-func TestCommitContainer(t *testing.T) {
+-	response := `{"Id":"596069db4bf5"}`
+-	client := newTestClient(&FakeRoundTripper{message: response, status: http.StatusOK})
+-	id := "596069db4bf5"
+-	image, err := client.CommitContainer(CommitContainerOptions{})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if image.ID != id {
+-		t.Errorf("CommitContainer: Wrong image id. Want %q. Got %q.", id, image.ID)
+-	}
+-}
+-
+-func TestCommitContainerParams(t *testing.T) {
+-	cfg := Config{Memory: 67108864}
+-	json, _ := json.Marshal(&cfg)
+-	var tests = []struct {
+-		input  CommitContainerOptions
+-		params map[string][]string
+-		body   []byte
+-	}{
+-		{CommitContainerOptions{}, map[string][]string{}, nil},
+-		{CommitContainerOptions{Container: "44c004db4b17"}, map[string][]string{"container": {"44c004db4b17"}}, nil},
+-		{
+-			CommitContainerOptions{Container: "44c004db4b17", Repository: "tsuru/python", Message: "something"},
+-			map[string][]string{"container": {"44c004db4b17"}, "repo": {"tsuru/python"}, "m": {"something"}},
+-			nil,
+-		},
+-		{
+-			CommitContainerOptions{Container: "44c004db4b17", Run: &cfg},
+-			map[string][]string{"container": {"44c004db4b17"}},
+-			json,
+-		},
+-	}
+-	fakeRT := &FakeRoundTripper{message: "[]", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	u, _ := url.Parse(client.getURL("/commit"))
+-	for _, tt := range tests {
+-		client.CommitContainer(tt.input)
+-		got := map[string][]string(fakeRT.requests[0].URL.Query())
+-		if !reflect.DeepEqual(got, tt.params) {
+-			t.Errorf("Expected %#v, got %#v.", tt.params, got)
+-		}
+-		if path := fakeRT.requests[0].URL.Path; path != u.Path {
+-			t.Errorf("Wrong path on request. Want %q. Got %q.", u.Path, path)
+-		}
+-		if meth := fakeRT.requests[0].Method; meth != "POST" {
+-			t.Errorf("Wrong HTTP method. Want POST. Got %s.", meth)
+-		}
+-		if tt.body != nil {
+-			if requestBody, err := ioutil.ReadAll(fakeRT.requests[0].Body); err == nil {
+-				if bytes.Compare(requestBody, tt.body) != 0 {
+-					t.Errorf("Expected body %#v, got %#v", tt.body, requestBody)
+-				}
+-			} else {
+-				t.Errorf("Error reading request body: %#v", err)
+-			}
+-		}
+-		fakeRT.Reset()
+-	}
+-}
+-
+-func TestCommitContainerFailure(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusInternalServerError})
+-	_, err := client.CommitContainer(CommitContainerOptions{})
+-	if err == nil {
+-		t.Error("Expected non-nil error, got <nil>.")
+-	}
+-}
+-
+-func TestCommitContainerNotFound(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
+-	_, err := client.CommitContainer(CommitContainerOptions{})
+-	expected := &NoSuchContainer{ID: ""}
+-	if !reflect.DeepEqual(err, expected) {
+-		t.Errorf("CommitContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
+-	}
+-}
+-
+-func TestAttachToContainerLogs(t *testing.T) {
+-	var req http.Request
+-	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+-		w.Write([]byte{1, 0, 0, 0, 0, 0, 0, 19})
+-		w.Write([]byte("something happened!"))
+-		req = *r
+-	}))
+-	defer server.Close()
+-	client, _ := NewClient(server.URL)
+-	client.SkipServerVersionCheck = true
+-	var buf bytes.Buffer
+-	opts := AttachToContainerOptions{
+-		Container:    "a123456",
+-		OutputStream: &buf,
+-		Stdout:       true,
+-		Stderr:       true,
+-		Logs:         true,
+-	}
+-	err := client.AttachToContainer(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	expected := "something happened!"
+-	if buf.String() != expected {
+-		t.Errorf("AttachToContainer for logs: wrong output. Want %q. Got %q.", expected, buf.String())
+-	}
+-	if req.Method != "POST" {
+-		t.Errorf("AttachToContainer: wrong HTTP method. Want POST. Got %s.", req.Method)
+-	}
+-	u, _ := url.Parse(client.getURL("/containers/a123456/attach"))
+-	if req.URL.Path != u.Path {
+-		t.Errorf("AttachToContainer for logs: wrong HTTP path. Want %q. Got %q.", u.Path, req.URL.Path)
+-	}
+-	expectedQs := map[string][]string{
+-		"logs":   {"1"},
+-		"stdout": {"1"},
+-		"stderr": {"1"},
+-	}
+-	got := map[string][]string(req.URL.Query())
+-	if !reflect.DeepEqual(got, expectedQs) {
+-		t.Errorf("AttachToContainer: wrong query string. Want %#v. Got %#v.", expectedQs, got)
+-	}
+-}
+-
+-func TestAttachToContainer(t *testing.T) {
+-	var reader = strings.NewReader("send value")
+-	var req http.Request
+-	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+-		w.Write([]byte{1, 0, 0, 0, 0, 0, 0, 5})
+-		w.Write([]byte("hello"))
+-		req = *r
+-	}))
+-	defer server.Close()
+-	client, _ := NewClient(server.URL)
+-	client.SkipServerVersionCheck = true
+-	var stdout, stderr bytes.Buffer
+-	opts := AttachToContainerOptions{
+-		Container:    "a123456",
+-		OutputStream: &stdout,
+-		ErrorStream:  &stderr,
+-		InputStream:  reader,
+-		Stdin:        true,
+-		Stdout:       true,
+-		Stderr:       true,
+-		Stream:       true,
+-		RawTerminal:  true,
+-	}
+-	err := client.AttachToContainer(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	expected := map[string][]string{
+-		"stdin":  {"1"},
+-		"stdout": {"1"},
+-		"stderr": {"1"},
+-		"stream": {"1"},
+-	}
+-	got := map[string][]string(req.URL.Query())
+-	if !reflect.DeepEqual(got, expected) {
+-		t.Errorf("AttachToContainer: wrong query string. Want %#v. Got %#v.", expected, got)
+-	}
+-}
+-
+-func TestAttachToContainerSentinel(t *testing.T) {
+-	var reader = strings.NewReader("send value")
+-	var req http.Request
+-	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+-		w.Write([]byte{1, 0, 0, 0, 0, 0, 0, 5})
+-		w.Write([]byte("hello"))
+-		req = *r
+-	}))
+-	defer server.Close()
+-	client, _ := NewClient(server.URL)
+-	client.SkipServerVersionCheck = true
+-	var stdout, stderr bytes.Buffer
+-	success := make(chan struct{})
+-	opts := AttachToContainerOptions{
+-		Container:    "a123456",
+-		OutputStream: &stdout,
+-		ErrorStream:  &stderr,
+-		InputStream:  reader,
+-		Stdin:        true,
+-		Stdout:       true,
+-		Stderr:       true,
+-		Stream:       true,
+-		RawTerminal:  true,
+-		Success:      success,
+-	}
+-	go client.AttachToContainer(opts)
+-	success <- <-success
+-}
+-
+-func TestAttachToContainerNilStdout(t *testing.T) {
+-	var reader = strings.NewReader("send value")
+-	var req http.Request
+-	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+-		w.Write([]byte{1, 0, 0, 0, 0, 0, 0, 5})
+-		w.Write([]byte("hello"))
+-		req = *r
+-	}))
+-	defer server.Close()
+-	client, _ := NewClient(server.URL)
+-	client.SkipServerVersionCheck = true
+-	var stderr bytes.Buffer
+-	opts := AttachToContainerOptions{
+-		Container:    "a123456",
+-		OutputStream: nil,
+-		ErrorStream:  &stderr,
+-		InputStream:  reader,
+-		Stdin:        true,
+-		Stdout:       true,
+-		Stderr:       true,
+-		Stream:       true,
+-		RawTerminal:  true,
+-	}
+-	err := client.AttachToContainer(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-}
+-
+-func TestAttachToContainerNilStderr(t *testing.T) {
+-	var reader = strings.NewReader("send value")
+-	var req http.Request
+-	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+-		w.Write([]byte{1, 0, 0, 0, 0, 0, 0, 5})
+-		w.Write([]byte("hello"))
+-		req = *r
+-	}))
+-	defer server.Close()
+-	client, _ := NewClient(server.URL)
+-	client.SkipServerVersionCheck = true
+-	var stdout bytes.Buffer
+-	opts := AttachToContainerOptions{
+-		Container:    "a123456",
+-		OutputStream: &stdout,
+-		InputStream:  reader,
+-		Stdin:        true,
+-		Stdout:       true,
+-		Stderr:       true,
+-		Stream:       true,
+-		RawTerminal:  true,
+-	}
+-	err := client.AttachToContainer(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-}
+-
+-func TestAttachToContainerRawTerminalFalse(t *testing.T) {
+-	input := strings.NewReader("send value")
+-	var req http.Request
+-	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+-		prefix := []byte{1, 0, 0, 0, 0, 0, 0, 5}
+-		w.Write(prefix)
+-		w.Write([]byte("hello"))
+-		req = *r
+-	}))
+-	defer server.Close()
+-	client, _ := NewClient(server.URL)
+-	client.SkipServerVersionCheck = true
+-	var stdout, stderr bytes.Buffer
+-	opts := AttachToContainerOptions{
+-		Container:    "a123456",
+-		OutputStream: &stdout,
+-		ErrorStream:  &stderr,
+-		InputStream:  input,
+-		Stdin:        true,
+-		Stdout:       true,
+-		Stderr:       true,
+-		Stream:       true,
+-		RawTerminal:  false,
+-	}
+-	err := client.AttachToContainer(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	expected := map[string][]string{
+-		"stdin":  {"1"},
+-		"stdout": {"1"},
+-		"stderr": {"1"},
+-		"stream": {"1"},
+-	}
+-	got := map[string][]string(req.URL.Query())
+-	if !reflect.DeepEqual(got, expected) {
+-		t.Errorf("AttachToContainer: wrong query string. Want %#v. Got %#v.", expected, got)
+-	}
+-	t.Log(stderr.String())
+-	t.Log(stdout.String())
+-	if stdout.String() != "hello" {
+-		t.Errorf("AttachToContainer: wrong content written to stdout. Want %q. Got %q.", "hello", stderr.String())
+-	}
+-}
+-
+-func TestAttachToContainerWithoutContainer(t *testing.T) {
+-	var client Client
+-	err := client.AttachToContainer(AttachToContainerOptions{})
+-	expected := &NoSuchContainer{ID: ""}
+-	if !reflect.DeepEqual(err, expected) {
+-		t.Errorf("AttachToContainer: wrong error. Want %#v. Got %#v.", expected, err)
+-	}
+-}
+-
+-func TestLogs(t *testing.T) {
+-	var req http.Request
+-	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+-		prefix := []byte{1, 0, 0, 0, 0, 0, 0, 19}
+-		w.Write(prefix)
+-		w.Write([]byte("something happened!"))
+-		req = *r
+-	}))
+-	defer server.Close()
+-	client, _ := NewClient(server.URL)
+-	client.SkipServerVersionCheck = true
+-	var buf bytes.Buffer
+-	opts := LogsOptions{
+-		Container:    "a123456",
+-		OutputStream: &buf,
+-		Follow:       true,
+-		Stdout:       true,
+-		Stderr:       true,
+-		Timestamps:   true,
+-	}
+-	err := client.Logs(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	expected := "something happened!"
+-	if buf.String() != expected {
+-		t.Errorf("Logs: wrong output. Want %q. Got %q.", expected, buf.String())
+-	}
+-	if req.Method != "GET" {
+-		t.Errorf("Logs: wrong HTTP method. Want GET. Got %s.", req.Method)
+-	}
+-	u, _ := url.Parse(client.getURL("/containers/a123456/logs"))
+-	if req.URL.Path != u.Path {
+-		t.Errorf("AttachToContainer for logs: wrong HTTP path. Want %q. Got %q.", u.Path, req.URL.Path)
+-	}
+-	expectedQs := map[string][]string{
+-		"follow":     {"1"},
+-		"stdout":     {"1"},
+-		"stderr":     {"1"},
+-		"timestamps": {"1"},
+-		"tail":       {"all"},
+-	}
+-	got := map[string][]string(req.URL.Query())
+-	if !reflect.DeepEqual(got, expectedQs) {
+-		t.Errorf("Logs: wrong query string. Want %#v. Got %#v.", expectedQs, got)
+-	}
+-}
+-
+-func TestLogsNilStdoutDoesntFail(t *testing.T) {
+-	var req http.Request
+-	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+-		prefix := []byte{1, 0, 0, 0, 0, 0, 0, 19}
+-		w.Write(prefix)
+-		w.Write([]byte("something happened!"))
+-		req = *r
+-	}))
+-	defer server.Close()
+-	client, _ := NewClient(server.URL)
+-	client.SkipServerVersionCheck = true
+-	opts := LogsOptions{
+-		Container:  "a123456",
+-		Follow:     true,
+-		Stdout:     true,
+-		Stderr:     true,
+-		Timestamps: true,
+-	}
+-	err := client.Logs(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-}
+-
+-func TestLogsNilStderrDoesntFail(t *testing.T) {
+-	var req http.Request
+-	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+-		prefix := []byte{2, 0, 0, 0, 0, 0, 0, 19}
+-		w.Write(prefix)
+-		w.Write([]byte("something happened!"))
+-		req = *r
+-	}))
+-	defer server.Close()
+-	client, _ := NewClient(server.URL)
+-	client.SkipServerVersionCheck = true
+-	opts := LogsOptions{
+-		Container:  "a123456",
+-		Follow:     true,
+-		Stdout:     true,
+-		Stderr:     true,
+-		Timestamps: true,
+-	}
+-	err := client.Logs(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-}
+-
+-func TestLogsSpecifyingTail(t *testing.T) {
+-	var req http.Request
+-	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+-		prefix := []byte{1, 0, 0, 0, 0, 0, 0, 19}
+-		w.Write(prefix)
+-		w.Write([]byte("something happened!"))
+-		req = *r
+-	}))
+-	defer server.Close()
+-	client, _ := NewClient(server.URL)
+-	client.SkipServerVersionCheck = true
+-	var buf bytes.Buffer
+-	opts := LogsOptions{
+-		Container:    "a123456",
+-		OutputStream: &buf,
+-		Follow:       true,
+-		Stdout:       true,
+-		Stderr:       true,
+-		Timestamps:   true,
+-		Tail:         "100",
+-	}
+-	err := client.Logs(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	expected := "something happened!"
+-	if buf.String() != expected {
+-		t.Errorf("Logs: wrong output. Want %q. Got %q.", expected, buf.String())
+-	}
+-	if req.Method != "GET" {
+-		t.Errorf("Logs: wrong HTTP method. Want GET. Got %s.", req.Method)
+-	}
+-	u, _ := url.Parse(client.getURL("/containers/a123456/logs"))
+-	if req.URL.Path != u.Path {
+-		t.Errorf("AttachToContainer for logs: wrong HTTP path. Want %q. Got %q.", u.Path, req.URL.Path)
+-	}
+-	expectedQs := map[string][]string{
+-		"follow":     {"1"},
+-		"stdout":     {"1"},
+-		"stderr":     {"1"},
+-		"timestamps": {"1"},
+-		"tail":       {"100"},
+-	}
+-	got := map[string][]string(req.URL.Query())
+-	if !reflect.DeepEqual(got, expectedQs) {
+-		t.Errorf("Logs: wrong query string. Want %#v. Got %#v.", expectedQs, got)
+-	}
+-}
+-
+-func TestLogsRawTerminal(t *testing.T) {
+-	var req http.Request
+-	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+-		w.Write([]byte("something happened!"))
+-		req = *r
+-	}))
+-	defer server.Close()
+-	client, _ := NewClient(server.URL)
+-	client.SkipServerVersionCheck = true
+-	var buf bytes.Buffer
+-	opts := LogsOptions{
+-		Container:    "a123456",
+-		OutputStream: &buf,
+-		Follow:       true,
+-		RawTerminal:  true,
+-		Stdout:       true,
+-		Stderr:       true,
+-		Timestamps:   true,
+-		Tail:         "100",
+-	}
+-	err := client.Logs(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	expected := "something happened!"
+-	if buf.String() != expected {
+-		t.Errorf("Logs: wrong output. Want %q. Got %q.", expected, buf.String())
+-	}
+-}
+-
+-func TestLogsNoContainer(t *testing.T) {
+-	var client Client
+-	err := client.Logs(LogsOptions{})
+-	expected := &NoSuchContainer{ID: ""}
+-	if !reflect.DeepEqual(err, expected) {
+-		t.Errorf("AttachToContainer: wrong error. Want %#v. Got %#v.", expected, err)
+-	}
+-}
+-
+-func TestNoSuchContainerError(t *testing.T) {
+-	var err = &NoSuchContainer{ID: "i345"}
+-	expected := "No such container: i345"
+-	if got := err.Error(); got != expected {
+-		t.Errorf("NoSuchContainer: wrong message. Want %q. Got %q.", expected, got)
+-	}
+-}
+-
+-func TestExportContainer(t *testing.T) {
+-	content := "exported container tar content"
+-	out := stdoutMock{bytes.NewBufferString(content)}
+-	client := newTestClient(&FakeRoundTripper{status: http.StatusOK})
+-	opts := ExportContainerOptions{ID: "4fa6e0f0c678", OutputStream: out}
+-	err := client.ExportContainer(opts)
+-	if err != nil {
+-		t.Errorf("ExportContainer: caugh error %#v while exporting container, expected nil", err.Error())
+-	}
+-	if out.String() != content {
+-		t.Errorf("ExportContainer: wrong stdout. Want %#v. Got %#v.", content, out.String())
+-	}
+-}
+-
+-func TestExportContainerViaUnixSocket(t *testing.T) {
+-	if runtime.GOOS != "darwin" {
+-		t.Skip("skipping test on %q", runtime.GOOS)
+-	}
+-	content := "exported container tar content"
+-	var buf []byte
+-	out := bytes.NewBuffer(buf)
+-	tempSocket := tempfile("export_socket")
+-	defer os.Remove(tempSocket)
+-	endpoint := "unix://" + tempSocket
+-	u, _ := parseEndpoint(endpoint)
+-	client := Client{
+-		HTTPClient:             http.DefaultClient,
+-		endpoint:               endpoint,
+-		endpointURL:            u,
+-		SkipServerVersionCheck: true,
+-	}
+-	listening := make(chan string)
+-	done := make(chan int)
+-	go runStreamConnServer(t, "unix", tempSocket, listening, done)
+-	<-listening // wait for server to start
+-	opts := ExportContainerOptions{ID: "4fa6e0f0c678", OutputStream: out}
+-	err := client.ExportContainer(opts)
+-	<-done // make sure server stopped
+-	if err != nil {
+-		t.Errorf("ExportContainer: caugh error %#v while exporting container, expected nil", err.Error())
+-	}
+-	if out.String() != content {
+-		t.Errorf("ExportContainer: wrong stdout. Want %#v. Got %#v.", content, out.String())
+-	}
+-}
+-
+-func runStreamConnServer(t *testing.T, network, laddr string, listening chan<- string, done chan<- int) {
+-	defer close(done)
+-	l, err := net.Listen(network, laddr)
+-	if err != nil {
+-		t.Errorf("Listen(%q, %q) failed: %v", network, laddr, err)
+-		listening <- "<nil>"
+-		return
+-	}
+-	defer l.Close()
+-	listening <- l.Addr().String()
+-	c, err := l.Accept()
+-	if err != nil {
+-		t.Logf("Accept failed: %v", err)
+-		return
+-	}
+-	c.Write([]byte("HTTP/1.1 200 OK\n\nexported container tar content"))
+-	c.Close()
+-}
+-
+-func tempfile(filename string) string {
+-	return os.TempDir() + "/" + filename + "." + strconv.Itoa(os.Getpid())
+-}
+-
+-func TestExportContainerNoId(t *testing.T) {
+-	client := Client{}
+-	out := stdoutMock{bytes.NewBufferString("")}
+-	err := client.ExportContainer(ExportContainerOptions{OutputStream: out})
+-	e, ok := err.(*NoSuchContainer)
+-	if !ok {
+-		t.Errorf("ExportContainer: wrong error. Want NoSuchContainer. Got %#v.", e)
+-	}
+-	if e.ID != "" {
+-		t.Errorf("ExportContainer: wrong ID. Want %q. Got %q", "", e.ID)
+-	}
+-}
+-
+-func TestCopyFromContainer(t *testing.T) {
+-	content := "File content"
+-	out := stdoutMock{bytes.NewBufferString(content)}
+-	client := newTestClient(&FakeRoundTripper{status: http.StatusOK})
+-	opts := CopyFromContainerOptions{
+-		Container:    "a123456",
+-		OutputStream: out,
+-	}
+-	err := client.CopyFromContainer(opts)
+-	if err != nil {
+-		t.Errorf("CopyFromContainer: caugh error %#v while copying from container, expected nil", err.Error())
+-	}
+-	if out.String() != content {
+-		t.Errorf("CopyFromContainer: wrong stdout. Want %#v. Got %#v.", content, out.String())
+-	}
+-}
+-
+-func TestCopyFromContainerEmptyContainer(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{status: http.StatusOK})
+-	err := client.CopyFromContainer(CopyFromContainerOptions{})
+-	_, ok := err.(*NoSuchContainer)
+-	if !ok {
+-		t.Errorf("CopyFromContainer: invalid error returned. Want NoSuchContainer, got %#v.", err)
+-	}
+-}
+-
+-func TestPassingNameOptToCreateContainerReturnsItInContainer(t *testing.T) {
+-	jsonContainer := `{
+-             "Id": "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2",
+-	     "Warnings": []
+-}`
+-	fakeRT := &FakeRoundTripper{message: jsonContainer, status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	config := Config{AttachStdout: true, AttachStdin: true}
+-	opts := CreateContainerOptions{Name: "TestCreateContainer", Config: &config}
+-	container, err := client.CreateContainer(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if container.Name != "TestCreateContainer" {
+-		t.Errorf("Container name expected to be TestCreateContainer, was %s", container.Name)
+-	}
+-}
+-
+-func TestAlwaysRestart(t *testing.T) {
+-	policy := AlwaysRestart()
+-	if policy.Name != "always" {
+-		t.Errorf("AlwaysRestart(): wrong policy name. Want %q. Got %q", "always", policy.Name)
+-	}
+-	if policy.MaximumRetryCount != 0 {
+-		t.Errorf("AlwaysRestart(): wrong MaximumRetryCount. Want 0. Got %d", policy.MaximumRetryCount)
+-	}
+-}
+-
+-func TestRestartOnFailure(t *testing.T) {
+-	const retry = 5
+-	policy := RestartOnFailure(retry)
+-	if policy.Name != "on-failure" {
+-		t.Errorf("RestartOnFailure(%d): wrong policy name. Want %q. Got %q", retry, "on-failure", policy.Name)
+-	}
+-	if policy.MaximumRetryCount != retry {
+-		t.Errorf("RestartOnFailure(%d): wrong MaximumRetryCount. Want %d. Got %d", retry, retry, policy.MaximumRetryCount)
+-	}
+-}
+-
+-func TestNeverRestart(t *testing.T) {
+-	policy := NeverRestart()
+-	if policy.Name != "no" {
+-		t.Errorf("NeverRestart(): wrong policy name. Want %q. Got %q", "always", policy.Name)
+-	}
+-	if policy.MaximumRetryCount != 0 {
+-		t.Errorf("NeverRestart(): wrong MaximumRetryCount. Want 0. Got %d", policy.MaximumRetryCount)
+-	}
+-}
+-
+-func TestTopContainer(t *testing.T) {
+-	jsonTop := `{
+-  "Processes": [
+-    [
+-      "ubuntu",
+-      "3087",
+-      "815",
+-      "0",
+-      "01:44",
+-      "?",
+-      "00:00:00",
+-      "cmd1"
+-    ],
+-    [
+-      "root",
+-      "3158",
+-      "3087",
+-      "0",
+-      "01:44",
+-      "?",
+-      "00:00:01",
+-      "cmd2"
+-    ]
+-  ],
+-  "Titles": [
+-    "UID",
+-    "PID",
+-    "PPID",
+-    "C",
+-    "STIME",
+-    "TTY",
+-    "TIME",
+-    "CMD"
+-  ]
+-}`
+-	var expected TopResult
+-	err := json.Unmarshal([]byte(jsonTop), &expected)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	id := "4fa6e0f0"
+-	fakeRT := &FakeRoundTripper{message: jsonTop, status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	processes, err := client.TopContainer(id, "")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !reflect.DeepEqual(processes, expected) {
+-		t.Errorf("TopContainer: Expected %#v. Got %#v.", expected, processes)
+-	}
+-	if len(processes.Processes) != 2 || len(processes.Processes[0]) != 8 ||
+-		processes.Processes[0][7] != "cmd1" {
+-		t.Errorf("TopContainer: Process list to include cmd1. Got %#v.", expected, processes)
+-	}
+-	expectedURI := "/containers/" + id + "/top"
+-	if !strings.HasSuffix(fakeRT.requests[0].URL.String(), expectedURI) {
+-		t.Errorf("TopContainer: Expected URI to have %q. Got %q.", expectedURI, fakeRT.requests[0].URL.String())
+-	}
+-}
+-
+-func TestTopContainerNotFound(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
+-	_, err := client.TopContainer("abef348", "")
+-	expected := &NoSuchContainer{ID: "abef348"}
+-	if !reflect.DeepEqual(err, expected) {
+-		t.Errorf("StopContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
+-	}
+-}
+-
+-func TestTopContainerWithPsArgs(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "no such container", status: http.StatusNotFound}
+-	client := newTestClient(fakeRT)
+-	client.TopContainer("abef348", "aux")
+-	expectedURI := "/containers/abef348/top?ps_args=aux"
+-	if !strings.HasSuffix(fakeRT.requests[0].URL.String(), expectedURI) {
+-		t.Errorf("TopContainer: Expected URI to have %q. Got %q.", expectedURI, fakeRT.requests[0].URL.String())
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/env.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/env.go
+deleted file mode 100644
+index c54b0b0..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/env.go
++++ /dev/null
+@@ -1,168 +0,0 @@
+-// Copyright 2014 Docker authors. All rights reserved.
+-// Use of this source code is governed by a BSD-style
+-// license that can be found in the DOCKER-LICENSE file.
+-
+-package docker
+-
+-import (
+-	"encoding/json"
+-	"fmt"
+-	"io"
+-	"strconv"
+-	"strings"
+-)
+-
+-// Env represents a list of key-pair represented in the form KEY=VALUE.
+-type Env []string
+-
+-// Get returns the string value of the given key.
+-func (env *Env) Get(key string) (value string) {
+-	return env.Map()[key]
+-}
+-
+-// Exists checks whether the given key is defined in the internal Env
+-// representation.
+-func (env *Env) Exists(key string) bool {
+-	_, exists := env.Map()[key]
+-	return exists
+-}
+-
+-// GetBool returns a boolean representation of the given key. The key is false
+-// whenever its value if 0, no, false, none or an empty string. Any other value
+-// will be interpreted as true.
+-func (env *Env) GetBool(key string) (value bool) {
+-	s := strings.ToLower(strings.Trim(env.Get(key), " \t"))
+-	if s == "" || s == "0" || s == "no" || s == "false" || s == "none" {
+-		return false
+-	}
+-	return true
+-}
+-
+-// SetBool defines a boolean value to the given key.
+-func (env *Env) SetBool(key string, value bool) {
+-	if value {
+-		env.Set(key, "1")
+-	} else {
+-		env.Set(key, "0")
+-	}
+-}
+-
+-// GetInt returns the value of the provided key, converted to int.
+-//
+-// It the value cannot be represented as an integer, it returns -1.
+-func (env *Env) GetInt(key string) int {
+-	return int(env.GetInt64(key))
+-}
+-
+-// SetInt defines an integer value to the given key.
+-func (env *Env) SetInt(key string, value int) {
+-	env.Set(key, strconv.Itoa(value))
+-}
+-
+-// GetInt64 returns the value of the provided key, converted to int64.
+-//
+-// It the value cannot be represented as an integer, it returns -1.
+-func (env *Env) GetInt64(key string) int64 {
+-	s := strings.Trim(env.Get(key), " \t")
+-	val, err := strconv.ParseInt(s, 10, 64)
+-	if err != nil {
+-		return -1
+-	}
+-	return val
+-}
+-
+-// SetInt64 defines an integer (64-bit wide) value to the given key.
+-func (env *Env) SetInt64(key string, value int64) {
+-	env.Set(key, strconv.FormatInt(value, 10))
+-}
+-
+-// GetJSON unmarshals the value of the provided key in the provided iface.
+-//
+-// iface is a value that can be provided to the json.Unmarshal function.
+-func (env *Env) GetJSON(key string, iface interface{}) error {
+-	sval := env.Get(key)
+-	if sval == "" {
+-		return nil
+-	}
+-	return json.Unmarshal([]byte(sval), iface)
+-}
+-
+-// SetJSON marshals the given value to JSON format and stores it using the
+-// provided key.
+-func (env *Env) SetJSON(key string, value interface{}) error {
+-	sval, err := json.Marshal(value)
+-	if err != nil {
+-		return err
+-	}
+-	env.Set(key, string(sval))
+-	return nil
+-}
+-
+-// GetList returns a list of strings matching the provided key. It handles the
+-// list as a JSON representation of a list of strings.
+-//
+-// If the given key matches to a single string, it will return a list
+-// containing only the value that matches the key.
+-func (env *Env) GetList(key string) []string {
+-	sval := env.Get(key)
+-	if sval == "" {
+-		return nil
+-	}
+-	var l []string
+-	if err := json.Unmarshal([]byte(sval), &l); err != nil {
+-		l = append(l, sval)
+-	}
+-	return l
+-}
+-
+-// SetList stores the given list in the provided key, after serializing it to
+-// JSON format.
+-func (env *Env) SetList(key string, value []string) error {
+-	return env.SetJSON(key, value)
+-}
+-
+-// Set defines the value of a key to the given string.
+-func (env *Env) Set(key, value string) {
+-	*env = append(*env, key+"="+value)
+-}
+-
+-// Decode decodes `src` as a json dictionary, and adds each decoded key-value
+-// pair to the environment.
+-//
+-// If `src` cannot be decoded as a json dictionary, an error is returned.
+-func (env *Env) Decode(src io.Reader) error {
+-	m := make(map[string]interface{})
+-	if err := json.NewDecoder(src).Decode(&m); err != nil {
+-		return err
+-	}
+-	for k, v := range m {
+-		env.SetAuto(k, v)
+-	}
+-	return nil
+-}
+-
+-// SetAuto will try to define the Set* method to call based on the given value.
+-func (env *Env) SetAuto(key string, value interface{}) {
+-	if fval, ok := value.(float64); ok {
+-		env.SetInt64(key, int64(fval))
+-	} else if sval, ok := value.(string); ok {
+-		env.Set(key, sval)
+-	} else if val, err := json.Marshal(value); err == nil {
+-		env.Set(key, string(val))
+-	} else {
+-		env.Set(key, fmt.Sprintf("%v", value))
+-	}
+-}
+-
+-// Map returns the map representation of the env.
+-func (env *Env) Map() map[string]string {
+-	if len(*env) == 0 {
+-		return nil
+-	}
+-	m := make(map[string]string)
+-	for _, kv := range *env {
+-		parts := strings.SplitN(kv, "=", 2)
+-		m[parts[0]] = parts[1]
+-	}
+-	return m
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/env_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/env_test.go
+deleted file mode 100644
+index 6d03d7b..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/env_test.go
++++ /dev/null
+@@ -1,349 +0,0 @@
+-// Copyright 2014 go-dockerclient authors. All rights reserved.
+-// Use of this source code is governed by a BSD-style
+-// license that can be found in the DOCKER-LICENSE file.
+-
+-package docker
+-
+-import (
+-	"bytes"
+-	"errors"
+-	"reflect"
+-	"sort"
+-	"testing"
+-)
+-
+-func TestGet(t *testing.T) {
+-	var tests = []struct {
+-		input    []string
+-		query    string
+-		expected string
+-	}{
+-		{[]string{"PATH=/usr/bin:/bin", "PYTHONPATH=/usr/local"}, "PATH", "/usr/bin:/bin"},
+-		{[]string{"PATH=/usr/bin:/bin", "PYTHONPATH=/usr/local"}, "PYTHONPATH", "/usr/local"},
+-		{[]string{"PATH=/usr/bin:/bin", "PYTHONPATH=/usr/local"}, "PYTHONPATHI", ""},
+-		{[]string{"WAT="}, "WAT", ""},
+-	}
+-	for _, tt := range tests {
+-		env := Env(tt.input)
+-		got := env.Get(tt.query)
+-		if got != tt.expected {
+-			t.Errorf("Env.Get(%q): wrong result. Want %q. Got %q", tt.query, tt.expected, got)
+-		}
+-	}
+-}
+-
+-func TestExists(t *testing.T) {
+-	var tests = []struct {
+-		input    []string
+-		query    string
+-		expected bool
+-	}{
+-		{[]string{"WAT=", "PYTHONPATH=/usr/local"}, "WAT", true},
+-		{[]string{"PATH=/usr/bin:/bin", "PYTHONPATH=/usr/local"}, "PYTHONPATH", true},
+-		{[]string{"PATH=/usr/bin:/bin", "PYTHONPATH=/usr/local"}, "PYTHONPATHI", false},
+-	}
+-	for _, tt := range tests {
+-		env := Env(tt.input)
+-		got := env.Exists(tt.query)
+-		if got != tt.expected {
+-			t.Errorf("Env.Exists(%q): wrong result. Want %v. Got %v", tt.query, tt.expected, got)
+-		}
+-	}
+-}
+-
+-func TestGetBool(t *testing.T) {
+-	var tests = []struct {
+-		input    string
+-		expected bool
+-	}{
+-		{"EMTPY_VAR", false}, {"ZERO_VAR", false}, {"NO_VAR", false},
+-		{"FALSE_VAR", false}, {"NONE_VAR", false}, {"TRUE_VAR", true},
+-		{"WAT", true}, {"PATH", true}, {"ONE_VAR", true}, {"NO_VAR_TAB", false},
+-	}
+-	env := Env([]string{
+-		"EMPTY_VAR=", "ZERO_VAR=0", "NO_VAR=no", "FALSE_VAR=false",
+-		"NONE_VAR=none", "TRUE_VAR=true", "WAT=wat", "PATH=/usr/bin:/bin",
+-		"ONE_VAR=1", "NO_VAR_TAB=0 \t\t\t",
+-	})
+-	for _, tt := range tests {
+-		got := env.GetBool(tt.input)
+-		if got != tt.expected {
+-			t.Errorf("Env.GetBool(%q): wrong result. Want %v. Got %v.", tt.input, tt.expected, got)
+-		}
+-	}
+-}
+-
+-func TestSetBool(t *testing.T) {
+-	var tests = []struct {
+-		input    bool
+-		expected string
+-	}{
+-		{true, "1"}, {false, "0"},
+-	}
+-	for _, tt := range tests {
+-		var env Env
+-		env.SetBool("SOME", tt.input)
+-		if got := env.Get("SOME"); got != tt.expected {
+-			t.Errorf("Env.SetBool(%v): wrong result. Want %q. Got %q", tt.input, tt.expected, got)
+-		}
+-	}
+-}
+-
+-func TestGetInt(t *testing.T) {
+-	var tests = []struct {
+-		input    string
+-		expected int
+-	}{
+-		{"NEGATIVE_INTEGER", -10}, {"NON_INTEGER", -1}, {"ONE", 1}, {"TWO", 2},
+-	}
+-	env := Env([]string{"NEGATIVE_INTEGER=-10", "NON_INTEGER=wat", "ONE=1", "TWO=2"})
+-	for _, tt := range tests {
+-		got := env.GetInt(tt.input)
+-		if got != tt.expected {
+-			t.Errorf("Env.GetInt(%q): wrong result. Want %d. Got %d", tt.input, tt.expected, got)
+-		}
+-	}
+-}
+-
+-func TestSetInt(t *testing.T) {
+-	var tests = []struct {
+-		input    int
+-		expected string
+-	}{
+-		{10, "10"}, {13, "13"}, {7, "7"}, {33, "33"},
+-		{0, "0"}, {-34, "-34"},
+-	}
+-	for _, tt := range tests {
+-		var env Env
+-		env.SetInt("SOME", tt.input)
+-		if got := env.Get("SOME"); got != tt.expected {
+-			t.Errorf("Env.SetBool(%d): wrong result. Want %q. Got %q", tt.input, tt.expected, got)
+-		}
+-	}
+-}
+-
+-func TestGetInt64(t *testing.T) {
+-	var tests = []struct {
+-		input    string
+-		expected int64
+-	}{
+-		{"NEGATIVE_INTEGER", -10}, {"NON_INTEGER", -1}, {"ONE", 1}, {"TWO", 2},
+-	}
+-	env := Env([]string{"NEGATIVE_INTEGER=-10", "NON_INTEGER=wat", "ONE=1", "TWO=2"})
+-	for _, tt := range tests {
+-		got := env.GetInt64(tt.input)
+-		if got != tt.expected {
+-			t.Errorf("Env.GetInt64(%q): wrong result. Want %d. Got %d", tt.input, tt.expected, got)
+-		}
+-	}
+-}
+-
+-func TestSetInt64(t *testing.T) {
+-	var tests = []struct {
+-		input    int64
+-		expected string
+-	}{
+-		{10, "10"}, {13, "13"}, {7, "7"}, {33, "33"},
+-		{0, "0"}, {-34, "-34"},
+-	}
+-	for _, tt := range tests {
+-		var env Env
+-		env.SetInt64("SOME", tt.input)
+-		if got := env.Get("SOME"); got != tt.expected {
+-			t.Errorf("Env.SetBool(%d): wrong result. Want %q. Got %q", tt.input, tt.expected, got)
+-		}
+-	}
+-}
+-
+-func TestGetJSON(t *testing.T) {
+-	var p struct {
+-		Name string `json:"name"`
+-		Age  int    `json:"age"`
+-	}
+-	var env Env
+-	env.Set("person", `{"name":"Gopher","age":5}`)
+-	err := env.GetJSON("person", &p)
+-	if err != nil {
+-		t.Error(err)
+-	}
+-	if p.Name != "Gopher" {
+-		t.Errorf("Env.GetJSON(%q): wrong name. Want %q. Got %q", "person", "Gopher", p.Name)
+-	}
+-	if p.Age != 5 {
+-		t.Errorf("Env.GetJSON(%q): wrong age. Want %d. Got %d", "person", 5, p.Age)
+-	}
+-}
+-
+-func TestGetJSONAbsent(t *testing.T) {
+-	var l []string
+-	var env Env
+-	err := env.GetJSON("person", &l)
+-	if err != nil {
+-		t.Error(err)
+-	}
+-	if l != nil {
+-		t.Errorf("Env.GetJSON(): get unexpected list %v", l)
+-	}
+-}
+-
+-func TestGetJSONFailure(t *testing.T) {
+-	var p []string
+-	var env Env
+-	env.Set("list-person", `{"name":"Gopher","age":5}`)
+-	err := env.GetJSON("list-person", &p)
+-	if err == nil {
+-		t.Errorf("Env.GetJSON(%q): got unexpected <nil> error.", "list-person")
+-	}
+-}
+-
+-func TestSetJSON(t *testing.T) {
+-	var p1 = struct {
+-		Name string `json:"name"`
+-		Age  int    `json:"age"`
+-	}{Name: "Gopher", Age: 5}
+-	var env Env
+-	err := env.SetJSON("person", p1)
+-	if err != nil {
+-		t.Error(err)
+-	}
+-	var p2 struct {
+-		Name string `json:"name"`
+-		Age  int    `json:"age"`
+-	}
+-	err = env.GetJSON("person", &p2)
+-	if err != nil {
+-		t.Error(err)
+-	}
+-	if !reflect.DeepEqual(p1, p2) {
+-		t.Errorf("Env.SetJSON(%q): wrong result. Want %v. Got %v", "person", p1, p2)
+-	}
+-}
+-
+-func TestSetJSONFailure(t *testing.T) {
+-	var env Env
+-	err := env.SetJSON("person", unmarshable{})
+-	if err == nil {
+-		t.Error("Env.SetJSON(): got unexpected <nil> error")
+-	}
+-	if env.Exists("person") {
+-		t.Errorf("Env.SetJSON(): should not define the key %q, but did", "person")
+-	}
+-}
+-
+-func TestGetList(t *testing.T) {
+-	var tests = []struct {
+-		input    string
+-		expected []string
+-	}{
+-		{"WAT=wat", []string{"wat"}},
+-		{`WAT=["wat","wet","wit","wot","wut"]`, []string{"wat", "wet", "wit", "wot", "wut"}},
+-		{"WAT=", nil},
+-	}
+-	for _, tt := range tests {
+-		env := Env([]string{tt.input})
+-		got := env.GetList("WAT")
+-		if !reflect.DeepEqual(got, tt.expected) {
+-			t.Errorf("Env.GetList(%q): wrong result. Want %v. Got %v", "WAT", tt.expected, got)
+-		}
+-	}
+-}
+-
+-func TestSetList(t *testing.T) {
+-	list := []string{"a", "b", "c"}
+-	var env Env
+-	env.SetList("SOME", list)
+-	if got := env.GetList("SOME"); !reflect.DeepEqual(got, list) {
+-		t.Errorf("Env.SetList(%v): wrong result. Got %v", list, got)
+-	}
+-}
+-
+-func TestSet(t *testing.T) {
+-	var env Env
+-	env.Set("PATH", "/home/bin:/bin")
+-	env.Set("SOMETHING", "/usr/bin")
+-	env.Set("PATH", "/bin")
+-	if expected, got := "/usr/bin", env.Get("SOMETHING"); got != expected {
+-		t.Errorf("Env.Set(%q): wrong result. Want %q. Got %q", expected, expected, got)
+-	}
+-	if expected, got := "/bin", env.Get("PATH"); got != expected {
+-		t.Errorf("Env.Set(%q): wrong result. Want %q. Got %q", expected, expected, got)
+-	}
+-}
+-
+-func TestDecode(t *testing.T) {
+-	var tests = []struct {
+-		input       string
+-		expectedOut []string
+-		expectedErr string
+-	}{
+-		{
+-			`{"PATH":"/usr/bin:/bin","containers":54,"wat":["123","345"]}`,
+-			[]string{"PATH=/usr/bin:/bin", "containers=54", `wat=["123","345"]`},
+-			"",
+-		},
+-		{"}}", nil, "invalid character '}' looking for beginning of value"},
+-		{`{}`, nil, ""},
+-	}
+-	for _, tt := range tests {
+-		var env Env
+-		err := env.Decode(bytes.NewBufferString(tt.input))
+-		if tt.expectedErr == "" {
+-			if err != nil {
+-				t.Error(err)
+-			}
+-		} else if tt.expectedErr != err.Error() {
+-			t.Errorf("Env.Decode(): invalid error. Want %q. Got %q.", tt.expectedErr, err)
+-		}
+-		got := []string(env)
+-		sort.Strings(got)
+-		sort.Strings(tt.expectedOut)
+-		if !reflect.DeepEqual(got, tt.expectedOut) {
+-			t.Errorf("Env.Decode(): wrong result. Want %v. Got %v.", tt.expectedOut, got)
+-		}
+-	}
+-}
+-
+-func TestSetAuto(t *testing.T) {
+-	buf := bytes.NewBufferString("oi")
+-	var tests = []struct {
+-		input    interface{}
+-		expected string
+-	}{
+-		{10, "10"},
+-		{10.3, "10"},
+-		{"oi", "oi"},
+-		{buf, "{}"},
+-		{unmarshable{}, "{}"},
+-	}
+-	for _, tt := range tests {
+-		var env Env
+-		env.SetAuto("SOME", tt.input)
+-		if got := env.Get("SOME"); got != tt.expected {
+-			t.Errorf("Env.SetAuto(%v): wrong result. Want %q. Got %q", tt.input, tt.expected, got)
+-		}
+-	}
+-}
+-
+-func TestMap(t *testing.T) {
+-	var tests = []struct {
+-		input    []string
+-		expected map[string]string
+-	}{
+-		{[]string{"PATH=/usr/bin:/bin", "PYTHONPATH=/usr/local"}, map[string]string{"PATH": "/usr/bin:/bin", "PYTHONPATH": "/usr/local"}},
+-		{nil, nil},
+-	}
+-	for _, tt := range tests {
+-		env := Env(tt.input)
+-		got := env.Map()
+-		if !reflect.DeepEqual(got, tt.expected) {
+-			t.Errorf("Env.Map(): wrong result. Want %v. Got %v", tt.expected, got)
+-		}
+-	}
+-}
+-
+-type unmarshable struct {
+-}
+-
+-func (unmarshable) MarshalJSON() ([]byte, error) {
+-	return nil, errors.New("cannot marshal")
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/event.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/event.go
+deleted file mode 100644
+index 7c055c5..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/event.go
++++ /dev/null
+@@ -1,309 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 docker
+-
+-import (
+-	"crypto/tls"
+-	"encoding/json"
+-	"errors"
+-	"fmt"
+-	"io"
+-	"math"
+-	"net"
+-	"net/http"
+-	"net/http/httputil"
+-	"sync"
+-	"sync/atomic"
+-	"time"
+-)
+-
+-// APIEvents represents an event returned by the API.
+-type APIEvents struct {
+-	Status string `json:"Status,omitempty" yaml:"Status,omitempty"`
+-	ID     string `json:"ID,omitempty" yaml:"ID,omitempty"`
+-	From   string `json:"From,omitempty" yaml:"From,omitempty"`
+-	Time   int64  `json:"Time,omitempty" yaml:"Time,omitempty"`
+-}
+-
+-type eventMonitoringState struct {
+-	sync.RWMutex
+-	sync.WaitGroup
+-	enabled   bool
+-	lastSeen  *int64
+-	C         chan *APIEvents
+-	errC      chan error
+-	listeners []chan<- *APIEvents
+-}
+-
+-const (
+-	maxMonitorConnRetries = 5
+-	retryInitialWaitTime  = 10.
+-)
+-
+-var (
+-	// ErrNoListeners is the error returned when no listeners are available
+-	// to receive an event.
+-	ErrNoListeners = errors.New("no listeners present to receive event")
+-
+-	// ErrListenerAlreadyExists is the error returned when the listerner already
+-	// exists.
+-	ErrListenerAlreadyExists = errors.New("listener already exists for docker events")
+-
+-	// EOFEvent is sent when the event listener receives an EOF error.
+-	EOFEvent = &APIEvents{
+-		Status: "EOF",
+-	}
+-)
+-
+-// AddEventListener adds a new listener to container events in the Docker API.
+-//
+-// The parameter is a channel through which events will be sent.
+-func (c *Client) AddEventListener(listener chan<- *APIEvents) error {
+-	var err error
+-	if !c.eventMonitor.isEnabled() {
+-		err = c.eventMonitor.enableEventMonitoring(c)
+-		if err != nil {
+-			return err
+-		}
+-	}
+-	err = c.eventMonitor.addListener(listener)
+-	if err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-// RemoveEventListener removes a listener from the monitor.
+-func (c *Client) RemoveEventListener(listener chan *APIEvents) error {
+-	err := c.eventMonitor.removeListener(listener)
+-	if err != nil {
+-		return err
+-	}
+-	if len(c.eventMonitor.listeners) == 0 {
+-		err = c.eventMonitor.disableEventMonitoring()
+-		if err != nil {
+-			return err
+-		}
+-	}
+-	return nil
+-}
+-
+-func (eventState *eventMonitoringState) addListener(listener chan<- *APIEvents) error {
+-	eventState.Lock()
+-	defer eventState.Unlock()
+-	if listenerExists(listener, &eventState.listeners) {
+-		return ErrListenerAlreadyExists
+-	}
+-	eventState.Add(1)
+-	eventState.listeners = append(eventState.listeners, listener)
+-	return nil
+-}
+-
+-func (eventState *eventMonitoringState) removeListener(listener chan<- *APIEvents) error {
+-	eventState.Lock()
+-	defer eventState.Unlock()
+-	if listenerExists(listener, &eventState.listeners) {
+-		var newListeners []chan<- *APIEvents
+-		for _, l := range eventState.listeners {
+-			if l != listener {
+-				newListeners = append(newListeners, l)
+-			}
+-		}
+-		eventState.listeners = newListeners
+-		eventState.Add(-1)
+-	}
+-	return nil
+-}
+-
+-func (eventState *eventMonitoringState) closeListeners() {
+-	eventState.Lock()
+-	defer eventState.Unlock()
+-	for _, l := range eventState.listeners {
+-		close(l)
+-		eventState.Add(-1)
+-	}
+-	eventState.listeners = nil
+-}
+-
+-func listenerExists(a chan<- *APIEvents, list *[]chan<- *APIEvents) bool {
+-	for _, b := range *list {
+-		if b == a {
+-			return true
+-		}
+-	}
+-	return false
+-}
+-
+-func (eventState *eventMonitoringState) enableEventMonitoring(c *Client) error {
+-	eventState.Lock()
+-	defer eventState.Unlock()
+-	if !eventState.enabled {
+-		eventState.enabled = true
+-		var lastSeenDefault = int64(0)
+-		eventState.lastSeen = &lastSeenDefault
+-		eventState.C = make(chan *APIEvents, 100)
+-		eventState.errC = make(chan error, 1)
+-		go eventState.monitorEvents(c)
+-	}
+-	return nil
+-}
+-
+-func (eventState *eventMonitoringState) disableEventMonitoring() error {
+-	eventState.Wait()
+-	eventState.Lock()
+-	defer eventState.Unlock()
+-	if eventState.enabled {
+-		eventState.enabled = false
+-		close(eventState.C)
+-		close(eventState.errC)
+-	}
+-	return nil
+-}
+-
+-func (eventState *eventMonitoringState) monitorEvents(c *Client) {
+-	var err error
+-	for eventState.noListeners() {
+-		time.Sleep(10 * time.Millisecond)
+-	}
+-	if err = eventState.connectWithRetry(c); err != nil {
+-		eventState.terminate()
+-	}
+-	for eventState.isEnabled() {
+-		timeout := time.After(100 * time.Millisecond)
+-		select {
+-		case ev, ok := <-eventState.C:
+-			if !ok {
+-				return
+-			}
+-			if ev == EOFEvent {
+-				eventState.closeListeners()
+-				eventState.terminate()
+-				return
+-			}
+-			go eventState.sendEvent(ev)
+-			go eventState.updateLastSeen(ev)
+-		case err = <-eventState.errC:
+-			if err == ErrNoListeners {
+-				eventState.terminate()
+-				return
+-			} else if err != nil {
+-				defer func() { go eventState.monitorEvents(c) }()
+-				return
+-			}
+-		case <-timeout:
+-			continue
+-		}
+-	}
+-}
+-
+-func (eventState *eventMonitoringState) connectWithRetry(c *Client) error {
+-	var retries int
+-	var err error
+-	for err = c.eventHijack(atomic.LoadInt64(eventState.lastSeen), eventState.C, eventState.errC); err != nil && retries < maxMonitorConnRetries; retries++ {
+-		waitTime := int64(retryInitialWaitTime * math.Pow(2, float64(retries)))
+-		time.Sleep(time.Duration(waitTime) * time.Millisecond)
+-		err = c.eventHijack(atomic.LoadInt64(eventState.lastSeen), eventState.C, eventState.errC)
+-	}
+-	return err
+-}
+-
+-func (eventState *eventMonitoringState) noListeners() bool {
+-	eventState.RLock()
+-	defer eventState.RUnlock()
+-	return len(eventState.listeners) == 0
+-}
+-
+-func (eventState *eventMonitoringState) isEnabled() bool {
+-	eventState.RLock()
+-	defer eventState.RUnlock()
+-	return eventState.enabled
+-}
+-
+-func (eventState *eventMonitoringState) sendEvent(event *APIEvents) {
+-	eventState.RLock()
+-	defer eventState.RUnlock()
+-	eventState.Add(1)
+-	defer eventState.Done()
+-	if eventState.isEnabled() {
+-		if eventState.noListeners() {
+-			eventState.errC <- ErrNoListeners
+-			return
+-		}
+-
+-		for _, listener := range eventState.listeners {
+-			listener <- event
+-		}
+-	}
+-}
+-
+-func (eventState *eventMonitoringState) updateLastSeen(e *APIEvents) {
+-	eventState.Lock()
+-	defer eventState.Unlock()
+-	if atomic.LoadInt64(eventState.lastSeen) < e.Time {
+-		atomic.StoreInt64(eventState.lastSeen, e.Time)
+-	}
+-}
+-
+-func (eventState *eventMonitoringState) terminate() {
+-	eventState.disableEventMonitoring()
+-}
+-
+-func (c *Client) eventHijack(startTime int64, eventChan chan *APIEvents, errChan chan error) error {
+-	uri := "/events"
+-	if startTime != 0 {
+-		uri += fmt.Sprintf("?since=%d", startTime)
+-	}
+-	protocol := c.endpointURL.Scheme
+-	address := c.endpointURL.Path
+-	if protocol != "unix" {
+-		protocol = "tcp"
+-		address = c.endpointURL.Host
+-	}
+-	var dial net.Conn
+-	var err error
+-	if c.TLSConfig == nil {
+-		dial, err = net.Dial(protocol, address)
+-	} else {
+-		dial, err = tls.Dial(protocol, address, c.TLSConfig)
+-	}
+-	if err != nil {
+-		return err
+-	}
+-	conn := httputil.NewClientConn(dial, nil)
+-	req, err := http.NewRequest("GET", uri, nil)
+-	if err != nil {
+-		return err
+-	}
+-	res, err := conn.Do(req)
+-	if err != nil {
+-		return err
+-	}
+-	go func(res *http.Response, conn *httputil.ClientConn) {
+-		defer conn.Close()
+-		defer res.Body.Close()
+-		decoder := json.NewDecoder(res.Body)
+-		for {
+-			var event APIEvents
+-			if err = decoder.Decode(&event); err != nil {
+-				if err == io.EOF || err == io.ErrUnexpectedEOF {
+-					if c.eventMonitor.isEnabled() {
+-						// Signal that we're exiting.
+-						eventChan <- EOFEvent
+-					}
+-					break
+-				}
+-				errChan <- err
+-			}
+-			if event.Time == 0 {
+-				continue
+-			}
+-			if !c.eventMonitor.isEnabled() {
+-				return
+-			}
+-			eventChan <- &event
+-		}
+-	}(res, conn)
+-	return nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/event_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/event_test.go
+deleted file mode 100644
+index 0de0474..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/event_test.go
++++ /dev/null
+@@ -1,129 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 docker
+-
+-import (
+-	"bufio"
+-	"crypto/tls"
+-	"crypto/x509"
+-	"fmt"
+-	"io/ioutil"
+-	"net/http"
+-	"net/http/httptest"
+-	"strings"
+-	"testing"
+-	"time"
+-)
+-
+-func TestEventListeners(t *testing.T) {
+-	testEventListeners("TestEventListeners", t, httptest.NewServer, NewClient)
+-}
+-
+-func TestTLSEventListeners(t *testing.T) {
+-	testEventListeners("TestTLSEventListeners", t, func(handler http.Handler) *httptest.Server {
+-		server := httptest.NewUnstartedServer(handler)
+-
+-		cert, err := tls.LoadX509KeyPair("testing/data/server.pem", "testing/data/serverkey.pem")
+-		if err != nil {
+-			t.Fatalf("Error loading server key pair: %s", err)
+-		}
+-
+-		caCert, err := ioutil.ReadFile("testing/data/ca.pem")
+-		if err != nil {
+-			t.Fatalf("Error loading ca certificate: %s", err)
+-		}
+-		caPool := x509.NewCertPool()
+-		if !caPool.AppendCertsFromPEM(caCert) {
+-			t.Fatalf("Could not add ca certificate")
+-		}
+-
+-		server.TLS = &tls.Config{
+-			Certificates: []tls.Certificate{cert},
+-			RootCAs:      caPool,
+-		}
+-		server.StartTLS()
+-		return server
+-	}, func(url string) (*Client, error) {
+-		return NewTLSClient(url, "testing/data/cert.pem", "testing/data/key.pem", "testing/data/ca.pem")
+-	})
+-}
+-
+-func testEventListeners(testName string, t *testing.T, buildServer func(http.Handler) *httptest.Server, buildClient func(string) (*Client, error)) {
+-	response := `{"status":"create","id":"dfdf82bd3881","from":"base:latest","time":1374067924}
+-{"status":"start","id":"dfdf82bd3881","from":"base:latest","time":1374067924}
+-{"status":"stop","id":"dfdf82bd3881","from":"base:latest","time":1374067966}
+-{"status":"destroy","id":"dfdf82bd3881","from":"base:latest","time":1374067970}
+-`
+-
+-	var req http.Request
+-	server := buildServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+-		rsc := bufio.NewScanner(strings.NewReader(response))
+-		for rsc.Scan() {
+-			w.Write([]byte(rsc.Text()))
+-			w.(http.Flusher).Flush()
+-			time.Sleep(10 * time.Millisecond)
+-		}
+-		req = *r
+-	}))
+-	defer server.Close()
+-
+-	client, err := buildClient(server.URL)
+-	if err != nil {
+-		t.Errorf("Failed to create client: %s", err)
+-	}
+-	client.SkipServerVersionCheck = true
+-
+-	listener := make(chan *APIEvents, 10)
+-	defer func() { time.Sleep(10 * time.Millisecond); client.RemoveEventListener(listener) }()
+-
+-	err = client.AddEventListener(listener)
+-	if err != nil {
+-		t.Errorf("Failed to add event listener: %s", err)
+-	}
+-
+-	timeout := time.After(1 * time.Second)
+-	var count int
+-
+-	for {
+-		select {
+-		case msg := <-listener:
+-			t.Logf("Received: %s", *msg)
+-			count++
+-			err = checkEvent(count, msg)
+-			if err != nil {
+-				t.Fatalf("Check event failed: %s", err)
+-			}
+-			if count == 4 {
+-				return
+-			}
+-		case <-timeout:
+-			t.Fatalf("%s timed out waiting on events", testName)
+-		}
+-	}
+-}
+-
+-func checkEvent(index int, event *APIEvents) error {
+-	if event.ID != "dfdf82bd3881" {
+-		return fmt.Errorf("event ID did not match. Expected dfdf82bd3881 got %s", event.ID)
+-	}
+-	if event.From != "base:latest" {
+-		return fmt.Errorf("event from did not match. Expected base:latest got %s", event.From)
+-	}
+-	var status string
+-	switch index {
+-	case 1:
+-		status = "create"
+-	case 2:
+-		status = "start"
+-	case 3:
+-		status = "stop"
+-	case 4:
+-		status = "destroy"
+-	}
+-	if event.Status != status {
+-		return fmt.Errorf("event status did not match. Expected %s got %s", status, event.Status)
+-	}
+-	return nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/example_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/example_test.go
+deleted file mode 100644
+index 8c2c719..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/example_test.go
++++ /dev/null
+@@ -1,168 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 docker_test
+-
+-import (
+-	"archive/tar"
+-	"bytes"
+-	"fmt"
+-	"io"
+-	"log"
+-	"time"
+-
+-	"github.com/fsouza/go-dockerclient"
+-)
+-
+-func ExampleClient_AttachToContainer() {
+-	client, err := docker.NewClient("http://localhost:4243")
+-	if err != nil {
+-		log.Fatal(err)
+-	}
+-	client.SkipServerVersionCheck = true
+-	// Reading logs from container a84849 and sending them to buf.
+-	var buf bytes.Buffer
+-	err = client.AttachToContainer(docker.AttachToContainerOptions{
+-		Container:    "a84849",
+-		OutputStream: &buf,
+-		Logs:         true,
+-		Stdout:       true,
+-		Stderr:       true,
+-	})
+-	if err != nil {
+-		log.Fatal(err)
+-	}
+-	log.Println(buf.String())
+-	buf.Reset()
+-	err = client.AttachToContainer(docker.AttachToContainerOptions{
+-		Container:    "a84849",
+-		OutputStream: &buf,
+-		Stdout:       true,
+-		Stream:       true,
+-	})
+-	if err != nil {
+-		log.Fatal(err)
+-	}
+-	log.Println(buf.String())
+-}
+-
+-func ExampleClient_CopyFromContainer() {
+-	client, err := docker.NewClient("http://localhost:4243")
+-	if err != nil {
+-		log.Fatal(err)
+-	}
+-	cid := "a84849"
+-	var buf bytes.Buffer
+-	filename := "/tmp/output.txt"
+-	err = client.CopyFromContainer(docker.CopyFromContainerOptions{
+-		Container:    cid,
+-		Resource:     filename,
+-		OutputStream: &buf,
+-	})
+-	if err != nil {
+-		log.Fatalf("Error while copying from %s: %s\n", cid, err)
+-	}
+-	content := new(bytes.Buffer)
+-	r := bytes.NewReader(buf.Bytes())
+-	tr := tar.NewReader(r)
+-	tr.Next()
+-	if err != nil && err != io.EOF {
+-		log.Fatal(err)
+-	}
+-	if _, err := io.Copy(content, tr); err != nil {
+-		log.Fatal(err)
+-	}
+-	log.Println(buf.String())
+-}
+-
+-func ExampleClient_BuildImage() {
+-	client, err := docker.NewClient("http://localhost:4243")
+-	if err != nil {
+-		log.Fatal(err)
+-	}
+-
+-	t := time.Now()
+-	inputbuf, outputbuf := bytes.NewBuffer(nil), bytes.NewBuffer(nil)
+-	tr := tar.NewWriter(inputbuf)
+-	tr.WriteHeader(&tar.Header{Name: "Dockerfile", Size: 10, ModTime: t, AccessTime: t, ChangeTime: t})
+-	tr.Write([]byte("FROM base\n"))
+-	tr.Close()
+-	opts := docker.BuildImageOptions{
+-		Name:         "test",
+-		InputStream:  inputbuf,
+-		OutputStream: outputbuf,
+-	}
+-	if err := client.BuildImage(opts); err != nil {
+-		log.Fatal(err)
+-	}
+-}
+-
+-func ExampleClient_ListenEvents() {
+-	client, err := docker.NewClient("http://localhost:4243")
+-	if err != nil {
+-		log.Fatal(err)
+-	}
+-
+-	listener := make(chan *docker.APIEvents)
+-	err = client.AddEventListener(listener)
+-	if err != nil {
+-		log.Fatal(err)
+-	}
+-
+-	defer func() {
+-
+-		err = client.RemoveEventListener(listener)
+-		if err != nil {
+-			log.Fatal(err)
+-		}
+-
+-	}()
+-
+-	timeout := time.After(1 * time.Second)
+-
+-	for {
+-		select {
+-		case msg := <-listener:
+-			log.Println(msg)
+-		case <-timeout:
+-			break
+-		}
+-	}
+-
+-}
+-
+-func ExampleEnv_Map() {
+-	e := docker.Env([]string{"A=1", "B=2", "C=3"})
+-	envs := e.Map()
+-	for k, v := range envs {
+-		fmt.Printf("%s=%q\n", k, v)
+-	}
+-}
+-
+-func ExampleEnv_SetJSON() {
+-	type Person struct {
+-		Name string
+-		Age  int
+-	}
+-	p := Person{Name: "Gopher", Age: 4}
+-	var e docker.Env
+-	err := e.SetJSON("person", p)
+-	if err != nil {
+-		log.Fatal(err)
+-	}
+-}
+-
+-func ExampleEnv_GetJSON() {
+-	type Person struct {
+-		Name string
+-		Age  int
+-	}
+-	p := Person{Name: "Gopher", Age: 4}
+-	var e docker.Env
+-	e.Set("person", `{"name":"Gopher","age":4}`)
+-	err := e.GetJSON("person", &p)
+-	if err != nil {
+-		log.Fatal(err)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/exec.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/exec.go
+deleted file mode 100644
+index 9ce7b44..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/exec.go
++++ /dev/null
+@@ -1,129 +0,0 @@
+-// Copyright 2014 go-dockerclient authors. All rights reserved.
+-// Use of this source code is governed by a BSD-style
+-// license that can be found in the LICENSE file.
+-
+-// Docs can currently be found at https://github.com/docker/docker/blob/master/docs/sources/reference/api/docker_remote_api_v1.15.md#exec-create
+-
+-package docker
+-
+-import (
+-	"encoding/json"
+-	"fmt"
+-	"io"
+-	"net/http"
+-	"net/url"
+-	"strconv"
+-)
+-
+-// CreateExecOptions specify parameters to the CreateExecContainer function.
+-//
+-// See http://goo.gl/8izrzI for more details
+-type CreateExecOptions struct {
+-	AttachStdin  bool     `json:"AttachStdin,omitempty" yaml:"AttachStdin,omitempty"`
+-	AttachStdout bool     `json:"AttachStdout,omitempty" yaml:"AttachStdout,omitempty"`
+-	AttachStderr bool     `json:"AttachStderr,omitempty" yaml:"AttachStderr,omitempty"`
+-	Tty          bool     `json:"Tty,omitempty" yaml:"Tty,omitempty"`
+-	Cmd          []string `json:"Cmd,omitempty" yaml:"Cmd,omitempty"`
+-	Container    string   `json:"Container,omitempty" yaml:"Container,omitempty"`
+-}
+-
+-// StartExecOptions specify parameters to the StartExecContainer function.
+-//
+-// See http://goo.gl/JW8Lxl for more details
+-type StartExecOptions struct {
+-	Detach bool `json:"Detach,omitempty" yaml:"Detach,omitempty"`
+-
+-	Tty bool `json:"Tty,omitempty" yaml:"Tty,omitempty"`
+-
+-	InputStream  io.Reader `qs:"-"`
+-	OutputStream io.Writer `qs:"-"`
+-	ErrorStream  io.Writer `qs:"-"`
+-
+-	// Use raw terminal? Usually true when the container contains a TTY.
+-	RawTerminal bool `qs:"-"`
+-
+-	// If set, after a successful connect, a sentinel will be sent and then the
+-	// client will block on receive before continuing.
+-	//
+-	// It must be an unbuffered channel. Using a buffered channel can lead
+-	// to unexpected behavior.
+-	Success chan struct{} `json:"-"`
+-}
+-
+-// Exec is the type representing a `docker exec` instance and containing the
+-// instance ID
+-type Exec struct {
+-	ID string `json:"Id,omitempty" yaml:"Id,omitempty"`
+-}
+-
+-// CreateExec sets up an exec instance in a running container `id`, returning the exec
+-// instance, or an error in case of failure.
+-//
+-// See http://goo.gl/8izrzI for more details
+-func (c *Client) CreateExec(opts CreateExecOptions) (*Exec, error) {
+-	path := fmt.Sprintf("/containers/%s/exec", opts.Container)
+-	body, status, err := c.do("POST", path, opts)
+-	if status == http.StatusNotFound {
+-		return nil, &NoSuchContainer{ID: opts.Container}
+-	}
+-	if err != nil {
+-		return nil, err
+-	}
+-	var exec Exec
+-	err = json.Unmarshal(body, &exec)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	return &exec, nil
+-}
+-
+-// StartExec starts a previously set up exec instance id. If opts.Detach is
+-// true, it returns after starting the exec command. Otherwise, it sets up an
+-// interactive session with the exec command.
+-//
+-// See http://goo.gl/JW8Lxl for more details
+-func (c *Client) StartExec(id string, opts StartExecOptions) error {
+-	if id == "" {
+-		return &NoSuchExec{ID: id}
+-	}
+-
+-	path := fmt.Sprintf("/exec/%s/start", id)
+-
+-	if opts.Detach {
+-		_, status, err := c.do("POST", path, opts)
+-		if status == http.StatusNotFound {
+-			return &NoSuchExec{ID: id}
+-		}
+-		if err != nil {
+-			return err
+-		}
+-		return nil
+-	}
+-
+-	return c.hijack("POST", path, opts.Success, opts.RawTerminal, opts.InputStream, opts.ErrorStream, opts.OutputStream, opts)
+-}
+-
+-// ResizeExecTTY resizes the tty session used by the exec command id. This API
+-// is valid only if Tty was specified as part of creating and starting the exec
+-// command.
+-//
+-// See http://goo.gl/YDSx1f for more details
+-func (c *Client) ResizeExecTTY(id string, height, width int) error {
+-	params := make(url.Values)
+-	params.Set("h", strconv.Itoa(height))
+-	params.Set("w", strconv.Itoa(width))
+-
+-	path := fmt.Sprintf("/exec/%s/resize?%s", id, params.Encode())
+-	_, _, err := c.do("POST", path, nil)
+-	return err
+-}
+-
+-// NoSuchExec is the error returned when a given exec instance does not exist.
+-type NoSuchExec struct {
+-	ID string
+-}
+-
+-func (err *NoSuchExec) Error() string {
+-	return "No such exec instance: " + err.ID
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/exec_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/exec_test.go
+deleted file mode 100644
+index 31de162..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/exec_test.go
++++ /dev/null
+@@ -1,128 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 docker
+-
+-import (
+-	"bytes"
+-	"encoding/json"
+-	"net/http"
+-	"net/http/httptest"
+-	"net/url"
+-	"strings"
+-	"testing"
+-)
+-
+-func TestExecCreate(t *testing.T) {
+-	jsonContainer := `{"Id": "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"}`
+-	var expected struct{ ID string }
+-	err := json.Unmarshal([]byte(jsonContainer), &expected)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	fakeRT := &FakeRoundTripper{message: jsonContainer, status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	config := CreateExecOptions{
+-		Container:    "test",
+-		AttachStdin:  true,
+-		AttachStdout: true,
+-		AttachStderr: false,
+-		Tty:          false,
+-		Cmd:          []string{"touch", "/tmp/file"},
+-	}
+-	execObj, err := client.CreateExec(config)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	expectedID := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
+-	if execObj.ID != expectedID {
+-		t.Errorf("ExecCreate: wrong ID. Want %q. Got %q.", expectedID, execObj.ID)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "POST" {
+-		t.Errorf("ExecCreate: wrong HTTP method. Want %q. Got %q.", "POST", req.Method)
+-	}
+-	expectedURL, _ := url.Parse(client.getURL("/containers/test/exec"))
+-	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
+-		t.Errorf("ExecCreate: Wrong path in request. Want %q. Got %q.", expectedURL.Path, gotPath)
+-	}
+-	var gotBody struct{ ID string }
+-	err = json.NewDecoder(req.Body).Decode(&gotBody)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-}
+-
+-func TestExecStartDetached(t *testing.T) {
+-	execID := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
+-	fakeRT := &FakeRoundTripper{status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	config := StartExecOptions{
+-		Detach: true,
+-	}
+-	err := client.StartExec(execID, config)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "POST" {
+-		t.Errorf("ExecStart: wrong HTTP method. Want %q. Got %q.", "POST", req.Method)
+-	}
+-	expectedURL, _ := url.Parse(client.getURL("/exec/" + execID + "/start"))
+-	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
+-		t.Errorf("ExecCreate: Wrong path in request. Want %q. Got %q.", expectedURL.Path, gotPath)
+-	}
+-	t.Log(req.Body)
+-	var gotBody struct{ Detach bool }
+-	err = json.NewDecoder(req.Body).Decode(&gotBody)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !gotBody.Detach {
+-		t.Fatal("Expected Detach in StartExecOptions to be true")
+-	}
+-}
+-
+-func TestExecStartAndAttach(t *testing.T) {
+-	var reader = strings.NewReader("send value")
+-	var req http.Request
+-	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+-		w.Write([]byte{1, 0, 0, 0, 0, 0, 0, 5})
+-		w.Write([]byte("hello"))
+-		req = *r
+-	}))
+-	defer server.Close()
+-	client, _ := NewClient(server.URL)
+-	client.SkipServerVersionCheck = true
+-	var stdout, stderr bytes.Buffer
+-	success := make(chan struct{})
+-	execID := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
+-	opts := StartExecOptions{
+-		OutputStream: &stdout,
+-		ErrorStream:  &stderr,
+-		InputStream:  reader,
+-		RawTerminal:  true,
+-		Success:      success,
+-	}
+-	go client.StartExec(execID, opts)
+-	<-success
+-}
+-
+-func TestExecResize(t *testing.T) {
+-	execID := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
+-	fakeRT := &FakeRoundTripper{status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	err := client.ResizeExecTTY(execID, 10, 20)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "POST" {
+-		t.Errorf("ExecStart: wrong HTTP method. Want %q. Got %q.", "POST", req.Method)
+-	}
+-	expectedURL, _ := url.Parse(client.getURL("/exec/" + execID + "/resize?h=10&w=20"))
+-	if gotPath := req.URL.RequestURI(); gotPath != expectedURL.RequestURI() {
+-		t.Errorf("ExecCreate: Wrong path in request. Want %q. Got %q.", expectedURL.Path, gotPath)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/image.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/image.go
+deleted file mode 100644
+index 3d55155..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/image.go
++++ /dev/null
+@@ -1,458 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 docker
+-
+-import (
+-	"bytes"
+-	"encoding/base64"
+-	"encoding/json"
+-	"errors"
+-	"fmt"
+-	"io"
+-	"io/ioutil"
+-	"net/http"
+-	"net/url"
+-	"os"
+-	"time"
+-)
+-
+-// APIImages represent an image returned in the ListImages call.
+-type APIImages struct {
+-	ID          string   `json:"Id" yaml:"Id"`
+-	RepoTags    []string `json:"RepoTags,omitempty" yaml:"RepoTags,omitempty"`
+-	Created     int64    `json:"Created,omitempty" yaml:"Created,omitempty"`
+-	Size        int64    `json:"Size,omitempty" yaml:"Size,omitempty"`
+-	VirtualSize int64    `json:"VirtualSize,omitempty" yaml:"VirtualSize,omitempty"`
+-	ParentID    string   `json:"ParentId,omitempty" yaml:"ParentId,omitempty"`
+-}
+-
+-// Image is the type representing a docker image and its various properties
+-type Image struct {
+-	ID              string    `json:"Id" yaml:"Id"`
+-	Parent          string    `json:"Parent,omitempty" yaml:"Parent,omitempty"`
+-	Comment         string    `json:"Comment,omitempty" yaml:"Comment,omitempty"`
+-	Created         time.Time `json:"Created,omitempty" yaml:"Created,omitempty"`
+-	Container       string    `json:"Container,omitempty" yaml:"Container,omitempty"`
+-	ContainerConfig Config    `json:"ContainerConfig,omitempty" yaml:"ContainerConfig,omitempty"`
+-	DockerVersion   string    `json:"DockerVersion,omitempty" yaml:"DockerVersion,omitempty"`
+-	Author          string    `json:"Author,omitempty" yaml:"Author,omitempty"`
+-	Config          *Config   `json:"Config,omitempty" yaml:"Config,omitempty"`
+-	Architecture    string    `json:"Architecture,omitempty" yaml:"Architecture,omitempty"`
+-	Size            int64     `json:"Size,omitempty" yaml:"Size,omitempty"`
+-}
+-
+-// ImageHistory represent a layer in an image's history returned by the
+-// ImageHistory call.
+-type ImageHistory struct {
+-	ID        string   `json:"Id" yaml:"Id"`
+-	Tags      []string `json:"Tags,omitempty" yaml:"Tags,omitempty"`
+-	Created   int64    `json:"Created,omitempty" yaml:"Created,omitempty"`
+-	CreatedBy string   `json:"CreatedBy,omitempty" yaml:"CreatedBy,omitempty"`
+-	Size      int64    `json:"Size,omitempty" yaml:"Size,omitempty"`
+-}
+-
+-// ImagePre012 serves the same purpose as the Image type except that it is for
+-// earlier versions of the Docker API (pre-012 to be specific)
+-type ImagePre012 struct {
+-	ID              string    `json:"id"`
+-	Parent          string    `json:"parent,omitempty"`
+-	Comment         string    `json:"comment,omitempty"`
+-	Created         time.Time `json:"created"`
+-	Container       string    `json:"container,omitempty"`
+-	ContainerConfig Config    `json:"container_config,omitempty"`
+-	DockerVersion   string    `json:"docker_version,omitempty"`
+-	Author          string    `json:"author,omitempty"`
+-	Config          *Config   `json:"config,omitempty"`
+-	Architecture    string    `json:"architecture,omitempty"`
+-	Size            int64     `json:"size,omitempty"`
+-}
+-
+-// ListImagesOptions specify parameters to the ListImages function.
+-//
+-// See http://goo.gl/2rOLFF for more details.
+-type ListImagesOptions struct {
+-	All     bool
+-	Filters map[string][]string
+-}
+-
+-var (
+-	// ErrNoSuchImage is the error returned when the image does not exist.
+-	ErrNoSuchImage = errors.New("no such image")
+-
+-	// ErrMissingRepo is the error returned when the remote repository is
+-	// missing.
+-	ErrMissingRepo = errors.New("missing remote repository e.g. 'github.com/user/repo'")
+-
+-	// ErrMissingOutputStream is the error returned when no output stream
+-	// is provided to some calls, like BuildImage.
+-	ErrMissingOutputStream = errors.New("missing output stream")
+-
+-	// ErrMultipleContexts is the error returned when both a ContextDir and
+-	// InputStream are provided in BuildImageOptions
+-	ErrMultipleContexts = errors.New("image build may not be provided BOTH context dir and input stream")
+-)
+-
+-// ListImages returns the list of available images in the server.
+-//
+-// See http://goo.gl/2rOLFF for more details.
+-func (c *Client) ListImages(opts ListImagesOptions) ([]APIImages, error) {
+-	path := "/images/json?" + queryString(opts)
+-	body, _, err := c.do("GET", path, nil)
+-	if err != nil {
+-		return nil, err
+-	}
+-	var images []APIImages
+-	err = json.Unmarshal(body, &images)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return images, nil
+-}
+-
+-// ImageHistory returns the history of the image by its name or ID.
+-//
+-// See http://goo.gl/2oJmNs for more details.
+-func (c *Client) ImageHistory(name string) ([]ImageHistory, error) {
+-	body, status, err := c.do("GET", "/images/"+name+"/history", nil)
+-	if status == http.StatusNotFound {
+-		return nil, ErrNoSuchImage
+-	}
+-	if err != nil {
+-		return nil, err
+-	}
+-	var history []ImageHistory
+-	err = json.Unmarshal(body, &history)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return history, nil
+-}
+-
+-// RemoveImage removes an image by its name or ID.
+-//
+-// See http://goo.gl/znj0wM for more details.
+-func (c *Client) RemoveImage(name string) error {
+-	_, status, err := c.do("DELETE", "/images/"+name, nil)
+-	if status == http.StatusNotFound {
+-		return ErrNoSuchImage
+-	}
+-	return err
+-}
+-
+-// InspectImage returns an image by its name or ID.
+-//
+-// See http://goo.gl/Q112NY for more details.
+-func (c *Client) InspectImage(name string) (*Image, error) {
+-	body, status, err := c.do("GET", "/images/"+name+"/json", nil)
+-	if status == http.StatusNotFound {
+-		return nil, ErrNoSuchImage
+-	}
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	var image Image
+-
+-	// if the caller elected to skip checking the server's version, assume it's the latest
+-	if c.SkipServerVersionCheck || c.expectedAPIVersion.GreaterThanOrEqualTo(apiVersion1_12) {
+-		err = json.Unmarshal(body, &image)
+-		if err != nil {
+-			return nil, err
+-		}
+-	} else {
+-		var imagePre012 ImagePre012
+-		err = json.Unmarshal(body, &imagePre012)
+-		if err != nil {
+-			return nil, err
+-		}
+-
+-		image.ID = imagePre012.ID
+-		image.Parent = imagePre012.Parent
+-		image.Comment = imagePre012.Comment
+-		image.Created = imagePre012.Created
+-		image.Container = imagePre012.Container
+-		image.ContainerConfig = imagePre012.ContainerConfig
+-		image.DockerVersion = imagePre012.DockerVersion
+-		image.Author = imagePre012.Author
+-		image.Config = imagePre012.Config
+-		image.Architecture = imagePre012.Architecture
+-		image.Size = imagePre012.Size
+-	}
+-
+-	return &image, nil
+-}
+-
+-// PushImageOptions represents options to use in the PushImage method.
+-//
+-// See http://goo.gl/pN8A3P for more details.
+-type PushImageOptions struct {
+-	// Name of the image
+-	Name string
+-
+-	// Tag of the image
+-	Tag string
+-
+-	// Registry server to push the image
+-	Registry string
+-
+-	OutputStream  io.Writer `qs:"-"`
+-	RawJSONStream bool      `qs:"-"`
+-}
+-
+-// AuthConfiguration represents authentication options to use in the PushImage
+-// method. It represents the authentication in the Docker index server.
+-type AuthConfiguration struct {
+-	Username      string `json:"username,omitempty"`
+-	Password      string `json:"password,omitempty"`
+-	Email         string `json:"email,omitempty"`
+-	ServerAddress string `json:"serveraddress,omitempty"`
+-}
+-
+-// AuthConfigurations represents authentication options to use for the
+-// PushImage method accommodating the new X-Registry-Config header
+-type AuthConfigurations struct {
+-	Configs map[string]AuthConfiguration `json:"configs"`
+-}
+-
+-// PushImage pushes an image to a remote registry, logging progress to w.
+-//
+-// An empty instance of AuthConfiguration may be used for unauthenticated
+-// pushes.
+-//
+-// See http://goo.gl/pN8A3P for more details.
+-func (c *Client) PushImage(opts PushImageOptions, auth AuthConfiguration) error {
+-	if opts.Name == "" {
+-		return ErrNoSuchImage
+-	}
+-	name := opts.Name
+-	opts.Name = ""
+-	path := "/images/" + name + "/push?" + queryString(&opts)
+-	headers := headersWithAuth(auth)
+-	return c.stream("POST", path, true, opts.RawJSONStream, headers, nil, opts.OutputStream, nil)
+-}
+-
+-// PullImageOptions present the set of options available for pulling an image
+-// from a registry.
+-//
+-// See http://goo.gl/ACyYNS for more details.
+-type PullImageOptions struct {
+-	Repository    string `qs:"fromImage"`
+-	Registry      string
+-	Tag           string
+-	OutputStream  io.Writer `qs:"-"`
+-	RawJSONStream bool      `qs:"-"`
+-}
+-
+-// PullImage pulls an image from a remote registry, logging progress to w.
+-//
+-// See http://goo.gl/ACyYNS for more details.
+-func (c *Client) PullImage(opts PullImageOptions, auth AuthConfiguration) error {
+-	if opts.Repository == "" {
+-		return ErrNoSuchImage
+-	}
+-
+-	headers := headersWithAuth(auth)
+-	return c.createImage(queryString(&opts), headers, nil, opts.OutputStream, opts.RawJSONStream)
+-}
+-
+-func (c *Client) createImage(qs string, headers map[string]string, in io.Reader, w io.Writer, rawJSONStream bool) error {
+-	path := "/images/create?" + qs
+-	return c.stream("POST", path, true, rawJSONStream, headers, in, w, nil)
+-}
+-
+-// LoadImageOptions represents the options for LoadImage Docker API Call
+-//
+-// See http://goo.gl/Y8NNCq for more details.
+-type LoadImageOptions struct {
+-	InputStream io.Reader
+-}
+-
+-// LoadImage imports a tarball docker image
+-//
+-// See http://goo.gl/Y8NNCq for more details.
+-func (c *Client) LoadImage(opts LoadImageOptions) error {
+-	return c.stream("POST", "/images/load", true, false, nil, opts.InputStream, nil, nil)
+-}
+-
+-// ExportImageOptions represent the options for ExportImage Docker API call
+-//
+-// See http://goo.gl/mi6kvk for more details.
+-type ExportImageOptions struct {
+-	Name         string
+-	OutputStream io.Writer
+-}
+-
+-// ExportImage exports an image (as a tar file) into the stream
+-//
+-// See http://goo.gl/mi6kvk for more details.
+-func (c *Client) ExportImage(opts ExportImageOptions) error {
+-	return c.stream("GET", fmt.Sprintf("/images/%s/get", opts.Name), true, false, nil, nil, opts.OutputStream, nil)
+-}
+-
+-// ImportImageOptions present the set of informations available for importing
+-// an image from a source file or the stdin.
+-//
+-// See http://goo.gl/PhBKnS for more details.
+-type ImportImageOptions struct {
+-	Repository string `qs:"repo"`
+-	Source     string `qs:"fromSrc"`
+-	Tag        string `qs:"tag"`
+-
+-	InputStream  io.Reader `qs:"-"`
+-	OutputStream io.Writer `qs:"-"`
+-}
+-
+-// ImportImage imports an image from a url, a file or stdin
+-//
+-// See http://goo.gl/PhBKnS for more details.
+-func (c *Client) ImportImage(opts ImportImageOptions) error {
+-	if opts.Repository == "" {
+-		return ErrNoSuchImage
+-	}
+-	if opts.Source != "-" {
+-		opts.InputStream = nil
+-	}
+-	if opts.Source != "-" && !isURL(opts.Source) {
+-		f, err := os.Open(opts.Source)
+-		if err != nil {
+-			return err
+-		}
+-		b, err := ioutil.ReadAll(f)
+-		opts.InputStream = bytes.NewBuffer(b)
+-		opts.Source = "-"
+-	}
+-	return c.createImage(queryString(&opts), nil, opts.InputStream, opts.OutputStream, false)
+-}
+-
+-// BuildImageOptions present the set of informations available for building an
+-// image from a tarfile with a Dockerfile in it.
+-//
+-// For more details about the Docker building process, see
+-// http://goo.gl/tlPXPu.
+-type BuildImageOptions struct {
+-	Name                string             `qs:"t"`
+-	NoCache             bool               `qs:"nocache"`
+-	SuppressOutput      bool               `qs:"q"`
+-	RmTmpContainer      bool               `qs:"rm"`
+-	ForceRmTmpContainer bool               `qs:"forcerm"`
+-	InputStream         io.Reader          `qs:"-"`
+-	OutputStream        io.Writer          `qs:"-"`
+-	RawJSONStream       bool               `qs:"-"`
+-	Remote              string             `qs:"remote"`
+-	Auth                AuthConfiguration  `qs:"-"` // for older docker X-Registry-Auth header
+-	AuthConfigs         AuthConfigurations `qs:"-"` // for newer docker X-Registry-Config header
+-	ContextDir          string             `qs:"-"`
+-}
+-
+-// BuildImage builds an image from a tarball's url or a Dockerfile in the input
+-// stream.
+-//
+-// See http://goo.gl/wRsW76 for more details.
+-func (c *Client) BuildImage(opts BuildImageOptions) error {
+-	if opts.OutputStream == nil {
+-		return ErrMissingOutputStream
+-	}
+-	var headers = headersWithAuth(opts.Auth, opts.AuthConfigs)
+-
+-	if opts.Remote != "" && opts.Name == "" {
+-		opts.Name = opts.Remote
+-	}
+-	if opts.InputStream != nil || opts.ContextDir != "" {
+-		headers["Content-Type"] = "application/tar"
+-	} else if opts.Remote == "" {
+-		return ErrMissingRepo
+-	}
+-	if opts.ContextDir != "" {
+-		if opts.InputStream != nil {
+-			return ErrMultipleContexts
+-		}
+-		var err error
+-		if opts.InputStream, err = createTarStream(opts.ContextDir); err != nil {
+-			return err
+-		}
+-	}
+-
+-	return c.stream("POST", fmt.Sprintf("/build?%s",
+-		queryString(&opts)), true, opts.RawJSONStream, headers, opts.InputStream, opts.OutputStream, nil)
+-}
+-
+-// TagImageOptions present the set of options to tag an image.
+-//
+-// See http://goo.gl/5g6qFy for more details.
+-type TagImageOptions struct {
+-	Repo  string
+-	Tag   string
+-	Force bool
+-}
+-
+-// TagImage adds a tag to the image identified by the given name.
+-//
+-// See http://goo.gl/5g6qFy for more details.
+-func (c *Client) TagImage(name string, opts TagImageOptions) error {
+-	if name == "" {
+-		return ErrNoSuchImage
+-	}
+-	_, status, err := c.do("POST", fmt.Sprintf("/images/"+name+"/tag?%s",
+-		queryString(&opts)), nil)
+-	if status == http.StatusNotFound {
+-		return ErrNoSuchImage
+-	}
+-
+-	return err
+-}
+-
+-func isURL(u string) bool {
+-	p, err := url.Parse(u)
+-	if err != nil {
+-		return false
+-	}
+-	return p.Scheme == "http" || p.Scheme == "https"
+-}
+-
+-func headersWithAuth(auths ...interface{}) map[string]string {
+-	var headers = make(map[string]string)
+-
+-	for _, auth := range auths {
+-		switch auth.(type) {
+-		case AuthConfiguration:
+-			var buf bytes.Buffer
+-			json.NewEncoder(&buf).Encode(auth)
+-			headers["X-Registry-Auth"] = base64.URLEncoding.EncodeToString(buf.Bytes())
+-		case AuthConfigurations:
+-			var buf bytes.Buffer
+-			json.NewEncoder(&buf).Encode(auth)
+-			headers["X-Registry-Config"] = base64.URLEncoding.EncodeToString(buf.Bytes())
+-		}
+-	}
+-
+-	return headers
+-}
+-
+-// APIImageSearch reflect the result of a search on the dockerHub
+-//
+-// See http://goo.gl/xI5lLZ for more details.
+-type APIImageSearch struct {
+-	Description string `json:"description,omitempty" yaml:"description,omitempty"`
+-	IsOfficial  bool   `json:"is_official,omitempty" yaml:"is_official,omitempty"`
+-	IsAutomated bool   `json:"is_automated,omitempty" yaml:"is_automated,omitempty"`
+-	Name        string `json:"name,omitempty" yaml:"name,omitempty"`
+-	StarCount   int    `json:"star_count,omitempty" yaml:"star_count,omitempty"`
+-}
+-
+-// SearchImages search the docker hub with a specific given term.
+-//
+-// See http://goo.gl/xI5lLZ for more details.
+-func (c *Client) SearchImages(term string) ([]APIImageSearch, error) {
+-	body, _, err := c.do("GET", "/images/search?term="+term, nil)
+-	if err != nil {
+-		return nil, err
+-	}
+-	var searchResult []APIImageSearch
+-	err = json.Unmarshal(body, &searchResult)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return searchResult, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/image_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/image_test.go
+deleted file mode 100644
+index 11776e8..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/image_test.go
++++ /dev/null
+@@ -1,878 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 docker
+-
+-import (
+-	"bytes"
+-	"encoding/base64"
+-	"encoding/json"
+-	"io/ioutil"
+-	"net/http"
+-	"net/url"
+-	"os"
+-	"reflect"
+-	"strings"
+-	"testing"
+-)
+-
+-func newTestClient(rt *FakeRoundTripper) Client {
+-	endpoint := "http://localhost:4243"
+-	u, _ := parseEndpoint("http://localhost:4243")
+-	client := Client{
+-		HTTPClient:             &http.Client{Transport: rt},
+-		endpoint:               endpoint,
+-		endpointURL:            u,
+-		SkipServerVersionCheck: true,
+-	}
+-	return client
+-}
+-
+-type stdoutMock struct {
+-	*bytes.Buffer
+-}
+-
+-func (m stdoutMock) Close() error {
+-	return nil
+-}
+-
+-type stdinMock struct {
+-	*bytes.Buffer
+-}
+-
+-func (m stdinMock) Close() error {
+-	return nil
+-}
+-
+-func TestListImages(t *testing.T) {
+-	body := `[
+-     {
+-             "Repository":"base",
+-             "Tag":"ubuntu-12.10",
+-             "Id":"b750fe79269d",
+-             "Created":1364102658
+-     },
+-     {
+-             "Repository":"base",
+-             "Tag":"ubuntu-quantal",
+-             "Id":"b750fe79269d",
+-             "Created":1364102658
+-     },
+-     {
+-             "RepoTag": [
+-             "ubuntu:12.04",
+-             "ubuntu:precise",
+-             "ubuntu:latest"
+-             ],
+-             "Id": "8dbd9e392a964c",
+-             "Created": 1365714795,
+-             "Size": 131506275,
+-             "VirtualSize": 131506275
+-      },
+-      {
+-             "RepoTag": [
+-             "ubuntu:12.10",
+-             "ubuntu:quantal"
+-             ],
+-             "ParentId": "27cf784147099545",
+-             "Id": "b750fe79269d2e",
+-             "Created": 1364102658,
+-             "Size": 24653,
+-             "VirtualSize": 180116135
+-      }
+-]`
+-	var expected []APIImages
+-	err := json.Unmarshal([]byte(body), &expected)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	client := newTestClient(&FakeRoundTripper{message: body, status: http.StatusOK})
+-	images, err := client.ListImages(ListImagesOptions{})
+-	if err != nil {
+-		t.Error(err)
+-	}
+-	if !reflect.DeepEqual(images, expected) {
+-		t.Errorf("ListImages: Wrong return value. Want %#v. Got %#v.", expected, images)
+-	}
+-}
+-
+-func TestListImagesParameters(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "null", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	_, err := client.ListImages(ListImagesOptions{All: false})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "GET" {
+-		t.Errorf("ListImages({All: false}: Wrong HTTP method. Want GET. Got %s.", req.Method)
+-	}
+-	if all := req.URL.Query().Get("all"); all != "0" && all != "" {
+-		t.Errorf("ListImages({All: false}): Wrong parameter. Want all=0 or not present at all. Got all=%s", all)
+-	}
+-	fakeRT.Reset()
+-	_, err = client.ListImages(ListImagesOptions{All: true})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req = fakeRT.requests[0]
+-	if all := req.URL.Query().Get("all"); all != "1" {
+-		t.Errorf("ListImages({All: true}): Wrong parameter. Want all=1. Got all=%s", all)
+-	}
+-	fakeRT.Reset()
+-	_, err = client.ListImages(ListImagesOptions{Filters: map[string][]string{
+-		"dangling": {"true"},
+-	}})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req = fakeRT.requests[0]
+-	body := req.URL.Query().Get("filters")
+-	var filters map[string][]string
+-	err = json.Unmarshal([]byte(body), &filters)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if len(filters["dangling"]) != 1 || filters["dangling"][0] != "true" {
+-		t.Errorf("ListImages(dangling=[true]): Wrong filter map. Want dangling=[true], got dangling=%v", filters["dangling"])
+-	}
+-}
+-
+-func TestImageHistory(t *testing.T) {
+-	body := `[
+-	{
+-		"Id": "25daec02219d2d852f7526137213a9b199926b4b24e732eab5b8bc6c49bd470e",
+-		"Tags": [
+-			"debian:7.6",
+-			"debian:latest",
+-			"debian:7",
+-			"debian:wheezy"
+-		],
+-		"Created": 1409856216,
+-		"CreatedBy": "/bin/sh -c #(nop) CMD [/bin/bash]"
+-	},
+-	{
+-		"Id": "41026a5347fb5be6ed16115bf22df8569697139f246186de9ae8d4f67c335dce",
+-		"Created": 1409856213,
+-		"CreatedBy": "/bin/sh -c #(nop) ADD file:1ee9e97209d00e3416a4543b23574cc7259684741a46bbcbc755909b8a053a38 in /",
+-		"Size": 85178663
+-	},
+-	{
+-		"Id": "511136ea3c5a64f264b78b5433614aec563103b4d4702f3ba7d4d2698e22c158",
+-		"Tags": [
+-			"scratch:latest"
+-		],
+-		"Created": 1371157430
+-	}
+-]`
+-	var expected []ImageHistory
+-	err := json.Unmarshal([]byte(body), &expected)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	client := newTestClient(&FakeRoundTripper{message: body, status: http.StatusOK})
+-	history, err := client.ImageHistory("debian:latest")
+-	if err != nil {
+-		t.Error(err)
+-	}
+-	if !reflect.DeepEqual(history, expected) {
+-		t.Errorf("ImageHistory: Wrong return value. Want %#v. Got %#v.", expected, history)
+-	}
+-}
+-
+-func TestRemoveImage(t *testing.T) {
+-	name := "test"
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusNoContent}
+-	client := newTestClient(fakeRT)
+-	err := client.RemoveImage(name)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	expectedMethod := "DELETE"
+-	if req.Method != expectedMethod {
+-		t.Errorf("RemoveImage(%q): Wrong HTTP method. Want %s. Got %s.", name, expectedMethod, req.Method)
+-	}
+-	u, _ := url.Parse(client.getURL("/images/" + name))
+-	if req.URL.Path != u.Path {
+-		t.Errorf("RemoveImage(%q): Wrong request path. Want %q. Got %q.", name, u.Path, req.URL.Path)
+-	}
+-}
+-
+-func TestRemoveImageNotFound(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "no such image", status: http.StatusNotFound})
+-	err := client.RemoveImage("test:")
+-	if err != ErrNoSuchImage {
+-		t.Errorf("RemoveImage: wrong error. Want %#v. Got %#v.", ErrNoSuchImage, err)
+-	}
+-}
+-
+-func TestInspectImage(t *testing.T) {
+-	body := `{
+-     "id":"b750fe79269d2ec9a3c593ef05b4332b1d1a02a62b4accb2c21d589ff2f5f2dc",
+-     "parent":"27cf784147099545",
+-     "created":"2013-03-23T22:24:18.818426-07:00",
+-     "container":"3d67245a8d72ecf13f33dffac9f79dcdf70f75acb84d308770391510e0c23ad0",
+-     "container_config":{"Memory":0}
+-}`
+-	var expected Image
+-	json.Unmarshal([]byte(body), &expected)
+-	fakeRT := &FakeRoundTripper{message: body, status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	image, err := client.InspectImage(expected.ID)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !reflect.DeepEqual(*image, expected) {
+-		t.Errorf("InspectImage(%q): Wrong image returned. Want %#v. Got %#v.", expected.ID, expected, *image)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "GET" {
+-		t.Errorf("InspectImage(%q): Wrong HTTP method. Want GET. Got %s.", expected.ID, req.Method)
+-	}
+-	u, _ := url.Parse(client.getURL("/images/" + expected.ID + "/json"))
+-	if req.URL.Path != u.Path {
+-		t.Errorf("InspectImage(%q): Wrong request URL. Want %q. Got %q.", expected.ID, u.Path, req.URL.Path)
+-	}
+-}
+-
+-func TestInspectImageNotFound(t *testing.T) {
+-	client := newTestClient(&FakeRoundTripper{message: "no such image", status: http.StatusNotFound})
+-	name := "test"
+-	image, err := client.InspectImage(name)
+-	if image != nil {
+-		t.Errorf("InspectImage(%q): expected <nil> image, got %#v.", name, image)
+-	}
+-	if err != ErrNoSuchImage {
+-		t.Errorf("InspectImage(%q): wrong error. Want %#v. Got %#v.", name, ErrNoSuchImage, err)
+-	}
+-}
+-
+-func TestPushImage(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "Pushing 1/100", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-	err := client.PushImage(PushImageOptions{Name: "test", OutputStream: &buf}, AuthConfiguration{})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	expected := "Pushing 1/100"
+-	if buf.String() != expected {
+-		t.Errorf("PushImage: Wrong output. Want %q. Got %q.", expected, buf.String())
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "POST" {
+-		t.Errorf("PushImage: Wrong HTTP method. Want POST. Got %s.", req.Method)
+-	}
+-	u, _ := url.Parse(client.getURL("/images/test/push"))
+-	if req.URL.Path != u.Path {
+-		t.Errorf("PushImage: Wrong request path. Want %q. Got %q.", u.Path, req.URL.Path)
+-	}
+-	if query := req.URL.Query().Encode(); query != "" {
+-		t.Errorf("PushImage: Wrong query string. Want no parameters, got %q.", query)
+-	}
+-
+-	auth, err := base64.URLEncoding.DecodeString(req.Header.Get("X-Registry-Auth"))
+-	if err != nil {
+-		t.Errorf("PushImage: caught error decoding auth. %#v", err.Error())
+-	}
+-	if strings.TrimSpace(string(auth)) != "{}" {
+-		t.Errorf("PushImage: wrong body. Want %q. Got %q.",
+-			base64.URLEncoding.EncodeToString([]byte("{}")), req.Header.Get("X-Registry-Auth"))
+-	}
+-}
+-
+-func TestPushImageWithRawJSON(t *testing.T) {
+-	body := `
+-	{"status":"Pushing..."}
+-	{"status":"Pushing", "progress":"1/? (n/a)", "progressDetail":{"current":1}}}
+-	{"status":"Image successfully pushed"}
+-	`
+-	fakeRT := &FakeRoundTripper{
+-		message: body,
+-		status:  http.StatusOK,
+-		header: map[string]string{
+-			"Content-Type": "application/json",
+-		},
+-	}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-
+-	err := client.PushImage(PushImageOptions{
+-		Name:          "test",
+-		OutputStream:  &buf,
+-		RawJSONStream: true,
+-	}, AuthConfiguration{})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if buf.String() != body {
+-		t.Errorf("PushImage: Wrong raw output. Want %q. Got %q.", body, buf.String())
+-	}
+-}
+-
+-func TestPushImageWithAuthentication(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "Pushing 1/100", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-	inputAuth := AuthConfiguration{
+-		Username: "gopher",
+-		Password: "gopher123",
+-		Email:    "gopher at tsuru.io",
+-	}
+-	err := client.PushImage(PushImageOptions{Name: "test", OutputStream: &buf}, inputAuth)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	var gotAuth AuthConfiguration
+-
+-	auth, err := base64.URLEncoding.DecodeString(req.Header.Get("X-Registry-Auth"))
+-	if err != nil {
+-		t.Errorf("PushImage: caught error decoding auth. %#v", err.Error())
+-	}
+-
+-	err = json.Unmarshal(auth, &gotAuth)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !reflect.DeepEqual(gotAuth, inputAuth) {
+-		t.Errorf("PushImage: wrong auth configuration. Want %#v. Got %#v.", inputAuth, gotAuth)
+-	}
+-}
+-
+-func TestPushImageCustomRegistry(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "Pushing 1/100", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	var authConfig AuthConfiguration
+-	var buf bytes.Buffer
+-	opts := PushImageOptions{
+-		Name: "test", Registry: "docker.tsuru.io",
+-		OutputStream: &buf,
+-	}
+-	err := client.PushImage(opts, authConfig)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	expectedQuery := "registry=docker.tsuru.io"
+-	if query := req.URL.Query().Encode(); query != expectedQuery {
+-		t.Errorf("PushImage: Wrong query string. Want %q. Got %q.", expectedQuery, query)
+-	}
+-}
+-
+-func TestPushImageNoName(t *testing.T) {
+-	client := Client{}
+-	err := client.PushImage(PushImageOptions{}, AuthConfiguration{})
+-	if err != ErrNoSuchImage {
+-		t.Errorf("PushImage: got wrong error. Want %#v. Got %#v.", ErrNoSuchImage, err)
+-	}
+-}
+-
+-func TestPullImage(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "Pulling 1/100", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-	err := client.PullImage(PullImageOptions{Repository: "base", OutputStream: &buf},
+-		AuthConfiguration{})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	expected := "Pulling 1/100"
+-	if buf.String() != expected {
+-		t.Errorf("PullImage: Wrong output. Want %q. Got %q.", expected, buf.String())
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "POST" {
+-		t.Errorf("PullImage: Wrong HTTP method. Want POST. Got %s.", req.Method)
+-	}
+-	u, _ := url.Parse(client.getURL("/images/create"))
+-	if req.URL.Path != u.Path {
+-		t.Errorf("PullImage: Wrong request path. Want %q. Got %q.", u.Path, req.URL.Path)
+-	}
+-	expectedQuery := "fromImage=base"
+-	if query := req.URL.Query().Encode(); query != expectedQuery {
+-		t.Errorf("PullImage: Wrong query strin. Want %q. Got %q.", expectedQuery, query)
+-	}
+-}
+-
+-func TestPullImageWithRawJSON(t *testing.T) {
+-	body := `
+-	{"status":"Pulling..."}
+-	{"status":"Pulling", "progress":"1 B/ 100 B", "progressDetail":{"current":1, "total":100}}
+-	`
+-	fakeRT := &FakeRoundTripper{
+-		message: body,
+-		status:  http.StatusOK,
+-		header: map[string]string{
+-			"Content-Type": "application/json",
+-		},
+-	}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-	err := client.PullImage(PullImageOptions{
+-		Repository:    "base",
+-		OutputStream:  &buf,
+-		RawJSONStream: true,
+-	}, AuthConfiguration{})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if buf.String() != body {
+-		t.Errorf("PullImage: Wrong raw output. Want %q. Got %q", body, buf.String())
+-	}
+-}
+-
+-func TestPullImageWithoutOutputStream(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "Pulling 1/100", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	opts := PullImageOptions{
+-		Repository: "base",
+-		Registry:   "docker.tsuru.io",
+-	}
+-	err := client.PullImage(opts, AuthConfiguration{})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	expected := map[string][]string{"fromImage": {"base"}, "registry": {"docker.tsuru.io"}}
+-	got := map[string][]string(req.URL.Query())
+-	if !reflect.DeepEqual(got, expected) {
+-		t.Errorf("PullImage: wrong query string. Want %#v. Got %#v.", expected, got)
+-	}
+-}
+-
+-func TestPullImageCustomRegistry(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "Pulling 1/100", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-	opts := PullImageOptions{
+-		Repository:   "base",
+-		Registry:     "docker.tsuru.io",
+-		OutputStream: &buf,
+-	}
+-	err := client.PullImage(opts, AuthConfiguration{})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	expected := map[string][]string{"fromImage": {"base"}, "registry": {"docker.tsuru.io"}}
+-	got := map[string][]string(req.URL.Query())
+-	if !reflect.DeepEqual(got, expected) {
+-		t.Errorf("PullImage: wrong query string. Want %#v. Got %#v.", expected, got)
+-	}
+-}
+-
+-func TestPullImageTag(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "Pulling 1/100", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-	opts := PullImageOptions{
+-		Repository:   "base",
+-		Registry:     "docker.tsuru.io",
+-		Tag:          "latest",
+-		OutputStream: &buf,
+-	}
+-	err := client.PullImage(opts, AuthConfiguration{})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	expected := map[string][]string{"fromImage": {"base"}, "registry": {"docker.tsuru.io"}, "tag": {"latest"}}
+-	got := map[string][]string(req.URL.Query())
+-	if !reflect.DeepEqual(got, expected) {
+-		t.Errorf("PullImage: wrong query string. Want %#v. Got %#v.", expected, got)
+-	}
+-}
+-
+-func TestPullImageNoRepository(t *testing.T) {
+-	var opts PullImageOptions
+-	client := Client{}
+-	err := client.PullImage(opts, AuthConfiguration{})
+-	if err != ErrNoSuchImage {
+-		t.Errorf("PullImage: got wrong error. Want %#v. Got %#v.", ErrNoSuchImage, err)
+-	}
+-}
+-
+-func TestImportImageFromUrl(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-	opts := ImportImageOptions{
+-		Source:       "http://mycompany.com/file.tar",
+-		Repository:   "testimage",
+-		Tag:          "tag",
+-		OutputStream: &buf,
+-	}
+-	err := client.ImportImage(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	expected := map[string][]string{"fromSrc": {opts.Source}, "repo": {opts.Repository}, "tag": {opts.Tag}}
+-	got := map[string][]string(req.URL.Query())
+-	if !reflect.DeepEqual(got, expected) {
+-		t.Errorf("ImportImage: wrong query string. Want %#v. Got %#v.", expected, got)
+-	}
+-}
+-
+-func TestImportImageFromInput(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	in := bytes.NewBufferString("tar content")
+-	var buf bytes.Buffer
+-	opts := ImportImageOptions{
+-		Source: "-", Repository: "testimage",
+-		InputStream: in, OutputStream: &buf,
+-		Tag: "tag",
+-	}
+-	err := client.ImportImage(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	expected := map[string][]string{"fromSrc": {opts.Source}, "repo": {opts.Repository}, "tag": {opts.Tag}}
+-	got := map[string][]string(req.URL.Query())
+-	if !reflect.DeepEqual(got, expected) {
+-		t.Errorf("ImportImage: wrong query string. Want %#v. Got %#v.", expected, got)
+-	}
+-	body, err := ioutil.ReadAll(req.Body)
+-	if err != nil {
+-		t.Errorf("ImportImage: caugth error while reading body %#v", err.Error())
+-	}
+-	e := "tar content"
+-	if string(body) != e {
+-		t.Errorf("ImportImage: wrong body. Want %#v. Got %#v.", e, string(body))
+-	}
+-}
+-
+-func TestImportImageDoesNotPassesInputIfSourceIsNotDash(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-	in := bytes.NewBufferString("foo")
+-	opts := ImportImageOptions{
+-		Source: "http://test.com/container.tar", Repository: "testimage",
+-		InputStream: in, OutputStream: &buf,
+-	}
+-	err := client.ImportImage(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	expected := map[string][]string{"fromSrc": {opts.Source}, "repo": {opts.Repository}}
+-	got := map[string][]string(req.URL.Query())
+-	if !reflect.DeepEqual(got, expected) {
+-		t.Errorf("ImportImage: wrong query string. Want %#v. Got %#v.", expected, got)
+-	}
+-	body, err := ioutil.ReadAll(req.Body)
+-	if err != nil {
+-		t.Errorf("ImportImage: caugth error while reading body %#v", err.Error())
+-	}
+-	if string(body) != "" {
+-		t.Errorf("ImportImage: wrong body. Want nothing. Got %#v.", string(body))
+-	}
+-}
+-
+-func TestImportImageShouldPassTarContentToBodyWhenSourceIsFilePath(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-	tarPath := "testing/data/container.tar"
+-	opts := ImportImageOptions{
+-		Source: tarPath, Repository: "testimage",
+-		OutputStream: &buf,
+-	}
+-	err := client.ImportImage(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	tar, err := os.Open(tarPath)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	tarContent, err := ioutil.ReadAll(tar)
+-	body, err := ioutil.ReadAll(req.Body)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !reflect.DeepEqual(tarContent, body) {
+-		t.Errorf("ImportImage: wrong body. Want %#v content. Got %#v.", tarPath, body)
+-	}
+-}
+-
+-func TestImportImageShouldChangeSourceToDashWhenItsAFilePath(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-	tarPath := "testing/data/container.tar"
+-	opts := ImportImageOptions{
+-		Source: tarPath, Repository: "testimage",
+-		OutputStream: &buf,
+-	}
+-	err := client.ImportImage(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	expected := map[string][]string{"fromSrc": {"-"}, "repo": {opts.Repository}}
+-	got := map[string][]string(req.URL.Query())
+-	if !reflect.DeepEqual(got, expected) {
+-		t.Errorf("ImportImage: wrong query string. Want %#v. Got %#v.", expected, got)
+-	}
+-}
+-
+-func TestBuildImageParameters(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-	opts := BuildImageOptions{
+-		Name:                "testImage",
+-		NoCache:             true,
+-		SuppressOutput:      true,
+-		RmTmpContainer:      true,
+-		ForceRmTmpContainer: true,
+-		InputStream:         &buf,
+-		OutputStream:        &buf,
+-	}
+-	err := client.BuildImage(opts)
+-	if err != nil && strings.Index(err.Error(), "build image fail") == -1 {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	expected := map[string][]string{"t": {opts.Name}, "nocache": {"1"}, "q": {"1"}, "rm": {"1"}, "forcerm": {"1"}}
+-	got := map[string][]string(req.URL.Query())
+-	if !reflect.DeepEqual(got, expected) {
+-		t.Errorf("BuildImage: wrong query string. Want %#v. Got %#v.", expected, got)
+-	}
+-}
+-
+-func TestBuildImageParametersForRemoteBuild(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-	opts := BuildImageOptions{
+-		Name:           "testImage",
+-		Remote:         "testing/data/container.tar",
+-		SuppressOutput: true,
+-		OutputStream:   &buf,
+-	}
+-	err := client.BuildImage(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	expected := map[string][]string{"t": {opts.Name}, "remote": {opts.Remote}, "q": {"1"}}
+-	got := map[string][]string(req.URL.Query())
+-	if !reflect.DeepEqual(got, expected) {
+-		t.Errorf("BuildImage: wrong query string. Want %#v. Got %#v.", expected, got)
+-	}
+-}
+-
+-func TestBuildImageMissingRepoAndNilInput(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-	opts := BuildImageOptions{
+-		Name:           "testImage",
+-		SuppressOutput: true,
+-		OutputStream:   &buf,
+-	}
+-	err := client.BuildImage(opts)
+-	if err != ErrMissingRepo {
+-		t.Errorf("BuildImage: wrong error returned. Want %#v. Got %#v.", ErrMissingRepo, err)
+-	}
+-}
+-
+-func TestBuildImageMissingOutputStream(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	opts := BuildImageOptions{Name: "testImage"}
+-	err := client.BuildImage(opts)
+-	if err != ErrMissingOutputStream {
+-		t.Errorf("BuildImage: wrong error returned. Want %#v. Got %#v.", ErrMissingOutputStream, err)
+-	}
+-}
+-
+-func TestBuildImageWithRawJSON(t *testing.T) {
+-	body := `
+-	{"stream":"Step 0 : FROM ubuntu:latest\n"}
+-	{"stream":" ---\u003e 4300eb9d3c8d\n"}
+-	{"stream":"Step 1 : MAINTAINER docker <eng at docker.com>\n"}
+-	{"stream":" ---\u003e Using cache\n"}
+-	{"stream":" ---\u003e 3a3ed758c370\n"}
+-	{"stream":"Step 2 : CMD /usr/bin/top\n"}
+-	{"stream":" ---\u003e Running in 36b1479cc2e4\n"}
+-	{"stream":" ---\u003e 4b6188aebe39\n"}
+-	{"stream":"Removing intermediate container 36b1479cc2e4\n"}
+-	{"stream":"Successfully built 4b6188aebe39\n"}
+-    `
+-	fakeRT := &FakeRoundTripper{
+-		message: body,
+-		status:  http.StatusOK,
+-		header: map[string]string{
+-			"Content-Type": "application/json",
+-		},
+-	}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-	opts := BuildImageOptions{
+-		Name:           "testImage",
+-		RmTmpContainer: true,
+-		InputStream:    &buf,
+-		OutputStream:   &buf,
+-		RawJSONStream:  true,
+-	}
+-	err := client.BuildImage(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if buf.String() != body {
+-		t.Errorf("BuildImage: Wrong raw output. Want %q. Got %q.", body, buf.String())
+-	}
+-}
+-
+-func TestBuildImageRemoteWithoutName(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	var buf bytes.Buffer
+-	opts := BuildImageOptions{
+-		Remote:         "testing/data/container.tar",
+-		SuppressOutput: true,
+-		OutputStream:   &buf,
+-	}
+-	err := client.BuildImage(opts)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	expected := map[string][]string{"t": {opts.Remote}, "remote": {opts.Remote}, "q": {"1"}}
+-	got := map[string][]string(req.URL.Query())
+-	if !reflect.DeepEqual(got, expected) {
+-		t.Errorf("BuildImage: wrong query string. Want %#v. Got %#v.", expected, got)
+-	}
+-}
+-
+-func TestTagImageParameters(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	opts := TagImageOptions{Repo: "testImage"}
+-	err := client.TagImage("base", opts)
+-	if err != nil && strings.Index(err.Error(), "tag image fail") == -1 {
+-		t.Fatal(err)
+-	}
+-	req := fakeRT.requests[0]
+-	expected := "http://localhost:4243/images/base/tag?repo=testImage"
+-	got := req.URL.String()
+-	if !reflect.DeepEqual(got, expected) {
+-		t.Errorf("TagImage: wrong query string. Want %#v. Got %#v.", expected, got)
+-	}
+-}
+-
+-func TestTagImageMissingRepo(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	opts := TagImageOptions{Repo: "testImage"}
+-	err := client.TagImage("", opts)
+-	if err != ErrNoSuchImage {
+-		t.Errorf("TestTag: wrong error returned. Want %#v. Got %#v.",
+-			ErrNoSuchImage, err)
+-	}
+-}
+-
+-func TestIsUrl(t *testing.T) {
+-	url := "http://foo.bar/"
+-	result := isURL(url)
+-	if !result {
+-		t.Errorf("isURL: wrong match. Expected %#v to be a url. Got %#v.", url, result)
+-	}
+-	url = "/foo/bar.tar"
+-	result = isURL(url)
+-	if result {
+-		t.Errorf("isURL: wrong match. Expected %#v to not be a url. Got %#v", url, result)
+-	}
+-}
+-
+-func TestLoadImage(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	tar, err := os.Open("testing/data/container.tar")
+-	if err != nil {
+-		t.Fatal(err)
+-	} else {
+-		defer tar.Close()
+-	}
+-	opts := LoadImageOptions{InputStream: tar}
+-	err = client.LoadImage(opts)
+-	if nil != err {
+-		t.Error(err)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "POST" {
+-		t.Errorf("LoadImage: wrong method. Expected %q. Got %q.", "POST", req.Method)
+-	}
+-	if req.URL.Path != "/images/load" {
+-		t.Errorf("LoadImage: wrong URL. Expected %q. Got %q.", "/images/load", req.URL.Path)
+-	}
+-}
+-
+-func TestExportImage(t *testing.T) {
+-	var buf bytes.Buffer
+-	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
+-	client := newTestClient(fakeRT)
+-	opts := ExportImageOptions{Name: "testimage", OutputStream: &buf}
+-	err := client.ExportImage(opts)
+-	if nil != err {
+-		t.Error(err)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "GET" {
+-		t.Errorf("ExportImage: wrong method. Expected %q. Got %q.", "GET", req.Method)
+-	}
+-	expectedPath := "/images/testimage/get"
+-	if req.URL.Path != expectedPath {
+-		t.Errorf("ExportIMage: wrong path. Expected %q. Got %q.", expectedPath, req.URL.Path)
+-	}
+-}
+-
+-func TestSearchImages(t *testing.T) {
+-	body := `[
+-	{
+-		"description":"A container with Cassandra 2.0.3",
+-		"is_official":true,
+-		"is_automated":true,
+-		"name":"poklet/cassandra",
+-		"star_count":17
+-	},
+-	{
+-		"description":"A container with Cassandra 2.0.3",
+-		"is_official":true,
+-		"is_automated":false,
+-		"name":"poklet/cassandra",
+-		"star_count":17
+-	}
+-	,
+-	{
+-		"description":"A container with Cassandra 2.0.3",
+-		"is_official":false,
+-		"is_automated":true,
+-		"name":"poklet/cassandra",
+-		"star_count":17
+-	}
+-]`
+-	var expected []APIImageSearch
+-	err := json.Unmarshal([]byte(body), &expected)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	client := newTestClient(&FakeRoundTripper{message: body, status: http.StatusOK})
+-	result, err := client.SearchImages("cassandra")
+-	if err != nil {
+-		t.Error(err)
+-	}
+-	if !reflect.DeepEqual(result, expected) {
+-		t.Errorf("SearchImages: Wrong return value. Want %#v. Got %#v.", expected, result)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/misc.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/misc.go
+deleted file mode 100644
+index 2678ab5..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/misc.go
++++ /dev/null
+@@ -1,59 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 docker
+-
+-import (
+-	"bytes"
+-	"strings"
+-)
+-
+-// Version returns version information about the docker server.
+-//
+-// See http://goo.gl/BOZrF5 for more details.
+-func (c *Client) Version() (*Env, error) {
+-	body, _, err := c.do("GET", "/version", nil)
+-	if err != nil {
+-		return nil, err
+-	}
+-	var env Env
+-	if err := env.Decode(bytes.NewReader(body)); err != nil {
+-		return nil, err
+-	}
+-	return &env, nil
+-}
+-
+-// Info returns system-wide information about the Docker server.
+-//
+-// See http://goo.gl/wmqZsW for more details.
+-func (c *Client) Info() (*Env, error) {
+-	body, _, err := c.do("GET", "/info", nil)
+-	if err != nil {
+-		return nil, err
+-	}
+-	var info Env
+-	err = info.Decode(bytes.NewReader(body))
+-	if err != nil {
+-		return nil, err
+-	}
+-	return &info, nil
+-}
+-
+-// ParseRepositoryTag gets the name of the repository and returns it splitted
+-// in two parts: the repository and the tag.
+-//
+-// Some examples:
+-//
+-//     localhost.localdomain:5000/samalba/hipache:latest -> localhost.localdomain:5000/samalba/hipache, latest
+-//     localhost.localdomain:5000/samalba/hipache -> localhost.localdomain:5000/samalba/hipache, ""
+-func ParseRepositoryTag(repoTag string) (repository string, tag string) {
+-	n := strings.LastIndex(repoTag, ":")
+-	if n < 0 {
+-		return repoTag, ""
+-	}
+-	if tag := repoTag[n+1:]; !strings.Contains(tag, "/") {
+-		return repoTag[:n], tag
+-	}
+-	return repoTag, ""
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/misc_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/misc_test.go
+deleted file mode 100644
+index ceaf076..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/misc_test.go
++++ /dev/null
+@@ -1,159 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 docker
+-
+-import (
+-	"net/http"
+-	"net/url"
+-	"reflect"
+-	"sort"
+-	"testing"
+-)
+-
+-type DockerVersion struct {
+-	Version   string
+-	GitCommit string
+-	GoVersion string
+-}
+-
+-func TestVersion(t *testing.T) {
+-	body := `{
+-     "Version":"0.2.2",
+-     "GitCommit":"5a2a5cc+CHANGES",
+-     "GoVersion":"go1.0.3"
+-}`
+-	fakeRT := FakeRoundTripper{message: body, status: http.StatusOK}
+-	client := newTestClient(&fakeRT)
+-	expected := DockerVersion{
+-		Version:   "0.2.2",
+-		GitCommit: "5a2a5cc+CHANGES",
+-		GoVersion: "go1.0.3",
+-	}
+-	version, err := client.Version()
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	if result := version.Get("Version"); result != expected.Version {
+-		t.Errorf("Version(): Wrong result. Want %#v. Got %#v.", expected.Version, version.Get("Version"))
+-	}
+-	if result := version.Get("GitCommit"); result != expected.GitCommit {
+-		t.Errorf("GitCommit(): Wrong result. Want %#v. Got %#v.", expected.GitCommit, version.Get("GitCommit"))
+-	}
+-	if result := version.Get("GoVersion"); result != expected.GoVersion {
+-		t.Errorf("GoVersion(): Wrong result. Want %#v. Got %#v.", expected.GoVersion, version.Get("GoVersion"))
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "GET" {
+-		t.Errorf("Version(): wrong request method. Want GET. Got %s.", req.Method)
+-	}
+-	u, _ := url.Parse(client.getURL("/version"))
+-	if req.URL.Path != u.Path {
+-		t.Errorf("Version(): wrong request path. Want %q. Got %q.", u.Path, req.URL.Path)
+-	}
+-}
+-
+-func TestVersionError(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "internal error", status: http.StatusInternalServerError}
+-	client := newTestClient(fakeRT)
+-	version, err := client.Version()
+-	if version != nil {
+-		t.Errorf("Version(): expected <nil> value, got %#v.", version)
+-	}
+-	if err == nil {
+-		t.Error("Version(): unexpected <nil> error")
+-	}
+-}
+-
+-func TestInfo(t *testing.T) {
+-	body := `{
+-     "Containers":11,
+-     "Images":16,
+-     "Debug":0,
+-     "NFd":11,
+-     "NGoroutines":21,
+-     "MemoryLimit":1,
+-     "SwapLimit":0
+-}`
+-	fakeRT := FakeRoundTripper{message: body, status: http.StatusOK}
+-	client := newTestClient(&fakeRT)
+-	expected := Env{}
+-	expected.SetInt("Containers", 11)
+-	expected.SetInt("Images", 16)
+-	expected.SetBool("Debug", false)
+-	expected.SetInt("NFd", 11)
+-	expected.SetInt("NGoroutines", 21)
+-	expected.SetBool("MemoryLimit", true)
+-	expected.SetBool("SwapLimit", false)
+-	info, err := client.Info()
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	infoSlice := []string(*info)
+-	expectedSlice := []string(expected)
+-	sort.Strings(infoSlice)
+-	sort.Strings(expectedSlice)
+-	if !reflect.DeepEqual(expectedSlice, infoSlice) {
+-		t.Errorf("Info(): Wrong result.\nWant %#v.\nGot %#v.", expected, *info)
+-	}
+-	req := fakeRT.requests[0]
+-	if req.Method != "GET" {
+-		t.Errorf("Info(): Wrong HTTP method. Want GET. Got %s.", req.Method)
+-	}
+-	u, _ := url.Parse(client.getURL("/info"))
+-	if req.URL.Path != u.Path {
+-		t.Errorf("Info(): Wrong request path. Want %q. Got %q.", u.Path, req.URL.Path)
+-	}
+-}
+-
+-func TestInfoError(t *testing.T) {
+-	fakeRT := &FakeRoundTripper{message: "internal error", status: http.StatusInternalServerError}
+-	client := newTestClient(fakeRT)
+-	version, err := client.Info()
+-	if version != nil {
+-		t.Errorf("Info(): expected <nil> value, got %#v.", version)
+-	}
+-	if err == nil {
+-		t.Error("Info(): unexpected <nil> error")
+-	}
+-}
+-
+-func TestParseRepositoryTag(t *testing.T) {
+-	var tests = []struct {
+-		input        string
+-		expectedRepo string
+-		expectedTag  string
+-	}{
+-		{
+-			"localhost.localdomain:5000/samalba/hipache:latest",
+-			"localhost.localdomain:5000/samalba/hipache",
+-			"latest",
+-		},
+-		{
+-			"localhost.localdomain:5000/samalba/hipache",
+-			"localhost.localdomain:5000/samalba/hipache",
+-			"",
+-		},
+-		{
+-			"tsuru/python",
+-			"tsuru/python",
+-			"",
+-		},
+-		{
+-			"tsuru/python:2.7",
+-			"tsuru/python",
+-			"2.7",
+-		},
+-	}
+-	for _, tt := range tests {
+-		repo, tag := ParseRepositoryTag(tt.input)
+-		if repo != tt.expectedRepo {
+-			t.Errorf("ParseRepositoryTag(%q): wrong repository. Want %q. Got %q", tt.input, tt.expectedRepo, repo)
+-		}
+-		if tag != tt.expectedTag {
+-			t.Errorf("ParseRepositoryTag(%q): wrong tag. Want %q. Got %q", tt.input, tt.expectedTag, tag)
+-		}
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/signal.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/signal.go
+deleted file mode 100644
+index 16aa003..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/signal.go
++++ /dev/null
+@@ -1,49 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 docker
+-
+-// Signal represents a signal that can be send to the container on
+-// KillContainer call.
+-type Signal int
+-
+-// These values represent all signals available on Linux, where containers will
+-// be running.
+-const (
+-	SIGABRT   = Signal(0x6)
+-	SIGALRM   = Signal(0xe)
+-	SIGBUS    = Signal(0x7)
+-	SIGCHLD   = Signal(0x11)
+-	SIGCLD    = Signal(0x11)
+-	SIGCONT   = Signal(0x12)
+-	SIGFPE    = Signal(0x8)
+-	SIGHUP    = Signal(0x1)
+-	SIGILL    = Signal(0x4)
+-	SIGINT    = Signal(0x2)
+-	SIGIO     = Signal(0x1d)
+-	SIGIOT    = Signal(0x6)
+-	SIGKILL   = Signal(0x9)
+-	SIGPIPE   = Signal(0xd)
+-	SIGPOLL   = Signal(0x1d)
+-	SIGPROF   = Signal(0x1b)
+-	SIGPWR    = Signal(0x1e)
+-	SIGQUIT   = Signal(0x3)
+-	SIGSEGV   = Signal(0xb)
+-	SIGSTKFLT = Signal(0x10)
+-	SIGSTOP   = Signal(0x13)
+-	SIGSYS    = Signal(0x1f)
+-	SIGTERM   = Signal(0xf)
+-	SIGTRAP   = Signal(0x5)
+-	SIGTSTP   = Signal(0x14)
+-	SIGTTIN   = Signal(0x15)
+-	SIGTTOU   = Signal(0x16)
+-	SIGUNUSED = Signal(0x1f)
+-	SIGURG    = Signal(0x17)
+-	SIGUSR1   = Signal(0xa)
+-	SIGUSR2   = Signal(0xc)
+-	SIGVTALRM = Signal(0x1a)
+-	SIGWINCH  = Signal(0x1c)
+-	SIGXCPU   = Signal(0x18)
+-	SIGXFSZ   = Signal(0x19)
+-)
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/stdcopy.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/stdcopy.go
+deleted file mode 100644
+index 3782f3d..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/stdcopy.go
++++ /dev/null
+@@ -1,91 +0,0 @@
+-// Copyright 2014 Docker authors. All rights reserved.
+-// Use of this source code is governed by a BSD-style
+-// license that can be found in the DOCKER-LICENSE file.
+-
+-package docker
+-
+-import (
+-	"encoding/binary"
+-	"errors"
+-	"io"
+-)
+-
+-const (
+-	stdWriterPrefixLen = 8
+-	stdWriterFdIndex   = 0
+-	stdWriterSizeIndex = 4
+-)
+-
+-var errInvalidStdHeader = errors.New("Unrecognized input header")
+-
+-func stdCopy(dstout, dsterr io.Writer, src io.Reader) (written int64, err error) {
+-	var (
+-		buf       = make([]byte, 32*1024+stdWriterPrefixLen+1)
+-		bufLen    = len(buf)
+-		nr, nw    int
+-		er, ew    error
+-		out       io.Writer
+-		frameSize int
+-	)
+-	for {
+-		for nr < stdWriterPrefixLen {
+-			var nr2 int
+-			nr2, er = src.Read(buf[nr:])
+-			if er == io.EOF {
+-				if nr < stdWriterPrefixLen && nr2 < stdWriterPrefixLen {
+-					return written, nil
+-				}
+-				nr += nr2
+-				break
+-			} else if er != nil {
+-				return 0, er
+-			}
+-			nr += nr2
+-		}
+-		switch buf[stdWriterFdIndex] {
+-		case 0:
+-			fallthrough
+-		case 1:
+-			out = dstout
+-		case 2:
+-			out = dsterr
+-		default:
+-			return 0, errInvalidStdHeader
+-		}
+-		frameSize = int(binary.BigEndian.Uint32(buf[stdWriterSizeIndex : stdWriterSizeIndex+4]))
+-		if frameSize+stdWriterPrefixLen > bufLen {
+-			buf = append(buf, make([]byte, frameSize+stdWriterPrefixLen-len(buf)+1)...)
+-			bufLen = len(buf)
+-		}
+-		for nr < frameSize+stdWriterPrefixLen {
+-			var nr2 int
+-			nr2, er = src.Read(buf[nr:])
+-			if er == io.EOF {
+-				if nr == 0 {
+-					return written, nil
+-				}
+-				nr += nr2
+-				break
+-			} else if er != nil {
+-				return 0, er
+-			}
+-			nr += nr2
+-		}
+-		bound := frameSize + stdWriterPrefixLen
+-		if bound > nr {
+-			bound = nr
+-		}
+-		nw, ew = out.Write(buf[stdWriterPrefixLen:bound])
+-		if nw > 0 {
+-			written += int64(nw)
+-		}
+-		if ew != nil {
+-			return 0, ew
+-		}
+-		if nw != frameSize {
+-			return written, io.ErrShortWrite
+-		}
+-		copy(buf, buf[frameSize+stdWriterPrefixLen:])
+-		nr -= frameSize + stdWriterPrefixLen
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/stdcopy_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/stdcopy_test.go
+deleted file mode 100644
+index 75b8922..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/stdcopy_test.go
++++ /dev/null
+@@ -1,255 +0,0 @@
+-// Copyright 2014 go-dockerclient authors. All rights reserved.
+-// Use of this source code is governed by a BSD-style
+-// license that can be found in the DOCKER-LICENSE file.
+-
+-package docker
+-
+-import (
+-	"bytes"
+-	"encoding/binary"
+-	"errors"
+-	"io"
+-	"strings"
+-	"testing"
+-	"testing/iotest"
+-)
+-
+-type errorWriter struct {
+-}
+-
+-func (errorWriter) Write([]byte) (int, error) {
+-	return 0, errors.New("something went wrong")
+-}
+-
+-func TestStdCopy(t *testing.T) {
+-	var input, stdout, stderr bytes.Buffer
+-	input.Write([]byte{2, 0, 0, 0, 0, 0, 0, 19})
+-	input.Write([]byte("something happened!"))
+-	input.Write([]byte{1, 0, 0, 0, 0, 0, 0, 12})
+-	input.Write([]byte("just kidding"))
+-	input.Write([]byte{0, 0, 0, 0, 0, 0, 0, 6})
+-	input.Write([]byte("\nyeah!"))
+-	n, err := stdCopy(&stdout, &stderr, &input)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if expected := int64(19 + 12 + 6); n != expected {
+-		t.Errorf("Wrong number of bytes. Want %d. Got %d.", expected, n)
+-	}
+-	if got := stderr.String(); got != "something happened!" {
+-		t.Errorf("stdCopy: wrong stderr. Want %q. Got %q.", "something happened!", got)
+-	}
+-	if got := stdout.String(); got != "just kidding\nyeah!" {
+-		t.Errorf("stdCopy: wrong stdout. Want %q. Got %q.", "just kidding\nyeah!", got)
+-	}
+-}
+-
+-func TestStdCopyStress(t *testing.T) {
+-	var input, stdout, stderr bytes.Buffer
+-	value := strings.Repeat("something ", 4096)
+-	writer := newStdWriter(&input, Stdout)
+-	writer.Write([]byte(value))
+-	n, err := stdCopy(&stdout, &stderr, &input)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if n != 40960 {
+-		t.Errorf("Wrong number of bytes. Want 40960. Got %d.", n)
+-	}
+-	if got := stderr.String(); got != "" {
+-		t.Errorf("stdCopy: wrong stderr. Want empty string. Got %q", got)
+-	}
+-	if got := stdout.String(); got != value {
+-		t.Errorf("stdCopy: wrong stdout. Want %q. Got %q", value, got)
+-	}
+-}
+-
+-func TestStdCopyInvalidStdHeader(t *testing.T) {
+-	var input, stdout, stderr bytes.Buffer
+-	input.Write([]byte{3, 0, 0, 0, 0, 0, 0, 19})
+-	n, err := stdCopy(&stdout, &stderr, &input)
+-	if n != 0 {
+-		t.Errorf("stdCopy: wrong number of bytes. Want 0. Got %d", n)
+-	}
+-	if err != errInvalidStdHeader {
+-		t.Errorf("stdCopy: wrong error. Want ErrInvalidStdHeader. Got %#v", err)
+-	}
+-}
+-
+-func TestStdCopyBigFrame(t *testing.T) {
+-	var input, stdout, stderr bytes.Buffer
+-	input.Write([]byte{2, 0, 0, 0, 0, 0, 0, 18})
+-	input.Write([]byte("something happened!"))
+-	n, err := stdCopy(&stdout, &stderr, &input)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if expected := int64(18); n != expected {
+-		t.Errorf("Wrong number of bytes. Want %d. Got %d.", expected, n)
+-	}
+-	if got := stderr.String(); got != "something happened" {
+-		t.Errorf("stdCopy: wrong stderr. Want %q. Got %q.", "something happened", got)
+-	}
+-	if got := stdout.String(); got != "" {
+-		t.Errorf("stdCopy: wrong stdout. Want %q. Got %q.", "", got)
+-	}
+-}
+-
+-func TestStdCopySmallFrame(t *testing.T) {
+-	var input, stdout, stderr bytes.Buffer
+-	input.Write([]byte{2, 0, 0, 0, 0, 0, 0, 20})
+-	input.Write([]byte("something happened!"))
+-	n, err := stdCopy(&stdout, &stderr, &input)
+-	if err != io.ErrShortWrite {
+-		t.Errorf("stdCopy: wrong error. Want ShortWrite. Got %#v", err)
+-	}
+-	if expected := int64(19); n != expected {
+-		t.Errorf("Wrong number of bytes. Want %d. Got %d.", expected, n)
+-	}
+-	if got := stderr.String(); got != "something happened!" {
+-		t.Errorf("stdCopy: wrong stderr. Want %q. Got %q.", "something happened", got)
+-	}
+-	if got := stdout.String(); got != "" {
+-		t.Errorf("stdCopy: wrong stdout. Want %q. Got %q.", "", got)
+-	}
+-}
+-
+-func TestStdCopyEmpty(t *testing.T) {
+-	var input, stdout, stderr bytes.Buffer
+-	n, err := stdCopy(&stdout, &stderr, &input)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if n != 0 {
+-		t.Errorf("stdCopy: wrong number of bytes. Want 0. Got %d.", n)
+-	}
+-}
+-
+-func TestStdCopyCorruptedHeader(t *testing.T) {
+-	var input, stdout, stderr bytes.Buffer
+-	input.Write([]byte{2, 0, 0, 0, 0})
+-	n, err := stdCopy(&stdout, &stderr, &input)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if n != 0 {
+-		t.Errorf("stdCopy: wrong number of bytes. Want 0. Got %d.", n)
+-	}
+-}
+-
+-func TestStdCopyTruncateWriter(t *testing.T) {
+-	var input, stdout, stderr bytes.Buffer
+-	input.Write([]byte{2, 0, 0, 0, 0, 0, 0, 19})
+-	input.Write([]byte("something happened!"))
+-	n, err := stdCopy(&stdout, iotest.TruncateWriter(&stderr, 7), &input)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if expected := int64(19); n != expected {
+-		t.Errorf("Wrong number of bytes. Want %d. Got %d.", expected, n)
+-	}
+-	if got := stderr.String(); got != "somethi" {
+-		t.Errorf("stdCopy: wrong stderr. Want %q. Got %q.", "somethi", got)
+-	}
+-	if got := stdout.String(); got != "" {
+-		t.Errorf("stdCopy: wrong stdout. Want %q. Got %q.", "", got)
+-	}
+-}
+-
+-func TestStdCopyHeaderOnly(t *testing.T) {
+-	var input, stdout, stderr bytes.Buffer
+-	input.Write([]byte{2, 0, 0, 0, 0, 0, 0, 19})
+-	n, err := stdCopy(&stdout, iotest.TruncateWriter(&stderr, 7), &input)
+-	if err != io.ErrShortWrite {
+-		t.Errorf("stdCopy: wrong error. Want ShortWrite. Got %#v", err)
+-	}
+-	if n != 0 {
+-		t.Errorf("Wrong number of bytes. Want 0. Got %d.", n)
+-	}
+-	if got := stderr.String(); got != "" {
+-		t.Errorf("stdCopy: wrong stderr. Want %q. Got %q.", "", got)
+-	}
+-	if got := stdout.String(); got != "" {
+-		t.Errorf("stdCopy: wrong stdout. Want %q. Got %q.", "", got)
+-	}
+-}
+-
+-func TestStdCopyDataErrReader(t *testing.T) {
+-	var input, stdout, stderr bytes.Buffer
+-	input.Write([]byte{2, 0, 0, 0, 0, 0, 0, 19})
+-	input.Write([]byte("something happened!"))
+-	n, err := stdCopy(&stdout, &stderr, iotest.DataErrReader(&input))
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if expected := int64(19); n != expected {
+-		t.Errorf("Wrong number of bytes. Want %d. Got %d.", expected, n)
+-	}
+-	if got := stderr.String(); got != "something happened!" {
+-		t.Errorf("stdCopy: wrong stderr. Want %q. Got %q.", "something happened!", got)
+-	}
+-	if got := stdout.String(); got != "" {
+-		t.Errorf("stdCopy: wrong stdout. Want %q. Got %q.", "", got)
+-	}
+-}
+-
+-func TestStdCopyTimeoutReader(t *testing.T) {
+-	var input, stdout, stderr bytes.Buffer
+-	input.Write([]byte{2, 0, 0, 0, 0, 0, 0, 19})
+-	input.Write([]byte("something happened!"))
+-	_, err := stdCopy(&stdout, &stderr, iotest.TimeoutReader(&input))
+-	if err != iotest.ErrTimeout {
+-		t.Errorf("stdCopy: wrong error. Want ErrTimeout. Got %#v.", err)
+-	}
+-}
+-
+-func TestStdCopyWriteError(t *testing.T) {
+-	var input bytes.Buffer
+-	input.Write([]byte{2, 0, 0, 0, 0, 0, 0, 19})
+-	input.Write([]byte("something happened!"))
+-	var stdout, stderr errorWriter
+-	n, err := stdCopy(stdout, stderr, &input)
+-	if err.Error() != "something went wrong" {
+-		t.Errorf("stdCopy: wrong error. Want %q. Got %q", "something went wrong", err)
+-	}
+-	if n != 0 {
+-		t.Errorf("stdCopy: wrong number of bytes. Want 0. Got %d.", n)
+-	}
+-}
+-
+-type StdType [8]byte
+-
+-var (
+-	Stdin  = StdType{0: 0}
+-	Stdout = StdType{0: 1}
+-	Stderr = StdType{0: 2}
+-)
+-
+-type StdWriter struct {
+-	io.Writer
+-	prefix  StdType
+-	sizeBuf []byte
+-}
+-
+-func (w *StdWriter) Write(buf []byte) (n int, err error) {
+-	if w == nil || w.Writer == nil {
+-		return 0, errors.New("Writer not instanciated")
+-	}
+-	binary.BigEndian.PutUint32(w.prefix[4:], uint32(len(buf)))
+-	buf = append(w.prefix[:], buf...)
+-
+-	n, err = w.Writer.Write(buf)
+-	return n - 8, err
+-}
+-
+-func newStdWriter(w io.Writer, t StdType) *StdWriter {
+-	if len(t) != 8 {
+-		return nil
+-	}
+-
+-	return &StdWriter{
+-		Writer:  w,
+-		prefix:  t,
+-		sizeBuf: make([]byte, 4),
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/tar.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/tar.go
+deleted file mode 100644
+index 7c4a204..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/tar.go
++++ /dev/null
+@@ -1,99 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 docker
+-
+-import (
+-	"fmt"
+-	"io"
+-	"io/ioutil"
+-	"os"
+-	"path"
+-	"path/filepath"
+-	"strings"
+-
+-	"github.com/docker/docker/pkg/archive"
+-	"github.com/docker/docker/pkg/fileutils"
+-)
+-
+-func createTarStream(srcPath string) (io.ReadCloser, error) {
+-	excludes, err := parseDockerignore(srcPath)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	if err := validateContextDirectory(srcPath, excludes); err != nil {
+-		return nil, err
+-	}
+-	tarOpts := &archive.TarOptions{
+-		Excludes:    excludes,
+-		Compression: archive.Uncompressed,
+-		NoLchown:    true,
+-	}
+-	return archive.TarWithOptions(srcPath, tarOpts)
+-}
+-
+-// validateContextDirectory checks if all the contents of the directory
+-// can be read and returns an error if some files can't be read.
+-// Symlinks which point to non-existing files don't trigger an error
+-func validateContextDirectory(srcPath string, excludes []string) error {
+-	return filepath.Walk(filepath.Join(srcPath, "."), func(filePath string, f os.FileInfo, err error) error {
+-		// skip this directory/file if it's not in the path, it won't get added to the context
+-		if relFilePath, err := filepath.Rel(srcPath, filePath); err != nil {
+-			return err
+-		} else if skip, err := fileutils.Matches(relFilePath, excludes); err != nil {
+-			return err
+-		} else if skip {
+-			if f.IsDir() {
+-				return filepath.SkipDir
+-			}
+-			return nil
+-		}
+-
+-		if err != nil {
+-			if os.IsPermission(err) {
+-				return fmt.Errorf("can't stat '%s'", filePath)
+-			}
+-			if os.IsNotExist(err) {
+-				return nil
+-			}
+-			return err
+-		}
+-
+-		// skip checking if symlinks point to non-existing files, such symlinks can be useful
+-		// also skip named pipes, because they hanging on open
+-		if f.Mode()&(os.ModeSymlink|os.ModeNamedPipe) != 0 {
+-			return nil
+-		}
+-
+-		if !f.IsDir() {
+-			currentFile, err := os.Open(filePath)
+-			if err != nil && os.IsPermission(err) {
+-				return fmt.Errorf("no permission to read from '%s'", filePath)
+-			}
+-			currentFile.Close()
+-		}
+-		return nil
+-	})
+-}
+-
+-func parseDockerignore(root string) ([]string, error) {
+-	var excludes []string
+-	ignore, err := ioutil.ReadFile(path.Join(root, ".dockerignore"))
+-	if err != nil && !os.IsNotExist(err) {
+-		return excludes, fmt.Errorf("error reading .dockerignore: '%s'", err)
+-	}
+-	for _, pattern := range strings.Split(string(ignore), "\n") {
+-		matches, err := filepath.Match(pattern, "Dockerfile")
+-		if err != nil {
+-			return excludes, fmt.Errorf("bad .dockerignore pattern: '%s', error: %s", pattern, err)
+-		}
+-		if matches {
+-			return excludes, fmt.Errorf("dockerfile was excluded by .dockerignore pattern '%s'", pattern)
+-		}
+-		excludes = append(excludes, pattern)
+-	}
+-
+-	return excludes, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/bin/fmtpolice b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/bin/fmtpolice
+deleted file mode 100644
+index d13bd0c..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/bin/fmtpolice
++++ /dev/null
+@@ -1,38 +0,0 @@
+-#!/bin/bash
+-
+-readonly GOPATH="${GOPATH%%:*}"
+-
+-main() {
+-  check_fmt
+-  check_lint
+-}
+-
+-check_fmt() {
+-  eval "set -e"
+-  for file in $(git ls-files '*.go') ; do
+-    gofmt $file | diff -u $file -
+-  done
+-  eval "set +e"
+-}
+-
+-check_lint() {
+-  _install_linter
+-
+-  for file in $(git ls-files '*.go') ; do
+-    if [[ ! "$(${GOPATH}/bin/golint $file)" =~ ^[[:blank:]]*$ ]] ; then
+-      _lint_verbose && exit 1
+-    fi
+-  done
+-}
+-
+-_lint_verbose() {
+-  for file in $(git ls-files '*.go') ; do $GOPATH/bin/golint $file ; done
+-}
+-
+-_install_linter() {
+-  if [[ ! -x "${GOPATH}/bin/golint" ]] ; then
+-    go get -u github.com/golang/lint/golint
+-  fi
+-}
+-
+-main "$@"
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/.dockerignore b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/.dockerignore
+deleted file mode 100644
+index 027e8c2..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/.dockerignore
++++ /dev/null
+@@ -1,3 +0,0 @@
+-container.tar
+-dockerfile.tar
+-foofile
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/Dockerfile b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/Dockerfile
+deleted file mode 100644
+index 0948dcf..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/Dockerfile
++++ /dev/null
+@@ -1,15 +0,0 @@
+-# this file describes how to build tsuru python image
+-# to run it:
+-# 1- install docker
+-# 2- run: $ docker build -t tsuru/python https://raw.github.com/tsuru/basebuilder/master/python/Dockerfile
+-
+-from	base:ubuntu-quantal
+-run	apt-get install wget -y --force-yes
+-run	wget http://github.com/tsuru/basebuilder/tarball/master -O basebuilder.tar.gz --no-check-certificate
+-run	mkdir /var/lib/tsuru
+-run	tar -xvf basebuilder.tar.gz -C /var/lib/tsuru --strip 1
+-run	cp /var/lib/tsuru/python/deploy /var/lib/tsuru
+-run	cp /var/lib/tsuru/base/restart /var/lib/tsuru
+-run	cp /var/lib/tsuru/base/start /var/lib/tsuru
+-run	/var/lib/tsuru/base/install
+-run	/var/lib/tsuru/base/setup
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/barfile b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/barfile
+deleted file mode 100644
+index e69de29..0000000
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/ca.pem b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/ca.pem
+deleted file mode 100644
+index 8e38bba..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/ca.pem
++++ /dev/null
+@@ -1,18 +0,0 @@
+------BEGIN CERTIFICATE-----
+-MIIC1TCCAb+gAwIBAgIQJ9MsNxrUxumNbAytGi3GEDALBgkqhkiG9w0BAQswFjEU
+-MBIGA1UEChMLQm9vdDJEb2NrZXIwHhcNMTQxMDE2MjAyMTM4WhcNMTcwOTMwMjAy
+-MTM4WjAWMRQwEgYDVQQKEwtCb290MkRvY2tlcjCCASIwDQYJKoZIhvcNAQEBBQAD
+-ggEPADCCAQoCggEBALpFCSARjG+5yXoqr7UMzuE0df7RRZfeRZI06lJ02ZqV4Iii
+-rgL7ML9yPxX50NbLnjiilSDTUhnyocYFItokzUzz8qpX/nlYhuN2Iqwh4d0aWS8z
+-f5y248F+H1z+HY2W8NPl/6DVlVwYaNW1/k+RPMlHS0INLR6j+3Ievew7RNE0NnM2
+-znELW6NetekDt3GUcz0Z95vDUDfdPnIk1eIFMmYvLxZh23xOca4Q37a3S8F3d+dN
+-+OOpwjdgY9Qme0NQUaXpgp58jWuQfB8q7mZrdnLlLqRa8gx1HeDSotX7UmWtWPkb
+-vd9EdlKLYw5PVpxMV1rkwf2t4TdgD5NfkpXlXkkCAwEAAaMjMCEwDgYDVR0PAQH/
+-BAQDAgCkMA8GA1UdEwEB/wQFMAMBAf8wCwYJKoZIhvcNAQELA4IBAQBxYjHVSKqE
+-MJw7CW0GddesULtXXVWGJuZdWJLQlPvPMfIfjIvlcZyS4cdVNiQ3sREFIZz8TpII
+-CT0/Pg3sgv/FcOQe1CN0xZYZcyiAZHK1z0fJQq2qVpdv7+tJcjI2vvU6NI24iQCo
+-W1wz25trJz9QbdB2MRLMjyz7TSWuafztIvcfEzaIdQ0Whqund/cSuPGQx5IwF83F
+-rvlkOyJSH2+VIEBTCIuykJeL0DLTt8cePBQR5L1ISXb4RUMK9ZtqRscBRv8sn7o2
+-ixG3wtL0gYF4xLtsQWVxI3iFVrU3WzOH/3c5shVRkWBd+AQRSwCJI4mKH7penJCF
+-i3/zzlkvOnjV
+------END CERTIFICATE-----
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/cert.pem b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/cert.pem
+deleted file mode 100644
+index 5e7244b..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/cert.pem
++++ /dev/null
+@@ -1,18 +0,0 @@
+------BEGIN CERTIFICATE-----
+-MIIC6DCCAdKgAwIBAgIRANO6ymxQAjp66KmEka1G6b0wCwYJKoZIhvcNAQELMBYx
+-FDASBgNVBAoTC0Jvb3QyRG9ja2VyMB4XDTE0MTAxNjIwMjE1MloXDTE3MDkzMDIw
+-MjE1MlowFjEUMBIGA1UEChMLQm9vdDJEb2NrZXIwggEiMA0GCSqGSIb3DQEBAQUA
+-A4IBDwAwggEKAoIBAQDGA1mAhSOpZspD1dpZ7qVEQrIJw4Xo8252jHaORnEdDiFm
+-b6brEmr6jw8t4P3IGxbqBc/TqRV+SSXxwYEVvfpeQKH+SmqStoMNtD3Ura161az4
+-V0BcxMtSlsUGpoz+//QCAq8qiaxMwgiyc5253mkQm88anj2cNt7xbewiu/KFWuf7
+-BVpNK1+ltpJmlukfcj/G+I1bw7j1KxBjDrFqe5cyDuuZcDL2tmUXP/ZWDyXwSv+H
+-AOckqn44z6aXlBkVvOXDBZJqY76d/vWVDNCuZeXRnqlhP3t1kH4V0RQXo+JD2tgt
+-JgdU0unzyoFOSWNUBPm73tqmjUGGAmGHBmeegJr/AgMBAAGjNTAzMA4GA1UdDwEB
+-/wQEAwIAgDATBgNVHSUEDDAKBggrBgEFBQcDAjAMBgNVHRMBAf8EAjAAMAsGCSqG
+-SIb3DQEBCwOCAQEABVTWl5SmBP+j5He5bQsgnIXjviSKqe40/10V4LJAOmilycRF
+-zLrzM+YMwfjg6PLIs8CldAMWHw9y9ktZY4MxkgCktaiaN/QmMTMwFWEcN4wy5IpM
+-U5l93eAg7xsnY430h3QBBADujX4wdF3fs8rSL8zAAQFL0ihurwU124K3yXKsrwpb
+-CiVUGfIN4sPwjy8Ws9oxHFDC9/P8lgjHZ1nBIf8KSHnMzlxDGj7isQfhtH+7mcCL
+-cM1qO2NirS2v7uaEPPY+MJstAz+W7EJCW9dfMSmHna2SDC37Xkin7uEY9z+qaKFL
+-8d/XxOB/L8Ucy8VZhdsv0dsBq5KfJntITM0ksQ==
+------END CERTIFICATE-----
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/container.tar b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/container.tar
+deleted file mode 100644
+index e4b066e3b6df8cb78ac445a34234f3780d164cf4..0000000000000000000000000000000000000000
+GIT binary patch
+literal 0
+HcmV?d00001
+
+literal 2048
+zcmeH_Q3``F42FH)DgF~kTC`qZ7s*`9%A^%r$Bu89Fp<6NMew1akmheFe?H>)Y5N#5
+z`(UT)m>?q4G^iwZ#(XmAwH8Ujv`|_rQd)Ig3sQ!(szArs+5bAH%#&Di1HU}iJx_zp
+z+3uU9k~Zgl)J<3?S%)LS_Hgc7e)t4AX&%Rz>>WAcX2Ec>82D}md=O1Y)p%bo=N_rJ
+OD+CIGLZA@%gTMmt=q{T8
+
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/dockerfile.tar b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/dockerfile.tar
+deleted file mode 100644
+index 32c9ce64704835cd096b85ac44c35b5087b5ccdd..0000000000000000000000000000000000000000
+GIT binary patch
+literal 0
+HcmV?d00001
+
+literal 2560
+zcmeHGy>8<$49;3V1%d0TNOs}`$a>xT46-c8LTt+?QB8ACf0XPiQll-<p+kUZFvXvb
+z{76$zR-LqKOs7{rc7zbS?G{!f_q$z^qL_3tiM%LE$cs&}-<R8RFF at p*a#OBA{1~IF
+z#KEI<M2)`Q_$$ZaN?}d2uwARM6CtMNqP&sw3$QgF;sQXey>h0~9$I?_v`_`p)qp;@
+z0OJK)JAmosQD=m*-~y?5ASGvD1{zS;L7n!AYz2z}2Y8%Kb25fgK0fDb5l4UE+{yF$
+zXs`{{TG^hbn!J);Cl1>2UV0=k!T8hL+GbhfZ2u5L51|SJ2KFb&fyiW3|3Qw(jvC+i
+zouk4oz*u9Q((Iyric9uLhPZsmgZ8ANMrS_2p5cn+n!M}dU&=mMrdq8|OlgOvF-oFN
+zh5A!%9Pk(EcxS4q(c~Z~u-BL7!+gIN2&&-GnGy1YRpY|{e@?X?J9}9;KY_$PxYO}H
+o;5QJT#=q||{Y*ZuNn-Gk-)jtGb|Y`+PV+v2`vmS2xaA4_1I+dVl>h($
+
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/foofile b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/foofile
+deleted file mode 100644
+index e69de29..0000000
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/key.pem b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/key.pem
+deleted file mode 100644
+index a9346bc..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/key.pem
++++ /dev/null
+@@ -1,27 +0,0 @@
+------BEGIN RSA PRIVATE KEY-----
+-MIIEowIBAAKCAQEAxgNZgIUjqWbKQ9XaWe6lREKyCcOF6PNudox2jkZxHQ4hZm+m
+-6xJq+o8PLeD9yBsW6gXP06kVfkkl8cGBFb36XkCh/kpqkraDDbQ91K2tetWs+FdA
+-XMTLUpbFBqaM/v/0AgKvKomsTMIIsnOdud5pEJvPGp49nDbe8W3sIrvyhVrn+wVa
+-TStfpbaSZpbpH3I/xviNW8O49SsQYw6xanuXMg7rmXAy9rZlFz/2Vg8l8Er/hwDn
+-JKp+OM+ml5QZFbzlwwWSamO+nf71lQzQrmXl0Z6pYT97dZB+FdEUF6PiQ9rYLSYH
+-VNLp88qBTkljVAT5u97apo1BhgJhhwZnnoCa/wIDAQABAoIBAQCaGy9EC9pmU95l
+-DwGh7k5nIrUnTilg1FwLHWSDdCVCZKXv8ENrPelOWZqJrUo1u4eI2L8XTsewgkNq
+-tJu/DRzWz9yDaO0qg6rZNobMh+K076lvmZA44twOydJLS8H+D7ua+PXU2FLlZjmY
+-kMyXRJZmW6zCXZc7haTbJx6ZJccoquk/DkS4FcFurJP177u1YrWS9TTw9kensUtU
+-jQ63uf56UTN1i+0+Rxl7OW1TZlqwlri5I4njg5249+FxwwHzIq8+l7zD7K9pl8c/
+-nG1HuulvU2bVlDlRdyslMPAH34vw9Sku1BD8furrJLr1na5lRSLKJODEaIPEsLwv
+-CdEUwP9JAoGBAO76ZW80RyNB2fA+wbTq70Sr8CwrXxYemXrez5LKDC7SsohKFCPE
+-IedpO/n+nmymiiJvMm874EExoG6BVrbkWkeb+2vinEfOQNlDMsDx7WLjPekP3t6i
+-rXHO3CjFooVFq2z3mZa/Nc5NZqu8fNWNCKJxZDJphdoj6sORNJIUvZVjAoGBANQd
+-++J+ITcu3/+A6JrGcgLunBFQYPqkiItk0J4QKYKuX5ik9rWcQDN8TTtfW2mDuiQ4
+-NrCwuVPq1V1kB16JzH017SsYLo9g8I20YjnBZge9pKTeUaLVTb3C50LW8FBylop0
+-Bnm597dNbtSjphjoTMg0XyC19o3Esf2YeWG0QNS1AoGAWWDfFRNJU99qIldmXULM
+-0DM6NVrXSk+ReYnhunXEzrJQwXZrR+EwCPurydk36Uz0NuK9yypquhdUeF/5TZfk
+-SAoHo5byekyipl9imRUigqyY2BTudvgCxKDoaHtaSFwBPFTyZZYICquaLbrmOXxw
+-8UhVgCFFRYvPXuts7QHC0h8CgYBWEvy9gfU0kV7wLX02IUTuj6jhFb7ktpN6DSTi
+-nyhZES1VoctDEu6ydcRZTW6ouH12aSE4Pd5WgTqntQmQgVZrkNB25k8ue2Xh+srJ
+-KQOgLIJ9LIHwE6KCWG7DnrjRzE3uTPq7to0g4tkQjH/AJ7PQof/gJDayfJjFkXPg
+-A+cy6QKBgEPbKpiqscm03gT2QanBut5pg4dqPOxp0SlErA3kSFNTRK3oYBQPC+LH
+-qA5nD5brdkeNBB58Rll8Zpzxiff50bcvLP/7/Sb3NjaXFTEY0gVbdRof3n6N0YP3
+-Hu5XDNJ9RNkNzE5RIG1g86KE+aKlcrKMaigqAiuIy2PSnjkQeGk8
+------END RSA PRIVATE KEY-----
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/server.pem b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/server.pem
+deleted file mode 100644
+index 89cc445..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/server.pem
++++ /dev/null
+@@ -1,18 +0,0 @@
+------BEGIN CERTIFICATE-----
+-MIIC/DCCAeagAwIBAgIQMUILcXtvmSOK63zEBo0VXzALBgkqhkiG9w0BAQswFjEU
+-MBIGA1UEChMLQm9vdDJEb2NrZXIwHhcNMTQxMDE2MjAyMTQ2WhcNMTcwOTMwMjAy
+-MTQ2WjAWMRQwEgYDVQQKEwtCb290MkRvY2tlcjCCASIwDQYJKoZIhvcNAQEBBQAD
+-ggEPADCCAQoCggEBANxUOUhNnqFnrTlLsBYzfFRZWQo268l+4K4lOJCVbfDonP3g
+-Mz0vGi9fcyFqEWSA8Y+ShXna625HTnReCwFdsu0861qCIq7v95hFFCyOe0iIxpd0
+-AKLnl90d+1vonE7andgFgoobbTiMly4UK4H6z8D148fFNIihoteOG3PIF89TFxP7
+-CJ/3wXnx/IKpdlO8PAnub3tBPJHvGDj7KORLy4IBxRX5VBAdfGNybE66fcrehEva
+-rLA4m9pgiaR/Nnr9FdKhPyqYdjflLNvzydxNvMIV4M0hFlhXmYvpMjA5/XsTnsyV
+-t9JHJa5Upwqsbne08t7rsm7liZNxZlko8xPOTQcCAwEAAaNKMEgwDgYDVR0PAQH/
+-BAQDAgCgMAwGA1UdEwEB/wQCMAAwKAYDVR0RBCEwH4ILYm9vdDJkb2NrZXKHBH8A
+-AAGHBAoAAg+HBMCoO2cwCwYJKoZIhvcNAQELA4IBAQAYoYcDkDWkl73FZ0WnPmAj
+-LiF7HU95Qg3KyEpFsAJeShSLPPbQntmwhdekEzY4tQ3eKQB/+zHFjzsCr/lmDUmH
+-Ea/ryQ17C+jyH+Ykg0IWW6L6veZhvRDg6Z9focVtPVBRxPTqC/Qhb54blWRASV+W
+-UreMuXQ5+1dQptAM7ixOeLVHjBi/bd9TL3jvwBVCr9QedteMjjK4TCF9Tbcou+MF
+-2w3OJJZMDhcD+YwoK9uJDqlKmcTm/vVMbSsp/pTMcnQ7jxCeR8/XyX+VwTZwaHAa
+-o92Q/eg3THAiWhvyT/SzyH9dHHBAyXynUwGCggKawHktfvW4QXRPuLxLrJ7iB5cy
+------END CERTIFICATE-----
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/serverkey.pem b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/serverkey.pem
+deleted file mode 100644
+index c897e5d..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/serverkey.pem
++++ /dev/null
+@@ -1,27 +0,0 @@
+------BEGIN RSA PRIVATE KEY-----
+-MIIEoAIBAAKCAQEA3FQ5SE2eoWetOUuwFjN8VFlZCjbryX7griU4kJVt8Oic/eAz
+-PS8aL19zIWoRZIDxj5KFedrrbkdOdF4LAV2y7TzrWoIiru/3mEUULI57SIjGl3QA
+-oueX3R37W+icTtqd2AWCihttOIyXLhQrgfrPwPXjx8U0iKGi144bc8gXz1MXE/sI
+-n/fBefH8gql2U7w8Ce5ve0E8ke8YOPso5EvLggHFFflUEB18Y3JsTrp9yt6ES9qs
+-sDib2mCJpH82ev0V0qE/Kph2N+Us2/PJ3E28whXgzSEWWFeZi+kyMDn9exOezJW3
+-0kclrlSnCqxud7Ty3uuybuWJk3FmWSjzE85NBwIDAQABAoIBAG0ak+cW8LeShHf7
+-3+2Of0GxoOLrAWWdG5uAuPr31CJYve0FybnBimDtDjD8ujIfm/7xmoEWBEFutA3x
+-x9dcU88gvJbsHEqub9gKVQwfXjMz78tt2SbSMiR/xUnk7QorPcCMMfE71aEMFYzu
+-1gCed6Rg3vO81t/V0rKVH0j9S7UQz5v/oX15eVDV5LOqyCHwAi6K0eXXbqnbI0TH
+-SOQ/nexM2msVXWbO9t6ra6f5V7FXziDK5Xi+rPxRbX9mkrDzxDAevfuRqYBx5vtL
+-W2Q2hKjUAHFgXFniNSZBS7dCdAtz0el/3ct+cNmpuTMhhs7M6wC1CuYiZ/DxLiFh
+-Si73VckCgYEA+/ceh3+VjtQ0rgEw8sD9bqYEA8IaBiObjneIoFnKBYRG7yZd8JMm
+-HD4M/aQ1qhcRLPN7GR03YQULgQJURbKSjJHnhfTXHyeHC3NN4gMVHQXewu2MHCh6
+-7FCQ9CfK0KcYLgegVVvL3PrF3hyWGnmTu+G0UkDQRYVnaNrB7snrW6UCgYEA39tq
+-+MCQdu0moJ5szSZf02undg9EeW6isk9qzi7TId3/MLci2eH7PEnipipPUK3+DERq
+-aba0y0TKgBR2EXvXLFJA/+kfdo2loIEHOfox85HVfxgUaFRti63ZI0uF8D0QT2Yy
+-oJal+RFghVoSnv4LjhRKEPbIkScTXGjdK+7wFjsCfz79iKRXQQx0ALd/lL0bgkAn
+-QNmvrNHcFQeI2p8700WNzC39aX67SsvEt3qxkrjzC1gxhpTAuReIK1gVPPwvqHN8
+-BmV20FD5kMlMCix2mNCopwgUWvKvLAvoGFTxncKMA39+aJbuXAjiqJTekKgNvOE7
+-i9kEWw0GTNPp3JHV6QECgYAPwb0M11kT1euDIMOdyRazpf86kyaJuZzgGjD1ZFxe
+-JOcigbGFTp/FhZnbglzk2+pm6KXo3QBq0mPCki4hWusxZnTGzpz1VlETNCHTFeZQ
+-M7KoaIR/N3oie9Et59H8r/+m5xWnMhNqratyl316DX24uXrhKM3DUdHODl+LCR2D
+-IwKBgE1MbHuwolUPEw3HeO4R7NMFVTFei7E/fpUsimPfArGg8UydwvloNT1myJos
+-N2JzfGGjN2KPVcBk9fOs71mJ6VcK3C3g5JIccplk6h9VNaw55+zdQvKPTzoBoTvy
+-A+Fwx2AlF61KeRF87DL2YTRJ6B9MHmWgf7+GVZOxomLgEAcZ
+------END RSA PRIVATE KEY-----
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/symlink b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/symlink
+deleted file mode 120000
+index 3ddf86a..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/symlink
++++ /dev/null
+@@ -1 +0,0 @@
+-doesnotexist
+\ No newline at end of file
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/server.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/server.go
+deleted file mode 100644
+index da24fb2..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/server.go
++++ /dev/null
+@@ -1,744 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 testing provides a fake implementation of the Docker API, useful for
+-// testing purpose.
+-package testing
+-
+-import (
+-	"archive/tar"
+-	"crypto/rand"
+-	"encoding/json"
+-	"errors"
+-	"fmt"
+-	mathrand "math/rand"
+-	"net"
+-	"net/http"
+-	"regexp"
+-	"strconv"
+-	"strings"
+-	"sync"
+-	"time"
+-
+-	"github.com/fsouza/go-dockerclient"
+-	"github.com/gorilla/mux"
+-)
+-
+-// DockerServer represents a programmable, concurrent (not much), HTTP server
+-// implementing a fake version of the Docker remote API.
+-//
+-// It can used in standalone mode, listening for connections or as an arbitrary
+-// HTTP handler.
+-//
+-// For more details on the remote API, check http://goo.gl/G3plxW.
+-type DockerServer struct {
+-	containers     []*docker.Container
+-	execs          []*docker.Exec
+-	cMut           sync.RWMutex
+-	images         []docker.Image
+-	iMut           sync.RWMutex
+-	imgIDs         map[string]string
+-	listener       net.Listener
+-	mux            *mux.Router
+-	hook           func(*http.Request)
+-	failures       map[string]string
+-	customHandlers map[string]http.Handler
+-	handlerMutex   sync.RWMutex
+-	cChan          chan<- *docker.Container
+-}
+-
+-// NewServer returns a new instance of the fake server, in standalone mode. Use
+-// the method URL to get the URL of the server.
+-//
+-// It receives the bind address (use 127.0.0.1:0 for getting an available port
+-// on the host), a channel of containers and a hook function, that will be
+-// called on every request.
+-//
+-// The fake server will send containers in the channel whenever the container
+-// changes its state, via the HTTP API (i.e.: create, start and stop). This
+-// channel may be nil, which means that the server won't notify on state
+-// changes.
+-func NewServer(bind string, containerChan chan<- *docker.Container, hook func(*http.Request)) (*DockerServer, error) {
+-	listener, err := net.Listen("tcp", bind)
+-	if err != nil {
+-		return nil, err
+-	}
+-	server := DockerServer{
+-		listener:       listener,
+-		imgIDs:         make(map[string]string),
+-		hook:           hook,
+-		failures:       make(map[string]string),
+-		customHandlers: make(map[string]http.Handler),
+-		cChan:          containerChan,
+-	}
+-	server.buildMuxer()
+-	go http.Serve(listener, &server)
+-	return &server, nil
+-}
+-
+-func (s *DockerServer) notify(container *docker.Container) {
+-	if s.cChan != nil {
+-		s.cChan <- container
+-	}
+-}
+-
+-func (s *DockerServer) buildMuxer() {
+-	s.mux = mux.NewRouter()
+-	s.mux.Path("/commit").Methods("POST").HandlerFunc(s.handlerWrapper(s.commitContainer))
+-	s.mux.Path("/containers/json").Methods("GET").HandlerFunc(s.handlerWrapper(s.listContainers))
+-	s.mux.Path("/containers/create").Methods("POST").HandlerFunc(s.handlerWrapper(s.createContainer))
+-	s.mux.Path("/containers/{id:.*}/json").Methods("GET").HandlerFunc(s.handlerWrapper(s.inspectContainer))
+-	s.mux.Path("/containers/{id:.*}/top").Methods("GET").HandlerFunc(s.handlerWrapper(s.topContainer))
+-	s.mux.Path("/containers/{id:.*}/start").Methods("POST").HandlerFunc(s.handlerWrapper(s.startContainer))
+-	s.mux.Path("/containers/{id:.*}/kill").Methods("POST").HandlerFunc(s.handlerWrapper(s.stopContainer))
+-	s.mux.Path("/containers/{id:.*}/stop").Methods("POST").HandlerFunc(s.handlerWrapper(s.stopContainer))
+-	s.mux.Path("/containers/{id:.*}/pause").Methods("POST").HandlerFunc(s.handlerWrapper(s.pauseContainer))
+-	s.mux.Path("/containers/{id:.*}/unpause").Methods("POST").HandlerFunc(s.handlerWrapper(s.unpauseContainer))
+-	s.mux.Path("/containers/{id:.*}/wait").Methods("POST").HandlerFunc(s.handlerWrapper(s.waitContainer))
+-	s.mux.Path("/containers/{id:.*}/attach").Methods("POST").HandlerFunc(s.handlerWrapper(s.attachContainer))
+-	s.mux.Path("/containers/{id:.*}").Methods("DELETE").HandlerFunc(s.handlerWrapper(s.removeContainer))
+-	s.mux.Path("/containers/{id:.*}/exec").Methods("POST").HandlerFunc(s.handlerWrapper(s.createExecContainer))
+-	s.mux.Path("/exec/{id:.*}/start").Methods("POST").HandlerFunc(s.handlerWrapper(s.startExecContainer))
+-	s.mux.Path("/images/create").Methods("POST").HandlerFunc(s.handlerWrapper(s.pullImage))
+-	s.mux.Path("/build").Methods("POST").HandlerFunc(s.handlerWrapper(s.buildImage))
+-	s.mux.Path("/images/json").Methods("GET").HandlerFunc(s.handlerWrapper(s.listImages))
+-	s.mux.Path("/images/{id:.*}").Methods("DELETE").HandlerFunc(s.handlerWrapper(s.removeImage))
+-	s.mux.Path("/images/{name:.*}/json").Methods("GET").HandlerFunc(s.handlerWrapper(s.inspectImage))
+-	s.mux.Path("/images/{name:.*}/push").Methods("POST").HandlerFunc(s.handlerWrapper(s.pushImage))
+-	s.mux.Path("/images/{name:.*}/tag").Methods("POST").HandlerFunc(s.handlerWrapper(s.tagImage))
+-	s.mux.Path("/events").Methods("GET").HandlerFunc(s.listEvents)
+-	s.mux.Path("/_ping").Methods("GET").HandlerFunc(s.handlerWrapper(s.pingDocker))
+-	s.mux.Path("/images/load").Methods("POST").HandlerFunc(s.handlerWrapper(s.loadImage))
+-	s.mux.Path("/images/{id:.*}/get").Methods("GET").HandlerFunc(s.handlerWrapper(s.getImage))
+-}
+-
+-// PrepareFailure adds a new expected failure based on a URL regexp it receives
+-// an id for the failure.
+-func (s *DockerServer) PrepareFailure(id string, urlRegexp string) {
+-	s.failures[id] = urlRegexp
+-}
+-
+-// ResetFailure removes an expected failure identified by the given id.
+-func (s *DockerServer) ResetFailure(id string) {
+-	delete(s.failures, id)
+-}
+-
+-// CustomHandler registers a custom handler for a specific path.
+-//
+-// For example:
+-//
+-//     server.CustomHandler("/containers/json", http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+-//         http.Error(w, "Something wrong is not right", http.StatusInternalServerError)
+-//     }))
+-func (s *DockerServer) CustomHandler(path string, handler http.Handler) {
+-	s.handlerMutex.Lock()
+-	s.customHandlers[path] = handler
+-	s.handlerMutex.Unlock()
+-}
+-
+-// MutateContainer changes the state of a container, returning an error if the
+-// given id does not match to any container "running" in the server.
+-func (s *DockerServer) MutateContainer(id string, state docker.State) error {
+-	for _, container := range s.containers {
+-		if container.ID == id {
+-			container.State = state
+-			return nil
+-		}
+-	}
+-	return errors.New("container not found")
+-}
+-
+-// Stop stops the server.
+-func (s *DockerServer) Stop() {
+-	if s.listener != nil {
+-		s.listener.Close()
+-	}
+-}
+-
+-// URL returns the HTTP URL of the server.
+-func (s *DockerServer) URL() string {
+-	if s.listener == nil {
+-		return ""
+-	}
+-	return "http://" + s.listener.Addr().String() + "/"
+-}
+-
+-// ServeHTTP handles HTTP requests sent to the server.
+-func (s *DockerServer) ServeHTTP(w http.ResponseWriter, r *http.Request) {
+-	s.handlerMutex.RLock()
+-	defer s.handlerMutex.RUnlock()
+-	if handler, ok := s.customHandlers[r.URL.Path]; ok {
+-		handler.ServeHTTP(w, r)
+-		return
+-	}
+-	s.mux.ServeHTTP(w, r)
+-	if s.hook != nil {
+-		s.hook(r)
+-	}
+-}
+-
+-// DefaultHandler returns default http.Handler mux, it allows customHandlers to
+-// call the default behavior if wanted.
+-func (s *DockerServer) DefaultHandler() http.Handler {
+-	return s.mux
+-}
+-
+-func (s *DockerServer) handlerWrapper(f func(http.ResponseWriter, *http.Request)) func(http.ResponseWriter, *http.Request) {
+-	return func(w http.ResponseWriter, r *http.Request) {
+-		for errorID, urlRegexp := range s.failures {
+-			matched, err := regexp.MatchString(urlRegexp, r.URL.Path)
+-			if err != nil {
+-				http.Error(w, err.Error(), http.StatusBadRequest)
+-				return
+-			}
+-			if !matched {
+-				continue
+-			}
+-			http.Error(w, errorID, http.StatusBadRequest)
+-			return
+-		}
+-		f(w, r)
+-	}
+-}
+-
+-func (s *DockerServer) listContainers(w http.ResponseWriter, r *http.Request) {
+-	all := r.URL.Query().Get("all")
+-	s.cMut.RLock()
+-	result := make([]docker.APIContainers, len(s.containers))
+-	for i, container := range s.containers {
+-		if all == "1" || container.State.Running {
+-			result[i] = docker.APIContainers{
+-				ID:      container.ID,
+-				Image:   container.Image,
+-				Command: fmt.Sprintf("%s %s", container.Path, strings.Join(container.Args, " ")),
+-				Created: container.Created.Unix(),
+-				Status:  container.State.String(),
+-				Ports:   container.NetworkSettings.PortMappingAPI(),
+-				Names:   []string{fmt.Sprintf("/%s", container.Name)},
+-			}
+-		}
+-	}
+-	s.cMut.RUnlock()
+-	w.Header().Set("Content-Type", "application/json")
+-	w.WriteHeader(http.StatusOK)
+-	json.NewEncoder(w).Encode(result)
+-}
+-
+-func (s *DockerServer) listImages(w http.ResponseWriter, r *http.Request) {
+-	s.cMut.RLock()
+-	result := make([]docker.APIImages, len(s.images))
+-	for i, image := range s.images {
+-		result[i] = docker.APIImages{
+-			ID:      image.ID,
+-			Created: image.Created.Unix(),
+-		}
+-		for tag, id := range s.imgIDs {
+-			if id == image.ID {
+-				result[i].RepoTags = append(result[i].RepoTags, tag)
+-			}
+-		}
+-	}
+-	s.cMut.RUnlock()
+-	w.Header().Set("Content-Type", "application/json")
+-	w.WriteHeader(http.StatusOK)
+-	json.NewEncoder(w).Encode(result)
+-}
+-
+-func (s *DockerServer) findImage(id string) (string, error) {
+-	s.iMut.RLock()
+-	defer s.iMut.RUnlock()
+-	image, ok := s.imgIDs[id]
+-	if ok {
+-		return image, nil
+-	}
+-	image, _, err := s.findImageByID(id)
+-	return image, err
+-}
+-
+-func (s *DockerServer) findImageByID(id string) (string, int, error) {
+-	s.iMut.RLock()
+-	defer s.iMut.RUnlock()
+-	for i, image := range s.images {
+-		if image.ID == id {
+-			return image.ID, i, nil
+-		}
+-	}
+-	return "", -1, errors.New("No such image")
+-}
+-
+-func (s *DockerServer) createContainer(w http.ResponseWriter, r *http.Request) {
+-	var config docker.Config
+-	defer r.Body.Close()
+-	err := json.NewDecoder(r.Body).Decode(&config)
+-	if err != nil {
+-		http.Error(w, err.Error(), http.StatusBadRequest)
+-		return
+-	}
+-	if _, err := s.findImage(config.Image); err != nil {
+-		http.Error(w, err.Error(), http.StatusNotFound)
+-		return
+-	}
+-	w.WriteHeader(http.StatusCreated)
+-	ports := map[docker.Port][]docker.PortBinding{}
+-	for port := range config.ExposedPorts {
+-		ports[port] = []docker.PortBinding{{
+-			HostIP:   "0.0.0.0",
+-			HostPort: strconv.Itoa(mathrand.Int() % 65536),
+-		}}
+-	}
+-
+-	//the container may not have cmd when using a Dockerfile
+-	var path string
+-	var args []string
+-	if len(config.Cmd) == 1 {
+-		path = config.Cmd[0]
+-	} else if len(config.Cmd) > 1 {
+-		path = config.Cmd[0]
+-		args = config.Cmd[1:]
+-	}
+-
+-	container := docker.Container{
+-		Name:    r.URL.Query().Get("name"),
+-		ID:      s.generateID(),
+-		Created: time.Now(),
+-		Path:    path,
+-		Args:    args,
+-		Config:  &config,
+-		State: docker.State{
+-			Running:   false,
+-			Pid:       mathrand.Int() % 50000,
+-			ExitCode:  0,
+-			StartedAt: time.Now(),
+-		},
+-		Image: config.Image,
+-		NetworkSettings: &docker.NetworkSettings{
+-			IPAddress:   fmt.Sprintf("172.16.42.%d", mathrand.Int()%250+2),
+-			IPPrefixLen: 24,
+-			Gateway:     "172.16.42.1",
+-			Bridge:      "docker0",
+-			Ports:       ports,
+-		},
+-	}
+-	s.cMut.Lock()
+-	s.containers = append(s.containers, &container)
+-	s.cMut.Unlock()
+-	s.notify(&container)
+-	var c = struct{ ID string }{ID: container.ID}
+-	json.NewEncoder(w).Encode(c)
+-}
+-
+-func (s *DockerServer) generateID() string {
+-	var buf [16]byte
+-	rand.Read(buf[:])
+-	return fmt.Sprintf("%x", buf)
+-}
+-
+-func (s *DockerServer) inspectContainer(w http.ResponseWriter, r *http.Request) {
+-	id := mux.Vars(r)["id"]
+-	container, _, err := s.findContainer(id)
+-	if err != nil {
+-		http.Error(w, err.Error(), http.StatusNotFound)
+-		return
+-	}
+-	w.Header().Set("Content-Type", "application/json")
+-	w.WriteHeader(http.StatusOK)
+-	json.NewEncoder(w).Encode(container)
+-}
+-
+-func (s *DockerServer) topContainer(w http.ResponseWriter, r *http.Request) {
+-	id := mux.Vars(r)["id"]
+-	container, _, err := s.findContainer(id)
+-	if err != nil {
+-		http.Error(w, err.Error(), http.StatusNotFound)
+-		return
+-	}
+-	if !container.State.Running {
+-		w.WriteHeader(http.StatusInternalServerError)
+-		fmt.Fprintf(w, "Container %s is not running", id)
+-		return
+-	}
+-	w.Header().Set("Content-Type", "application/json")
+-	w.WriteHeader(http.StatusOK)
+-	result := docker.TopResult{
+-		Titles: []string{"UID", "PID", "PPID", "C", "STIME", "TTY", "TIME", "CMD"},
+-		Processes: [][]string{
+-			{"root", "7535", "7516", "0", "03:20", "?", "00:00:00", container.Path + " " + strings.Join(container.Args, " ")},
+-		},
+-	}
+-	json.NewEncoder(w).Encode(result)
+-}
+-
+-func (s *DockerServer) startContainer(w http.ResponseWriter, r *http.Request) {
+-	id := mux.Vars(r)["id"]
+-	container, _, err := s.findContainer(id)
+-	if err != nil {
+-		http.Error(w, err.Error(), http.StatusNotFound)
+-		return
+-	}
+-	s.cMut.Lock()
+-	defer s.cMut.Unlock()
+-	if container.State.Running {
+-		http.Error(w, "Container already running", http.StatusBadRequest)
+-		return
+-	}
+-	container.State.Running = true
+-	s.notify(container)
+-}
+-
+-func (s *DockerServer) stopContainer(w http.ResponseWriter, r *http.Request) {
+-	id := mux.Vars(r)["id"]
+-	container, _, err := s.findContainer(id)
+-	if err != nil {
+-		http.Error(w, err.Error(), http.StatusNotFound)
+-		return
+-	}
+-	s.cMut.Lock()
+-	defer s.cMut.Unlock()
+-	if !container.State.Running {
+-		http.Error(w, "Container not running", http.StatusBadRequest)
+-		return
+-	}
+-	w.WriteHeader(http.StatusNoContent)
+-	container.State.Running = false
+-	s.notify(container)
+-}
+-
+-func (s *DockerServer) pauseContainer(w http.ResponseWriter, r *http.Request) {
+-	id := mux.Vars(r)["id"]
+-	container, _, err := s.findContainer(id)
+-	if err != nil {
+-		http.Error(w, err.Error(), http.StatusNotFound)
+-		return
+-	}
+-	s.cMut.Lock()
+-	defer s.cMut.Unlock()
+-	if container.State.Paused {
+-		http.Error(w, "Container already paused", http.StatusBadRequest)
+-		return
+-	}
+-	w.WriteHeader(http.StatusNoContent)
+-	container.State.Paused = true
+-}
+-
+-func (s *DockerServer) unpauseContainer(w http.ResponseWriter, r *http.Request) {
+-	id := mux.Vars(r)["id"]
+-	container, _, err := s.findContainer(id)
+-	if err != nil {
+-		http.Error(w, err.Error(), http.StatusNotFound)
+-		return
+-	}
+-	s.cMut.Lock()
+-	defer s.cMut.Unlock()
+-	if !container.State.Paused {
+-		http.Error(w, "Container not paused", http.StatusBadRequest)
+-		return
+-	}
+-	w.WriteHeader(http.StatusNoContent)
+-	container.State.Paused = false
+-}
+-
+-func (s *DockerServer) attachContainer(w http.ResponseWriter, r *http.Request) {
+-	id := mux.Vars(r)["id"]
+-	container, _, err := s.findContainer(id)
+-	if err != nil {
+-		http.Error(w, err.Error(), http.StatusNotFound)
+-		return
+-	}
+-	outStream := newStdWriter(w, stdout)
+-	fmt.Fprintf(outStream, "HTTP/1.1 200 OK\r\nContent-Type: application/vnd.docker.raw-stream\r\n\r\n")
+-	if container.State.Running {
+-		fmt.Fprintf(outStream, "Container %q is running\n", container.ID)
+-	} else {
+-		fmt.Fprintf(outStream, "Container %q is not running\n", container.ID)
+-	}
+-	fmt.Fprintln(outStream, "What happened?")
+-	fmt.Fprintln(outStream, "Something happened")
+-}
+-
+-func (s *DockerServer) waitContainer(w http.ResponseWriter, r *http.Request) {
+-	id := mux.Vars(r)["id"]
+-	container, _, err := s.findContainer(id)
+-	if err != nil {
+-		http.Error(w, err.Error(), http.StatusNotFound)
+-		return
+-	}
+-	for {
+-		time.Sleep(1e6)
+-		s.cMut.RLock()
+-		if !container.State.Running {
+-			s.cMut.RUnlock()
+-			break
+-		}
+-		s.cMut.RUnlock()
+-	}
+-	result := map[string]int{"StatusCode": container.State.ExitCode}
+-	json.NewEncoder(w).Encode(result)
+-}
+-
+-func (s *DockerServer) removeContainer(w http.ResponseWriter, r *http.Request) {
+-	id := mux.Vars(r)["id"]
+-	_, index, err := s.findContainer(id)
+-	if err != nil {
+-		http.Error(w, err.Error(), http.StatusNotFound)
+-		return
+-	}
+-	if s.containers[index].State.Running {
+-		msg := "Error: API error (406): Impossible to remove a running container, please stop it first"
+-		http.Error(w, msg, http.StatusInternalServerError)
+-		return
+-	}
+-	w.WriteHeader(http.StatusNoContent)
+-	s.cMut.Lock()
+-	defer s.cMut.Unlock()
+-	s.containers[index] = s.containers[len(s.containers)-1]
+-	s.containers = s.containers[:len(s.containers)-1]
+-}
+-
+-func (s *DockerServer) commitContainer(w http.ResponseWriter, r *http.Request) {
+-	id := r.URL.Query().Get("container")
+-	container, _, err := s.findContainer(id)
+-	if err != nil {
+-		http.Error(w, err.Error(), http.StatusNotFound)
+-		return
+-	}
+-	var config *docker.Config
+-	runConfig := r.URL.Query().Get("run")
+-	if runConfig != "" {
+-		config = new(docker.Config)
+-		err = json.Unmarshal([]byte(runConfig), config)
+-		if err != nil {
+-			http.Error(w, err.Error(), http.StatusBadRequest)
+-			return
+-		}
+-	}
+-	w.WriteHeader(http.StatusOK)
+-	image := docker.Image{
+-		ID:        "img-" + container.ID,
+-		Parent:    container.Image,
+-		Container: container.ID,
+-		Comment:   r.URL.Query().Get("m"),
+-		Author:    r.URL.Query().Get("author"),
+-		Config:    config,
+-	}
+-	repository := r.URL.Query().Get("repo")
+-	s.iMut.Lock()
+-	s.images = append(s.images, image)
+-	if repository != "" {
+-		s.imgIDs[repository] = image.ID
+-	}
+-	s.iMut.Unlock()
+-	fmt.Fprintf(w, `{"ID":%q}`, image.ID)
+-}
+-
+-func (s *DockerServer) findContainer(id string) (*docker.Container, int, error) {
+-	s.cMut.RLock()
+-	defer s.cMut.RUnlock()
+-	for i, container := range s.containers {
+-		if container.ID == id {
+-			return container, i, nil
+-		}
+-	}
+-	return nil, -1, errors.New("No such container")
+-}
+-
+-func (s *DockerServer) buildImage(w http.ResponseWriter, r *http.Request) {
+-	if ct := r.Header.Get("Content-Type"); ct == "application/tar" {
+-		gotDockerFile := false
+-		tr := tar.NewReader(r.Body)
+-		for {
+-			header, err := tr.Next()
+-			if err != nil {
+-				break
+-			}
+-			if header.Name == "Dockerfile" {
+-				gotDockerFile = true
+-			}
+-		}
+-		if !gotDockerFile {
+-			w.WriteHeader(http.StatusBadRequest)
+-			w.Write([]byte("miss Dockerfile"))
+-			return
+-		}
+-	}
+-	//we did not use that Dockerfile to build image cause we are a fake Docker daemon
+-	image := docker.Image{
+-		ID:      s.generateID(),
+-		Created: time.Now(),
+-	}
+-
+-	query := r.URL.Query()
+-	repository := image.ID
+-	if t := query.Get("t"); t != "" {
+-		repository = t
+-	}
+-	s.iMut.Lock()
+-	s.images = append(s.images, image)
+-	s.imgIDs[repository] = image.ID
+-	s.iMut.Unlock()
+-	w.Write([]byte(fmt.Sprintf("Successfully built %s", image.ID)))
+-}
+-
+-func (s *DockerServer) pullImage(w http.ResponseWriter, r *http.Request) {
+-	repository := r.URL.Query().Get("fromImage")
+-	image := docker.Image{
+-		ID: s.generateID(),
+-	}
+-	s.iMut.Lock()
+-	s.images = append(s.images, image)
+-	if repository != "" {
+-		s.imgIDs[repository] = image.ID
+-	}
+-	s.iMut.Unlock()
+-}
+-
+-func (s *DockerServer) pushImage(w http.ResponseWriter, r *http.Request) {
+-	name := mux.Vars(r)["name"]
+-	s.iMut.RLock()
+-	if _, ok := s.imgIDs[name]; !ok {
+-		s.iMut.RUnlock()
+-		http.Error(w, "No such image", http.StatusNotFound)
+-		return
+-	}
+-	s.iMut.RUnlock()
+-	fmt.Fprintln(w, "Pushing...")
+-	fmt.Fprintln(w, "Pushed")
+-}
+-
+-func (s *DockerServer) tagImage(w http.ResponseWriter, r *http.Request) {
+-	name := mux.Vars(r)["name"]
+-	s.iMut.RLock()
+-	if _, ok := s.imgIDs[name]; !ok {
+-		s.iMut.RUnlock()
+-		http.Error(w, "No such image", http.StatusNotFound)
+-		return
+-	}
+-	s.iMut.RUnlock()
+-	s.iMut.Lock()
+-	defer s.iMut.Unlock()
+-	newRepo := r.URL.Query().Get("repo")
+-	s.imgIDs[newRepo] = s.imgIDs[name]
+-	w.WriteHeader(http.StatusCreated)
+-}
+-
+-func (s *DockerServer) removeImage(w http.ResponseWriter, r *http.Request) {
+-	id := mux.Vars(r)["id"]
+-	s.iMut.RLock()
+-	var tag string
+-	if img, ok := s.imgIDs[id]; ok {
+-		id, tag = img, id
+-	}
+-	var tags []string
+-	for tag, taggedID := range s.imgIDs {
+-		if taggedID == id {
+-			tags = append(tags, tag)
+-		}
+-	}
+-	s.iMut.RUnlock()
+-	_, index, err := s.findImageByID(id)
+-	if err != nil {
+-		http.Error(w, err.Error(), http.StatusNotFound)
+-		return
+-	}
+-	w.WriteHeader(http.StatusNoContent)
+-	s.iMut.Lock()
+-	defer s.iMut.Unlock()
+-	if len(tags) < 2 {
+-		s.images[index] = s.images[len(s.images)-1]
+-		s.images = s.images[:len(s.images)-1]
+-	}
+-	if tag != "" {
+-		delete(s.imgIDs, tag)
+-	}
+-}
+-
+-func (s *DockerServer) inspectImage(w http.ResponseWriter, r *http.Request) {
+-	name := mux.Vars(r)["name"]
+-	if id, ok := s.imgIDs[name]; ok {
+-		s.iMut.Lock()
+-		defer s.iMut.Unlock()
+-
+-		for _, img := range s.images {
+-			if img.ID == id {
+-				w.Header().Set("Content-Type", "application/json")
+-				w.WriteHeader(http.StatusOK)
+-				json.NewEncoder(w).Encode(img)
+-				return
+-			}
+-		}
+-	}
+-	http.Error(w, "not found", http.StatusNotFound)
+-}
+-
+-func (s *DockerServer) listEvents(w http.ResponseWriter, r *http.Request) {
+-	w.Header().Set("Content-Type", "application/json")
+-	var events [][]byte
+-	count := mathrand.Intn(20)
+-	for i := 0; i < count; i++ {
+-		data, err := json.Marshal(s.generateEvent())
+-		if err != nil {
+-			w.WriteHeader(http.StatusInternalServerError)
+-			return
+-		}
+-		events = append(events, data)
+-	}
+-	w.WriteHeader(http.StatusOK)
+-	for _, d := range events {
+-		fmt.Fprintln(w, d)
+-		time.Sleep(time.Duration(mathrand.Intn(200)) * time.Millisecond)
+-	}
+-}
+-
+-func (s *DockerServer) pingDocker(w http.ResponseWriter, r *http.Request) {
+-	w.WriteHeader(http.StatusOK)
+-}
+-
+-func (s *DockerServer) generateEvent() *docker.APIEvents {
+-	var eventType string
+-	switch mathrand.Intn(4) {
+-	case 0:
+-		eventType = "create"
+-	case 1:
+-		eventType = "start"
+-	case 2:
+-		eventType = "stop"
+-	case 3:
+-		eventType = "destroy"
+-	}
+-	return &docker.APIEvents{
+-		ID:     s.generateID(),
+-		Status: eventType,
+-		From:   "mybase:latest",
+-		Time:   time.Now().Unix(),
+-	}
+-}
+-
+-func (s *DockerServer) loadImage(w http.ResponseWriter, r *http.Request) {
+-	w.WriteHeader(http.StatusOK)
+-}
+-
+-func (s *DockerServer) getImage(w http.ResponseWriter, r *http.Request) {
+-	w.WriteHeader(http.StatusOK)
+-	w.Header().Set("Content-Type", "application/tar")
+-
+-}
+-
+-func (s *DockerServer) createExecContainer(w http.ResponseWriter, r *http.Request) {
+-	w.WriteHeader(http.StatusOK)
+-	w.Header().Set("Content-Type", "application/json")
+-	exec := docker.Exec{ID: "id-exec-created-by-test"}
+-	s.execs = append(s.execs, &exec)
+-	json.NewEncoder(w).Encode(map[string]string{"Id": exec.ID})
+-
+-}
+-
+-func (s *DockerServer) startExecContainer(w http.ResponseWriter, r *http.Request) {
+-	id := mux.Vars(r)["id"]
+-	for _, exec := range s.execs {
+-		if exec.ID == id {
+-			w.WriteHeader(http.StatusOK)
+-			return
+-		}
+-	}
+-	w.WriteHeader(http.StatusNotFound)
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/server_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/server_test.go
+deleted file mode 100644
+index d8763cb..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/server_test.go
++++ /dev/null
+@@ -1,1091 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 testing
+-
+-import (
+-	"encoding/json"
+-	"fmt"
+-	"math/rand"
+-	"net"
+-	"net/http"
+-	"net/http/httptest"
+-	"os"
+-	"reflect"
+-	"strings"
+-	"testing"
+-	"time"
+-
+-	"github.com/fsouza/go-dockerclient"
+-)
+-
+-func TestNewServer(t *testing.T) {
+-	server, err := NewServer("127.0.0.1:0", nil, nil)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	defer server.listener.Close()
+-	conn, err := net.Dial("tcp", server.listener.Addr().String())
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	conn.Close()
+-}
+-
+-func TestServerStop(t *testing.T) {
+-	server, err := NewServer("127.0.0.1:0", nil, nil)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	server.Stop()
+-	_, err = net.Dial("tcp", server.listener.Addr().String())
+-	if err == nil {
+-		t.Error("Unexpected <nil> error when dialing to stopped server")
+-	}
+-}
+-
+-func TestServerStopNoListener(t *testing.T) {
+-	server := DockerServer{}
+-	server.Stop()
+-}
+-
+-func TestServerURL(t *testing.T) {
+-	server, err := NewServer("127.0.0.1:0", nil, nil)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	defer server.Stop()
+-	url := server.URL()
+-	if expected := "http://" + server.listener.Addr().String() + "/"; url != expected {
+-		t.Errorf("DockerServer.URL(): Want %q. Got %q.", expected, url)
+-	}
+-}
+-
+-func TestServerURLNoListener(t *testing.T) {
+-	server := DockerServer{}
+-	url := server.URL()
+-	if url != "" {
+-		t.Errorf("DockerServer.URL(): Expected empty URL on handler mode, got %q.", url)
+-	}
+-}
+-
+-func TestHandleWithHook(t *testing.T) {
+-	var called bool
+-	server, _ := NewServer("127.0.0.1:0", nil, func(*http.Request) { called = true })
+-	defer server.Stop()
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("GET", "/containers/json?all=1", nil)
+-	server.ServeHTTP(recorder, request)
+-	if !called {
+-		t.Error("ServeHTTP did not call the hook function.")
+-	}
+-}
+-
+-func TestCustomHandler(t *testing.T) {
+-	var called bool
+-	server, _ := NewServer("127.0.0.1:0", nil, nil)
+-	addContainers(server, 2)
+-	server.CustomHandler("/containers/json", http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+-		called = true
+-		fmt.Fprint(w, "Hello world")
+-	}))
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("GET", "/containers/json?all=1", nil)
+-	server.ServeHTTP(recorder, request)
+-	if !called {
+-		t.Error("Did not call the custom handler")
+-	}
+-	if got := recorder.Body.String(); got != "Hello world" {
+-		t.Errorf("Wrong output for custom handler: want %q. Got %q.", "Hello world", got)
+-	}
+-}
+-
+-func TestListContainers(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 2)
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("GET", "/containers/json?all=1", nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusOK {
+-		t.Errorf("ListContainers: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
+-	}
+-	expected := make([]docker.APIContainers, 2)
+-	for i, container := range server.containers {
+-		expected[i] = docker.APIContainers{
+-			ID:      container.ID,
+-			Image:   container.Image,
+-			Command: strings.Join(container.Config.Cmd, " "),
+-			Created: container.Created.Unix(),
+-			Status:  container.State.String(),
+-			Ports:   container.NetworkSettings.PortMappingAPI(),
+-			Names:   []string{"/" + container.Name},
+-		}
+-	}
+-	var got []docker.APIContainers
+-	err := json.NewDecoder(recorder.Body).Decode(&got)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !reflect.DeepEqual(got, expected) {
+-		t.Errorf("ListContainers. Want %#v. Got %#v.", expected, got)
+-	}
+-}
+-
+-func TestListRunningContainers(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 2)
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("GET", "/containers/json?all=0", nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusOK {
+-		t.Errorf("ListRunningContainers: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
+-	}
+-	var got []docker.APIContainers
+-	err := json.NewDecoder(recorder.Body).Decode(&got)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if len(got) == 0 {
+-		t.Errorf("ListRunningContainers: Want 0. Got %d.", len(got))
+-	}
+-}
+-
+-func TestCreateContainer(t *testing.T) {
+-	server := DockerServer{}
+-	server.imgIDs = map[string]string{"base": "a1234"}
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	body := `{"Hostname":"", "User":"", "Memory":0, "MemorySwap":0, "AttachStdin":false, "AttachStdout":true, "AttachStderr":true,
+-"PortSpecs":null, "Tty":false, "OpenStdin":false, "StdinOnce":false, "Env":null, "Cmd":["date"], "Image":"base", "Volumes":{}, "VolumesFrom":""}`
+-	request, _ := http.NewRequest("POST", "/containers/create", strings.NewReader(body))
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusCreated {
+-		t.Errorf("CreateContainer: wrong status. Want %d. Got %d.", http.StatusCreated, recorder.Code)
+-	}
+-	var returned docker.Container
+-	err := json.NewDecoder(recorder.Body).Decode(&returned)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	stored := server.containers[0]
+-	if returned.ID != stored.ID {
+-		t.Errorf("CreateContainer: ID mismatch. Stored: %q. Returned: %q.", stored.ID, returned.ID)
+-	}
+-	if stored.State.Running {
+-		t.Errorf("CreateContainer should not set container to running state.")
+-	}
+-}
+-
+-func TestCreateContainerWithNotifyChannel(t *testing.T) {
+-	ch := make(chan *docker.Container, 1)
+-	server := DockerServer{}
+-	server.imgIDs = map[string]string{"base": "a1234"}
+-	server.cChan = ch
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	body := `{"Hostname":"", "User":"", "Memory":0, "MemorySwap":0, "AttachStdin":false, "AttachStdout":true, "AttachStderr":true,
+-"PortSpecs":null, "Tty":false, "OpenStdin":false, "StdinOnce":false, "Env":null, "Cmd":["date"], "Image":"base", "Volumes":{}, "VolumesFrom":""}`
+-	request, _ := http.NewRequest("POST", "/containers/create", strings.NewReader(body))
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusCreated {
+-		t.Errorf("CreateContainer: wrong status. Want %d. Got %d.", http.StatusCreated, recorder.Code)
+-	}
+-	if notified := <-ch; notified != server.containers[0] {
+-		t.Errorf("CreateContainer: did not notify the proper container. Want %q. Got %q.", server.containers[0].ID, notified.ID)
+-	}
+-}
+-
+-func TestCreateContainerInvalidBody(t *testing.T) {
+-	server := DockerServer{}
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("POST", "/containers/create", strings.NewReader("whaaaaaat---"))
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusBadRequest {
+-		t.Errorf("CreateContainer: wrong status. Want %d. Got %d.", http.StatusBadRequest, recorder.Code)
+-	}
+-}
+-
+-func TestCreateContainerImageNotFound(t *testing.T) {
+-	server := DockerServer{}
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	body := `{"Hostname":"", "User":"", "Memory":0, "MemorySwap":0, "AttachStdin":false, "AttachStdout":true, "AttachStderr":true,
+-"PortSpecs":null, "Tty":false, "OpenStdin":false, "StdinOnce":false, "Env":null, "Cmd":["date"],
+-"Image":"base", "Volumes":{}, "VolumesFrom":""}`
+-	request, _ := http.NewRequest("POST", "/containers/create", strings.NewReader(body))
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNotFound {
+-		t.Errorf("CreateContainer: wrong status. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
+-	}
+-}
+-
+-func TestCommitContainer(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 2)
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("POST", "/commit?container="+server.containers[0].ID, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusOK {
+-		t.Errorf("CommitContainer: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
+-	}
+-	expected := fmt.Sprintf(`{"ID":"%s"}`, server.images[0].ID)
+-	if got := recorder.Body.String(); got != expected {
+-		t.Errorf("CommitContainer: wrong response body. Want %q. Got %q.", expected, got)
+-	}
+-}
+-
+-func TestCommitContainerComplete(t *testing.T) {
+-	server := DockerServer{}
+-	server.imgIDs = make(map[string]string)
+-	addContainers(&server, 2)
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	queryString := "container=" + server.containers[0].ID + "&repo=tsuru/python&m=saving&author=developers"
+-	queryString += `&run={"Cmd": ["cat", "/world"],"PortSpecs":["22"]}`
+-	request, _ := http.NewRequest("POST", "/commit?"+queryString, nil)
+-	server.ServeHTTP(recorder, request)
+-	image := server.images[0]
+-	if image.Parent != server.containers[0].Image {
+-		t.Errorf("CommitContainer: wrong parent image. Want %q. Got %q.", server.containers[0].Image, image.Parent)
+-	}
+-	if image.Container != server.containers[0].ID {
+-		t.Errorf("CommitContainer: wrong container. Want %q. Got %q.", server.containers[0].ID, image.Container)
+-	}
+-	message := "saving"
+-	if image.Comment != message {
+-		t.Errorf("CommitContainer: wrong comment (commit message). Want %q. Got %q.", message, image.Comment)
+-	}
+-	author := "developers"
+-	if image.Author != author {
+-		t.Errorf("CommitContainer: wrong author. Want %q. Got %q.", author, image.Author)
+-	}
+-	if id := server.imgIDs["tsuru/python"]; id != image.ID {
+-		t.Errorf("CommitContainer: wrong ID saved for repository. Want %q. Got %q.", image.ID, id)
+-	}
+-	portSpecs := []string{"22"}
+-	if !reflect.DeepEqual(image.Config.PortSpecs, portSpecs) {
+-		t.Errorf("CommitContainer: wrong port spec in config. Want %#v. Got %#v.", portSpecs, image.Config.PortSpecs)
+-	}
+-	cmd := []string{"cat", "/world"}
+-	if !reflect.DeepEqual(image.Config.Cmd, cmd) {
+-		t.Errorf("CommitContainer: wrong cmd in config. Want %#v. Got %#v.", cmd, image.Config.Cmd)
+-	}
+-}
+-
+-func TestCommitContainerInvalidRun(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 1)
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("POST", "/commit?container="+server.containers[0].ID+"&run=abc---", nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusBadRequest {
+-		t.Errorf("CommitContainer. Wrong status. Want %d. Got %d.", http.StatusBadRequest, recorder.Code)
+-	}
+-}
+-
+-func TestCommitContainerNotFound(t *testing.T) {
+-	server := DockerServer{}
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("POST", "/commit?container=abc123", nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNotFound {
+-		t.Errorf("CommitContainer. Wrong status. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
+-	}
+-}
+-
+-func TestInspectContainer(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 2)
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s/json", server.containers[0].ID)
+-	request, _ := http.NewRequest("GET", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusOK {
+-		t.Errorf("InspectContainer: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
+-	}
+-	expected := server.containers[0]
+-	var got docker.Container
+-	err := json.NewDecoder(recorder.Body).Decode(&got)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !reflect.DeepEqual(got.Config, expected.Config) {
+-		t.Errorf("InspectContainer: wrong value. Want %#v. Got %#v.", *expected, got)
+-	}
+-	if !reflect.DeepEqual(got.NetworkSettings, expected.NetworkSettings) {
+-		t.Errorf("InspectContainer: wrong value. Want %#v. Got %#v.", *expected, got)
+-	}
+-	got.State.StartedAt = expected.State.StartedAt
+-	got.State.FinishedAt = expected.State.FinishedAt
+-	got.Config = expected.Config
+-	got.Created = expected.Created
+-	got.NetworkSettings = expected.NetworkSettings
+-	if !reflect.DeepEqual(got, *expected) {
+-		t.Errorf("InspectContainer: wrong value. Want %#v. Got %#v.", *expected, got)
+-	}
+-}
+-
+-func TestInspectContainerNotFound(t *testing.T) {
+-	server := DockerServer{}
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("GET", "/containers/abc123/json", nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNotFound {
+-		t.Errorf("InspectContainer: wrong status code. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
+-	}
+-}
+-
+-func TestTopContainer(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 1)
+-	server.containers[0].State.Running = true
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s/top", server.containers[0].ID)
+-	request, _ := http.NewRequest("GET", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusOK {
+-		t.Errorf("TopContainer: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
+-	}
+-	var got docker.TopResult
+-	err := json.NewDecoder(recorder.Body).Decode(&got)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !reflect.DeepEqual(got.Titles, []string{"UID", "PID", "PPID", "C", "STIME", "TTY", "TIME", "CMD"}) {
+-		t.Fatalf("TopContainer: Unexpected titles, got: %#v", got.Titles)
+-	}
+-	if len(got.Processes) != 1 {
+-		t.Fatalf("TopContainer: Unexpected process len, got: %d", len(got.Processes))
+-	}
+-	if got.Processes[0][len(got.Processes[0])-1] != "ls -la .." {
+-		t.Fatalf("TopContainer: Unexpected command name, got: %s", got.Processes[0][len(got.Processes[0])-1])
+-	}
+-}
+-
+-func TestTopContainerNotFound(t *testing.T) {
+-	server := DockerServer{}
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("GET", "/containers/xyz/top", nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNotFound {
+-		t.Errorf("TopContainer: wrong status. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
+-	}
+-}
+-
+-func TestTopContainerStopped(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 1)
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s/top", server.containers[0].ID)
+-	request, _ := http.NewRequest("GET", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusInternalServerError {
+-		t.Errorf("TopContainer: wrong status. Want %d. Got %d.", http.StatusInternalServerError, recorder.Code)
+-	}
+-}
+-
+-func TestStartContainer(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 1)
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s/start", server.containers[0].ID)
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusOK {
+-		t.Errorf("StartContainer: wrong status code. Want %d. Got %d.", http.StatusOK, recorder.Code)
+-	}
+-	if !server.containers[0].State.Running {
+-		t.Error("StartContainer: did not set the container to running state")
+-	}
+-}
+-
+-func TestStartContainerWithNotifyChannel(t *testing.T) {
+-	ch := make(chan *docker.Container, 1)
+-	server := DockerServer{}
+-	server.cChan = ch
+-	addContainers(&server, 1)
+-	addContainers(&server, 1)
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s/start", server.containers[1].ID)
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusOK {
+-		t.Errorf("StartContainer: wrong status code. Want %d. Got %d.", http.StatusOK, recorder.Code)
+-	}
+-	if notified := <-ch; notified != server.containers[1] {
+-		t.Errorf("StartContainer: did not notify the proper container. Want %q. Got %q.", server.containers[1].ID, notified.ID)
+-	}
+-}
+-
+-func TestStartContainerNotFound(t *testing.T) {
+-	server := DockerServer{}
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := "/containers/abc123/start"
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNotFound {
+-		t.Errorf("StartContainer: wrong status code. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
+-	}
+-}
+-
+-func TestStartContainerAlreadyRunning(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 1)
+-	server.containers[0].State.Running = true
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s/start", server.containers[0].ID)
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusBadRequest {
+-		t.Errorf("StartContainer: wrong status code. Want %d. Got %d.", http.StatusBadRequest, recorder.Code)
+-	}
+-}
+-
+-func TestStopContainer(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 1)
+-	server.containers[0].State.Running = true
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s/stop", server.containers[0].ID)
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNoContent {
+-		t.Errorf("StopContainer: wrong status code. Want %d. Got %d.", http.StatusNoContent, recorder.Code)
+-	}
+-	if server.containers[0].State.Running {
+-		t.Error("StopContainer: did not stop the container")
+-	}
+-}
+-
+-func TestKillContainer(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 1)
+-	server.containers[0].State.Running = true
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s/kill", server.containers[0].ID)
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNoContent {
+-		t.Errorf("KillContainer: wrong status code. Want %d. Got %d.", http.StatusNoContent, recorder.Code)
+-	}
+-	if server.containers[0].State.Running {
+-		t.Error("KillContainer: did not stop the container")
+-	}
+-}
+-
+-func TestStopContainerWithNotifyChannel(t *testing.T) {
+-	ch := make(chan *docker.Container, 1)
+-	server := DockerServer{}
+-	server.cChan = ch
+-	addContainers(&server, 1)
+-	addContainers(&server, 1)
+-	server.containers[1].State.Running = true
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s/stop", server.containers[1].ID)
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNoContent {
+-		t.Errorf("StopContainer: wrong status code. Want %d. Got %d.", http.StatusNoContent, recorder.Code)
+-	}
+-	if notified := <-ch; notified != server.containers[1] {
+-		t.Errorf("StopContainer: did not notify the proper container. Want %q. Got %q.", server.containers[1].ID, notified.ID)
+-	}
+-}
+-
+-func TestStopContainerNotFound(t *testing.T) {
+-	server := DockerServer{}
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := "/containers/abc123/stop"
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNotFound {
+-		t.Errorf("StopContainer: wrong status code. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
+-	}
+-}
+-
+-func TestStopContainerNotRunning(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 1)
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s/stop", server.containers[0].ID)
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusBadRequest {
+-		t.Errorf("StopContainer: wrong status code. Want %d. Got %d.", http.StatusBadRequest, recorder.Code)
+-	}
+-}
+-
+-func TestPauseContainer(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 1)
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s/pause", server.containers[0].ID)
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNoContent {
+-		t.Errorf("PauseContainer: wrong status code. Want %d. Got %d.", http.StatusNoContent, recorder.Code)
+-	}
+-	if !server.containers[0].State.Paused {
+-		t.Error("PauseContainer: did not pause the container")
+-	}
+-}
+-
+-func TestPauseContainerAlreadyPaused(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 1)
+-	server.containers[0].State.Paused = true
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s/pause", server.containers[0].ID)
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusBadRequest {
+-		t.Errorf("PauseContainer: wrong status code. Want %d. Got %d.", http.StatusBadRequest, recorder.Code)
+-	}
+-}
+-
+-func TestPauseContainerNotFound(t *testing.T) {
+-	server := DockerServer{}
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := "/containers/abc123/pause"
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNotFound {
+-		t.Errorf("PauseContainer: wrong status code. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
+-	}
+-}
+-
+-func TestUnpauseContainer(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 1)
+-	server.containers[0].State.Paused = true
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s/unpause", server.containers[0].ID)
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNoContent {
+-		t.Errorf("UnpauseContainer: wrong status code. Want %d. Got %d.", http.StatusNoContent, recorder.Code)
+-	}
+-	if server.containers[0].State.Paused {
+-		t.Error("UnpauseContainer: did not unpause the container")
+-	}
+-}
+-
+-func TestUnpauseContainerNotPaused(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 1)
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s/unpause", server.containers[0].ID)
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusBadRequest {
+-		t.Errorf("UnpauseContainer: wrong status code. Want %d. Got %d.", http.StatusBadRequest, recorder.Code)
+-	}
+-}
+-
+-func TestUnpauseContainerNotFound(t *testing.T) {
+-	server := DockerServer{}
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := "/containers/abc123/unpause"
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNotFound {
+-		t.Errorf("UnpauseContainer: wrong status code. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
+-	}
+-}
+-
+-func TestWaitContainer(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 1)
+-	server.containers[0].State.Running = true
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s/wait", server.containers[0].ID)
+-	request, _ := http.NewRequest("POST", path, nil)
+-	go func() {
+-		server.cMut.Lock()
+-		server.containers[0].State.Running = false
+-		server.cMut.Unlock()
+-	}()
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusOK {
+-		t.Errorf("WaitContainer: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
+-	}
+-	expected := `{"StatusCode":0}` + "\n"
+-	if body := recorder.Body.String(); body != expected {
+-		t.Errorf("WaitContainer: wrong body. Want %q. Got %q.", expected, body)
+-	}
+-}
+-
+-func TestWaitContainerStatus(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 1)
+-	server.buildMuxer()
+-	server.containers[0].State.ExitCode = 63
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s/wait", server.containers[0].ID)
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusOK {
+-		t.Errorf("WaitContainer: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
+-	}
+-	expected := `{"StatusCode":63}` + "\n"
+-	if body := recorder.Body.String(); body != expected {
+-		t.Errorf("WaitContainer: wrong body. Want %q. Got %q.", expected, body)
+-	}
+-}
+-
+-func TestWaitContainerNotFound(t *testing.T) {
+-	server := DockerServer{}
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := "/containers/abc123/wait"
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNotFound {
+-		t.Errorf("WaitContainer: wrong status code. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
+-	}
+-}
+-
+-func TestAttachContainer(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 1)
+-	server.containers[0].State.Running = true
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s/attach?logs=1", server.containers[0].ID)
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	lines := []string{
+-		fmt.Sprintf("\x01\x00\x00\x00\x03\x00\x00\x00Container %q is running", server.containers[0].ID),
+-		"What happened?",
+-		"Something happened",
+-	}
+-	expected := strings.Join(lines, "\n") + "\n"
+-	if body := recorder.Body.String(); body == expected {
+-		t.Errorf("AttachContainer: wrong body. Want %q. Got %q.", expected, body)
+-	}
+-}
+-
+-func TestAttachContainerNotFound(t *testing.T) {
+-	server := DockerServer{}
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := "/containers/abc123/attach?logs=1"
+-	request, _ := http.NewRequest("POST", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNotFound {
+-		t.Errorf("AttachContainer: wrong status. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
+-	}
+-}
+-
+-func TestRemoveContainer(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 1)
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s", server.containers[0].ID)
+-	request, _ := http.NewRequest("DELETE", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNoContent {
+-		t.Errorf("RemoveContainer: wrong status. Want %d. Got %d.", http.StatusNoContent, recorder.Code)
+-	}
+-	if len(server.containers) > 0 {
+-		t.Error("RemoveContainer: did not remove the container.")
+-	}
+-}
+-
+-func TestRemoveContainerNotFound(t *testing.T) {
+-	server := DockerServer{}
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/abc123")
+-	request, _ := http.NewRequest("DELETE", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNotFound {
+-		t.Errorf("RemoveContainer: wrong status. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
+-	}
+-}
+-
+-func TestRemoveContainerRunning(t *testing.T) {
+-	server := DockerServer{}
+-	addContainers(&server, 1)
+-	server.containers[0].State.Running = true
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/containers/%s", server.containers[0].ID)
+-	request, _ := http.NewRequest("DELETE", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusInternalServerError {
+-		t.Errorf("RemoveContainer: wrong status. Want %d. Got %d.", http.StatusInternalServerError, recorder.Code)
+-	}
+-	if len(server.containers) < 1 {
+-		t.Error("RemoveContainer: should not remove the container.")
+-	}
+-}
+-
+-func TestPullImage(t *testing.T) {
+-	server := DockerServer{imgIDs: make(map[string]string)}
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("POST", "/images/create?fromImage=base", nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusOK {
+-		t.Errorf("PullImage: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
+-	}
+-	if len(server.images) != 1 {
+-		t.Errorf("PullImage: Want 1 image. Got %d.", len(server.images))
+-	}
+-	if _, ok := server.imgIDs["base"]; !ok {
+-		t.Error("PullImage: Repository should not be empty.")
+-	}
+-}
+-
+-func TestPushImage(t *testing.T) {
+-	server := DockerServer{imgIDs: map[string]string{"tsuru/python": "a123"}}
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("POST", "/images/tsuru/python/push", nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusOK {
+-		t.Errorf("PushImage: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
+-	}
+-}
+-
+-func TestPushImageNotFound(t *testing.T) {
+-	server := DockerServer{}
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("POST", "/images/tsuru/python/push", nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNotFound {
+-		t.Errorf("PushImage: wrong status. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
+-	}
+-}
+-
+-func TestTagImage(t *testing.T) {
+-	server := DockerServer{imgIDs: map[string]string{"tsuru/python": "a123"}}
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("POST", "/images/tsuru/python/tag?repo=tsuru/new-python", nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusCreated {
+-		t.Errorf("TagImage: wrong status. Want %d. Got %d.", http.StatusCreated, recorder.Code)
+-	}
+-	if server.imgIDs["tsuru/python"] != server.imgIDs["tsuru/new-python"] {
+-		t.Errorf("TagImage: did not tag the image")
+-	}
+-}
+-
+-func TestTagImageNotFound(t *testing.T) {
+-	server := DockerServer{}
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("POST", "/images/tsuru/python/tag", nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNotFound {
+-		t.Errorf("TagImage: wrong status. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
+-	}
+-}
+-
+-func addContainers(server *DockerServer, n int) {
+-	server.cMut.Lock()
+-	defer server.cMut.Unlock()
+-	for i := 0; i < n; i++ {
+-		date := time.Now().Add(time.Duration((rand.Int() % (i + 1))) * time.Hour)
+-		container := docker.Container{
+-			Name:    fmt.Sprintf("%x", rand.Int()%10000),
+-			ID:      fmt.Sprintf("%x", rand.Int()%10000),
+-			Created: date,
+-			Path:    "ls",
+-			Args:    []string{"-la", ".."},
+-			Config: &docker.Config{
+-				Hostname:     fmt.Sprintf("docker-%d", i),
+-				AttachStdout: true,
+-				AttachStderr: true,
+-				Env:          []string{"ME=you", fmt.Sprintf("NUMBER=%d", i)},
+-				Cmd:          []string{"ls", "-la", ".."},
+-				Image:        "base",
+-			},
+-			State: docker.State{
+-				Running:   false,
+-				Pid:       400 + i,
+-				ExitCode:  0,
+-				StartedAt: date,
+-			},
+-			Image: "b750fe79269d2ec9a3c593ef05b4332b1d1a02a62b4accb2c21d589ff2f5f2dc",
+-			NetworkSettings: &docker.NetworkSettings{
+-				IPAddress:   fmt.Sprintf("10.10.10.%d", i+2),
+-				IPPrefixLen: 24,
+-				Gateway:     "10.10.10.1",
+-				Bridge:      "docker0",
+-				PortMapping: map[string]docker.PortMapping{
+-					"Tcp": {"8888": fmt.Sprintf("%d", 49600+i)},
+-				},
+-			},
+-			ResolvConfPath: "/etc/resolv.conf",
+-		}
+-		server.containers = append(server.containers, &container)
+-	}
+-}
+-
+-func addImages(server *DockerServer, n int, repo bool) {
+-	server.iMut.Lock()
+-	defer server.iMut.Unlock()
+-	if server.imgIDs == nil {
+-		server.imgIDs = make(map[string]string)
+-	}
+-	for i := 0; i < n; i++ {
+-		date := time.Now().Add(time.Duration((rand.Int() % (i + 1))) * time.Hour)
+-		image := docker.Image{
+-			ID:      fmt.Sprintf("%x", rand.Int()%10000),
+-			Created: date,
+-		}
+-		server.images = append(server.images, image)
+-		if repo {
+-			repo := "docker/python-" + image.ID
+-			server.imgIDs[repo] = image.ID
+-		}
+-	}
+-}
+-
+-func TestListImages(t *testing.T) {
+-	server := DockerServer{}
+-	addImages(&server, 2, true)
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("GET", "/images/json?all=1", nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusOK {
+-		t.Errorf("ListImages: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
+-	}
+-	expected := make([]docker.APIImages, 2)
+-	for i, image := range server.images {
+-		expected[i] = docker.APIImages{
+-			ID:       image.ID,
+-			Created:  image.Created.Unix(),
+-			RepoTags: []string{"docker/python-" + image.ID},
+-		}
+-	}
+-	var got []docker.APIImages
+-	err := json.NewDecoder(recorder.Body).Decode(&got)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !reflect.DeepEqual(got, expected) {
+-		t.Errorf("ListImages. Want %#v. Got %#v.", expected, got)
+-	}
+-}
+-
+-func TestRemoveImage(t *testing.T) {
+-	server := DockerServer{}
+-	addImages(&server, 1, false)
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/images/%s", server.images[0].ID)
+-	request, _ := http.NewRequest("DELETE", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNoContent {
+-		t.Errorf("RemoveImage: wrong status. Want %d. Got %d.", http.StatusNoContent, recorder.Code)
+-	}
+-	if len(server.images) > 0 {
+-		t.Error("RemoveImage: did not remove the image.")
+-	}
+-}
+-
+-func TestRemoveImageByName(t *testing.T) {
+-	server := DockerServer{}
+-	addImages(&server, 1, true)
+-	server.buildMuxer()
+-	recorder := httptest.NewRecorder()
+-	imgName := "docker/python-" + server.images[0].ID
+-	path := "/images/" + imgName
+-	request, _ := http.NewRequest("DELETE", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusNoContent {
+-		t.Errorf("RemoveImage: wrong status. Want %d. Got %d.", http.StatusNoContent, recorder.Code)
+-	}
+-	if len(server.images) > 0 {
+-		t.Error("RemoveImage: did not remove the image.")
+-	}
+-	_, ok := server.imgIDs[imgName]
+-	if ok {
+-		t.Error("RemoveImage: did not remove image tag name.")
+-	}
+-}
+-
+-func TestRemoveImageWithMultipleTags(t *testing.T) {
+-	server := DockerServer{}
+-	addImages(&server, 1, true)
+-	server.buildMuxer()
+-	imgID := server.images[0].ID
+-	imgName := "docker/python-" + imgID
+-	server.imgIDs["docker/python-wat"] = imgID
+-	recorder := httptest.NewRecorder()
+-	path := fmt.Sprintf("/images/%s", imgName)
+-	request, _ := http.NewRequest("DELETE", path, nil)
+-	server.ServeHTTP(recorder, request)
+-	_, ok := server.imgIDs[imgName]
+-	if ok {
+-		t.Error("RemoveImage: did not remove image tag name.")
+-	}
+-	id, ok := server.imgIDs["docker/python-wat"]
+-	if !ok {
+-		t.Error("RemoveImage: removed the wrong tag name.")
+-	}
+-	if id != imgID {
+-		t.Error("RemoveImage: disassociated the wrong ID from the tag")
+-	}
+-	if len(server.images) < 1 {
+-		t.Fatal("RemoveImage: removed the image, but should keep it")
+-	}
+-	if server.images[0].ID != imgID {
+-		t.Error("RemoveImage: changed the ID of the image!")
+-	}
+-}
+-
+-func TestPrepareFailure(t *testing.T) {
+-	server := DockerServer{failures: make(map[string]string)}
+-	server.buildMuxer()
+-	errorID := "my_error"
+-	server.PrepareFailure(errorID, "containers/json")
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("GET", "/containers/json?all=1", nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusBadRequest {
+-		t.Errorf("PrepareFailure: wrong status. Want %d. Got %d.", http.StatusBadRequest, recorder.Code)
+-	}
+-	if recorder.Body.String() != errorID+"\n" {
+-		t.Errorf("PrepareFailure: wrong message. Want %s. Got %s.", errorID, recorder.Body.String())
+-	}
+-}
+-
+-func TestRemoveFailure(t *testing.T) {
+-	server := DockerServer{failures: make(map[string]string)}
+-	server.buildMuxer()
+-	errorID := "my_error"
+-	server.PrepareFailure(errorID, "containers/json")
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("GET", "/containers/json?all=1", nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusBadRequest {
+-		t.Errorf("PrepareFailure: wrong status. Want %d. Got %d.", http.StatusBadRequest, recorder.Code)
+-	}
+-	server.ResetFailure(errorID)
+-	recorder = httptest.NewRecorder()
+-	request, _ = http.NewRequest("GET", "/containers/json?all=1", nil)
+-	server.ServeHTTP(recorder, request)
+-	if recorder.Code != http.StatusOK {
+-		t.Errorf("RemoveFailure: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
+-	}
+-}
+-
+-func TestMutateContainer(t *testing.T) {
+-	server := DockerServer{failures: make(map[string]string)}
+-	server.buildMuxer()
+-	server.containers = append(server.containers, &docker.Container{ID: "id123"})
+-	state := docker.State{Running: false, ExitCode: 1}
+-	err := server.MutateContainer("id123", state)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !reflect.DeepEqual(server.containers[0].State, state) {
+-		t.Errorf("Wrong state after mutation.\nWant %#v.\nGot %#v.",
+-			state, server.containers[0].State)
+-	}
+-}
+-
+-func TestMutateContainerNotFound(t *testing.T) {
+-	server := DockerServer{failures: make(map[string]string)}
+-	server.buildMuxer()
+-	state := docker.State{Running: false, ExitCode: 1}
+-	err := server.MutateContainer("id123", state)
+-	if err == nil {
+-		t.Error("Unexpected <nil> error")
+-	}
+-	if err.Error() != "container not found" {
+-		t.Errorf("wrong error message. Want %q. Got %q.", "container not found", err)
+-	}
+-}
+-
+-func TestBuildImageWithContentTypeTar(t *testing.T) {
+-	server := DockerServer{imgIDs: make(map[string]string)}
+-	imageName := "teste"
+-	recorder := httptest.NewRecorder()
+-	tarFile, err := os.Open("data/dockerfile.tar")
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	defer tarFile.Close()
+-	request, _ := http.NewRequest("POST", "/build?t=teste", tarFile)
+-	request.Header.Add("Content-Type", "application/tar")
+-	server.buildImage(recorder, request)
+-	if recorder.Body.String() == "miss Dockerfile" {
+-		t.Errorf("BuildImage: miss Dockerfile")
+-		return
+-	}
+-	if _, ok := server.imgIDs[imageName]; ok == false {
+-		t.Errorf("BuildImage: image %s not builded", imageName)
+-	}
+-}
+-
+-func TestBuildImageWithRemoteDockerfile(t *testing.T) {
+-	server := DockerServer{imgIDs: make(map[string]string)}
+-	imageName := "teste"
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("POST", "/build?t=teste&remote=http://localhost/Dockerfile", nil)
+-	server.buildImage(recorder, request)
+-	if _, ok := server.imgIDs[imageName]; ok == false {
+-		t.Errorf("BuildImage: image %s not builded", imageName)
+-	}
+-}
+-
+-func TestPing(t *testing.T) {
+-	server := DockerServer{}
+-	recorder := httptest.NewRecorder()
+-	request, _ := http.NewRequest("GET", "/_ping", nil)
+-	server.pingDocker(recorder, request)
+-	if recorder.Body.String() != "" {
+-		t.Errorf("Ping: Unexpected body: %s", recorder.Body.String())
+-	}
+-	if recorder.Code != http.StatusOK {
+-		t.Errorf("Ping: Expected code %d, got: %d", http.StatusOK, recorder.Code)
+-	}
+-}
+-
+-func TestDefaultHandler(t *testing.T) {
+-	server, err := NewServer("127.0.0.1:0", nil, nil)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	defer server.listener.Close()
+-	if server.mux != server.DefaultHandler() {
+-		t.Fatalf("DefaultHandler: Expected to return server.mux, got: %#v", server.DefaultHandler())
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/writer.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/writer.go
+deleted file mode 100644
+index 4ef857a..0000000
+--- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/writer.go
++++ /dev/null
+@@ -1,43 +0,0 @@
+-// Copyright 2014 go-dockerclient 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 testing
+-
+-import (
+-	"encoding/binary"
+-	"errors"
+-	"io"
+-)
+-
+-type stdType [8]byte
+-
+-var (
+-	stdin  = stdType{0: 0}
+-	stdout = stdType{0: 1}
+-	stderr = stdType{0: 2}
+-)
+-
+-type stdWriter struct {
+-	io.Writer
+-	prefix  stdType
+-	sizeBuf []byte
+-}
+-
+-func (w *stdWriter) Write(buf []byte) (n int, err error) {
+-	if w == nil || w.Writer == nil {
+-		return 0, errors.New("Writer not instanciated")
+-	}
+-	binary.BigEndian.PutUint32(w.prefix[4:], uint32(len(buf)))
+-	buf = append(w.prefix[:], buf...)
+-
+-	n, err = w.Writer.Write(buf)
+-	return n - 8, err
+-}
+-
+-func newStdWriter(w io.Writer, t stdType) *stdWriter {
+-	if len(t) != 8 {
+-		return nil
+-	}
+-	return &stdWriter{Writer: w, prefix: t, sizeBuf: make([]byte, 4)}
+-}
+diff --git a/Godeps/_workspace/src/github.com/ghodss/yaml/.gitignore b/Godeps/_workspace/src/github.com/ghodss/yaml/.gitignore
+deleted file mode 100644
+index e256a31..0000000
+--- a/Godeps/_workspace/src/github.com/ghodss/yaml/.gitignore
++++ /dev/null
+@@ -1,20 +0,0 @@
+-# OSX leaves these everywhere on SMB shares
+-._*
+-
+-# Eclipse files
+-.classpath
+-.project
+-.settings/**
+-
+-# Emacs save files
+-*~
+-
+-# Vim-related files
+-[._]*.s[a-w][a-z]
+-[._]s[a-w][a-z]
+-*.un~
+-Session.vim
+-.netrwhist
+-
+-# Go test binaries
+-*.test
+diff --git a/Godeps/_workspace/src/github.com/ghodss/yaml/LICENSE b/Godeps/_workspace/src/github.com/ghodss/yaml/LICENSE
+deleted file mode 100644
+index 7805d36..0000000
+--- a/Godeps/_workspace/src/github.com/ghodss/yaml/LICENSE
++++ /dev/null
+@@ -1,50 +0,0 @@
+-The MIT License (MIT)
+-
+-Copyright (c) 2014 Sam Ghods
+-
+-Permission is hereby granted, free of charge, to any person obtaining a copy
+-of this software and associated documentation files (the "Software"), to deal
+-in the Software without restriction, including without limitation the rights
+-to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+-copies of the Software, and to permit persons to whom the Software is
+-furnished to do so, subject to the following conditions:
+-
+-The above copyright notice and this permission notice shall be included in all
+-copies or substantial portions of the Software.
+-
+-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+-IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+-FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+-AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+-LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+-OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+-SOFTWARE.
+-
+-
+-Copyright (c) 2012 The Go Authors. All rights reserved.
+-
+-Redistribution and use in source and binary forms, with or without
+-modification, are permitted provided that the following conditions are
+-met:
+-
+-   * Redistributions of source code must retain the above copyright
+-notice, this list of conditions and the following disclaimer.
+-   * Redistributions in binary form must reproduce the above
+-copyright notice, this list of conditions and the following disclaimer
+-in the documentation and/or other materials provided with the
+-distribution.
+-   * Neither the name of Google Inc. nor the names of its
+-contributors may be used to endorse or promote products derived from
+-this software without specific prior written permission.
+-
+-THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+-"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+-LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+-A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+-OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+-SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+-LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+-DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+-THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+-(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+-OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+diff --git a/Godeps/_workspace/src/github.com/ghodss/yaml/README.md b/Godeps/_workspace/src/github.com/ghodss/yaml/README.md
+deleted file mode 100644
+index 2d60309..0000000
+--- a/Godeps/_workspace/src/github.com/ghodss/yaml/README.md
++++ /dev/null
+@@ -1,114 +0,0 @@
+-# YAML marshaling and unmarshaling support for Go
+-
+-## Introduction
+-
+-A wrapper around [go-yaml](https://github.com/go-yaml/yaml) designed to enable a better way of handling YAML when marshaling to and from structs. 
+-
+-In short, this library first converts YAML to JSON using go-yaml and then uses `json.Marshal` and `json.Unmarshal` to convert to or from the struct. This means that it effectively reuses the JSON struct tags as well as the custom JSON methods `MarshalJSON` and `UnmarshalJSON` unlike go-yaml. For a detailed overview of the rationale behind this method, [see this blog post](http://ghodss.com/2014/the-right-way-to-handle-yaml-in-golang/).
+-
+-## Compatibility
+-
+-This package uses [go-yaml v2](https://github.com/go-yaml/yaml) and therefore supports [everything go-yaml supports](https://github.com/go-yaml/yaml#compatibility).
+-
+-## Caveats
+-
+-**Caveat #1:** When using `yaml.Marshal` and `yaml.Unmarshal`, binary data should NOT be preceded with the `!!binary` YAML tag. If you do, go-yaml will convert the binary data from base64 to native binary data, which is not compatible with JSON. You can still use binary in your YAML files though - just store them without the `!!binary` tag and decode the base64 in your code (e.g. in the custom JSON methods `MarshalJSON` and `UnmarshalJSON`). This also has the benefit that your YAML and your JSON binary data will be decoded exactly the same way. As an example:
+-
+-```
+-BAD:
+-	exampleKey: !!binary gIGC
+-
+-GOOD:
+-	exampleKey: gIGC
+-... and decode the base64 data in your code.
+-```
+-
+-**Caveat #2:** When using `YAMLToJSON` directly, maps with keys that are maps will result in an error since this is not supported by JSON. This error will occur in `Unmarshal` as well since you can't unmarshal map keys anyways since struct fields can't be keys.
+-
+-## Installation and usage
+-
+-To install, run:
+-
+-```
+-$ go get github.com/ghodss/yaml
+-```
+-
+-And import using:
+-
+-```
+-import "github.com/ghodss/yaml"
+-```
+-
+-Usage is very similar to the JSON library:
+-
+-```go
+-import (
+-	"fmt"
+-
+-	"github.com/ghodss/yaml"
+-)
+-
+-type Person struct {
+-	Name string `json:"name"`  // Affects YAML field names too.
+-	Age int `json:"name"`
+-}
+-
+-func main() {
+-	// Marshal a Person struct to YAML.
+-	p := Person{"John", 30}
+-	y, err := yaml.Marshal(p)
+-	if err != nil {
+-		fmt.Printf("err: %v\n", err)
+-		return
+-	}
+-	fmt.Println(string(y))
+-	/* Output:
+-	name: John
+-	age: 30
+-	*/
+-
+-	// Unmarshal the YAML back into a Person struct.
+-	var p2 Person
+-	err := yaml.Unmarshal(y, &p2)
+-	if err != nil {
+-		fmt.Printf("err: %v\n", err)
+-		return
+-	}
+-	fmt.Println(p2)
+-	/* Output:
+-	{John 30}
+-	*/
+-}
+-```
+-
+-`yaml.YAMLToJSON` and `yaml.JSONToYAML` methods are also available:
+-
+-```go
+-import (
+-	"fmt"
+-
+-	"github.com/ghodss/yaml"
+-)
+-func main() {
+-	j := []byte(`{"name": "John", "age": 30}`)
+-	y, err := yaml.JSONToYAML(j)
+-	if err != nil {
+-		fmt.Printf("err: %v\n", err)
+-		return
+-	}
+-	fmt.Println(string(y))
+-	/* Output:
+-	name: John
+-	age: 30
+-	*/
+-	j2, err := yaml.YAMLToJSON(y)
+-	if err != nil {
+-		fmt.Printf("err: %v\n", err)
+-		return
+-	}
+-	fmt.Println(string(j2))
+-	/* Output:
+-	{"age":30,"name":"John"}
+-	*/
+-}
+-```
+diff --git a/Godeps/_workspace/src/github.com/ghodss/yaml/fields.go b/Godeps/_workspace/src/github.com/ghodss/yaml/fields.go
+deleted file mode 100644
+index 0bd3c2b..0000000
+--- a/Godeps/_workspace/src/github.com/ghodss/yaml/fields.go
++++ /dev/null
+@@ -1,497 +0,0 @@
+-// Copyright 2013 The Go 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 yaml
+-
+-import (
+-	"bytes"
+-	"encoding"
+-	"encoding/json"
+-	"reflect"
+-	"sort"
+-	"strings"
+-	"sync"
+-	"unicode"
+-	"unicode/utf8"
+-)
+-
+-// indirect walks down v allocating pointers as needed,
+-// until it gets to a non-pointer.
+-// if it encounters an Unmarshaler, indirect stops and returns that.
+-// if decodingNull is true, indirect stops at the last pointer so it can be set to nil.
+-func indirect(v reflect.Value, decodingNull bool) (json.Unmarshaler, encoding.TextUnmarshaler, reflect.Value) {
+-	// If v is a named type and is addressable,
+-	// start with its address, so that if the type has pointer methods,
+-	// we find them.
+-	if v.Kind() != reflect.Ptr && v.Type().Name() != "" && v.CanAddr() {
+-		v = v.Addr()
+-	}
+-	for {
+-		// Load value from interface, but only if the result will be
+-		// usefully addressable.
+-		if v.Kind() == reflect.Interface && !v.IsNil() {
+-			e := v.Elem()
+-			if e.Kind() == reflect.Ptr && !e.IsNil() && (!decodingNull || e.Elem().Kind() == reflect.Ptr) {
+-				v = e
+-				continue
+-			}
+-		}
+-
+-		if v.Kind() != reflect.Ptr {
+-			break
+-		}
+-
+-		if v.Elem().Kind() != reflect.Ptr && decodingNull && v.CanSet() {
+-			break
+-		}
+-		if v.IsNil() {
+-			v.Set(reflect.New(v.Type().Elem()))
+-		}
+-		if v.Type().NumMethod() > 0 {
+-			if u, ok := v.Interface().(json.Unmarshaler); ok {
+-				return u, nil, reflect.Value{}
+-			}
+-			if u, ok := v.Interface().(encoding.TextUnmarshaler); ok {
+-				return nil, u, reflect.Value{}
+-			}
+-		}
+-		v = v.Elem()
+-	}
+-	return nil, nil, v
+-}
+-
+-// A field represents a single field found in a struct.
+-type field struct {
+-	name      string
+-	nameBytes []byte                 // []byte(name)
+-	equalFold func(s, t []byte) bool // bytes.EqualFold or equivalent
+-
+-	tag       bool
+-	index     []int
+-	typ       reflect.Type
+-	omitEmpty bool
+-	quoted    bool
+-}
+-
+-func fillField(f field) field {
+-	f.nameBytes = []byte(f.name)
+-	f.equalFold = foldFunc(f.nameBytes)
+-	return f
+-}
+-
+-// byName sorts field by name, breaking ties with depth,
+-// then breaking ties with "name came from json tag", then
+-// breaking ties with index sequence.
+-type byName []field
+-
+-func (x byName) Len() int { return len(x) }
+-
+-func (x byName) Swap(i, j int) { x[i], x[j] = x[j], x[i] }
+-
+-func (x byName) Less(i, j int) bool {
+-	if x[i].name != x[j].name {
+-		return x[i].name < x[j].name
+-	}
+-	if len(x[i].index) != len(x[j].index) {
+-		return len(x[i].index) < len(x[j].index)
+-	}
+-	if x[i].tag != x[j].tag {
+-		return x[i].tag
+-	}
+-	return byIndex(x).Less(i, j)
+-}
+-
+-// byIndex sorts field by index sequence.
+-type byIndex []field
+-
+-func (x byIndex) Len() int { return len(x) }
+-
+-func (x byIndex) Swap(i, j int) { x[i], x[j] = x[j], x[i] }
+-
+-func (x byIndex) Less(i, j int) bool {
+-	for k, xik := range x[i].index {
+-		if k >= len(x[j].index) {
+-			return false
+-		}
+-		if xik != x[j].index[k] {
+-			return xik < x[j].index[k]
+-		}
+-	}
+-	return len(x[i].index) < len(x[j].index)
+-}
+-
+-// typeFields returns a list of fields that JSON should recognize for the given type.
+-// The algorithm is breadth-first search over the set of structs to include - the top struct
+-// and then any reachable anonymous structs.
+-func typeFields(t reflect.Type) []field {
+-	// Anonymous fields to explore at the current level and the next.
+-	current := []field{}
+-	next := []field{{typ: t}}
+-
+-	// Count of queued names for current level and the next.
+-	count := map[reflect.Type]int{}
+-	nextCount := map[reflect.Type]int{}
+-
+-	// Types already visited at an earlier level.
+-	visited := map[reflect.Type]bool{}
+-
+-	// Fields found.
+-	var fields []field
+-
+-	for len(next) > 0 {
+-		current, next = next, current[:0]
+-		count, nextCount = nextCount, map[reflect.Type]int{}
+-
+-		for _, f := range current {
+-			if visited[f.typ] {
+-				continue
+-			}
+-			visited[f.typ] = true
+-
+-			// Scan f.typ for fields to include.
+-			for i := 0; i < f.typ.NumField(); i++ {
+-				sf := f.typ.Field(i)
+-				if sf.PkgPath != "" { // unexported
+-					continue
+-				}
+-				tag := sf.Tag.Get("json")
+-				if tag == "-" {
+-					continue
+-				}
+-				name, opts := parseTag(tag)
+-				if !isValidTag(name) {
+-					name = ""
+-				}
+-				index := make([]int, len(f.index)+1)
+-				copy(index, f.index)
+-				index[len(f.index)] = i
+-
+-				ft := sf.Type
+-				if ft.Name() == "" && ft.Kind() == reflect.Ptr {
+-					// Follow pointer.
+-					ft = ft.Elem()
+-				}
+-
+-				// Record found field and index sequence.
+-				if name != "" || !sf.Anonymous || ft.Kind() != reflect.Struct {
+-					tagged := name != ""
+-					if name == "" {
+-						name = sf.Name
+-					}
+-					fields = append(fields, fillField(field{
+-						name:      name,
+-						tag:       tagged,
+-						index:     index,
+-						typ:       ft,
+-						omitEmpty: opts.Contains("omitempty"),
+-						quoted:    opts.Contains("string"),
+-					}))
+-					if count[f.typ] > 1 {
+-						// If there were multiple instances, add a second,
+-						// so that the annihilation code will see a duplicate.
+-						// It only cares about the distinction between 1 or 2,
+-						// so don't bother generating any more copies.
+-						fields = append(fields, fields[len(fields)-1])
+-					}
+-					continue
+-				}
+-
+-				// Record new anonymous struct to explore in next round.
+-				nextCount[ft]++
+-				if nextCount[ft] == 1 {
+-					next = append(next, fillField(field{name: ft.Name(), index: index, typ: ft}))
+-				}
+-			}
+-		}
+-	}
+-
+-	sort.Sort(byName(fields))
+-
+-	// Delete all fields that are hidden by the Go rules for embedded fields,
+-	// except that fields with JSON tags are promoted.
+-
+-	// The fields are sorted in primary order of name, secondary order
+-	// of field index length. Loop over names; for each name, delete
+-	// hidden fields by choosing the one dominant field that survives.
+-	out := fields[:0]
+-	for advance, i := 0, 0; i < len(fields); i += advance {
+-		// One iteration per name.
+-		// Find the sequence of fields with the name of this first field.
+-		fi := fields[i]
+-		name := fi.name
+-		for advance = 1; i+advance < len(fields); advance++ {
+-			fj := fields[i+advance]
+-			if fj.name != name {
+-				break
+-			}
+-		}
+-		if advance == 1 { // Only one field with this name
+-			out = append(out, fi)
+-			continue
+-		}
+-		dominant, ok := dominantField(fields[i : i+advance])
+-		if ok {
+-			out = append(out, dominant)
+-		}
+-	}
+-
+-	fields = out
+-	sort.Sort(byIndex(fields))
+-
+-	return fields
+-}
+-
+-// dominantField looks through the fields, all of which are known to
+-// have the same name, to find the single field that dominates the
+-// others using Go's embedding rules, modified by the presence of
+-// JSON tags. If there are multiple top-level fields, the boolean
+-// will be false: This condition is an error in Go and we skip all
+-// the fields.
+-func dominantField(fields []field) (field, bool) {
+-	// The fields are sorted in increasing index-length order. The winner
+-	// must therefore be one with the shortest index length. Drop all
+-	// longer entries, which is easy: just truncate the slice.
+-	length := len(fields[0].index)
+-	tagged := -1 // Index of first tagged field.
+-	for i, f := range fields {
+-		if len(f.index) > length {
+-			fields = fields[:i]
+-			break
+-		}
+-		if f.tag {
+-			if tagged >= 0 {
+-				// Multiple tagged fields at the same level: conflict.
+-				// Return no field.
+-				return field{}, false
+-			}
+-			tagged = i
+-		}
+-	}
+-	if tagged >= 0 {
+-		return fields[tagged], true
+-	}
+-	// All remaining fields have the same length. If there's more than one,
+-	// we have a conflict (two fields named "X" at the same level) and we
+-	// return no field.
+-	if len(fields) > 1 {
+-		return field{}, false
+-	}
+-	return fields[0], true
+-}
+-
+-var fieldCache struct {
+-	sync.RWMutex
+-	m map[reflect.Type][]field
+-}
+-
+-// cachedTypeFields is like typeFields but uses a cache to avoid repeated work.
+-func cachedTypeFields(t reflect.Type) []field {
+-	fieldCache.RLock()
+-	f := fieldCache.m[t]
+-	fieldCache.RUnlock()
+-	if f != nil {
+-		return f
+-	}
+-
+-	// Compute fields without lock.
+-	// Might duplicate effort but won't hold other computations back.
+-	f = typeFields(t)
+-	if f == nil {
+-		f = []field{}
+-	}
+-
+-	fieldCache.Lock()
+-	if fieldCache.m == nil {
+-		fieldCache.m = map[reflect.Type][]field{}
+-	}
+-	fieldCache.m[t] = f
+-	fieldCache.Unlock()
+-	return f
+-}
+-
+-func isValidTag(s string) bool {
+-	if s == "" {
+-		return false
+-	}
+-	for _, c := range s {
+-		switch {
+-		case strings.ContainsRune("!#$%&()*+-./:<=>?@[]^_{|}~ ", c):
+-			// Backslash and quote chars are reserved, but
+-			// otherwise any punctuation chars are allowed
+-			// in a tag name.
+-		default:
+-			if !unicode.IsLetter(c) && !unicode.IsDigit(c) {
+-				return false
+-			}
+-		}
+-	}
+-	return true
+-}
+-
+-const (
+-	caseMask     = ^byte(0x20) // Mask to ignore case in ASCII.
+-	kelvin       = '\u212a'
+-	smallLongEss = '\u017f'
+-)
+-
+-// foldFunc returns one of four different case folding equivalence
+-// functions, from most general (and slow) to fastest:
+-//
+-// 1) bytes.EqualFold, if the key s contains any non-ASCII UTF-8
+-// 2) equalFoldRight, if s contains special folding ASCII ('k', 'K', 's', 'S')
+-// 3) asciiEqualFold, no special, but includes non-letters (including _)
+-// 4) simpleLetterEqualFold, no specials, no non-letters.
+-//
+-// The letters S and K are special because they map to 3 runes, not just 2:
+-//  * S maps to s and to U+017F 'ſ' Latin small letter long s
+-//  * k maps to K and to U+212A 'K' Kelvin sign
+-// See http://play.golang.org/p/tTxjOc0OGo
+-//
+-// The returned function is specialized for matching against s and
+-// should only be given s. It's not curried for performance reasons.
+-func foldFunc(s []byte) func(s, t []byte) bool {
+-	nonLetter := false
+-	special := false // special letter
+-	for _, b := range s {
+-		if b >= utf8.RuneSelf {
+-			return bytes.EqualFold
+-		}
+-		upper := b & caseMask
+-		if upper < 'A' || upper > 'Z' {
+-			nonLetter = true
+-		} else if upper == 'K' || upper == 'S' {
+-			// See above for why these letters are special.
+-			special = true
+-		}
+-	}
+-	if special {
+-		return equalFoldRight
+-	}
+-	if nonLetter {
+-		return asciiEqualFold
+-	}
+-	return simpleLetterEqualFold
+-}
+-
+-// equalFoldRight is a specialization of bytes.EqualFold when s is
+-// known to be all ASCII (including punctuation), but contains an 's',
+-// 'S', 'k', or 'K', requiring a Unicode fold on the bytes in t.
+-// See comments on foldFunc.
+-func equalFoldRight(s, t []byte) bool {
+-	for _, sb := range s {
+-		if len(t) == 0 {
+-			return false
+-		}
+-		tb := t[0]
+-		if tb < utf8.RuneSelf {
+-			if sb != tb {
+-				sbUpper := sb & caseMask
+-				if 'A' <= sbUpper && sbUpper <= 'Z' {
+-					if sbUpper != tb&caseMask {
+-						return false
+-					}
+-				} else {
+-					return false
+-				}
+-			}
+-			t = t[1:]
+-			continue
+-		}
+-		// sb is ASCII and t is not. t must be either kelvin
+-		// sign or long s; sb must be s, S, k, or K.
+-		tr, size := utf8.DecodeRune(t)
+-		switch sb {
+-		case 's', 'S':
+-			if tr != smallLongEss {
+-				return false
+-			}
+-		case 'k', 'K':
+-			if tr != kelvin {
+-				return false
+-			}
+-		default:
+-			return false
+-		}
+-		t = t[size:]
+-
+-	}
+-	if len(t) > 0 {
+-		return false
+-	}
+-	return true
+-}
+-
+-// asciiEqualFold is a specialization of bytes.EqualFold for use when
+-// s is all ASCII (but may contain non-letters) and contains no
+-// special-folding letters.
+-// See comments on foldFunc.
+-func asciiEqualFold(s, t []byte) bool {
+-	if len(s) != len(t) {
+-		return false
+-	}
+-	for i, sb := range s {
+-		tb := t[i]
+-		if sb == tb {
+-			continue
+-		}
+-		if ('a' <= sb && sb <= 'z') || ('A' <= sb && sb <= 'Z') {
+-			if sb&caseMask != tb&caseMask {
+-				return false
+-			}
+-		} else {
+-			return false
+-		}
+-	}
+-	return true
+-}
+-
+-// simpleLetterEqualFold is a specialization of bytes.EqualFold for
+-// use when s is all ASCII letters (no underscores, etc) and also
+-// doesn't contain 'k', 'K', 's', or 'S'.
+-// See comments on foldFunc.
+-func simpleLetterEqualFold(s, t []byte) bool {
+-	if len(s) != len(t) {
+-		return false
+-	}
+-	for i, b := range s {
+-		if b&caseMask != t[i]&caseMask {
+-			return false
+-		}
+-	}
+-	return true
+-}
+-
+-// tagOptions is the string following a comma in a struct field's "json"
+-// tag, or the empty string. It does not include the leading comma.
+-type tagOptions string
+-
+-// parseTag splits a struct field's json tag into its name and
+-// comma-separated options.
+-func parseTag(tag string) (string, tagOptions) {
+-	if idx := strings.Index(tag, ","); idx != -1 {
+-		return tag[:idx], tagOptions(tag[idx+1:])
+-	}
+-	return tag, tagOptions("")
+-}
+-
+-// Contains reports whether a comma-separated list of options
+-// contains a particular substr flag. substr must be surrounded by a
+-// string boundary or commas.
+-func (o tagOptions) Contains(optionName string) bool {
+-	if len(o) == 0 {
+-		return false
+-	}
+-	s := string(o)
+-	for s != "" {
+-		var next string
+-		i := strings.Index(s, ",")
+-		if i >= 0 {
+-			s, next = s[:i], s[i+1:]
+-		}
+-		if s == optionName {
+-			return true
+-		}
+-		s = next
+-	}
+-	return false
+-}
+diff --git a/Godeps/_workspace/src/github.com/ghodss/yaml/yaml.go b/Godeps/_workspace/src/github.com/ghodss/yaml/yaml.go
+deleted file mode 100644
+index feab226..0000000
+--- a/Godeps/_workspace/src/github.com/ghodss/yaml/yaml.go
++++ /dev/null
+@@ -1,250 +0,0 @@
+-package yaml
+-
+-import (
+-	"bytes"
+-	"encoding/json"
+-	"fmt"
+-	"reflect"
+-	"strconv"
+-
+-	"gopkg.in/v2/yaml"
+-)
+-
+-// Marshals the object into JSON then converts JSON to YAML and returns the
+-// YAML.
+-func Marshal(o interface{}) ([]byte, error) {
+-	j, err := json.Marshal(o)
+-	if err != nil {
+-		return nil, fmt.Errorf("error marshaling into JSON: ", err)
+-	}
+-
+-	y, err := JSONToYAML(j)
+-	if err != nil {
+-		return nil, fmt.Errorf("error converting JSON to YAML: ", err)
+-	}
+-
+-	return y, nil
+-}
+-
+-// Converts YAML to JSON then uses JSON to unmarshal into an object.
+-func Unmarshal(y []byte, o interface{}) error {
+-	vo := reflect.ValueOf(o)
+-	j, err := yamlToJSON(y, &vo)
+-	if err != nil {
+-		return fmt.Errorf("error converting YAML to JSON: %v", err)
+-	}
+-
+-	err = json.Unmarshal(j, o)
+-	if err != nil {
+-		return fmt.Errorf("error unmarshaling JSON: %v", err)
+-	}
+-
+-	return nil
+-}
+-
+-// Convert JSON to YAML.
+-func JSONToYAML(j []byte) ([]byte, error) {
+-	// Convert the JSON to an object.
+-	var jsonObj interface{}
+-	err := json.Unmarshal(j, &jsonObj)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	// Marshal this object into YAML.
+-	return yaml.Marshal(jsonObj)
+-}
+-
+-// Convert YAML to JSON. Since JSON is a subset of YAML, passing JSON through
+-// this method should be a no-op.
+-//
+-// Things YAML can do that are not supported by JSON:
+-// * In YAML you can have binary and null keys in your maps. These are invalid
+-//   in JSON. (int and float keys are converted to strings.)
+-// * Binary data in YAML with the !!binary tag is not supported. If you want to
+-//   use binary data with this library, encode the data as base64 as usual but do
+-//   not use the !!binary tag in your YAML. This will ensure the original base64
+-//   encoded data makes it all the way through to the JSON.
+-func YAMLToJSON(y []byte) ([]byte, error) {
+-	return yamlToJSON(y, nil)
+-}
+-
+-func yamlToJSON(y []byte, jsonTarget *reflect.Value) ([]byte, error) {
+-	// Convert the YAML to an object.
+-	var yamlObj interface{}
+-	err := yaml.Unmarshal(y, &yamlObj)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	// YAML objects are not completely compatible with JSON objects (e.g. you
+-	// can have non-string keys in YAML). So, convert the YAML-compatible object
+-	// to a JSON-compatible object, failing with an error if irrecoverable
+-	// incompatibilties happen along the way.
+-	jsonObj, err := convertToJSONableObject(yamlObj, jsonTarget)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	// Convert this object to JSON and return the data.
+-	return json.Marshal(jsonObj)
+-}
+-
+-func convertToJSONableObject(yamlObj interface{}, jsonTarget *reflect.Value) (interface{}, error) {
+-	var err error
+-
+-	// Resolve jsonTarget to a concrete value (i.e. not a pointer or an
+-	// interface). We pass decodingNull as false because we're not actually
+-	// decoding into the value, we're just checking if the ultimate target is a
+-	// string.
+-	if jsonTarget != nil {
+-		ju, tu, pv := indirect(*jsonTarget, false)
+-		// We have a JSON or Text Umarshaler at this level, so we can't be trying
+-		// to decode into a string.
+-		if ju != nil || tu != nil {
+-			jsonTarget = nil
+-		} else {
+-			jsonTarget = &pv
+-		}
+-	}
+-
+-	// If yamlObj is a number, check if jsonTarget is a string - if so, coerce.
+-	// Else return normal.
+-	// If yamlObj is a map or array, find the field that each key is
+-	// unmarshaling to, and when you recurse pass the reflect.Value for that
+-	// field back into this function.
+-
+-	switch typedYAMLObj := yamlObj.(type) {
+-	case map[interface{}]interface{}:
+-		// JSON does not support arbitrary keys in a map, so we must convert
+-		// these keys to strings.
+-		//
+-		// From my reading of go-yaml v2 (specifically the resolve function),
+-		// keys can only have the types string, int, int64, float64, binary
+-		// (unsupported), or null (unsupported).
+-		strMap := make(map[string]interface{})
+-		for k, v := range typedYAMLObj {
+-			// Resolve the key to a string first.
+-			var keyString string
+-			switch typedKey := k.(type) {
+-			case string:
+-				keyString = typedKey
+-			case int:
+-				keyString = strconv.Itoa(typedKey)
+-			case int64:
+-				// go-yaml will only return an int64 as a key if the system
+-				// architecture is 32-bit and the key's value is between 32-bit
+-				// and 64-bit. Otherwise the key type will simply be int.
+-				keyString = strconv.FormatInt(typedKey, 10)
+-			case float64:
+-				// Stolen from go-yaml to use the same conversion to string as
+-				// the go-yaml library uses to convert float to string when
+-				// Marshaling.
+-				s := strconv.FormatFloat(typedKey, 'g', -1, 32)
+-				switch s {
+-				case "+Inf":
+-					s = ".inf"
+-				case "-Inf":
+-					s = "-.inf"
+-				case "NaN":
+-					s = ".nan"
+-				}
+-				keyString = s
+-			default:
+-				return nil, fmt.Errorf("Unsupported map key of type: %s, key: %+#v, value: %+#v",
+-					reflect.TypeOf(k), k, v)
+-			}
+-
+-			// If jsonTarget is a struct (which it really should be), find the
+-			// field it's going to map to. If it's not a struct, just pass nil
+-			// - JSON conversion will error for us if it's a real issue.
+-			if jsonTarget != nil {
+-				t := *jsonTarget
+-				if t.Kind() == reflect.Struct {
+-					keyBytes := []byte(keyString)
+-					// Find the field that the JSON library would use.
+-					var f *field
+-					fields := cachedTypeFields(t.Type())
+-					for i := range fields {
+-						ff := &fields[i]
+-						if bytes.Equal(ff.nameBytes, keyBytes) {
+-							f = ff
+-							break
+-						}
+-						// Do case-insensitive comparison.
+-						if f == nil && ff.equalFold(ff.nameBytes, keyBytes) {
+-							f = ff
+-						}
+-					}
+-					if f != nil {
+-						// Find the reflect.Value of the most preferential
+-						// struct field.
+-						jtf := t.Field(f.index[0])
+-						strMap[keyString], err = convertToJSONableObject(v, &jtf)
+-						if err != nil {
+-							return nil, err
+-						}
+-						continue
+-					}
+-				}
+-			}
+-			strMap[keyString], err = convertToJSONableObject(v, nil)
+-			if err != nil {
+-				return nil, err
+-			}
+-		}
+-		return strMap, nil
+-	case []interface{}:
+-		// We need to recurse into arrays in case there are any
+-		// map[interface{}]interface{}'s inside and to convert any
+-		// numbers to strings.
+-
+-		// If jsonTarget is a slice (which it really should be), find the
+-		// thing it's going to map to. If it's not a slice, just pass nil
+-		// - JSON conversion will error for us if it's a real issue.
+-		var jsonSliceElemValue *reflect.Value
+-		if jsonTarget != nil {
+-			t := *jsonTarget
+-			if t.Kind() == reflect.Slice {
+-				// By default slices point to nil, but we need a reflect.Value
+-				// pointing to a value of the slice type, so we create one here.
+-				ev := reflect.Indirect(reflect.New(t.Type().Elem()))
+-				jsonSliceElemValue = &ev
+-			}
+-		}
+-
+-		// Make and use a new array.
+-		arr := make([]interface{}, len(typedYAMLObj))
+-		for i, v := range typedYAMLObj {
+-			arr[i], err = convertToJSONableObject(v, jsonSliceElemValue)
+-			if err != nil {
+-				return nil, err
+-			}
+-		}
+-		return arr, nil
+-	default:
+-		// If the target type is a string and the YAML type is a number,
+-		// convert the YAML type to a string.
+-		if jsonTarget != nil && (*jsonTarget).Kind() == reflect.String {
+-			// Based on my reading of go-yaml, it may return int, int64,
+-			// float64, or uint64.
+-			var s string
+-			switch num := typedYAMLObj.(type) {
+-			case int:
+-				s = strconv.FormatInt(int64(num), 10)
+-			case int64:
+-				s = strconv.FormatInt(num, 10)
+-			case float64:
+-				s = strconv.FormatFloat(num, 'g', -1, 32)
+-			case uint64:
+-				s = strconv.FormatUint(num, 10)
+-			}
+-			if len(s) > 0 {
+-				yamlObj = interface{}(s)
+-			}
+-		}
+-		return yamlObj, nil
+-	}
+-
+-	return nil, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/ghodss/yaml/yaml_test.go b/Godeps/_workspace/src/github.com/ghodss/yaml/yaml_test.go
+deleted file mode 100644
+index c569ebd..0000000
+--- a/Godeps/_workspace/src/github.com/ghodss/yaml/yaml_test.go
++++ /dev/null
+@@ -1,243 +0,0 @@
+-package yaml
+-
+-import (
+-	"reflect"
+-	"testing"
+-)
+-
+-type MarshalTest struct {
+-	A string
+-}
+-
+-func TestMarshal(t *testing.T) {
+-	s := MarshalTest{"a"}
+-	e := []byte("A: a\n")
+-
+-	y, err := Marshal(s)
+-	if err != nil {
+-		t.Errorf("error marshaling YAML: %v", err)
+-	}
+-
+-	if !reflect.DeepEqual(y, e) {
+-		t.Errorf("marshal YAML was unsuccessful, expected: %#v, got: %#v",
+-			string(e), string(y))
+-	}
+-}
+-
+-type UnmarshalString struct {
+-	A string
+-}
+-
+-type UnmarshalNestedString struct {
+-	A NestedString
+-}
+-
+-type NestedString struct {
+-	A string
+-}
+-
+-type UnmarshalSlice struct {
+-	A []NestedSlice
+-}
+-
+-type NestedSlice struct {
+-	B string
+-	C *string
+-}
+-
+-func TestUnmarshal(t *testing.T) {
+-	y := []byte("a: 1")
+-	s1 := UnmarshalString{}
+-	e1 := UnmarshalString{"1"}
+-	unmarshal(t, y, &s1, &e1)
+-
+-	y = []byte("a:\n  a: 1")
+-	s2 := UnmarshalNestedString{}
+-	e2 := UnmarshalNestedString{NestedString{"1"}}
+-	unmarshal(t, y, &s2, &e2)
+-
+-	y = []byte("a:\n  - b: abc\n    c: def\n  - b: 123\n    c: 456\n")
+-	s3 := UnmarshalSlice{}
+-	e3 := UnmarshalSlice{[]NestedSlice{NestedSlice{"abc", strPtr("def")}, NestedSlice{"123", strPtr("456")}}}
+-	unmarshal(t, y, &s3, &e3)
+-}
+-
+-func unmarshal(t *testing.T, y []byte, s, e interface{}) {
+-	err := Unmarshal(y, s)
+-	if err != nil {
+-		t.Errorf("error unmarshaling YAML: %v", err)
+-	}
+-
+-	if !reflect.DeepEqual(s, e) {
+-		t.Errorf("unmarshal YAML was unsuccessful, expected: %+#v, got: %+#v",
+-			e, s)
+-	}
+-}
+-
+-type Case struct {
+-	input  string
+-	output string
+-	// By default we test that reversing the output == input. But if there is a
+-	// difference in the reversed output, you can optionally specify it here.
+-	reverse *string
+-}
+-
+-type RunType int
+-
+-const (
+-	RunTypeJSONToYAML RunType = iota
+-	RunTypeYAMLToJSON
+-)
+-
+-func TestJSONToYAML(t *testing.T) {
+-	cases := []Case{
+-		{
+-			`{"t":"a"}`,
+-			"t: a\n",
+-			nil,
+-		}, {
+-			`{"t":null}`,
+-			"t: null\n",
+-			nil,
+-		},
+-	}
+-
+-	runCases(t, RunTypeJSONToYAML, cases)
+-}
+-
+-func TestYAMLToJSON(t *testing.T) {
+-	cases := []Case{
+-		{
+-			"t: a\n",
+-			`{"t":"a"}`,
+-			nil,
+-		}, {
+-			"t: \n",
+-			`{"t":null}`,
+-			strPtr("t: null\n"),
+-		}, {
+-			"t: null\n",
+-			`{"t":null}`,
+-			nil,
+-		}, {
+-			"1: a\n",
+-			`{"1":"a"}`,
+-			strPtr("\"1\": a\n"),
+-		}, {
+-			"1000000000000000000000000000000000000: a\n",
+-			`{"1e+36":"a"}`,
+-			strPtr("\"1e+36\": a\n"),
+-		}, {
+-			"1e+36: a\n",
+-			`{"1e+36":"a"}`,
+-			strPtr("\"1e+36\": a\n"),
+-		}, {
+-			"\"1e+36\": a\n",
+-			`{"1e+36":"a"}`,
+-			nil,
+-		}, {
+-			"\"1.2\": a\n",
+-			`{"1.2":"a"}`,
+-			nil,
+-		}, {
+-			"- t: a\n",
+-			`[{"t":"a"}]`,
+-			nil,
+-		}, {
+-			"- t: a\n" +
+-				"- t:\n" +
+-				"    b: 1\n" +
+-				"    c: 2\n",
+-			`[{"t":"a"},{"t":{"b":1,"c":2}}]`,
+-			nil,
+-		}, {
+-			`[{t: a}, {t: {b: 1, c: 2}}]`,
+-			`[{"t":"a"},{"t":{"b":1,"c":2}}]`,
+-			strPtr("- t: a\n" +
+-				"- t:\n" +
+-				"    b: 1\n" +
+-				"    c: 2\n"),
+-		}, {
+-			"- t: \n",
+-			`[{"t":null}]`,
+-			strPtr("- t: null\n"),
+-		}, {
+-			"- t: null\n",
+-			`[{"t":null}]`,
+-			nil,
+-		},
+-	}
+-
+-	// Cases that should produce errors.
+-	_ = []Case{
+-		{
+-			"~: a",
+-			`{"null":"a"}`,
+-			nil,
+-		}, {
+-			"a: !!binary gIGC\n",
+-			"{\"a\":\"\x80\x81\x82\"}",
+-			nil,
+-		},
+-	}
+-
+-	runCases(t, RunTypeYAMLToJSON, cases)
+-}
+-
+-func runCases(t *testing.T, runType RunType, cases []Case) {
+-	var f func([]byte) ([]byte, error)
+-	var invF func([]byte) ([]byte, error)
+-	var msg string
+-	var invMsg string
+-	if runType == RunTypeJSONToYAML {
+-		f = JSONToYAML
+-		invF = YAMLToJSON
+-		msg = "JSON to YAML"
+-		invMsg = "YAML back to JSON"
+-	} else {
+-		f = YAMLToJSON
+-		invF = JSONToYAML
+-		msg = "YAML to JSON"
+-		invMsg = "JSON back to YAML"
+-	}
+-
+-	for _, c := range cases {
+-		// Convert the string.
+-		t.Logf("converting %s\n", c.input)
+-		output, err := f([]byte(c.input))
+-		if err != nil {
+-			t.Errorf("Failed to convert %s, input: `%s`, err: %v", msg, c.input, err)
+-		}
+-
+-		// Check it against the expected output.
+-		if string(output) != c.output {
+-			t.Errorf("Failed to convert %s, input: `%s`, expected `%s`, got `%s`",
+-				msg, c.input, c.output, string(output))
+-		}
+-
+-		// Set the string that we will compare the reversed output to.
+-		reverse := c.input
+-		// If a special reverse string was specified, use that instead.
+-		if c.reverse != nil {
+-			reverse = *c.reverse
+-		}
+-
+-		// Reverse the output.
+-		input, err := invF(output)
+-		if err != nil {
+-			t.Errorf("Failed to convert %s, input: `%s`, err: %v", invMsg, string(output), err)
+-		}
+-
+-		// Check the reverse is equal to the input (or to *c.reverse).
+-		if string(input) != reverse {
+-			t.Errorf("Failed to convert %s, input: `%s`, expected `%s`, got `%s`",
+-				invMsg, string(output), reverse, string(input))
+-		}
+-	}
+-
+-}
+-
+-// To be able to easily fill in the *Case.reverse string above.
+-func strPtr(s string) *string {
+-	return &s
+-}
+diff --git a/Godeps/_workspace/src/github.com/golang/glog/LICENSE b/Godeps/_workspace/src/github.com/golang/glog/LICENSE
+deleted file mode 100644
+index 37ec93a..0000000
+--- a/Godeps/_workspace/src/github.com/golang/glog/LICENSE
++++ /dev/null
+@@ -1,191 +0,0 @@
+-Apache License
+-Version 2.0, January 2004
+-http://www.apache.org/licenses/
+-
+-TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+-
+-1. Definitions.
+-
+-"License" shall mean the terms and conditions for use, reproduction, and
+-distribution as defined by Sections 1 through 9 of this document.
+-
+-"Licensor" shall mean the copyright owner or entity authorized by the copyright
+-owner that is granting the License.
+-
+-"Legal Entity" shall mean the union of the acting entity and all other entities
+-that control, are controlled by, or are under common control with that entity.
+-For the purposes of this definition, "control" means (i) the power, direct or
+-indirect, to cause the direction or management of such entity, whether by
+-contract or otherwise, or (ii) ownership of fifty percent (50%) or more of the
+-outstanding shares, or (iii) beneficial ownership of such entity.
+-
+-"You" (or "Your") shall mean an individual or Legal Entity exercising
+-permissions granted by this License.
+-
+-"Source" form shall mean the preferred form for making modifications, including
+-but not limited to software source code, documentation source, and configuration
+-files.
+-
+-"Object" form shall mean any form resulting from mechanical transformation or
+-translation of a Source form, including but not limited to compiled object code,
+-generated documentation, and conversions to other media types.
+-
+-"Work" shall mean the work of authorship, whether in Source or Object form, made
+-available under the License, as indicated by a copyright notice that is included
+-in or attached to the work (an example is provided in the Appendix below).
+-
+-"Derivative Works" shall mean any work, whether in Source or Object form, that
+-is based on (or derived from) the Work and for which the editorial revisions,
+-annotations, elaborations, or other modifications represent, as a whole, an
+-original work of authorship. For the purposes of this License, Derivative Works
+-shall not include works that remain separable from, or merely link (or bind by
+-name) to the interfaces of, the Work and Derivative Works thereof.
+-
+-"Contribution" shall mean any work of authorship, including the original version
+-of the Work and any modifications or additions to that Work or Derivative Works
+-thereof, that is intentionally submitted to Licensor for inclusion in the Work
+-by the copyright owner or by an individual or Legal Entity authorized to submit
+-on behalf of the copyright owner. For the purposes of this definition,
+-"submitted" means any form of electronic, verbal, or written communication sent
+-to the Licensor or its representatives, including but not limited to
+-communication on electronic mailing lists, source code control systems, and
+-issue tracking systems that are managed by, or on behalf of, the Licensor for
+-the purpose of discussing and improving the Work, but excluding communication
+-that is conspicuously marked or otherwise designated in writing by the copyright
+-owner as "Not a Contribution."
+-
+-"Contributor" shall mean Licensor and any individual or Legal Entity on behalf
+-of whom a Contribution has been received by Licensor and subsequently
+-incorporated within the Work.
+-
+-2. Grant of Copyright License.
+-
+-Subject to the terms and conditions of this License, each Contributor hereby
+-grants to You a perpetual, worldwide, non-exclusive, no-charge, royalty-free,
+-irrevocable copyright license to reproduce, prepare Derivative Works of,
+-publicly display, publicly perform, sublicense, and distribute the Work and such
+-Derivative Works in Source or Object form.
+-
+-3. Grant of Patent License.
+-
+-Subject to the terms and conditions of this License, each Contributor hereby
+-grants to You a perpetual, worldwide, non-exclusive, no-charge, royalty-free,
+-irrevocable (except as stated in this section) patent license to make, have
+-made, use, offer to sell, sell, import, and otherwise transfer the Work, where
+-such license applies only to those patent claims licensable by such Contributor
+-that are necessarily infringed by their Contribution(s) alone or by combination
+-of their Contribution(s) with the Work to which such Contribution(s) was
+-submitted. If You institute patent litigation against any entity (including a
+-cross-claim or counterclaim in a lawsuit) alleging that the Work or a
+-Contribution incorporated within the Work constitutes direct or contributory
+-patent infringement, then any patent licenses granted to You under this License
+-for that Work shall terminate as of the date such litigation is filed.
+-
+-4. Redistribution.
+-
+-You may reproduce and distribute copies of the Work or Derivative Works thereof
+-in any medium, with or without modifications, and in Source or Object form,
+-provided that You meet the following conditions:
+-
+-You must give any other recipients of the Work or Derivative Works a copy of
+-this License; and
+-You must cause any modified files to carry prominent notices stating that You
+-changed the files; and
+-You must retain, in the Source form of any Derivative Works that You distribute,
+-all copyright, patent, trademark, and attribution notices from the Source form
+-of the Work, excluding those notices that do not pertain to any part of the
+-Derivative Works; and
+-If the Work includes a "NOTICE" text file as part of its distribution, then any
+-Derivative Works that You distribute must include a readable copy of the
+-attribution notices contained within such NOTICE file, excluding those notices
+-that do not pertain to any part of the Derivative Works, in at least one of the
+-following places: within a NOTICE text file distributed as part of the
+-Derivative Works; within the Source form or documentation, if provided along
+-with the Derivative Works; or, within a display generated by the Derivative
+-Works, if and wherever such third-party notices normally appear. The contents of
+-the NOTICE file are for informational purposes only and do not modify the
+-License. You may add Your own attribution notices within Derivative Works that
+-You distribute, alongside or as an addendum to the NOTICE text from the Work,
+-provided that such additional attribution notices cannot be construed as
+-modifying the License.
+-You may add Your own copyright statement to Your modifications and may provide
+-additional or different license terms and conditions for use, reproduction, or
+-distribution of Your modifications, or for any such Derivative Works as a whole,
+-provided Your use, reproduction, and distribution of the Work otherwise complies
+-with the conditions stated in this License.
+-
+-5. Submission of Contributions.
+-
+-Unless You explicitly state otherwise, any Contribution intentionally submitted
+-for inclusion in the Work by You to the Licensor shall be under the terms and
+-conditions of this License, without any additional terms or conditions.
+-Notwithstanding the above, nothing herein shall supersede or modify the terms of
+-any separate license agreement you may have executed with Licensor regarding
+-such Contributions.
+-
+-6. Trademarks.
+-
+-This License does not grant permission to use the trade names, trademarks,
+-service marks, or product names of the Licensor, except as required for
+-reasonable and customary use in describing the origin of the Work and
+-reproducing the content of the NOTICE file.
+-
+-7. Disclaimer of Warranty.
+-
+-Unless required by applicable law or agreed to in writing, Licensor provides the
+-Work (and each Contributor provides its Contributions) on an "AS IS" BASIS,
+-WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied,
+-including, without limitation, any warranties or conditions of TITLE,
+-NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A PARTICULAR PURPOSE. You are
+-solely responsible for determining the appropriateness of using or
+-redistributing the Work and assume any risks associated with Your exercise of
+-permissions under this License.
+-
+-8. Limitation of Liability.
+-
+-In no event and under no legal theory, whether in tort (including negligence),
+-contract, or otherwise, unless required by applicable law (such as deliberate
+-and grossly negligent acts) or agreed to in writing, shall any Contributor be
+-liable to You for damages, including any direct, indirect, special, incidental,
+-or consequential damages of any character arising as a result of this License or
+-out of the use or inability to use the Work (including but not limited to
+-damages for loss of goodwill, work stoppage, computer failure or malfunction, or
+-any and all other commercial damages or losses), even if such Contributor has
+-been advised of the possibility of such damages.
+-
+-9. Accepting Warranty or Additional Liability.
+-
+-While redistributing the Work or Derivative Works thereof, You may choose to
+-offer, and charge a fee for, acceptance of support, warranty, indemnity, or
+-other liability obligations and/or rights consistent with this License. However,
+-in accepting such obligations, You may act only on Your own behalf and on Your
+-sole responsibility, not on behalf of any other Contributor, and only if You
+-agree to indemnify, defend, and hold each Contributor harmless for any liability
+-incurred by, or claims asserted against, such Contributor by reason of your
+-accepting any such warranty or additional liability.
+-
+-END OF TERMS AND CONDITIONS
+-
+-APPENDIX: How to apply the Apache License to your work
+-
+-To apply the Apache License to your work, attach the following boilerplate
+-notice, with the fields enclosed by brackets "[]" replaced with your own
+-identifying information. (Don't include the brackets!) The text should be
+-enclosed in the appropriate comment syntax for the file format. We also
+-recommend that a file or class name and description of purpose be included on
+-the same "printed page" as the copyright notice for easier identification within
+-third-party archives.
+-
+-   Copyright [yyyy] [name of copyright owner]
+-
+-   Licensed under the Apache License, Version 2.0 (the "License");
+-   you may not use this file except in compliance with the License.
+-   You may obtain a copy of the License at
+-
+-     http://www.apache.org/licenses/LICENSE-2.0
+-
+-   Unless required by applicable law or agreed to in writing, software
+-   distributed under the License is distributed on an "AS IS" BASIS,
+-   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-   See the License for the specific language governing permissions and
+-   limitations under the License.
+diff --git a/Godeps/_workspace/src/github.com/golang/glog/README b/Godeps/_workspace/src/github.com/golang/glog/README
+deleted file mode 100644
+index 5f9c114..0000000
+--- a/Godeps/_workspace/src/github.com/golang/glog/README
++++ /dev/null
+@@ -1,44 +0,0 @@
+-glog
+-====
+-
+-Leveled execution logs for Go.
+-
+-This is an efficient pure Go implementation of leveled logs in the
+-manner of the open source C++ package
+-	http://code.google.com/p/google-glog
+-
+-By binding methods to booleans it is possible to use the log package
+-without paying the expense of evaluating the arguments to the log.
+-Through the -vmodule flag, the package also provides fine-grained
+-control over logging at the file level.
+-
+-The comment from glog.go introduces the ideas:
+-
+-	Package glog implements logging analogous to the Google-internal
+-	C++ INFO/ERROR/V setup.  It provides functions Info, Warning,
+-	Error, Fatal, plus formatting variants such as Infof. It
+-	also provides V-style logging controlled by the -v and
+-	-vmodule=file=2 flags.
+-	
+-	Basic examples:
+-	
+-		glog.Info("Prepare to repel boarders")
+-	
+-		glog.Fatalf("Initialization failed: %s", err)
+-	
+-	See the documentation for the V function for an explanation
+-	of these examples:
+-	
+-		if glog.V(2) {
+-			glog.Info("Starting transaction...")
+-		}
+-	
+-		glog.V(2).Infoln("Processed", nItems, "elements")
+-
+-
+-The repository contains an open source version of the log package
+-used inside Google. The master copy of the source lives inside
+-Google, not here. The code in this repo is for export only and is not itself
+-under development. Feature requests will be ignored.
+-
+-Send bug reports to golang-nuts at googlegroups.com.
+diff --git a/Godeps/_workspace/src/github.com/golang/glog/glog.go b/Godeps/_workspace/src/github.com/golang/glog/glog.go
+deleted file mode 100644
+index 3e63fff..0000000
+--- a/Godeps/_workspace/src/github.com/golang/glog/glog.go
++++ /dev/null
+@@ -1,1177 +0,0 @@
+-// Go support for leveled logs, analogous to https://code.google.com/p/google-glog/
+-//
+-// Copyright 2013 Google Inc. All Rights Reserved.
+-//
+-// Licensed under the Apache License, Version 2.0 (the "License");
+-// you may not use this file except in compliance with the License.
+-// You may obtain a copy of the License at
+-//
+-//     http://www.apache.org/licenses/LICENSE-2.0
+-//
+-// Unless required by applicable law or agreed to in writing, software
+-// distributed under the License is distributed on an "AS IS" BASIS,
+-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-// See the License for the specific language governing permissions and
+-// limitations under the License.
+-
+-// Package glog implements logging analogous to the Google-internal C++ INFO/ERROR/V setup.
+-// It provides functions Info, Warning, Error, Fatal, plus formatting variants such as
+-// Infof. It also provides V-style logging controlled by the -v and -vmodule=file=2 flags.
+-//
+-// Basic examples:
+-//
+-//	glog.Info("Prepare to repel boarders")
+-//
+-//	glog.Fatalf("Initialization failed: %s", err)
+-//
+-// See the documentation for the V function for an explanation of these examples:
+-//
+-//	if glog.V(2) {
+-//		glog.Info("Starting transaction...")
+-//	}
+-//
+-//	glog.V(2).Infoln("Processed", nItems, "elements")
+-//
+-// Log output is buffered and written periodically using Flush. Programs
+-// should call Flush before exiting to guarantee all log output is written.
+-//
+-// By default, all log statements write to files in a temporary directory.
+-// This package provides several flags that modify this behavior.
+-// As a result, flag.Parse must be called before any logging is done.
+-//
+-//	-logtostderr=false
+-//		Logs are written to standard error instead of to files.
+-//	-alsologtostderr=false
+-//		Logs are written to standard error as well as to files.
+-//	-stderrthreshold=ERROR
+-//		Log events at or above this severity are logged to standard
+-//		error as well as to files.
+-//	-log_dir=""
+-//		Log files will be written to this directory instead of the
+-//		default temporary directory.
+-//
+-//	Other flags provide aids to debugging.
+-//
+-//	-log_backtrace_at=""
+-//		When set to a file and line number holding a logging statement,
+-//		such as
+-//			-log_backtrace_at=gopherflakes.go:234
+-//		a stack trace will be written to the Info log whenever execution
+-//		hits that statement. (Unlike with -vmodule, the ".go" must be
+-//		present.)
+-//	-v=0
+-//		Enable V-leveled logging at the specified level.
+-//	-vmodule=""
+-//		The syntax of the argument is a comma-separated list of pattern=N,
+-//		where pattern is a literal file name (minus the ".go" suffix) or
+-//		"glob" pattern and N is a V level. For instance,
+-//			-vmodule=gopher*=3
+-//		sets the V level to 3 in all Go files whose names begin "gopher".
+-//
+-package glog
+-
+-import (
+-	"bufio"
+-	"bytes"
+-	"errors"
+-	"flag"
+-	"fmt"
+-	"io"
+-	stdLog "log"
+-	"os"
+-	"path/filepath"
+-	"runtime"
+-	"strconv"
+-	"strings"
+-	"sync"
+-	"sync/atomic"
+-	"time"
+-)
+-
+-// severity identifies the sort of log: info, warning etc. It also implements
+-// the flag.Value interface. The -stderrthreshold flag is of type severity and
+-// should be modified only through the flag.Value interface. The values match
+-// the corresponding constants in C++.
+-type severity int32 // sync/atomic int32
+-
+-// These constants identify the log levels in order of increasing severity.
+-// A message written to a high-severity log file is also written to each
+-// lower-severity log file.
+-const (
+-	infoLog severity = iota
+-	warningLog
+-	errorLog
+-	fatalLog
+-	numSeverity = 4
+-)
+-
+-const severityChar = "IWEF"
+-
+-var severityName = []string{
+-	infoLog:    "INFO",
+-	warningLog: "WARNING",
+-	errorLog:   "ERROR",
+-	fatalLog:   "FATAL",
+-}
+-
+-// get returns the value of the severity.
+-func (s *severity) get() severity {
+-	return severity(atomic.LoadInt32((*int32)(s)))
+-}
+-
+-// set sets the value of the severity.
+-func (s *severity) set(val severity) {
+-	atomic.StoreInt32((*int32)(s), int32(val))
+-}
+-
+-// String is part of the flag.Value interface.
+-func (s *severity) String() string {
+-	return strconv.FormatInt(int64(*s), 10)
+-}
+-
+-// Get is part of the flag.Value interface.
+-func (s *severity) Get() interface{} {
+-	return *s
+-}
+-
+-// Set is part of the flag.Value interface.
+-func (s *severity) Set(value string) error {
+-	var threshold severity
+-	// Is it a known name?
+-	if v, ok := severityByName(value); ok {
+-		threshold = v
+-	} else {
+-		v, err := strconv.Atoi(value)
+-		if err != nil {
+-			return err
+-		}
+-		threshold = severity(v)
+-	}
+-	logging.stderrThreshold.set(threshold)
+-	return nil
+-}
+-
+-func severityByName(s string) (severity, bool) {
+-	s = strings.ToUpper(s)
+-	for i, name := range severityName {
+-		if name == s {
+-			return severity(i), true
+-		}
+-	}
+-	return 0, false
+-}
+-
+-// OutputStats tracks the number of output lines and bytes written.
+-type OutputStats struct {
+-	lines int64
+-	bytes int64
+-}
+-
+-// Lines returns the number of lines written.
+-func (s *OutputStats) Lines() int64 {
+-	return atomic.LoadInt64(&s.lines)
+-}
+-
+-// Bytes returns the number of bytes written.
+-func (s *OutputStats) Bytes() int64 {
+-	return atomic.LoadInt64(&s.bytes)
+-}
+-
+-// Stats tracks the number of lines of output and number of bytes
+-// per severity level. Values must be read with atomic.LoadInt64.
+-var Stats struct {
+-	Info, Warning, Error OutputStats
+-}
+-
+-var severityStats = [numSeverity]*OutputStats{
+-	infoLog:    &Stats.Info,
+-	warningLog: &Stats.Warning,
+-	errorLog:   &Stats.Error,
+-}
+-
+-// Level is exported because it appears in the arguments to V and is
+-// the type of the v flag, which can be set programmatically.
+-// It's a distinct type because we want to discriminate it from logType.
+-// Variables of type level are only changed under logging.mu.
+-// The -v flag is read only with atomic ops, so the state of the logging
+-// module is consistent.
+-
+-// Level is treated as a sync/atomic int32.
+-
+-// Level specifies a level of verbosity for V logs. *Level implements
+-// flag.Value; the -v flag is of type Level and should be modified
+-// only through the flag.Value interface.
+-type Level int32
+-
+-// get returns the value of the Level.
+-func (l *Level) get() Level {
+-	return Level(atomic.LoadInt32((*int32)(l)))
+-}
+-
+-// set sets the value of the Level.
+-func (l *Level) set(val Level) {
+-	atomic.StoreInt32((*int32)(l), int32(val))
+-}
+-
+-// String is part of the flag.Value interface.
+-func (l *Level) String() string {
+-	return strconv.FormatInt(int64(*l), 10)
+-}
+-
+-// Get is part of the flag.Value interface.
+-func (l *Level) Get() interface{} {
+-	return *l
+-}
+-
+-// Set is part of the flag.Value interface.
+-func (l *Level) Set(value string) error {
+-	v, err := strconv.Atoi(value)
+-	if err != nil {
+-		return err
+-	}
+-	logging.mu.Lock()
+-	defer logging.mu.Unlock()
+-	logging.setVState(Level(v), logging.vmodule.filter, false)
+-	return nil
+-}
+-
+-// moduleSpec represents the setting of the -vmodule flag.
+-type moduleSpec struct {
+-	filter []modulePat
+-}
+-
+-// modulePat contains a filter for the -vmodule flag.
+-// It holds a verbosity level and a file pattern to match.
+-type modulePat struct {
+-	pattern string
+-	literal bool // The pattern is a literal string
+-	level   Level
+-}
+-
+-// match reports whether the file matches the pattern. It uses a string
+-// comparison if the pattern contains no metacharacters.
+-func (m *modulePat) match(file string) bool {
+-	if m.literal {
+-		return file == m.pattern
+-	}
+-	match, _ := filepath.Match(m.pattern, file)
+-	return match
+-}
+-
+-func (m *moduleSpec) String() string {
+-	// Lock because the type is not atomic. TODO: clean this up.
+-	logging.mu.Lock()
+-	defer logging.mu.Unlock()
+-	var b bytes.Buffer
+-	for i, f := range m.filter {
+-		if i > 0 {
+-			b.WriteRune(',')
+-		}
+-		fmt.Fprintf(&b, "%s=%d", f.pattern, f.level)
+-	}
+-	return b.String()
+-}
+-
+-// Get is part of the (Go 1.2)  flag.Getter interface. It always returns nil for this flag type since the
+-// struct is not exported.
+-func (m *moduleSpec) Get() interface{} {
+-	return nil
+-}
+-
+-var errVmoduleSyntax = errors.New("syntax error: expect comma-separated list of filename=N")
+-
+-// Syntax: -vmodule=recordio=2,file=1,gfs*=3
+-func (m *moduleSpec) Set(value string) error {
+-	var filter []modulePat
+-	for _, pat := range strings.Split(value, ",") {
+-		if len(pat) == 0 {
+-			// Empty strings such as from a trailing comma can be ignored.
+-			continue
+-		}
+-		patLev := strings.Split(pat, "=")
+-		if len(patLev) != 2 || len(patLev[0]) == 0 || len(patLev[1]) == 0 {
+-			return errVmoduleSyntax
+-		}
+-		pattern := patLev[0]
+-		v, err := strconv.Atoi(patLev[1])
+-		if err != nil {
+-			return errors.New("syntax error: expect comma-separated list of filename=N")
+-		}
+-		if v < 0 {
+-			return errors.New("negative value for vmodule level")
+-		}
+-		if v == 0 {
+-			continue // Ignore. It's harmless but no point in paying the overhead.
+-		}
+-		// TODO: check syntax of filter?
+-		filter = append(filter, modulePat{pattern, isLiteral(pattern), Level(v)})
+-	}
+-	logging.mu.Lock()
+-	defer logging.mu.Unlock()
+-	logging.setVState(logging.verbosity, filter, true)
+-	return nil
+-}
+-
+-// isLiteral reports whether the pattern is a literal string, that is, has no metacharacters
+-// that require filepath.Match to be called to match the pattern.
+-func isLiteral(pattern string) bool {
+-	return !strings.ContainsAny(pattern, `\*?[]`)
+-}
+-
+-// traceLocation represents the setting of the -log_backtrace_at flag.
+-type traceLocation struct {
+-	file string
+-	line int
+-}
+-
+-// isSet reports whether the trace location has been specified.
+-// logging.mu is held.
+-func (t *traceLocation) isSet() bool {
+-	return t.line > 0
+-}
+-
+-// match reports whether the specified file and line matches the trace location.
+-// The argument file name is the full path, not the basename specified in the flag.
+-// logging.mu is held.
+-func (t *traceLocation) match(file string, line int) bool {
+-	if t.line != line {
+-		return false
+-	}
+-	if i := strings.LastIndex(file, "/"); i >= 0 {
+-		file = file[i+1:]
+-	}
+-	return t.file == file
+-}
+-
+-func (t *traceLocation) String() string {
+-	// Lock because the type is not atomic. TODO: clean this up.
+-	logging.mu.Lock()
+-	defer logging.mu.Unlock()
+-	return fmt.Sprintf("%s:%d", t.file, t.line)
+-}
+-
+-// Get is part of the (Go 1.2) flag.Getter interface. It always returns nil for this flag type since the
+-// struct is not exported
+-func (t *traceLocation) Get() interface{} {
+-	return nil
+-}
+-
+-var errTraceSyntax = errors.New("syntax error: expect file.go:234")
+-
+-// Syntax: -log_backtrace_at=gopherflakes.go:234
+-// Note that unlike vmodule the file extension is included here.
+-func (t *traceLocation) Set(value string) error {
+-	if value == "" {
+-		// Unset.
+-		t.line = 0
+-		t.file = ""
+-	}
+-	fields := strings.Split(value, ":")
+-	if len(fields) != 2 {
+-		return errTraceSyntax
+-	}
+-	file, line := fields[0], fields[1]
+-	if !strings.Contains(file, ".") {
+-		return errTraceSyntax
+-	}
+-	v, err := strconv.Atoi(line)
+-	if err != nil {
+-		return errTraceSyntax
+-	}
+-	if v <= 0 {
+-		return errors.New("negative or zero value for level")
+-	}
+-	logging.mu.Lock()
+-	defer logging.mu.Unlock()
+-	t.line = v
+-	t.file = file
+-	return nil
+-}
+-
+-// flushSyncWriter is the interface satisfied by logging destinations.
+-type flushSyncWriter interface {
+-	Flush() error
+-	Sync() error
+-	io.Writer
+-}
+-
+-func init() {
+-	flag.BoolVar(&logging.toStderr, "logtostderr", false, "log to standard error instead of files")
+-	flag.BoolVar(&logging.alsoToStderr, "alsologtostderr", false, "log to standard error as well as files")
+-	flag.Var(&logging.verbosity, "v", "log level for V logs")
+-	flag.Var(&logging.stderrThreshold, "stderrthreshold", "logs at or above this threshold go to stderr")
+-	flag.Var(&logging.vmodule, "vmodule", "comma-separated list of pattern=N settings for file-filtered logging")
+-	flag.Var(&logging.traceLocation, "log_backtrace_at", "when logging hits line file:N, emit a stack trace")
+-
+-	// Default stderrThreshold is ERROR.
+-	logging.stderrThreshold = errorLog
+-
+-	logging.setVState(0, nil, false)
+-	go logging.flushDaemon()
+-}
+-
+-// Flush flushes all pending log I/O.
+-func Flush() {
+-	logging.lockAndFlushAll()
+-}
+-
+-// loggingT collects all the global state of the logging setup.
+-type loggingT struct {
+-	// Boolean flags. Not handled atomically because the flag.Value interface
+-	// does not let us avoid the =true, and that shorthand is necessary for
+-	// compatibility. TODO: does this matter enough to fix? Seems unlikely.
+-	toStderr     bool // The -logtostderr flag.
+-	alsoToStderr bool // The -alsologtostderr flag.
+-
+-	// Level flag. Handled atomically.
+-	stderrThreshold severity // The -stderrthreshold flag.
+-
+-	// freeList is a list of byte buffers, maintained under freeListMu.
+-	freeList *buffer
+-	// freeListMu maintains the free list. It is separate from the main mutex
+-	// so buffers can be grabbed and printed to without holding the main lock,
+-	// for better parallelization.
+-	freeListMu sync.Mutex
+-
+-	// mu protects the remaining elements of this structure and is
+-	// used to synchronize logging.
+-	mu sync.Mutex
+-	// file holds writer for each of the log types.
+-	file [numSeverity]flushSyncWriter
+-	// pcs is used in V to avoid an allocation when computing the caller's PC.
+-	pcs [1]uintptr
+-	// vmap is a cache of the V Level for each V() call site, identified by PC.
+-	// It is wiped whenever the vmodule flag changes state.
+-	vmap map[uintptr]Level
+-	// filterLength stores the length of the vmodule filter chain. If greater
+-	// than zero, it means vmodule is enabled. It may be read safely
+-	// using sync.LoadInt32, but is only modified under mu.
+-	filterLength int32
+-	// traceLocation is the state of the -log_backtrace_at flag.
+-	traceLocation traceLocation
+-	// These flags are modified only under lock, although verbosity may be fetched
+-	// safely using atomic.LoadInt32.
+-	vmodule   moduleSpec // The state of the -vmodule flag.
+-	verbosity Level      // V logging level, the value of the -v flag/
+-}
+-
+-// buffer holds a byte Buffer for reuse. The zero value is ready for use.
+-type buffer struct {
+-	bytes.Buffer
+-	tmp  [64]byte // temporary byte array for creating headers.
+-	next *buffer
+-}
+-
+-var logging loggingT
+-
+-// setVState sets a consistent state for V logging.
+-// l.mu is held.
+-func (l *loggingT) setVState(verbosity Level, filter []modulePat, setFilter bool) {
+-	// Turn verbosity off so V will not fire while we are in transition.
+-	logging.verbosity.set(0)
+-	// Ditto for filter length.
+-	atomic.StoreInt32(&logging.filterLength, 0)
+-
+-	// Set the new filters and wipe the pc->Level map if the filter has changed.
+-	if setFilter {
+-		logging.vmodule.filter = filter
+-		logging.vmap = make(map[uintptr]Level)
+-	}
+-
+-	// Things are consistent now, so enable filtering and verbosity.
+-	// They are enabled in order opposite to that in V.
+-	atomic.StoreInt32(&logging.filterLength, int32(len(filter)))
+-	logging.verbosity.set(verbosity)
+-}
+-
+-// getBuffer returns a new, ready-to-use buffer.
+-func (l *loggingT) getBuffer() *buffer {
+-	l.freeListMu.Lock()
+-	b := l.freeList
+-	if b != nil {
+-		l.freeList = b.next
+-	}
+-	l.freeListMu.Unlock()
+-	if b == nil {
+-		b = new(buffer)
+-	} else {
+-		b.next = nil
+-		b.Reset()
+-	}
+-	return b
+-}
+-
+-// putBuffer returns a buffer to the free list.
+-func (l *loggingT) putBuffer(b *buffer) {
+-	if b.Len() >= 256 {
+-		// Let big buffers die a natural death.
+-		return
+-	}
+-	l.freeListMu.Lock()
+-	b.next = l.freeList
+-	l.freeList = b
+-	l.freeListMu.Unlock()
+-}
+-
+-var timeNow = time.Now // Stubbed out for testing.
+-
+-/*
+-header formats a log header as defined by the C++ implementation.
+-It returns a buffer containing the formatted header and the user's file and line number.
+-The depth specifies how many stack frames above lives the source line to be identified in the log message.
+-
+-Log lines have this form:
+-	Lmmdd hh:mm:ss.uuuuuu threadid file:line] msg...
+-where the fields are defined as follows:
+-	L                A single character, representing the log level (eg 'I' for INFO)
+-	mm               The month (zero padded; ie May is '05')
+-	dd               The day (zero padded)
+-	hh:mm:ss.uuuuuu  Time in hours, minutes and fractional seconds
+-	threadid         The space-padded thread ID as returned by GetTID()
+-	file             The file name
+-	line             The line number
+-	msg              The user-supplied message
+-*/
+-func (l *loggingT) header(s severity, depth int) (*buffer, string, int) {
+-	_, file, line, ok := runtime.Caller(3 + depth)
+-	if !ok {
+-		file = "???"
+-		line = 1
+-	} else {
+-		slash := strings.LastIndex(file, "/")
+-		if slash >= 0 {
+-			file = file[slash+1:]
+-		}
+-	}
+-	return l.formatHeader(s, file, line), file, line
+-}
+-
+-// formatHeader formats a log header using the provided file name and line number.
+-func (l *loggingT) formatHeader(s severity, file string, line int) *buffer {
+-	now := timeNow()
+-	if line < 0 {
+-		line = 0 // not a real line number, but acceptable to someDigits
+-	}
+-	if s > fatalLog {
+-		s = infoLog // for safety.
+-	}
+-	buf := l.getBuffer()
+-
+-	// Avoid Fprintf, for speed. The format is so simple that we can do it quickly by hand.
+-	// It's worth about 3X. Fprintf is hard.
+-	_, month, day := now.Date()
+-	hour, minute, second := now.Clock()
+-	// Lmmdd hh:mm:ss.uuuuuu threadid file:line]
+-	buf.tmp[0] = severityChar[s]
+-	buf.twoDigits(1, int(month))
+-	buf.twoDigits(3, day)
+-	buf.tmp[5] = ' '
+-	buf.twoDigits(6, hour)
+-	buf.tmp[8] = ':'
+-	buf.twoDigits(9, minute)
+-	buf.tmp[11] = ':'
+-	buf.twoDigits(12, second)
+-	buf.tmp[14] = '.'
+-	buf.nDigits(6, 15, now.Nanosecond()/1000, '0')
+-	buf.tmp[21] = ' '
+-	buf.nDigits(7, 22, pid, ' ') // TODO: should be TID
+-	buf.tmp[29] = ' '
+-	buf.Write(buf.tmp[:30])
+-	buf.WriteString(file)
+-	buf.tmp[0] = ':'
+-	n := buf.someDigits(1, line)
+-	buf.tmp[n+1] = ']'
+-	buf.tmp[n+2] = ' '
+-	buf.Write(buf.tmp[:n+3])
+-	return buf
+-}
+-
+-// Some custom tiny helper functions to print the log header efficiently.
+-
+-const digits = "0123456789"
+-
+-// twoDigits formats a zero-prefixed two-digit integer at buf.tmp[i].
+-func (buf *buffer) twoDigits(i, d int) {
+-	buf.tmp[i+1] = digits[d%10]
+-	d /= 10
+-	buf.tmp[i] = digits[d%10]
+-}
+-
+-// nDigits formats an n-digit integer at buf.tmp[i],
+-// padding with pad on the left.
+-// It assumes d >= 0.
+-func (buf *buffer) nDigits(n, i, d int, pad byte) {
+-	j := n - 1
+-	for ; j >= 0 && d > 0; j-- {
+-		buf.tmp[i+j] = digits[d%10]
+-		d /= 10
+-	}
+-	for ; j >= 0; j-- {
+-		buf.tmp[i+j] = pad
+-	}
+-}
+-
+-// someDigits formats a zero-prefixed variable-width integer at buf.tmp[i].
+-func (buf *buffer) someDigits(i, d int) int {
+-	// Print into the top, then copy down. We know there's space for at least
+-	// a 10-digit number.
+-	j := len(buf.tmp)
+-	for {
+-		j--
+-		buf.tmp[j] = digits[d%10]
+-		d /= 10
+-		if d == 0 {
+-			break
+-		}
+-	}
+-	return copy(buf.tmp[i:], buf.tmp[j:])
+-}
+-
+-func (l *loggingT) println(s severity, args ...interface{}) {
+-	buf, file, line := l.header(s, 0)
+-	fmt.Fprintln(buf, args...)
+-	l.output(s, buf, file, line, false)
+-}
+-
+-func (l *loggingT) print(s severity, args ...interface{}) {
+-	l.printDepth(s, 1, args...)
+-}
+-
+-func (l *loggingT) printDepth(s severity, depth int, args ...interface{}) {
+-	buf, file, line := l.header(s, depth)
+-	fmt.Fprint(buf, args...)
+-	if buf.Bytes()[buf.Len()-1] != '\n' {
+-		buf.WriteByte('\n')
+-	}
+-	l.output(s, buf, file, line, false)
+-}
+-
+-func (l *loggingT) printf(s severity, format string, args ...interface{}) {
+-	buf, file, line := l.header(s, 0)
+-	fmt.Fprintf(buf, format, args...)
+-	if buf.Bytes()[buf.Len()-1] != '\n' {
+-		buf.WriteByte('\n')
+-	}
+-	l.output(s, buf, file, line, false)
+-}
+-
+-// printWithFileLine behaves like print but uses the provided file and line number.  If
+-// alsoLogToStderr is true, the log message always appears on standard error; it
+-// will also appear in the log file unless --logtostderr is set.
+-func (l *loggingT) printWithFileLine(s severity, file string, line int, alsoToStderr bool, args ...interface{}) {
+-	buf := l.formatHeader(s, file, line)
+-	fmt.Fprint(buf, args...)
+-	if buf.Bytes()[buf.Len()-1] != '\n' {
+-		buf.WriteByte('\n')
+-	}
+-	l.output(s, buf, file, line, alsoToStderr)
+-}
+-
+-// output writes the data to the log files and releases the buffer.
+-func (l *loggingT) output(s severity, buf *buffer, file string, line int, alsoToStderr bool) {
+-	l.mu.Lock()
+-	if l.traceLocation.isSet() {
+-		if l.traceLocation.match(file, line) {
+-			buf.Write(stacks(false))
+-		}
+-	}
+-	data := buf.Bytes()
+-	if l.toStderr {
+-		os.Stderr.Write(data)
+-	} else {
+-		if alsoToStderr || l.alsoToStderr || s >= l.stderrThreshold.get() {
+-			os.Stderr.Write(data)
+-		}
+-		if l.file[s] == nil {
+-			if err := l.createFiles(s); err != nil {
+-				os.Stderr.Write(data) // Make sure the message appears somewhere.
+-				l.exit(err)
+-			}
+-		}
+-		switch s {
+-		case fatalLog:
+-			l.file[fatalLog].Write(data)
+-			fallthrough
+-		case errorLog:
+-			l.file[errorLog].Write(data)
+-			fallthrough
+-		case warningLog:
+-			l.file[warningLog].Write(data)
+-			fallthrough
+-		case infoLog:
+-			l.file[infoLog].Write(data)
+-		}
+-	}
+-	if s == fatalLog {
+-		// If we got here via Exit rather than Fatal, print no stacks.
+-		if atomic.LoadUint32(&fatalNoStacks) > 0 {
+-			l.mu.Unlock()
+-			timeoutFlush(10 * time.Second)
+-			os.Exit(1)
+-		}
+-		// Dump all goroutine stacks before exiting.
+-		// First, make sure we see the trace for the current goroutine on standard error.
+-		// If -logtostderr has been specified, the loop below will do that anyway
+-		// as the first stack in the full dump.
+-		if !l.toStderr {
+-			os.Stderr.Write(stacks(false))
+-		}
+-		// Write the stack trace for all goroutines to the files.
+-		trace := stacks(true)
+-		logExitFunc = func(error) {} // If we get a write error, we'll still exit below.
+-		for log := fatalLog; log >= infoLog; log-- {
+-			if f := l.file[log]; f != nil { // Can be nil if -logtostderr is set.
+-				f.Write(trace)
+-			}
+-		}
+-		l.mu.Unlock()
+-		timeoutFlush(10 * time.Second)
+-		os.Exit(255) // C++ uses -1, which is silly because it's anded with 255 anyway.
+-	}
+-	l.putBuffer(buf)
+-	l.mu.Unlock()
+-	if stats := severityStats[s]; stats != nil {
+-		atomic.AddInt64(&stats.lines, 1)
+-		atomic.AddInt64(&stats.bytes, int64(len(data)))
+-	}
+-}
+-
+-// timeoutFlush calls Flush and returns when it completes or after timeout
+-// elapses, whichever happens first.  This is needed because the hooks invoked
+-// by Flush may deadlock when glog.Fatal is called from a hook that holds
+-// a lock.
+-func timeoutFlush(timeout time.Duration) {
+-	done := make(chan bool, 1)
+-	go func() {
+-		Flush() // calls logging.lockAndFlushAll()
+-		done <- true
+-	}()
+-	select {
+-	case <-done:
+-	case <-time.After(timeout):
+-		fmt.Fprintln(os.Stderr, "glog: Flush took longer than", timeout)
+-	}
+-}
+-
+-// stacks is a wrapper for runtime.Stack that attempts to recover the data for all goroutines.
+-func stacks(all bool) []byte {
+-	// We don't know how big the traces are, so grow a few times if they don't fit. Start large, though.
+-	n := 10000
+-	if all {
+-		n = 100000
+-	}
+-	var trace []byte
+-	for i := 0; i < 5; i++ {
+-		trace = make([]byte, n)
+-		nbytes := runtime.Stack(trace, all)
+-		if nbytes < len(trace) {
+-			return trace[:nbytes]
+-		}
+-		n *= 2
+-	}
+-	return trace
+-}
+-
+-// logExitFunc provides a simple mechanism to override the default behavior
+-// of exiting on error. Used in testing and to guarantee we reach a required exit
+-// for fatal logs. Instead, exit could be a function rather than a method but that
+-// would make its use clumsier.
+-var logExitFunc func(error)
+-
+-// exit is called if there is trouble creating or writing log files.
+-// It flushes the logs and exits the program; there's no point in hanging around.
+-// l.mu is held.
+-func (l *loggingT) exit(err error) {
+-	fmt.Fprintf(os.Stderr, "log: exiting because of error: %s\n", err)
+-	// If logExitFunc is set, we do that instead of exiting.
+-	if logExitFunc != nil {
+-		logExitFunc(err)
+-		return
+-	}
+-	l.flushAll()
+-	os.Exit(2)
+-}
+-
+-// syncBuffer joins a bufio.Writer to its underlying file, providing access to the
+-// file's Sync method and providing a wrapper for the Write method that provides log
+-// file rotation. There are conflicting methods, so the file cannot be embedded.
+-// l.mu is held for all its methods.
+-type syncBuffer struct {
+-	logger *loggingT
+-	*bufio.Writer
+-	file   *os.File
+-	sev    severity
+-	nbytes uint64 // The number of bytes written to this file
+-}
+-
+-func (sb *syncBuffer) Sync() error {
+-	return sb.file.Sync()
+-}
+-
+-func (sb *syncBuffer) Write(p []byte) (n int, err error) {
+-	if sb.nbytes+uint64(len(p)) >= MaxSize {
+-		if err := sb.rotateFile(time.Now()); err != nil {
+-			sb.logger.exit(err)
+-		}
+-	}
+-	n, err = sb.Writer.Write(p)
+-	sb.nbytes += uint64(n)
+-	if err != nil {
+-		sb.logger.exit(err)
+-	}
+-	return
+-}
+-
+-// rotateFile closes the syncBuffer's file and starts a new one.
+-func (sb *syncBuffer) rotateFile(now time.Time) error {
+-	if sb.file != nil {
+-		sb.Flush()
+-		sb.file.Close()
+-	}
+-	var err error
+-	sb.file, _, err = create(severityName[sb.sev], now)
+-	sb.nbytes = 0
+-	if err != nil {
+-		return err
+-	}
+-
+-	sb.Writer = bufio.NewWriterSize(sb.file, bufferSize)
+-
+-	// Write header.
+-	var buf bytes.Buffer
+-	fmt.Fprintf(&buf, "Log file created at: %s\n", now.Format("2006/01/02 15:04:05"))
+-	fmt.Fprintf(&buf, "Running on machine: %s\n", host)
+-	fmt.Fprintf(&buf, "Binary: Built with %s %s for %s/%s\n", runtime.Compiler, runtime.Version(), runtime.GOOS, runtime.GOARCH)
+-	fmt.Fprintf(&buf, "Log line format: [IWEF]mmdd hh:mm:ss.uuuuuu threadid file:line] msg\n")
+-	n, err := sb.file.Write(buf.Bytes())
+-	sb.nbytes += uint64(n)
+-	return err
+-}
+-
+-// bufferSize sizes the buffer associated with each log file. It's large
+-// so that log records can accumulate without the logging thread blocking
+-// on disk I/O. The flushDaemon will block instead.
+-const bufferSize = 256 * 1024
+-
+-// createFiles creates all the log files for severity from sev down to infoLog.
+-// l.mu is held.
+-func (l *loggingT) createFiles(sev severity) error {
+-	now := time.Now()
+-	// Files are created in decreasing severity order, so as soon as we find one
+-	// has already been created, we can stop.
+-	for s := sev; s >= infoLog && l.file[s] == nil; s-- {
+-		sb := &syncBuffer{
+-			logger: l,
+-			sev:    s,
+-		}
+-		if err := sb.rotateFile(now); err != nil {
+-			return err
+-		}
+-		l.file[s] = sb
+-	}
+-	return nil
+-}
+-
+-const flushInterval = 30 * time.Second
+-
+-// flushDaemon periodically flushes the log file buffers.
+-func (l *loggingT) flushDaemon() {
+-	for _ = range time.NewTicker(flushInterval).C {
+-		l.lockAndFlushAll()
+-	}
+-}
+-
+-// lockAndFlushAll is like flushAll but locks l.mu first.
+-func (l *loggingT) lockAndFlushAll() {
+-	l.mu.Lock()
+-	l.flushAll()
+-	l.mu.Unlock()
+-}
+-
+-// flushAll flushes all the logs and attempts to "sync" their data to disk.
+-// l.mu is held.
+-func (l *loggingT) flushAll() {
+-	// Flush from fatal down, in case there's trouble flushing.
+-	for s := fatalLog; s >= infoLog; s-- {
+-		file := l.file[s]
+-		if file != nil {
+-			file.Flush() // ignore error
+-			file.Sync()  // ignore error
+-		}
+-	}
+-}
+-
+-// CopyStandardLogTo arranges for messages written to the Go "log" package's
+-// default logs to also appear in the Google logs for the named and lower
+-// severities.  Subsequent changes to the standard log's default output location
+-// or format may break this behavior.
+-//
+-// Valid names are "INFO", "WARNING", "ERROR", and "FATAL".  If the name is not
+-// recognized, CopyStandardLogTo panics.
+-func CopyStandardLogTo(name string) {
+-	sev, ok := severityByName(name)
+-	if !ok {
+-		panic(fmt.Sprintf("log.CopyStandardLogTo(%q): unrecognized severity name", name))
+-	}
+-	// Set a log format that captures the user's file and line:
+-	//   d.go:23: message
+-	stdLog.SetFlags(stdLog.Lshortfile)
+-	stdLog.SetOutput(logBridge(sev))
+-}
+-
+-// logBridge provides the Write method that enables CopyStandardLogTo to connect
+-// Go's standard logs to the logs provided by this package.
+-type logBridge severity
+-
+-// Write parses the standard logging line and passes its components to the
+-// logger for severity(lb).
+-func (lb logBridge) Write(b []byte) (n int, err error) {
+-	var (
+-		file = "???"
+-		line = 1
+-		text string
+-	)
+-	// Split "d.go:23: message" into "d.go", "23", and "message".
+-	if parts := bytes.SplitN(b, []byte{':'}, 3); len(parts) != 3 || len(parts[0]) < 1 || len(parts[2]) < 1 {
+-		text = fmt.Sprintf("bad log format: %s", b)
+-	} else {
+-		file = string(parts[0])
+-		text = string(parts[2][1:]) // skip leading space
+-		line, err = strconv.Atoi(string(parts[1]))
+-		if err != nil {
+-			text = fmt.Sprintf("bad line number: %s", b)
+-			line = 1
+-		}
+-	}
+-	// printWithFileLine with alsoToStderr=true, so standard log messages
+-	// always appear on standard error.
+-	logging.printWithFileLine(severity(lb), file, line, true, text)
+-	return len(b), nil
+-}
+-
+-// setV computes and remembers the V level for a given PC
+-// when vmodule is enabled.
+-// File pattern matching takes the basename of the file, stripped
+-// of its .go suffix, and uses filepath.Match, which is a little more
+-// general than the *? matching used in C++.
+-// l.mu is held.
+-func (l *loggingT) setV(pc uintptr) Level {
+-	fn := runtime.FuncForPC(pc)
+-	file, _ := fn.FileLine(pc)
+-	// The file is something like /a/b/c/d.go. We want just the d.
+-	if strings.HasSuffix(file, ".go") {
+-		file = file[:len(file)-3]
+-	}
+-	if slash := strings.LastIndex(file, "/"); slash >= 0 {
+-		file = file[slash+1:]
+-	}
+-	for _, filter := range l.vmodule.filter {
+-		if filter.match(file) {
+-			l.vmap[pc] = filter.level
+-			return filter.level
+-		}
+-	}
+-	l.vmap[pc] = 0
+-	return 0
+-}
+-
+-// Verbose is a boolean type that implements Infof (like Printf) etc.
+-// See the documentation of V for more information.
+-type Verbose bool
+-
+-// V reports whether verbosity at the call site is at least the requested level.
+-// The returned value is a boolean of type Verbose, which implements Info, Infoln
+-// and Infof. These methods will write to the Info log if called.
+-// Thus, one may write either
+-//	if glog.V(2) { glog.Info("log this") }
+-// or
+-//	glog.V(2).Info("log this")
+-// The second form is shorter but the first is cheaper if logging is off because it does
+-// not evaluate its arguments.
+-//
+-// Whether an individual call to V generates a log record depends on the setting of
+-// the -v and --vmodule flags; both are off by default. If the level in the call to
+-// V is at least the value of -v, or of -vmodule for the source file containing the
+-// call, the V call will log.
+-func V(level Level) Verbose {
+-	// This function tries hard to be cheap unless there's work to do.
+-	// The fast path is two atomic loads and compares.
+-
+-	// Here is a cheap but safe test to see if V logging is enabled globally.
+-	if logging.verbosity.get() >= level {
+-		return Verbose(true)
+-	}
+-
+-	// It's off globally but it vmodule may still be set.
+-	// Here is another cheap but safe test to see if vmodule is enabled.
+-	if atomic.LoadInt32(&logging.filterLength) > 0 {
+-		// Now we need a proper lock to use the logging structure. The pcs field
+-		// is shared so we must lock before accessing it. This is fairly expensive,
+-		// but if V logging is enabled we're slow anyway.
+-		logging.mu.Lock()
+-		defer logging.mu.Unlock()
+-		if runtime.Callers(2, logging.pcs[:]) == 0 {
+-			return Verbose(false)
+-		}
+-		v, ok := logging.vmap[logging.pcs[0]]
+-		if !ok {
+-			v = logging.setV(logging.pcs[0])
+-		}
+-		return Verbose(v >= level)
+-	}
+-	return Verbose(false)
+-}
+-
+-// Info is equivalent to the global Info function, guarded by the value of v.
+-// See the documentation of V for usage.
+-func (v Verbose) Info(args ...interface{}) {
+-	if v {
+-		logging.print(infoLog, args...)
+-	}
+-}
+-
+-// Infoln is equivalent to the global Infoln function, guarded by the value of v.
+-// See the documentation of V for usage.
+-func (v Verbose) Infoln(args ...interface{}) {
+-	if v {
+-		logging.println(infoLog, args...)
+-	}
+-}
+-
+-// Infof is equivalent to the global Infof function, guarded by the value of v.
+-// See the documentation of V for usage.
+-func (v Verbose) Infof(format string, args ...interface{}) {
+-	if v {
+-		logging.printf(infoLog, format, args...)
+-	}
+-}
+-
+-// Info logs to the INFO log.
+-// Arguments are handled in the manner of fmt.Print; a newline is appended if missing.
+-func Info(args ...interface{}) {
+-	logging.print(infoLog, args...)
+-}
+-
+-// InfoDepth acts as Info but uses depth to determine which call frame to log.
+-// InfoDepth(0, "msg") is the same as Info("msg").
+-func InfoDepth(depth int, args ...interface{}) {
+-	logging.printDepth(infoLog, depth, args...)
+-}
+-
+-// Infoln logs to the INFO log.
+-// Arguments are handled in the manner of fmt.Println; a newline is appended if missing.
+-func Infoln(args ...interface{}) {
+-	logging.println(infoLog, args...)
+-}
+-
+-// Infof logs to the INFO log.
+-// Arguments are handled in the manner of fmt.Printf; a newline is appended if missing.
+-func Infof(format string, args ...interface{}) {
+-	logging.printf(infoLog, format, args...)
+-}
+-
+-// Warning logs to the WARNING and INFO logs.
+-// Arguments are handled in the manner of fmt.Print; a newline is appended if missing.
+-func Warning(args ...interface{}) {
+-	logging.print(warningLog, args...)
+-}
+-
+-// WarningDepth acts as Warning but uses depth to determine which call frame to log.
+-// WarningDepth(0, "msg") is the same as Warning("msg").
+-func WarningDepth(depth int, args ...interface{}) {
+-	logging.printDepth(warningLog, depth, args...)
+-}
+-
+-// Warningln logs to the WARNING and INFO logs.
+-// Arguments are handled in the manner of fmt.Println; a newline is appended if missing.
+-func Warningln(args ...interface{}) {
+-	logging.println(warningLog, args...)
+-}
+-
+-// Warningf logs to the WARNING and INFO logs.
+-// Arguments are handled in the manner of fmt.Printf; a newline is appended if missing.
+-func Warningf(format string, args ...interface{}) {
+-	logging.printf(warningLog, format, args...)
+-}
+-
+-// Error logs to the ERROR, WARNING, and INFO logs.
+-// Arguments are handled in the manner of fmt.Print; a newline is appended if missing.
+-func Error(args ...interface{}) {
+-	logging.print(errorLog, args...)
+-}
+-
+-// ErrorDepth acts as Error but uses depth to determine which call frame to log.
+-// ErrorDepth(0, "msg") is the same as Error("msg").
+-func ErrorDepth(depth int, args ...interface{}) {
+-	logging.printDepth(errorLog, depth, args...)
+-}
+-
+-// Errorln logs to the ERROR, WARNING, and INFO logs.
+-// Arguments are handled in the manner of fmt.Println; a newline is appended if missing.
+-func Errorln(args ...interface{}) {
+-	logging.println(errorLog, args...)
+-}
+-
+-// Errorf logs to the ERROR, WARNING, and INFO logs.
+-// Arguments are handled in the manner of fmt.Printf; a newline is appended if missing.
+-func Errorf(format string, args ...interface{}) {
+-	logging.printf(errorLog, format, args...)
+-}
+-
+-// Fatal logs to the FATAL, ERROR, WARNING, and INFO logs,
+-// including a stack trace of all running goroutines, then calls os.Exit(255).
+-// Arguments are handled in the manner of fmt.Print; a newline is appended if missing.
+-func Fatal(args ...interface{}) {
+-	logging.print(fatalLog, args...)
+-}
+-
+-// FatalDepth acts as Fatal but uses depth to determine which call frame to log.
+-// FatalDepth(0, "msg") is the same as Fatal("msg").
+-func FatalDepth(depth int, args ...interface{}) {
+-	logging.printDepth(fatalLog, depth, args...)
+-}
+-
+-// Fatalln logs to the FATAL, ERROR, WARNING, and INFO logs,
+-// including a stack trace of all running goroutines, then calls os.Exit(255).
+-// Arguments are handled in the manner of fmt.Println; a newline is appended if missing.
+-func Fatalln(args ...interface{}) {
+-	logging.println(fatalLog, args...)
+-}
+-
+-// Fatalf logs to the FATAL, ERROR, WARNING, and INFO logs,
+-// including a stack trace of all running goroutines, then calls os.Exit(255).
+-// Arguments are handled in the manner of fmt.Printf; a newline is appended if missing.
+-func Fatalf(format string, args ...interface{}) {
+-	logging.printf(fatalLog, format, args...)
+-}
+-
+-// fatalNoStacks is non-zero if we are to exit without dumping goroutine stacks.
+-// It allows Exit and relatives to use the Fatal logs.
+-var fatalNoStacks uint32
+-
+-// Exit logs to the FATAL, ERROR, WARNING, and INFO logs, then calls os.Exit(1).
+-// Arguments are handled in the manner of fmt.Print; a newline is appended if missing.
+-func Exit(args ...interface{}) {
+-	atomic.StoreUint32(&fatalNoStacks, 1)
+-	logging.print(fatalLog, args...)
+-}
+-
+-// ExitDepth acts as Exit but uses depth to determine which call frame to log.
+-// ExitDepth(0, "msg") is the same as Exit("msg").
+-func ExitDepth(depth int, args ...interface{}) {
+-	atomic.StoreUint32(&fatalNoStacks, 1)
+-	logging.printDepth(fatalLog, depth, args...)
+-}
+-
+-// Exitln logs to the FATAL, ERROR, WARNING, and INFO logs, then calls os.Exit(1).
+-func Exitln(args ...interface{}) {
+-	atomic.StoreUint32(&fatalNoStacks, 1)
+-	logging.println(fatalLog, args...)
+-}
+-
+-// Exitf logs to the FATAL, ERROR, WARNING, and INFO logs, then calls os.Exit(1).
+-// Arguments are handled in the manner of fmt.Printf; a newline is appended if missing.
+-func Exitf(format string, args ...interface{}) {
+-	atomic.StoreUint32(&fatalNoStacks, 1)
+-	logging.printf(fatalLog, format, args...)
+-}
+diff --git a/Godeps/_workspace/src/github.com/golang/glog/glog_file.go b/Godeps/_workspace/src/github.com/golang/glog/glog_file.go
+deleted file mode 100644
+index 65075d2..0000000
+--- a/Godeps/_workspace/src/github.com/golang/glog/glog_file.go
++++ /dev/null
+@@ -1,124 +0,0 @@
+-// Go support for leveled logs, analogous to https://code.google.com/p/google-glog/
+-//
+-// Copyright 2013 Google Inc. All Rights Reserved.
+-//
+-// Licensed under the Apache License, Version 2.0 (the "License");
+-// you may not use this file except in compliance with the License.
+-// You may obtain a copy of the License at
+-//
+-//     http://www.apache.org/licenses/LICENSE-2.0
+-//
+-// Unless required by applicable law or agreed to in writing, software
+-// distributed under the License is distributed on an "AS IS" BASIS,
+-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-// See the License for the specific language governing permissions and
+-// limitations under the License.
+-
+-// File I/O for logs.
+-
+-package glog
+-
+-import (
+-	"errors"
+-	"flag"
+-	"fmt"
+-	"os"
+-	"os/user"
+-	"path/filepath"
+-	"strings"
+-	"sync"
+-	"time"
+-)
+-
+-// MaxSize is the maximum size of a log file in bytes.
+-var MaxSize uint64 = 1024 * 1024 * 1800
+-
+-// logDirs lists the candidate directories for new log files.
+-var logDirs []string
+-
+-// If non-empty, overrides the choice of directory in which to write logs.
+-// See createLogDirs for the full list of possible destinations.
+-var logDir = flag.String("log_dir", "", "If non-empty, write log files in this directory")
+-
+-func createLogDirs() {
+-	if *logDir != "" {
+-		logDirs = append(logDirs, *logDir)
+-	}
+-	logDirs = append(logDirs, os.TempDir())
+-}
+-
+-var (
+-	pid      = os.Getpid()
+-	program  = filepath.Base(os.Args[0])
+-	host     = "unknownhost"
+-	userName = "unknownuser"
+-)
+-
+-func init() {
+-	h, err := os.Hostname()
+-	if err == nil {
+-		host = shortHostname(h)
+-	}
+-
+-	current, err := user.Current()
+-	if err == nil {
+-		userName = current.Username
+-	}
+-
+-	// Sanitize userName since it may contain filepath separators on Windows.
+-	userName = strings.Replace(userName, `\`, "_", -1)
+-}
+-
+-// shortHostname returns its argument, truncating at the first period.
+-// For instance, given "www.google.com" it returns "www".
+-func shortHostname(hostname string) string {
+-	if i := strings.Index(hostname, "."); i >= 0 {
+-		return hostname[:i]
+-	}
+-	return hostname
+-}
+-
+-// logName returns a new log file name containing tag, with start time t, and
+-// the name for the symlink for tag.
+-func logName(tag string, t time.Time) (name, link string) {
+-	name = fmt.Sprintf("%s.%s.%s.log.%s.%04d%02d%02d-%02d%02d%02d.%d",
+-		program,
+-		host,
+-		userName,
+-		tag,
+-		t.Year(),
+-		t.Month(),
+-		t.Day(),
+-		t.Hour(),
+-		t.Minute(),
+-		t.Second(),
+-		pid)
+-	return name, program + "." + tag
+-}
+-
+-var onceLogDirs sync.Once
+-
+-// create creates a new log file and returns the file and its filename, which
+-// contains tag ("INFO", "FATAL", etc.) and t.  If the file is created
+-// successfully, create also attempts to update the symlink for that tag, ignoring
+-// errors.
+-func create(tag string, t time.Time) (f *os.File, filename string, err error) {
+-	onceLogDirs.Do(createLogDirs)
+-	if len(logDirs) == 0 {
+-		return nil, "", errors.New("log: no log dirs")
+-	}
+-	name, link := logName(tag, t)
+-	var lastErr error
+-	for _, dir := range logDirs {
+-		fname := filepath.Join(dir, name)
+-		f, err := os.Create(fname)
+-		if err == nil {
+-			symlink := filepath.Join(dir, link)
+-			os.Remove(symlink)        // ignore err
+-			os.Symlink(name, symlink) // ignore err
+-			return f, fname, nil
+-		}
+-		lastErr = err
+-	}
+-	return nil, "", fmt.Errorf("log: cannot create log: %v", lastErr)
+-}
+diff --git a/Godeps/_workspace/src/github.com/golang/glog/glog_test.go b/Godeps/_workspace/src/github.com/golang/glog/glog_test.go
+deleted file mode 100644
+index 0fb376e..0000000
+--- a/Godeps/_workspace/src/github.com/golang/glog/glog_test.go
++++ /dev/null
+@@ -1,415 +0,0 @@
+-// Go support for leveled logs, analogous to https://code.google.com/p/google-glog/
+-//
+-// Copyright 2013 Google Inc. All Rights Reserved.
+-//
+-// Licensed under the Apache License, Version 2.0 (the "License");
+-// you may not use this file except in compliance with the License.
+-// You may obtain a copy of the License at
+-//
+-//     http://www.apache.org/licenses/LICENSE-2.0
+-//
+-// Unless required by applicable law or agreed to in writing, software
+-// distributed under the License is distributed on an "AS IS" BASIS,
+-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-// See the License for the specific language governing permissions and
+-// limitations under the License.
+-
+-package glog
+-
+-import (
+-	"bytes"
+-	"fmt"
+-	stdLog "log"
+-	"path/filepath"
+-	"runtime"
+-	"strconv"
+-	"strings"
+-	"testing"
+-	"time"
+-)
+-
+-// Test that shortHostname works as advertised.
+-func TestShortHostname(t *testing.T) {
+-	for hostname, expect := range map[string]string{
+-		"":                "",
+-		"host":            "host",
+-		"host.google.com": "host",
+-	} {
+-		if got := shortHostname(hostname); expect != got {
+-			t.Errorf("shortHostname(%q): expected %q, got %q", hostname, expect, got)
+-		}
+-	}
+-}
+-
+-// flushBuffer wraps a bytes.Buffer to satisfy flushSyncWriter.
+-type flushBuffer struct {
+-	bytes.Buffer
+-}
+-
+-func (f *flushBuffer) Flush() error {
+-	return nil
+-}
+-
+-func (f *flushBuffer) Sync() error {
+-	return nil
+-}
+-
+-// swap sets the log writers and returns the old array.
+-func (l *loggingT) swap(writers [numSeverity]flushSyncWriter) (old [numSeverity]flushSyncWriter) {
+-	l.mu.Lock()
+-	defer l.mu.Unlock()
+-	old = l.file
+-	for i, w := range writers {
+-		logging.file[i] = w
+-	}
+-	return
+-}
+-
+-// newBuffers sets the log writers to all new byte buffers and returns the old array.
+-func (l *loggingT) newBuffers() [numSeverity]flushSyncWriter {
+-	return l.swap([numSeverity]flushSyncWriter{new(flushBuffer), new(flushBuffer), new(flushBuffer), new(flushBuffer)})
+-}
+-
+-// contents returns the specified log value as a string.
+-func contents(s severity) string {
+-	return logging.file[s].(*flushBuffer).String()
+-}
+-
+-// contains reports whether the string is contained in the log.
+-func contains(s severity, str string, t *testing.T) bool {
+-	return strings.Contains(contents(s), str)
+-}
+-
+-// setFlags configures the logging flags how the test expects them.
+-func setFlags() {
+-	logging.toStderr = false
+-}
+-
+-// Test that Info works as advertised.
+-func TestInfo(t *testing.T) {
+-	setFlags()
+-	defer logging.swap(logging.newBuffers())
+-	Info("test")
+-	if !contains(infoLog, "I", t) {
+-		t.Errorf("Info has wrong character: %q", contents(infoLog))
+-	}
+-	if !contains(infoLog, "test", t) {
+-		t.Error("Info failed")
+-	}
+-}
+-
+-func TestInfoDepth(t *testing.T) {
+-	setFlags()
+-	defer logging.swap(logging.newBuffers())
+-
+-	f := func() { InfoDepth(1, "depth-test1") }
+-
+-	// The next three lines must stay together
+-	_, _, wantLine, _ := runtime.Caller(0)
+-	InfoDepth(0, "depth-test0")
+-	f()
+-
+-	msgs := strings.Split(strings.TrimSuffix(contents(infoLog), "\n"), "\n")
+-	if len(msgs) != 2 {
+-		t.Fatalf("Got %d lines, expected 2", len(msgs))
+-	}
+-
+-	for i, m := range msgs {
+-		if !strings.HasPrefix(m, "I") {
+-			t.Errorf("InfoDepth[%d] has wrong character: %q", i, m)
+-		}
+-		w := fmt.Sprintf("depth-test%d", i)
+-		if !strings.Contains(m, w) {
+-			t.Errorf("InfoDepth[%d] missing %q: %q", i, w, m)
+-		}
+-
+-		// pull out the line number (between : and ])
+-		msg := m[strings.LastIndex(m, ":")+1:]
+-		x := strings.Index(msg, "]")
+-		if x < 0 {
+-			t.Errorf("InfoDepth[%d]: missing ']': %q", i, m)
+-			continue
+-		}
+-		line, err := strconv.Atoi(msg[:x])
+-		if err != nil {
+-			t.Errorf("InfoDepth[%d]: bad line number: %q", i, m)
+-			continue
+-		}
+-		wantLine++
+-		if wantLine != line {
+-			t.Errorf("InfoDepth[%d]: got line %d, want %d", i, line, wantLine)
+-		}
+-	}
+-}
+-
+-func init() {
+-	CopyStandardLogTo("INFO")
+-}
+-
+-// Test that CopyStandardLogTo panics on bad input.
+-func TestCopyStandardLogToPanic(t *testing.T) {
+-	defer func() {
+-		if s, ok := recover().(string); !ok || !strings.Contains(s, "LOG") {
+-			t.Errorf(`CopyStandardLogTo("LOG") should have panicked: %v`, s)
+-		}
+-	}()
+-	CopyStandardLogTo("LOG")
+-}
+-
+-// Test that using the standard log package logs to INFO.
+-func TestStandardLog(t *testing.T) {
+-	setFlags()
+-	defer logging.swap(logging.newBuffers())
+-	stdLog.Print("test")
+-	if !contains(infoLog, "I", t) {
+-		t.Errorf("Info has wrong character: %q", contents(infoLog))
+-	}
+-	if !contains(infoLog, "test", t) {
+-		t.Error("Info failed")
+-	}
+-}
+-
+-// Test that the header has the correct format.
+-func TestHeader(t *testing.T) {
+-	setFlags()
+-	defer logging.swap(logging.newBuffers())
+-	defer func(previous func() time.Time) { timeNow = previous }(timeNow)
+-	timeNow = func() time.Time {
+-		return time.Date(2006, 1, 2, 15, 4, 5, .067890e9, time.Local)
+-	}
+-	pid = 1234
+-	Info("test")
+-	var line int
+-	format := "I0102 15:04:05.067890    1234 glog_test.go:%d] test\n"
+-	n, err := fmt.Sscanf(contents(infoLog), format, &line)
+-	if n != 1 || err != nil {
+-		t.Errorf("log format error: %d elements, error %s:\n%s", n, err, contents(infoLog))
+-	}
+-	// Scanf treats multiple spaces as equivalent to a single space,
+-	// so check for correct space-padding also.
+-	want := fmt.Sprintf(format, line)
+-	if contents(infoLog) != want {
+-		t.Errorf("log format error: got:\n\t%q\nwant:\t%q", contents(infoLog), want)
+-	}
+-}
+-
+-// Test that an Error log goes to Warning and Info.
+-// Even in the Info log, the source character will be E, so the data should
+-// all be identical.
+-func TestError(t *testing.T) {
+-	setFlags()
+-	defer logging.swap(logging.newBuffers())
+-	Error("test")
+-	if !contains(errorLog, "E", t) {
+-		t.Errorf("Error has wrong character: %q", contents(errorLog))
+-	}
+-	if !contains(errorLog, "test", t) {
+-		t.Error("Error failed")
+-	}
+-	str := contents(errorLog)
+-	if !contains(warningLog, str, t) {
+-		t.Error("Warning failed")
+-	}
+-	if !contains(infoLog, str, t) {
+-		t.Error("Info failed")
+-	}
+-}
+-
+-// Test that a Warning log goes to Info.
+-// Even in the Info log, the source character will be W, so the data should
+-// all be identical.
+-func TestWarning(t *testing.T) {
+-	setFlags()
+-	defer logging.swap(logging.newBuffers())
+-	Warning("test")
+-	if !contains(warningLog, "W", t) {
+-		t.Errorf("Warning has wrong character: %q", contents(warningLog))
+-	}
+-	if !contains(warningLog, "test", t) {
+-		t.Error("Warning failed")
+-	}
+-	str := contents(warningLog)
+-	if !contains(infoLog, str, t) {
+-		t.Error("Info failed")
+-	}
+-}
+-
+-// Test that a V log goes to Info.
+-func TestV(t *testing.T) {
+-	setFlags()
+-	defer logging.swap(logging.newBuffers())
+-	logging.verbosity.Set("2")
+-	defer logging.verbosity.Set("0")
+-	V(2).Info("test")
+-	if !contains(infoLog, "I", t) {
+-		t.Errorf("Info has wrong character: %q", contents(infoLog))
+-	}
+-	if !contains(infoLog, "test", t) {
+-		t.Error("Info failed")
+-	}
+-}
+-
+-// Test that a vmodule enables a log in this file.
+-func TestVmoduleOn(t *testing.T) {
+-	setFlags()
+-	defer logging.swap(logging.newBuffers())
+-	logging.vmodule.Set("glog_test=2")
+-	defer logging.vmodule.Set("")
+-	if !V(1) {
+-		t.Error("V not enabled for 1")
+-	}
+-	if !V(2) {
+-		t.Error("V not enabled for 2")
+-	}
+-	if V(3) {
+-		t.Error("V enabled for 3")
+-	}
+-	V(2).Info("test")
+-	if !contains(infoLog, "I", t) {
+-		t.Errorf("Info has wrong character: %q", contents(infoLog))
+-	}
+-	if !contains(infoLog, "test", t) {
+-		t.Error("Info failed")
+-	}
+-}
+-
+-// Test that a vmodule of another file does not enable a log in this file.
+-func TestVmoduleOff(t *testing.T) {
+-	setFlags()
+-	defer logging.swap(logging.newBuffers())
+-	logging.vmodule.Set("notthisfile=2")
+-	defer logging.vmodule.Set("")
+-	for i := 1; i <= 3; i++ {
+-		if V(Level(i)) {
+-			t.Errorf("V enabled for %d", i)
+-		}
+-	}
+-	V(2).Info("test")
+-	if contents(infoLog) != "" {
+-		t.Error("V logged incorrectly")
+-	}
+-}
+-
+-// vGlobs are patterns that match/don't match this file at V=2.
+-var vGlobs = map[string]bool{
+-	// Easy to test the numeric match here.
+-	"glog_test=1": false, // If -vmodule sets V to 1, V(2) will fail.
+-	"glog_test=2": true,
+-	"glog_test=3": true, // If -vmodule sets V to 1, V(3) will succeed.
+-	// These all use 2 and check the patterns. All are true.
+-	"*=2":           true,
+-	"?l*=2":         true,
+-	"????_*=2":      true,
+-	"??[mno]?_*t=2": true,
+-	// These all use 2 and check the patterns. All are false.
+-	"*x=2":         false,
+-	"m*=2":         false,
+-	"??_*=2":       false,
+-	"?[abc]?_*t=2": false,
+-}
+-
+-// Test that vmodule globbing works as advertised.
+-func testVmoduleGlob(pat string, match bool, t *testing.T) {
+-	setFlags()
+-	defer logging.swap(logging.newBuffers())
+-	defer logging.vmodule.Set("")
+-	logging.vmodule.Set(pat)
+-	if V(2) != Verbose(match) {
+-		t.Errorf("incorrect match for %q: got %t expected %t", pat, V(2), match)
+-	}
+-}
+-
+-// Test that a vmodule globbing works as advertised.
+-func TestVmoduleGlob(t *testing.T) {
+-	for glob, match := range vGlobs {
+-		testVmoduleGlob(glob, match, t)
+-	}
+-}
+-
+-func TestRollover(t *testing.T) {
+-	setFlags()
+-	var err error
+-	defer func(previous func(error)) { logExitFunc = previous }(logExitFunc)
+-	logExitFunc = func(e error) {
+-		err = e
+-	}
+-	defer func(previous uint64) { MaxSize = previous }(MaxSize)
+-	MaxSize = 512
+-
+-	Info("x") // Be sure we have a file.
+-	info, ok := logging.file[infoLog].(*syncBuffer)
+-	if !ok {
+-		t.Fatal("info wasn't created")
+-	}
+-	if err != nil {
+-		t.Fatalf("info has initial error: %v", err)
+-	}
+-	fname0 := info.file.Name()
+-	Info(strings.Repeat("x", int(MaxSize))) // force a rollover
+-	if err != nil {
+-		t.Fatalf("info has error after big write: %v", err)
+-	}
+-
+-	// Make sure the next log file gets a file name with a different
+-	// time stamp.
+-	//
+-	// TODO: determine whether we need to support subsecond log
+-	// rotation.  C++ does not appear to handle this case (nor does it
+-	// handle Daylight Savings Time properly).
+-	time.Sleep(1 * time.Second)
+-
+-	Info("x") // create a new file
+-	if err != nil {
+-		t.Fatalf("error after rotation: %v", err)
+-	}
+-	fname1 := info.file.Name()
+-	if fname0 == fname1 {
+-		t.Errorf("info.f.Name did not change: %v", fname0)
+-	}
+-	if info.nbytes >= MaxSize {
+-		t.Errorf("file size was not reset: %d", info.nbytes)
+-	}
+-}
+-
+-func TestLogBacktraceAt(t *testing.T) {
+-	setFlags()
+-	defer logging.swap(logging.newBuffers())
+-	// The peculiar style of this code simplifies line counting and maintenance of the
+-	// tracing block below.
+-	var infoLine string
+-	setTraceLocation := func(file string, line int, ok bool, delta int) {
+-		if !ok {
+-			t.Fatal("could not get file:line")
+-		}
+-		_, file = filepath.Split(file)
+-		infoLine = fmt.Sprintf("%s:%d", file, line+delta)
+-		err := logging.traceLocation.Set(infoLine)
+-		if err != nil {
+-			t.Fatal("error setting log_backtrace_at: ", err)
+-		}
+-	}
+-	{
+-		// Start of tracing block. These lines know about each other's relative position.
+-		_, file, line, ok := runtime.Caller(0)
+-		setTraceLocation(file, line, ok, +2) // Two lines between Caller and Info calls.
+-		Info("we want a stack trace here")
+-	}
+-	numAppearances := strings.Count(contents(infoLog), infoLine)
+-	if numAppearances < 2 {
+-		// Need 2 appearances, one in the log header and one in the trace:
+-		//   log_test.go:281: I0511 16:36:06.952398 02238 log_test.go:280] we want a stack trace here
+-		//   ...
+-		//   github.com/glog/glog_test.go:280 (0x41ba91)
+-		//   ...
+-		// We could be more precise but that would require knowing the details
+-		// of the traceback format, which may not be dependable.
+-		t.Fatal("got no trace back; log is ", contents(infoLog))
+-	}
+-}
+-
+-func BenchmarkHeader(b *testing.B) {
+-	for i := 0; i < b.N; i++ {
+-		buf, _, _ := logging.header(infoLog, 0)
+-		logging.putBuffer(buf)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/google/cadvisor/client/README.md b/Godeps/_workspace/src/github.com/google/cadvisor/client/README.md
+deleted file mode 100644
+index fededef..0000000
+--- a/Godeps/_workspace/src/github.com/google/cadvisor/client/README.md
++++ /dev/null
+@@ -1,54 +0,0 @@
+-# Example REST API Client
+-
+-This is an implementation of a cAdvisor REST API in Go.  You can use it like this:
+-
+-```go
+-client, err := client.NewClient("http://192.168.59.103:8080/")
+-```
+-
+-Obviously, replace the URL with the path to your actual cAdvisor REST endpoint.
+-
+-
+-### MachineInfo
+-
+-```go
+-client.MachineInfo()
+-```
+-
+-This method returns a cadvisor/info.MachineInfo struct with all the fields filled in.  Here is an example return value:
+-
+-```
+-(*info.MachineInfo)(0xc208022b10)({
+- NumCores: (int) 4,
+- MemoryCapacity: (int64) 2106028032,
+- Filesystems: ([]info.FsInfo) (len=1 cap=4) {
+-  (info.FsInfo) {
+-   Device: (string) (len=9) "/dev/sda1",
+-   Capacity: (uint64) 19507089408
+-  }
+- }
+-})
+-```
+-
+-You can see the full specification of the [MachineInfo struct in the source](../info/container.go)
+-
+-### ContainerInfo
+-
+-Given a container name and a ContainerInfoRequest, will return all information about the specified container.  The ContainerInfoRequest struct just has one field, NumStats, which is the number of stat entries that you want returned.
+-
+-```go
+-request := info.ContainerInfoRequest{10}
+-sInfo, err := client.ContainerInfo("/docker/d9d3eb10179e6f93a...", &request)
+-```
+-Returns a [ContainerInfo struct](../info/container.go)
+-
+-### SubcontainersInfo
+-
+-Given a container name and a ContainerInfoRequest, will recursively return all info about the container and all subcontainers contained within the container.  The ContainerInfoRequest struct just has one field, NumStats, which is the number of stat entries that you want returned.
+-
+-```go
+-request := info.ContainerInfoRequest{10}
+-sInfo, err := client.SubcontainersInfo("/docker", &request)
+-```
+-
+-Returns a [ContainerInfo struct](../info/container.go) with the Subcontainers field populated.
+diff --git a/Godeps/_workspace/src/github.com/google/cadvisor/client/client.go b/Godeps/_workspace/src/github.com/google/cadvisor/client/client.go
+deleted file mode 100644
+index 5c016e0..0000000
+--- a/Godeps/_workspace/src/github.com/google/cadvisor/client/client.go
++++ /dev/null
+@@ -1,161 +0,0 @@
+-// Copyright 2014 Google Inc. All Rights Reserved.
+-//
+-// Licensed under the Apache License, Version 2.0 (the "License");
+-// you may not use this file except in compliance with the License.
+-// You may obtain a copy of the License at
+-//
+-//     http://www.apache.org/licenses/LICENSE-2.0
+-//
+-// Unless required by applicable law or agreed to in writing, software
+-// distributed under the License is distributed on an "AS IS" BASIS,
+-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-// See the License for the specific language governing permissions and
+-// limitations under the License.
+-
+-// TODO(cAdvisor): Package comment.
+-package client
+-
+-import (
+-	"bytes"
+-	"encoding/json"
+-	"fmt"
+-	"io/ioutil"
+-	"net/http"
+-	"path"
+-	"strings"
+-
+-	"github.com/google/cadvisor/info"
+-)
+-
+-// Client represents the base URL for a cAdvisor client.
+-type Client struct {
+-	baseUrl string
+-}
+-
+-// NewClient returns a new client with the specified base URL.
+-func NewClient(url string) (*Client, error) {
+-	if !strings.HasSuffix(url, "/") {
+-		url += "/"
+-	}
+-
+-	return &Client{
+-		baseUrl: fmt.Sprintf("%sapi/v1.2/", url),
+-	}, nil
+-}
+-
+-// MachineInfo returns the JSON machine information for this client.
+-// A non-nil error result indicates a problem with obtaining
+-// the JSON machine information data.
+-func (self *Client) MachineInfo() (minfo *info.MachineInfo, err error) {
+-	u := self.machineInfoUrl()
+-	ret := new(info.MachineInfo)
+-	if err = self.httpGetJsonData(ret, nil, u, "machine info"); err != nil {
+-		return
+-	}
+-	minfo = ret
+-	return
+-}
+-
+-// ContainerInfo returns the JSON container information for the specified
+-// container and request.
+-func (self *Client) ContainerInfo(name string, query *info.ContainerInfoRequest) (cinfo *info.ContainerInfo, err error) {
+-	u := self.containerInfoUrl(name)
+-	ret := new(info.ContainerInfo)
+-	if err = self.httpGetJsonData(ret, query, u, fmt.Sprintf("container info for %q", name)); err != nil {
+-		return
+-	}
+-	cinfo = ret
+-	return
+-}
+-
+-// Returns the information about all subcontainers (recursive) of the specified container (including itself).
+-func (self *Client) SubcontainersInfo(name string, query *info.ContainerInfoRequest) ([]info.ContainerInfo, error) {
+-	var response []info.ContainerInfo
+-	url := self.subcontainersInfoUrl(name)
+-	err := self.httpGetJsonData(&response, query, url, fmt.Sprintf("subcontainers container info for %q", name))
+-	if err != nil {
+-		return []info.ContainerInfo{}, err
+-
+-	}
+-	return response, nil
+-}
+-
+-// Returns the JSON container information for the specified
+-// Docker container and request.
+-func (self *Client) DockerContainer(name string, query *info.ContainerInfoRequest) (cinfo info.ContainerInfo, err error) {
+-	u := self.dockerInfoUrl(name)
+-	ret := make(map[string]info.ContainerInfo)
+-	if err = self.httpGetJsonData(&ret, query, u, fmt.Sprintf("Docker container info for %q", name)); err != nil {
+-		return
+-	}
+-	if len(ret) != 1 {
+-		err = fmt.Errorf("expected to only receive 1 Docker container: %+v", ret)
+-		return
+-	}
+-	for _, cont := range ret {
+-		cinfo = cont
+-	}
+-	return
+-}
+-
+-// Returns the JSON container information for all Docker containers.
+-func (self *Client) AllDockerContainers(query *info.ContainerInfoRequest) (cinfo []info.ContainerInfo, err error) {
+-	u := self.dockerInfoUrl("/")
+-	ret := make(map[string]info.ContainerInfo)
+-	if err = self.httpGetJsonData(&ret, query, u, "all Docker containers info"); err != nil {
+-		return
+-	}
+-	cinfo = make([]info.ContainerInfo, 0, len(ret))
+-	for _, cont := range ret {
+-		cinfo = append(cinfo, cont)
+-	}
+-	return
+-}
+-
+-func (self *Client) machineInfoUrl() string {
+-	return self.baseUrl + path.Join("machine")
+-}
+-
+-func (self *Client) containerInfoUrl(name string) string {
+-	return self.baseUrl + path.Join("containers", name)
+-}
+-
+-func (self *Client) subcontainersInfoUrl(name string) string {
+-	return self.baseUrl + path.Join("subcontainers", name)
+-}
+-
+-func (self *Client) dockerInfoUrl(name string) string {
+-	return self.baseUrl + path.Join("docker", name)
+-}
+-
+-func (self *Client) httpGetJsonData(data, postData interface{}, url, infoName string) error {
+-	var resp *http.Response
+-	var err error
+-
+-	if postData != nil {
+-		data, err := json.Marshal(postData)
+-		if err != nil {
+-			return fmt.Errorf("unable to marshal data: %v", err)
+-		}
+-		resp, err = http.Post(url, "application/json", bytes.NewBuffer(data))
+-	} else {
+-		resp, err = http.Get(url)
+-	}
+-	if err != nil {
+-		return fmt.Errorf("unable to get %q: %v", infoName, err)
+-	}
+-	if resp == nil {
+-		return fmt.Errorf("received empty response from %q", infoName)
+-	}
+-	defer resp.Body.Close()
+-	body, err := ioutil.ReadAll(resp.Body)
+-	if err != nil {
+-		err = fmt.Errorf("unable to read all %q: %v", infoName, err)
+-		return err
+-	}
+-	if err = json.Unmarshal(body, data); err != nil {
+-		err = fmt.Errorf("unable to unmarshal %q (%v): %v", infoName, string(body), err)
+-		return err
+-	}
+-	return nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/google/cadvisor/client/client_test.go b/Godeps/_workspace/src/github.com/google/cadvisor/client/client_test.go
+deleted file mode 100644
+index 67bf3c2..0000000
+--- a/Godeps/_workspace/src/github.com/google/cadvisor/client/client_test.go
++++ /dev/null
+@@ -1,154 +0,0 @@
+-// Copyright 2014 Google Inc. All Rights Reserved.
+-//
+-// Licensed under the Apache License, Version 2.0 (the "License");
+-// you may not use this file except in compliance with the License.
+-// You may obtain a copy of the License at
+-//
+-//     http://www.apache.org/licenses/LICENSE-2.0
+-//
+-// Unless required by applicable law or agreed to in writing, software
+-// distributed under the License is distributed on an "AS IS" BASIS,
+-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-// See the License for the specific language governing permissions and
+-// limitations under the License.
+-
+-package client
+-
+-import (
+-	"encoding/json"
+-	"fmt"
+-	"net/http"
+-	"net/http/httptest"
+-	"path"
+-	"reflect"
+-	"testing"
+-	"time"
+-
+-	"github.com/google/cadvisor/info"
+-	itest "github.com/google/cadvisor/info/test"
+-	"github.com/kr/pretty"
+-)
+-
+-func testGetJsonData(
+-	expected interface{},
+-	f func() (interface{}, error),
+-) error {
+-	reply, err := f()
+-	if err != nil {
+-		return fmt.Errorf("unable to retrieve data: %v", err)
+-	}
+-	if !reflect.DeepEqual(reply, expected) {
+-		return pretty.Errorf("retrieved wrong data: %# v != %# v", reply, expected)
+-	}
+-	return nil
+-}
+-
+-func cadvisorTestClient(path string, expectedPostObj, expectedPostObjEmpty, replyObj interface{}, t *testing.T) (*Client, *httptest.Server, error) {
+-	ts := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+-		if r.URL.Path == path {
+-			if expectedPostObj != nil {
+-				decoder := json.NewDecoder(r.Body)
+-				if err := decoder.Decode(expectedPostObjEmpty); err != nil {
+-					t.Errorf("Received invalid object: %v", err)
+-				}
+-				if !reflect.DeepEqual(expectedPostObj, expectedPostObjEmpty) {
+-					t.Errorf("Received unexpected object: %+v", expectedPostObjEmpty)
+-				}
+-			}
+-			encoder := json.NewEncoder(w)
+-			encoder.Encode(replyObj)
+-		} else if r.URL.Path == "/api/v1.2/machine" {
+-			fmt.Fprint(w, `{"num_cores":8,"memory_capacity":31625871360}`)
+-		} else {
+-			w.WriteHeader(http.StatusNotFound)
+-			fmt.Fprintf(w, "Page not found.")
+-		}
+-	}))
+-	client, err := NewClient(ts.URL)
+-	if err != nil {
+-		ts.Close()
+-		return nil, nil, err
+-	}
+-	return client, ts, err
+-}
+-
+-// TestGetMachineInfo performs one test to check if MachineInfo()
+-// in a cAdvisor client returns the correct result.
+-func TestGetMachineinfo(t *testing.T) {
+-	minfo := &info.MachineInfo{
+-		NumCores:       8,
+-		MemoryCapacity: 31625871360,
+-	}
+-	client, server, err := cadvisorTestClient("/api/v1.2/machine", nil, nil, minfo, t)
+-	if err != nil {
+-		t.Fatalf("unable to get a client %v", err)
+-	}
+-	defer server.Close()
+-	returned, err := client.MachineInfo()
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if !reflect.DeepEqual(returned, minfo) {
+-		t.Fatalf("received unexpected machine info")
+-	}
+-}
+-
+-// TestGetContainerInfo generates a random container information object
+-// and then checks that ContainerInfo returns the expected result.
+-func TestGetContainerInfo(t *testing.T) {
+-	query := &info.ContainerInfoRequest{
+-		NumStats: 3,
+-	}
+-	containerName := "/some/container"
+-	cinfo := itest.GenerateRandomContainerInfo(containerName, 4, query, 1*time.Second)
+-	client, server, err := cadvisorTestClient(fmt.Sprintf("/api/v1.2/containers%v", containerName), query, &info.ContainerInfoRequest{}, cinfo, t)
+-	if err != nil {
+-		t.Fatalf("unable to get a client %v", err)
+-	}
+-	defer server.Close()
+-	returned, err := client.ContainerInfo(containerName, query)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	if !returned.Eq(cinfo) {
+-		t.Error("received unexpected ContainerInfo")
+-	}
+-}
+-
+-func TestGetSubcontainersInfo(t *testing.T) {
+-	query := &info.ContainerInfoRequest{
+-		NumStats: 3,
+-	}
+-	containerName := "/some/container"
+-	cinfo := itest.GenerateRandomContainerInfo(containerName, 4, query, 1*time.Second)
+-	cinfo1 := itest.GenerateRandomContainerInfo(path.Join(containerName, "sub1"), 4, query, 1*time.Second)
+-	cinfo2 := itest.GenerateRandomContainerInfo(path.Join(containerName, "sub2"), 4, query, 1*time.Second)
+-	response := []info.ContainerInfo{
+-		*cinfo,
+-		*cinfo1,
+-		*cinfo2,
+-	}
+-	client, server, err := cadvisorTestClient(fmt.Sprintf("/api/v1.2/subcontainers%v", containerName), query, &info.ContainerInfoRequest{}, response, t)
+-	if err != nil {
+-		t.Fatalf("unable to get a client %v", err)
+-	}
+-	defer server.Close()
+-	returned, err := client.SubcontainersInfo(containerName, query)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	if len(returned) != 3 {
+-		t.Errorf("unexpected number of results: got %d, expected 3", len(returned))
+-	}
+-	if !returned[0].Eq(cinfo) {
+-		t.Error("received unexpected ContainerInfo")
+-	}
+-	if !returned[1].Eq(cinfo1) {
+-		t.Error("received unexpected ContainerInfo")
+-	}
+-	if !returned[2].Eq(cinfo2) {
+-		t.Error("received unexpected ContainerInfo")
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/google/cadvisor/info/container.go b/Godeps/_workspace/src/github.com/google/cadvisor/info/container.go
+deleted file mode 100644
+index 5a4fbbd..0000000
+--- a/Godeps/_workspace/src/github.com/google/cadvisor/info/container.go
++++ /dev/null
+@@ -1,379 +0,0 @@
+-// Copyright 2014 Google Inc. All Rights Reserved.
+-//
+-// Licensed under the Apache License, Version 2.0 (the "License");
+-// you may not use this file except in compliance with the License.
+-// You may obtain a copy of the License at
+-//
+-//     http://www.apache.org/licenses/LICENSE-2.0
+-//
+-// Unless required by applicable law or agreed to in writing, software
+-// distributed under the License is distributed on an "AS IS" BASIS,
+-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-// See the License for the specific language governing permissions and
+-// limitations under the License.
+-
+-package info
+-
+-import (
+-	"reflect"
+-	"time"
+-)
+-
+-type CpuSpec struct {
+-	Limit    uint64 `json:"limit"`
+-	MaxLimit uint64 `json:"max_limit"`
+-	Mask     string `json:"mask,omitempty"`
+-}
+-
+-type MemorySpec struct {
+-	// The amount of memory requested. Default is unlimited (-1).
+-	// Units: bytes.
+-	Limit uint64 `json:"limit,omitempty"`
+-
+-	// The amount of guaranteed memory.  Default is 0.
+-	// Units: bytes.
+-	Reservation uint64 `json:"reservation,omitempty"`
+-
+-	// The amount of swap space requested. Default is unlimited (-1).
+-	// Units: bytes.
+-	SwapLimit uint64 `json:"swap_limit,omitempty"`
+-}
+-
+-type ContainerSpec struct {
+-	HasCpu bool    `json:"has_cpu"`
+-	Cpu    CpuSpec `json:"cpu,omitempty"`
+-
+-	HasMemory bool       `json:"has_memory"`
+-	Memory    MemorySpec `json:"memory,omitempty"`
+-
+-	HasNetwork bool `json:"has_network"`
+-
+-	HasFilesystem bool `json:"has_filesystem"`
+-}
+-
+-// Container reference contains enough information to uniquely identify a container
+-type ContainerReference struct {
+-	// The absolute name of the container. This is unique on the machine.
+-	Name string `json:"name"`
+-
+-	// Other names by which the container is known within a certain namespace.
+-	// This is unique within that namespace.
+-	Aliases []string `json:"aliases,omitempty"`
+-
+-	// Namespace under which the aliases of a container are unique.
+-	// An example of a namespace is "docker" for Docker containers.
+-	Namespace string `json:"namespace,omitempty"`
+-}
+-
+-// ContainerInfoQuery is used when users check a container info from the REST api.
+-// It specifies how much data users want to get about a container
+-type ContainerInfoRequest struct {
+-	// Max number of stats to return.
+-	NumStats int `json:"num_stats,omitempty"`
+-}
+-
+-type ContainerInfo struct {
+-	ContainerReference
+-
+-	// The direct subcontainers of the current container.
+-	Subcontainers []ContainerReference `json:"subcontainers,omitempty"`
+-
+-	// The isolation used in the container.
+-	Spec ContainerSpec `json:"spec,omitempty"`
+-
+-	// Historical statistics gathered from the container.
+-	Stats []*ContainerStats `json:"stats,omitempty"`
+-}
+-
+-// ContainerInfo may be (un)marshaled by json or other en/decoder. In that
+-// case, the Timestamp field in each stats/sample may not be precisely
+-// en/decoded.  This will lead to small but acceptable differences between a
+-// ContainerInfo and its encode-then-decode version.  Eq() is used to compare
+-// two ContainerInfo accepting small difference (<10ms) of Time fields.
+-func (self *ContainerInfo) Eq(b *ContainerInfo) bool {
+-
+-	// If both self and b are nil, then Eq() returns true
+-	if self == nil {
+-		return b == nil
+-	}
+-	if b == nil {
+-		return self == nil
+-	}
+-
+-	// For fields other than time.Time, we will compare them precisely.
+-	// This would require that any slice should have same order.
+-	if !reflect.DeepEqual(self.ContainerReference, b.ContainerReference) {
+-		return false
+-	}
+-	if !reflect.DeepEqual(self.Subcontainers, b.Subcontainers) {
+-		return false
+-	}
+-	if !reflect.DeepEqual(self.Spec, b.Spec) {
+-		return false
+-	}
+-
+-	for i, expectedStats := range b.Stats {
+-		selfStats := self.Stats[i]
+-		if !expectedStats.Eq(selfStats) {
+-			return false
+-		}
+-	}
+-
+-	return true
+-}
+-
+-func (self *ContainerInfo) StatsAfter(ref time.Time) []*ContainerStats {
+-	n := len(self.Stats) + 1
+-	for i, s := range self.Stats {
+-		if s.Timestamp.After(ref) {
+-			n = i
+-			break
+-		}
+-	}
+-	if n > len(self.Stats) {
+-		return nil
+-	}
+-	return self.Stats[n:]
+-}
+-
+-func (self *ContainerInfo) StatsStartTime() time.Time {
+-	var ret time.Time
+-	for _, s := range self.Stats {
+-		if s.Timestamp.Before(ret) || ret.IsZero() {
+-			ret = s.Timestamp
+-		}
+-	}
+-	return ret
+-}
+-
+-func (self *ContainerInfo) StatsEndTime() time.Time {
+-	var ret time.Time
+-	for i := len(self.Stats) - 1; i >= 0; i-- {
+-		s := self.Stats[i]
+-		if s.Timestamp.After(ret) {
+-			ret = s.Timestamp
+-		}
+-	}
+-	return ret
+-}
+-
+-// All CPU usage metrics are cumulative from the creation of the container
+-type CpuStats struct {
+-	Usage struct {
+-		// Total CPU usage.
+-		// Units: nanoseconds
+-		Total uint64 `json:"total"`
+-
+-		// Per CPU/core usage of the container.
+-		// Unit: nanoseconds.
+-		PerCpu []uint64 `json:"per_cpu_usage,omitempty"`
+-
+-		// Time spent in user space.
+-		// Unit: nanoseconds
+-		User uint64 `json:"user"`
+-
+-		// Time spent in kernel space.
+-		// Unit: nanoseconds
+-		System uint64 `json:"system"`
+-	} `json:"usage"`
+-	Load int32 `json:"load"`
+-}
+-
+-type PerDiskStats struct {
+-	Major uint64            `json:"major"`
+-	Minor uint64            `json:"minor"`
+-	Stats map[string]uint64 `json:"stats"`
+-}
+-
+-type DiskIoStats struct {
+-	IoServiceBytes []PerDiskStats `json:"io_service_bytes,omitempty"`
+-	IoServiced     []PerDiskStats `json:"io_serviced,omitempty"`
+-	IoQueued       []PerDiskStats `json:"io_queued,omitempty"`
+-	Sectors        []PerDiskStats `json:"sectors,omitempty"`
+-	IoServiceTime  []PerDiskStats `json:"io_service_time,omitempty"`
+-	IoWaitTime     []PerDiskStats `json:"io_wait_time,omitempty"`
+-	IoMerged       []PerDiskStats `json:"io_merged,omitempty"`
+-	IoTime         []PerDiskStats `json:"io_time,omitempty"`
+-}
+-
+-type MemoryStats struct {
+-	// Current memory usage, this includes all memory regardless of when it was
+-	// accessed.
+-	// Units: Bytes.
+-	Usage uint64 `json:"usage"`
+-
+-	// The amount of working set memory, this includes recently accessed memory,
+-	// dirty memory, and kernel memory. Working set is <= "usage".
+-	// Units: Bytes.
+-	WorkingSet uint64 `json:"working_set"`
+-
+-	ContainerData    MemoryStatsMemoryData `json:"container_data,omitempty"`
+-	HierarchicalData MemoryStatsMemoryData `json:"hierarchical_data,omitempty"`
+-}
+-
+-type MemoryStatsMemoryData struct {
+-	Pgfault    uint64 `json:"pgfault"`
+-	Pgmajfault uint64 `json:"pgmajfault"`
+-}
+-
+-type NetworkStats struct {
+-	// Cumulative count of bytes received.
+-	RxBytes uint64 `json:"rx_bytes"`
+-	// Cumulative count of packets received.
+-	RxPackets uint64 `json:"rx_packets"`
+-	// Cumulative count of receive errors encountered.
+-	RxErrors uint64 `json:"rx_errors"`
+-	// Cumulative count of packets dropped while receiving.
+-	RxDropped uint64 `json:"rx_dropped"`
+-	// Cumulative count of bytes transmitted.
+-	TxBytes uint64 `json:"tx_bytes"`
+-	// Cumulative count of packets transmitted.
+-	TxPackets uint64 `json:"tx_packets"`
+-	// Cumulative count of transmit errors encountered.
+-	TxErrors uint64 `json:"tx_errors"`
+-	// Cumulative count of packets dropped while transmitting.
+-	TxDropped uint64 `json:"tx_dropped"`
+-}
+-
+-type FsStats struct {
+-	// The block device name associated with the filesystem.
+-	Device string `json:"device,omitempty"`
+-
+-	// Number of bytes that can be consumed by the container on this filesystem.
+-	Limit uint64 `json:"capacity"`
+-
+-	// Number of bytes that is consumed by the container on this filesystem.
+-	Usage uint64 `json:"usage"`
+-
+-	// Number of reads completed
+-	// This is the total number of reads completed successfully.
+-	ReadsCompleted uint64 `json:"reads_completed"`
+-
+-	// Number of reads merged
+-	// Reads and writes which are adjacent to each other may be merged for
+-	// efficiency.  Thus two 4K reads may become one 8K read before it is
+-	// ultimately handed to the disk, and so it will be counted (and queued)
+-	// as only one I/O.  This field lets you know how often this was done.
+-	ReadsMerged uint64 `json:"reads_merged"`
+-
+-	// Number of sectors read
+-	// This is the total number of sectors read successfully.
+-	SectorsRead uint64 `json:"sectors_read"`
+-
+-	// Number of milliseconds spent reading
+-	// This is the total number of milliseconds spent by all reads (as
+-	// measured from __make_request() to end_that_request_last()).
+-	ReadTime uint64 `json:"read_time"`
+-
+-	// Number of writes completed
+-	// This is the total number of writes completed successfully.
+-	WritesCompleted uint64 `json:"writes_completed"`
+-
+-	// Number of writes merged
+-	// See the description of reads merged.
+-	WritesMerged uint64 `json:"writes_merged"`
+-
+-	// Number of sectors written
+-	// This is the total number of sectors written successfully.
+-	SectorsWritten uint64 `json:"sectors_written"`
+-
+-	// Number of milliseconds spent writing
+-	// This is the total number of milliseconds spent by all writes (as
+-	// measured from __make_request() to end_that_request_last()).
+-	WriteTime uint64 `json:"write_time"`
+-
+-	// Number of I/Os currently in progress
+-	// The only field that should go to zero. Incremented as requests are
+-	// given to appropriate struct request_queue and decremented as they finish.
+-	IoInProgress uint64 `json:"io_in_progress"`
+-
+-	// Number of milliseconds spent doing I/Os
+-	// This field increases so long as field 9 is nonzero.
+-	IoTime uint64 `json:"io_time"`
+-
+-	// weighted number of milliseconds spent doing I/Os
+-	// This field is incremented at each I/O start, I/O completion, I/O
+-	// merge, or read of these stats by the number of I/Os in progress
+-	// (field 9) times the number of milliseconds spent doing I/O since the
+-	// last update of this field.  This can provide an easy measure of both
+-	// I/O completion time and the backlog that may be accumulating.
+-	WeightedIoTime uint64 `json:"weighted_io_time"`
+-}
+-
+-type ContainerStats struct {
+-	// The time of this stat point.
+-	Timestamp time.Time    `json:"timestamp"`
+-	Cpu       CpuStats     `json:"cpu,omitempty"`
+-	DiskIo    DiskIoStats  `json:"diskio,omitempty"`
+-	Memory    MemoryStats  `json:"memory,omitempty"`
+-	Network   NetworkStats `json:"network,omitempty"`
+-
+-	// Filesystem statistics
+-	Filesystem []FsStats `json:"filesystem,omitempty"`
+-}
+-
+-func timeEq(t1, t2 time.Time, tolerance time.Duration) bool {
+-	// t1 should not be later than t2
+-	if t1.After(t2) {
+-		t1, t2 = t2, t1
+-	}
+-	diff := t2.Sub(t1)
+-	if diff <= tolerance {
+-		return true
+-	}
+-	return false
+-}
+-
+-func durationEq(a, b time.Duration, tolerance time.Duration) bool {
+-	if a > b {
+-		a, b = b, a
+-	}
+-	diff := a - b
+-	if diff <= tolerance {
+-		return true
+-	}
+-	return false
+-}
+-
+-const (
+-	// 10ms, i.e. 0.01s
+-	timePrecision time.Duration = 10 * time.Millisecond
+-)
+-
+-// This function is useful because we do not require precise time
+-// representation.
+-func (a *ContainerStats) Eq(b *ContainerStats) bool {
+-	if !timeEq(a.Timestamp, b.Timestamp, timePrecision) {
+-		return false
+-	}
+-	return a.StatsEq(b)
+-}
+-
+-// Checks equality of the stats values.
+-func (a *ContainerStats) StatsEq(b *ContainerStats) bool {
+-	// TODO(vmarmol): Consider using this through reflection.
+-	if !reflect.DeepEqual(a.Cpu, b.Cpu) {
+-		return false
+-	}
+-	if !reflect.DeepEqual(a.Memory, b.Memory) {
+-		return false
+-	}
+-	if !reflect.DeepEqual(a.DiskIo, b.DiskIo) {
+-		return false
+-	}
+-	if !reflect.DeepEqual(a.Network, b.Network) {
+-		return false
+-	}
+-	if !reflect.DeepEqual(a.Filesystem, b.Filesystem) {
+-		return false
+-	}
+-	return true
+-}
+-
+-// Saturate CPU usage to 0.
+-func calculateCpuUsage(prev, cur uint64) uint64 {
+-	if prev > cur {
+-		return 0
+-	}
+-	return cur - prev
+-}
+diff --git a/Godeps/_workspace/src/github.com/google/cadvisor/info/container_test.go b/Godeps/_workspace/src/github.com/google/cadvisor/info/container_test.go
+deleted file mode 100644
+index 2ff38e6..0000000
+--- a/Godeps/_workspace/src/github.com/google/cadvisor/info/container_test.go
++++ /dev/null
+@@ -1,79 +0,0 @@
+-// Copyright 2014 Google Inc. All Rights Reserved.
+-//
+-// Licensed under the Apache License, Version 2.0 (the "License");
+-// you may not use this file except in compliance with the License.
+-// You may obtain a copy of the License at
+-//
+-//     http://www.apache.org/licenses/LICENSE-2.0
+-//
+-// Unless required by applicable law or agreed to in writing, software
+-// distributed under the License is distributed on an "AS IS" BASIS,
+-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-// See the License for the specific language governing permissions and
+-// limitations under the License.
+-
+-package info
+-
+-import (
+-	"testing"
+-	"time"
+-)
+-
+-func TestStatsStartTime(t *testing.T) {
+-	N := 10
+-	stats := make([]*ContainerStats, 0, N)
+-	ct := time.Now()
+-	for i := 0; i < N; i++ {
+-		s := &ContainerStats{
+-			Timestamp: ct.Add(time.Duration(i) * time.Second),
+-		}
+-		stats = append(stats, s)
+-	}
+-	cinfo := &ContainerInfo{
+-		ContainerReference: ContainerReference{
+-			Name: "/some/container",
+-		},
+-		Stats: stats,
+-	}
+-	ref := ct.Add(time.Duration(N-1) * time.Second)
+-	end := cinfo.StatsEndTime()
+-
+-	if !ref.Equal(end) {
+-		t.Errorf("end time is %v; should be %v", end, ref)
+-	}
+-}
+-
+-func TestStatsEndTime(t *testing.T) {
+-	N := 10
+-	stats := make([]*ContainerStats, 0, N)
+-	ct := time.Now()
+-	for i := 0; i < N; i++ {
+-		s := &ContainerStats{
+-			Timestamp: ct.Add(time.Duration(i) * time.Second),
+-		}
+-		stats = append(stats, s)
+-	}
+-	cinfo := &ContainerInfo{
+-		ContainerReference: ContainerReference{
+-			Name: "/some/container",
+-		},
+-		Stats: stats,
+-	}
+-	ref := ct
+-	start := cinfo.StatsStartTime()
+-
+-	if !ref.Equal(start) {
+-		t.Errorf("start time is %v; should be %v", start, ref)
+-	}
+-}
+-
+-func createStats(cpuUsage, memUsage uint64, timestamp time.Time) *ContainerStats {
+-	stats := &ContainerStats{}
+-	stats.Cpu.Usage.PerCpu = []uint64{cpuUsage}
+-	stats.Cpu.Usage.Total = cpuUsage
+-	stats.Cpu.Usage.System = 0
+-	stats.Cpu.Usage.User = cpuUsage
+-	stats.Memory.Usage = memUsage
+-	stats.Timestamp = timestamp
+-	return stats
+-}
+diff --git a/Godeps/_workspace/src/github.com/google/cadvisor/info/machine.go b/Godeps/_workspace/src/github.com/google/cadvisor/info/machine.go
+deleted file mode 100644
+index 0e73a8e..0000000
+--- a/Godeps/_workspace/src/github.com/google/cadvisor/info/machine.go
++++ /dev/null
+@@ -1,53 +0,0 @@
+-// Copyright 2014 Google Inc. All Rights Reserved.
+-//
+-// Licensed under the Apache License, Version 2.0 (the "License");
+-// you may not use this file except in compliance with the License.
+-// You may obtain a copy of the License at
+-//
+-//     http://www.apache.org/licenses/LICENSE-2.0
+-//
+-// Unless required by applicable law or agreed to in writing, software
+-// distributed under the License is distributed on an "AS IS" BASIS,
+-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-// See the License for the specific language governing permissions and
+-// limitations under the License.
+-
+-package info
+-
+-type FsInfo struct {
+-	// Block device associated with the filesystem.
+-	Device string `json:"device"`
+-
+-	// Total number of bytes available on the filesystem.
+-	Capacity uint64 `json:"capacity"`
+-}
+-
+-type MachineInfo struct {
+-	// The number of cores in this machine.
+-	NumCores int `json:"num_cores"`
+-
+-	// The amount of memory (in bytes) in this machine
+-	MemoryCapacity int64 `json:"memory_capacity"`
+-
+-	// Filesystems on this machine.
+-	Filesystems []FsInfo `json:"filesystems"`
+-}
+-
+-type VersionInfo struct {
+-	// Kernel version.
+-	KernelVersion string `json:"kernel_version"`
+-
+-	// OS image being used for cadvisor container, or host image if running on host directly.
+-	ContainerOsVersion string `json:"container_os_version"`
+-
+-	// Docker version.
+-	DockerVersion string `json:"docker_version"`
+-
+-	// cAdvisor version.
+-	CadvisorVersion string `json:"cadvisor_version"`
+-}
+-
+-type MachineInfoFactory interface {
+-	GetMachineInfo() (*MachineInfo, error)
+-	GetVersionInfo() (*VersionInfo, error)
+-}
+diff --git a/Godeps/_workspace/src/github.com/google/cadvisor/info/test/datagen.go b/Godeps/_workspace/src/github.com/google/cadvisor/info/test/datagen.go
+deleted file mode 100644
+index 519e28c..0000000
+--- a/Godeps/_workspace/src/github.com/google/cadvisor/info/test/datagen.go
++++ /dev/null
+@@ -1,76 +0,0 @@
+-// Copyright 2014 Google Inc. All Rights Reserved.
+-//
+-// Licensed under the Apache License, Version 2.0 (the "License");
+-// you may not use this file except in compliance with the License.
+-// You may obtain a copy of the License at
+-//
+-//     http://www.apache.org/licenses/LICENSE-2.0
+-//
+-// Unless required by applicable law or agreed to in writing, software
+-// distributed under the License is distributed on an "AS IS" BASIS,
+-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-// See the License for the specific language governing permissions and
+-// limitations under the License.
+-
+-package test
+-
+-import (
+-	"fmt"
+-	"math/rand"
+-	"time"
+-
+-	"github.com/google/cadvisor/info"
+-)
+-
+-func GenerateRandomStats(numStats, numCores int, duration time.Duration) []*info.ContainerStats {
+-	ret := make([]*info.ContainerStats, numStats)
+-	perCoreUsages := make([]uint64, numCores)
+-	currentTime := time.Now()
+-	for i := range perCoreUsages {
+-		perCoreUsages[i] = uint64(rand.Int63n(1000))
+-	}
+-	for i := 0; i < numStats; i++ {
+-		stats := new(info.ContainerStats)
+-		stats.Timestamp = currentTime
+-		currentTime = currentTime.Add(duration)
+-
+-		percore := make([]uint64, numCores)
+-		for i := range perCoreUsages {
+-			perCoreUsages[i] += uint64(rand.Int63n(1000))
+-			percore[i] = perCoreUsages[i]
+-			stats.Cpu.Usage.Total += percore[i]
+-		}
+-		stats.Cpu.Usage.PerCpu = percore
+-		stats.Cpu.Usage.User = stats.Cpu.Usage.Total
+-		stats.Cpu.Usage.System = 0
+-		stats.Memory.Usage = uint64(rand.Int63n(4096))
+-		ret[i] = stats
+-	}
+-	return ret
+-}
+-
+-func GenerateRandomContainerSpec(numCores int) info.ContainerSpec {
+-	ret := info.ContainerSpec{
+-		Cpu:    info.CpuSpec{},
+-		Memory: info.MemorySpec{},
+-	}
+-	ret.Cpu.Limit = uint64(1000 + rand.Int63n(2000))
+-	ret.Cpu.MaxLimit = uint64(1000 + rand.Int63n(2000))
+-	ret.Cpu.Mask = fmt.Sprintf("0-%d", numCores-1)
+-	ret.Memory.Limit = uint64(4096 + rand.Int63n(4096))
+-	return ret
+-}
+-
+-func GenerateRandomContainerInfo(containerName string, numCores int, query *info.ContainerInfoRequest, duration time.Duration) *info.ContainerInfo {
+-	stats := GenerateRandomStats(query.NumStats, numCores, duration)
+-	spec := GenerateRandomContainerSpec(numCores)
+-
+-	ret := &info.ContainerInfo{
+-		ContainerReference: info.ContainerReference{
+-			Name: containerName,
+-		},
+-		Spec:  spec,
+-		Stats: stats,
+-	}
+-	return ret
+-}
+diff --git a/Godeps/_workspace/src/github.com/google/cadvisor/info/version.go b/Godeps/_workspace/src/github.com/google/cadvisor/info/version.go
+deleted file mode 100644
+index 771382a..0000000
+--- a/Godeps/_workspace/src/github.com/google/cadvisor/info/version.go
++++ /dev/null
+@@ -1,18 +0,0 @@
+-// Copyright 2014 Google Inc. All Rights Reserved.
+-//
+-// Licensed under the Apache License, Version 2.0 (the "License");
+-// you may not use this file except in compliance with the License.
+-// You may obtain a copy of the License at
+-//
+-//     http://www.apache.org/licenses/LICENSE-2.0
+-//
+-// Unless required by applicable law or agreed to in writing, software
+-// distributed under the License is distributed on an "AS IS" BASIS,
+-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-// See the License for the specific language governing permissions and
+-// limitations under the License.
+-
+-package info
+-
+-// Version of cAdvisor.
+-const VERSION = "0.6.2"
+diff --git a/Godeps/_workspace/src/github.com/google/gofuzz/.travis.yml b/Godeps/_workspace/src/github.com/google/gofuzz/.travis.yml
+deleted file mode 100644
+index 9384a54..0000000
+--- a/Godeps/_workspace/src/github.com/google/gofuzz/.travis.yml
++++ /dev/null
+@@ -1,12 +0,0 @@
+-language: go
+-
+-go:
+-  - 1.3
+-  - 1.2
+-  - tip
+-
+-install: 
+-  - go get code.google.com/p/go.tools/cmd/cover
+-
+-script:
+-  - go test -cover
+diff --git a/Godeps/_workspace/src/github.com/google/gofuzz/CONTRIBUTING.md b/Godeps/_workspace/src/github.com/google/gofuzz/CONTRIBUTING.md
+deleted file mode 100644
+index 51cf5cd..0000000
+--- a/Godeps/_workspace/src/github.com/google/gofuzz/CONTRIBUTING.md
++++ /dev/null
+@@ -1,67 +0,0 @@
+-# How to contribute #
+-
+-We'd love to accept your patches and contributions to this project.  There are
+-a just a few small guidelines you need to follow.
+-
+-
+-## Contributor License Agreement ##
+-
+-Contributions to any Google project must be accompanied by a Contributor
+-License Agreement.  This is not a copyright **assignment**, it simply gives
+-Google permission to use and redistribute your contributions as part of the
+-project.
+-
+-  * If you are an individual writing original source code and you're sure you
+-    own the intellectual property, then you'll need to sign an [individual
+-    CLA][].
+-
+-  * If you work for a company that wants to allow you to contribute your work,
+-    then you'll need to sign a [corporate CLA][].
+-
+-You generally only need to submit a CLA once, so if you've already submitted
+-one (even if it was for a different project), you probably don't need to do it
+-again.
+-
+-[individual CLA]: https://developers.google.com/open-source/cla/individual
+-[corporate CLA]: https://developers.google.com/open-source/cla/corporate
+-
+-
+-## Submitting a patch ##
+-
+-  1. It's generally best to start by opening a new issue describing the bug or
+-     feature you're intending to fix.  Even if you think it's relatively minor,
+-     it's helpful to know what people are working on.  Mention in the initial
+-     issue that you are planning to work on that bug or feature so that it can
+-     be assigned to you.
+-
+-  1. Follow the normal process of [forking][] the project, and setup a new
+-     branch to work in.  It's important that each group of changes be done in
+-     separate branches in order to ensure that a pull request only includes the
+-     commits related to that bug or feature.
+-
+-  1. Go makes it very simple to ensure properly formatted code, so always run
+-     `go fmt` on your code before committing it.  You should also run
+-     [golint][] over your code.  As noted in the [golint readme][], it's not
+-     strictly necessary that your code be completely "lint-free", but this will
+-     help you find common style issues.
+-
+-  1. Any significant changes should almost always be accompanied by tests.  The
+-     project already has good test coverage, so look at some of the existing
+-     tests if you're unsure how to go about it.  [gocov][] and [gocov-html][]
+-     are invaluable tools for seeing which parts of your code aren't being
+-     exercised by your tests.
+-
+-  1. Do your best to have [well-formed commit messages][] for each change.
+-     This provides consistency throughout the project, and ensures that commit
+-     messages are able to be formatted properly by various git tools.
+-
+-  1. Finally, push the commits to your fork and submit a [pull request][].
+-
+-[forking]: https://help.github.com/articles/fork-a-repo
+-[golint]: https://github.com/golang/lint
+-[golint readme]: https://github.com/golang/lint/blob/master/README
+-[gocov]: https://github.com/axw/gocov
+-[gocov-html]: https://github.com/matm/gocov-html
+-[well-formed commit messages]: http://tbaggery.com/2008/04/19/a-note-about-git-commit-messages.html
+-[squash]: http://git-scm.com/book/en/Git-Tools-Rewriting-History#Squashing-Commits
+-[pull request]: https://help.github.com/articles/creating-a-pull-request
+diff --git a/Godeps/_workspace/src/github.com/google/gofuzz/LICENSE b/Godeps/_workspace/src/github.com/google/gofuzz/LICENSE
+deleted file mode 100644
+index d645695..0000000
+--- a/Godeps/_workspace/src/github.com/google/gofuzz/LICENSE
++++ /dev/null
+@@ -1,202 +0,0 @@
+-
+-                                 Apache License
+-                           Version 2.0, January 2004
+-                        http://www.apache.org/licenses/
+-
+-   TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+-
+-   1. Definitions.
+-
+-      "License" shall mean the terms and conditions for use, reproduction,
+-      and distribution as defined by Sections 1 through 9 of this document.
+-
+-      "Licensor" shall mean the copyright owner or entity authorized by
+-      the copyright owner that is granting the License.
+-
+-      "Legal Entity" shall mean the union of the acting entity and all
+-      other entities that control, are controlled by, or are under common
+-      control with that entity. For the purposes of this definition,
+-      "control" means (i) the power, direct or indirect, to cause the
+-      direction or management of such entity, whether by contract or
+-      otherwise, or (ii) ownership of fifty percent (50%) or more of the
+-      outstanding shares, or (iii) beneficial ownership of such entity.
+-
+-      "You" (or "Your") shall mean an individual or Legal Entity
+-      exercising permissions granted by this License.
+-
+-      "Source" form shall mean the preferred form for making modifications,
+-      including but not limited to software source code, documentation
+-      source, and configuration files.
+-
+-      "Object" form shall mean any form resulting from mechanical
+-      transformation or translation of a Source form, including but
+-      not limited to compiled object code, generated documentation,
+-      and conversions to other media types.
+-
+-      "Work" shall mean the work of authorship, whether in Source or
+-      Object form, made available under the License, as indicated by a
+-      copyright notice that is included in or attached to the work
+-      (an example is provided in the Appendix below).
+-
+-      "Derivative Works" shall mean any work, whether in Source or Object
+-      form, that is based on (or derived from) the Work and for which the
+-      editorial revisions, annotations, elaborations, or other modifications
+-      represent, as a whole, an original work of authorship. For the purposes
+-      of this License, Derivative Works shall not include works that remain
+-      separable from, or merely link (or bind by name) to the interfaces of,
+-      the Work and Derivative Works thereof.
+-
+-      "Contribution" shall mean any work of authorship, including
+-      the original version of the Work and any modifications or additions
+-      to that Work or Derivative Works thereof, that is intentionally
+-      submitted to Licensor for inclusion in the Work by the copyright owner
+-      or by an individual or Legal Entity authorized to submit on behalf of
+-      the copyright owner. For the purposes of this definition, "submitted"
+-      means any form of electronic, verbal, or written communication sent
+-      to the Licensor or its representatives, including but not limited to
+-      communication on electronic mailing lists, source code control systems,
+-      and issue tracking systems that are managed by, or on behalf of, the
+-      Licensor for the purpose of discussing and improving the Work, but
+-      excluding communication that is conspicuously marked or otherwise
+-      designated in writing by the copyright owner as "Not a Contribution."
+-
+-      "Contributor" shall mean Licensor and any individual or Legal Entity
+-      on behalf of whom a Contribution has been received by Licensor and
+-      subsequently incorporated within the Work.
+-
+-   2. Grant of Copyright License. Subject to the terms and conditions of
+-      this License, each Contributor hereby grants to You a perpetual,
+-      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+-      copyright license to reproduce, prepare Derivative Works of,
+-      publicly display, publicly perform, sublicense, and distribute the
+-      Work and such Derivative Works in Source or Object form.
+-
+-   3. Grant of Patent License. Subject to the terms and conditions of
+-      this License, each Contributor hereby grants to You a perpetual,
+-      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+-      (except as stated in this section) patent license to make, have made,
+-      use, offer to sell, sell, import, and otherwise transfer the Work,
+-      where such license applies only to those patent claims licensable
+-      by such Contributor that are necessarily infringed by their
+-      Contribution(s) alone or by combination of their Contribution(s)
+-      with the Work to which such Contribution(s) was submitted. If You
+-      institute patent litigation against any entity (including a
+-      cross-claim or counterclaim in a lawsuit) alleging that the Work
+-      or a Contribution incorporated within the Work constitutes direct
+-      or contributory patent infringement, then any patent licenses
+-      granted to You under this License for that Work shall terminate
+-      as of the date such litigation is filed.
+-
+-   4. Redistribution. You may reproduce and distribute copies of the
+-      Work or Derivative Works thereof in any medium, with or without
+-      modifications, and in Source or Object form, provided that You
+-      meet the following conditions:
+-
+-      (a) You must give any other recipients of the Work or
+-          Derivative Works a copy of this License; and
+-
+-      (b) You must cause any modified files to carry prominent notices
+-          stating that You changed the files; and
+-
+-      (c) You must retain, in the Source form of any Derivative Works
+-          that You distribute, all copyright, patent, trademark, and
+-          attribution notices from the Source form of the Work,
+-          excluding those notices that do not pertain to any part of
+-          the Derivative Works; and
+-
+-      (d) If the Work includes a "NOTICE" text file as part of its
+-          distribution, then any Derivative Works that You distribute must
+-          include a readable copy of the attribution notices contained
+-          within such NOTICE file, excluding those notices that do not
+-          pertain to any part of the Derivative Works, in at least one
+-          of the following places: within a NOTICE text file distributed
+-          as part of the Derivative Works; within the Source form or
+-          documentation, if provided along with the Derivative Works; or,
+-          within a display generated by the Derivative Works, if and
+-          wherever such third-party notices normally appear. The contents
+-          of the NOTICE file are for informational purposes only and
+-          do not modify the License. You may add Your own attribution
+-          notices within Derivative Works that You distribute, alongside
+-          or as an addendum to the NOTICE text from the Work, provided
+-          that such additional attribution notices cannot be construed
+-          as modifying the License.
+-
+-      You may add Your own copyright statement to Your modifications and
+-      may provide additional or different license terms and conditions
+-      for use, reproduction, or distribution of Your modifications, or
+-      for any such Derivative Works as a whole, provided Your use,
+-      reproduction, and distribution of the Work otherwise complies with
+-      the conditions stated in this License.
+-
+-   5. Submission of Contributions. Unless You explicitly state otherwise,
+-      any Contribution intentionally submitted for inclusion in the Work
+-      by You to the Licensor shall be under the terms and conditions of
+-      this License, without any additional terms or conditions.
+-      Notwithstanding the above, nothing herein shall supersede or modify
+-      the terms of any separate license agreement you may have executed
+-      with Licensor regarding such Contributions.
+-
+-   6. Trademarks. This License does not grant permission to use the trade
+-      names, trademarks, service marks, or product names of the Licensor,
+-      except as required for reasonable and customary use in describing the
+-      origin of the Work and reproducing the content of the NOTICE file.
+-
+-   7. Disclaimer of Warranty. Unless required by applicable law or
+-      agreed to in writing, Licensor provides the Work (and each
+-      Contributor provides its Contributions) on an "AS IS" BASIS,
+-      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+-      implied, including, without limitation, any warranties or conditions
+-      of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+-      PARTICULAR PURPOSE. You are solely responsible for determining the
+-      appropriateness of using or redistributing the Work and assume any
+-      risks associated with Your exercise of permissions under this License.
+-
+-   8. Limitation of Liability. In no event and under no legal theory,
+-      whether in tort (including negligence), contract, or otherwise,
+-      unless required by applicable law (such as deliberate and grossly
+-      negligent acts) or agreed to in writing, shall any Contributor be
+-      liable to You for damages, including any direct, indirect, special,
+-      incidental, or consequential damages of any character arising as a
+-      result of this License or out of the use or inability to use the
+-      Work (including but not limited to damages for loss of goodwill,
+-      work stoppage, computer failure or malfunction, or any and all
+-      other commercial damages or losses), even if such Contributor
+-      has been advised of the possibility of such damages.
+-
+-   9. Accepting Warranty or Additional Liability. While redistributing
+-      the Work or Derivative Works thereof, You may choose to offer,
+-      and charge a fee for, acceptance of support, warranty, indemnity,
+-      or other liability obligations and/or rights consistent with this
+-      License. However, in accepting such obligations, You may act only
+-      on Your own behalf and on Your sole responsibility, not on behalf
+-      of any other Contributor, and only if You agree to indemnify,
+-      defend, and hold each Contributor harmless for any liability
+-      incurred by, or claims asserted against, such Contributor by reason
+-      of your accepting any such warranty or additional liability.
+-
+-   END OF TERMS AND CONDITIONS
+-
+-   APPENDIX: How to apply the Apache License to your work.
+-
+-      To apply the Apache License to your work, attach the following
+-      boilerplate notice, with the fields enclosed by brackets "[]"
+-      replaced with your own identifying information. (Don't include
+-      the brackets!)  The text should be enclosed in the appropriate
+-      comment syntax for the file format. We also recommend that a
+-      file or class name and description of purpose be included on the
+-      same "printed page" as the copyright notice for easier
+-      identification within third-party archives.
+-
+-   Copyright [yyyy] [name of copyright owner]
+-
+-   Licensed under the Apache License, Version 2.0 (the "License");
+-   you may not use this file except in compliance with the License.
+-   You may obtain a copy of the License at
+-
+-       http://www.apache.org/licenses/LICENSE-2.0
+-
+-   Unless required by applicable law or agreed to in writing, software
+-   distributed under the License is distributed on an "AS IS" BASIS,
+-   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-   See the License for the specific language governing permissions and
+-   limitations under the License.
+diff --git a/Godeps/_workspace/src/github.com/google/gofuzz/README.md b/Godeps/_workspace/src/github.com/google/gofuzz/README.md
+deleted file mode 100644
+index 68fcf2c..0000000
+--- a/Godeps/_workspace/src/github.com/google/gofuzz/README.md
++++ /dev/null
+@@ -1,71 +0,0 @@
+-gofuzz
+-======
+-
+-gofuzz is a library for populating go objects with random values.
+-
+-[![GoDoc](https://godoc.org/github.com/google/gofuzz?status.png)](https://godoc.org/github.com/google/gofuzz)
+-[![Travis](https://travis-ci.org/google/gofuzz.svg?branch=master)](https://travis-ci.org/google/gofuzz)
+-
+-This is useful for testing:
+-
+-* Do your project's objects really serialize/unserialize correctly in all cases?
+-* Is there an incorrectly formatted object that will cause your project to panic?
+-
+-Import with ```import "github.com/google/gofuzz"```
+-
+-You can use it on single variables:
+-```
+-f := fuzz.New()
+-var myInt int
+-f.Fuzz(&myInt) // myInt gets a random value.
+-```
+-
+-You can use it on maps:
+-```
+-f := fuzz.New().NilChance(0).NumElements(1, 1)
+-var myMap map[ComplexKeyType]string
+-f.Fuzz(&myMap) // myMap will have exactly one element.
+-```
+-
+-Customize the chance of getting a nil pointer:
+-```
+-f := fuzz.New().NilChance(.5)
+-var fancyStruct struct {
+-  A, B, C, D *string
+-}
+-f.Fuzz(&fancyStruct) // About half the pointers should be set.
+-```
+-
+-You can even customize the randomization completely if needed:
+-```
+-type MyEnum string
+-const (
+-        A MyEnum = "A"
+-        B MyEnum = "B"
+-)
+-type MyInfo struct {
+-        Type MyEnum
+-        AInfo *string
+-        BInfo *string
+-}
+-
+-f := fuzz.New().NilChance(0).Funcs(
+-        func(e *MyInfo, c fuzz.Continue) {
+-                switch c.Intn(2) {
+-                case 0:
+-                        e.Type = A
+-                        c.Fuzz(&e.AInfo)
+-                case 1:
+-                        e.Type = B
+-                        c.Fuzz(&e.BInfo)
+-                }
+-        },
+-)
+-
+-var myObject MyInfo
+-f.Fuzz(&myObject) // Type will correspond to whether A or B info is set.
+-```
+-
+-See more examples in ```example_test.go```.
+-
+-Happy testing!
+diff --git a/Godeps/_workspace/src/github.com/google/gofuzz/doc.go b/Godeps/_workspace/src/github.com/google/gofuzz/doc.go
+deleted file mode 100644
+index 9f9956d..0000000
+--- a/Godeps/_workspace/src/github.com/google/gofuzz/doc.go
++++ /dev/null
+@@ -1,18 +0,0 @@
+-/*
+-Copyright 2014 Google Inc. All rights reserved.
+-
+-Licensed under the Apache License, Version 2.0 (the "License");
+-you may not use this file except in compliance with the License.
+-You may obtain a copy of the License at
+-
+-    http://www.apache.org/licenses/LICENSE-2.0
+-
+-Unless required by applicable law or agreed to in writing, software
+-distributed under the License is distributed on an "AS IS" BASIS,
+-WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-See the License for the specific language governing permissions and
+-limitations under the License.
+-*/
+-
+-// Package fuzz is a library for populating go objects with random values.
+-package fuzz
+diff --git a/Godeps/_workspace/src/github.com/google/gofuzz/example_test.go b/Godeps/_workspace/src/github.com/google/gofuzz/example_test.go
+deleted file mode 100644
+index 792707a..0000000
+--- a/Godeps/_workspace/src/github.com/google/gofuzz/example_test.go
++++ /dev/null
+@@ -1,225 +0,0 @@
+-/*
+-Copyright 2014 Google Inc. All rights reserved.
+-
+-Licensed under the Apache License, Version 2.0 (the "License");
+-you may not use this file except in compliance with the License.
+-You may obtain a copy of the License at
+-
+-    http://www.apache.org/licenses/LICENSE-2.0
+-
+-Unless required by applicable law or agreed to in writing, software
+-distributed under the License is distributed on an "AS IS" BASIS,
+-WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-See the License for the specific language governing permissions and
+-limitations under the License.
+-*/
+-
+-package fuzz_test
+-
+-import (
+-	"encoding/json"
+-	"fmt"
+-	"math/rand"
+-
+-	"github.com/google/gofuzz"
+-)
+-
+-func ExampleSimple() {
+-	type MyType struct {
+-		A string
+-		B string
+-		C int
+-		D struct {
+-			E float64
+-		}
+-	}
+-
+-	f := fuzz.New()
+-	object := MyType{}
+-
+-	uniqueObjects := map[MyType]int{}
+-
+-	for i := 0; i < 1000; i++ {
+-		f.Fuzz(&object)
+-		uniqueObjects[object]++
+-	}
+-	fmt.Printf("Got %v unique objects.\n", len(uniqueObjects))
+-	// Output:
+-	// Got 1000 unique objects.
+-}
+-
+-func ExampleCustom() {
+-	type MyType struct {
+-		A int
+-		B string
+-	}
+-
+-	counter := 0
+-	f := fuzz.New().Funcs(
+-		func(i *int, c fuzz.Continue) {
+-			*i = counter
+-			counter++
+-		},
+-	)
+-	object := MyType{}
+-
+-	uniqueObjects := map[MyType]int{}
+-
+-	for i := 0; i < 100; i++ {
+-		f.Fuzz(&object)
+-		if object.A != i {
+-			fmt.Printf("Unexpected value: %#v\n", object)
+-		}
+-		uniqueObjects[object]++
+-	}
+-	fmt.Printf("Got %v unique objects.\n", len(uniqueObjects))
+-	// Output:
+-	// Got 100 unique objects.
+-}
+-
+-func ExampleComplex() {
+-	type OtherType struct {
+-		A string
+-		B string
+-	}
+-	type MyType struct {
+-		Pointer             *OtherType
+-		Map                 map[string]OtherType
+-		PointerMap          *map[string]OtherType
+-		Slice               []OtherType
+-		SlicePointer        []*OtherType
+-		PointerSlicePointer *[]*OtherType
+-	}
+-
+-	f := fuzz.New().RandSource(rand.NewSource(0)).NilChance(0).NumElements(1, 1).Funcs(
+-		func(o *OtherType, c fuzz.Continue) {
+-			o.A = "Foo"
+-			o.B = "Bar"
+-		},
+-		func(op **OtherType, c fuzz.Continue) {
+-			*op = &OtherType{"A", "B"}
+-		},
+-		func(m map[string]OtherType, c fuzz.Continue) {
+-			m["Works Because"] = OtherType{
+-				"Fuzzer",
+-				"Preallocated",
+-			}
+-		},
+-	)
+-	object := MyType{}
+-	f.Fuzz(&object)
+-	bytes, err := json.MarshalIndent(&object, "", "    ")
+-	if err != nil {
+-		fmt.Printf("error: %v\n", err)
+-	}
+-	fmt.Printf("%s\n", string(bytes))
+-	// Output:
+-	// {
+-	//     "Pointer": {
+-	//         "A": "A",
+-	//         "B": "B"
+-	//     },
+-	//     "Map": {
+-	//         "Works Because": {
+-	//             "A": "Fuzzer",
+-	//             "B": "Preallocated"
+-	//         }
+-	//     },
+-	//     "PointerMap": {
+-	//         "Works Because": {
+-	//             "A": "Fuzzer",
+-	//             "B": "Preallocated"
+-	//         }
+-	//     },
+-	//     "Slice": [
+-	//         {
+-	//             "A": "Foo",
+-	//             "B": "Bar"
+-	//         }
+-	//     ],
+-	//     "SlicePointer": [
+-	//         {
+-	//             "A": "A",
+-	//             "B": "B"
+-	//         }
+-	//     ],
+-	//     "PointerSlicePointer": [
+-	//         {
+-	//             "A": "A",
+-	//             "B": "B"
+-	//         }
+-	//     ]
+-	// }
+-}
+-
+-func ExampleMap() {
+-	f := fuzz.New().NilChance(0).NumElements(1, 1)
+-	var myMap map[struct{ A, B, C int }]string
+-	f.Fuzz(&myMap)
+-	fmt.Printf("myMap has %v element(s).\n", len(myMap))
+-	// Output:
+-	// myMap has 1 element(s).
+-}
+-
+-func ExampleSingle() {
+-	f := fuzz.New()
+-	var i int
+-	f.Fuzz(&i)
+-
+-	// Technically, we'd expect this to fail one out of 2 billion attempts...
+-	fmt.Printf("(i == 0) == %v", i == 0)
+-	// Output:
+-	// (i == 0) == false
+-}
+-
+-func ExampleEnum() {
+-	type MyEnum string
+-	const (
+-		A MyEnum = "A"
+-		B MyEnum = "B"
+-	)
+-	type MyInfo struct {
+-		Type  MyEnum
+-		AInfo *string
+-		BInfo *string
+-	}
+-
+-	f := fuzz.New().NilChance(0).Funcs(
+-		func(e *MyInfo, c fuzz.Continue) {
+-			// Note c's embedded Rand allows for direct use.
+-			// We could also use c.RandBool() here.
+-			switch c.Intn(2) {
+-			case 0:
+-				e.Type = A
+-				c.Fuzz(&e.AInfo)
+-			case 1:
+-				e.Type = B
+-				c.Fuzz(&e.BInfo)
+-			}
+-		},
+-	)
+-
+-	for i := 0; i < 100; i++ {
+-		var myObject MyInfo
+-		f.Fuzz(&myObject)
+-		switch myObject.Type {
+-		case A:
+-			if myObject.AInfo == nil {
+-				fmt.Println("AInfo should have been set!")
+-			}
+-			if myObject.BInfo != nil {
+-				fmt.Println("BInfo should NOT have been set!")
+-			}
+-		case B:
+-			if myObject.BInfo == nil {
+-				fmt.Println("BInfo should have been set!")
+-			}
+-			if myObject.AInfo != nil {
+-				fmt.Println("AInfo should NOT have been set!")
+-			}
+-		default:
+-			fmt.Println("Invalid enum value!")
+-		}
+-	}
+-	// Output:
+-}
+diff --git a/Godeps/_workspace/src/github.com/google/gofuzz/fuzz.go b/Godeps/_workspace/src/github.com/google/gofuzz/fuzz.go
+deleted file mode 100644
+index 31c2838..0000000
+--- a/Godeps/_workspace/src/github.com/google/gofuzz/fuzz.go
++++ /dev/null
+@@ -1,366 +0,0 @@
+-/*
+-Copyright 2014 Google Inc. All rights reserved.
+-
+-Licensed under the Apache License, Version 2.0 (the "License");
+-you may not use this file except in compliance with the License.
+-You may obtain a copy of the License at
+-
+-    http://www.apache.org/licenses/LICENSE-2.0
+-
+-Unless required by applicable law or agreed to in writing, software
+-distributed under the License is distributed on an "AS IS" BASIS,
+-WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-See the License for the specific language governing permissions and
+-limitations under the License.
+-*/
+-
+-package fuzz
+-
+-import (
+-	"fmt"
+-	"math/rand"
+-	"reflect"
+-	"time"
+-)
+-
+-// fuzzFuncMap is a map from a type to a fuzzFunc that handles that type.
+-type fuzzFuncMap map[reflect.Type]reflect.Value
+-
+-// Fuzzer knows how to fill any object with random fields.
+-type Fuzzer struct {
+-	fuzzFuncs   fuzzFuncMap
+-	r           *rand.Rand
+-	nilChance   float64
+-	minElements int
+-	maxElements int
+-}
+-
+-// New returns a new Fuzzer. Customize your Fuzzer further by calling Funcs,
+-// RandSource, NilChance, or NumElements in any order.
+-func New() *Fuzzer {
+-	f := &Fuzzer{
+-		fuzzFuncs:   fuzzFuncMap{},
+-		r:           rand.New(rand.NewSource(time.Now().UnixNano())),
+-		nilChance:   .2,
+-		minElements: 1,
+-		maxElements: 10,
+-	}
+-	return f
+-}
+-
+-// Funcs adds each entry in fuzzFuncs as a custom fuzzing function.
+-//
+-// Each entry in fuzzFuncs must be a function taking two parameters.
+-// The first parameter must be a pointer or map. It is the variable that
+-// function will fill with random data. The second parameter must be a
+-// fuzz.Continue, which will provide a source of randomness and a way
+-// to automatically continue fuzzing smaller pieces of the first parameter.
+-//
+-// These functions are called sensibly, e.g., if you wanted custom string
+-// fuzzing, the function `func(s *string, c fuzz.Continue)` would get
+-// called and passed the address of strings. Maps and pointers will always
+-// be made/new'd for you, ignoring the NilChange option. For slices, it
+-// doesn't make much sense to  pre-create them--Fuzzer doesn't know how
+-// long you want your slice--so take a pointer to a slice, and make it
+-// yourself. (If you don't want your map/pointer type pre-made, take a
+-// pointer to it, and make it yourself.) See the examples for a range of
+-// custom functions.
+-func (f *Fuzzer) Funcs(fuzzFuncs ...interface{}) *Fuzzer {
+-	for i := range fuzzFuncs {
+-		v := reflect.ValueOf(fuzzFuncs[i])
+-		if v.Kind() != reflect.Func {
+-			panic("Need only funcs!")
+-		}
+-		t := v.Type()
+-		if t.NumIn() != 2 || t.NumOut() != 0 {
+-			panic("Need 2 in and 0 out params!")
+-		}
+-		argT := t.In(0)
+-		switch argT.Kind() {
+-		case reflect.Ptr, reflect.Map:
+-		default:
+-			panic("fuzzFunc must take pointer or map type")
+-		}
+-		if t.In(1) != reflect.TypeOf(Continue{}) {
+-			panic("fuzzFunc's second parameter must be type fuzz.Continue")
+-		}
+-		f.fuzzFuncs[argT] = v
+-	}
+-	return f
+-}
+-
+-// RandSource causes f to get values from the given source of randomness.
+-// Use if you want deterministic fuzzing.
+-func (f *Fuzzer) RandSource(s rand.Source) *Fuzzer {
+-	f.r = rand.New(s)
+-	return f
+-}
+-
+-// NilChance sets the probability of creating a nil pointer, map, or slice to
+-// 'p'. 'p' should be between 0 (no nils) and 1 (all nils), inclusive.
+-func (f *Fuzzer) NilChance(p float64) *Fuzzer {
+-	if p < 0 || p > 1 {
+-		panic("p should be between 0 and 1, inclusive.")
+-	}
+-	f.nilChance = p
+-	return f
+-}
+-
+-// NumElements sets the minimum and maximum number of elements that will be
+-// added to a non-nil map or slice.
+-func (f *Fuzzer) NumElements(atLeast, atMost int) *Fuzzer {
+-	if atLeast > atMost {
+-		panic("atLeast must be <= atMost")
+-	}
+-	if atLeast < 0 {
+-		panic("atLeast must be >= 0")
+-	}
+-	f.minElements = atLeast
+-	f.maxElements = atMost
+-	return f
+-}
+-
+-func (f *Fuzzer) genElementCount() int {
+-	if f.minElements == f.maxElements {
+-		return f.minElements
+-	}
+-	return f.minElements + f.r.Intn(f.maxElements-f.minElements)
+-}
+-
+-func (f *Fuzzer) genShouldFill() bool {
+-	return f.r.Float64() > f.nilChance
+-}
+-
+-// Fuzz recursively fills all of obj's fields with something random.
+-// Not safe for cyclic or tree-like structs!
+-// obj must be a pointer. Only exported (public) fields can be set (thanks, golang :/ )
+-// Intended for tests, so will panic on bad input or unimplemented fields.
+-func (f *Fuzzer) Fuzz(obj interface{}) {
+-	v := reflect.ValueOf(obj)
+-	if v.Kind() != reflect.Ptr {
+-		panic("needed ptr!")
+-	}
+-	v = v.Elem()
+-	f.doFuzz(v)
+-}
+-
+-func (f *Fuzzer) doFuzz(v reflect.Value) {
+-	if !v.CanSet() {
+-		return
+-	}
+-	// Check for both pointer and non-pointer custom functions.
+-	if v.CanAddr() && f.tryCustom(v.Addr()) {
+-		return
+-	}
+-	if f.tryCustom(v) {
+-		return
+-	}
+-	if fn, ok := fillFuncMap[v.Kind()]; ok {
+-		fn(v, f.r)
+-		return
+-	}
+-	switch v.Kind() {
+-	case reflect.Map:
+-		if f.genShouldFill() {
+-			v.Set(reflect.MakeMap(v.Type()))
+-			n := f.genElementCount()
+-			for i := 0; i < n; i++ {
+-				key := reflect.New(v.Type().Key()).Elem()
+-				f.doFuzz(key)
+-				val := reflect.New(v.Type().Elem()).Elem()
+-				f.doFuzz(val)
+-				v.SetMapIndex(key, val)
+-			}
+-			return
+-		}
+-		v.Set(reflect.Zero(v.Type()))
+-	case reflect.Ptr:
+-		if f.genShouldFill() {
+-			v.Set(reflect.New(v.Type().Elem()))
+-			f.doFuzz(v.Elem())
+-			return
+-		}
+-		v.Set(reflect.Zero(v.Type()))
+-	case reflect.Slice:
+-		if f.genShouldFill() {
+-			n := f.genElementCount()
+-			v.Set(reflect.MakeSlice(v.Type(), n, n))
+-			for i := 0; i < n; i++ {
+-				f.doFuzz(v.Index(i))
+-			}
+-			return
+-		}
+-		v.Set(reflect.Zero(v.Type()))
+-	case reflect.Struct:
+-		for i := 0; i < v.NumField(); i++ {
+-			f.doFuzz(v.Field(i))
+-		}
+-	case reflect.Array:
+-		fallthrough
+-	case reflect.Chan:
+-		fallthrough
+-	case reflect.Func:
+-		fallthrough
+-	case reflect.Interface:
+-		fallthrough
+-	default:
+-		panic(fmt.Sprintf("Can't handle %#v", v.Interface()))
+-	}
+-}
+-
+-// tryCustom searches for custom handlers, and returns true iff it finds a match
+-// and successfully randomizes v.
+-func (f *Fuzzer) tryCustom(v reflect.Value) bool {
+-	doCustom, ok := f.fuzzFuncs[v.Type()]
+-	if !ok {
+-		return false
+-	}
+-
+-	switch v.Kind() {
+-	case reflect.Ptr:
+-		if v.IsNil() {
+-			if !v.CanSet() {
+-				return false
+-			}
+-			v.Set(reflect.New(v.Type().Elem()))
+-		}
+-	case reflect.Map:
+-		if v.IsNil() {
+-			if !v.CanSet() {
+-				return false
+-			}
+-			v.Set(reflect.MakeMap(v.Type()))
+-		}
+-	default:
+-		return false
+-	}
+-
+-	doCustom.Call([]reflect.Value{v, reflect.ValueOf(Continue{
+-		f:    f,
+-		Rand: f.r,
+-	})})
+-	return true
+-}
+-
+-// Continue can be passed to custom fuzzing functions to allow them to use
+-// the correct source of randomness and to continue fuzzing their members.
+-type Continue struct {
+-	f *Fuzzer
+-
+-	// For convenience, Continue implements rand.Rand via embedding.
+-	// Use this for generating any randomness if you want your fuzzing
+-	// to be repeatable for a given seed.
+-	*rand.Rand
+-}
+-
+-// Fuzz continues fuzzing obj. obj must be a pointer.
+-func (c Continue) Fuzz(obj interface{}) {
+-	v := reflect.ValueOf(obj)
+-	if v.Kind() != reflect.Ptr {
+-		panic("needed ptr!")
+-	}
+-	v = v.Elem()
+-	c.f.doFuzz(v)
+-}
+-
+-// RandString makes a random string up to 20 characters long. The returned string
+-// may include a variety of (valid) UTF-8 encodings.
+-func (c Continue) RandString() string {
+-	return randString(c.Rand)
+-}
+-
+-// RandUint64 makes random 64 bit numbers.
+-// Weirdly, rand doesn't have a function that gives you 64 random bits.
+-func (c Continue) RandUint64() uint64 {
+-	return randUint64(c.Rand)
+-}
+-
+-// RandBool returns true or false randomly.
+-func (c Continue) RandBool() bool {
+-	return randBool(c.Rand)
+-}
+-
+-func fuzzInt(v reflect.Value, r *rand.Rand) {
+-	v.SetInt(int64(randUint64(r)))
+-}
+-
+-func fuzzUint(v reflect.Value, r *rand.Rand) {
+-	v.SetUint(randUint64(r))
+-}
+-
+-var fillFuncMap = map[reflect.Kind]func(reflect.Value, *rand.Rand){
+-	reflect.Bool: func(v reflect.Value, r *rand.Rand) {
+-		v.SetBool(randBool(r))
+-	},
+-	reflect.Int:     fuzzInt,
+-	reflect.Int8:    fuzzInt,
+-	reflect.Int16:   fuzzInt,
+-	reflect.Int32:   fuzzInt,
+-	reflect.Int64:   fuzzInt,
+-	reflect.Uint:    fuzzUint,
+-	reflect.Uint8:   fuzzUint,
+-	reflect.Uint16:  fuzzUint,
+-	reflect.Uint32:  fuzzUint,
+-	reflect.Uint64:  fuzzUint,
+-	reflect.Uintptr: fuzzUint,
+-	reflect.Float32: func(v reflect.Value, r *rand.Rand) {
+-		v.SetFloat(float64(r.Float32()))
+-	},
+-	reflect.Float64: func(v reflect.Value, r *rand.Rand) {
+-		v.SetFloat(r.Float64())
+-	},
+-	reflect.Complex64: func(v reflect.Value, r *rand.Rand) {
+-		panic("unimplemented")
+-	},
+-	reflect.Complex128: func(v reflect.Value, r *rand.Rand) {
+-		panic("unimplemented")
+-	},
+-	reflect.String: func(v reflect.Value, r *rand.Rand) {
+-		v.SetString(randString(r))
+-	},
+-	reflect.UnsafePointer: func(v reflect.Value, r *rand.Rand) {
+-		panic("unimplemented")
+-	},
+-}
+-
+-// randBool returns true or false randomly.
+-func randBool(r *rand.Rand) bool {
+-	if r.Int()&1 == 1 {
+-		return true
+-	}
+-	return false
+-}
+-
+-type charRange struct {
+-	first, last rune
+-}
+-
+-// choose returns a random unicode character from the given range, using the
+-// given randomness source.
+-func (r *charRange) choose(rand *rand.Rand) rune {
+-	count := int64(r.last - r.first)
+-	return r.first + rune(rand.Int63n(count))
+-}
+-
+-var unicodeRanges = []charRange{
+-	{' ', '~'},           // ASCII characters
+-	{'\u00a0', '\u02af'}, // Multi-byte encoded characters
+-	{'\u4e00', '\u9fff'}, // Common CJK (even longer encodings)
+-}
+-
+-// randString makes a random string up to 20 characters long. The returned string
+-// may include a variety of (valid) UTF-8 encodings.
+-func randString(r *rand.Rand) string {
+-	n := r.Intn(20)
+-	runes := make([]rune, n)
+-	for i := range runes {
+-		runes[i] = unicodeRanges[r.Intn(len(unicodeRanges))].choose(r)
+-	}
+-	return string(runes)
+-}
+-
+-// randUint64 makes random 64 bit numbers.
+-// Weirdly, rand doesn't have a function that gives you 64 random bits.
+-func randUint64(r *rand.Rand) uint64 {
+-	return uint64(r.Uint32())<<32 | uint64(r.Uint32())
+-}
+diff --git a/Godeps/_workspace/src/github.com/google/gofuzz/fuzz_test.go b/Godeps/_workspace/src/github.com/google/gofuzz/fuzz_test.go
+deleted file mode 100644
+index 4f0d4db..0000000
+--- a/Godeps/_workspace/src/github.com/google/gofuzz/fuzz_test.go
++++ /dev/null
+@@ -1,258 +0,0 @@
+-/*
+-Copyright 2014 Google Inc. All rights reserved.
+-
+-Licensed under the Apache License, Version 2.0 (the "License");
+-you may not use this file except in compliance with the License.
+-You may obtain a copy of the License at
+-
+-    http://www.apache.org/licenses/LICENSE-2.0
+-
+-Unless required by applicable law or agreed to in writing, software
+-distributed under the License is distributed on an "AS IS" BASIS,
+-WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-See the License for the specific language governing permissions and
+-limitations under the License.
+-*/
+-
+-package fuzz
+-
+-import (
+-	"reflect"
+-	"testing"
+-)
+-
+-func TestFuzz_basic(t *testing.T) {
+-	obj := &struct {
+-		I    int
+-		I8   int8
+-		I16  int16
+-		I32  int32
+-		I64  int64
+-		U    uint
+-		U8   uint8
+-		U16  uint16
+-		U32  uint32
+-		U64  uint64
+-		Uptr uintptr
+-		S    string
+-		B    bool
+-	}{}
+-
+-	failed := map[string]int{}
+-	for i := 0; i < 10; i++ {
+-		New().Fuzz(obj)
+-
+-		if n, v := "i", obj.I; v == 0 {
+-			failed[n] = failed[n] + 1
+-		}
+-		if n, v := "i8", obj.I8; v == 0 {
+-			failed[n] = failed[n] + 1
+-		}
+-		if n, v := "i16", obj.I16; v == 0 {
+-			failed[n] = failed[n] + 1
+-		}
+-		if n, v := "i32", obj.I32; v == 0 {
+-			failed[n] = failed[n] + 1
+-		}
+-		if n, v := "i64", obj.I64; v == 0 {
+-			failed[n] = failed[n] + 1
+-		}
+-		if n, v := "u", obj.U; v == 0 {
+-			failed[n] = failed[n] + 1
+-		}
+-		if n, v := "u8", obj.U8; v == 0 {
+-			failed[n] = failed[n] + 1
+-		}
+-		if n, v := "u16", obj.U16; v == 0 {
+-			failed[n] = failed[n] + 1
+-		}
+-		if n, v := "u32", obj.U32; v == 0 {
+-			failed[n] = failed[n] + 1
+-		}
+-		if n, v := "u64", obj.U64; v == 0 {
+-			failed[n] = failed[n] + 1
+-		}
+-		if n, v := "uptr", obj.Uptr; v == 0 {
+-			failed[n] = failed[n] + 1
+-		}
+-		if n, v := "s", obj.S; v == "" {
+-			failed[n] = failed[n] + 1
+-		}
+-		if n, v := "b", obj.B; v == false {
+-			failed[n] = failed[n] + 1
+-		}
+-	}
+-	checkFailed(t, failed)
+-}
+-
+-func checkFailed(t *testing.T, failed map[string]int) {
+-	for k, v := range failed {
+-		if v > 8 {
+-			t.Errorf("%v seems to not be getting set, was zero value %v times", k, v)
+-		}
+-	}
+-}
+-
+-func TestFuzz_structptr(t *testing.T) {
+-	obj := &struct {
+-		A *struct {
+-			S string
+-		}
+-	}{}
+-
+-	f := New().NilChance(.5)
+-	failed := map[string]int{}
+-	for i := 0; i < 10; i++ {
+-		f.Fuzz(obj)
+-
+-		if n, v := "a not nil", obj.A; v == nil {
+-			failed[n] = failed[n] + 1
+-		}
+-		if n, v := "a nil", obj.A; v != nil {
+-			failed[n] = failed[n] + 1
+-		}
+-		if n, v := "as", obj.A; v == nil || v.S == "" {
+-			failed[n] = failed[n] + 1
+-		}
+-	}
+-	checkFailed(t, failed)
+-}
+-
+-// tryFuzz tries fuzzing up to 20 times. Fail if check() never passes, report the highest
+-// stage it ever got to.
+-func tryFuzz(t *testing.T, f *Fuzzer, obj interface{}, check func() (stage int, passed bool)) {
+-	maxStage := 0
+-	for i := 0; i < 20; i++ {
+-		f.Fuzz(obj)
+-		stage, passed := check()
+-		if stage > maxStage {
+-			maxStage = stage
+-		}
+-		if passed {
+-			return
+-		}
+-	}
+-	t.Errorf("Only ever got to stage %v", maxStage)
+-}
+-
+-func TestFuzz_structmap(t *testing.T) {
+-	obj := &struct {
+-		A map[struct {
+-			S string
+-		}]struct {
+-			S2 string
+-		}
+-		B map[string]string
+-	}{}
+-
+-	tryFuzz(t, New(), obj, func() (int, bool) {
+-		if obj.A == nil {
+-			return 1, false
+-		}
+-		if len(obj.A) == 0 {
+-			return 2, false
+-		}
+-		for k, v := range obj.A {
+-			if k.S == "" {
+-				return 3, false
+-			}
+-			if v.S2 == "" {
+-				return 4, false
+-			}
+-		}
+-
+-		if obj.B == nil {
+-			return 5, false
+-		}
+-		if len(obj.B) == 0 {
+-			return 6, false
+-		}
+-		for k, v := range obj.B {
+-			if k == "" {
+-				return 7, false
+-			}
+-			if v == "" {
+-				return 8, false
+-			}
+-		}
+-		return 9, true
+-	})
+-}
+-
+-func TestFuzz_structslice(t *testing.T) {
+-	obj := &struct {
+-		A []struct {
+-			S string
+-		}
+-		B []string
+-	}{}
+-
+-	tryFuzz(t, New(), obj, func() (int, bool) {
+-		if obj.A == nil {
+-			return 1, false
+-		}
+-		if len(obj.A) == 0 {
+-			return 2, false
+-		}
+-		for _, v := range obj.A {
+-			if v.S == "" {
+-				return 3, false
+-			}
+-		}
+-
+-		if obj.B == nil {
+-			return 4, false
+-		}
+-		if len(obj.B) == 0 {
+-			return 5, false
+-		}
+-		for _, v := range obj.B {
+-			if v == "" {
+-				return 6, false
+-			}
+-		}
+-		return 7, true
+-	})
+-}
+-
+-func TestFuzz_custom(t *testing.T) {
+-	obj := &struct {
+-		A string
+-		B *string
+-		C map[string]string
+-		D *map[string]string
+-	}{}
+-
+-	testPhrase := "gotcalled"
+-	testMap := map[string]string{"C": "D"}
+-	f := New().Funcs(
+-		func(s *string, c Continue) {
+-			*s = testPhrase
+-		},
+-		func(m map[string]string, c Continue) {
+-			m["C"] = "D"
+-		},
+-	)
+-
+-	tryFuzz(t, f, obj, func() (int, bool) {
+-		if obj.A != testPhrase {
+-			return 1, false
+-		}
+-		if obj.B == nil {
+-			return 2, false
+-		}
+-		if *obj.B != testPhrase {
+-			return 3, false
+-		}
+-		if e, a := testMap, obj.C; !reflect.DeepEqual(e, a) {
+-			return 4, false
+-		}
+-		if obj.D == nil {
+-			return 5, false
+-		}
+-		if e, a := testMap, *obj.D; !reflect.DeepEqual(e, a) {
+-			return 6, false
+-		}
+-		return 7, true
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/imdario/mergo/.travis.yml b/Godeps/_workspace/src/github.com/imdario/mergo/.travis.yml
+deleted file mode 100644
+index 9d91c63..0000000
+--- a/Godeps/_workspace/src/github.com/imdario/mergo/.travis.yml
++++ /dev/null
+@@ -1,2 +0,0 @@
+-language: go
+-install: go get -t
+diff --git a/Godeps/_workspace/src/github.com/imdario/mergo/LICENSE b/Godeps/_workspace/src/github.com/imdario/mergo/LICENSE
+deleted file mode 100644
+index 6866802..0000000
+--- a/Godeps/_workspace/src/github.com/imdario/mergo/LICENSE
++++ /dev/null
+@@ -1,28 +0,0 @@
+-Copyright (c) 2013 Dario Castañé. All rights reserved.
+-Copyright (c) 2012 The Go Authors. All rights reserved.
+-
+-Redistribution and use in source and binary forms, with or without
+-modification, are permitted provided that the following conditions are
+-met:
+-
+-   * Redistributions of source code must retain the above copyright
+-notice, this list of conditions and the following disclaimer.
+-   * Redistributions in binary form must reproduce the above
+-copyright notice, this list of conditions and the following disclaimer
+-in the documentation and/or other materials provided with the
+-distribution.
+-   * Neither the name of Google Inc. nor the names of its
+-contributors may be used to endorse or promote products derived from
+-this software without specific prior written permission.
+-
+-THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+-"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+-LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+-A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+-OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+-SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+-LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+-DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+-THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+-(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+-OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+diff --git a/Godeps/_workspace/src/github.com/imdario/mergo/README.md b/Godeps/_workspace/src/github.com/imdario/mergo/README.md
+deleted file mode 100644
+index cdcea0f..0000000
+--- a/Godeps/_workspace/src/github.com/imdario/mergo/README.md
++++ /dev/null
+@@ -1,68 +0,0 @@
+-# Mergo
+-
+-A helper to merge structs and maps in Golang. Useful for configuration default values, avoiding messy if-statements.
+-
+-Also a lovely [comune](http://en.wikipedia.org/wiki/Mergo) (municipality) in the Province of Ancona in the Italian region Marche.
+-
+-![Mergo dall'alto](http://www.comune.mergo.an.it/Siti/Mergo/Immagini/Foto/mergo_dall_alto.jpg)
+-
+-## Status
+-
+-It is ready for production use. It works fine although it may use more of testing. Here some projects in the wild using Mergo:
+-
+-- [EagerIO/Stout](https://github.com/EagerIO/Stout)
+-- [lynndylanhurley/defsynth-api](https://github.com/lynndylanhurley/defsynth-api)
+-- [russross/canvasassignments](https://github.com/russross/canvasassignments)
+-- [rdegges/cryptly-api](https://github.com/rdegges/cryptly-api)
+-- [casualjim/exeggutor](https://github.com/casualjim/exeggutor)
+-- [divshot/gitling](https://github.com/divshot/gitling)
+-- [RWJMurphy/gorl](https://github.com/RWJMurphy/gorl)
+-
+-[![Build Status][1]][2]
+-[![GoDoc](https://godoc.org/github.com/imdario/mergo?status.svg)](https://godoc.org/github.com/imdario/mergo)
+-
+-[1]: https://travis-ci.org/imdario/mergo.png
+-[2]: https://travis-ci.org/imdario/mergo
+-
+-## Installation
+-
+-    go get github.com/imdario/mergo
+-
+-    // use in your .go code
+-    import (
+-        "github.com/imdario/mergo"
+-    )
+-
+-## Usage
+-
+-You can only merge same-type structs with exported fields initialized as zero value of their type and same-types maps. Mergo won't merge unexported (private) fields but will do recursively any exported one. Also maps will be merged recursively except for structs inside maps (because they are not addressable using Go reflection).
+-
+-    if err := mergo.Merge(&dst, src); err != nil {
+-        // ...
+-    }
+-
+-Additionally, you can map a map[string]interface{} to a struct (and otherwise, from struct to map), following the same restrictions as in Merge(). Keys are capitalized to find each corresponding exported field.
+-
+-    if err := mergo.Map(&dst, srcMap); err != nil {
+-        // ...
+-    }
+-
+-Warning: if you map a struct to map, it won't do it recursively. Don't expect Mergo to map struct members of your struct as map[string]interface{}. They will be just assigned as values.
+-
+-More information and examples in [godoc documentation](http://godoc.org/github.com/imdario/mergo).
+-
+-Note: if test are failing due missing package, please execute:
+-
+-    go get gopkg.in/yaml.v1
+-
+-## Contact me
+-
+-If I can help you, you have an idea or you are using Mergo in your projects, don't hesitate to drop me a line (or a pull request): [@im_dario](https://twitter.com/im_dario)
+-
+-## About
+-
+-Written by [Dario Castañé](http://dario.im).
+-
+-## License
+-
+-[BSD 3-Clause](http://opensource.org/licenses/BSD-3-Clause) license, as [Go language](http://golang.org/LICENSE).
+diff --git a/Godeps/_workspace/src/github.com/imdario/mergo/doc.go b/Godeps/_workspace/src/github.com/imdario/mergo/doc.go
+deleted file mode 100644
+index 6e9aa7b..0000000
+--- a/Godeps/_workspace/src/github.com/imdario/mergo/doc.go
++++ /dev/null
+@@ -1,44 +0,0 @@
+-// Copyright 2013 Dario Castañé. All rights reserved.
+-// Copyright 2009 The Go 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 mergo merges same-type structs and maps by setting default values in zero-value fields.
+-
+-Mergo won't merge unexported (private) fields but will do recursively any exported one. It also won't merge structs inside maps (because they are not addressable using Go reflection).
+-
+-Usage
+-
+-From my own work-in-progress project:
+-
+-	type networkConfig struct {
+-		Protocol string
+-		Address string
+-		ServerType string `json: "server_type"`
+-		Port uint16
+-	}
+-
+-	type FssnConfig struct {
+-		Network networkConfig
+-	}
+-
+-	var fssnDefault = FssnConfig {
+-		networkConfig {
+-			"tcp",
+-			"127.0.0.1",
+-			"http",
+-			31560,
+-		},
+-	}
+-
+-	// Inside a function [...]
+-
+-	if err := mergo.Merge(&config, fssnDefault); err != nil {
+-		log.Fatal(err)
+-	}
+-
+-	// More code [...]
+-
+-*/
+-package mergo
+diff --git a/Godeps/_workspace/src/github.com/imdario/mergo/map.go b/Godeps/_workspace/src/github.com/imdario/mergo/map.go
+deleted file mode 100644
+index 44361e8..0000000
+--- a/Godeps/_workspace/src/github.com/imdario/mergo/map.go
++++ /dev/null
+@@ -1,146 +0,0 @@
+-// Copyright 2014 Dario Castañé. All rights reserved.
+-// Copyright 2009 The Go Authors. All rights reserved.
+-// Use of this source code is governed by a BSD-style
+-// license that can be found in the LICENSE file.
+-
+-// Based on src/pkg/reflect/deepequal.go from official
+-// golang's stdlib.
+-
+-package mergo
+-
+-import (
+-	"fmt"
+-	"reflect"
+-	"unicode"
+-	"unicode/utf8"
+-)
+-
+-func changeInitialCase(s string, mapper func(rune) rune) string {
+-	if s == "" {
+-		return s
+-	}
+-	r, n := utf8.DecodeRuneInString(s)
+-	return string(mapper(r)) + s[n:]
+-}
+-
+-func isExported(field reflect.StructField) bool {
+-	r, _ := utf8.DecodeRuneInString(field.Name)
+-	return r >= 'A' && r <= 'Z'
+-}
+-
+-// Traverses recursively both values, assigning src's fields values to dst.
+-// The map argument tracks comparisons that have already been seen, which allows
+-// short circuiting on recursive types.
+-func deepMap(dst, src reflect.Value, visited map[uintptr]*visit, depth int) (err error) {
+-	if dst.CanAddr() {
+-		addr := dst.UnsafeAddr()
+-		h := 17 * addr
+-		seen := visited[h]
+-		typ := dst.Type()
+-		for p := seen; p != nil; p = p.next {
+-			if p.ptr == addr && p.typ == typ {
+-				return nil
+-			}
+-		}
+-		// Remember, remember...
+-		visited[h] = &visit{addr, typ, seen}
+-	}
+-	zeroValue := reflect.Value{}
+-	switch dst.Kind() {
+-	case reflect.Map:
+-		dstMap := dst.Interface().(map[string]interface{})
+-		for i, n := 0, src.NumField(); i < n; i++ {
+-			srcType := src.Type()
+-			field := srcType.Field(i)
+-			if !isExported(field) {
+-				continue
+-			}
+-			fieldName := field.Name
+-			fieldName = changeInitialCase(fieldName, unicode.ToLower)
+-			if v, ok := dstMap[fieldName]; !ok || isEmptyValue(reflect.ValueOf(v)) {
+-				dstMap[fieldName] = src.Field(i).Interface()
+-			}
+-		}
+-	case reflect.Struct:
+-		srcMap := src.Interface().(map[string]interface{})
+-		for key := range srcMap {
+-			srcValue := srcMap[key]
+-			fieldName := changeInitialCase(key, unicode.ToUpper)
+-			dstElement := dst.FieldByName(fieldName)
+-			if dstElement == zeroValue {
+-				// We discard it because the field doesn't exist.
+-				continue
+-			}
+-			srcElement := reflect.ValueOf(srcValue)
+-			dstKind := dstElement.Kind()
+-			srcKind := srcElement.Kind()
+-			if srcKind == reflect.Ptr && dstKind != reflect.Ptr {
+-				srcElement = srcElement.Elem()
+-				srcKind = reflect.TypeOf(srcElement.Interface()).Kind()
+-			} else if dstKind == reflect.Ptr {
+-				// Can this work? I guess it can't.
+-				if srcKind != reflect.Ptr && srcElement.CanAddr() {
+-					srcPtr := srcElement.Addr()
+-					srcElement = reflect.ValueOf(srcPtr)
+-					srcKind = reflect.Ptr
+-				}
+-			}
+-			if !srcElement.IsValid() {
+-				continue
+-			}
+-			if srcKind == dstKind {
+-				if err = deepMerge(dstElement, srcElement, visited, depth+1); err != nil {
+-					return
+-				}
+-			} else {
+-				if srcKind == reflect.Map {
+-					if err = deepMap(dstElement, srcElement, visited, depth+1); err != nil {
+-						return
+-					}
+-				} else {
+-					return fmt.Errorf("type mismatch on %s field: found %v, expected %v", fieldName, srcKind, dstKind)
+-				}
+-			}
+-		}
+-	}
+-	return
+-}
+-
+-// Map sets fields' values in dst from src.
+-// src can be a map with string keys or a struct. dst must be the opposite:
+-// if src is a map, dst must be a valid pointer to struct. If src is a struct,
+-// dst must be map[string]interface{}.
+-// It won't merge unexported (private) fields and will do recursively
+-// any exported field.
+-// If dst is a map, keys will be src fields' names in lower camel case.
+-// Missing key in src that doesn't match a field in dst will be skipped. This
+-// doesn't apply if dst is a map.
+-// This is separated method from Merge because it is cleaner and it keeps sane
+-// semantics: merging equal types, mapping different (restricted) types.
+-func Map(dst, src interface{}) error {
+-	var (
+-		vDst, vSrc reflect.Value
+-		err        error
+-	)
+-	if vDst, vSrc, err = resolveValues(dst, src); err != nil {
+-		return err
+-	}
+-	// To be friction-less, we redirect equal-type arguments
+-	// to deepMerge. Only because arguments can be anything.
+-	if vSrc.Kind() == vDst.Kind() {
+-		return deepMerge(vDst, vSrc, make(map[uintptr]*visit), 0)
+-	}
+-	switch vSrc.Kind() {
+-	case reflect.Struct:
+-		if vDst.Kind() != reflect.Map {
+-			return ErrExpectedMapAsDestination
+-		}
+-	case reflect.Map:
+-		if vDst.Kind() != reflect.Struct {
+-			return ErrExpectedStructAsDestination
+-		}
+-	default:
+-		return ErrNotSupported
+-	}
+-	return deepMap(vDst, vSrc, make(map[uintptr]*visit), 0)
+-}
+diff --git a/Godeps/_workspace/src/github.com/imdario/mergo/merge.go b/Godeps/_workspace/src/github.com/imdario/mergo/merge.go
+deleted file mode 100644
+index 5d328b1..0000000
+--- a/Godeps/_workspace/src/github.com/imdario/mergo/merge.go
++++ /dev/null
+@@ -1,99 +0,0 @@
+-// Copyright 2013 Dario Castañé. All rights reserved.
+-// Copyright 2009 The Go Authors. All rights reserved.
+-// Use of this source code is governed by a BSD-style
+-// license that can be found in the LICENSE file.
+-
+-// Based on src/pkg/reflect/deepequal.go from official
+-// golang's stdlib.
+-
+-package mergo
+-
+-import (
+-	"reflect"
+-)
+-
+-// Traverses recursively both values, assigning src's fields values to dst.
+-// The map argument tracks comparisons that have already been seen, which allows
+-// short circuiting on recursive types.
+-func deepMerge(dst, src reflect.Value, visited map[uintptr]*visit, depth int) (err error) {
+-	if !src.IsValid() {
+-		return
+-	}
+-	if dst.CanAddr() {
+-		addr := dst.UnsafeAddr()
+-		h := 17 * addr
+-		seen := visited[h]
+-		typ := dst.Type()
+-		for p := seen; p != nil; p = p.next {
+-			if p.ptr == addr && p.typ == typ {
+-				return nil
+-			}
+-		}
+-		// Remember, remember...
+-		visited[h] = &visit{addr, typ, seen}
+-	}
+-	switch dst.Kind() {
+-	case reflect.Struct:
+-		for i, n := 0, dst.NumField(); i < n; i++ {
+-			if err = deepMerge(dst.Field(i), src.Field(i), visited, depth+1); err != nil {
+-				return
+-			}
+-		}
+-	case reflect.Map:
+-		for _, key := range src.MapKeys() {
+-			srcElement := src.MapIndex(key)
+-			if !srcElement.IsValid() {
+-				continue
+-			}
+-			dstElement := dst.MapIndex(key)
+-			switch reflect.TypeOf(srcElement.Interface()).Kind() {
+-			case reflect.Struct:
+-				fallthrough
+-			case reflect.Map:
+-				if err = deepMerge(dstElement, srcElement, visited, depth+1); err != nil {
+-					return
+-				}
+-			}
+-			if !dstElement.IsValid() {
+-				dst.SetMapIndex(key, srcElement)
+-			}
+-		}
+-	case reflect.Ptr:
+-		fallthrough
+-	case reflect.Interface:
+-		if src.IsNil() {
+-			break
+-		} else if dst.IsNil() {
+-			if dst.CanSet() && isEmptyValue(dst) {
+-				dst.Set(src)
+-			}
+-		} else if err = deepMerge(dst.Elem(), src.Elem(), visited, depth+1); err != nil {
+-			return
+-		}
+-	default:
+-		if dst.CanSet() && !isEmptyValue(src) {
+-			dst.Set(src)
+-		}
+-	}
+-	return
+-}
+-
+-// Merge sets fields' values in dst from src if they have a zero
+-// value of their type.
+-// dst and src must be valid same-type structs and dst must be
+-// a pointer to struct.
+-// It won't merge unexported (private) fields and will do recursively
+-// any exported field.
+-func Merge(dst, src interface{}) error {
+-	var (
+-		vDst, vSrc reflect.Value
+-		err        error
+-	)
+-	if vDst, vSrc, err = resolveValues(dst, src); err != nil {
+-		return err
+-	}
+-	if vDst.Type() != vSrc.Type() {
+-		return ErrDifferentArgumentsTypes
+-	}
+-	return deepMerge(vDst, vSrc, make(map[uintptr]*visit), 0)
+-}
+diff --git a/Godeps/_workspace/src/github.com/imdario/mergo/mergo.go b/Godeps/_workspace/src/github.com/imdario/mergo/mergo.go
+deleted file mode 100644
+index f8a0991..0000000
+--- a/Godeps/_workspace/src/github.com/imdario/mergo/mergo.go
++++ /dev/null
+@@ -1,90 +0,0 @@
+-// Copyright 2013 Dario Castañé. All rights reserved.
+-// Copyright 2009 The Go Authors. All rights reserved.
+-// Use of this source code is governed by a BSD-style
+-// license that can be found in the LICENSE file.
+-
+-// Based on src/pkg/reflect/deepequal.go from official
+-// golang's stdlib.
+-
+-package mergo
+-
+-import (
+-	"errors"
+-	"reflect"
+-)
+-
+-// Errors reported by Mergo when it finds invalid arguments.
+-var (
+-	ErrNilArguments                = errors.New("src and dst must not be nil")
+-	ErrDifferentArgumentsTypes     = errors.New("src and dst must be of same type")
+-	ErrNotSupported                = errors.New("only structs and maps are supported")
+-	ErrExpectedMapAsDestination    = errors.New("dst was expected to be a map")
+-	ErrExpectedStructAsDestination = errors.New("dst was expected to be a struct")
+-)
+-
+-// During deepMerge, must keep track of checks that are
+-// in progress.  The comparison algorithm assumes that all
+-// checks in progress are true when it reencounters them.
+-// Visited are stored in a map indexed by 17 * a1 + a2;
+-type visit struct {
+-	ptr  uintptr
+-	typ  reflect.Type
+-	next *visit
+-}
+-
+-// From src/pkg/encoding/json.
+-func isEmptyValue(v reflect.Value) bool {
+-	switch v.Kind() {
+-	case reflect.Array, reflect.Map, reflect.Slice, reflect.String:
+-		return v.Len() == 0
+-	case reflect.Bool:
+-		return !v.Bool()
+-	case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
+-		return v.Int() == 0
+-	case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
+-		return v.Uint() == 0
+-	case reflect.Float32, reflect.Float64:
+-		return v.Float() == 0
+-	case reflect.Interface, reflect.Ptr:
+-		return v.IsNil()
+-	}
+-	return false
+-}
+-
+-func resolveValues(dst, src interface{}) (vDst, vSrc reflect.Value, err error) {
+-	if dst == nil || src == nil {
+-		err = ErrNilArguments
+-		return
+-	}
+-	vDst = reflect.ValueOf(dst).Elem()
+-	if vDst.Kind() != reflect.Struct && vDst.Kind() != reflect.Map {
+-		err = ErrNotSupported
+-		return
+-	}
+-	vSrc = reflect.ValueOf(src)
+-	// We check if vSrc is a pointer to dereference it.
+-	if vSrc.Kind() == reflect.Ptr {
+-		vSrc = vSrc.Elem()
+-	}
+-	return
+-}
+-
+-// Traverses recursively both values, assigning src's fields values to dst.
+-// The map argument tracks comparisons that have already been seen, which allows
+-// short circuiting on recursive types.
+-func deeper(dst, src reflect.Value, visited map[uintptr]*visit, depth int) (err error) {
+-	if dst.CanAddr() {
+-		addr := dst.UnsafeAddr()
+-		h := 17 * addr
+-		seen := visited[h]
+-		typ := dst.Type()
+-		for p := seen; p != nil; p = p.next {
+-			if p.ptr == addr && p.typ == typ {
+-				return nil
+-			}
+-		}
+-		// Remember, remember...
+-		visited[h] = &visit{addr, typ, seen}
+-	}
+-	return // TODO refactor
+-}
+diff --git a/Godeps/_workspace/src/github.com/imdario/mergo/mergo_test.go b/Godeps/_workspace/src/github.com/imdario/mergo/mergo_test.go
+deleted file mode 100644
+index 072bddb..0000000
+--- a/Godeps/_workspace/src/github.com/imdario/mergo/mergo_test.go
++++ /dev/null
+@@ -1,288 +0,0 @@
+-// Copyright 2013 Dario Castañé. All rights reserved.
+-// Copyright 2009 The Go 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 mergo
+-
+-import (
+-	"gopkg.in/yaml.v1"
+-	"io/ioutil"
+-	"reflect"
+-	"testing"
+-)
+-
+-type simpleTest struct {
+-	Value int
+-}
+-
+-type complexTest struct {
+-	St simpleTest
+-	sz int
+-	Id string
+-}
+-
+-type moreComplextText struct {
+-	Ct complexTest
+-	St simpleTest
+-	Nt simpleTest
+-}
+-
+-type pointerTest struct {
+-	C *simpleTest
+-}
+-
+-type sliceTest struct {
+-	S []int
+-}
+-
+-func TestNil(t *testing.T) {
+-	if err := Merge(nil, nil); err != ErrNilArguments {
+-		t.Fail()
+-	}
+-}
+-
+-func TestDifferentTypes(t *testing.T) {
+-	a := simpleTest{42}
+-	b := 42
+-	if err := Merge(&a, b); err != ErrDifferentArgumentsTypes {
+-		t.Fail()
+-	}
+-}
+-
+-func TestSimpleStruct(t *testing.T) {
+-	a := simpleTest{}
+-	b := simpleTest{42}
+-	if err := Merge(&a, b); err != nil {
+-		t.FailNow()
+-	}
+-	if a.Value != 42 {
+-		t.Fatalf("b not merged in a properly: a.Value(%d) != b.Value(%d)", a.Value, b.Value)
+-	}
+-	if !reflect.DeepEqual(a, b) {
+-		t.FailNow()
+-	}
+-}
+-
+-func TestComplexStruct(t *testing.T) {
+-	a := complexTest{}
+-	a.Id = "athing"
+-	b := complexTest{simpleTest{42}, 1, "bthing"}
+-	if err := Merge(&a, b); err != nil {
+-		t.FailNow()
+-	}
+-	if a.St.Value != 42 {
+-		t.Fatalf("b not merged in a properly: a.St.Value(%d) != b.St.Value(%d)", a.St.Value, b.St.Value)
+-	}
+-	if a.sz == 1 {
+-		t.Fatalf("a's private field sz not preserved from merge: a.sz(%d) == b.sz(%d)", a.sz, b.sz)
+-	}
+-	if a.Id != b.Id {
+-		t.Fatalf("a's field Id not merged properly: a.Id(%s) != b.Id(%s)", a.Id, b.Id)
+-	}
+-}
+-
+-func TestPointerStruct(t *testing.T) {
+-	s1 := simpleTest{}
+-	s2 := simpleTest{19}
+-	a := pointerTest{&s1}
+-	b := pointerTest{&s2}
+-	if err := Merge(&a, b); err != nil {
+-		t.FailNow()
+-	}
+-	if a.C.Value != b.C.Value {
+-		//t.Fatalf("b not merged in a properly: a.C.Value(%d) != b.C.Value(%d)", a.C.Value, b.C.Value)
+-	}
+-}
+-
+-func TestPointerStructNil(t *testing.T) {
+-	a := pointerTest{nil}
+-	b := pointerTest{&simpleTest{19}}
+-	if err := Merge(&a, b); err != nil {
+-		t.FailNow()
+-	}
+-	if a.C.Value != b.C.Value {
+-		t.Fatalf("b not merged in a properly: a.C.Value(%d) != b.C.Value(%d)", a.C.Value, b.C.Value)
+-	}
+-}
+-
+-func TestSliceStruct(t *testing.T) {
+-	a := sliceTest{}
+-	b := sliceTest{[]int{1, 2, 3}}
+-	if err := Merge(&a, b); err != nil {
+-		t.FailNow()
+-	}
+-	if len(b.S) != 3 {
+-		t.FailNow()
+-	}
+-	if len(a.S) != len(b.S) {
+-		t.Fatalf("b not merged in a properly %d != %d", len(a.S), len(b.S))
+-	}
+-
+-	a = sliceTest{[]int{1}}
+-	b = sliceTest{[]int{1, 2, 3}}
+-	if err := Merge(&a, b); err != nil {
+-		t.FailNow()
+-	}
+-	if len(b.S) != 3 {
+-		t.FailNow()
+-	}
+-	if len(a.S) != len(b.S) {
+-		t.Fatalf("b not merged in a properly %d != %d", len(a.S), len(b.S))
+-	}
+-}
+-
+-func TestMaps(t *testing.T) {
+-	m := map[string]simpleTest{
+-		"a": simpleTest{},
+-		"b": simpleTest{42},
+-	}
+-	n := map[string]simpleTest{
+-		"a": simpleTest{16},
+-		"b": simpleTest{},
+-		"c": simpleTest{12},
+-	}
+-	if err := Merge(&m, n); err != nil {
+-		t.Fatalf(err.Error())
+-	}
+-	if len(m) != 3 {
+-		t.Fatalf(`n not merged in m properly, m must have 3 elements instead of %d`, len(m))
+-	}
+-	if m["a"].Value != 0 {
+-		t.Fatalf(`n merged in m because I solved non-addressable map values TODO: m["a"].Value(%d) != n["a"].Value(%d)`, m["a"].Value, n["a"].Value)
+-	}
+-	if m["b"].Value != 42 {
+-		t.Fatalf(`n wrongly merged in m: m["b"].Value(%d) != n["b"].Value(%d)`, m["b"].Value, n["b"].Value)
+-	}
+-	if m["c"].Value != 12 {
+-		t.Fatalf(`n not merged in m: m["c"].Value(%d) != n["c"].Value(%d)`, m["c"].Value, n["c"].Value)
+-	}
+-}
+-
+-func TestYAMLMaps(t *testing.T) {
+-	thing := loadYAML("testdata/thing.yml")
+-	license := loadYAML("testdata/license.yml")
+-	ft := thing["fields"].(map[interface{}]interface{})
+-	fl := license["fields"].(map[interface{}]interface{})
+-	expectedLength := len(ft) + len(fl)
+-	if err := Merge(&license, thing); err != nil {
+-		t.Fatal(err.Error())
+-	}
+-	currentLength := len(license["fields"].(map[interface{}]interface{}))
+-	if currentLength != expectedLength {
+-		t.Fatalf(`thing not merged in license properly, license must have %d elements instead of %d`, expectedLength, currentLength)
+-	}
+-	fields := license["fields"].(map[interface{}]interface{})
+-	if _, ok := fields["id"]; !ok {
+-		t.Fatalf(`thing not merged in license properly, license must have a new id field from thing`)
+-	}
+-}
+-
+-func TestTwoPointerValues(t *testing.T) {
+-	a := &simpleTest{}
+-	b := &simpleTest{42}
+-	if err := Merge(a, b); err != nil {
+-		t.Fatalf(`Boom. You crossed the streams: %s`, err)
+-	}
+-}
+-
+-func TestMap(t *testing.T) {
+-	a := complexTest{}
+-	a.Id = "athing"
+-	c := moreComplextText{a, simpleTest{}, simpleTest{}}
+-	b := map[string]interface{}{
+-		"ct": map[string]interface{}{
+-			"st": map[string]interface{}{
+-				"value": 42,
+-			},
+-			"sz": 1,
+-			"id": "bthing",
+-		},
+-		"st": &simpleTest{144}, // Mapping a reference
+-		"zt": simpleTest{299},  // Mapping a missing field (zt doesn't exist)
+-		"nt": simpleTest{3},
+-	}
+-	if err := Map(&c, b); err != nil {
+-		t.FailNow()
+-	}
+-	m := b["ct"].(map[string]interface{})
+-	n := m["st"].(map[string]interface{})
+-	o := b["st"].(*simpleTest)
+-	p := b["nt"].(simpleTest)
+-	if c.Ct.St.Value != 42 {
+-		t.Fatalf("b not merged in a properly: c.Ct.St.Value(%d) != b.Ct.St.Value(%d)", c.Ct.St.Value, n["value"])
+-	}
+-	if c.St.Value != 144 {
+-		t.Fatalf("b not merged in a properly: c.St.Value(%d) != b.St.Value(%d)", c.St.Value, o.Value)
+-	}
+-	if c.Nt.Value != 3 {
+-		t.Fatalf("b not merged in a properly: c.Nt.Value(%d) != b.Nt.Value(%d)", c.St.Value, p.Value)
+-	}
+-	if c.Ct.sz == 1 {
+-		t.Fatalf("a's private field sz not preserved from merge: c.Ct.sz(%d) == b.Ct.sz(%d)", c.Ct.sz, m["sz"])
+-	}
+-	if c.Ct.Id != m["id"] {
+-		t.Fatalf("a's field Id not merged properly: c.Ct.Id(%s) != b.Ct.Id(%s)", c.Ct.Id, m["id"])
+-	}
+-}
+-
+-func TestSimpleMap(t *testing.T) {
+-	a := simpleTest{}
+-	b := map[string]interface{}{
+-		"value": 42,
+-	}
+-	if err := Map(&a, b); err != nil {
+-		t.FailNow()
+-	}
+-	if a.Value != 42 {
+-		t.Fatalf("b not merged in a properly: a.Value(%d) != b.Value(%v)", a.Value, b["value"])
+-	}
+-}
+-
+-type pointerMapTest struct {
+-	A      int
+-	hidden int
+-	B      *simpleTest
+-}
+-
+-func TestBackAndForth(t *testing.T) {
+-	pt := pointerMapTest{42, 1, &simpleTest{66}}
+-	m := make(map[string]interface{})
+-	if err := Map(&m, pt); err != nil {
+-		t.FailNow()
+-	}
+-	var (
+-		v  interface{}
+-		ok bool
+-	)
+-	if v, ok = m["a"]; v.(int) != pt.A || !ok {
+-		t.Fatalf("pt not merged properly: m[`a`](%d) != pt.A(%d)", v, pt.A)
+-	}
+-	if v, ok = m["b"]; !ok {
+-		t.Fatalf("pt not merged properly: B is missing in m")
+-	}
+-	var st *simpleTest
+-	if st = v.(*simpleTest); st.Value != 66 {
+-		t.Fatalf("something went wrong while mapping pt on m, B wasn't copied")
+-	}
+-	bpt := pointerMapTest{}
+-	if err := Map(&bpt, m); err != nil {
+-		t.Fatal(err)
+-	}
+-	if bpt.A != pt.A {
+-		t.Fatalf("pt not merged properly: bpt.A(%d) != pt.A(%d)", bpt.A, pt.A)
+-	}
+-	if bpt.hidden == pt.hidden {
+-		t.Fatalf("pt unexpectedly merged: bpt.hidden(%d) == pt.hidden(%d)", bpt.hidden, pt.hidden)
+-	}
+-	if bpt.B.Value != pt.B.Value {
+-		t.Fatalf("pt not merged properly: bpt.B.Value(%d) != pt.B.Value(%d)", bpt.B.Value, pt.B.Value)
+-	}
+-}
+-
+-func loadYAML(path string) (m map[string]interface{}) {
+-	m = make(map[string]interface{})
+-	raw, _ := ioutil.ReadFile(path)
+-	_ = yaml.Unmarshal(raw, &m)
+-	return
+-}
+diff --git a/Godeps/_workspace/src/github.com/imdario/mergo/testdata/license.yml b/Godeps/_workspace/src/github.com/imdario/mergo/testdata/license.yml
+deleted file mode 100644
+index 62fdb61..0000000
+--- a/Godeps/_workspace/src/github.com/imdario/mergo/testdata/license.yml
++++ /dev/null
+@@ -1,3 +0,0 @@
+-import: ../../../../fossene/db/schema/thing.yml
+-fields:
+-    site: string
+diff --git a/Godeps/_workspace/src/github.com/imdario/mergo/testdata/thing.yml b/Godeps/_workspace/src/github.com/imdario/mergo/testdata/thing.yml
+deleted file mode 100644
+index c28eab0..0000000
+--- a/Godeps/_workspace/src/github.com/imdario/mergo/testdata/thing.yml
++++ /dev/null
+@@ -1,5 +0,0 @@
+-fields:
+-    id: int
+-    name: string
+-    parent: ref "datu:thing"
+-    status: enum(draft, public, private)
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/.gitignore b/Godeps/_workspace/src/github.com/miekg/dns/.gitignore
+deleted file mode 100644
+index 776cd95..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/.gitignore
++++ /dev/null
+@@ -1,4 +0,0 @@
+-*.6
+-tags
+-test.out
+-a.out
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/.travis.yml b/Godeps/_workspace/src/github.com/miekg/dns/.travis.yml
+deleted file mode 100644
+index 4485679..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/.travis.yml
++++ /dev/null
+@@ -1,21 +0,0 @@
+-language: go
+-go:
+-  - 1.2
+-  - 1.3
+-env:
+-  # "gvm update" resets GOOS and GOARCH environment variable, workaround it by setting
+-  # BUILD_GOOS and BUILD_GOARCH and overriding GOARCH and GOOS in the build script
+-  global:
+-    - BUILD_GOARCH=amd64
+-  matrix:
+-    - BUILD_GOOS=linux
+-    - BUILD_GOOS=darwin
+-    - BUILD_GOOS=windows
+-script:
+-  - gvm cross $BUILD_GOOS $BUILD_GOARCH
+-  - GOARCH=$BUILD_GOARCH GOOS=$BUILD_GOOS go build
+-
+-  # only test on linux
+-  # also specify -short; the crypto tests fail in weird ways *sometimes*
+-  # See issue #151
+-  - if [ $BUILD_GOOS == "linux" ]; then GOARCH=$BUILD_GOARCH GOOS=$BUILD_GOOS go test -short -bench=.; fi
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/AUTHORS b/Godeps/_workspace/src/github.com/miekg/dns/AUTHORS
+deleted file mode 100644
+index 1965683..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/AUTHORS
++++ /dev/null
+@@ -1 +0,0 @@
+-Miek Gieben <miek at miek.nl>
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/CONTRIBUTORS b/Godeps/_workspace/src/github.com/miekg/dns/CONTRIBUTORS
+deleted file mode 100644
+index f77e8a8..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/CONTRIBUTORS
++++ /dev/null
+@@ -1,9 +0,0 @@
+-Alex A. Skinner
+-Andrew Tunnell-Jones
+-Ask Bjørn Hansen
+-Dave Cheney
+-Dusty Wilson
+-Marek Majkowski
+-Peter van Dijk
+-Omri Bahumi
+-Alex Sergeyev
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/COPYRIGHT b/Godeps/_workspace/src/github.com/miekg/dns/COPYRIGHT
+deleted file mode 100644
+index 35702b1..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/COPYRIGHT
++++ /dev/null
+@@ -1,9 +0,0 @@
+-Copyright 2009 The Go Authors. All rights reserved. Use of this source code
+-is governed by a BSD-style license that can be found in the LICENSE file.
+-Extensions of the original work are copyright (c) 2011 Miek Gieben
+-
+-Copyright 2011 Miek Gieben. All rights reserved. Use of this source code is
+-governed by a BSD-style license that can be found in the LICENSE file.
+-
+-Copyright 2014 CloudFlare. All rights reserved. Use of this source code is
+-governed by a BSD-style license that can be found in the LICENSE file.
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/LICENSE b/Godeps/_workspace/src/github.com/miekg/dns/LICENSE
+deleted file mode 100644
+index 5763fa7..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/LICENSE
++++ /dev/null
+@@ -1,32 +0,0 @@
+-Extensions of the original work are copyright (c) 2011 Miek Gieben
+-
+-As this is fork of the official Go code the same license applies:
+-
+-Copyright (c) 2009 The Go Authors. All rights reserved.
+-
+-Redistribution and use in source and binary forms, with or without
+-modification, are permitted provided that the following conditions are
+-met:
+-
+-   * Redistributions of source code must retain the above copyright
+-notice, this list of conditions and the following disclaimer.
+-   * Redistributions in binary form must reproduce the above
+-copyright notice, this list of conditions and the following disclaimer
+-in the documentation and/or other materials provided with the
+-distribution.
+-   * Neither the name of Google Inc. nor the names of its
+-contributors may be used to endorse or promote products derived from
+-this software without specific prior written permission.
+-
+-THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+-"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+-LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+-A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+-OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+-SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+-LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+-DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+-THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+-(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+-OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+-
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/README.md b/Godeps/_workspace/src/github.com/miekg/dns/README.md
+deleted file mode 100644
+index 3cb850a..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/README.md
++++ /dev/null
+@@ -1,140 +0,0 @@
+-[![Build Status](https://travis-ci.org/miekg/dns.svg?branch=master)](https://travis-ci.org/miekg/dns)
+-
+-# Alternative (more granular) approach to a DNS library
+-
+-> Less is more.
+-
+-Complete and usable DNS library. All widely used Resource Records are
+-supported, including the DNSSEC types. It follows a lean and mean philosophy.
+-If there is stuff you should know as a DNS programmer there isn't a convenience
+-function for it. Server side and client side programming is supported, i.e. you
+-can build servers and resolvers with it.
+-
+-If you like this, you may also be interested in:
+-
+-* https://github.com/miekg/unbound -- Go wrapper for the Unbound resolver.
+-
+-# Goals
+-
+-* KISS;
+-* Fast;
+-* Small API, if its easy to code in Go, don't make a function for it.
+-
+-# Users
+-
+-A not-so-up-to-date-list-that-may-be-actually-current:
+-
+-* https://github.com/abh/geodns
+-* http://www.statdns.com/
+-* http://www.dnsinspect.com/
+-* https://github.com/chuangbo/jianbing-dictionary-dns
+-* http://www.dns-lg.com/
+-* https://github.com/fcambus/rrda
+-* https://github.com/kenshinx/godns
+-* https://github.com/skynetservices/skydns
+-* https://github.com/DevelopersPL/godnsagent
+-* https://github.com/duedil-ltd/discodns
+-
+-Send pull request if you want to be listed here.
+-
+-# Features
+-
+-* UDP/TCP queries, IPv4 and IPv6;
+-* RFC 1035 zone file parsing ($INCLUDE, $ORIGIN, $TTL and $GENERATE (for all record types) are supported;
+-* Fast:
+-    * Reply speed around ~ 80K qps (faster hardware results in more qps);
+-    * Parsing RRs ~ 100K RR/s, that's 5M records in about 50 seconds;
+-* Server side programming (mimicking the net/http package);
+-* Client side programming;
+-* DNSSEC: signing, validating and key generation for DSA, RSA and ECDSA;
+-* EDNS0, NSID;
+-* AXFR/IXFR;
+-* TSIG, SIG(0);
+-* DNS name compression;
+-* Depends only on the standard library.
+-
+-Have fun!
+-
+-Miek Gieben  -  2010-2012  -  <miek at miek.nl>
+-
+-# Building
+-
+-Building is done with the `go` tool. If you have setup your GOPATH
+-correctly, the following should work:
+-
+-    go get github.com/miekg/dns
+-    go build github.com/miekg/dns
+-
+-## Examples
+-
+-A short "how to use the API" is at the beginning of dns.go (this also will show
+-when you call `godoc github.com/miekg/dns`).
+-
+-Example programs can be found in the `github.com/miekg/exdns` repository.
+-
+-## Supported RFCs
+-
+-*all of them*
+-
+-* 103{4,5} - DNS standard
+-* 1348 - NSAP record
+-* 1982 - Serial Arithmetic
+-* 1876 - LOC record
+-* 1995 - IXFR
+-* 1996 - DNS notify
+-* 2136 - DNS Update (dynamic updates)
+-* 2181 - RRset definition - there is no RRset type though, just []RR
+-* 2537 - RSAMD5 DNS keys
+-* 2065 - DNSSEC (updated in later RFCs)
+-* 2671 - EDNS record
+-* 2782 - SRV record
+-* 2845 - TSIG record
+-* 2915 - NAPTR record
+-* 2929 - DNS IANA Considerations
+-* 3110 - RSASHA1 DNS keys
+-* 3225 - DO bit (DNSSEC OK)
+-* 340{1,2,3} - NAPTR record
+-* 3445 - Limiting the scope of (DNS)KEY
+-* 3597 - Unkown RRs
+-* 403{3,4,5} - DNSSEC + validation functions
+-* 4255 - SSHFP record
+-* 4343 - Case insensitivity
+-* 4408 - SPF record
+-* 4509 - SHA256 Hash in DS
+-* 4592 - Wildcards in the DNS
+-* 4635 - HMAC SHA TSIG
+-* 4701 - DHCID
+-* 4892 - id.server
+-* 5001 - NSID
+-* 5155 - NSEC3 record
+-* 5205 - HIP record
+-* 5702 - SHA2 in the DNS
+-* 5936 - AXFR
+-* 5966 - TCP implementation recommendations
+-* 6605 - ECDSA
+-* 6725 - IANA Registry Update
+-* 6742 - ILNP DNS
+-* 6891 - EDNS0 update
+-* 6895 - DNS IANA considerations
+-* 6975 - Algorithm Understanding in DNSSEC
+-* 7043 - EUI48/EUI64 records
+-* 7314 - DNS (EDNS) EXPIRE Option
+-* xxxx - URI record (draft)
+-* xxxx - EDNS0 DNS Update Lease (draft)
+-
+-## Loosely based upon
+-
+-* `ldns`
+-* `NSD`
+-* `Net::DNS`
+-* `GRONG`
+-
+-## TODO
+-
+-* privatekey.Precompute() when signing?
+-* Last remaining RRs: APL, ATMA, A6 and NXT;
+-* Missing in parsing: ISDN, UNSPEC, ATMA;
+-* CAA parsing is broken;
+-* NSEC(3) cover/match/closest enclose;
+-* Replies with TC bit are not parsed to the end;
+-* Create IsMsg to validate a message before fully parsing it.
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/client.go b/Godeps/_workspace/src/github.com/miekg/dns/client.go
+deleted file mode 100644
+index ee8e223..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/client.go
++++ /dev/null
+@@ -1,319 +0,0 @@
+-package dns
+-
+-// A client implementation.
+-
+-import (
+-	"bytes"
+-	"io"
+-	"net"
+-	"time"
+-)
+-
+-const dnsTimeout time.Duration = 2 * 1e9
+-const tcpIdleTimeout time.Duration = 8 * time.Second
+-
+-// A Conn represents a connection to a DNS server.
+-type Conn struct {
+-	net.Conn                         // a net.Conn holding the connection
+-	UDPSize        uint16            // minimum receive buffer for UDP messages
+-	TsigSecret     map[string]string // secret(s) for Tsig map[<zonename>]<base64 secret>, zonename must be fully qualified
+-	rtt            time.Duration
+-	t              time.Time
+-	tsigRequestMAC string
+-}
+-
+-// A Client defines parameters for a DNS client.
+-type Client struct {
+-	Net            string            // if "tcp" a TCP query will be initiated, otherwise an UDP one (default is "" for UDP)
+-	UDPSize        uint16            // minimum receive buffer for UDP messages
+-	DialTimeout    time.Duration     // net.DialTimeout (ns), defaults to 2 * 1e9
+-	ReadTimeout    time.Duration     // net.Conn.SetReadTimeout value for connections (ns), defaults to 2 * 1e9
+-	WriteTimeout   time.Duration     // net.Conn.SetWriteTimeout value for connections (ns), defaults to 2 * 1e9
+-	TsigSecret     map[string]string // secret(s) for Tsig map[<zonename>]<base64 secret>, zonename must be fully qualified
+-	SingleInflight bool              // if true suppress multiple outstanding queries for the same Qname, Qtype and Qclass
+-	group          singleflight
+-}
+-
+-// Exchange performs a synchronous UDP query. It sends the message m to the address
+-// contained in a and waits for an reply. Exchange does not retry a failed query, nor
+-// will it fall back to TCP in case of truncation.
+-// If you need to send a DNS message on an already existing connection, you can use the
+-// following:
+-//
+-//	co := &dns.Conn{Conn: c} // c is your net.Conn
+-//	co.WriteMsg(m)
+-//	in, err  := co.ReadMsg()
+-//	co.Close()
+-//
+-func Exchange(m *Msg, a string) (r *Msg, err error) {
+-	var co *Conn
+-	co, err = DialTimeout("udp", a, dnsTimeout)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	defer co.Close()
+-	co.SetReadDeadline(time.Now().Add(dnsTimeout))
+-	co.SetWriteDeadline(time.Now().Add(dnsTimeout))
+-	if err = co.WriteMsg(m); err != nil {
+-		return nil, err
+-	}
+-	r, err = co.ReadMsg()
+-	return r, err
+-}
+-
+-// ExchangeConn performs a synchronous query. It sends the message m via the connection
+-// c and waits for a reply. The connection c is not closed by ExchangeConn.
+-// This function is going away, but can easily be mimicked:
+-//
+-//	co := &dns.Conn{Conn: c} // c is your net.Conn
+-//	co.WriteMsg(m)
+-//	in, _  := co.ReadMsg()
+-//	co.Close()
+-//
+-func ExchangeConn(c net.Conn, m *Msg) (r *Msg, err error) {
+-	println("dns: this function is deprecated")
+-	co := new(Conn)
+-	co.Conn = c
+-	if err = co.WriteMsg(m); err != nil {
+-		return nil, err
+-	}
+-	r, err = co.ReadMsg()
+-	return r, err
+-}
+-
+-// Exchange performs an synchronous query. It sends the message m to the address
+-// contained in a and waits for an reply. Basic use pattern with a *dns.Client:
+-//
+-//	c := new(dns.Client)
+-//	in, rtt, err := c.Exchange(message, "127.0.0.1:53")
+-//
+-// Exchange does not retry a failed query, nor will it fall back to TCP in
+-// case of truncation.
+-func (c *Client) Exchange(m *Msg, a string) (r *Msg, rtt time.Duration, err error) {
+-	if !c.SingleInflight {
+-		return c.exchange(m, a)
+-	}
+-	// This adds a bunch of garbage, TODO(miek).
+-	t := "nop"
+-	if t1, ok := TypeToString[m.Question[0].Qtype]; ok {
+-		t = t1
+-	}
+-	cl := "nop"
+-	if cl1, ok := ClassToString[m.Question[0].Qclass]; ok {
+-		cl = cl1
+-	}
+-	r, rtt, err, shared := c.group.Do(m.Question[0].Name+t+cl, func() (*Msg, time.Duration, error) {
+-		return c.exchange(m, a)
+-	})
+-	if err != nil {
+-		return r, rtt, err
+-	}
+-	if shared {
+-		return r.Copy(), rtt, nil
+-	}
+-	return r, rtt, nil
+-}
+-
+-func (c *Client) exchange(m *Msg, a string) (r *Msg, rtt time.Duration, err error) {
+-	timeout := dnsTimeout
+-	var co *Conn
+-	if c.DialTimeout != 0 {
+-		timeout = c.DialTimeout
+-	}
+-	if c.Net == "" {
+-		co, err = DialTimeout("udp", a, timeout)
+-	} else {
+-		co, err = DialTimeout(c.Net, a, timeout)
+-	}
+-	if err != nil {
+-		return nil, 0, err
+-	}
+-	timeout = dnsTimeout
+-	if c.ReadTimeout != 0 {
+-		timeout = c.ReadTimeout
+-	}
+-	co.SetReadDeadline(time.Now().Add(timeout))
+-	timeout = dnsTimeout
+-	if c.WriteTimeout != 0 {
+-		timeout = c.WriteTimeout
+-	}
+-	co.SetWriteDeadline(time.Now().Add(timeout))
+-	defer co.Close()
+-	opt := m.IsEdns0()
+-	// If EDNS0 is used use that for size.
+-	if opt != nil && opt.UDPSize() >= MinMsgSize {
+-		co.UDPSize = opt.UDPSize()
+-	}
+-	// Otherwise use the client's configured UDP size.
+-	if opt == nil && c.UDPSize >= MinMsgSize {
+-		co.UDPSize = c.UDPSize
+-	}
+-	co.TsigSecret = c.TsigSecret
+-	if err = co.WriteMsg(m); err != nil {
+-		return nil, 0, err
+-	}
+-	r, err = co.ReadMsg()
+-	return r, co.rtt, err
+-}
+-
+-// ReadMsg reads a message from the connection co.
+-// If the received message contains a TSIG record the transaction
+-// signature is verified.
+-func (co *Conn) ReadMsg() (*Msg, error) {
+-	var p []byte
+-	m := new(Msg)
+-	if _, ok := co.Conn.(*net.TCPConn); ok {
+-		p = make([]byte, MaxMsgSize)
+-	} else {
+-		if co.UDPSize >= 512 {
+-			p = make([]byte, co.UDPSize)
+-		} else {
+-			p = make([]byte, MinMsgSize)
+-		}
+-	}
+-	n, err := co.Read(p)
+-	if err != nil && n == 0 {
+-		return nil, err
+-	}
+-	p = p[:n]
+-	if err := m.Unpack(p); err != nil {
+-		return nil, err
+-	}
+-	co.rtt = time.Since(co.t)
+-	if t := m.IsTsig(); t != nil {
+-		if _, ok := co.TsigSecret[t.Hdr.Name]; !ok {
+-			return m, ErrSecret
+-		}
+-		// Need to work on the original message p, as that was used to calculate the tsig.
+-		err = TsigVerify(p, co.TsigSecret[t.Hdr.Name], co.tsigRequestMAC, false)
+-	}
+-	return m, err
+-}
+-
+-// Read implements the net.Conn read method.
+-func (co *Conn) Read(p []byte) (n int, err error) {
+-	if co.Conn == nil {
+-		return 0, ErrConnEmpty
+-	}
+-	if len(p) < 2 {
+-		return 0, io.ErrShortBuffer
+-	}
+-	if t, ok := co.Conn.(*net.TCPConn); ok {
+-		n, err = t.Read(p[0:2])
+-		if err != nil || n != 2 {
+-			return n, err
+-		}
+-		l, _ := unpackUint16(p[0:2], 0)
+-		if l == 0 {
+-			return 0, ErrShortRead
+-		}
+-		if int(l) > len(p) {
+-			return int(l), io.ErrShortBuffer
+-		}
+-		n, err = t.Read(p[:l])
+-		if err != nil {
+-			return n, err
+-		}
+-		i := n
+-		for i < int(l) {
+-			j, err := t.Read(p[i:int(l)])
+-			if err != nil {
+-				return i, err
+-			}
+-			i += j
+-		}
+-		n = i
+-		return n, err
+-	}
+-	// UDP connection
+-	n, err = co.Conn.Read(p)
+-	if err != nil {
+-		return n, err
+-	}
+-	return n, err
+-}
+-
+-// WriteMsg sends a message throught the connection co.
+-// If the message m contains a TSIG record the transaction
+-// signature is calculated.
+-func (co *Conn) WriteMsg(m *Msg) (err error) {
+-	var out []byte
+-	if t := m.IsTsig(); t != nil {
+-		mac := ""
+-		if _, ok := co.TsigSecret[t.Hdr.Name]; !ok {
+-			return ErrSecret
+-		}
+-		out, mac, err = TsigGenerate(m, co.TsigSecret[t.Hdr.Name], co.tsigRequestMAC, false)
+-		// Set for the next read, allthough only used in zone transfers
+-		co.tsigRequestMAC = mac
+-	} else {
+-		out, err = m.Pack()
+-	}
+-	if err != nil {
+-		return err
+-	}
+-	co.t = time.Now()
+-	if _, err = co.Write(out); err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-// Write implements the net.Conn Write method.
+-func (co *Conn) Write(p []byte) (n int, err error) {
+-	if t, ok := co.Conn.(*net.TCPConn); ok {
+-		lp := len(p)
+-		if lp < 2 {
+-			return 0, io.ErrShortBuffer
+-		}
+-		if lp > MaxMsgSize {
+-			return 0, &Error{err: "message too large"}
+-		}
+-		l := make([]byte, 2, lp+2)
+-		l[0], l[1] = packUint16(uint16(lp))
+-		p = append(l, p...)
+-		n, err := io.Copy(t, bytes.NewReader(p))
+-		return int(n), err
+-	}
+-	n, err = co.Conn.(*net.UDPConn).Write(p)
+-	return n, err
+-}
+-
+-// Dial connects to the address on the named network.
+-func Dial(network, address string) (conn *Conn, err error) {
+-	conn = new(Conn)
+-	conn.Conn, err = net.Dial(network, address)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return conn, nil
+-}
+-
+-// Dialtimeout acts like Dial but takes a timeout.
+-func DialTimeout(network, address string, timeout time.Duration) (conn *Conn, err error) {
+-	conn = new(Conn)
+-	conn.Conn, err = net.DialTimeout(network, address, timeout)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return conn, nil
+-}
+-
+-// Close implements the net.Conn Close method.
+-func (co *Conn) Close() error { return co.Conn.Close() }
+-
+-// LocalAddr implements the net.Conn LocalAddr method.
+-func (co *Conn) LocalAddr() net.Addr { return co.Conn.LocalAddr() }
+-
+-// RemoteAddr implements the net.Conn RemoteAddr method.
+-func (co *Conn) RemoteAddr() net.Addr { return co.Conn.RemoteAddr() }
+-
+-// SetDeadline implements the net.Conn SetDeadline method.
+-func (co *Conn) SetDeadline(t time.Time) error { return co.Conn.SetDeadline(t) }
+-
+-// SetReadDeadline implements the net.Conn SetReadDeadline method.
+-func (co *Conn) SetReadDeadline(t time.Time) error { return co.Conn.SetReadDeadline(t) }
+-
+-// SetWriteDeadline implements the net.Conn SetWriteDeadline method.
+-func (co *Conn) SetWriteDeadline(t time.Time) error { return co.Conn.SetWriteDeadline(t) }
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/client_test.go b/Godeps/_workspace/src/github.com/miekg/dns/client_test.go
+deleted file mode 100644
+index 2113f3b..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/client_test.go
++++ /dev/null
+@@ -1,195 +0,0 @@
+-package dns
+-
+-import (
+-	"testing"
+-	"time"
+-)
+-
+-func TestClientSync(t *testing.T) {
+-	HandleFunc("miek.nl.", HelloServer)
+-	defer HandleRemove("miek.nl.")
+-
+-	s, addrstr, err := RunLocalUDPServer("127.0.0.1:0")
+-	if err != nil {
+-		t.Fatalf("Unable to run test server: %s", err)
+-	}
+-	defer s.Shutdown()
+-
+-	m := new(Msg)
+-	m.SetQuestion("miek.nl.", TypeSOA)
+-
+-	c := new(Client)
+-	r, _, e := c.Exchange(m, addrstr)
+-	if e != nil {
+-		t.Logf("failed to exchange: %s", e.Error())
+-		t.Fail()
+-	}
+-	if r != nil && r.Rcode != RcodeSuccess {
+-		t.Log("failed to get an valid answer")
+-		t.Fail()
+-		t.Logf("%v\n", r)
+-	}
+-	// And now with plain Exchange().
+-	r, e = Exchange(m, addrstr)
+-	if e != nil {
+-		t.Logf("failed to exchange: %s", e.Error())
+-		t.Fail()
+-	}
+-	if r != nil && r.Rcode != RcodeSuccess {
+-		t.Log("failed to get an valid answer")
+-		t.Fail()
+-		t.Logf("%v\n", r)
+-	}
+-}
+-
+-func TestClientEDNS0(t *testing.T) {
+-	HandleFunc("miek.nl.", HelloServer)
+-	defer HandleRemove("miek.nl.")
+-
+-	s, addrstr, err := RunLocalUDPServer("127.0.0.1:0")
+-	if err != nil {
+-		t.Fatalf("Unable to run test server: %s", err)
+-	}
+-	defer s.Shutdown()
+-
+-	m := new(Msg)
+-	m.SetQuestion("miek.nl.", TypeDNSKEY)
+-
+-	m.SetEdns0(2048, true)
+-
+-	c := new(Client)
+-	r, _, e := c.Exchange(m, addrstr)
+-	if e != nil {
+-		t.Logf("failed to exchange: %s", e.Error())
+-		t.Fail()
+-	}
+-
+-	if r != nil && r.Rcode != RcodeSuccess {
+-		t.Log("failed to get an valid answer")
+-		t.Fail()
+-		t.Logf("%v\n", r)
+-	}
+-}
+-
+-func TestSingleSingleInflight(t *testing.T) {
+-	HandleFunc("miek.nl.", HelloServer)
+-	defer HandleRemove("miek.nl.")
+-
+-	s, addrstr, err := RunLocalUDPServer("127.0.0.1:0")
+-	if err != nil {
+-		t.Fatalf("Unable to run test server: %s", err)
+-	}
+-	defer s.Shutdown()
+-
+-	m := new(Msg)
+-	m.SetQuestion("miek.nl.", TypeDNSKEY)
+-
+-	c := new(Client)
+-	c.SingleInflight = true
+-	nr := 10
+-	ch := make(chan time.Duration)
+-	for i := 0; i < nr; i++ {
+-		go func() {
+-			_, rtt, _ := c.Exchange(m, addrstr)
+-			ch <- rtt
+-		}()
+-	}
+-	i := 0
+-	var first time.Duration
+-	// With inflight *all* rtt are identical, and by doing actual lookups
+-	// the changes that this is a coincidence is small.
+-Loop:
+-	for {
+-		select {
+-		case rtt := <-ch:
+-			if i == 0 {
+-				first = rtt
+-			} else {
+-				if first != rtt {
+-					t.Log("all rtts should be equal")
+-					t.Fail()
+-				}
+-			}
+-			i++
+-			if i == 10 {
+-				break Loop
+-			}
+-		}
+-	}
+-}
+-
+-/*
+-func TestClientTsigAXFR(t *testing.T) {
+-	m := new(Msg)
+-	m.SetAxfr("example.nl.")
+-	m.SetTsig("axfr.", HmacMD5, 300, time.Now().Unix())
+-
+-	tr := new(Transfer)
+-	tr.TsigSecret = map[string]string{"axfr.": "so6ZGir4GPAqINNh9U5c3A=="}
+-
+-	if a, err := tr.In(m, "176.58.119.54:53"); err != nil {
+-		t.Log("failed to setup axfr: " + err.Error())
+-		t.Fatal()
+-	} else {
+-		for ex := range a {
+-			if ex.Error != nil {
+-				t.Logf("error %s\n", ex.Error.Error())
+-				t.Fail()
+-				break
+-			}
+-			for _, rr := range ex.RR {
+-				t.Logf("%s\n", rr.String())
+-			}
+-		}
+-	}
+-}
+-
+-func TestClientAXFRMultipleEnvelopes(t *testing.T) {
+-	m := new(Msg)
+-	m.SetAxfr("nlnetlabs.nl.")
+-
+-	tr := new(Transfer)
+-	if a, err := tr.In(m, "213.154.224.1:53"); err != nil {
+-		t.Log("Failed to setup axfr" + err.Error())
+-		t.Fail()
+-		return
+-	} else {
+-		for ex := range a {
+-			if ex.Error != nil {
+-				t.Logf("Error %s\n", ex.Error.Error())
+-				t.Fail()
+-				break
+-			}
+-		}
+-	}
+-}
+-*/
+-
+-// ExampleUpdateLeaseTSIG shows how to update a lease signed with TSIG.
+-func ExampleUpdateLeaseTSIG(t *testing.T) {
+-	m := new(Msg)
+-	m.SetUpdate("t.local.ip6.io.")
+-	rr, _ := NewRR("t.local.ip6.io. 30 A 127.0.0.1")
+-	rrs := make([]RR, 1)
+-	rrs[0] = rr
+-	m.Insert(rrs)
+-
+-	lease_rr := new(OPT)
+-	lease_rr.Hdr.Name = "."
+-	lease_rr.Hdr.Rrtype = TypeOPT
+-	e := new(EDNS0_UL)
+-	e.Code = EDNS0UL
+-	e.Lease = 120
+-	lease_rr.Option = append(lease_rr.Option, e)
+-	m.Extra = append(m.Extra, lease_rr)
+-
+-	c := new(Client)
+-	m.SetTsig("polvi.", HmacMD5, 300, time.Now().Unix())
+-	c.TsigSecret = map[string]string{"polvi.": "pRZgBrBvI4NAHZYhxmhs/Q=="}
+-
+-	_, _, err := c.Exchange(m, "127.0.0.1:53")
+-	if err != nil {
+-		t.Log(err.Error())
+-		t.Fail()
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/clientconfig.go b/Godeps/_workspace/src/github.com/miekg/dns/clientconfig.go
+deleted file mode 100644
+index 87cf896..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/clientconfig.go
++++ /dev/null
+@@ -1,94 +0,0 @@
+-package dns
+-
+-import (
+-	"bufio"
+-	"os"
+-	"strconv"
+-	"strings"
+-)
+-
+-// Wraps the contents of the /etc/resolv.conf.
+-type ClientConfig struct {
+-	Servers  []string // servers to use
+-	Search   []string // suffixes to append to local name
+-	Port     string   // what port to use
+-	Ndots    int      // number of dots in name to trigger absolute lookup
+-	Timeout  int      // seconds before giving up on packet
+-	Attempts int      // lost packets before giving up on server, not used in the package dns
+-}
+-
+-// ClientConfigFromFile parses a resolv.conf(5) like file and returns
+-// a *ClientConfig.
+-func ClientConfigFromFile(resolvconf string) (*ClientConfig, error) {
+-	file, err := os.Open(resolvconf)
+-	if err != nil {
+-		return nil, err
+-	}
+-	defer file.Close()
+-	c := new(ClientConfig)
+-	b := bufio.NewReader(file)
+-	c.Servers = make([]string, 0)
+-	c.Search = make([]string, 0)
+-	c.Port = "53"
+-	c.Ndots = 1
+-	c.Timeout = 5
+-	c.Attempts = 2
+-	for line, ok := b.ReadString('\n'); ok == nil; line, ok = b.ReadString('\n') {
+-		f := strings.Fields(line)
+-		if len(f) < 1 {
+-			continue
+-		}
+-		switch f[0] {
+-		case "nameserver": // add one name server
+-			if len(f) > 1 {
+-				// One more check: make sure server name is
+-				// just an IP address.  Otherwise we need DNS
+-				// to look it up.
+-				name := f[1]
+-				c.Servers = append(c.Servers, name)
+-			}
+-
+-		case "domain": // set search path to just this domain
+-			if len(f) > 1 {
+-				c.Search = make([]string, 1)
+-				c.Search[0] = f[1]
+-			} else {
+-				c.Search = make([]string, 0)
+-			}
+-
+-		case "search": // set search path to given servers
+-			c.Search = make([]string, len(f)-1)
+-			for i := 0; i < len(c.Search); i++ {
+-				c.Search[i] = f[i+1]
+-			}
+-
+-		case "options": // magic options
+-			for i := 1; i < len(f); i++ {
+-				s := f[i]
+-				switch {
+-				case len(s) >= 6 && s[:6] == "ndots:":
+-					n, _ := strconv.Atoi(s[6:])
+-					if n < 1 {
+-						n = 1
+-					}
+-					c.Ndots = n
+-				case len(s) >= 8 && s[:8] == "timeout:":
+-					n, _ := strconv.Atoi(s[8:])
+-					if n < 1 {
+-						n = 1
+-					}
+-					c.Timeout = n
+-				case len(s) >= 8 && s[:9] == "attempts:":
+-					n, _ := strconv.Atoi(s[9:])
+-					if n < 1 {
+-						n = 1
+-					}
+-					c.Attempts = n
+-				case s == "rotate":
+-					/* not imp */
+-				}
+-			}
+-		}
+-	}
+-	return c, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/defaults.go b/Godeps/_workspace/src/github.com/miekg/dns/defaults.go
+deleted file mode 100644
+index 0c8fa9c..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/defaults.go
++++ /dev/null
+@@ -1,242 +0,0 @@
+-package dns
+-
+-import (
+-	"errors"
+-	"net"
+-	"strconv"
+-)
+-
+-const hexDigit = "0123456789abcdef"
+-
+-// Everything is assumed in ClassINET.
+-
+-// SetReply creates a reply message from a request message.
+-func (dns *Msg) SetReply(request *Msg) *Msg {
+-	dns.Id = request.Id
+-	dns.RecursionDesired = request.RecursionDesired // Copy rd bit
+-	dns.Response = true
+-	dns.Opcode = OpcodeQuery
+-	dns.Rcode = RcodeSuccess
+-	if len(request.Question) > 0 {
+-		dns.Question = make([]Question, 1)
+-		dns.Question[0] = request.Question[0]
+-	}
+-	return dns
+-}
+-
+-// SetQuestion creates a question message.
+-func (dns *Msg) SetQuestion(z string, t uint16) *Msg {
+-	dns.Id = Id()
+-	dns.RecursionDesired = true
+-	dns.Question = make([]Question, 1)
+-	dns.Question[0] = Question{z, t, ClassINET}
+-	return dns
+-}
+-
+-// SetNotify creates a notify message.
+-func (dns *Msg) SetNotify(z string) *Msg {
+-	dns.Opcode = OpcodeNotify
+-	dns.Authoritative = true
+-	dns.Id = Id()
+-	dns.Question = make([]Question, 1)
+-	dns.Question[0] = Question{z, TypeSOA, ClassINET}
+-	return dns
+-}
+-
+-// SetRcode creates an error message suitable for the request.
+-func (dns *Msg) SetRcode(request *Msg, rcode int) *Msg {
+-	dns.SetReply(request)
+-	dns.Rcode = rcode
+-	return dns
+-}
+-
+-// SetRcodeFormatError creates a message with FormError set.
+-func (dns *Msg) SetRcodeFormatError(request *Msg) *Msg {
+-	dns.Rcode = RcodeFormatError
+-	dns.Opcode = OpcodeQuery
+-	dns.Response = true
+-	dns.Authoritative = false
+-	dns.Id = request.Id
+-	return dns
+-}
+-
+-// SetUpdate makes the message a dynamic update message. It
+-// sets the ZONE section to: z, TypeSOA, ClassINET.
+-func (dns *Msg) SetUpdate(z string) *Msg {
+-	dns.Id = Id()
+-	dns.Response = false
+-	dns.Opcode = OpcodeUpdate
+-	dns.Compress = false // BIND9 cannot handle compression
+-	dns.Question = make([]Question, 1)
+-	dns.Question[0] = Question{z, TypeSOA, ClassINET}
+-	return dns
+-}
+-
+-// SetIxfr creates message for requesting an IXFR.
+-func (dns *Msg) SetIxfr(z string, serial uint32) *Msg {
+-	dns.Id = Id()
+-	dns.Question = make([]Question, 1)
+-	dns.Ns = make([]RR, 1)
+-	s := new(SOA)
+-	s.Hdr = RR_Header{z, TypeSOA, ClassINET, defaultTtl, 0}
+-	s.Serial = serial
+-	dns.Question[0] = Question{z, TypeIXFR, ClassINET}
+-	dns.Ns[0] = s
+-	return dns
+-}
+-
+-// SetAxfr creates message for requesting an AXFR.
+-func (dns *Msg) SetAxfr(z string) *Msg {
+-	dns.Id = Id()
+-	dns.Question = make([]Question, 1)
+-	dns.Question[0] = Question{z, TypeAXFR, ClassINET}
+-	return dns
+-}
+-
+-// SetTsig appends a TSIG RR to the message.
+-// This is only a skeleton TSIG RR that is added as the last RR in the
+-// additional section. The Tsig is calculated when the message is being send.
+-func (dns *Msg) SetTsig(z, algo string, fudge, timesigned int64) *Msg {
+-	t := new(TSIG)
+-	t.Hdr = RR_Header{z, TypeTSIG, ClassANY, 0, 0}
+-	t.Algorithm = algo
+-	t.Fudge = 300
+-	t.TimeSigned = uint64(timesigned)
+-	t.OrigId = dns.Id
+-	dns.Extra = append(dns.Extra, t)
+-	return dns
+-}
+-
+-// SetEdns0 appends a EDNS0 OPT RR to the message.
+-// TSIG should always the last RR in a message.
+-func (dns *Msg) SetEdns0(udpsize uint16, do bool) *Msg {
+-	e := new(OPT)
+-	e.Hdr.Name = "."
+-	e.Hdr.Rrtype = TypeOPT
+-	e.SetUDPSize(udpsize)
+-	if do {
+-		e.SetDo()
+-	}
+-	dns.Extra = append(dns.Extra, e)
+-	return dns
+-}
+-
+-// IsTsig checks if the message has a TSIG record as the last record
+-// in the additional section. It returns the TSIG record found or nil.
+-func (dns *Msg) IsTsig() *TSIG {
+-	if len(dns.Extra) > 0 {
+-		if dns.Extra[len(dns.Extra)-1].Header().Rrtype == TypeTSIG {
+-			return dns.Extra[len(dns.Extra)-1].(*TSIG)
+-		}
+-	}
+-	return nil
+-}
+-
+-// IsEdns0 checks if the message has a EDNS0 (OPT) record, any EDNS0
+-// record in the additional section will do. It returns the OPT record
+-// found or nil.
+-func (dns *Msg) IsEdns0() *OPT {
+-	for _, r := range dns.Extra {
+-		if r.Header().Rrtype == TypeOPT {
+-			return r.(*OPT)
+-		}
+-	}
+-	return nil
+-}
+-
+-// IsDomainName checks if s is a valid domainname, it returns
+-// the number of labels and true, when a domain name is valid.
+-// Note that non fully qualified domain name is considered valid, in this case the
+-// last label is counted in the number of labels.
+-// When false is returned the number of labels is not defined.
+-func IsDomainName(s string) (labels int, ok bool) {
+-	_, labels, err := packDomainName(s, nil, 0, nil, false)
+-	return labels, err == nil
+-}
+-
+-// IsSubDomain checks if child is indeed a child of the parent. Both child and
+-// parent are *not* downcased before doing the comparison.
+-func IsSubDomain(parent, child string) bool {
+-	// Entire child is contained in parent
+-	return CompareDomainName(parent, child) == CountLabel(parent)
+-}
+-
+-// IsMsg sanity checks buf and returns an error if it isn't a valid DNS packet.
+-// The checking is performed on the binary payload.
+-func IsMsg(buf []byte) error {
+-	// Header
+-	if len(buf) < 12 {
+-		return errors.New("dns: bad message header")
+-	}
+-	// Header: Opcode
+-	// TODO(miek): more checks here, e.g. check all header bits.
+-	return nil
+-}
+-
+-// IsFqdn checks if a domain name is fully qualified.
+-func IsFqdn(s string) bool {
+-	l := len(s)
+-	if l == 0 {
+-		return false
+-	}
+-	return s[l-1] == '.'
+-}
+-
+-// Fqdns return the fully qualified domain name from s.
+-// If s is already fully qualified, it behaves as the identity function.
+-func Fqdn(s string) string {
+-	if IsFqdn(s) {
+-		return s
+-	}
+-	return s + "."
+-}
+-
+-// Copied from the official Go code.
+-
+-// ReverseAddr returns the in-addr.arpa. or ip6.arpa. hostname of the IP
+-// address suitable for reverse DNS (PTR) record lookups or an error if it fails
+-// to parse the IP address.
+-func ReverseAddr(addr string) (arpa string, err error) {
+-	ip := net.ParseIP(addr)
+-	if ip == nil {
+-		return "", &Error{err: "unrecognized address: " + addr}
+-	}
+-	if ip.To4() != nil {
+-		return strconv.Itoa(int(ip[15])) + "." + strconv.Itoa(int(ip[14])) + "." + strconv.Itoa(int(ip[13])) + "." +
+-			strconv.Itoa(int(ip[12])) + ".in-addr.arpa.", nil
+-	}
+-	// Must be IPv6
+-	buf := make([]byte, 0, len(ip)*4+len("ip6.arpa."))
+-	// Add it, in reverse, to the buffer
+-	for i := len(ip) - 1; i >= 0; i-- {
+-		v := ip[i]
+-		buf = append(buf, hexDigit[v&0xF])
+-		buf = append(buf, '.')
+-		buf = append(buf, hexDigit[v>>4])
+-		buf = append(buf, '.')
+-	}
+-	// Append "ip6.arpa." and return (buf already has the final .)
+-	buf = append(buf, "ip6.arpa."...)
+-	return string(buf), nil
+-}
+-
+-// String returns the string representation for the type t.
+-func (t Type) String() string {
+-	if t1, ok := TypeToString[uint16(t)]; ok {
+-		return t1
+-	}
+-	return "TYPE" + strconv.Itoa(int(t))
+-}
+-
+-// String returns the string representation for the class c.
+-func (c Class) String() string {
+-	if c1, ok := ClassToString[uint16(c)]; ok {
+-		return c1
+-	}
+-	return "CLASS" + strconv.Itoa(int(c))
+-}
+-
+-// String returns the string representation for the name n.
+-func (n Name) String() string {
+-	return sprintName(string(n))
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/dns.go b/Godeps/_workspace/src/github.com/miekg/dns/dns.go
+deleted file mode 100644
+index 7540c0d..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/dns.go
++++ /dev/null
+@@ -1,193 +0,0 @@
+-// Package dns implements a full featured interface to the Domain Name System.
+-// Server- and client-side programming is supported.
+-// The package allows complete control over what is send out to the DNS. The package
+-// API follows the less-is-more principle, by presenting a small, clean interface.
+-//
+-// The package dns supports (asynchronous) querying/replying, incoming/outgoing zone transfers,
+-// TSIG, EDNS0, dynamic updates, notifies and DNSSEC validation/signing.
+-// Note that domain names MUST be fully qualified, before sending them, unqualified
+-// names in a message will result in a packing failure.
+-//
+-// Resource records are native types. They are not stored in wire format.
+-// Basic usage pattern for creating a new resource record:
+-//
+-//      r := new(dns.MX)
+-//      r.Hdr = dns.RR_Header{Name: "miek.nl.", Rrtype: dns.TypeMX, Class: dns.ClassINET, Ttl: 3600}
+-//      r.Preference = 10
+-//      r.Mx = "mx.miek.nl."
+-//
+-// Or directly from a string:
+-//
+-//      mx, err := dns.NewRR("miek.nl. 3600 IN MX 10 mx.miek.nl.")
+-//
+-// Or when the default TTL (3600) and class (IN) suit you:
+-//
+-//      mx, err := dns.NewRR("miek.nl. MX 10 mx.miek.nl.")
+-//
+-// Or even:
+-//
+-//      mx, err := dns.NewRR("$ORIGIN nl.\nmiek 1H IN MX 10 mx.miek")
+-//
+-// In the DNS messages are exchanged, these messages contain resource
+-// records (sets).  Use pattern for creating a message:
+-//
+-//      m := new(dns.Msg)
+-//      m.SetQuestion("miek.nl.", dns.TypeMX)
+-//
+-// Or when not certain if the domain name is fully qualified:
+-//
+-//	m.SetQuestion(dns.Fqdn("miek.nl"), dns.TypeMX)
+-//
+-// The message m is now a message with the question section set to ask
+-// the MX records for the miek.nl. zone.
+-//
+-// The following is slightly more verbose, but more flexible:
+-//
+-//      m1 := new(dns.Msg)
+-//      m1.Id = dns.Id()
+-//      m1.RecursionDesired = true
+-//      m1.Question = make([]dns.Question, 1)
+-//      m1.Question[0] = dns.Question{"miek.nl.", dns.TypeMX, dns.ClassINET}
+-//
+-// After creating a message it can be send.
+-// Basic use pattern for synchronous querying the DNS at a
+-// server configured on 127.0.0.1 and port 53:
+-//
+-//      c := new(dns.Client)
+-//      in, rtt, err := c.Exchange(m1, "127.0.0.1:53")
+-//
+-// Suppressing
+-// multiple outstanding queries (with the same question, type and class) is as easy as setting:
+-//
+-//	c.SingleInflight = true
+-//
+-// If these "advanced" features are not needed, a simple UDP query can be send,
+-// with:
+-//
+-//	in, err := dns.Exchange(m1, "127.0.0.1:53")
+-//
+-// When this functions returns you will get dns message. A dns message consists
+-// out of four sections.
+-// The question section: in.Question, the answer section: in.Answer,
+-// the authority section: in.Ns and the additional section: in.Extra.
+-//
+-// Each of these sections (except the Question section) contain a []RR. Basic
+-// use pattern for accessing the rdata of a TXT RR as the first RR in
+-// the Answer section:
+-//
+-//	if t, ok := in.Answer[0].(*dns.TXT); ok {
+-//		// do something with t.Txt
+-//	}
+-//
+-// Domain Name and TXT Character String Representations
+-//
+-// Both domain names and TXT character strings are converted to presentation
+-// form both when unpacked and when converted to strings.
+-//
+-// For TXT character strings, tabs, carriage returns and line feeds will be
+-// converted to \t, \r and \n respectively. Back slashes and quotations marks
+-// will be escaped. Bytes below 32 and above 127 will be converted to \DDD
+-// form.
+-//
+-// For domain names, in addition to the above rules brackets, periods,
+-// spaces, semicolons and the at symbol are escaped.
+-package dns
+-
+-import (
+-	"strconv"
+-)
+-
+-const (
+-	year68         = 1 << 31 // For RFC1982 (Serial Arithmetic) calculations in 32 bits.
+-	DefaultMsgSize = 4096    // Standard default for larger than 512 bytes.
+-	MinMsgSize     = 512     // Minimal size of a DNS packet.
+-	MaxMsgSize     = 65536   // Largest possible DNS packet.
+-	defaultTtl     = 3600    // Default TTL.
+-)
+-
+-// Error represents a DNS error
+-type Error struct{ err string }
+-
+-func (e *Error) Error() string {
+-	if e == nil {
+-		return "dns: <nil>"
+-	}
+-	return "dns: " + e.err
+-}
+-
+-// An RR represents a resource record.
+-type RR interface {
+-	// Header returns the header of an resource record. The header contains
+-	// everything up to the rdata.
+-	Header() *RR_Header
+-	// String returns the text representation of the resource record.
+-	String() string
+-	// copy returns a copy of the RR
+-	copy() RR
+-	// len returns the length (in octects) of the uncompressed RR in wire format.
+-	len() int
+-}
+-
+-// DNS resource records.
+-// There are many types of RRs,
+-// but they all share the same header.
+-type RR_Header struct {
+-	Name     string `dns:"cdomain-name"`
+-	Rrtype   uint16
+-	Class    uint16
+-	Ttl      uint32
+-	Rdlength uint16 // length of data after header
+-}
+-
+-func (h *RR_Header) Header() *RR_Header { return h }
+-
+-// Just to imlement the RR interface
+-func (h *RR_Header) copy() RR { return nil }
+-
+-func (h *RR_Header) copyHeader() *RR_Header {
+-	r := new(RR_Header)
+-	r.Name = h.Name
+-	r.Rrtype = h.Rrtype
+-	r.Class = h.Class
+-	r.Ttl = h.Ttl
+-	r.Rdlength = h.Rdlength
+-	return r
+-}
+-
+-func (h *RR_Header) String() string {
+-	var s string
+-
+-	if h.Rrtype == TypeOPT {
+-		s = ";"
+-		// and maybe other things
+-	}
+-
+-	s += sprintName(h.Name) + "\t"
+-	s += strconv.FormatInt(int64(h.Ttl), 10) + "\t"
+-	s += Class(h.Class).String() + "\t"
+-	s += Type(h.Rrtype).String() + "\t"
+-	return s
+-}
+-
+-func (h *RR_Header) len() int {
+-	l := len(h.Name) + 1
+-	l += 10 // rrtype(2) + class(2) + ttl(4) + rdlength(2)
+-	return l
+-}
+-
+-// ToRFC3597 converts a known RR to the unknown RR representation
+-// from RFC 3597.
+-func (rr *RFC3597) ToRFC3597(r RR) error {
+-	buf := make([]byte, r.len()*2)
+-	off, err := PackStruct(r, buf, 0)
+-	if err != nil {
+-		return err
+-	}
+-	buf = buf[:off]
+-	rawSetRdlength(buf, 0, off)
+-	_, err = UnpackStruct(rr, buf, 0)
+-	if err != nil {
+-		return err
+-	}
+-	return nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/dns_test.go b/Godeps/_workspace/src/github.com/miekg/dns/dns_test.go
+deleted file mode 100644
+index 16c86f4..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/dns_test.go
++++ /dev/null
+@@ -1,511 +0,0 @@
+-package dns
+-
+-import (
+-	"encoding/hex"
+-	"net"
+-	"testing"
+-)
+-
+-func TestPackUnpack(t *testing.T) {
+-	out := new(Msg)
+-	out.Answer = make([]RR, 1)
+-	key := new(DNSKEY)
+-	key = &DNSKEY{Flags: 257, Protocol: 3, Algorithm: RSASHA1}
+-	key.Hdr = RR_Header{Name: "miek.nl.", Rrtype: TypeDNSKEY, Class: ClassINET, Ttl: 3600}
+-	key.PublicKey = "AwEAAaHIwpx3w4VHKi6i1LHnTaWeHCL154Jug0Rtc9ji5qwPXpBo6A5sRv7cSsPQKPIwxLpyCrbJ4mr2L0EPOdvP6z6YfljK2ZmTbogU9aSU2fiq/4wjxbdkLyoDVgtO+JsxNN4bjr4WcWhsmk1Hg93FV9ZpkWb0Tbad8DFqNDzr//kZ"
+-
+-	out.Answer[0] = key
+-	msg, err := out.Pack()
+-	if err != nil {
+-		t.Log("failed to pack msg with DNSKEY")
+-		t.Fail()
+-	}
+-	in := new(Msg)
+-	if in.Unpack(msg) != nil {
+-		t.Log("failed to unpack msg with DNSKEY")
+-		t.Fail()
+-	}
+-
+-	sig := new(RRSIG)
+-	sig = &RRSIG{TypeCovered: TypeDNSKEY, Algorithm: RSASHA1, Labels: 2,
+-		OrigTtl: 3600, Expiration: 4000, Inception: 4000, KeyTag: 34641, SignerName: "miek.nl.",
+-		Signature: "AwEAAaHIwpx3w4VHKi6i1LHnTaWeHCL154Jug0Rtc9ji5qwPXpBo6A5sRv7cSsPQKPIwxLpyCrbJ4mr2L0EPOdvP6z6YfljK2ZmTbogU9aSU2fiq/4wjxbdkLyoDVgtO+JsxNN4bjr4WcWhsmk1Hg93FV9ZpkWb0Tbad8DFqNDzr//kZ"}
+-	sig.Hdr = RR_Header{Name: "miek.nl.", Rrtype: TypeRRSIG, Class: ClassINET, Ttl: 3600}
+-
+-	out.Answer[0] = sig
+-	msg, err = out.Pack()
+-	if err != nil {
+-		t.Log("failed to pack msg with RRSIG")
+-		t.Fail()
+-	}
+-
+-	if in.Unpack(msg) != nil {
+-		t.Log("failed to unpack msg with RRSIG")
+-		t.Fail()
+-	}
+-}
+-
+-func TestPackUnpack2(t *testing.T) {
+-	m := new(Msg)
+-	m.Extra = make([]RR, 1)
+-	m.Answer = make([]RR, 1)
+-	dom := "miek.nl."
+-	rr := new(A)
+-	rr.Hdr = RR_Header{Name: dom, Rrtype: TypeA, Class: ClassINET, Ttl: 0}
+-	rr.A = net.IPv4(127, 0, 0, 1)
+-
+-	x := new(TXT)
+-	x.Hdr = RR_Header{Name: dom, Rrtype: TypeTXT, Class: ClassINET, Ttl: 0}
+-	x.Txt = []string{"heelalaollo"}
+-
+-	m.Extra[0] = x
+-	m.Answer[0] = rr
+-	_, err := m.Pack()
+-	if err != nil {
+-		t.Log("Packing failed: " + err.Error())
+-		t.Fail()
+-		return
+-	}
+-}
+-
+-func TestPackUnpack3(t *testing.T) {
+-	m := new(Msg)
+-	m.Extra = make([]RR, 2)
+-	m.Answer = make([]RR, 1)
+-	dom := "miek.nl."
+-	rr := new(A)
+-	rr.Hdr = RR_Header{Name: dom, Rrtype: TypeA, Class: ClassINET, Ttl: 0}
+-	rr.A = net.IPv4(127, 0, 0, 1)
+-
+-	x1 := new(TXT)
+-	x1.Hdr = RR_Header{Name: dom, Rrtype: TypeTXT, Class: ClassINET, Ttl: 0}
+-	x1.Txt = []string{}
+-
+-	x2 := new(TXT)
+-	x2.Hdr = RR_Header{Name: dom, Rrtype: TypeTXT, Class: ClassINET, Ttl: 0}
+-	x2.Txt = []string{"heelalaollo"}
+-
+-	m.Extra[0] = x1
+-	m.Extra[1] = x2
+-	m.Answer[0] = rr
+-	b, err := m.Pack()
+-	if err != nil {
+-		t.Log("packing failed: " + err.Error())
+-		t.Fail()
+-		return
+-	}
+-
+-	var unpackMsg Msg
+-	err = unpackMsg.Unpack(b)
+-	if err != nil {
+-		t.Log("unpacking failed")
+-		t.Fail()
+-		return
+-	}
+-}
+-
+-func TestBailiwick(t *testing.T) {
+-	yes := map[string]string{
+-		"miek.nl": "ns.miek.nl",
+-		".":       "miek.nl",
+-	}
+-	for parent, child := range yes {
+-		if !IsSubDomain(parent, child) {
+-			t.Logf("%s should be child of %s\n", child, parent)
+-			t.Logf("comparelabels %d", CompareDomainName(parent, child))
+-			t.Logf("lenlabels %d %d", CountLabel(parent), CountLabel(child))
+-			t.Fail()
+-		}
+-	}
+-	no := map[string]string{
+-		"www.miek.nl":  "ns.miek.nl",
+-		"m\\.iek.nl":   "ns.miek.nl",
+-		"w\\.iek.nl":   "w.iek.nl",
+-		"p\\\\.iek.nl": "ns.p.iek.nl", // p\\.iek.nl , literal \ in domain name
+-		"miek.nl":      ".",
+-	}
+-	for parent, child := range no {
+-		if IsSubDomain(parent, child) {
+-			t.Logf("%s should not be child of %s\n", child, parent)
+-			t.Logf("comparelabels %d", CompareDomainName(parent, child))
+-			t.Logf("lenlabels %d %d", CountLabel(parent), CountLabel(child))
+-			t.Fail()
+-		}
+-	}
+-}
+-
+-func TestPack(t *testing.T) {
+-	rr := []string{"US.    86400	IN	NSEC	0-.us. NS SOA RRSIG NSEC DNSKEY TYPE65534"}
+-	m := new(Msg)
+-	var err error
+-	m.Answer = make([]RR, 1)
+-	for _, r := range rr {
+-		m.Answer[0], err = NewRR(r)
+-		if err != nil {
+-			t.Logf("failed to create RR: %s\n", err.Error())
+-			t.Fail()
+-			continue
+-		}
+-		if _, err := m.Pack(); err != nil {
+-			t.Logf("packing failed: %s\n", err.Error())
+-			t.Fail()
+-		}
+-	}
+-	x := new(Msg)
+-	ns, _ := NewRR("pool.ntp.org.   390 IN  NS  a.ntpns.org")
+-	ns.(*NS).Ns = "a.ntpns.org"
+-	x.Ns = append(m.Ns, ns)
+-	x.Ns = append(m.Ns, ns)
+-	x.Ns = append(m.Ns, ns)
+-	// This crashes due to the fact the a.ntpns.org isn't a FQDN
+-	// How to recover() from a remove panic()?
+-	if _, err := x.Pack(); err == nil {
+-		t.Log("packing should fail")
+-		t.Fail()
+-	}
+-	x.Answer = make([]RR, 1)
+-	x.Answer[0], err = NewRR(rr[0])
+-	if _, err := x.Pack(); err == nil {
+-		t.Log("packing should fail")
+-		t.Fail()
+-	}
+-	x.Question = make([]Question, 1)
+-	x.Question[0] = Question{";sd#edddds鍛↙赏‘℅∥↙xzztsestxssweewwsssstx at s@Z嵌e at cn.pool.ntp.org.", TypeA, ClassINET}
+-	if _, err := x.Pack(); err == nil {
+-		t.Log("packing should fail")
+-		t.Fail()
+-	}
+-}
+-
+-func TestPackNAPTR(t *testing.T) {
+-	for _, n := range []string{
+-		`apple.com. IN NAPTR   100 50 "se" "SIP+D2U" "" _sip._udp.apple.com.`,
+-		`apple.com. IN NAPTR   90 50 "se" "SIP+D2T" "" _sip._tcp.apple.com.`,
+-		`apple.com. IN NAPTR   50 50 "se" "SIPS+D2T" "" _sips._tcp.apple.com.`,
+-	} {
+-		rr, _ := NewRR(n)
+-		msg := make([]byte, rr.len())
+-		if off, err := PackRR(rr, msg, 0, nil, false); err != nil {
+-			t.Logf("packing failed: %s", err.Error())
+-			t.Logf("length %d, need more than %d\n", rr.len(), off)
+-			t.Fail()
+-		} else {
+-			t.Logf("buf size needed: %d\n", off)
+-		}
+-	}
+-}
+-
+-func TestCompressLength(t *testing.T) {
+-	m := new(Msg)
+-	m.SetQuestion("miek.nl", TypeMX)
+-	ul := m.Len()
+-	m.Compress = true
+-	if ul != m.Len() {
+-		t.Fatalf("should be equal")
+-	}
+-}
+-
+-// Does the predicted length match final packed length?
+-func TestMsgCompressLength(t *testing.T) {
+-	makeMsg := func(question string, ans, ns, e []RR) *Msg {
+-		msg := new(Msg)
+-		msg.SetQuestion(Fqdn(question), TypeANY)
+-		msg.Answer = append(msg.Answer, ans...)
+-		msg.Ns = append(msg.Ns, ns...)
+-		msg.Extra = append(msg.Extra, e...)
+-		msg.Compress = true
+-		return msg
+-	}
+-
+-	name1 := "12345678901234567890123456789012345.12345678.123."
+-	rrA, _ := NewRR(name1 + " 3600 IN A 192.0.2.1")
+-	rrMx, _ := NewRR(name1 + " 3600 IN MX 10 " + name1)
+-	tests := []*Msg{
+-		makeMsg(name1, []RR{rrA}, nil, nil),
+-		makeMsg(name1, []RR{rrMx, rrMx}, nil, nil)}
+-
+-	for _, msg := range tests {
+-		predicted := msg.Len()
+-		buf, err := msg.Pack()
+-		if err != nil {
+-			t.Error(err)
+-			t.Fail()
+-		}
+-		if predicted < len(buf) {
+-			t.Errorf("predicted compressed length is wrong: predicted %s (len=%d) %d, actual %d\n",
+-				msg.Question[0].Name, len(msg.Answer), predicted, len(buf))
+-			t.Fail()
+-		}
+-	}
+-}
+-
+-func TestMsgLength(t *testing.T) {
+-	makeMsg := func(question string, ans, ns, e []RR) *Msg {
+-		msg := new(Msg)
+-		msg.SetQuestion(Fqdn(question), TypeANY)
+-		msg.Answer = append(msg.Answer, ans...)
+-		msg.Ns = append(msg.Ns, ns...)
+-		msg.Extra = append(msg.Extra, e...)
+-		return msg
+-	}
+-
+-	name1 := "12345678901234567890123456789012345.12345678.123."
+-	rrA, _ := NewRR(name1 + " 3600 IN A 192.0.2.1")
+-	rrMx, _ := NewRR(name1 + " 3600 IN MX 10 " + name1)
+-	tests := []*Msg{
+-		makeMsg(name1, []RR{rrA}, nil, nil),
+-		makeMsg(name1, []RR{rrMx, rrMx}, nil, nil)}
+-
+-	for _, msg := range tests {
+-		predicted := msg.Len()
+-		buf, err := msg.Pack()
+-		if err != nil {
+-			t.Error(err)
+-			t.Fail()
+-		}
+-		if predicted < len(buf) {
+-			t.Errorf("predicted length is wrong: predicted %s (len=%d), actual %d\n",
+-				msg.Question[0].Name, predicted, len(buf))
+-			t.Fail()
+-		}
+-	}
+-}
+-
+-func TestMsgLength2(t *testing.T) {
+-	// Serialized replies
+-	var testMessages = []string{
+-		// google.com. IN A?
+-		"064e81800001000b0004000506676f6f676c6503636f6d0000010001c00c00010001000000050004adc22986c00c00010001000000050004adc22987c00c00010001000000050004adc22988c00c00010001000000050004adc22989c00c00010001000000050004adc2298ec00c00010001000000050004adc22980c00c00010001000000050004adc22981c00c00010001000000050004adc22982c00c00010001000000050004adc22983c00c00010001000000050004adc22984c00c00010001000000050004adc22985c00c00020001000000050006036e7331c00cc00c00020001000000050006036e7332c00cc00c00020001000000050006036e7333c00cc00c00020001000000050006036e7334c00cc0d800010001000000050004d8ef200ac0ea00010001000000050004d8ef220ac0fc00010001000000050004d8ef240ac10e00010001000000050004d8ef260a0000290500000000050000",
+-		// amazon.com. IN A? (reply has no EDNS0 record)
+-		// TODO(miek): this one is off-by-one, need to find out why
+-		//"6de1818000010004000a000806616d617a6f6e03636f6d0000010001c00c000100010000000500044815c2d4c00c000100010000000500044815d7e8c00c00010001000000050004b02062a6c00c00010001000000050004cdfbf236c00c000200010000000500140570646e733408756c747261646e73036f726700c00c000200010000000500150570646e733508756c747261646e7304696e666f00c00c000200010000000500160570646e733608756c747261646e7302636f02756b00c00c00020001000000050014036e7331037033310664796e656374036e657400c00c00020001000000050006036e7332c0cfc00c00020001000000050006036e7333c0cfc00c00020001000000050006036e7334c0cfc00c000200010000000500110570646e733108756c747261646e73c0dac00c000200010000000500080570646e7332c127c00c000200010000000500080570646e7333c06ec0cb00010001000000050004d04e461fc0eb00010001000000050004cc0dfa1fc0fd00010001000000050004d04e471fc10f00010001000000050004cc0dfb1fc12100010001000000050004cc4a6c01c121001c000100000005001020010502f3ff00000000000000000001c13e00010001000000050004cc4a6d01c13e001c0001000000050010261000a1101400000000000000000001",
+-		// yahoo.com. IN A?
+-		"fc2d81800001000300070008057961686f6f03636f6d0000010001c00c00010001000000050004628afd6dc00c00010001000000050004628bb718c00c00010001000000050004cebe242dc00c00020001000000050006036e7336c00cc00c00020001000000050006036e7338c00cc00c00020001000000050006036e7331c00cc00c00020001000000050006036e7332c00cc00c00020001000000050006036e7333c00cc00c00020001000000050006036e7334c00cc00c00020001000000050006036e7335c00cc07b0001000100000005000444b48310c08d00010001000000050004448eff10c09f00010001000000050004cb54dd35c0b100010001000000050004628a0b9dc0c30001000100000005000477a0f77cc05700010001000000050004ca2bdfaac06900010001000000050004caa568160000290500000000050000",
+-		// microsoft.com. IN A?
+-		"f4368180000100020005000b096d6963726f736f667403636f6d0000010001c00c0001000100000005000440040b25c00c0001000100000005000441373ac9c00c0002000100000005000e036e7331046d736674036e657400c00c00020001000000050006036e7332c04fc00c00020001000000050006036e7333c04fc00c00020001000000050006036e7334c04fc00c00020001000000050006036e7335c04fc04b000100010000000500044137253ec04b001c00010000000500102a010111200500000000000000010001c0650001000100000005000440043badc065001c00010000000500102a010111200600060000000000010001c07700010001000000050004d5c7b435c077001c00010000000500102a010111202000000000000000010001c08900010001000000050004cf2e4bfec089001c00010000000500102404f800200300000000000000010001c09b000100010000000500044137e28cc09b001c00010000000500102a010111200f000100000000000100010000290500000000050000",
+-		// google.com. IN MX?
+-		"724b8180000100050004000b06676f6f676c6503636f6d00000f0001c00c000f000100000005000c000a056173706d78016cc00cc00c000f0001000000050009001404616c7431c02ac00c000f0001000000050009001e04616c7432c02ac00c000f0001000000050009002804616c7433c02ac00c000f0001000000050009003204616c7434c02ac00c00020001000000050006036e7332c00cc00c00020001000000050006036e7333c00cc00c00020001000000050006036e7334c00cc00c00020001000000050006036e7331c00cc02a00010001000000050004adc2421bc02a001c00010000000500102a00145040080c01000000000000001bc04200010001000000050004adc2461bc05700010001000000050004adc2451bc06c000100010000000500044a7d8f1bc081000100010000000500044a7d191bc0ca00010001000000050004d8ef200ac09400010001000000050004d8ef220ac0a600010001000000050004d8ef240ac0b800010001000000050004d8ef260a0000290500000000050000",
+-		// reddit.com. IN A?
+-		"12b98180000100080000000c0672656464697403636f6d0000020001c00c0002000100000005000f046175733204616b616d036e657400c00c000200010000000500070475736534c02dc00c000200010000000500070475737733c02dc00c000200010000000500070475737735c02dc00c00020001000000050008056173696131c02dc00c00020001000000050008056173696139c02dc00c00020001000000050008056e73312d31c02dc00c0002000100000005000a076e73312d313935c02dc02800010001000000050004c30a242ec04300010001000000050004451f1d39c05600010001000000050004451f3bc7c0690001000100000005000460073240c07c000100010000000500046007fb81c090000100010000000500047c283484c090001c00010000000500102a0226f0006700000000000000000064c0a400010001000000050004c16c5b01c0a4001c000100000005001026001401000200000000000000000001c0b800010001000000050004c16c5bc3c0b8001c0001000000050010260014010002000000000000000000c30000290500000000050000",
+-	}
+-
+-	for i, hexData := range testMessages {
+-		// we won't fail the decoding of the hex
+-		input, _ := hex.DecodeString(hexData)
+-		m := new(Msg)
+-		m.Unpack(input)
+-		//println(m.String())
+-		m.Compress = true
+-		lenComp := m.Len()
+-		b, _ := m.Pack()
+-		pacComp := len(b)
+-		m.Compress = false
+-		lenUnComp := m.Len()
+-		b, _ = m.Pack()
+-		pacUnComp := len(b)
+-		if pacComp+1 != lenComp {
+-			t.Errorf("msg.Len(compressed)=%d actual=%d for test %d", lenComp, pacComp, i)
+-		}
+-		if pacUnComp+1 != lenUnComp {
+-			t.Errorf("msg.Len(uncompressed)=%d actual=%d for test %d", lenUnComp, pacUnComp, i)
+-		}
+-	}
+-}
+-
+-func TestMsgLengthCompressionMalformed(t *testing.T) {
+-	// SOA with empty hostmaster, which is illegal
+-	soa := &SOA{Hdr: RR_Header{Name: ".", Rrtype: TypeSOA, Class: ClassINET, Ttl: 12345},
+-		Ns:      ".",
+-		Mbox:    "",
+-		Serial:  0,
+-		Refresh: 28800,
+-		Retry:   7200,
+-		Expire:  604800,
+-		Minttl:  60}
+-	m := new(Msg)
+-	m.Compress = true
+-	m.Ns = []RR{soa}
+-	m.Len() // Should not crash.
+-}
+-
+-func BenchmarkMsgLength(b *testing.B) {
+-	b.StopTimer()
+-	makeMsg := func(question string, ans, ns, e []RR) *Msg {
+-		msg := new(Msg)
+-		msg.SetQuestion(Fqdn(question), TypeANY)
+-		msg.Answer = append(msg.Answer, ans...)
+-		msg.Ns = append(msg.Ns, ns...)
+-		msg.Extra = append(msg.Extra, e...)
+-		msg.Compress = true
+-		return msg
+-	}
+-	name1 := "12345678901234567890123456789012345.12345678.123."
+-	rrMx, _ := NewRR(name1 + " 3600 IN MX 10 " + name1)
+-	msg := makeMsg(name1, []RR{rrMx, rrMx}, nil, nil)
+-	b.StartTimer()
+-	for i := 0; i < b.N; i++ {
+-		msg.Len()
+-	}
+-}
+-
+-func BenchmarkMsgLengthPack(b *testing.B) {
+-	makeMsg := func(question string, ans, ns, e []RR) *Msg {
+-		msg := new(Msg)
+-		msg.SetQuestion(Fqdn(question), TypeANY)
+-		msg.Answer = append(msg.Answer, ans...)
+-		msg.Ns = append(msg.Ns, ns...)
+-		msg.Extra = append(msg.Extra, e...)
+-		msg.Compress = true
+-		return msg
+-	}
+-	name1 := "12345678901234567890123456789012345.12345678.123."
+-	rrMx, _ := NewRR(name1 + " 3600 IN MX 10 " + name1)
+-	msg := makeMsg(name1, []RR{rrMx, rrMx}, nil, nil)
+-	b.ResetTimer()
+-	for i := 0; i < b.N; i++ {
+-		_, _ = msg.Pack()
+-	}
+-}
+-
+-func BenchmarkMsgPackBuffer(b *testing.B) {
+-	makeMsg := func(question string, ans, ns, e []RR) *Msg {
+-		msg := new(Msg)
+-		msg.SetQuestion(Fqdn(question), TypeANY)
+-		msg.Answer = append(msg.Answer, ans...)
+-		msg.Ns = append(msg.Ns, ns...)
+-		msg.Extra = append(msg.Extra, e...)
+-		msg.Compress = true
+-		return msg
+-	}
+-	name1 := "12345678901234567890123456789012345.12345678.123."
+-	rrMx, _ := NewRR(name1 + " 3600 IN MX 10 " + name1)
+-	msg := makeMsg(name1, []RR{rrMx, rrMx}, nil, nil)
+-	buf := make([]byte, 512)
+-	b.ResetTimer()
+-	for i := 0; i < b.N; i++ {
+-		_, _ = msg.PackBuffer(buf)
+-	}
+-}
+-
+-func BenchmarkMsgUnpack(b *testing.B) {
+-	makeMsg := func(question string, ans, ns, e []RR) *Msg {
+-		msg := new(Msg)
+-		msg.SetQuestion(Fqdn(question), TypeANY)
+-		msg.Answer = append(msg.Answer, ans...)
+-		msg.Ns = append(msg.Ns, ns...)
+-		msg.Extra = append(msg.Extra, e...)
+-		msg.Compress = true
+-		return msg
+-	}
+-	name1 := "12345678901234567890123456789012345.12345678.123."
+-	rrMx, _ := NewRR(name1 + " 3600 IN MX 10 " + name1)
+-	msg := makeMsg(name1, []RR{rrMx, rrMx}, nil, nil)
+-	msg_buf, _ := msg.Pack()
+-	b.ResetTimer()
+-	for i := 0; i < b.N; i++ {
+-		_ = msg.Unpack(msg_buf)
+-	}
+-}
+-
+-func BenchmarkPackDomainName(b *testing.B) {
+-	name1 := "12345678901234567890123456789012345.12345678.123."
+-	buf := make([]byte, len(name1)+1)
+-	b.ResetTimer()
+-	for i := 0; i < b.N; i++ {
+-		_, _ = PackDomainName(name1, buf, 0, nil, false)
+-	}
+-}
+-
+-func BenchmarkUnpackDomainName(b *testing.B) {
+-	name1 := "12345678901234567890123456789012345.12345678.123."
+-	buf := make([]byte, len(name1)+1)
+-	_, _ = PackDomainName(name1, buf, 0, nil, false)
+-	b.ResetTimer()
+-	for i := 0; i < b.N; i++ {
+-		_, _, _ = UnpackDomainName(buf, 0)
+-	}
+-}
+-
+-func BenchmarkUnpackDomainNameUnprintable(b *testing.B) {
+-	name1 := "\x02\x02\x02\x025\x02\x02\x02\x02.12345678.123."
+-	buf := make([]byte, len(name1)+1)
+-	_, _ = PackDomainName(name1, buf, 0, nil, false)
+-	b.ResetTimer()
+-	for i := 0; i < b.N; i++ {
+-		_, _, _ = UnpackDomainName(buf, 0)
+-	}
+-}
+-
+-func TestToRFC3597(t *testing.T) {
+-	a, _ := NewRR("miek.nl. IN A 10.0.1.1")
+-	x := new(RFC3597)
+-	x.ToRFC3597(a)
+-	if x.String() != `miek.nl.	3600	CLASS1	TYPE1	\# 4 0a000101` {
+-		t.Fail()
+-	}
+-}
+-
+-func TestNoRdataPack(t *testing.T) {
+-	data := make([]byte, 1024)
+-	for typ, fn := range typeToRR {
+-		if typ == TypeCAA {
+-			continue // TODO(miek): known omission
+-		}
+-		r := fn()
+-		*r.Header() = RR_Header{Name: "miek.nl.", Rrtype: typ, Class: ClassINET, Ttl: 3600}
+-		_, e := PackRR(r, data, 0, nil, false)
+-		if e != nil {
+-			t.Logf("failed to pack RR with zero rdata: %s: %s\n", TypeToString[typ], e.Error())
+-			t.Fail()
+-		}
+-	}
+-}
+-
+-// TODO(miek): fix dns buffer too small errors this throws
+-func TestNoRdataUnpack(t *testing.T) {
+-	data := make([]byte, 1024)
+-	for typ, fn := range typeToRR {
+-		if typ == TypeSOA || typ == TypeTSIG || typ == TypeWKS {
+-			// SOA, TSIG will not be seen (like this) in dyn. updates?
+-			// WKS is an bug, but...deprecated record.
+-			continue
+-		}
+-		r := fn()
+-		*r.Header() = RR_Header{Name: "miek.nl.", Rrtype: typ, Class: ClassINET, Ttl: 3600}
+-		off, e := PackRR(r, data, 0, nil, false)
+-		if e != nil {
+-			// Should always works, TestNoDataPack should have catched this
+-			continue
+-		}
+-		rr, _, e := UnpackRR(data[:off], 0)
+-		if e != nil {
+-			t.Logf("failed to unpack RR with zero rdata: %s: %s\n", TypeToString[typ], e.Error())
+-			t.Fail()
+-		}
+-		t.Logf("%s\n", rr)
+-	}
+-}
+-
+-func TestRdataOverflow(t *testing.T) {
+-	rr := new(RFC3597)
+-	rr.Hdr.Name = "."
+-	rr.Hdr.Class = ClassINET
+-	rr.Hdr.Rrtype = 65280
+-	rr.Rdata = hex.EncodeToString(make([]byte, 0xFFFF))
+-	buf := make([]byte, 0xFFFF*2)
+-	if _, err := PackRR(rr, buf, 0, nil, false); err != nil {
+-		t.Fatalf("maximum size rrdata pack failed: %v", err)
+-	}
+-	rr.Rdata += "00"
+-	if _, err := PackRR(rr, buf, 0, nil, false); err != ErrRdata {
+-		t.Fatalf("oversize rrdata pack didn't return ErrRdata - instead: %v", err)
+-	}
+-}
+-
+-func TestCopy(t *testing.T) {
+-	rr, _ := NewRR("miek.nl. 2311 IN A 127.0.0.1") // Weird TTL to avoid catching TTL
+-	rr1 := Copy(rr)
+-	if rr.String() != rr1.String() {
+-		t.Fatalf("Copy() failed %s != %s", rr.String(), rr1.String())
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/dnssec.go b/Godeps/_workspace/src/github.com/miekg/dns/dnssec.go
+deleted file mode 100644
+index d1c2ae6..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/dnssec.go
++++ /dev/null
+@@ -1,756 +0,0 @@
+-// DNSSEC
+-//
+-// DNSSEC (DNS Security Extension) adds a layer of security to the DNS. It
+-// uses public key cryptography to sign resource records. The
+-// public keys are stored in DNSKEY records and the signatures in RRSIG records.
+-//
+-// Requesting DNSSEC information for a zone is done by adding the DO (DNSSEC OK) bit
+-// to an request.
+-//
+-//      m := new(dns.Msg)
+-//      m.SetEdns0(4096, true)
+-//
+-// Signature generation, signature verification and key generation are all supported.
+-package dns
+-
+-import (
+-	"bytes"
+-	"crypto"
+-	"crypto/dsa"
+-	"crypto/ecdsa"
+-	"crypto/elliptic"
+-	"crypto/md5"
+-	"crypto/rand"
+-	"crypto/rsa"
+-	"crypto/sha1"
+-	"crypto/sha256"
+-	"crypto/sha512"
+-	"encoding/hex"
+-	"hash"
+-	"io"
+-	"math/big"
+-	"sort"
+-	"strings"
+-	"time"
+-)
+-
+-// DNSSEC encryption algorithm codes.
+-const (
+-	_ uint8 = iota
+-	RSAMD5
+-	DH
+-	DSA
+-	_ // Skip 4, RFC 6725, section 2.1
+-	RSASHA1
+-	DSANSEC3SHA1
+-	RSASHA1NSEC3SHA1
+-	RSASHA256
+-	_ // Skip 9, RFC 6725, section 2.1
+-	RSASHA512
+-	_ // Skip 11, RFC 6725, section 2.1
+-	ECCGOST
+-	ECDSAP256SHA256
+-	ECDSAP384SHA384
+-	INDIRECT   uint8 = 252
+-	PRIVATEDNS uint8 = 253 // Private (experimental keys)
+-	PRIVATEOID uint8 = 254
+-)
+-
+-// DNSSEC hashing algorithm codes.
+-const (
+-	_      uint8 = iota
+-	SHA1         // RFC 4034
+-	SHA256       // RFC 4509
+-	GOST94       // RFC 5933
+-	SHA384       // Experimental
+-	SHA512       // Experimental
+-)
+-
+-// DNSKEY flag values.
+-const (
+-	SEP    = 1
+-	REVOKE = 1 << 7
+-	ZONE   = 1 << 8
+-)
+-
+-// The RRSIG needs to be converted to wireformat with some of
+-// the rdata (the signature) missing. Use this struct to easy
+-// the conversion (and re-use the pack/unpack functions).
+-type rrsigWireFmt struct {
+-	TypeCovered uint16
+-	Algorithm   uint8
+-	Labels      uint8
+-	OrigTtl     uint32
+-	Expiration  uint32
+-	Inception   uint32
+-	KeyTag      uint16
+-	SignerName  string `dns:"domain-name"`
+-	/* No Signature */
+-}
+-
+-// Used for converting DNSKEY's rdata to wirefmt.
+-type dnskeyWireFmt struct {
+-	Flags     uint16
+-	Protocol  uint8
+-	Algorithm uint8
+-	PublicKey string `dns:"base64"`
+-	/* Nothing is left out */
+-}
+-
+-func divRoundUp(a, b int) int {
+-	return (a + b - 1) / b
+-}
+-
+-// KeyTag calculates the keytag (or key-id) of the DNSKEY.
+-func (k *DNSKEY) KeyTag() uint16 {
+-	if k == nil {
+-		return 0
+-	}
+-	var keytag int
+-	switch k.Algorithm {
+-	case RSAMD5:
+-		// Look at the bottom two bytes of the modules, which the last
+-		// item in the pubkey. We could do this faster by looking directly
+-		// at the base64 values. But I'm lazy.
+-		modulus, _ := fromBase64([]byte(k.PublicKey))
+-		if len(modulus) > 1 {
+-			x, _ := unpackUint16(modulus, len(modulus)-2)
+-			keytag = int(x)
+-		}
+-	default:
+-		keywire := new(dnskeyWireFmt)
+-		keywire.Flags = k.Flags
+-		keywire.Protocol = k.Protocol
+-		keywire.Algorithm = k.Algorithm
+-		keywire.PublicKey = k.PublicKey
+-		wire := make([]byte, DefaultMsgSize)
+-		n, err := PackStruct(keywire, wire, 0)
+-		if err != nil {
+-			return 0
+-		}
+-		wire = wire[:n]
+-		for i, v := range wire {
+-			if i&1 != 0 {
+-				keytag += int(v) // must be larger than uint32
+-			} else {
+-				keytag += int(v) << 8
+-			}
+-		}
+-		keytag += (keytag >> 16) & 0xFFFF
+-		keytag &= 0xFFFF
+-	}
+-	return uint16(keytag)
+-}
+-
+-// ToDS converts a DNSKEY record to a DS record.
+-func (k *DNSKEY) ToDS(h uint8) *DS {
+-	if k == nil {
+-		return nil
+-	}
+-	ds := new(DS)
+-	ds.Hdr.Name = k.Hdr.Name
+-	ds.Hdr.Class = k.Hdr.Class
+-	ds.Hdr.Rrtype = TypeDS
+-	ds.Hdr.Ttl = k.Hdr.Ttl
+-	ds.Algorithm = k.Algorithm
+-	ds.DigestType = h
+-	ds.KeyTag = k.KeyTag()
+-
+-	keywire := new(dnskeyWireFmt)
+-	keywire.Flags = k.Flags
+-	keywire.Protocol = k.Protocol
+-	keywire.Algorithm = k.Algorithm
+-	keywire.PublicKey = k.PublicKey
+-	wire := make([]byte, DefaultMsgSize)
+-	n, err := PackStruct(keywire, wire, 0)
+-	if err != nil {
+-		return nil
+-	}
+-	wire = wire[:n]
+-
+-	owner := make([]byte, 255)
+-	off, err1 := PackDomainName(strings.ToLower(k.Hdr.Name), owner, 0, nil, false)
+-	if err1 != nil {
+-		return nil
+-	}
+-	owner = owner[:off]
+-	// RFC4034:
+-	// digest = digest_algorithm( DNSKEY owner name | DNSKEY RDATA);
+-	// "|" denotes concatenation
+-	// DNSKEY RDATA = Flags | Protocol | Algorithm | Public Key.
+-
+-	// digest buffer
+-	digest := append(owner, wire...) // another copy
+-
+-	switch h {
+-	case SHA1:
+-		s := sha1.New()
+-		io.WriteString(s, string(digest))
+-		ds.Digest = hex.EncodeToString(s.Sum(nil))
+-	case SHA256:
+-		s := sha256.New()
+-		io.WriteString(s, string(digest))
+-		ds.Digest = hex.EncodeToString(s.Sum(nil))
+-	case SHA384:
+-		s := sha512.New384()
+-		io.WriteString(s, string(digest))
+-		ds.Digest = hex.EncodeToString(s.Sum(nil))
+-	case GOST94:
+-		/* I have no clue */
+-	default:
+-		return nil
+-	}
+-	return ds
+-}
+-
+-// Sign signs an RRSet. The signature needs to be filled in with
+-// the values: Inception, Expiration, KeyTag, SignerName and Algorithm.
+-// The rest is copied from the RRset. Sign returns true when the signing went OK,
+-// otherwise false.
+-// There is no check if RRSet is a proper (RFC 2181) RRSet.
+-// If OrigTTL is non zero, it is used as-is, otherwise the TTL of the RRset
+-// is used as the OrigTTL.
+-func (rr *RRSIG) Sign(k PrivateKey, rrset []RR) error {
+-	if k == nil {
+-		return ErrPrivKey
+-	}
+-	// s.Inception and s.Expiration may be 0 (rollover etc.), the rest must be set
+-	if rr.KeyTag == 0 || len(rr.SignerName) == 0 || rr.Algorithm == 0 {
+-		return ErrKey
+-	}
+-
+-	rr.Hdr.Rrtype = TypeRRSIG
+-	rr.Hdr.Name = rrset[0].Header().Name
+-	rr.Hdr.Class = rrset[0].Header().Class
+-	if rr.OrigTtl == 0 { // If set don't override
+-		rr.OrigTtl = rrset[0].Header().Ttl
+-	}
+-	rr.TypeCovered = rrset[0].Header().Rrtype
+-	rr.Labels = uint8(CountLabel(rrset[0].Header().Name))
+-
+-	if strings.HasPrefix(rrset[0].Header().Name, "*") {
+-		rr.Labels-- // wildcard, remove from label count
+-	}
+-
+-	sigwire := new(rrsigWireFmt)
+-	sigwire.TypeCovered = rr.TypeCovered
+-	sigwire.Algorithm = rr.Algorithm
+-	sigwire.Labels = rr.Labels
+-	sigwire.OrigTtl = rr.OrigTtl
+-	sigwire.Expiration = rr.Expiration
+-	sigwire.Inception = rr.Inception
+-	sigwire.KeyTag = rr.KeyTag
+-	// For signing, lowercase this name
+-	sigwire.SignerName = strings.ToLower(rr.SignerName)
+-
+-	// Create the desired binary blob
+-	signdata := make([]byte, DefaultMsgSize)
+-	n, err := PackStruct(sigwire, signdata, 0)
+-	if err != nil {
+-		return err
+-	}
+-	signdata = signdata[:n]
+-	wire, err := rawSignatureData(rrset, rr)
+-	if err != nil {
+-		return err
+-	}
+-	signdata = append(signdata, wire...)
+-
+-	var sighash []byte
+-	var h hash.Hash
+-	var ch crypto.Hash // Only need for RSA
+-	var intlen int
+-	switch rr.Algorithm {
+-	case DSA, DSANSEC3SHA1:
+-		// Implicit in the ParameterSizes
+-	case RSASHA1, RSASHA1NSEC3SHA1:
+-		h = sha1.New()
+-		ch = crypto.SHA1
+-	case RSASHA256, ECDSAP256SHA256:
+-		h = sha256.New()
+-		ch = crypto.SHA256
+-		intlen = 32
+-	case ECDSAP384SHA384:
+-		h = sha512.New384()
+-		intlen = 48
+-	case RSASHA512:
+-		h = sha512.New()
+-		ch = crypto.SHA512
+-	case RSAMD5:
+-		fallthrough // Deprecated in RFC 6725
+-	default:
+-		return ErrAlg
+-	}
+-	io.WriteString(h, string(signdata))
+-	sighash = h.Sum(nil)
+-
+-	switch p := k.(type) {
+-	case *dsa.PrivateKey:
+-		r1, s1, err := dsa.Sign(rand.Reader, p, sighash)
+-		if err != nil {
+-			return err
+-		}
+-		signature := []byte{0x4D} // T value, here the ASCII M for Miek (not used in DNSSEC)
+-		signature = append(signature, intToBytes(r1, 20)...)
+-		signature = append(signature, intToBytes(s1, 20)...)
+-		rr.Signature = toBase64(signature)
+-	case *rsa.PrivateKey:
+-		// We can use nil as rand.Reader here (says AGL)
+-		signature, err := rsa.SignPKCS1v15(nil, p, ch, sighash)
+-		if err != nil {
+-			return err
+-		}
+-		rr.Signature = toBase64(signature)
+-	case *ecdsa.PrivateKey:
+-		r1, s1, err := ecdsa.Sign(rand.Reader, p, sighash)
+-		if err != nil {
+-			return err
+-		}
+-		signature := intToBytes(r1, intlen)
+-		signature = append(signature, intToBytes(s1, intlen)...)
+-		rr.Signature = toBase64(signature)
+-	default:
+-		// Not given the correct key
+-		return ErrKeyAlg
+-	}
+-	return nil
+-}
+-
+-// Verify validates an RRSet with the signature and key. This is only the
+-// cryptographic test, the signature validity period must be checked separately.
+-// This function copies the rdata of some RRs (to lowercase domain names) for the validation to work.
+-func (rr *RRSIG) Verify(k *DNSKEY, rrset []RR) error {
+-	// First the easy checks
+-	if len(rrset) == 0 {
+-		return ErrRRset
+-	}
+-	if rr.KeyTag != k.KeyTag() {
+-		return ErrKey
+-	}
+-	if rr.Hdr.Class != k.Hdr.Class {
+-		return ErrKey
+-	}
+-	if rr.Algorithm != k.Algorithm {
+-		return ErrKey
+-	}
+-	if strings.ToLower(rr.SignerName) != strings.ToLower(k.Hdr.Name) {
+-		return ErrKey
+-	}
+-	if k.Protocol != 3 {
+-		return ErrKey
+-	}
+-	for _, r := range rrset {
+-		if r.Header().Class != rr.Hdr.Class {
+-			return ErrRRset
+-		}
+-		if r.Header().Rrtype != rr.TypeCovered {
+-			return ErrRRset
+-		}
+-	}
+-	// RFC 4035 5.3.2.  Reconstructing the Signed Data
+-	// Copy the sig, except the rrsig data
+-	sigwire := new(rrsigWireFmt)
+-	sigwire.TypeCovered = rr.TypeCovered
+-	sigwire.Algorithm = rr.Algorithm
+-	sigwire.Labels = rr.Labels
+-	sigwire.OrigTtl = rr.OrigTtl
+-	sigwire.Expiration = rr.Expiration
+-	sigwire.Inception = rr.Inception
+-	sigwire.KeyTag = rr.KeyTag
+-	sigwire.SignerName = strings.ToLower(rr.SignerName)
+-	// Create the desired binary blob
+-	signeddata := make([]byte, DefaultMsgSize)
+-	n, err := PackStruct(sigwire, signeddata, 0)
+-	if err != nil {
+-		return err
+-	}
+-	signeddata = signeddata[:n]
+-	wire, err := rawSignatureData(rrset, rr)
+-	if err != nil {
+-		return err
+-	}
+-	signeddata = append(signeddata, wire...)
+-
+-	sigbuf := rr.sigBuf()           // Get the binary signature data
+-	if rr.Algorithm == PRIVATEDNS { // PRIVATEOID
+-		// TODO(mg)
+-		// remove the domain name and assume its our
+-	}
+-
+-	switch rr.Algorithm {
+-	case RSASHA1, RSASHA1NSEC3SHA1, RSASHA256, RSASHA512, RSAMD5:
+-		// TODO(mg): this can be done quicker, ie. cache the pubkey data somewhere??
+-		pubkey := k.publicKeyRSA() // Get the key
+-		if pubkey == nil {
+-			return ErrKey
+-		}
+-		// Setup the hash as defined for this alg.
+-		var h hash.Hash
+-		var ch crypto.Hash
+-		switch rr.Algorithm {
+-		case RSAMD5:
+-			h = md5.New()
+-			ch = crypto.MD5
+-		case RSASHA1, RSASHA1NSEC3SHA1:
+-			h = sha1.New()
+-			ch = crypto.SHA1
+-		case RSASHA256:
+-			h = sha256.New()
+-			ch = crypto.SHA256
+-		case RSASHA512:
+-			h = sha512.New()
+-			ch = crypto.SHA512
+-		}
+-		io.WriteString(h, string(signeddata))
+-		sighash := h.Sum(nil)
+-		return rsa.VerifyPKCS1v15(pubkey, ch, sighash, sigbuf)
+-	case ECDSAP256SHA256, ECDSAP384SHA384:
+-		pubkey := k.publicKeyCurve()
+-		if pubkey == nil {
+-			return ErrKey
+-		}
+-		var h hash.Hash
+-		switch rr.Algorithm {
+-		case ECDSAP256SHA256:
+-			h = sha256.New()
+-		case ECDSAP384SHA384:
+-			h = sha512.New384()
+-		}
+-		io.WriteString(h, string(signeddata))
+-		sighash := h.Sum(nil)
+-		// Split sigbuf into the r and s coordinates
+-		r := big.NewInt(0)
+-		r.SetBytes(sigbuf[:len(sigbuf)/2])
+-		s := big.NewInt(0)
+-		s.SetBytes(sigbuf[len(sigbuf)/2:])
+-		if ecdsa.Verify(pubkey, sighash, r, s) {
+-			return nil
+-		}
+-		return ErrSig
+-	}
+-	// Unknown alg
+-	return ErrAlg
+-}
+-
+-// ValidityPeriod uses RFC1982 serial arithmetic to calculate
+-// if a signature period is valid. If t is the zero time, the
+-// current time is taken other t is.
+-func (rr *RRSIG) ValidityPeriod(t time.Time) bool {
+-	var utc int64
+-	if t.IsZero() {
+-		utc = time.Now().UTC().Unix()
+-	} else {
+-		utc = t.UTC().Unix()
+-	}
+-	modi := (int64(rr.Inception) - utc) / year68
+-	mode := (int64(rr.Expiration) - utc) / year68
+-	ti := int64(rr.Inception) + (modi * year68)
+-	te := int64(rr.Expiration) + (mode * year68)
+-	return ti <= utc && utc <= te
+-}
+-
+-// Return the signatures base64 encodedig sigdata as a byte slice.
+-func (s *RRSIG) sigBuf() []byte {
+-	sigbuf, err := fromBase64([]byte(s.Signature))
+-	if err != nil {
+-		return nil
+-	}
+-	return sigbuf
+-}
+-
+-// setPublicKeyInPrivate sets the public key in the private key.
+-func (k *DNSKEY) setPublicKeyInPrivate(p PrivateKey) bool {
+-	switch t := p.(type) {
+-	case *dsa.PrivateKey:
+-		x := k.publicKeyDSA()
+-		if x == nil {
+-			return false
+-		}
+-		t.PublicKey = *x
+-	case *rsa.PrivateKey:
+-		x := k.publicKeyRSA()
+-		if x == nil {
+-			return false
+-		}
+-		t.PublicKey = *x
+-	case *ecdsa.PrivateKey:
+-		x := k.publicKeyCurve()
+-		if x == nil {
+-			return false
+-		}
+-		t.PublicKey = *x
+-	}
+-	return true
+-}
+-
+-// publicKeyRSA returns the RSA public key from a DNSKEY record.
+-func (k *DNSKEY) publicKeyRSA() *rsa.PublicKey {
+-	keybuf, err := fromBase64([]byte(k.PublicKey))
+-	if err != nil {
+-		return nil
+-	}
+-
+-	// RFC 2537/3110, section 2. RSA Public KEY Resource Records
+-	// Length is in the 0th byte, unless its zero, then it
+-	// it in bytes 1 and 2 and its a 16 bit number
+-	explen := uint16(keybuf[0])
+-	keyoff := 1
+-	if explen == 0 {
+-		explen = uint16(keybuf[1])<<8 | uint16(keybuf[2])
+-		keyoff = 3
+-	}
+-	pubkey := new(rsa.PublicKey)
+-
+-	pubkey.N = big.NewInt(0)
+-	shift := uint64((explen - 1) * 8)
+-	expo := uint64(0)
+-	for i := int(explen - 1); i > 0; i-- {
+-		expo += uint64(keybuf[keyoff+i]) << shift
+-		shift -= 8
+-	}
+-	// Remainder
+-	expo += uint64(keybuf[keyoff])
+-	if expo > 2<<31 {
+-		// Larger expo than supported.
+-		// println("dns: F5 primes (or larger) are not supported")
+-		return nil
+-	}
+-	pubkey.E = int(expo)
+-
+-	pubkey.N.SetBytes(keybuf[keyoff+int(explen):])
+-	return pubkey
+-}
+-
+-// publicKeyCurve returns the Curve public key from the DNSKEY record.
+-func (k *DNSKEY) publicKeyCurve() *ecdsa.PublicKey {
+-	keybuf, err := fromBase64([]byte(k.PublicKey))
+-	if err != nil {
+-		return nil
+-	}
+-	pubkey := new(ecdsa.PublicKey)
+-	switch k.Algorithm {
+-	case ECDSAP256SHA256:
+-		pubkey.Curve = elliptic.P256()
+-		if len(keybuf) != 64 {
+-			// wrongly encoded key
+-			return nil
+-		}
+-	case ECDSAP384SHA384:
+-		pubkey.Curve = elliptic.P384()
+-		if len(keybuf) != 96 {
+-			// Wrongly encoded key
+-			return nil
+-		}
+-	}
+-	pubkey.X = big.NewInt(0)
+-	pubkey.X.SetBytes(keybuf[:len(keybuf)/2])
+-	pubkey.Y = big.NewInt(0)
+-	pubkey.Y.SetBytes(keybuf[len(keybuf)/2:])
+-	return pubkey
+-}
+-
+-func (k *DNSKEY) publicKeyDSA() *dsa.PublicKey {
+-	keybuf, err := fromBase64([]byte(k.PublicKey))
+-	if err != nil {
+-		return nil
+-	}
+-	if len(keybuf) < 22 {
+-		return nil
+-	}
+-	t, keybuf := int(keybuf[0]), keybuf[1:]
+-	size := 64 + t*8
+-	q, keybuf := keybuf[:20], keybuf[20:]
+-	if len(keybuf) != 3*size {
+-		return nil
+-	}
+-	p, keybuf := keybuf[:size], keybuf[size:]
+-	g, y := keybuf[:size], keybuf[size:]
+-	pubkey := new(dsa.PublicKey)
+-	pubkey.Parameters.Q = big.NewInt(0).SetBytes(q)
+-	pubkey.Parameters.P = big.NewInt(0).SetBytes(p)
+-	pubkey.Parameters.G = big.NewInt(0).SetBytes(g)
+-	pubkey.Y = big.NewInt(0).SetBytes(y)
+-	return pubkey
+-}
+-
+-// Set the public key (the value E and N)
+-func (k *DNSKEY) setPublicKeyRSA(_E int, _N *big.Int) bool {
+-	if _E == 0 || _N == nil {
+-		return false
+-	}
+-	buf := exponentToBuf(_E)
+-	buf = append(buf, _N.Bytes()...)
+-	k.PublicKey = toBase64(buf)
+-	return true
+-}
+-
+-// Set the public key for Elliptic Curves
+-func (k *DNSKEY) setPublicKeyCurve(_X, _Y *big.Int) bool {
+-	if _X == nil || _Y == nil {
+-		return false
+-	}
+-	var intlen int
+-	switch k.Algorithm {
+-	case ECDSAP256SHA256:
+-		intlen = 32
+-	case ECDSAP384SHA384:
+-		intlen = 48
+-	}
+-	k.PublicKey = toBase64(curveToBuf(_X, _Y, intlen))
+-	return true
+-}
+-
+-// Set the public key for DSA
+-func (k *DNSKEY) setPublicKeyDSA(_Q, _P, _G, _Y *big.Int) bool {
+-	if _Q == nil || _P == nil || _G == nil || _Y == nil {
+-		return false
+-	}
+-	buf := dsaToBuf(_Q, _P, _G, _Y)
+-	k.PublicKey = toBase64(buf)
+-	return true
+-}
+-
+-// Set the public key (the values E and N) for RSA
+-// RFC 3110: Section 2. RSA Public KEY Resource Records
+-func exponentToBuf(_E int) []byte {
+-	var buf []byte
+-	i := big.NewInt(int64(_E))
+-	if len(i.Bytes()) < 256 {
+-		buf = make([]byte, 1)
+-		buf[0] = uint8(len(i.Bytes()))
+-	} else {
+-		buf = make([]byte, 3)
+-		buf[0] = 0
+-		buf[1] = uint8(len(i.Bytes()) >> 8)
+-		buf[2] = uint8(len(i.Bytes()))
+-	}
+-	buf = append(buf, i.Bytes()...)
+-	return buf
+-}
+-
+-// Set the public key for X and Y for Curve. The two
+-// values are just concatenated.
+-func curveToBuf(_X, _Y *big.Int, intlen int) []byte {
+-	buf := intToBytes(_X, intlen)
+-	buf = append(buf, intToBytes(_Y, intlen)...)
+-	return buf
+-}
+-
+-// Set the public key for X and Y for Curve. The two
+-// values are just concatenated.
+-func dsaToBuf(_Q, _P, _G, _Y *big.Int) []byte {
+-	t := divRoundUp(divRoundUp(_G.BitLen(), 8)-64, 8)
+-	buf := []byte{byte(t)}
+-	buf = append(buf, intToBytes(_Q, 20)...)
+-	buf = append(buf, intToBytes(_P, 64+t*8)...)
+-	buf = append(buf, intToBytes(_G, 64+t*8)...)
+-	buf = append(buf, intToBytes(_Y, 64+t*8)...)
+-	return buf
+-}
+-
+-type wireSlice [][]byte
+-
+-func (p wireSlice) Len() int      { return len(p) }
+-func (p wireSlice) Swap(i, j int) { p[i], p[j] = p[j], p[i] }
+-func (p wireSlice) Less(i, j int) bool {
+-	_, ioff, _ := UnpackDomainName(p[i], 0)
+-	_, joff, _ := UnpackDomainName(p[j], 0)
+-	return bytes.Compare(p[i][ioff+10:], p[j][joff+10:]) < 0
+-}
+-
+-// Return the raw signature data.
+-func rawSignatureData(rrset []RR, s *RRSIG) (buf []byte, err error) {
+-	wires := make(wireSlice, len(rrset))
+-	for i, r := range rrset {
+-		r1 := r.copy()
+-		r1.Header().Ttl = s.OrigTtl
+-		labels := SplitDomainName(r1.Header().Name)
+-		// 6.2. Canonical RR Form. (4) - wildcards
+-		if len(labels) > int(s.Labels) {
+-			// Wildcard
+-			r1.Header().Name = "*." + strings.Join(labels[len(labels)-int(s.Labels):], ".") + "."
+-		}
+-		// RFC 4034: 6.2.  Canonical RR Form. (2) - domain name to lowercase
+-		r1.Header().Name = strings.ToLower(r1.Header().Name)
+-		// 6.2. Canonical RR Form. (3) - domain rdata to lowercase.
+-		//   NS, MD, MF, CNAME, SOA, MB, MG, MR, PTR,
+-		//   HINFO, MINFO, MX, RP, AFSDB, RT, SIG, PX, NXT, NAPTR, KX,
+-		//   SRV, DNAME, A6
+-		switch x := r1.(type) {
+-		case *NS:
+-			x.Ns = strings.ToLower(x.Ns)
+-		case *CNAME:
+-			x.Target = strings.ToLower(x.Target)
+-		case *SOA:
+-			x.Ns = strings.ToLower(x.Ns)
+-			x.Mbox = strings.ToLower(x.Mbox)
+-		case *MB:
+-			x.Mb = strings.ToLower(x.Mb)
+-		case *MG:
+-			x.Mg = strings.ToLower(x.Mg)
+-		case *MR:
+-			x.Mr = strings.ToLower(x.Mr)
+-		case *PTR:
+-			x.Ptr = strings.ToLower(x.Ptr)
+-		case *MINFO:
+-			x.Rmail = strings.ToLower(x.Rmail)
+-			x.Email = strings.ToLower(x.Email)
+-		case *MX:
+-			x.Mx = strings.ToLower(x.Mx)
+-		case *NAPTR:
+-			x.Replacement = strings.ToLower(x.Replacement)
+-		case *KX:
+-			x.Exchanger = strings.ToLower(x.Exchanger)
+-		case *SRV:
+-			x.Target = strings.ToLower(x.Target)
+-		case *DNAME:
+-			x.Target = strings.ToLower(x.Target)
+-		}
+-		// 6.2. Canonical RR Form. (5) - origTTL
+-		wire := make([]byte, r1.len()+1) // +1 to be safe(r)
+-		off, err1 := PackRR(r1, wire, 0, nil, false)
+-		if err1 != nil {
+-			return nil, err1
+-		}
+-		wire = wire[:off]
+-		wires[i] = wire
+-	}
+-	sort.Sort(wires)
+-	for _, wire := range wires {
+-		buf = append(buf, wire...)
+-	}
+-	return buf, nil
+-}
+-
+-// Map for algorithm names.
+-var AlgorithmToString = map[uint8]string{
+-	RSAMD5:           "RSAMD5",
+-	DH:               "DH",
+-	DSA:              "DSA",
+-	RSASHA1:          "RSASHA1",
+-	DSANSEC3SHA1:     "DSA-NSEC3-SHA1",
+-	RSASHA1NSEC3SHA1: "RSASHA1-NSEC3-SHA1",
+-	RSASHA256:        "RSASHA256",
+-	RSASHA512:        "RSASHA512",
+-	ECCGOST:          "ECC-GOST",
+-	ECDSAP256SHA256:  "ECDSAP256SHA256",
+-	ECDSAP384SHA384:  "ECDSAP384SHA384",
+-	INDIRECT:         "INDIRECT",
+-	PRIVATEDNS:       "PRIVATEDNS",
+-	PRIVATEOID:       "PRIVATEOID",
+-}
+-
+-// Map of algorithm strings.
+-var StringToAlgorithm = reverseInt8(AlgorithmToString)
+-
+-// Map for hash names.
+-var HashToString = map[uint8]string{
+-	SHA1:   "SHA1",
+-	SHA256: "SHA256",
+-	GOST94: "GOST94",
+-	SHA384: "SHA384",
+-	SHA512: "SHA512",
+-}
+-
+-// Map of hash strings.
+-var StringToHash = reverseInt8(HashToString)
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/dnssec_test.go b/Godeps/_workspace/src/github.com/miekg/dns/dnssec_test.go
+deleted file mode 100644
+index f6263d5..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/dnssec_test.go
++++ /dev/null
+@@ -1,672 +0,0 @@
+-package dns
+-
+-import (
+-	"crypto/rsa"
+-	"reflect"
+-	"strings"
+-	"testing"
+-	"time"
+-)
+-
+-func getKey() *DNSKEY {
+-	key := new(DNSKEY)
+-	key.Hdr.Name = "miek.nl."
+-	key.Hdr.Class = ClassINET
+-	key.Hdr.Ttl = 14400
+-	key.Flags = 256
+-	key.Protocol = 3
+-	key.Algorithm = RSASHA256
+-	key.PublicKey = "AwEAAcNEU67LJI5GEgF9QLNqLO1SMq1EdoQ6E9f85ha0k0ewQGCblyW2836GiVsm6k8Kr5ECIoMJ6fZWf3CQSQ9ycWfTyOHfmI3eQ/1Covhb2y4bAmL/07PhrL7ozWBW3wBfM335Ft9xjtXHPy7ztCbV9qZ4TVDTW/Iyg0PiwgoXVesz"
+-	return key
+-}
+-
+-func getSoa() *SOA {
+-	soa := new(SOA)
+-	soa.Hdr = RR_Header{"miek.nl.", TypeSOA, ClassINET, 14400, 0}
+-	soa.Ns = "open.nlnetlabs.nl."
+-	soa.Mbox = "miekg.atoom.net."
+-	soa.Serial = 1293945905
+-	soa.Refresh = 14400
+-	soa.Retry = 3600
+-	soa.Expire = 604800
+-	soa.Minttl = 86400
+-	return soa
+-}
+-
+-func TestGenerateEC(t *testing.T) {
+-	if testing.Short() {
+-		t.Skip("skipping test in short mode.")
+-	}
+-	key := new(DNSKEY)
+-	key.Hdr.Rrtype = TypeDNSKEY
+-	key.Hdr.Name = "miek.nl."
+-	key.Hdr.Class = ClassINET
+-	key.Hdr.Ttl = 14400
+-	key.Flags = 256
+-	key.Protocol = 3
+-	key.Algorithm = ECDSAP256SHA256
+-	privkey, _ := key.Generate(256)
+-	t.Logf("%s\n", key.String())
+-	t.Logf("%s\n", key.PrivateKeyString(privkey))
+-}
+-
+-func TestGenerateDSA(t *testing.T) {
+-	if testing.Short() {
+-		t.Skip("skipping test in short mode.")
+-	}
+-	key := new(DNSKEY)
+-	key.Hdr.Rrtype = TypeDNSKEY
+-	key.Hdr.Name = "miek.nl."
+-	key.Hdr.Class = ClassINET
+-	key.Hdr.Ttl = 14400
+-	key.Flags = 256
+-	key.Protocol = 3
+-	key.Algorithm = DSA
+-	privkey, _ := key.Generate(1024)
+-	t.Logf("%s\n", key.String())
+-	t.Logf("%s\n", key.PrivateKeyString(privkey))
+-}
+-
+-func TestGenerateRSA(t *testing.T) {
+-	if testing.Short() {
+-		t.Skip("skipping test in short mode.")
+-	}
+-	key := new(DNSKEY)
+-	key.Hdr.Rrtype = TypeDNSKEY
+-	key.Hdr.Name = "miek.nl."
+-	key.Hdr.Class = ClassINET
+-	key.Hdr.Ttl = 14400
+-	key.Flags = 256
+-	key.Protocol = 3
+-	key.Algorithm = RSASHA256
+-	privkey, _ := key.Generate(1024)
+-	t.Logf("%s\n", key.String())
+-	t.Logf("%s\n", key.PrivateKeyString(privkey))
+-}
+-
+-func TestSecure(t *testing.T) {
+-	soa := getSoa()
+-
+-	sig := new(RRSIG)
+-	sig.Hdr = RR_Header{"miek.nl.", TypeRRSIG, ClassINET, 14400, 0}
+-	sig.TypeCovered = TypeSOA
+-	sig.Algorithm = RSASHA256
+-	sig.Labels = 2
+-	sig.Expiration = 1296534305 // date -u '+%s' -d"2011-02-01 04:25:05"
+-	sig.Inception = 1293942305  // date -u '+%s' -d"2011-01-02 04:25:05"
+-	sig.OrigTtl = 14400
+-	sig.KeyTag = 12051
+-	sig.SignerName = "miek.nl."
+-	sig.Signature = "oMCbslaAVIp/8kVtLSms3tDABpcPRUgHLrOR48OOplkYo+8TeEGWwkSwaz/MRo2fB4FxW0qj/hTlIjUGuACSd+b1wKdH5GvzRJc2pFmxtCbm55ygAh4EUL0F6U5cKtGJGSXxxg6UFCQ0doJCmiGFa78LolaUOXImJrk6AFrGa0M="
+-
+-	key := new(DNSKEY)
+-	key.Hdr.Name = "miek.nl."
+-	key.Hdr.Class = ClassINET
+-	key.Hdr.Ttl = 14400
+-	key.Flags = 256
+-	key.Protocol = 3
+-	key.Algorithm = RSASHA256
+-	key.PublicKey = "AwEAAcNEU67LJI5GEgF9QLNqLO1SMq1EdoQ6E9f85ha0k0ewQGCblyW2836GiVsm6k8Kr5ECIoMJ6fZWf3CQSQ9ycWfTyOHfmI3eQ/1Covhb2y4bAmL/07PhrL7ozWBW3wBfM335Ft9xjtXHPy7ztCbV9qZ4TVDTW/Iyg0PiwgoXVesz"
+-
+-	// It should validate. Period is checked seperately, so this will keep on working
+-	if sig.Verify(key, []RR{soa}) != nil {
+-		t.Log("failure to validate")
+-		t.Fail()
+-	}
+-}
+-
+-func TestSignature(t *testing.T) {
+-	sig := new(RRSIG)
+-	sig.Hdr.Name = "miek.nl."
+-	sig.Hdr.Class = ClassINET
+-	sig.Hdr.Ttl = 3600
+-	sig.TypeCovered = TypeDNSKEY
+-	sig.Algorithm = RSASHA1
+-	sig.Labels = 2
+-	sig.OrigTtl = 4000
+-	sig.Expiration = 1000 //Thu Jan  1 02:06:40 CET 1970
+-	sig.Inception = 800   //Thu Jan  1 01:13:20 CET 1970
+-	sig.KeyTag = 34641
+-	sig.SignerName = "miek.nl."
+-	sig.Signature = "AwEAAaHIwpx3w4VHKi6i1LHnTaWeHCL154Jug0Rtc9ji5qwPXpBo6A5sRv7cSsPQKPIwxLpyCrbJ4mr2L0EPOdvP6z6YfljK2ZmTbogU9aSU2fiq/4wjxbdkLyoDVgtO+JsxNN4bjr4WcWhsmk1Hg93FV9ZpkWb0Tbad8DFqNDzr//kZ"
+-
+-	// Should not be valid
+-	if sig.ValidityPeriod(time.Now()) {
+-		t.Log("should not be valid")
+-		t.Fail()
+-	}
+-
+-	sig.Inception = 315565800   //Tue Jan  1 10:10:00 CET 1980
+-	sig.Expiration = 4102477800 //Fri Jan  1 10:10:00 CET 2100
+-	if !sig.ValidityPeriod(time.Now()) {
+-		t.Log("should be valid")
+-		t.Fail()
+-	}
+-}
+-
+-func TestSignVerify(t *testing.T) {
+-	// The record we want to sign
+-	soa := new(SOA)
+-	soa.Hdr = RR_Header{"miek.nl.", TypeSOA, ClassINET, 14400, 0}
+-	soa.Ns = "open.nlnetlabs.nl."
+-	soa.Mbox = "miekg.atoom.net."
+-	soa.Serial = 1293945905
+-	soa.Refresh = 14400
+-	soa.Retry = 3600
+-	soa.Expire = 604800
+-	soa.Minttl = 86400
+-
+-	soa1 := new(SOA)
+-	soa1.Hdr = RR_Header{"*.miek.nl.", TypeSOA, ClassINET, 14400, 0}
+-	soa1.Ns = "open.nlnetlabs.nl."
+-	soa1.Mbox = "miekg.atoom.net."
+-	soa1.Serial = 1293945905
+-	soa1.Refresh = 14400
+-	soa1.Retry = 3600
+-	soa1.Expire = 604800
+-	soa1.Minttl = 86400
+-
+-	srv := new(SRV)
+-	srv.Hdr = RR_Header{"srv.miek.nl.", TypeSRV, ClassINET, 14400, 0}
+-	srv.Port = 1000
+-	srv.Weight = 800
+-	srv.Target = "web1.miek.nl."
+-
+-	// With this key
+-	key := new(DNSKEY)
+-	key.Hdr.Rrtype = TypeDNSKEY
+-	key.Hdr.Name = "miek.nl."
+-	key.Hdr.Class = ClassINET
+-	key.Hdr.Ttl = 14400
+-	key.Flags = 256
+-	key.Protocol = 3
+-	key.Algorithm = RSASHA256
+-	privkey, _ := key.Generate(512)
+-
+-	// Fill in the values of the Sig, before signing
+-	sig := new(RRSIG)
+-	sig.Hdr = RR_Header{"miek.nl.", TypeRRSIG, ClassINET, 14400, 0}
+-	sig.TypeCovered = soa.Hdr.Rrtype
+-	sig.Labels = uint8(CountLabel(soa.Hdr.Name)) // works for all 3
+-	sig.OrigTtl = soa.Hdr.Ttl
+-	sig.Expiration = 1296534305 // date -u '+%s' -d"2011-02-01 04:25:05"
+-	sig.Inception = 1293942305  // date -u '+%s' -d"2011-01-02 04:25:05"
+-	sig.KeyTag = key.KeyTag()   // Get the keyfrom the Key
+-	sig.SignerName = key.Hdr.Name
+-	sig.Algorithm = RSASHA256
+-
+-	for _, r := range []RR{soa, soa1, srv} {
+-		if sig.Sign(privkey, []RR{r}) != nil {
+-			t.Log("failure to sign the record")
+-			t.Fail()
+-			continue
+-		}
+-		if sig.Verify(key, []RR{r}) != nil {
+-			t.Log("failure to validate")
+-			t.Fail()
+-			continue
+-		}
+-		t.Logf("validated: %s\n", r.Header().Name)
+-	}
+-}
+-
+-func Test65534(t *testing.T) {
+-	t6 := new(RFC3597)
+-	t6.Hdr = RR_Header{"miek.nl.", 65534, ClassINET, 14400, 0}
+-	t6.Rdata = "505D870001"
+-	key := new(DNSKEY)
+-	key.Hdr.Name = "miek.nl."
+-	key.Hdr.Rrtype = TypeDNSKEY
+-	key.Hdr.Class = ClassINET
+-	key.Hdr.Ttl = 14400
+-	key.Flags = 256
+-	key.Protocol = 3
+-	key.Algorithm = RSASHA256
+-	privkey, _ := key.Generate(1024)
+-
+-	sig := new(RRSIG)
+-	sig.Hdr = RR_Header{"miek.nl.", TypeRRSIG, ClassINET, 14400, 0}
+-	sig.TypeCovered = t6.Hdr.Rrtype
+-	sig.Labels = uint8(CountLabel(t6.Hdr.Name))
+-	sig.OrigTtl = t6.Hdr.Ttl
+-	sig.Expiration = 1296534305 // date -u '+%s' -d"2011-02-01 04:25:05"
+-	sig.Inception = 1293942305  // date -u '+%s' -d"2011-01-02 04:25:05"
+-	sig.KeyTag = key.KeyTag()
+-	sig.SignerName = key.Hdr.Name
+-	sig.Algorithm = RSASHA256
+-	if err := sig.Sign(privkey, []RR{t6}); err != nil {
+-		t.Log(err)
+-		t.Log("failure to sign the TYPE65534 record")
+-		t.Fail()
+-	}
+-	if err := sig.Verify(key, []RR{t6}); err != nil {
+-		t.Log(err)
+-		t.Log("failure to validate")
+-		t.Fail()
+-	} else {
+-		t.Logf("validated: %s\n", t6.Header().Name)
+-	}
+-}
+-
+-func TestDnskey(t *testing.T) {
+-	//	f, _ := os.Open("t/Kmiek.nl.+010+05240.key")
+-	pubkey, _ := ReadRR(strings.NewReader(`
+-miek.nl.	IN	DNSKEY	256 3 10 AwEAAZuMCu2FdugHkTrXYgl5qixvcDw1aDDlvL46/xJKbHBAHY16fNUb2b65cwko2Js/aJxUYJbZk5dwCDZxYfrfbZVtDPQuc3o8QaChVxC7/JYz2AHc9qHvqQ1j4VrH71RWINlQo6VYjzN/BGpMhOZoZOEwzp1HfsOE3lNYcoWU1smL ;{id = 5240 (zsk), size = 1024b}
+-`), "Kmiek.nl.+010+05240.key")
+-	privkey, _ := pubkey.(*DNSKEY).ReadPrivateKey(strings.NewReader(`
+-Private-key-format: v1.2
+-Algorithm: 10 (RSASHA512)
+-Modulus: m4wK7YV26AeROtdiCXmqLG9wPDVoMOW8vjr/EkpscEAdjXp81RvZvrlzCSjYmz9onFRgltmTl3AINnFh+t9tlW0M9C5zejxBoKFXELv8ljPYAdz2oe+pDWPhWsfvVFYg2VCjpViPM38EakyE5mhk4TDOnUd+w4TeU1hyhZTWyYs=
+-PublicExponent: AQAB
+-PrivateExponent: UfCoIQ/Z38l8vB6SSqOI/feGjHEl/fxIPX4euKf0D/32k30fHbSaNFrFOuIFmWMB3LimWVEs6u3dpbB9CQeCVg7hwU5puG7OtuiZJgDAhNeOnxvo5btp4XzPZrJSxR4WNQnwIiYWbl0aFlL1VGgHC/3By89ENZyWaZcMLW4KGWE=
+-Prime1: yxwC6ogAu8aVcDx2wg1V0b5M5P6jP8qkRFVMxWNTw60Vkn+ECvw6YAZZBHZPaMyRYZLzPgUlyYRd0cjupy4+fQ==
+-Prime2: xA1bF8M0RTIQ6+A11AoVG6GIR/aPGg5sogRkIZ7ID/sF6g9HMVU/CM2TqVEBJLRPp73cv6ZeC3bcqOCqZhz+pw==
+-Exponent1: xzkblyZ96bGYxTVZm2/vHMOXswod4KWIyMoOepK6B/ZPcZoIT6omLCgtypWtwHLfqyCz3MK51Nc0G2EGzg8rFQ==
+-Exponent2: Pu5+mCEb7T5F+kFNZhQadHUklt0JUHbi3hsEvVoHpEGSw3BGDQrtIflDde0/rbWHgDPM4WQY+hscd8UuTXrvLw==
+-Coefficient: UuRoNqe7YHnKmQzE6iDWKTMIWTuoqqrFAmXPmKQnC+Y+BQzOVEHUo9bXdDnoI9hzXP1gf8zENMYwYLeWpuYlFQ==
+-`), "Kmiek.nl.+010+05240.private")
+-	if pubkey.(*DNSKEY).PublicKey != "AwEAAZuMCu2FdugHkTrXYgl5qixvcDw1aDDlvL46/xJKbHBAHY16fNUb2b65cwko2Js/aJxUYJbZk5dwCDZxYfrfbZVtDPQuc3o8QaChVxC7/JYz2AHc9qHvqQ1j4VrH71RWINlQo6VYjzN/BGpMhOZoZOEwzp1HfsOE3lNYcoWU1smL" {
+-		t.Log("pubkey is not what we've read")
+-		t.Fail()
+-	}
+-	// Coefficient looks fishy...
+-	t.Logf("%s", pubkey.(*DNSKEY).PrivateKeyString(privkey))
+-}
+-
+-func TestTag(t *testing.T) {
+-	key := new(DNSKEY)
+-	key.Hdr.Name = "miek.nl."
+-	key.Hdr.Rrtype = TypeDNSKEY
+-	key.Hdr.Class = ClassINET
+-	key.Hdr.Ttl = 3600
+-	key.Flags = 256
+-	key.Protocol = 3
+-	key.Algorithm = RSASHA256
+-	key.PublicKey = "AwEAAcNEU67LJI5GEgF9QLNqLO1SMq1EdoQ6E9f85ha0k0ewQGCblyW2836GiVsm6k8Kr5ECIoMJ6fZWf3CQSQ9ycWfTyOHfmI3eQ/1Covhb2y4bAmL/07PhrL7ozWBW3wBfM335Ft9xjtXHPy7ztCbV9qZ4TVDTW/Iyg0PiwgoXVesz"
+-
+-	tag := key.KeyTag()
+-	if tag != 12051 {
+-		t.Logf("wrong key tag: %d for key %v\n", tag, key)
+-		t.Fail()
+-	}
+-}
+-
+-func TestKeyRSA(t *testing.T) {
+-	if testing.Short() {
+-		t.Skip("skipping test in short mode.")
+-	}
+-	key := new(DNSKEY)
+-	key.Hdr.Name = "miek.nl."
+-	key.Hdr.Rrtype = TypeDNSKEY
+-	key.Hdr.Class = ClassINET
+-	key.Hdr.Ttl = 3600
+-	key.Flags = 256
+-	key.Protocol = 3
+-	key.Algorithm = RSASHA256
+-	priv, _ := key.Generate(2048)
+-
+-	soa := new(SOA)
+-	soa.Hdr = RR_Header{"miek.nl.", TypeSOA, ClassINET, 14400, 0}
+-	soa.Ns = "open.nlnetlabs.nl."
+-	soa.Mbox = "miekg.atoom.net."
+-	soa.Serial = 1293945905
+-	soa.Refresh = 14400
+-	soa.Retry = 3600
+-	soa.Expire = 604800
+-	soa.Minttl = 86400
+-
+-	sig := new(RRSIG)
+-	sig.Hdr = RR_Header{"miek.nl.", TypeRRSIG, ClassINET, 14400, 0}
+-	sig.TypeCovered = TypeSOA
+-	sig.Algorithm = RSASHA256
+-	sig.Labels = 2
+-	sig.Expiration = 1296534305 // date -u '+%s' -d"2011-02-01 04:25:05"
+-	sig.Inception = 1293942305  // date -u '+%s' -d"2011-01-02 04:25:05"
+-	sig.OrigTtl = soa.Hdr.Ttl
+-	sig.KeyTag = key.KeyTag()
+-	sig.SignerName = key.Hdr.Name
+-
+-	if err := sig.Sign(priv, []RR{soa}); err != nil {
+-		t.Logf("failed to sign")
+-		t.Fail()
+-		return
+-	}
+-	if err := sig.Verify(key, []RR{soa}); err != nil {
+-		t.Logf("failed to verify")
+-		t.Fail()
+-	}
+-}
+-
+-func TestKeyToDS(t *testing.T) {
+-	key := new(DNSKEY)
+-	key.Hdr.Name = "miek.nl."
+-	key.Hdr.Rrtype = TypeDNSKEY
+-	key.Hdr.Class = ClassINET
+-	key.Hdr.Ttl = 3600
+-	key.Flags = 256
+-	key.Protocol = 3
+-	key.Algorithm = RSASHA256
+-	key.PublicKey = "AwEAAcNEU67LJI5GEgF9QLNqLO1SMq1EdoQ6E9f85ha0k0ewQGCblyW2836GiVsm6k8Kr5ECIoMJ6fZWf3CQSQ9ycWfTyOHfmI3eQ/1Covhb2y4bAmL/07PhrL7ozWBW3wBfM335Ft9xjtXHPy7ztCbV9qZ4TVDTW/Iyg0PiwgoXVesz"
+-
+-	ds := key.ToDS(SHA1)
+-	if strings.ToUpper(ds.Digest) != "B5121BDB5B8D86D0CC5FFAFBAAABE26C3E20BAC1" {
+-		t.Logf("wrong DS digest for SHA1\n%v\n", ds)
+-		t.Fail()
+-	}
+-}
+-
+-func TestSignRSA(t *testing.T) {
+-	pub := "miek.nl. IN DNSKEY 256 3 5 AwEAAb+8lGNCxJgLS8rYVer6EnHVuIkQDghdjdtewDzU3G5R7PbMbKVRvH2Ma7pQyYceoaqWZQirSj72euPWfPxQnMy9ucCylA+FuH9cSjIcPf4PqJfdupHk9X6EBYjxrCLY4p1/yBwgyBIRJtZtAqM3ceAH2WovEJD6rTtOuHo5AluJ"
+-
+-	priv := `Private-key-format: v1.3
+-Algorithm: 5 (RSASHA1)
+-Modulus: v7yUY0LEmAtLythV6voScdW4iRAOCF2N217APNTcblHs9sxspVG8fYxrulDJhx6hqpZlCKtKPvZ649Z8/FCczL25wLKUD4W4f1xKMhw9/g+ol926keT1foQFiPGsItjinX/IHCDIEhEm1m0Cozdx4AfZai8QkPqtO064ejkCW4k=
+-PublicExponent: AQAB
+-PrivateExponent: YPwEmwjk5HuiROKU4xzHQ6l1hG8Iiha4cKRG3P5W2b66/EN/GUh07ZSf0UiYB67o257jUDVEgwCuPJz776zfApcCB4oGV+YDyEu7Hp/rL8KcSN0la0k2r9scKwxTp4BTJT23zyBFXsV/1wRDK1A5NxsHPDMYi2SoK63Enm/1ptk=
+-Prime1: /wjOG+fD0ybNoSRn7nQ79udGeR1b0YhUA5mNjDx/x2fxtIXzygYk0Rhx9QFfDy6LOBvz92gbNQlzCLz3DJt5hw==
+-Prime2: wHZsJ8OGhkp5p3mrJFZXMDc2mbYusDVTA+t+iRPdS797Tj0pjvU2HN4vTnTj8KBQp6hmnY7dLp9Y1qserySGbw==
+-Exponent1: N0A7FsSRIg+IAN8YPQqlawoTtG1t1OkJ+nWrurPootScApX6iMvn8fyvw3p2k51rv84efnzpWAYiC8SUaQDNxQ==
+-Exponent2: SvuYRaGyvo0zemE3oS+WRm2scxR8eiA8WJGeOc+obwOKCcBgeZblXzfdHGcEC1KaOcetOwNW/vwMA46lpLzJNw==
+-Coefficient: 8+7ZN/JgByqv0NfULiFKTjtyegUcijRuyij7yNxYbCBneDvZGxJwKNi4YYXWx743pcAj4Oi4Oh86gcmxLs+hGw==
+-Created: 20110302104537
+-Publish: 20110302104537
+-Activate: 20110302104537`
+-
+-	xk, _ := NewRR(pub)
+-	k := xk.(*DNSKEY)
+-	p, err := k.NewPrivateKey(priv)
+-	if err != nil {
+-		t.Logf("%v\n", err)
+-		t.Fail()
+-	}
+-	switch priv := p.(type) {
+-	case *rsa.PrivateKey:
+-		if 65537 != priv.PublicKey.E {
+-			t.Log("exponenent should be 65537")
+-			t.Fail()
+-		}
+-	default:
+-		t.Logf("we should have read an RSA key: %v", priv)
+-		t.Fail()
+-	}
+-	if k.KeyTag() != 37350 {
+-		t.Logf("%d %v\n", k.KeyTag(), k)
+-		t.Log("keytag should be 37350")
+-		t.Fail()
+-	}
+-
+-	soa := new(SOA)
+-	soa.Hdr = RR_Header{"miek.nl.", TypeSOA, ClassINET, 14400, 0}
+-	soa.Ns = "open.nlnetlabs.nl."
+-	soa.Mbox = "miekg.atoom.net."
+-	soa.Serial = 1293945905
+-	soa.Refresh = 14400
+-	soa.Retry = 3600
+-	soa.Expire = 604800
+-	soa.Minttl = 86400
+-
+-	sig := new(RRSIG)
+-	sig.Hdr = RR_Header{"miek.nl.", TypeRRSIG, ClassINET, 14400, 0}
+-	sig.Expiration = 1296534305 // date -u '+%s' -d"2011-02-01 04:25:05"
+-	sig.Inception = 1293942305  // date -u '+%s' -d"2011-01-02 04:25:05"
+-	sig.KeyTag = k.KeyTag()
+-	sig.SignerName = k.Hdr.Name
+-	sig.Algorithm = k.Algorithm
+-
+-	sig.Sign(p, []RR{soa})
+-	if sig.Signature != "D5zsobpQcmMmYsUMLxCVEtgAdCvTu8V/IEeP4EyLBjqPJmjt96bwM9kqihsccofA5LIJ7DN91qkCORjWSTwNhzCv7bMyr2o5vBZElrlpnRzlvsFIoAZCD9xg6ZY7ZyzUJmU6IcTwG4v3xEYajcpbJJiyaw/RqR90MuRdKPiBzSo=" {
+-		t.Log("signature is not correct")
+-		t.Logf("%v\n", sig)
+-		t.Fail()
+-	}
+-}
+-
+-func TestSignVerifyECDSA(t *testing.T) {
+-	pub := `example.net. 3600 IN DNSKEY 257 3 14 (
+-	xKYaNhWdGOfJ+nPrL8/arkwf2EY3MDJ+SErKivBVSum1
+-	w/egsXvSADtNJhyem5RCOpgQ6K8X1DRSEkrbYQ+OB+v8
+-	/uX45NBwY8rp65F6Glur8I/mlVNgF6W/qTI37m40 )`
+-	priv := `Private-key-format: v1.2
+-Algorithm: 14 (ECDSAP384SHA384)
+-PrivateKey: WURgWHCcYIYUPWgeLmiPY2DJJk02vgrmTfitxgqcL4vwW7BOrbawVmVe0d9V94SR`
+-
+-	eckey, err := NewRR(pub)
+-	if err != nil {
+-		t.Fatal(err.Error())
+-	}
+-	privkey, err := eckey.(*DNSKEY).NewPrivateKey(priv)
+-	if err != nil {
+-		t.Fatal(err.Error())
+-	}
+-	// TODO: Create seperate test for this
+-	ds := eckey.(*DNSKEY).ToDS(SHA384)
+-	if ds.KeyTag != 10771 {
+-		t.Fatal("wrong keytag on DS")
+-	}
+-	if ds.Digest != "72d7b62976ce06438e9c0bf319013cf801f09ecc84b8d7e9495f27e305c6a9b0563a9b5f4d288405c3008a946df983d6" {
+-		t.Fatal("wrong DS Digest")
+-	}
+-	a, _ := NewRR("www.example.net. 3600 IN A 192.0.2.1")
+-	sig := new(RRSIG)
+-	sig.Hdr = RR_Header{"example.net.", TypeRRSIG, ClassINET, 14400, 0}
+-	sig.Expiration, _ = StringToTime("20100909102025")
+-	sig.Inception, _ = StringToTime("20100812102025")
+-	sig.KeyTag = eckey.(*DNSKEY).KeyTag()
+-	sig.SignerName = eckey.(*DNSKEY).Hdr.Name
+-	sig.Algorithm = eckey.(*DNSKEY).Algorithm
+-
+-	if sig.Sign(privkey, []RR{a}) != nil {
+-		t.Fatal("failure to sign the record")
+-	}
+-
+-	if e := sig.Verify(eckey.(*DNSKEY), []RR{a}); e != nil {
+-		t.Logf("\n%s\n%s\n%s\n\n%s\n\n",
+-			eckey.(*DNSKEY).String(),
+-			a.String(),
+-			sig.String(),
+-			eckey.(*DNSKEY).PrivateKeyString(privkey),
+-		)
+-
+-		t.Fatalf("failure to validate: %s", e.Error())
+-	}
+-}
+-
+-func TestSignVerifyECDSA2(t *testing.T) {
+-	srv1, err := NewRR("srv.miek.nl. IN SRV 1000 800 0 web1.miek.nl.")
+-	if err != nil {
+-		t.Fatalf(err.Error())
+-	}
+-	srv := srv1.(*SRV)
+-
+-	// With this key
+-	key := new(DNSKEY)
+-	key.Hdr.Rrtype = TypeDNSKEY
+-	key.Hdr.Name = "miek.nl."
+-	key.Hdr.Class = ClassINET
+-	key.Hdr.Ttl = 14400
+-	key.Flags = 256
+-	key.Protocol = 3
+-	key.Algorithm = ECDSAP256SHA256
+-	privkey, err := key.Generate(256)
+-	if err != nil {
+-		t.Fatal("failure to generate key")
+-	}
+-
+-	// Fill in the values of the Sig, before signing
+-	sig := new(RRSIG)
+-	sig.Hdr = RR_Header{"miek.nl.", TypeRRSIG, ClassINET, 14400, 0}
+-	sig.TypeCovered = srv.Hdr.Rrtype
+-	sig.Labels = uint8(CountLabel(srv.Hdr.Name)) // works for all 3
+-	sig.OrigTtl = srv.Hdr.Ttl
+-	sig.Expiration = 1296534305 // date -u '+%s' -d"2011-02-01 04:25:05"
+-	sig.Inception = 1293942305  // date -u '+%s' -d"2011-01-02 04:25:05"
+-	sig.KeyTag = key.KeyTag()   // Get the keyfrom the Key
+-	sig.SignerName = key.Hdr.Name
+-	sig.Algorithm = ECDSAP256SHA256
+-
+-	if sig.Sign(privkey, []RR{srv}) != nil {
+-		t.Fatal("failure to sign the record")
+-	}
+-
+-	err = sig.Verify(key, []RR{srv})
+-	if err != nil {
+-		t.Logf("\n%s\n%s\n%s\n\n%s\n\n",
+-			key.String(),
+-			srv.String(),
+-			sig.String(),
+-			key.PrivateKeyString(privkey),
+-		)
+-
+-		t.Fatal("Failure to validate:", err)
+-	}
+-}
+-
+-// Here the test vectors from the relevant RFCs are checked.
+-// rfc6605 6.1
+-func TestRFC6605P256(t *testing.T) {
+-	exDNSKEY := `example.net. 3600 IN DNSKEY 257 3 13 (
+-                 GojIhhXUN/u4v54ZQqGSnyhWJwaubCvTmeexv7bR6edb
+-                 krSqQpF64cYbcB7wNcP+e+MAnLr+Wi9xMWyQLc8NAA== )`
+-	exPriv := `Private-key-format: v1.2
+-Algorithm: 13 (ECDSAP256SHA256)
+-PrivateKey: GU6SnQ/Ou+xC5RumuIUIuJZteXT2z0O/ok1s38Et6mQ=`
+-	rrDNSKEY, err := NewRR(exDNSKEY)
+-	if err != nil {
+-		t.Fatal(err.Error())
+-	}
+-	priv, err := rrDNSKEY.(*DNSKEY).NewPrivateKey(exPriv)
+-	if err != nil {
+-		t.Fatal(err.Error())
+-	}
+-
+-	exDS := `example.net. 3600 IN DS 55648 13 2 (
+-             b4c8c1fe2e7477127b27115656ad6256f424625bf5c1
+-             e2770ce6d6e37df61d17 )`
+-	rrDS, err := NewRR(exDS)
+-	if err != nil {
+-		t.Fatal(err.Error())
+-	}
+-	ourDS := rrDNSKEY.(*DNSKEY).ToDS(SHA256)
+-	if !reflect.DeepEqual(ourDS, rrDS.(*DS)) {
+-		t.Errorf("DS record differs:\n%v\n%v\n", ourDS, rrDS.(*DS))
+-	}
+-
+-	exA := `www.example.net. 3600 IN A 192.0.2.1`
+-	exRRSIG := `www.example.net. 3600 IN RRSIG A 13 3 3600 (
+-                20100909100439 20100812100439 55648 example.net.
+-                qx6wLYqmh+l9oCKTN6qIc+bw6ya+KJ8oMz0YP107epXA
+-                yGmt+3SNruPFKG7tZoLBLlUzGGus7ZwmwWep666VCw== )`
+-	rrA, err := NewRR(exA)
+-	if err != nil {
+-		t.Fatal(err.Error())
+-	}
+-	rrRRSIG, err := NewRR(exRRSIG)
+-	if err != nil {
+-		t.Fatal(err.Error())
+-	}
+-	if err = rrRRSIG.(*RRSIG).Verify(rrDNSKEY.(*DNSKEY), []RR{rrA}); err != nil {
+-		t.Errorf("Failure to validate the spec RRSIG: %v", err)
+-	}
+-
+-	ourRRSIG := &RRSIG{
+-		Hdr: RR_Header{
+-			Ttl: rrA.Header().Ttl,
+-		},
+-		KeyTag:     rrDNSKEY.(*DNSKEY).KeyTag(),
+-		SignerName: rrDNSKEY.(*DNSKEY).Hdr.Name,
+-		Algorithm:  rrDNSKEY.(*DNSKEY).Algorithm,
+-	}
+-	ourRRSIG.Expiration, _ = StringToTime("20100909100439")
+-	ourRRSIG.Inception, _ = StringToTime("20100812100439")
+-	err = ourRRSIG.Sign(priv, []RR{rrA})
+-	if err != nil {
+-		t.Fatal(err.Error())
+-	}
+-
+-	if err = ourRRSIG.Verify(rrDNSKEY.(*DNSKEY), []RR{rrA}); err != nil {
+-		t.Errorf("Failure to validate our RRSIG: %v", err)
+-	}
+-
+-	// Signatures are randomized
+-	rrRRSIG.(*RRSIG).Signature = ""
+-	ourRRSIG.Signature = ""
+-	if !reflect.DeepEqual(ourRRSIG, rrRRSIG.(*RRSIG)) {
+-		t.Fatalf("RRSIG record differs:\n%v\n%v\n", ourRRSIG, rrRRSIG.(*RRSIG))
+-	}
+-}
+-
+-// rfc6605 6.2
+-func TestRFC6605P384(t *testing.T) {
+-	exDNSKEY := `example.net. 3600 IN DNSKEY 257 3 14 (
+-                 xKYaNhWdGOfJ+nPrL8/arkwf2EY3MDJ+SErKivBVSum1
+-                 w/egsXvSADtNJhyem5RCOpgQ6K8X1DRSEkrbYQ+OB+v8
+-                 /uX45NBwY8rp65F6Glur8I/mlVNgF6W/qTI37m40 )`
+-	exPriv := `Private-key-format: v1.2
+-Algorithm: 14 (ECDSAP384SHA384)
+-PrivateKey: WURgWHCcYIYUPWgeLmiPY2DJJk02vgrmTfitxgqcL4vwW7BOrbawVmVe0d9V94SR`
+-	rrDNSKEY, err := NewRR(exDNSKEY)
+-	if err != nil {
+-		t.Fatal(err.Error())
+-	}
+-	priv, err := rrDNSKEY.(*DNSKEY).NewPrivateKey(exPriv)
+-	if err != nil {
+-		t.Fatal(err.Error())
+-	}
+-
+-	exDS := `example.net. 3600 IN DS 10771 14 4 (
+-           72d7b62976ce06438e9c0bf319013cf801f09ecc84b8
+-           d7e9495f27e305c6a9b0563a9b5f4d288405c3008a94
+-           6df983d6 )`
+-	rrDS, err := NewRR(exDS)
+-	if err != nil {
+-		t.Fatal(err.Error())
+-	}
+-	ourDS := rrDNSKEY.(*DNSKEY).ToDS(SHA384)
+-	if !reflect.DeepEqual(ourDS, rrDS.(*DS)) {
+-		t.Fatalf("DS record differs:\n%v\n%v\n", ourDS, rrDS.(*DS))
+-	}
+-
+-	exA := `www.example.net. 3600 IN A 192.0.2.1`
+-	exRRSIG := `www.example.net. 3600 IN RRSIG A 14 3 3600 (
+-           20100909102025 20100812102025 10771 example.net.
+-           /L5hDKIvGDyI1fcARX3z65qrmPsVz73QD1Mr5CEqOiLP
+-           95hxQouuroGCeZOvzFaxsT8Glr74hbavRKayJNuydCuz
+-           WTSSPdz7wnqXL5bdcJzusdnI0RSMROxxwGipWcJm )`
+-	rrA, err := NewRR(exA)
+-	if err != nil {
+-		t.Fatal(err.Error())
+-	}
+-	rrRRSIG, err := NewRR(exRRSIG)
+-	if err != nil {
+-		t.Fatal(err.Error())
+-	}
+-	if err = rrRRSIG.(*RRSIG).Verify(rrDNSKEY.(*DNSKEY), []RR{rrA}); err != nil {
+-		t.Errorf("Failure to validate the spec RRSIG: %v", err)
+-	}
+-
+-	ourRRSIG := &RRSIG{
+-		Hdr: RR_Header{
+-			Ttl: rrA.Header().Ttl,
+-		},
+-		KeyTag:     rrDNSKEY.(*DNSKEY).KeyTag(),
+-		SignerName: rrDNSKEY.(*DNSKEY).Hdr.Name,
+-		Algorithm:  rrDNSKEY.(*DNSKEY).Algorithm,
+-	}
+-	ourRRSIG.Expiration, _ = StringToTime("20100909102025")
+-	ourRRSIG.Inception, _ = StringToTime("20100812102025")
+-	err = ourRRSIG.Sign(priv, []RR{rrA})
+-	if err != nil {
+-		t.Fatal(err.Error())
+-	}
+-
+-	if err = ourRRSIG.Verify(rrDNSKEY.(*DNSKEY), []RR{rrA}); err != nil {
+-		t.Errorf("Failure to validate our RRSIG: %v", err)
+-	}
+-
+-	// Signatures are randomized
+-	rrRRSIG.(*RRSIG).Signature = ""
+-	ourRRSIG.Signature = ""
+-	if !reflect.DeepEqual(ourRRSIG, rrRRSIG.(*RRSIG)) {
+-		t.Fatalf("RRSIG record differs:\n%v\n%v\n", ourRRSIG, rrRRSIG.(*RRSIG))
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/dyn_test.go b/Godeps/_workspace/src/github.com/miekg/dns/dyn_test.go
+deleted file mode 100644
+index 09986a5..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/dyn_test.go
++++ /dev/null
+@@ -1,3 +0,0 @@
+-package dns
+-
+-// Find better solution
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/edns.go b/Godeps/_workspace/src/github.com/miekg/dns/edns.go
+deleted file mode 100644
+index 8b676e6..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/edns.go
++++ /dev/null
+@@ -1,501 +0,0 @@
+-// EDNS0
+-//
+-// EDNS0 is an extension mechanism for the DNS defined in RFC 2671 and updated
+-// by RFC 6891. It defines an new RR type, the OPT RR, which is then completely
+-// abused.
+-// Basic use pattern for creating an (empty) OPT RR:
+-//
+-//	o := new(dns.OPT)
+-//	o.Hdr.Name = "." // MUST be the root zone, per definition.
+-//	o.Hdr.Rrtype = dns.TypeOPT
+-//
+-// The rdata of an OPT RR consists out of a slice of EDNS0 (RFC 6891)
+-// interfaces. Currently only a few have been standardized: EDNS0_NSID
+-// (RFC 5001) and EDNS0_SUBNET (draft-vandergaast-edns-client-subnet-02). Note
+-// that these options may be combined in an OPT RR.
+-// Basic use pattern for a server to check if (and which) options are set:
+-//
+-//	// o is a dns.OPT
+-//	for _, s := range o.Option {
+-//		switch e := s.(type) {
+-//		case *dns.EDNS0_NSID:
+-//			// do stuff with e.Nsid
+-//		case *dns.EDNS0_SUBNET:
+-//			// access e.Family, e.Address, etc.
+-//		}
+-//	}
+-package dns
+-
+-import (
+-	"encoding/hex"
+-	"errors"
+-	"net"
+-	"strconv"
+-)
+-
+-// EDNS0 Option codes.
+-const (
+-	EDNS0LLQ         = 0x1     // long lived queries: http://tools.ietf.org/html/draft-sekar-dns-llq-01
+-	EDNS0UL          = 0x2     // update lease draft: http://files.dns-sd.org/draft-sekar-dns-ul.txt
+-	EDNS0NSID        = 0x3     // nsid (RFC5001)
+-	EDNS0DAU         = 0x5     // DNSSEC Algorithm Understood
+-	EDNS0DHU         = 0x6     // DS Hash Understood
+-	EDNS0N3U         = 0x7     // NSEC3 Hash Understood
+-	EDNS0SUBNET      = 0x8     // client-subnet (RFC6891)
+-	EDNS0EXPIRE      = 0x9     // EDNS0 expire
+-	EDNS0SUBNETDRAFT = 0x50fa  // Don't use! Use EDNS0SUBNET
+-	_DO              = 1 << 15 // dnssec ok
+-)
+-
+-type OPT struct {
+-	Hdr    RR_Header
+-	Option []EDNS0 `dns:"opt"`
+-}
+-
+-func (rr *OPT) Header() *RR_Header {
+-	return &rr.Hdr
+-}
+-
+-func (rr *OPT) String() string {
+-	s := "\n;; OPT PSEUDOSECTION:\n; EDNS: version " + strconv.Itoa(int(rr.Version())) + "; "
+-	if rr.Do() {
+-		s += "flags: do; "
+-	} else {
+-		s += "flags: ; "
+-	}
+-	s += "udp: " + strconv.Itoa(int(rr.UDPSize()))
+-
+-	for _, o := range rr.Option {
+-		switch o.(type) {
+-		case *EDNS0_NSID:
+-			s += "\n; NSID: " + o.String()
+-			h, e := o.pack()
+-			var r string
+-			if e == nil {
+-				for _, c := range h {
+-					r += "(" + string(c) + ")"
+-				}
+-				s += "  " + r
+-			}
+-		case *EDNS0_SUBNET:
+-			s += "\n; SUBNET: " + o.String()
+-			if o.(*EDNS0_SUBNET).DraftOption {
+-				s += " (draft)"
+-			}
+-		case *EDNS0_UL:
+-			s += "\n; UPDATE LEASE: " + o.String()
+-		case *EDNS0_LLQ:
+-			s += "\n; LONG LIVED QUERIES: " + o.String()
+-		case *EDNS0_DAU:
+-			s += "\n; DNSSEC ALGORITHM UNDERSTOOD: " + o.String()
+-		case *EDNS0_DHU:
+-			s += "\n; DS HASH UNDERSTOOD: " + o.String()
+-		case *EDNS0_N3U:
+-			s += "\n; NSEC3 HASH UNDERSTOOD: " + o.String()
+-		}
+-	}
+-	return s
+-}
+-
+-func (rr *OPT) len() int {
+-	l := rr.Hdr.len()
+-	for i := 0; i < len(rr.Option); i++ {
+-		lo, _ := rr.Option[i].pack()
+-		l += 2 + len(lo)
+-	}
+-	return l
+-}
+-
+-func (rr *OPT) copy() RR {
+-	return &OPT{*rr.Hdr.copyHeader(), rr.Option}
+-}
+-
+-// return the old value -> delete SetVersion?
+-
+-// Version returns the EDNS version used. Only zero is defined.
+-func (rr *OPT) Version() uint8 {
+-	return uint8((rr.Hdr.Ttl & 0x00FF0000) >> 16)
+-}
+-
+-// SetVersion sets the version of EDNS. This is usually zero.
+-func (rr *OPT) SetVersion(v uint8) {
+-	rr.Hdr.Ttl = rr.Hdr.Ttl&0xFF00FFFF | (uint32(v) << 16)
+-}
+-
+-// ExtendedRcode returns the EDNS extended RCODE field (the upper 8 bits of the TTL).
+-func (rr *OPT) ExtendedRcode() uint8 {
+-	return uint8((rr.Hdr.Ttl & 0xFF000000) >> 24)
+-}
+-
+-// SetExtendedRcode sets the EDNS extended RCODE field.
+-func (rr *OPT) SetExtendedRcode(v uint8) {
+-	rr.Hdr.Ttl = rr.Hdr.Ttl&0x00FFFFFF | (uint32(v) << 24)
+-}
+-
+-// UDPSize returns the UDP buffer size.
+-func (rr *OPT) UDPSize() uint16 {
+-	return rr.Hdr.Class
+-}
+-
+-// SetUDPSize sets the UDP buffer size.
+-func (rr *OPT) SetUDPSize(size uint16) {
+-	rr.Hdr.Class = size
+-}
+-
+-// Do returns the value of the DO (DNSSEC OK) bit.
+-func (rr *OPT) Do() bool {
+-	return rr.Hdr.Ttl&_DO == _DO
+-}
+-
+-// SetDo sets the DO (DNSSEC OK) bit.
+-func (rr *OPT) SetDo() {
+-	rr.Hdr.Ttl |= _DO
+-}
+-
+-// EDNS0 defines an EDNS0 Option. An OPT RR can have multiple options appended to
+-// it.
+-type EDNS0 interface {
+-	// Option returns the option code for the option.
+-	Option() uint16
+-	// pack returns the bytes of the option data.
+-	pack() ([]byte, error)
+-	// unpack sets the data as found in the buffer. Is also sets
+-	// the length of the slice as the length of the option data.
+-	unpack([]byte) error
+-	// String returns the string representation of the option.
+-	String() string
+-}
+-
+-// The nsid EDNS0 option is used to retrieve a nameserver
+-// identifier. When sending a request Nsid must be set to the empty string
+-// The identifier is an opaque string encoded as hex.
+-// Basic use pattern for creating an nsid option:
+-//
+-//	o := new(dns.OPT)
+-//	o.Hdr.Name = "."
+-//	o.Hdr.Rrtype = dns.TypeOPT
+-//	e := new(dns.EDNS0_NSID)
+-//	e.Code = dns.EDNS0NSID
+-//	e.Nsid = "AA"
+-//	o.Option = append(o.Option, e)
+-type EDNS0_NSID struct {
+-	Code uint16 // Always EDNS0NSID
+-	Nsid string // This string needs to be hex encoded
+-}
+-
+-func (e *EDNS0_NSID) pack() ([]byte, error) {
+-	h, err := hex.DecodeString(e.Nsid)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return h, nil
+-}
+-
+-func (e *EDNS0_NSID) Option() uint16        { return EDNS0NSID }
+-func (e *EDNS0_NSID) unpack(b []byte) error { e.Nsid = hex.EncodeToString(b); return nil }
+-func (e *EDNS0_NSID) String() string        { return string(e.Nsid) }
+-
+-// The subnet EDNS0 option is used to give the remote nameserver
+-// an idea of where the client lives. It can then give back a different
+-// answer depending on the location or network topology.
+-// Basic use pattern for creating an subnet option:
+-//
+-//	o := new(dns.OPT)
+-//	o.Hdr.Name = "."
+-//	o.Hdr.Rrtype = dns.TypeOPT
+-//	e := new(dns.EDNS0_SUBNET)
+-//	e.Code = dns.EDNS0SUBNET
+-//	e.Family = 1	// 1 for IPv4 source address, 2 for IPv6
+-//	e.NetMask = 32	// 32 for IPV4, 128 for IPv6
+-//	e.SourceScope = 0
+-//	e.Address = net.ParseIP("127.0.0.1").To4()	// for IPv4
+-//	// e.Address = net.ParseIP("2001:7b8:32a::2")	// for IPV6
+-//	o.Option = append(o.Option, e)
+-type EDNS0_SUBNET struct {
+-	Code          uint16 // Always EDNS0SUBNET
+-	Family        uint16 // 1 for IP, 2 for IP6
+-	SourceNetmask uint8
+-	SourceScope   uint8
+-	Address       net.IP
+-	DraftOption   bool // Set to true if using the old (0x50fa) option code
+-}
+-
+-func (e *EDNS0_SUBNET) Option() uint16 {
+-	if e.DraftOption {
+-		return EDNS0SUBNETDRAFT
+-	}
+-	return EDNS0SUBNET
+-}
+-
+-func (e *EDNS0_SUBNET) pack() ([]byte, error) {
+-	b := make([]byte, 4)
+-	b[0], b[1] = packUint16(e.Family)
+-	b[2] = e.SourceNetmask
+-	b[3] = e.SourceScope
+-	switch e.Family {
+-	case 1:
+-		if e.SourceNetmask > net.IPv4len*8 {
+-			return nil, errors.New("dns: bad netmask")
+-		}
+-		ip := make([]byte, net.IPv4len)
+-		a := e.Address.To4().Mask(net.CIDRMask(int(e.SourceNetmask), net.IPv4len*8))
+-		for i := 0; i < net.IPv4len; i++ {
+-			if i+1 > len(e.Address) {
+-				break
+-			}
+-			ip[i] = a[i]
+-		}
+-		needLength := e.SourceNetmask / 8
+-		if e.SourceNetmask%8 > 0 {
+-			needLength++
+-		}
+-		ip = ip[:needLength]
+-		b = append(b, ip...)
+-	case 2:
+-		if e.SourceNetmask > net.IPv6len*8 {
+-			return nil, errors.New("dns: bad netmask")
+-		}
+-		ip := make([]byte, net.IPv6len)
+-		a := e.Address.Mask(net.CIDRMask(int(e.SourceNetmask), net.IPv6len*8))
+-		for i := 0; i < net.IPv6len; i++ {
+-			if i+1 > len(e.Address) {
+-				break
+-			}
+-			ip[i] = a[i]
+-		}
+-		needLength := e.SourceNetmask / 8
+-		if e.SourceNetmask%8 > 0 {
+-			needLength++
+-		}
+-		ip = ip[:needLength]
+-		b = append(b, ip...)
+-	default:
+-		return nil, errors.New("dns: bad address family")
+-	}
+-	return b, nil
+-}
+-
+-func (e *EDNS0_SUBNET) unpack(b []byte) error {
+-	lb := len(b)
+-	if lb < 4 {
+-		return ErrBuf
+-	}
+-	e.Family, _ = unpackUint16(b, 0)
+-	e.SourceNetmask = b[2]
+-	e.SourceScope = b[3]
+-	switch e.Family {
+-	case 1:
+-		addr := make([]byte, 4)
+-		for i := 0; i < int(e.SourceNetmask/8); i++ {
+-			if i >= len(addr) || 4+i >= len(b) {
+-				return ErrBuf
+-			}
+-			addr[i] = b[4+i]
+-		}
+-		e.Address = net.IPv4(addr[0], addr[1], addr[2], addr[3])
+-	case 2:
+-		addr := make([]byte, 16)
+-		for i := 0; i < int(e.SourceNetmask/8); i++ {
+-			if i >= len(addr) || 4+i >= len(b) {
+-				return ErrBuf
+-			}
+-			addr[i] = b[4+i]
+-		}
+-		e.Address = net.IP{addr[0], addr[1], addr[2], addr[3], addr[4],
+-			addr[5], addr[6], addr[7], addr[8], addr[9], addr[10],
+-			addr[11], addr[12], addr[13], addr[14], addr[15]}
+-	}
+-	return nil
+-}
+-
+-func (e *EDNS0_SUBNET) String() (s string) {
+-	if e.Address == nil {
+-		s = "<nil>"
+-	} else if e.Address.To4() != nil {
+-		s = e.Address.String()
+-	} else {
+-		s = "[" + e.Address.String() + "]"
+-	}
+-	s += "/" + strconv.Itoa(int(e.SourceNetmask)) + "/" + strconv.Itoa(int(e.SourceScope))
+-	return
+-}
+-
+-// The UL (Update Lease) EDNS0 (draft RFC) option is used to tell the server to set
+-// an expiration on an update RR. This is helpful for clients that cannot clean
+-// up after themselves. This is a draft RFC and more information can be found at
+-// http://files.dns-sd.org/draft-sekar-dns-ul.txt
+-//
+-//	o := new(dns.OPT)
+-//	o.Hdr.Name = "."
+-//	o.Hdr.Rrtype = dns.TypeOPT
+-//	e := new(dns.EDNS0_UL)
+-//	e.Code = dns.EDNS0UL
+-//	e.Lease = 120 // in seconds
+-//	o.Option = append(o.Option, e)
+-type EDNS0_UL struct {
+-	Code  uint16 // Always EDNS0UL
+-	Lease uint32
+-}
+-
+-func (e *EDNS0_UL) Option() uint16 { return EDNS0UL }
+-func (e *EDNS0_UL) String() string { return strconv.FormatUint(uint64(e.Lease), 10) }
+-
+-// Copied: http://golang.org/src/pkg/net/dnsmsg.go
+-func (e *EDNS0_UL) pack() ([]byte, error) {
+-	b := make([]byte, 4)
+-	b[0] = byte(e.Lease >> 24)
+-	b[1] = byte(e.Lease >> 16)
+-	b[2] = byte(e.Lease >> 8)
+-	b[3] = byte(e.Lease)
+-	return b, nil
+-}
+-
+-func (e *EDNS0_UL) unpack(b []byte) error {
+-	if len(b) < 4 {
+-		return ErrBuf
+-	}
+-	e.Lease = uint32(b[0])<<24 | uint32(b[1])<<16 | uint32(b[2])<<8 | uint32(b[3])
+-	return nil
+-}
+-
+-// Long Lived Queries: http://tools.ietf.org/html/draft-sekar-dns-llq-01
+-// Implemented for completeness, as the EDNS0 type code is assigned.
+-type EDNS0_LLQ struct {
+-	Code      uint16 // Always EDNS0LLQ
+-	Version   uint16
+-	Opcode    uint16
+-	Error     uint16
+-	Id        uint64
+-	LeaseLife uint32
+-}
+-
+-func (e *EDNS0_LLQ) Option() uint16 { return EDNS0LLQ }
+-
+-func (e *EDNS0_LLQ) pack() ([]byte, error) {
+-	b := make([]byte, 18)
+-	b[0], b[1] = packUint16(e.Version)
+-	b[2], b[3] = packUint16(e.Opcode)
+-	b[4], b[5] = packUint16(e.Error)
+-	b[6] = byte(e.Id >> 56)
+-	b[7] = byte(e.Id >> 48)
+-	b[8] = byte(e.Id >> 40)
+-	b[9] = byte(e.Id >> 32)
+-	b[10] = byte(e.Id >> 24)
+-	b[11] = byte(e.Id >> 16)
+-	b[12] = byte(e.Id >> 8)
+-	b[13] = byte(e.Id)
+-	b[14] = byte(e.LeaseLife >> 24)
+-	b[15] = byte(e.LeaseLife >> 16)
+-	b[16] = byte(e.LeaseLife >> 8)
+-	b[17] = byte(e.LeaseLife)
+-	return b, nil
+-}
+-
+-func (e *EDNS0_LLQ) unpack(b []byte) error {
+-	if len(b) < 18 {
+-		return ErrBuf
+-	}
+-	e.Version, _ = unpackUint16(b, 0)
+-	e.Opcode, _ = unpackUint16(b, 2)
+-	e.Error, _ = unpackUint16(b, 4)
+-	e.Id = uint64(b[6])<<56 | uint64(b[6+1])<<48 | uint64(b[6+2])<<40 |
+-		uint64(b[6+3])<<32 | uint64(b[6+4])<<24 | uint64(b[6+5])<<16 | uint64(b[6+6])<<8 | uint64(b[6+7])
+-	e.LeaseLife = uint32(b[14])<<24 | uint32(b[14+1])<<16 | uint32(b[14+2])<<8 | uint32(b[14+3])
+-	return nil
+-}
+-
+-func (e *EDNS0_LLQ) String() string {
+-	s := strconv.FormatUint(uint64(e.Version), 10) + " " + strconv.FormatUint(uint64(e.Opcode), 10) +
+-		" " + strconv.FormatUint(uint64(e.Error), 10) + " " + strconv.FormatUint(uint64(e.Id), 10) +
+-		" " + strconv.FormatUint(uint64(e.LeaseLife), 10)
+-	return s
+-}
+-
+-type EDNS0_DAU struct {
+-	Code    uint16 // Always EDNS0DAU
+-	AlgCode []uint8
+-}
+-
+-func (e *EDNS0_DAU) Option() uint16        { return EDNS0DAU }
+-func (e *EDNS0_DAU) pack() ([]byte, error) { return e.AlgCode, nil }
+-func (e *EDNS0_DAU) unpack(b []byte) error { e.AlgCode = b; return nil }
+-
+-func (e *EDNS0_DAU) String() string {
+-	s := ""
+-	for i := 0; i < len(e.AlgCode); i++ {
+-		if a, ok := AlgorithmToString[e.AlgCode[i]]; ok {
+-			s += " " + a
+-		} else {
+-			s += " " + strconv.Itoa(int(e.AlgCode[i]))
+-		}
+-	}
+-	return s
+-}
+-
+-type EDNS0_DHU struct {
+-	Code    uint16 // Always EDNS0DHU
+-	AlgCode []uint8
+-}
+-
+-func (e *EDNS0_DHU) Option() uint16        { return EDNS0DHU }
+-func (e *EDNS0_DHU) pack() ([]byte, error) { return e.AlgCode, nil }
+-func (e *EDNS0_DHU) unpack(b []byte) error { e.AlgCode = b; return nil }
+-
+-func (e *EDNS0_DHU) String() string {
+-	s := ""
+-	for i := 0; i < len(e.AlgCode); i++ {
+-		if a, ok := HashToString[e.AlgCode[i]]; ok {
+-			s += " " + a
+-		} else {
+-			s += " " + strconv.Itoa(int(e.AlgCode[i]))
+-		}
+-	}
+-	return s
+-}
+-
+-type EDNS0_N3U struct {
+-	Code    uint16 // Always EDNS0N3U
+-	AlgCode []uint8
+-}
+-
+-func (e *EDNS0_N3U) Option() uint16        { return EDNS0N3U }
+-func (e *EDNS0_N3U) pack() ([]byte, error) { return e.AlgCode, nil }
+-func (e *EDNS0_N3U) unpack(b []byte) error { e.AlgCode = b; return nil }
+-
+-func (e *EDNS0_N3U) String() string {
+-	// Re-use the hash map
+-	s := ""
+-	for i := 0; i < len(e.AlgCode); i++ {
+-		if a, ok := HashToString[e.AlgCode[i]]; ok {
+-			s += " " + a
+-		} else {
+-			s += " " + strconv.Itoa(int(e.AlgCode[i]))
+-		}
+-	}
+-	return s
+-}
+-
+-type EDNS0_EXPIRE struct {
+-	Code   uint16 // Always EDNS0EXPIRE
+-	Expire uint32
+-}
+-
+-func (e *EDNS0_EXPIRE) Option() uint16 { return EDNS0EXPIRE }
+-func (e *EDNS0_EXPIRE) String() string { return strconv.FormatUint(uint64(e.Expire), 10) }
+-
+-func (e *EDNS0_EXPIRE) pack() ([]byte, error) {
+-	b := make([]byte, 4)
+-	b[0] = byte(e.Expire >> 24)
+-	b[1] = byte(e.Expire >> 16)
+-	b[2] = byte(e.Expire >> 8)
+-	b[3] = byte(e.Expire)
+-	return b, nil
+-}
+-
+-func (e *EDNS0_EXPIRE) unpack(b []byte) error {
+-	if len(b) < 4 {
+-		return ErrBuf
+-	}
+-	e.Expire = uint32(b[0])<<24 | uint32(b[1])<<16 | uint32(b[2])<<8 | uint32(b[3])
+-	return nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/edns_test.go b/Godeps/_workspace/src/github.com/miekg/dns/edns_test.go
+deleted file mode 100644
+index 8ee82ab..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/edns_test.go
++++ /dev/null
+@@ -1,48 +0,0 @@
+-package dns
+-
+-import "testing"
+-
+-func TestOPTTtl(t *testing.T) {
+-	e := &OPT{}
+-	e.Hdr.Name = "."
+-	e.Hdr.Rrtype = TypeOPT
+-
+-	if e.Do() {
+-		t.Fail()
+-	}
+-
+-	e.SetDo()
+-	if !e.Do() {
+-		t.Fail()
+-	}
+-
+-	oldTtl := e.Hdr.Ttl
+-
+-	if e.Version() != 0 {
+-		t.Fail()
+-	}
+-
+-	e.SetVersion(42)
+-	if e.Version() != 42 {
+-		t.Fail()
+-	}
+-
+-	e.SetVersion(0)
+-	if e.Hdr.Ttl != oldTtl {
+-		t.Fail()
+-	}
+-
+-	if e.ExtendedRcode() != 0 {
+-		t.Fail()
+-	}
+-
+-	e.SetExtendedRcode(42)
+-	if e.ExtendedRcode() != 42 {
+-		t.Fail()
+-	}
+-
+-	e.SetExtendedRcode(0)
+-	if e.Hdr.Ttl != oldTtl {
+-		t.Fail()
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/example_test.go b/Godeps/_workspace/src/github.com/miekg/dns/example_test.go
+deleted file mode 100644
+index 1578a4d..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/example_test.go
++++ /dev/null
+@@ -1,147 +0,0 @@
+-package dns_test
+-
+-import (
+-	"errors"
+-	"fmt"
+-	"github.com/miekg/dns"
+-	"log"
+-	"net"
+-)
+-
+-// Retrieve the MX records for miek.nl.
+-func ExampleMX() {
+-	config, _ := dns.ClientConfigFromFile("/etc/resolv.conf")
+-	c := new(dns.Client)
+-	m := new(dns.Msg)
+-	m.SetQuestion("miek.nl.", dns.TypeMX)
+-	m.RecursionDesired = true
+-	r, _, err := c.Exchange(m, config.Servers[0]+":"+config.Port)
+-	if err != nil {
+-		return
+-	}
+-	if r.Rcode != dns.RcodeSuccess {
+-		return
+-	}
+-	for _, a := range r.Answer {
+-		if mx, ok := a.(*dns.MX); ok {
+-			fmt.Printf("%s\n", mx.String())
+-		}
+-	}
+-}
+-
+-// Retrieve the DNSKEY records of a zone and convert them
+-// to DS records for SHA1, SHA256 and SHA384.
+-func ExampleDS(zone string) {
+-	config, _ := dns.ClientConfigFromFile("/etc/resolv.conf")
+-	c := new(dns.Client)
+-	m := new(dns.Msg)
+-	if zone == "" {
+-		zone = "miek.nl"
+-	}
+-	m.SetQuestion(dns.Fqdn(zone), dns.TypeDNSKEY)
+-	m.SetEdns0(4096, true)
+-	r, _, err := c.Exchange(m, config.Servers[0]+":"+config.Port)
+-	if err != nil {
+-		return
+-	}
+-	if r.Rcode != dns.RcodeSuccess {
+-		return
+-	}
+-	for _, k := range r.Answer {
+-		if key, ok := k.(*dns.DNSKEY); ok {
+-			for _, alg := range []uint8{dns.SHA1, dns.SHA256, dns.SHA384} {
+-				fmt.Printf("%s; %d\n", key.ToDS(alg).String(), key.Flags)
+-			}
+-		}
+-	}
+-}
+-
+-const TypeAPAIR = 0x0F99
+-
+-type APAIR struct {
+-	addr [2]net.IP
+-}
+-
+-func NewAPAIR() dns.PrivateRdata { return new(APAIR) }
+-
+-func (rd *APAIR) String() string { return rd.addr[0].String() + " " + rd.addr[1].String() }
+-func (rd *APAIR) Parse(txt []string) error {
+-	if len(txt) != 2 {
+-		return errors.New("two addresses required for APAIR")
+-	}
+-	for i, s := range txt {
+-		ip := net.ParseIP(s)
+-		if ip == nil {
+-			return errors.New("invalid IP in APAIR text representation")
+-		}
+-		rd.addr[i] = ip
+-	}
+-	return nil
+-}
+-
+-func (rd *APAIR) Pack(buf []byte) (int, error) {
+-	b := append([]byte(rd.addr[0]), []byte(rd.addr[1])...)
+-	n := copy(buf, b)
+-	if n != len(b) {
+-		return n, dns.ErrBuf
+-	}
+-	return n, nil
+-}
+-
+-func (rd *APAIR) Unpack(buf []byte) (int, error) {
+-	ln := net.IPv4len * 2
+-	if len(buf) != ln {
+-		return 0, errors.New("invalid length of APAIR rdata")
+-	}
+-	cp := make([]byte, ln)
+-	copy(cp, buf) // clone bytes to use them in IPs
+-
+-	rd.addr[0] = net.IP(cp[:3])
+-	rd.addr[1] = net.IP(cp[4:])
+-
+-	return len(buf), nil
+-}
+-
+-func (rd *APAIR) Copy(dest dns.PrivateRdata) error {
+-	cp := make([]byte, rd.Len())
+-	_, err := rd.Pack(cp)
+-	if err != nil {
+-		return err
+-	}
+-
+-	d := dest.(*APAIR)
+-	d.addr[0] = net.IP(cp[:3])
+-	d.addr[1] = net.IP(cp[4:])
+-	return nil
+-}
+-
+-func (rd *APAIR) Len() int {
+-	return net.IPv4len * 2
+-}
+-
+-func ExamplePrivateHandle() {
+-	dns.PrivateHandle("APAIR", TypeAPAIR, NewAPAIR)
+-	defer dns.PrivateHandleRemove(TypeAPAIR)
+-
+-	rr, err := dns.NewRR("miek.nl. APAIR (1.2.3.4    1.2.3.5)")
+-	if err != nil {
+-		log.Fatal("could not parse APAIR record: ", err)
+-	}
+-	fmt.Println(rr)
+-	// Output: miek.nl.	3600	IN	APAIR	1.2.3.4 1.2.3.5
+-
+-	m := new(dns.Msg)
+-	m.Id = 12345
+-	m.SetQuestion("miek.nl.", TypeAPAIR)
+-	m.Answer = append(m.Answer, rr)
+-
+-	fmt.Println(m)
+-	// ;; opcode: QUERY, status: NOERROR, id: 12345
+-	// ;; flags: rd; QUERY: 1, ANSWER: 1, AUTHORITY: 0, ADDITIONAL: 0
+-	//
+-	// ;; QUESTION SECTION:
+-	// ;miek.nl.	IN	 APAIR
+-	//
+-	// ;; ANSWER SECTION:
+-	// miek.nl.	3600	IN	APAIR	1.2.3.4 1.2.3.5
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/idn/example_test.go b/Godeps/_workspace/src/github.com/miekg/dns/idn/example_test.go
+deleted file mode 100644
+index 8833cd9..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/idn/example_test.go
++++ /dev/null
+@@ -1,18 +0,0 @@
+-package idn_test
+-
+-import (
+-	"fmt"
+-	"github.com/miekg/dns/idn"
+-)
+-
+-func ExampleToPunycode() {
+-	name := "インターネット.テスト"
+-	fmt.Printf("%s -> %s", name, idn.ToPunycode(name))
+-	// Output: インターネット.テスト -> xn--eckucmux0ukc.xn--zckzah
+-}
+-
+-func ExampleFromPunycode() {
+-	name := "xn--mgbaja8a1hpac.xn--mgbachtv"
+-	fmt.Printf("%s -> %s", name, idn.FromPunycode(name))
+-	// Output: xn--mgbaja8a1hpac.xn--mgbachtv -> الانترنت.اختبار
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/idn/punycode.go b/Godeps/_workspace/src/github.com/miekg/dns/idn/punycode.go
+deleted file mode 100644
+index faab402..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/idn/punycode.go
++++ /dev/null
+@@ -1,268 +0,0 @@
+-// Package idn implements encoding from and to punycode as speficied by RFC 3492.
+-package idn
+-
+-import (
+-	"bytes"
+-	"github.com/miekg/dns"
+-	"strings"
+-	"unicode"
+-)
+-
+-// Implementation idea from RFC itself and from from IDNA::Punycode created by
+-// Tatsuhiko Miyagawa <miyagawa at bulknews.net> and released under Perl Artistic
+-// License in 2002.
+-
+-const (
+-	_MIN  rune = 1
+-	_MAX  rune = 26
+-	_SKEW rune = 38
+-	_BASE rune = 36
+-	_BIAS rune = 72
+-	_N    rune = 128
+-	_DAMP rune = 700
+-
+-	_DELIMITER = '-'
+-	_PREFIX    = "xn--"
+-)
+-
+-// ToPunycode converts unicode domain names to DNS-appropriate punycode names.
+-// This function would return incorrect result for strings for non-canonical
+-// unicode strings.
+-func ToPunycode(s string) string {
+-	tokens := dns.SplitDomainName(s)
+-	switch {
+-	case s == "":
+-		return ""
+-	case tokens == nil: // s == .
+-		return "."
+-	case s[len(s)-1] == '.':
+-		tokens = append(tokens, "")
+-	}
+-
+-	for i := range tokens {
+-		tokens[i] = string(encode([]byte(tokens[i])))
+-	}
+-	return strings.Join(tokens, ".")
+-}
+-
+-// FromPunycode returns unicode domain name from provided punycode string.
+-func FromPunycode(s string) string {
+-	tokens := dns.SplitDomainName(s)
+-	switch {
+-	case s == "":
+-		return ""
+-	case tokens == nil: // s == .
+-		return "."
+-	case s[len(s)-1] == '.':
+-		tokens = append(tokens, "")
+-	}
+-	for i := range tokens {
+-		tokens[i] = string(decode([]byte(tokens[i])))
+-	}
+-	return strings.Join(tokens, ".")
+-}
+-
+-// digitval converts single byte into meaningful value that's used to calculate decoded unicode character.
+-const errdigit = 0xffff
+-
+-func digitval(code rune) rune {
+-	switch {
+-	case code >= 'A' && code <= 'Z':
+-		return code - 'A'
+-	case code >= 'a' && code <= 'z':
+-		return code - 'a'
+-	case code >= '0' && code <= '9':
+-		return code - '0' + 26
+-	}
+-	return errdigit
+-}
+-
+-// lettercode finds BASE36 byte (a-z0-9) based on calculated number.
+-func lettercode(digit rune) rune {
+-	switch {
+-	case digit >= 0 && digit <= 25:
+-		return digit + 'a'
+-	case digit >= 26 && digit <= 36:
+-		return digit - 26 + '0'
+-	}
+-	panic("dns: not reached")
+-}
+-
+-// adapt calculates next bias to be used for next iteration delta.
+-func adapt(delta rune, numpoints int, firsttime bool) rune {
+-	if firsttime {
+-		delta /= _DAMP
+-	} else {
+-		delta /= 2
+-	}
+-
+-	var k rune
+-	for delta = delta + delta/rune(numpoints); delta > (_BASE-_MIN)*_MAX/2; k += _BASE {
+-		delta /= _BASE - _MIN
+-	}
+-
+-	return k + ((_BASE-_MIN+1)*delta)/(delta+_SKEW)
+-}
+-
+-// next finds minimal rune (one with lowest codepoint value) that should be equal or above boundary.
+-func next(b []rune, boundary rune) rune {
+-	if len(b) == 0 {
+-		panic("dns: invalid set of runes to determine next one")
+-	}
+-	m := b[0]
+-	for _, x := range b[1:] {
+-		if x >= boundary && (m < boundary || x < m) {
+-			m = x
+-		}
+-	}
+-	return m
+-}
+-
+-// preprune converts unicode rune to lower case. At this time it's not
+-// supporting all things described in RFCs
+-func preprune(r rune) rune {
+-	if unicode.IsUpper(r) {
+-		r = unicode.ToLower(r)
+-	}
+-	return r
+-}
+-
+-// tfunc is a function that helps calculate each character weight
+-func tfunc(k, bias rune) rune {
+-	switch {
+-	case k <= bias:
+-		return _MIN
+-	case k >= bias+_MAX:
+-		return _MAX
+-	}
+-	return k - bias
+-}
+-
+-// encode transforms Unicode input bytes (that represent DNS label) into punycode bytestream
+-func encode(input []byte) []byte {
+-	n, bias := _N, _BIAS
+-
+-	b := bytes.Runes(input)
+-	for i := range b {
+-		b[i] = preprune(b[i])
+-	}
+-
+-	basic := make([]byte, 0, len(b))
+-	for _, ltr := range b {
+-		if ltr <= 0x7f {
+-			basic = append(basic, byte(ltr))
+-		}
+-	}
+-	basiclen := len(basic)
+-	fulllen := len(b)
+-	if basiclen == fulllen {
+-		return basic
+-	}
+-
+-	var out bytes.Buffer
+-
+-	out.WriteString(_PREFIX)
+-	if basiclen > 0 {
+-		out.Write(basic)
+-		out.WriteByte(_DELIMITER)
+-	}
+-
+-	var (
+-		ltr, nextltr rune
+-		delta, q     rune // delta calculation (see rfc)
+-		t, k, cp     rune // weight and codepoint calculation
+-	)
+-
+-	s := &bytes.Buffer{}
+-	for h := basiclen; h < fulllen; n, delta = n+1, delta+1 {
+-		nextltr = next(b, n)
+-		s.Truncate(0)
+-		s.WriteRune(nextltr)
+-		delta, n = delta+(nextltr-n)*rune(h+1), nextltr
+-
+-		for _, ltr = range b {
+-			if ltr < n {
+-				delta++
+-			}
+-			if ltr == n {
+-				q = delta
+-				for k = _BASE; ; k += _BASE {
+-					t = tfunc(k, bias)
+-					if q < t {
+-						break
+-					}
+-					cp = t + ((q - t) % (_BASE - t))
+-					out.WriteRune(lettercode(cp))
+-					q = (q - t) / (_BASE - t)
+-				}
+-
+-				out.WriteRune(lettercode(q))
+-
+-				bias = adapt(delta, h+1, h == basiclen)
+-				h, delta = h+1, 0
+-			}
+-		}
+-	}
+-	return out.Bytes()
+-}
+-
+-// decode transforms punycode input bytes (that represent DNS label) into Unicode bytestream
+-func decode(b []byte) []byte {
+-	src := b // b would move and we need to keep it
+-
+-	n, bias := _N, _BIAS
+-	if !bytes.HasPrefix(b, []byte(_PREFIX)) {
+-		return b
+-	}
+-	out := make([]rune, 0, len(b))
+-	b = b[len(_PREFIX):]
+-	for pos, x := range b {
+-		if x == _DELIMITER {
+-			out = append(out, bytes.Runes(b[:pos])...)
+-			b = b[pos+1:] // trim source string
+-			break
+-		}
+-	}
+-	if len(b) == 0 {
+-		return src
+-	}
+-	var (
+-		i, oldi, w rune
+-		ch         byte
+-		t, digit   rune
+-		ln         int
+-	)
+-
+-	for i = 0; len(b) > 0; i++ {
+-		oldi, w = i, 1
+-		for k := _BASE; len(b) > 0; k += _BASE {
+-			ch, b = b[0], b[1:]
+-			digit = digitval(rune(ch))
+-			if digit == errdigit {
+-				return src
+-			}
+-			i += digit * w
+-
+-			t = tfunc(k, bias)
+-			if digit < t {
+-				break
+-			}
+-
+-			w *= _BASE - t
+-		}
+-		ln = len(out) + 1
+-		bias = adapt(i-oldi, ln, oldi == 0)
+-		n += i / rune(ln)
+-		i = i % rune(ln)
+-		// insert
+-		out = append(out, 0)
+-		copy(out[i+1:], out[i:])
+-		out[i] = n
+-	}
+-
+-	var ret bytes.Buffer
+-	for _, r := range out {
+-		ret.WriteRune(r)
+-	}
+-	return ret.Bytes()
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/idn/punycode_test.go b/Godeps/_workspace/src/github.com/miekg/dns/idn/punycode_test.go
+deleted file mode 100644
+index 3202450..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/idn/punycode_test.go
++++ /dev/null
+@@ -1,94 +0,0 @@
+-package idn
+-
+-import (
+-	"strings"
+-	"testing"
+-)
+-
+-var testcases = [][2]string{
+-	{"", ""},
+-	{"a", "a"},
+-	{"A-B", "a-b"},
+-	{"AbC", "abc"},
+-	{"я", "xn--41a"},
+-	{"zя", "xn--z-0ub"},
+-	{"ЯZ", "xn--z-zub"},
+-	{"إختبار", "xn--kgbechtv"},
+-	{"آزمایشی", "xn--hgbk6aj7f53bba"},
+-	{"测试", "xn--0zwm56d"},
+-	{"測試", "xn--g6w251d"},
+-	{"Испытание", "xn--80akhbyknj4f"},
+-	{"परीक्षा", "xn--11b5bs3a9aj6g"},
+-	{"δοκιμή", "xn--jxalpdlp"},
+-	{"테스트", "xn--9t4b11yi5a"},
+-	{"טעסט", "xn--deba0ad"},
+-	{"テスト", "xn--zckzah"},
+-	{"பரிட்சை", "xn--hlcj6aya9esc7a"},
+-}
+-
+-func TestEncodeDecodePunycode(t *testing.T) {
+-	for _, tst := range testcases {
+-		enc := encode([]byte(tst[0]))
+-		if string(enc) != tst[1] {
+-			t.Errorf("%s encodeded as %s but should be %s", tst[0], enc, tst[1])
+-		}
+-		dec := decode([]byte(tst[1]))
+-		if string(dec) != strings.ToLower(tst[0]) {
+-			t.Errorf("%s decoded as %s but should be %s", tst[1], dec, strings.ToLower(tst[0]))
+-		}
+-	}
+-}
+-
+-func TestToFromPunycode(t *testing.T) {
+-	for _, tst := range testcases {
+-		// assert unicode.com == punycode.com
+-		full := ToPunycode(tst[0] + ".com")
+-		if full != tst[1]+".com" {
+-			t.Errorf("invalid result from string conversion to punycode, %s and should be %s.com", full, tst[1])
+-		}
+-		// assert punycode.punycode == unicode.unicode
+-		decoded := FromPunycode(tst[1] + "." + tst[1])
+-		if decoded != strings.ToLower(tst[0]+"."+tst[0]) {
+-			t.Errorf("invalid result from string conversion to punycode, %s and should be %s.%s", decoded, tst[0], tst[0])
+-		}
+-	}
+-}
+-
+-func TestEncodeDecodeFinalPeriod(t *testing.T) {
+-	for _, tst := range testcases {
+-		// assert unicode.com. == punycode.com.
+-		full := ToPunycode(tst[0] + ".")
+-		if full != tst[1]+"." {
+-			t.Errorf("invalid result from string conversion to punycode when period added at the end, %#v and should be %#v", full, tst[1]+".")
+-		}
+-		// assert punycode.com. == unicode.com.
+-		decoded := FromPunycode(tst[1] + ".")
+-		if decoded != strings.ToLower(tst[0]+".") {
+-			t.Errorf("invalid result from string conversion to punycode when period added, %#v and should be %#v", decoded, tst[0]+".")
+-		}
+-		full = ToPunycode(tst[0])
+-		if full != tst[1] {
+-			t.Errorf("invalid result from string conversion to punycode when no period added at the end, %#v and should be %#v", full, tst[1]+".")
+-		}
+-		// assert punycode.com. == unicode.com.
+-		decoded = FromPunycode(tst[1])
+-		if decoded != strings.ToLower(tst[0]) {
+-			t.Errorf("invalid result from string conversion to punycode when no period added, %#v and should be %#v", decoded, tst[0]+".")
+-		}
+-	}
+-}
+-
+-var invalid = []string{
+-	"xn--*",
+-	"xn--",
+-	"xn---",
+-}
+-
+-func TestInvalidPunycode(t *testing.T) {
+-	for _, d := range invalid {
+-		s := FromPunycode(d)
+-		if s != d {
+-			t.Errorf("Changed invalid name %s to %#v", d, s)
+-		}
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/keygen.go b/Godeps/_workspace/src/github.com/miekg/dns/keygen.go
+deleted file mode 100644
+index dfe328e..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/keygen.go
++++ /dev/null
+@@ -1,157 +0,0 @@
+-package dns
+-
+-import (
+-	"crypto/dsa"
+-	"crypto/ecdsa"
+-	"crypto/elliptic"
+-	"crypto/rand"
+-	"crypto/rsa"
+-	"math/big"
+-	"strconv"
+-)
+-
+-const _FORMAT = "Private-key-format: v1.3\n"
+-
+-// Empty interface that is used as a wrapper around all possible
+-// private key implementations from the crypto package.
+-type PrivateKey interface{}
+-
+-// Generate generates a DNSKEY of the given bit size.
+-// The public part is put inside the DNSKEY record.
+-// The Algorithm in the key must be set as this will define
+-// what kind of DNSKEY will be generated.
+-// The ECDSA algorithms imply a fixed keysize, in that case
+-// bits should be set to the size of the algorithm.
+-func (r *DNSKEY) Generate(bits int) (PrivateKey, error) {
+-	switch r.Algorithm {
+-	case DSA, DSANSEC3SHA1:
+-		if bits != 1024 {
+-			return nil, ErrKeySize
+-		}
+-	case RSAMD5, RSASHA1, RSASHA256, RSASHA1NSEC3SHA1:
+-		if bits < 512 || bits > 4096 {
+-			return nil, ErrKeySize
+-		}
+-	case RSASHA512:
+-		if bits < 1024 || bits > 4096 {
+-			return nil, ErrKeySize
+-		}
+-	case ECDSAP256SHA256:
+-		if bits != 256 {
+-			return nil, ErrKeySize
+-		}
+-	case ECDSAP384SHA384:
+-		if bits != 384 {
+-			return nil, ErrKeySize
+-		}
+-	}
+-
+-	switch r.Algorithm {
+-	case DSA, DSANSEC3SHA1:
+-		params := new(dsa.Parameters)
+-		if err := dsa.GenerateParameters(params, rand.Reader, dsa.L1024N160); err != nil {
+-			return nil, err
+-		}
+-		priv := new(dsa.PrivateKey)
+-		priv.PublicKey.Parameters = *params
+-		err := dsa.GenerateKey(priv, rand.Reader)
+-		if err != nil {
+-			return nil, err
+-		}
+-		r.setPublicKeyDSA(params.Q, params.P, params.G, priv.PublicKey.Y)
+-		return priv, nil
+-	case RSAMD5, RSASHA1, RSASHA256, RSASHA512, RSASHA1NSEC3SHA1:
+-		priv, err := rsa.GenerateKey(rand.Reader, bits)
+-		if err != nil {
+-			return nil, err
+-		}
+-		r.setPublicKeyRSA(priv.PublicKey.E, priv.PublicKey.N)
+-		return priv, nil
+-	case ECDSAP256SHA256, ECDSAP384SHA384:
+-		var c elliptic.Curve
+-		switch r.Algorithm {
+-		case ECDSAP256SHA256:
+-			c = elliptic.P256()
+-		case ECDSAP384SHA384:
+-			c = elliptic.P384()
+-		}
+-		priv, err := ecdsa.GenerateKey(c, rand.Reader)
+-		if err != nil {
+-			return nil, err
+-		}
+-		r.setPublicKeyCurve(priv.PublicKey.X, priv.PublicKey.Y)
+-		return priv, nil
+-	default:
+-		return nil, ErrAlg
+-	}
+-	return nil, nil // Dummy return
+-}
+-
+-// PrivateKeyString converts a PrivateKey to a string. This
+-// string has the same format as the private-key-file of BIND9 (Private-key-format: v1.3).
+-// It needs some info from the key (hashing, keytag), so its a method of the DNSKEY.
+-func (r *DNSKEY) PrivateKeyString(p PrivateKey) (s string) {
+-	switch t := p.(type) {
+-	case *rsa.PrivateKey:
+-		algorithm := strconv.Itoa(int(r.Algorithm)) + " (" + AlgorithmToString[r.Algorithm] + ")"
+-		modulus := toBase64(t.PublicKey.N.Bytes())
+-		e := big.NewInt(int64(t.PublicKey.E))
+-		publicExponent := toBase64(e.Bytes())
+-		privateExponent := toBase64(t.D.Bytes())
+-		prime1 := toBase64(t.Primes[0].Bytes())
+-		prime2 := toBase64(t.Primes[1].Bytes())
+-		// Calculate Exponent1/2 and Coefficient as per: http://en.wikipedia.org/wiki/RSA#Using_the_Chinese_remainder_algorithm
+-		// and from: http://code.google.com/p/go/issues/detail?id=987
+-		one := big.NewInt(1)
+-		minusone := big.NewInt(-1)
+-		p_1 := big.NewInt(0).Sub(t.Primes[0], one)
+-		q_1 := big.NewInt(0).Sub(t.Primes[1], one)
+-		exp1 := big.NewInt(0).Mod(t.D, p_1)
+-		exp2 := big.NewInt(0).Mod(t.D, q_1)
+-		coeff := big.NewInt(0).Exp(t.Primes[1], minusone, t.Primes[0])
+-
+-		exponent1 := toBase64(exp1.Bytes())
+-		exponent2 := toBase64(exp2.Bytes())
+-		coefficient := toBase64(coeff.Bytes())
+-
+-		s = _FORMAT +
+-			"Algorithm: " + algorithm + "\n" +
+-			"Modules: " + modulus + "\n" +
+-			"PublicExponent: " + publicExponent + "\n" +
+-			"PrivateExponent: " + privateExponent + "\n" +
+-			"Prime1: " + prime1 + "\n" +
+-			"Prime2: " + prime2 + "\n" +
+-			"Exponent1: " + exponent1 + "\n" +
+-			"Exponent2: " + exponent2 + "\n" +
+-			"Coefficient: " + coefficient + "\n"
+-	case *ecdsa.PrivateKey:
+-		algorithm := strconv.Itoa(int(r.Algorithm)) + " (" + AlgorithmToString[r.Algorithm] + ")"
+-		var intlen int
+-		switch r.Algorithm {
+-		case ECDSAP256SHA256:
+-			intlen = 32
+-		case ECDSAP384SHA384:
+-			intlen = 48
+-		}
+-		private := toBase64(intToBytes(t.D, intlen))
+-		s = _FORMAT +
+-			"Algorithm: " + algorithm + "\n" +
+-			"PrivateKey: " + private + "\n"
+-	case *dsa.PrivateKey:
+-		algorithm := strconv.Itoa(int(r.Algorithm)) + " (" + AlgorithmToString[r.Algorithm] + ")"
+-		T := divRoundUp(divRoundUp(t.PublicKey.Parameters.G.BitLen(), 8)-64, 8)
+-		prime := toBase64(intToBytes(t.PublicKey.Parameters.P, 64+T*8))
+-		subprime := toBase64(intToBytes(t.PublicKey.Parameters.Q, 20))
+-		base := toBase64(intToBytes(t.PublicKey.Parameters.G, 64+T*8))
+-		priv := toBase64(intToBytes(t.X, 20))
+-		pub := toBase64(intToBytes(t.PublicKey.Y, 64+T*8))
+-		s = _FORMAT +
+-			"Algorithm: " + algorithm + "\n" +
+-			"Prime(p): " + prime + "\n" +
+-			"Subprime(q): " + subprime + "\n" +
+-			"Base(g): " + base + "\n" +
+-			"Private_value(x): " + priv + "\n" +
+-			"Public_value(y): " + pub + "\n"
+-	}
+-	return
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/kscan.go b/Godeps/_workspace/src/github.com/miekg/dns/kscan.go
+deleted file mode 100644
+index c48ca2d..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/kscan.go
++++ /dev/null
+@@ -1,244 +0,0 @@
+-package dns
+-
+-import (
+-	"crypto/dsa"
+-	"crypto/ecdsa"
+-	"crypto/rsa"
+-	"io"
+-	"math/big"
+-	"strings"
+-)
+-
+-func (k *DNSKEY) NewPrivateKey(s string) (PrivateKey, error) {
+-	if s[len(s)-1] != '\n' { // We need a closing newline
+-		return k.ReadPrivateKey(strings.NewReader(s+"\n"), "")
+-	}
+-	return k.ReadPrivateKey(strings.NewReader(s), "")
+-}
+-
+-// ReadPrivateKey reads a private key from the io.Reader q. The string file is
+-// only used in error reporting.
+-// The public key must be
+-// known, because some cryptographic algorithms embed the public inside the privatekey.
+-func (k *DNSKEY) ReadPrivateKey(q io.Reader, file string) (PrivateKey, error) {
+-	m, e := parseKey(q, file)
+-	if m == nil {
+-		return nil, e
+-	}
+-	if _, ok := m["private-key-format"]; !ok {
+-		return nil, ErrPrivKey
+-	}
+-	if m["private-key-format"] != "v1.2" && m["private-key-format"] != "v1.3" {
+-		return nil, ErrPrivKey
+-	}
+-	// TODO(mg): check if the pubkey matches the private key
+-	switch m["algorithm"] {
+-	case "3 (DSA)":
+-		p, e := readPrivateKeyDSA(m)
+-		if e != nil {
+-			return nil, e
+-		}
+-		if !k.setPublicKeyInPrivate(p) {
+-			return nil, ErrKey
+-		}
+-		return p, e
+-	case "1 (RSAMD5)":
+-		fallthrough
+-	case "5 (RSASHA1)":
+-		fallthrough
+-	case "7 (RSASHA1NSEC3SHA1)":
+-		fallthrough
+-	case "8 (RSASHA256)":
+-		fallthrough
+-	case "10 (RSASHA512)":
+-		p, e := readPrivateKeyRSA(m)
+-		if e != nil {
+-			return nil, e
+-		}
+-		if !k.setPublicKeyInPrivate(p) {
+-			return nil, ErrKey
+-		}
+-		return p, e
+-	case "12 (ECC-GOST)":
+-		p, e := readPrivateKeyGOST(m)
+-		if e != nil {
+-			return nil, e
+-		}
+-		// setPublicKeyInPrivate(p)
+-		return p, e
+-	case "13 (ECDSAP256SHA256)":
+-		fallthrough
+-	case "14 (ECDSAP384SHA384)":
+-		p, e := readPrivateKeyECDSA(m)
+-		if e != nil {
+-			return nil, e
+-		}
+-		if !k.setPublicKeyInPrivate(p) {
+-			return nil, ErrKey
+-		}
+-		return p, e
+-	}
+-	return nil, ErrPrivKey
+-}
+-
+-// Read a private key (file) string and create a public key. Return the private key.
+-func readPrivateKeyRSA(m map[string]string) (PrivateKey, error) {
+-	p := new(rsa.PrivateKey)
+-	p.Primes = []*big.Int{nil, nil}
+-	for k, v := range m {
+-		switch k {
+-		case "modulus", "publicexponent", "privateexponent", "prime1", "prime2":
+-			v1, err := fromBase64([]byte(v))
+-			if err != nil {
+-				return nil, err
+-			}
+-			switch k {
+-			case "modulus":
+-				p.PublicKey.N = big.NewInt(0)
+-				p.PublicKey.N.SetBytes(v1)
+-			case "publicexponent":
+-				i := big.NewInt(0)
+-				i.SetBytes(v1)
+-				p.PublicKey.E = int(i.Int64()) // int64 should be large enough
+-			case "privateexponent":
+-				p.D = big.NewInt(0)
+-				p.D.SetBytes(v1)
+-			case "prime1":
+-				p.Primes[0] = big.NewInt(0)
+-				p.Primes[0].SetBytes(v1)
+-			case "prime2":
+-				p.Primes[1] = big.NewInt(0)
+-				p.Primes[1].SetBytes(v1)
+-			}
+-		case "exponent1", "exponent2", "coefficient":
+-			// not used in Go (yet)
+-		case "created", "publish", "activate":
+-			// not used in Go (yet)
+-		}
+-	}
+-	return p, nil
+-}
+-
+-func readPrivateKeyDSA(m map[string]string) (PrivateKey, error) {
+-	p := new(dsa.PrivateKey)
+-	p.X = big.NewInt(0)
+-	for k, v := range m {
+-		switch k {
+-		case "private_value(x)":
+-			v1, err := fromBase64([]byte(v))
+-			if err != nil {
+-				return nil, err
+-			}
+-			p.X.SetBytes(v1)
+-		case "created", "publish", "activate":
+-			/* not used in Go (yet) */
+-		}
+-	}
+-	return p, nil
+-}
+-
+-func readPrivateKeyECDSA(m map[string]string) (PrivateKey, error) {
+-	p := new(ecdsa.PrivateKey)
+-	p.D = big.NewInt(0)
+-	// TODO: validate that the required flags are present
+-	for k, v := range m {
+-		switch k {
+-		case "privatekey":
+-			v1, err := fromBase64([]byte(v))
+-			if err != nil {
+-				return nil, err
+-			}
+-			p.D.SetBytes(v1)
+-		case "created", "publish", "activate":
+-			/* not used in Go (yet) */
+-		}
+-	}
+-	return p, nil
+-}
+-
+-func readPrivateKeyGOST(m map[string]string) (PrivateKey, error) {
+-	// TODO(miek)
+-	return nil, nil
+-}
+-
+-// parseKey reads a private key from r. It returns a map[string]string,
+-// with the key-value pairs, or an error when the file is not correct.
+-func parseKey(r io.Reader, file string) (map[string]string, error) {
+-	s := scanInit(r)
+-	m := make(map[string]string)
+-	c := make(chan lex)
+-	k := ""
+-	// Start the lexer
+-	go klexer(s, c)
+-	for l := range c {
+-		// It should alternate
+-		switch l.value {
+-		case _KEY:
+-			k = l.token
+-		case _VALUE:
+-			if k == "" {
+-				return nil, &ParseError{file, "no private key seen", l}
+-			}
+-			//println("Setting", strings.ToLower(k), "to", l.token, "b")
+-			m[strings.ToLower(k)] = l.token
+-			k = ""
+-		}
+-	}
+-	return m, nil
+-}
+-
+-// klexer scans the sourcefile and returns tokens on the channel c.
+-func klexer(s *scan, c chan lex) {
+-	var l lex
+-	str := "" // Hold the current read text
+-	commt := false
+-	key := true
+-	x, err := s.tokenText()
+-	defer close(c)
+-	for err == nil {
+-		l.column = s.position.Column
+-		l.line = s.position.Line
+-		switch x {
+-		case ':':
+-			if commt {
+-				break
+-			}
+-			l.token = str
+-			if key {
+-				l.value = _KEY
+-				c <- l
+-				// Next token is a space, eat it
+-				s.tokenText()
+-				key = false
+-				str = ""
+-			} else {
+-				l.value = _VALUE
+-			}
+-		case ';':
+-			commt = true
+-		case '\n':
+-			if commt {
+-				// Reset a comment
+-				commt = false
+-			}
+-			l.value = _VALUE
+-			l.token = str
+-			c <- l
+-			str = ""
+-			commt = false
+-			key = true
+-		default:
+-			if commt {
+-				break
+-			}
+-			str += string(x)
+-		}
+-		x, err = s.tokenText()
+-	}
+-	if len(str) > 0 {
+-		// Send remainder
+-		l.token = str
+-		l.value = _VALUE
+-		c <- l
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/labels.go b/Godeps/_workspace/src/github.com/miekg/dns/labels.go
+deleted file mode 100644
+index 758e578..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/labels.go
++++ /dev/null
+@@ -1,162 +0,0 @@
+-package dns
+-
+-// Holds a bunch of helper functions for dealing with labels.
+-
+-// SplitDomainName splits a name string into it's labels.
+-// www.miek.nl. returns []string{"www", "miek", "nl"}
+-// The root label (.) returns nil. Note that using
+-// strings.Split(s) will work in most cases, but does not handle
+-// escaped dots (\.) for instance.
+-func SplitDomainName(s string) (labels []string) {
+-	if len(s) == 0 {
+-		return nil
+-	}
+-	fqdnEnd := 0 // offset of the final '.' or the length of the name
+-	idx := Split(s)
+-	begin := 0
+-	if s[len(s)-1] == '.' {
+-		fqdnEnd = len(s) - 1
+-	} else {
+-		fqdnEnd = len(s)
+-	}
+-
+-	switch len(idx) {
+-	case 0:
+-		return nil
+-	case 1:
+-		// no-op
+-	default:
+-		end := 0
+-		for i := 1; i < len(idx); i++ {
+-			end = idx[i]
+-			labels = append(labels, s[begin:end-1])
+-			begin = end
+-		}
+-	}
+-
+-	labels = append(labels, s[begin:fqdnEnd])
+-	return labels
+-}
+-
+-// CompareDomainName compares the names s1 and s2 and
+-// returns how many labels they have in common starting from the *right*.
+-// The comparison stops at the first inequality. The names are not downcased
+-// before the comparison.
+-//
+-// www.miek.nl. and miek.nl. have two labels in common: miek and nl
+-// www.miek.nl. and www.bla.nl. have one label in common: nl
+-func CompareDomainName(s1, s2 string) (n int) {
+-	s1 = Fqdn(s1)
+-	s2 = Fqdn(s2)
+-	l1 := Split(s1)
+-	l2 := Split(s2)
+-
+-	// the first check: root label
+-	if l1 == nil || l2 == nil {
+-		return
+-	}
+-
+-	j1 := len(l1) - 1 // end
+-	i1 := len(l1) - 2 // start
+-	j2 := len(l2) - 1
+-	i2 := len(l2) - 2
+-	// the second check can be done here: last/only label
+-	// before we fall through into the for-loop below
+-	if s1[l1[j1]:] == s2[l2[j2]:] {
+-		n++
+-	} else {
+-		return
+-	}
+-	for {
+-		if i1 < 0 || i2 < 0 {
+-			break
+-		}
+-		if s1[l1[i1]:l1[j1]] == s2[l2[i2]:l2[j2]] {
+-			n++
+-		} else {
+-			break
+-		}
+-		j1--
+-		i1--
+-		j2--
+-		i2--
+-	}
+-	return
+-}
+-
+-// CountLabel counts the the number of labels in the string s.
+-func CountLabel(s string) (labels int) {
+-	if s == "." {
+-		return
+-	}
+-	off := 0
+-	end := false
+-	for {
+-		off, end = NextLabel(s, off)
+-		labels++
+-		if end {
+-			return
+-		}
+-	}
+-	panic("dns: not reached")
+-}
+-
+-// Split splits a name s into its label indexes.
+-// www.miek.nl. returns []int{0, 4, 9}, www.miek.nl also returns []int{0, 4, 9}.
+-// The root name (.) returns nil. Also see dns.SplitDomainName.
+-func Split(s string) []int {
+-	if s == "." {
+-		return nil
+-	}
+-	idx := make([]int, 1, 3)
+-	off := 0
+-	end := false
+-
+-	for {
+-		off, end = NextLabel(s, off)
+-		if end {
+-			return idx
+-		}
+-		idx = append(idx, off)
+-	}
+-	panic("dns: not reached")
+-}
+-
+-// NextLabel returns the index of the start of the next label in the
+-// string s starting at offset.
+-// The bool end is true when the end of the string has been reached.
+-func NextLabel(s string, offset int) (i int, end bool) {
+-	quote := false
+-	for i = offset; i < len(s)-1; i++ {
+-		switch s[i] {
+-		case '\\':
+-			quote = !quote
+-		default:
+-			quote = false
+-		case '.':
+-			if quote {
+-				quote = !quote
+-				continue
+-			}
+-			return i + 1, false
+-		}
+-	}
+-	return i + 1, true
+-}
+-
+-// PrevLabel returns the index of the label when starting from the right and
+-// jumping n labels to the left.
+-// The bool start is true when the start of the string has been overshot.
+-func PrevLabel(s string, n int) (i int, start bool) {
+-	if n == 0 {
+-		return len(s), false
+-	}
+-	lab := Split(s)
+-	if lab == nil {
+-		return 0, true
+-	}
+-	if n > len(lab) {
+-		return 0, true
+-	}
+-	return lab[len(lab)-n], false
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/labels_test.go b/Godeps/_workspace/src/github.com/miekg/dns/labels_test.go
+deleted file mode 100644
+index 1d8da15..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/labels_test.go
++++ /dev/null
+@@ -1,214 +0,0 @@
+-package dns
+-
+-import (
+-	"testing"
+-)
+-
+-func TestCompareDomainName(t *testing.T) {
+-	s1 := "www.miek.nl."
+-	s2 := "miek.nl."
+-	s3 := "www.bla.nl."
+-	s4 := "nl.www.bla."
+-	s5 := "nl"
+-	s6 := "miek.nl"
+-
+-	if CompareDomainName(s1, s2) != 2 {
+-		t.Logf("%s with %s should be %d", s1, s2, 2)
+-		t.Fail()
+-	}
+-	if CompareDomainName(s1, s3) != 1 {
+-		t.Logf("%s with %s should be %d", s1, s3, 1)
+-		t.Fail()
+-	}
+-	if CompareDomainName(s3, s4) != 0 {
+-		t.Logf("%s with %s should be %d", s3, s4, 0)
+-		t.Fail()
+-	}
+-	// Non qualified tests
+-	if CompareDomainName(s1, s5) != 1 {
+-		t.Logf("%s with %s should be %d", s1, s5, 1)
+-		t.Fail()
+-	}
+-	if CompareDomainName(s1, s6) != 2 {
+-		t.Logf("%s with %s should be %d", s1, s5, 2)
+-		t.Fail()
+-	}
+-
+-	if CompareDomainName(s1, ".") != 0 {
+-		t.Logf("%s with %s should be %d", s1, s5, 0)
+-		t.Fail()
+-	}
+-	if CompareDomainName(".", ".") != 0 {
+-		t.Logf("%s with %s should be %d", ".", ".", 0)
+-		t.Fail()
+-	}
+-}
+-
+-func TestSplit(t *testing.T) {
+-	splitter := map[string]int{
+-		"www.miek.nl.":   3,
+-		"www.miek.nl":    3,
+-		"www..miek.nl":   4,
+-		`www\.miek.nl.`:  2,
+-		`www\\.miek.nl.`: 3,
+-		".":              0,
+-		"nl.":            1,
+-		"nl":             1,
+-		"com.":           1,
+-		".com.":          2,
+-	}
+-	for s, i := range splitter {
+-		if x := len(Split(s)); x != i {
+-			t.Logf("labels should be %d, got %d: %s %v\n", i, x, s, Split(s))
+-			t.Fail()
+-		} else {
+-			t.Logf("%s %v\n", s, Split(s))
+-		}
+-	}
+-}
+-
+-func TestSplit2(t *testing.T) {
+-	splitter := map[string][]int{
+-		"www.miek.nl.": []int{0, 4, 9},
+-		"www.miek.nl":  []int{0, 4, 9},
+-		"nl":           []int{0},
+-	}
+-	for s, i := range splitter {
+-		x := Split(s)
+-		switch len(i) {
+-		case 1:
+-			if x[0] != i[0] {
+-				t.Logf("labels should be %v, got %v: %s\n", i, x, s)
+-				t.Fail()
+-			}
+-		default:
+-			if x[0] != i[0] || x[1] != i[1] || x[2] != i[2] {
+-				t.Logf("labels should be %v, got %v: %s\n", i, x, s)
+-				t.Fail()
+-			}
+-		}
+-	}
+-}
+-
+-func TestPrevLabel(t *testing.T) {
+-	type prev struct {
+-		string
+-		int
+-	}
+-	prever := map[prev]int{
+-		prev{"www.miek.nl.", 0}: 12,
+-		prev{"www.miek.nl.", 1}: 9,
+-		prev{"www.miek.nl.", 2}: 4,
+-
+-		prev{"www.miek.nl", 0}: 11,
+-		prev{"www.miek.nl", 1}: 9,
+-		prev{"www.miek.nl", 2}: 4,
+-
+-		prev{"www.miek.nl.", 5}: 0,
+-		prev{"www.miek.nl", 5}:  0,
+-
+-		prev{"www.miek.nl.", 3}: 0,
+-		prev{"www.miek.nl", 3}:  0,
+-	}
+-	for s, i := range prever {
+-		x, ok := PrevLabel(s.string, s.int)
+-		if i != x {
+-			t.Logf("label should be %d, got %d, %t: preving %d, %s\n", i, x, ok, s.int, s.string)
+-			t.Fail()
+-		}
+-	}
+-}
+-
+-func TestCountLabel(t *testing.T) {
+-	splitter := map[string]int{
+-		"www.miek.nl.": 3,
+-		"www.miek.nl":  3,
+-		"nl":           1,
+-		".":            0,
+-	}
+-	for s, i := range splitter {
+-		x := CountLabel(s)
+-		if x != i {
+-			t.Logf("CountLabel should have %d, got %d\n", i, x)
+-			t.Fail()
+-		}
+-	}
+-}
+-
+-func TestSplitDomainName(t *testing.T) {
+-	labels := map[string][]string{
+-		"miek.nl":       []string{"miek", "nl"},
+-		".":             nil,
+-		"www.miek.nl.":  []string{"www", "miek", "nl"},
+-		"www.miek.nl":   []string{"www", "miek", "nl"},
+-		"www..miek.nl":  []string{"www", "", "miek", "nl"},
+-		`www\.miek.nl`:  []string{`www\.miek`, "nl"},
+-		`www\\.miek.nl`: []string{`www\\`, "miek", "nl"},
+-	}
+-domainLoop:
+-	for domain, splits := range labels {
+-		parts := SplitDomainName(domain)
+-		if len(parts) != len(splits) {
+-			t.Logf("SplitDomainName returned %v for %s, expected %v", parts, domain, splits)
+-			t.Fail()
+-			continue domainLoop
+-		}
+-		for i := range parts {
+-			if parts[i] != splits[i] {
+-				t.Logf("SplitDomainName returned %v for %s, expected %v", parts, domain, splits)
+-				t.Fail()
+-				continue domainLoop
+-			}
+-		}
+-	}
+-}
+-
+-func TestIsDomainName(t *testing.T) {
+-	type ret struct {
+-		ok  bool
+-		lab int
+-	}
+-	names := map[string]*ret{
+-		"..":               &ret{false, 1},
+-		"@.":               &ret{true, 1},
+-		"www.example.com":  &ret{true, 3},
+-		"www.e%ample.com":  &ret{true, 3},
+-		"www.example.com.": &ret{true, 3},
+-		"mi\\k.nl.":        &ret{true, 2},
+-		"mi\\k.nl":         &ret{true, 2},
+-	}
+-	for d, ok := range names {
+-		l, k := IsDomainName(d)
+-		if ok.ok != k || ok.lab != l {
+-			t.Logf(" got %v %d for %s ", k, l, d)
+-			t.Logf("have %v %d for %s ", ok.ok, ok.lab, d)
+-			t.Fail()
+-		}
+-	}
+-}
+-
+-func BenchmarkSplitLabels(b *testing.B) {
+-	for i := 0; i < b.N; i++ {
+-		Split("www.example.com")
+-	}
+-}
+-
+-func BenchmarkLenLabels(b *testing.B) {
+-	for i := 0; i < b.N; i++ {
+-		CountLabel("www.example.com")
+-	}
+-}
+-
+-func BenchmarkCompareLabels(b *testing.B) {
+-	for i := 0; i < b.N; i++ {
+-		CompareDomainName("www.example.com", "aa.example.com")
+-	}
+-}
+-
+-func BenchmarkIsSubDomain(b *testing.B) {
+-	for i := 0; i < b.N; i++ {
+-		IsSubDomain("www.example.com", "aa.example.com")
+-		IsSubDomain("example.com", "aa.example.com")
+-		IsSubDomain("miek.nl", "aa.example.com")
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/msg.go b/Godeps/_workspace/src/github.com/miekg/dns/msg.go
+deleted file mode 100644
+index ecba463..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/msg.go
++++ /dev/null
+@@ -1,1899 +0,0 @@
+-// DNS packet assembly, see RFC 1035. Converting from - Unpack() -
+-// and to - Pack() - wire format.
+-// All the packers and unpackers take a (msg []byte, off int)
+-// and return (off1 int, ok bool).  If they return ok==false, they
+-// also return off1==len(msg), so that the next unpacker will
+-// also fail.  This lets us avoid checks of ok until the end of a
+-// packing sequence.
+-
+-package dns
+-
+-import (
+-	"encoding/base32"
+-	"encoding/base64"
+-	"encoding/hex"
+-	"math/big"
+-	"math/rand"
+-	"net"
+-	"reflect"
+-	"strconv"
+-	"time"
+-)
+-
+-const maxCompressionOffset = 2 << 13 // We have 14 bits for the compression pointer
+-
+-var (
+-	ErrAlg           error = &Error{err: "bad algorithm"}
+-	ErrAuth          error = &Error{err: "bad authentication"}
+-	ErrBuf           error = &Error{err: "buffer size too small"}
+-	ErrConnEmpty     error = &Error{err: "conn has no connection"}
+-	ErrConn          error = &Error{err: "conn holds both UDP and TCP connection"}
+-	ErrExtendedRcode error = &Error{err: "bad extended rcode"}
+-	ErrFqdn          error = &Error{err: "domain must be fully qualified"}
+-	ErrId            error = &Error{err: "id mismatch"}
+-	ErrKeyAlg        error = &Error{err: "bad key algorithm"}
+-	ErrKey           error = &Error{err: "bad key"}
+-	ErrKeySize       error = &Error{err: "bad key size"}
+-	ErrNoSig         error = &Error{err: "no signature found"}
+-	ErrPrivKey       error = &Error{err: "bad private key"}
+-	ErrRcode         error = &Error{err: "bad rcode"}
+-	ErrRdata         error = &Error{err: "bad rdata"}
+-	ErrRRset         error = &Error{err: "bad rrset"}
+-	ErrSecret        error = &Error{err: "no secrets defined"}
+-	ErrServ          error = &Error{err: "no servers could be reached"}
+-	ErrShortRead     error = &Error{err: "short read"}
+-	ErrSig           error = &Error{err: "bad signature"}
+-	ErrSigGen        error = &Error{err: "bad signature generation"}
+-	ErrSoa           error = &Error{err: "no SOA"}
+-	ErrTime          error = &Error{err: "bad time"}
+-)
+-
+-// Id, by default, returns a 16 bits random number to be used as a
+-// message id. The random provided should be good enough. This being a
+-// variable the function can be reassigned to a custom function.
+-// For instance, to make it return a static value:
+-//
+-//	dns.Id = func() uint16 { return 3 }
+-var Id func() uint16 = id
+-
+-// A manually-unpacked version of (id, bits).
+-// This is in its own struct for easy printing.
+-type MsgHdr struct {
+-	Id                 uint16
+-	Response           bool
+-	Opcode             int
+-	Authoritative      bool
+-	Truncated          bool
+-	RecursionDesired   bool
+-	RecursionAvailable bool
+-	Zero               bool
+-	AuthenticatedData  bool
+-	CheckingDisabled   bool
+-	Rcode              int
+-}
+-
+-// The layout of a DNS message.
+-type Msg struct {
+-	MsgHdr
+-	Compress bool       `json:"-"` // If true, the message will be compressed when converted to wire format. This not part of the official DNS packet format.
+-	Question []Question // Holds the RR(s) of the question section.
+-	Answer   []RR       // Holds the RR(s) of the answer section.
+-	Ns       []RR       // Holds the RR(s) of the authority section.
+-	Extra    []RR       // Holds the RR(s) of the additional section.
+-}
+-
+-// Map of strings for each RR wire type.
+-var TypeToString = map[uint16]string{
+-	TypeA:          "A",
+-	TypeAAAA:       "AAAA",
+-	TypeAFSDB:      "AFSDB",
+-	TypeANY:        "ANY", // Meta RR
+-	TypeATMA:       "ATMA",
+-	TypeAXFR:       "AXFR", // Meta RR
+-	TypeCAA:        "CAA",
+-	TypeCDNSKEY:    "CDNSKEY",
+-	TypeCDS:        "CDS",
+-	TypeCERT:       "CERT",
+-	TypeCNAME:      "CNAME",
+-	TypeDHCID:      "DHCID",
+-	TypeDLV:        "DLV",
+-	TypeDNAME:      "DNAME",
+-	TypeDNSKEY:     "DNSKEY",
+-	TypeDS:         "DS",
+-	TypeEID:        "EID",
+-	TypeEUI48:      "EUI48",
+-	TypeEUI64:      "EUI64",
+-	TypeGID:        "GID",
+-	TypeGPOS:       "GPOS",
+-	TypeHINFO:      "HINFO",
+-	TypeHIP:        "HIP",
+-	TypeIPSECKEY:   "IPSECKEY",
+-	TypeISDN:       "ISDN",
+-	TypeIXFR:       "IXFR", // Meta RR
+-	TypeKEY:        "KEY",
+-	TypeKX:         "KX",
+-	TypeL32:        "L32",
+-	TypeL64:        "L64",
+-	TypeLOC:        "LOC",
+-	TypeLP:         "LP",
+-	TypeMB:         "MB",
+-	TypeMD:         "MD",
+-	TypeMF:         "MF",
+-	TypeMG:         "MG",
+-	TypeMINFO:      "MINFO",
+-	TypeMR:         "MR",
+-	TypeMX:         "MX",
+-	TypeNAPTR:      "NAPTR",
+-	TypeNID:        "NID",
+-	TypeNINFO:      "NINFO",
+-	TypeNIMLOC:     "NIMLOC",
+-	TypeNS:         "NS",
+-	TypeNSAP:       "NSAP",
+-	TypeNSAPPTR:    "NSAP-PTR",
+-	TypeNSEC3:      "NSEC3",
+-	TypeNSEC3PARAM: "NSEC3PARAM",
+-	TypeNSEC:       "NSEC",
+-	TypeNULL:       "NULL",
+-	TypeOPT:        "OPT",
+-	TypeOPENPGPKEY: "OPENPGPKEY",
+-	TypePTR:        "PTR",
+-	TypeRKEY:       "RKEY",
+-	TypeRP:         "RP",
+-	TypeRRSIG:      "RRSIG",
+-	TypeRT:         "RT",
+-	TypeSIG:        "SIG",
+-	TypeSOA:        "SOA",
+-	TypeSPF:        "SPF",
+-	TypeSRV:        "SRV",
+-	TypeSSHFP:      "SSHFP",
+-	TypeTA:         "TA",
+-	TypeTALINK:     "TALINK",
+-	TypeTKEY:       "TKEY", // Meta RR
+-	TypeTLSA:       "TLSA",
+-	TypeTSIG:       "TSIG", // Meta RR
+-	TypeTXT:        "TXT",
+-	TypePX:         "PX",
+-	TypeUID:        "UID",
+-	TypeUINFO:      "UINFO",
+-	TypeUNSPEC:     "UNSPEC",
+-	TypeURI:        "URI",
+-	TypeWKS:        "WKS",
+-	TypeX25:        "X25",
+-}
+-
+-// Reverse, needed for string parsing.
+-var StringToType = reverseInt16(TypeToString)
+-var StringToClass = reverseInt16(ClassToString)
+-
+-// Map of opcodes strings.
+-var StringToOpcode = reverseInt(OpcodeToString)
+-
+-// Map of rcodes strings.
+-var StringToRcode = reverseInt(RcodeToString)
+-
+-// Map of strings for each CLASS wire type.
+-var ClassToString = map[uint16]string{
+-	ClassINET:   "IN",
+-	ClassCSNET:  "CS",
+-	ClassCHAOS:  "CH",
+-	ClassHESIOD: "HS",
+-	ClassNONE:   "NONE",
+-	ClassANY:    "ANY",
+-}
+-
+-// Map of strings for opcodes.
+-var OpcodeToString = map[int]string{
+-	OpcodeQuery:  "QUERY",
+-	OpcodeIQuery: "IQUERY",
+-	OpcodeStatus: "STATUS",
+-	OpcodeNotify: "NOTIFY",
+-	OpcodeUpdate: "UPDATE",
+-}
+-
+-// Map of strings for rcodes.
+-var RcodeToString = map[int]string{
+-	RcodeSuccess:        "NOERROR",
+-	RcodeFormatError:    "FORMERR",
+-	RcodeServerFailure:  "SERVFAIL",
+-	RcodeNameError:      "NXDOMAIN",
+-	RcodeNotImplemented: "NOTIMPL",
+-	RcodeRefused:        "REFUSED",
+-	RcodeYXDomain:       "YXDOMAIN", // From RFC 2136
+-	RcodeYXRrset:        "YXRRSET",
+-	RcodeNXRrset:        "NXRRSET",
+-	RcodeNotAuth:        "NOTAUTH",
+-	RcodeNotZone:        "NOTZONE",
+-	RcodeBadSig:         "BADSIG", // Also known as RcodeBadVers, see RFC 6891
+-	//	RcodeBadVers:        "BADVERS",
+-	RcodeBadKey:   "BADKEY",
+-	RcodeBadTime:  "BADTIME",
+-	RcodeBadMode:  "BADMODE",
+-	RcodeBadName:  "BADNAME",
+-	RcodeBadAlg:   "BADALG",
+-	RcodeBadTrunc: "BADTRUNC",
+-}
+-
+-// Rather than write the usual handful of routines to pack and
+-// unpack every message that can appear on the wire, we use
+-// reflection to write a generic pack/unpack for structs and then
+-// use it. Thus, if in the future we need to define new message
+-// structs, no new pack/unpack/printing code needs to be written.
+-
+-// Domain names are a sequence of counted strings
+-// split at the dots. They end with a zero-length string.
+-
+-// PackDomainName packs a domain name s into msg[off:].
+-// If compression is wanted compress must be true and the compression
+-// map needs to hold a mapping between domain names and offsets
+-// pointing into msg[].
+-func PackDomainName(s string, msg []byte, off int, compression map[string]int, compress bool) (off1 int, err error) {
+-	off1, _, err = packDomainName(s, msg, off, compression, compress)
+-	return
+-}
+-
+-func packDomainName(s string, msg []byte, off int, compression map[string]int, compress bool) (off1 int, labels int, err error) {
+-	// special case if msg == nil
+-	lenmsg := 256
+-	if msg != nil {
+-		lenmsg = len(msg)
+-	}
+-	ls := len(s)
+-	if ls == 0 { // Ok, for instance when dealing with update RR without any rdata.
+-		return off, 0, nil
+-	}
+-	// If not fully qualified, error out, but only if msg == nil #ugly
+-	switch {
+-	case msg == nil:
+-		if s[ls-1] != '.' {
+-			s += "."
+-			ls++
+-		}
+-	case msg != nil:
+-		if s[ls-1] != '.' {
+-			return lenmsg, 0, ErrFqdn
+-		}
+-	}
+-	// Each dot ends a segment of the name.
+-	// We trade each dot byte for a length byte.
+-	// Except for escaped dots (\.), which are normal dots.
+-	// There is also a trailing zero.
+-
+-	// Compression
+-	nameoffset := -1
+-	pointer := -1
+-	// Emit sequence of counted strings, chopping at dots.
+-	begin := 0
+-	bs := []byte(s)
+-	ro_bs, bs_fresh, escaped_dot := s, true, false
+-	for i := 0; i < ls; i++ {
+-		if bs[i] == '\\' {
+-			for j := i; j < ls-1; j++ {
+-				bs[j] = bs[j+1]
+-			}
+-			ls--
+-			if off+1 > lenmsg {
+-				return lenmsg, labels, ErrBuf
+-			}
+-			// check for \DDD
+-			if i+2 < ls && isDigit(bs[i]) && isDigit(bs[i+1]) && isDigit(bs[i+2]) {
+-				bs[i] = dddToByte(bs[i:])
+-				for j := i + 1; j < ls-2; j++ {
+-					bs[j] = bs[j+2]
+-				}
+-				ls -= 2
+-			} else if bs[i] == 't' {
+-				bs[i] = '\t'
+-			} else if bs[i] == 'r' {
+-				bs[i] = '\r'
+-			} else if bs[i] == 'n' {
+-				bs[i] = '\n'
+-			}
+-			escaped_dot = bs[i] == '.'
+-			bs_fresh = false
+-			continue
+-		}
+-
+-		if bs[i] == '.' {
+-			if i > 0 && bs[i-1] == '.' && !escaped_dot {
+-				// two dots back to back is not legal
+-				return lenmsg, labels, ErrRdata
+-			}
+-			if i-begin >= 1<<6 { // top two bits of length must be clear
+-				return lenmsg, labels, ErrRdata
+-			}
+-			// off can already (we're in a loop) be bigger than len(msg)
+-			// this happens when a name isn't fully qualified
+-			if off+1 > lenmsg {
+-				return lenmsg, labels, ErrBuf
+-			}
+-			if msg != nil {
+-				msg[off] = byte(i - begin)
+-			}
+-			offset := off
+-			off++
+-			for j := begin; j < i; j++ {
+-				if off+1 > lenmsg {
+-					return lenmsg, labels, ErrBuf
+-				}
+-				if msg != nil {
+-					msg[off] = bs[j]
+-				}
+-				off++
+-			}
+-			if compress && !bs_fresh {
+-				ro_bs = string(bs)
+-				bs_fresh = true
+-			}
+-			// Dont try to compress '.'
+-			if compress && ro_bs[begin:] != "." {
+-				if p, ok := compression[ro_bs[begin:]]; !ok {
+-					// Only offsets smaller than this can be used.
+-					if offset < maxCompressionOffset {
+-						compression[ro_bs[begin:]] = offset
+-					}
+-				} else {
+-					// The first hit is the longest matching dname
+-					// keep the pointer offset we get back and store
+-					// the offset of the current name, because that's
+-					// where we need to insert the pointer later
+-
+-					// If compress is true, we're allowed to compress this dname
+-					if pointer == -1 && compress {
+-						pointer = p         // Where to point to
+-						nameoffset = offset // Where to point from
+-						break
+-					}
+-				}
+-			}
+-			labels++
+-			begin = i + 1
+-		}
+-		escaped_dot = false
+-	}
+-	// Root label is special
+-	if len(bs) == 1 && bs[0] == '.' {
+-		return off, labels, nil
+-	}
+-	// If we did compression and we find something add the pointer here
+-	if pointer != -1 {
+-		// We have two bytes (14 bits) to put the pointer in
+-		// if msg == nil, we will never do compression
+-		msg[nameoffset], msg[nameoffset+1] = packUint16(uint16(pointer ^ 0xC000))
+-		off = nameoffset + 1
+-		goto End
+-	}
+-	if msg != nil {
+-		msg[off] = 0
+-	}
+-End:
+-	off++
+-	return off, labels, nil
+-}
+-
+-// Unpack a domain name.
+-// In addition to the simple sequences of counted strings above,
+-// domain names are allowed to refer to strings elsewhere in the
+-// packet, to avoid repeating common suffixes when returning
+-// many entries in a single domain.  The pointers are marked
+-// by a length byte with the top two bits set.  Ignoring those
+-// two bits, that byte and the next give a 14 bit offset from msg[0]
+-// where we should pick up the trail.
+-// Note that if we jump elsewhere in the packet,
+-// we return off1 == the offset after the first pointer we found,
+-// which is where the next record will start.
+-// In theory, the pointers are only allowed to jump backward.
+-// We let them jump anywhere and stop jumping after a while.
+-
+-// UnpackDomainName unpacks a domain name into a string.
+-func UnpackDomainName(msg []byte, off int) (string, int, error) {
+-	s := make([]byte, 0, 64)
+-	off1 := 0
+-	lenmsg := len(msg)
+-	ptr := 0 // number of pointers followed
+-Loop:
+-	for {
+-		if off >= lenmsg {
+-			return "", lenmsg, ErrBuf
+-		}
+-		c := int(msg[off])
+-		off++
+-		switch c & 0xC0 {
+-		case 0x00:
+-			if c == 0x00 {
+-				// end of name
+-				if len(s) == 0 {
+-					return ".", off, nil
+-				}
+-				break Loop
+-			}
+-			// literal string
+-			if off+c > lenmsg {
+-				return "", lenmsg, ErrBuf
+-			}
+-			for j := off; j < off+c; j++ {
+-				switch b := msg[j]; b {
+-				case '.', '(', ')', ';', ' ', '@':
+-					fallthrough
+-				case '"', '\\':
+-					s = append(s, '\\', b)
+-				case '\t':
+-					s = append(s, '\\', 't')
+-				case '\r':
+-					s = append(s, '\\', 'r')
+-				default:
+-					if b < 32 || b >= 127 { // unprintable use \DDD
+-						var buf [3]byte
+-						bufs := strconv.AppendInt(buf[:0], int64(b), 10)
+-						s = append(s, '\\')
+-						for i := 0; i < 3-len(bufs); i++ {
+-							s = append(s, '0')
+-						}
+-						for _, r := range bufs {
+-							s = append(s, r)
+-						}
+-					} else {
+-						s = append(s, b)
+-					}
+-				}
+-			}
+-			s = append(s, '.')
+-			off += c
+-		case 0xC0:
+-			// pointer to somewhere else in msg.
+-			// remember location after first ptr,
+-			// since that's how many bytes we consumed.
+-			// also, don't follow too many pointers --
+-			// maybe there's a loop.
+-			if off >= lenmsg {
+-				return "", lenmsg, ErrBuf
+-			}
+-			c1 := msg[off]
+-			off++
+-			if ptr == 0 {
+-				off1 = off
+-			}
+-			if ptr++; ptr > 10 {
+-				return "", lenmsg, &Error{err: "too many compression pointers"}
+-			}
+-			off = (c^0xC0)<<8 | int(c1)
+-		default:
+-			// 0x80 and 0x40 are reserved
+-			return "", lenmsg, ErrRdata
+-		}
+-	}
+-	if ptr == 0 {
+-		off1 = off
+-	}
+-	return string(s), off1, nil
+-}
+-
+-func packTxt(txt []string, msg []byte, offset int, tmp []byte) (int, error) {
+-	var err error
+-	if len(txt) == 0 {
+-		if offset >= len(msg) {
+-			return offset, ErrBuf
+-		}
+-		msg[offset] = 0
+-		return offset, nil
+-	}
+-	for i := range txt {
+-		if len(txt[i]) > len(tmp) {
+-			return offset, ErrBuf
+-		}
+-		offset, err = packTxtString(txt[i], msg, offset, tmp)
+-		if err != nil {
+-			return offset, err
+-		}
+-	}
+-	return offset, err
+-}
+-
+-func packTxtString(s string, msg []byte, offset int, tmp []byte) (int, error) {
+-	lenByteOffset := offset
+-	if offset >= len(msg) {
+-		return offset, ErrBuf
+-	}
+-	offset++
+-	bs := tmp[:len(s)]
+-	copy(bs, s)
+-	for i := 0; i < len(bs); i++ {
+-		if len(msg) <= offset {
+-			return offset, ErrBuf
+-		}
+-		if bs[i] == '\\' {
+-			i++
+-			if i == len(bs) {
+-				break
+-			}
+-			// check for \DDD
+-			if i+2 < len(bs) && isDigit(bs[i]) && isDigit(bs[i+1]) && isDigit(bs[i+2]) {
+-				msg[offset] = dddToByte(bs[i:])
+-				i += 2
+-			} else if bs[i] == 't' {
+-				msg[offset] = '\t'
+-			} else if bs[i] == 'r' {
+-				msg[offset] = '\r'
+-			} else if bs[i] == 'n' {
+-				msg[offset] = '\n'
+-			} else {
+-				msg[offset] = bs[i]
+-			}
+-		} else {
+-			msg[offset] = bs[i]
+-		}
+-		offset++
+-	}
+-	l := offset - lenByteOffset - 1
+-	if l > 255 {
+-		return offset, &Error{err: "string exceeded 255 bytes in txt"}
+-	}
+-	msg[lenByteOffset] = byte(l)
+-	return offset, nil
+-}
+-
+-func unpackTxt(msg []byte, offset, rdend int) ([]string, int, error) {
+-	var err error
+-	var ss []string
+-	var s string
+-	for offset < rdend && err == nil {
+-		s, offset, err = unpackTxtString(msg, offset)
+-		if err == nil {
+-			ss = append(ss, s)
+-		}
+-	}
+-	return ss, offset, err
+-}
+-
+-func unpackTxtString(msg []byte, offset int) (string, int, error) {
+-	if offset+1 > len(msg) {
+-		return "", offset, &Error{err: "overflow unpacking txt"}
+-	}
+-	l := int(msg[offset])
+-	if offset+l+1 > len(msg) {
+-		return "", offset, &Error{err: "overflow unpacking txt"}
+-	}
+-	s := make([]byte, 0, l)
+-	for _, b := range msg[offset+1 : offset+1+l] {
+-		switch b {
+-		case '"', '\\':
+-			s = append(s, '\\', b)
+-		case '\t':
+-			s = append(s, `\t`...)
+-		case '\r':
+-			s = append(s, `\r`...)
+-		case '\n':
+-			s = append(s, `\n`...)
+-		default:
+-			if b < 32 || b > 127 { // unprintable
+-				var buf [3]byte
+-				bufs := strconv.AppendInt(buf[:0], int64(b), 10)
+-				s = append(s, '\\')
+-				for i := 0; i < 3-len(bufs); i++ {
+-					s = append(s, '0')
+-				}
+-				for _, r := range bufs {
+-					s = append(s, r)
+-				}
+-			} else {
+-				s = append(s, b)
+-			}
+-		}
+-	}
+-	offset += 1 + l
+-	return string(s), offset, nil
+-}
+-
+-// Pack a reflect.StructValue into msg.  Struct members can only be uint8, uint16, uint32, string,
+-// slices and other (often anonymous) structs.
+-func packStructValue(val reflect.Value, msg []byte, off int, compression map[string]int, compress bool) (off1 int, err error) {
+-	var txtTmp []byte
+-	lenmsg := len(msg)
+-	numfield := val.NumField()
+-	for i := 0; i < numfield; i++ {
+-		typefield := val.Type().Field(i)
+-		if typefield.Tag == `dns:"-"` {
+-			continue
+-		}
+-		switch fv := val.Field(i); fv.Kind() {
+-		default:
+-			return lenmsg, &Error{err: "bad kind packing"}
+-		case reflect.Interface:
+-			// PrivateRR is the only RR implementation that has interface field.
+-			// therefore it's expected that this interface would be PrivateRdata
+-			switch data := fv.Interface().(type) {
+-			case PrivateRdata:
+-				n, err := data.Pack(msg[off:])
+-				if err != nil {
+-					return lenmsg, err
+-				}
+-				off += n
+-			default:
+-				return lenmsg, &Error{err: "bad kind interface packing"}
+-			}
+-		case reflect.Slice:
+-			switch typefield.Tag {
+-			default:
+-				return lenmsg, &Error{"bad tag packing slice: " + typefield.Tag.Get("dns")}
+-			case `dns:"domain-name"`:
+-				for j := 0; j < val.Field(i).Len(); j++ {
+-					element := val.Field(i).Index(j).String()
+-					off, err = PackDomainName(element, msg, off, compression, false && compress)
+-					if err != nil {
+-						return lenmsg, err
+-					}
+-				}
+-			case `dns:"txt"`:
+-				if txtTmp == nil {
+-					txtTmp = make([]byte, 256*4+1)
+-				}
+-				off, err = packTxt(fv.Interface().([]string), msg, off, txtTmp)
+-				if err != nil {
+-					return lenmsg, err
+-				}
+-			case `dns:"opt"`: // edns
+-				for j := 0; j < val.Field(i).Len(); j++ {
+-					element := val.Field(i).Index(j).Interface()
+-					b, e := element.(EDNS0).pack()
+-					if e != nil {
+-						return lenmsg, &Error{err: "overflow packing opt"}
+-					}
+-					// Option code
+-					msg[off], msg[off+1] = packUint16(element.(EDNS0).Option())
+-					// Length
+-					msg[off+2], msg[off+3] = packUint16(uint16(len(b)))
+-					off += 4
+-					if off+len(b) > lenmsg {
+-						copy(msg[off:], b)
+-						off = lenmsg
+-						continue
+-					}
+-					// Actual data
+-					copy(msg[off:off+len(b)], b)
+-					off += len(b)
+-				}
+-			case `dns:"a"`:
+-				// It must be a slice of 4, even if it is 16, we encode
+-				// only the first 4
+-				if off+net.IPv4len > lenmsg {
+-					return lenmsg, &Error{err: "overflow packing a"}
+-				}
+-				switch fv.Len() {
+-				case net.IPv6len:
+-					msg[off] = byte(fv.Index(12).Uint())
+-					msg[off+1] = byte(fv.Index(13).Uint())
+-					msg[off+2] = byte(fv.Index(14).Uint())
+-					msg[off+3] = byte(fv.Index(15).Uint())
+-					off += net.IPv4len
+-				case net.IPv4len:
+-					msg[off] = byte(fv.Index(0).Uint())
+-					msg[off+1] = byte(fv.Index(1).Uint())
+-					msg[off+2] = byte(fv.Index(2).Uint())
+-					msg[off+3] = byte(fv.Index(3).Uint())
+-					off += net.IPv4len
+-				case 0:
+-					// Allowed, for dynamic updates
+-				default:
+-					return lenmsg, &Error{err: "overflow packing a"}
+-				}
+-			case `dns:"aaaa"`:
+-				if fv.Len() == 0 {
+-					break
+-				}
+-				if fv.Len() > net.IPv6len || off+fv.Len() > lenmsg {
+-					return lenmsg, &Error{err: "overflow packing aaaa"}
+-				}
+-				for j := 0; j < net.IPv6len; j++ {
+-					msg[off] = byte(fv.Index(j).Uint())
+-					off++
+-				}
+-			case `dns:"wks"`:
+-				// TODO(miek): this is wrong should be lenrd
+-				if off == lenmsg {
+-					break // dyn. updates
+-				}
+-				if val.Field(i).Len() == 0 {
+-					break
+-				}
+-				var bitmapbyte uint16
+-				for j := 0; j < val.Field(i).Len(); j++ {
+-					serv := uint16((fv.Index(j).Uint()))
+-					bitmapbyte = uint16(serv / 8)
+-					if int(bitmapbyte) > lenmsg {
+-						return lenmsg, &Error{err: "overflow packing wks"}
+-					}
+-					bit := uint16(serv) - bitmapbyte*8
+-					msg[bitmapbyte] = byte(1 << (7 - bit))
+-				}
+-				off += int(bitmapbyte)
+-			case `dns:"nsec"`: // NSEC/NSEC3
+-				// This is the uint16 type bitmap
+-				if val.Field(i).Len() == 0 {
+-					// Do absolutely nothing
+-					break
+-				}
+-
+-				lastwindow := uint16(0)
+-				length := uint16(0)
+-				if off+2 > lenmsg {
+-					return lenmsg, &Error{err: "overflow packing nsecx"}
+-				}
+-				for j := 0; j < val.Field(i).Len(); j++ {
+-					t := uint16((fv.Index(j).Uint()))
+-					window := uint16(t / 256)
+-					if lastwindow != window {
+-						// New window, jump to the new offset
+-						off += int(length) + 3
+-						if off > lenmsg {
+-							return lenmsg, &Error{err: "overflow packing nsecx bitmap"}
+-						}
+-					}
+-					length = (t - window*256) / 8
+-					bit := t - (window * 256) - (length * 8)
+-					if off+2+int(length) > lenmsg {
+-						return lenmsg, &Error{err: "overflow packing nsecx bitmap"}
+-					}
+-
+-					// Setting the window #
+-					msg[off] = byte(window)
+-					// Setting the octets length
+-					msg[off+1] = byte(length + 1)
+-					// Setting the bit value for the type in the right octet
+-					msg[off+2+int(length)] |= byte(1 << (7 - bit))
+-					lastwindow = window
+-				}
+-				off += 2 + int(length)
+-				off++
+-				if off > lenmsg {
+-					return lenmsg, &Error{err: "overflow packing nsecx bitmap"}
+-				}
+-			}
+-		case reflect.Struct:
+-			off, err = packStructValue(fv, msg, off, compression, compress)
+-			if err != nil {
+-				return lenmsg, err
+-			}
+-		case reflect.Uint8:
+-			if off+1 > lenmsg {
+-				return lenmsg, &Error{err: "overflow packing uint8"}
+-			}
+-			msg[off] = byte(fv.Uint())
+-			off++
+-		case reflect.Uint16:
+-			if off+2 > lenmsg {
+-				return lenmsg, &Error{err: "overflow packing uint16"}
+-			}
+-			i := fv.Uint()
+-			msg[off] = byte(i >> 8)
+-			msg[off+1] = byte(i)
+-			off += 2
+-		case reflect.Uint32:
+-			if off+4 > lenmsg {
+-				return lenmsg, &Error{err: "overflow packing uint32"}
+-			}
+-			i := fv.Uint()
+-			msg[off] = byte(i >> 24)
+-			msg[off+1] = byte(i >> 16)
+-			msg[off+2] = byte(i >> 8)
+-			msg[off+3] = byte(i)
+-			off += 4
+-		case reflect.Uint64:
+-			switch typefield.Tag {
+-			default:
+-				if off+8 > lenmsg {
+-					return lenmsg, &Error{err: "overflow packing uint64"}
+-				}
+-				i := fv.Uint()
+-				msg[off] = byte(i >> 56)
+-				msg[off+1] = byte(i >> 48)
+-				msg[off+2] = byte(i >> 40)
+-				msg[off+3] = byte(i >> 32)
+-				msg[off+4] = byte(i >> 24)
+-				msg[off+5] = byte(i >> 16)
+-				msg[off+6] = byte(i >> 8)
+-				msg[off+7] = byte(i)
+-				off += 8
+-			case `dns:"uint48"`:
+-				// Used in TSIG, where it stops at 48 bits, so we discard the upper 16
+-				if off+6 > lenmsg {
+-					return lenmsg, &Error{err: "overflow packing uint64 as uint48"}
+-				}
+-				i := fv.Uint()
+-				msg[off] = byte(i >> 40)
+-				msg[off+1] = byte(i >> 32)
+-				msg[off+2] = byte(i >> 24)
+-				msg[off+3] = byte(i >> 16)
+-				msg[off+4] = byte(i >> 8)
+-				msg[off+5] = byte(i)
+-				off += 6
+-			}
+-		case reflect.String:
+-			// There are multiple string encodings.
+-			// The tag distinguishes ordinary strings from domain names.
+-			s := fv.String()
+-			switch typefield.Tag {
+-			default:
+-				return lenmsg, &Error{"bad tag packing string: " + typefield.Tag.Get("dns")}
+-			case `dns:"base64"`:
+-				b64, e := fromBase64([]byte(s))
+-				if e != nil {
+-					return lenmsg, e
+-				}
+-				copy(msg[off:off+len(b64)], b64)
+-				off += len(b64)
+-			case `dns:"domain-name"`:
+-				if off, err = PackDomainName(s, msg, off, compression, false && compress); err != nil {
+-					return lenmsg, err
+-				}
+-			case `dns:"cdomain-name"`:
+-				if off, err = PackDomainName(s, msg, off, compression, true && compress); err != nil {
+-					return lenmsg, err
+-				}
+-			case `dns:"size-base32"`:
+-				// This is purely for NSEC3 atm, the previous byte must
+-				// holds the length of the encoded string. As NSEC3
+-				// is only defined to SHA1, the hashlength is 20 (160 bits)
+-				msg[off-1] = 20
+-				fallthrough
+-			case `dns:"base32"`:
+-				b32, e := fromBase32([]byte(s))
+-				if e != nil {
+-					return lenmsg, e
+-				}
+-				copy(msg[off:off+len(b32)], b32)
+-				off += len(b32)
+-			case `dns:"size-hex"`:
+-				fallthrough
+-			case `dns:"hex"`:
+-				// There is no length encoded here
+-				h, e := hex.DecodeString(s)
+-				if e != nil {
+-					return lenmsg, e
+-				}
+-				if off+hex.DecodedLen(len(s)) > lenmsg {
+-					return lenmsg, &Error{err: "overflow packing hex"}
+-				}
+-				copy(msg[off:off+hex.DecodedLen(len(s))], h)
+-				off += hex.DecodedLen(len(s))
+-			case `dns:"size"`:
+-				// the size is already encoded in the RR, we can safely use the
+-				// length of string. String is RAW (not encoded in hex, nor base64)
+-				copy(msg[off:off+len(s)], s)
+-				off += len(s)
+-			case `dns:"txt"`:
+-				fallthrough
+-			case "":
+-				if txtTmp == nil {
+-					txtTmp = make([]byte, 256*4+1)
+-				}
+-				off, err = packTxtString(fv.String(), msg, off, txtTmp)
+-				if err != nil {
+-					return lenmsg, err
+-				}
+-			}
+-		}
+-	}
+-	return off, nil
+-}
+-
+-func structValue(any interface{}) reflect.Value {
+-	return reflect.ValueOf(any).Elem()
+-}
+-
+-// PackStruct packs any structure to wire format.
+-func PackStruct(any interface{}, msg []byte, off int) (off1 int, err error) {
+-	off, err = packStructValue(structValue(any), msg, off, nil, false)
+-	return off, err
+-}
+-
+-func packStructCompress(any interface{}, msg []byte, off int, compression map[string]int, compress bool) (off1 int, err error) {
+-	off, err = packStructValue(structValue(any), msg, off, compression, compress)
+-	return off, err
+-}
+-
+-// TODO(miek): Fix use of rdlength here
+-
+-// Unpack a reflect.StructValue from msg.
+-// Same restrictions as packStructValue.
+-func unpackStructValue(val reflect.Value, msg []byte, off int) (off1 int, err error) {
+-	var lenrd int
+-	lenmsg := len(msg)
+-	for i := 0; i < val.NumField(); i++ {
+-		if lenrd != 0 && lenrd == off {
+-			break
+-		}
+-		if off > lenmsg {
+-			return lenmsg, &Error{"bad offset unpacking"}
+-		}
+-		switch fv := val.Field(i); fv.Kind() {
+-		default:
+-			return lenmsg, &Error{err: "bad kind unpacking"}
+-		case reflect.Interface:
+-			// PrivateRR is the only RR implementation that has interface field.
+-			// therefore it's expected that this interface would be PrivateRdata
+-			switch data := fv.Interface().(type) {
+-			case PrivateRdata:
+-				n, err := data.Unpack(msg[off:lenrd])
+-				if err != nil {
+-					return lenmsg, err
+-				}
+-				off += n
+-			default:
+-				return lenmsg, &Error{err: "bad kind interface unpacking"}
+-			}
+-		case reflect.Slice:
+-			switch val.Type().Field(i).Tag {
+-			default:
+-				return lenmsg, &Error{"bad tag unpacking slice: " + val.Type().Field(i).Tag.Get("dns")}
+-			case `dns:"domain-name"`:
+-				// HIP record slice of name (or none)
+-				servers := make([]string, 0)
+-				var s string
+-				for off < lenrd {
+-					s, off, err = UnpackDomainName(msg, off)
+-					if err != nil {
+-						return lenmsg, err
+-					}
+-					servers = append(servers, s)
+-				}
+-				fv.Set(reflect.ValueOf(servers))
+-			case `dns:"txt"`:
+-				if off == lenmsg || lenrd == off {
+-					break
+-				}
+-				var txt []string
+-				txt, off, err = unpackTxt(msg, off, lenrd)
+-				if err != nil {
+-					return lenmsg, err
+-				}
+-				fv.Set(reflect.ValueOf(txt))
+-			case `dns:"opt"`: // edns0
+-				if off == lenrd {
+-					// This is an EDNS0 (OPT Record) with no rdata
+-					// We can safely return here.
+-					break
+-				}
+-				edns := make([]EDNS0, 0)
+-			Option:
+-				code := uint16(0)
+-				if off+2 > lenmsg {
+-					return lenmsg, &Error{err: "overflow unpacking opt"}
+-				}
+-				code, off = unpackUint16(msg, off)
+-				optlen, off1 := unpackUint16(msg, off)
+-				if off1+int(optlen) > lenrd {
+-					return lenmsg, &Error{err: "overflow unpacking opt"}
+-				}
+-				switch code {
+-				case EDNS0NSID:
+-					e := new(EDNS0_NSID)
+-					if err := e.unpack(msg[off1 : off1+int(optlen)]); err != nil {
+-						return lenmsg, err
+-					}
+-					edns = append(edns, e)
+-					off = off1 + int(optlen)
+-				case EDNS0SUBNET, EDNS0SUBNETDRAFT:
+-					e := new(EDNS0_SUBNET)
+-					if err := e.unpack(msg[off1 : off1+int(optlen)]); err != nil {
+-						return lenmsg, err
+-					}
+-					edns = append(edns, e)
+-					off = off1 + int(optlen)
+-					if code == EDNS0SUBNETDRAFT {
+-						e.DraftOption = true
+-					}
+-				case EDNS0UL:
+-					e := new(EDNS0_UL)
+-					if err := e.unpack(msg[off1 : off1+int(optlen)]); err != nil {
+-						return lenmsg, err
+-					}
+-					edns = append(edns, e)
+-					off = off1 + int(optlen)
+-				case EDNS0LLQ:
+-					e := new(EDNS0_LLQ)
+-					if err := e.unpack(msg[off1 : off1+int(optlen)]); err != nil {
+-						return lenmsg, err
+-					}
+-					edns = append(edns, e)
+-					off = off1 + int(optlen)
+-				case EDNS0DAU:
+-					e := new(EDNS0_DAU)
+-					if err := e.unpack(msg[off1 : off1+int(optlen)]); err != nil {
+-						return lenmsg, err
+-					}
+-					edns = append(edns, e)
+-					off = off1 + int(optlen)
+-				case EDNS0DHU:
+-					e := new(EDNS0_DHU)
+-					if err := e.unpack(msg[off1 : off1+int(optlen)]); err != nil {
+-						return lenmsg, err
+-					}
+-					edns = append(edns, e)
+-					off = off1 + int(optlen)
+-				case EDNS0N3U:
+-					e := new(EDNS0_N3U)
+-					if err := e.unpack(msg[off1 : off1+int(optlen)]); err != nil {
+-						return lenmsg, err
+-					}
+-					edns = append(edns, e)
+-					off = off1 + int(optlen)
+-				default:
+-					// do nothing?
+-					off = off1 + int(optlen)
+-				}
+-				if off < lenrd {
+-					goto Option
+-				}
+-				fv.Set(reflect.ValueOf(edns))
+-			case `dns:"a"`:
+-				if off == lenrd {
+-					break // dyn. update
+-				}
+-				if off+net.IPv4len > lenrd || off+net.IPv4len > lenmsg {
+-					return lenmsg, &Error{err: "overflow unpacking a"}
+-				}
+-				fv.Set(reflect.ValueOf(net.IPv4(msg[off], msg[off+1], msg[off+2], msg[off+3])))
+-				off += net.IPv4len
+-			case `dns:"aaaa"`:
+-				if off == lenrd {
+-					break
+-				}
+-				if off+net.IPv6len > lenrd || off+net.IPv6len > lenmsg {
+-					return lenmsg, &Error{err: "overflow unpacking aaaa"}
+-				}
+-				fv.Set(reflect.ValueOf(net.IP{msg[off], msg[off+1], msg[off+2], msg[off+3], msg[off+4],
+-					msg[off+5], msg[off+6], msg[off+7], msg[off+8], msg[off+9], msg[off+10],
+-					msg[off+11], msg[off+12], msg[off+13], msg[off+14], msg[off+15]}))
+-				off += net.IPv6len
+-			case `dns:"wks"`:
+-				// Rest of the record is the bitmap
+-				serv := make([]uint16, 0)
+-				j := 0
+-				for off < lenrd {
+-					if off+1 > lenmsg {
+-						return lenmsg, &Error{err: "overflow unpacking wks"}
+-					}
+-					b := msg[off]
+-					// Check the bits one by one, and set the type
+-					if b&0x80 == 0x80 {
+-						serv = append(serv, uint16(j*8+0))
+-					}
+-					if b&0x40 == 0x40 {
+-						serv = append(serv, uint16(j*8+1))
+-					}
+-					if b&0x20 == 0x20 {
+-						serv = append(serv, uint16(j*8+2))
+-					}
+-					if b&0x10 == 0x10 {
+-						serv = append(serv, uint16(j*8+3))
+-					}
+-					if b&0x8 == 0x8 {
+-						serv = append(serv, uint16(j*8+4))
+-					}
+-					if b&0x4 == 0x4 {
+-						serv = append(serv, uint16(j*8+5))
+-					}
+-					if b&0x2 == 0x2 {
+-						serv = append(serv, uint16(j*8+6))
+-					}
+-					if b&0x1 == 0x1 {
+-						serv = append(serv, uint16(j*8+7))
+-					}
+-					j++
+-					off++
+-				}
+-				fv.Set(reflect.ValueOf(serv))
+-			case `dns:"nsec"`: // NSEC/NSEC3
+-				if off == lenrd {
+-					break
+-				}
+-				// Rest of the record is the type bitmap
+-				if off+2 > lenrd || off+2 > lenmsg {
+-					return lenmsg, &Error{err: "overflow unpacking nsecx"}
+-				}
+-				nsec := make([]uint16, 0)
+-				length := 0
+-				window := 0
+-				for off+2 < lenrd {
+-					window = int(msg[off])
+-					length = int(msg[off+1])
+-					//println("off, windows, length, end", off, window, length, endrr)
+-					if length == 0 {
+-						// A length window of zero is strange. If there
+-						// the window should not have been specified. Bail out
+-						// println("dns: length == 0 when unpacking NSEC")
+-						return lenmsg, &Error{err: "overflow unpacking nsecx"}
+-					}
+-					if length > 32 {
+-						return lenmsg, &Error{err: "overflow unpacking nsecx"}
+-					}
+-
+-					// Walk the bytes in the window - and check the bit settings...
+-					off += 2
+-					for j := 0; j < length; j++ {
+-						if off+j+1 > lenmsg {
+-							return lenmsg, &Error{err: "overflow unpacking nsecx"}
+-						}
+-						b := msg[off+j]
+-						// Check the bits one by one, and set the type
+-						if b&0x80 == 0x80 {
+-							nsec = append(nsec, uint16(window*256+j*8+0))
+-						}
+-						if b&0x40 == 0x40 {
+-							nsec = append(nsec, uint16(window*256+j*8+1))
+-						}
+-						if b&0x20 == 0x20 {
+-							nsec = append(nsec, uint16(window*256+j*8+2))
+-						}
+-						if b&0x10 == 0x10 {
+-							nsec = append(nsec, uint16(window*256+j*8+3))
+-						}
+-						if b&0x8 == 0x8 {
+-							nsec = append(nsec, uint16(window*256+j*8+4))
+-						}
+-						if b&0x4 == 0x4 {
+-							nsec = append(nsec, uint16(window*256+j*8+5))
+-						}
+-						if b&0x2 == 0x2 {
+-							nsec = append(nsec, uint16(window*256+j*8+6))
+-						}
+-						if b&0x1 == 0x1 {
+-							nsec = append(nsec, uint16(window*256+j*8+7))
+-						}
+-					}
+-					off += length
+-				}
+-				fv.Set(reflect.ValueOf(nsec))
+-			}
+-		case reflect.Struct:
+-			off, err = unpackStructValue(fv, msg, off)
+-			if err != nil {
+-				return lenmsg, err
+-			}
+-			if val.Type().Field(i).Name == "Hdr" {
+-				lenrd = off + int(val.FieldByName("Hdr").FieldByName("Rdlength").Uint())
+-			}
+-		case reflect.Uint8:
+-			if off == lenmsg {
+-				break
+-			}
+-			if off+1 > lenmsg {
+-				return lenmsg, &Error{err: "overflow unpacking uint8"}
+-			}
+-			fv.SetUint(uint64(uint8(msg[off])))
+-			off++
+-		case reflect.Uint16:
+-			if off == lenmsg {
+-				break
+-			}
+-			var i uint16
+-			if off+2 > lenmsg {
+-				return lenmsg, &Error{err: "overflow unpacking uint16"}
+-			}
+-			i, off = unpackUint16(msg, off)
+-			fv.SetUint(uint64(i))
+-		case reflect.Uint32:
+-			if off == lenmsg {
+-				break
+-			}
+-			if off+4 > lenmsg {
+-				return lenmsg, &Error{err: "overflow unpacking uint32"}
+-			}
+-			fv.SetUint(uint64(uint32(msg[off])<<24 | uint32(msg[off+1])<<16 | uint32(msg[off+2])<<8 | uint32(msg[off+3])))
+-			off += 4
+-		case reflect.Uint64:
+-			switch val.Type().Field(i).Tag {
+-			default:
+-				if off+8 > lenmsg {
+-					return lenmsg, &Error{err: "overflow unpacking uint64"}
+-				}
+-				fv.SetUint(uint64(uint64(msg[off])<<56 | uint64(msg[off+1])<<48 | uint64(msg[off+2])<<40 |
+-					uint64(msg[off+3])<<32 | uint64(msg[off+4])<<24 | uint64(msg[off+5])<<16 | uint64(msg[off+6])<<8 | uint64(msg[off+7])))
+-				off += 8
+-			case `dns:"uint48"`:
+-				// Used in TSIG where the last 48 bits are occupied, so for now, assume a uint48 (6 bytes)
+-				if off+6 > lenmsg {
+-					return lenmsg, &Error{err: "overflow unpacking uint64 as uint48"}
+-				}
+-				fv.SetUint(uint64(uint64(msg[off])<<40 | uint64(msg[off+1])<<32 | uint64(msg[off+2])<<24 | uint64(msg[off+3])<<16 |
+-					uint64(msg[off+4])<<8 | uint64(msg[off+5])))
+-				off += 6
+-			}
+-		case reflect.String:
+-			var s string
+-			if off == lenmsg {
+-				break
+-			}
+-			switch val.Type().Field(i).Tag {
+-			default:
+-				return lenmsg, &Error{"bad tag unpacking string: " + val.Type().Field(i).Tag.Get("dns")}
+-			case `dns:"hex"`:
+-				hexend := lenrd
+-				if val.FieldByName("Hdr").FieldByName("Rrtype").Uint() == uint64(TypeHIP) {
+-					hexend = off + int(val.FieldByName("HitLength").Uint())
+-				}
+-				if hexend > lenrd || hexend > lenmsg {
+-					return lenmsg, &Error{err: "overflow unpacking hex"}
+-				}
+-				s = hex.EncodeToString(msg[off:hexend])
+-				off = hexend
+-			case `dns:"base64"`:
+-				// Rest of the RR is base64 encoded value
+-				b64end := lenrd
+-				if val.FieldByName("Hdr").FieldByName("Rrtype").Uint() == uint64(TypeHIP) {
+-					b64end = off + int(val.FieldByName("PublicKeyLength").Uint())
+-				}
+-				if b64end > lenrd || b64end > lenmsg {
+-					return lenmsg, &Error{err: "overflow unpacking base64"}
+-				}
+-				s = toBase64(msg[off:b64end])
+-				off = b64end
+-			case `dns:"cdomain-name"`:
+-				fallthrough
+-			case `dns:"domain-name"`:
+-				if off == lenmsg {
+-					// zero rdata foo, OK for dyn. updates
+-					break
+-				}
+-				s, off, err = UnpackDomainName(msg, off)
+-				if err != nil {
+-					return lenmsg, err
+-				}
+-			case `dns:"size-base32"`:
+-				var size int
+-				switch val.Type().Name() {
+-				case "NSEC3":
+-					switch val.Type().Field(i).Name {
+-					case "NextDomain":
+-						name := val.FieldByName("HashLength")
+-						size = int(name.Uint())
+-					}
+-				}
+-				if off+size > lenmsg {
+-					return lenmsg, &Error{err: "overflow unpacking base32"}
+-				}
+-				s = toBase32(msg[off : off+size])
+-				off += size
+-			case `dns:"size-hex"`:
+-				// a "size" string, but it must be encoded in hex in the string
+-				var size int
+-				switch val.Type().Name() {
+-				case "NSEC3":
+-					switch val.Type().Field(i).Name {
+-					case "Salt":
+-						name := val.FieldByName("SaltLength")
+-						size = int(name.Uint())
+-					case "NextDomain":
+-						name := val.FieldByName("HashLength")
+-						size = int(name.Uint())
+-					}
+-				case "TSIG":
+-					switch val.Type().Field(i).Name {
+-					case "MAC":
+-						name := val.FieldByName("MACSize")
+-						size = int(name.Uint())
+-					case "OtherData":
+-						name := val.FieldByName("OtherLen")
+-						size = int(name.Uint())
+-					}
+-				}
+-				if off+size > lenmsg {
+-					return lenmsg, &Error{err: "overflow unpacking hex"}
+-				}
+-				s = hex.EncodeToString(msg[off : off+size])
+-				off += size
+-			case `dns:"txt"`:
+-				fallthrough
+-			case "":
+-				s, off, err = unpackTxtString(msg, off)
+-			}
+-			fv.SetString(s)
+-		}
+-	}
+-	return off, nil
+-}
+-
+-// Helpers for dealing with escaped bytes
+-func isDigit(b byte) bool { return b >= '0' && b <= '9' }
+-
+-func dddToByte(s []byte) byte {
+-	return byte((s[0]-'0')*100 + (s[1]-'0')*10 + (s[2] - '0'))
+-}
+-
+-// UnpackStruct unpacks a binary message from offset off to the interface
+-// value given.
+-func UnpackStruct(any interface{}, msg []byte, off int) (int, error) {
+-	return unpackStructValue(structValue(any), msg, off)
+-}
+-
+-// Helper function for packing and unpacking
+-func intToBytes(i *big.Int, length int) []byte {
+-	buf := i.Bytes()
+-	if len(buf) < length {
+-		b := make([]byte, length)
+-		copy(b[length-len(buf):], buf)
+-		return b
+-	}
+-	return buf
+-}
+-
+-func unpackUint16(msg []byte, off int) (uint16, int) {
+-	return uint16(msg[off])<<8 | uint16(msg[off+1]), off + 2
+-}
+-
+-func packUint16(i uint16) (byte, byte) {
+-	return byte(i >> 8), byte(i)
+-}
+-
+-func toBase32(b []byte) string {
+-	return base32.HexEncoding.EncodeToString(b)
+-}
+-
+-func fromBase32(s []byte) (buf []byte, err error) {
+-	buflen := base32.HexEncoding.DecodedLen(len(s))
+-	buf = make([]byte, buflen)
+-	n, err := base32.HexEncoding.Decode(buf, s)
+-	buf = buf[:n]
+-	return
+-}
+-
+-func toBase64(b []byte) string {
+-	return base64.StdEncoding.EncodeToString(b)
+-}
+-
+-func fromBase64(s []byte) (buf []byte, err error) {
+-	buflen := base64.StdEncoding.DecodedLen(len(s))
+-	buf = make([]byte, buflen)
+-	n, err := base64.StdEncoding.Decode(buf, s)
+-	buf = buf[:n]
+-	return
+-}
+-
+-// PackRR packs a resource record rr into msg[off:].
+-// See PackDomainName for documentation about the compression.
+-func PackRR(rr RR, msg []byte, off int, compression map[string]int, compress bool) (off1 int, err error) {
+-	if rr == nil {
+-		return len(msg), &Error{err: "nil rr"}
+-	}
+-
+-	off1, err = packStructCompress(rr, msg, off, compression, compress)
+-	if err != nil {
+-		return len(msg), err
+-	}
+-	if rawSetRdlength(msg, off, off1) {
+-		return off1, nil
+-	}
+-	return off, ErrRdata
+-}
+-
+-// UnpackRR unpacks msg[off:] into an RR.
+-func UnpackRR(msg []byte, off int) (rr RR, off1 int, err error) {
+-	// unpack just the header, to find the rr type and length
+-	var h RR_Header
+-	off0 := off
+-	if off, err = UnpackStruct(&h, msg, off); err != nil {
+-		return nil, len(msg), err
+-	}
+-	end := off + int(h.Rdlength)
+-	// make an rr of that type and re-unpack.
+-	mk, known := typeToRR[h.Rrtype]
+-	if !known {
+-		rr = new(RFC3597)
+-	} else {
+-		rr = mk()
+-	}
+-	off, err = UnpackStruct(rr, msg, off0)
+-	if off != end {
+-		return &h, end, &Error{err: "bad rdlength"}
+-	}
+-	return rr, off, err
+-}
+-
+-// Reverse a map
+-func reverseInt8(m map[uint8]string) map[string]uint8 {
+-	n := make(map[string]uint8)
+-	for u, s := range m {
+-		n[s] = u
+-	}
+-	return n
+-}
+-
+-func reverseInt16(m map[uint16]string) map[string]uint16 {
+-	n := make(map[string]uint16)
+-	for u, s := range m {
+-		n[s] = u
+-	}
+-	return n
+-}
+-
+-func reverseInt(m map[int]string) map[string]int {
+-	n := make(map[string]int)
+-	for u, s := range m {
+-		n[s] = u
+-	}
+-	return n
+-}
+-
+-// Convert a MsgHdr to a string, with dig-like headers:
+-//
+-//;; opcode: QUERY, status: NOERROR, id: 48404
+-//
+-//;; flags: qr aa rd ra;
+-func (h *MsgHdr) String() string {
+-	if h == nil {
+-		return "<nil> MsgHdr"
+-	}
+-
+-	s := ";; opcode: " + OpcodeToString[h.Opcode]
+-	s += ", status: " + RcodeToString[h.Rcode]
+-	s += ", id: " + strconv.Itoa(int(h.Id)) + "\n"
+-
+-	s += ";; flags:"
+-	if h.Response {
+-		s += " qr"
+-	}
+-	if h.Authoritative {
+-		s += " aa"
+-	}
+-	if h.Truncated {
+-		s += " tc"
+-	}
+-	if h.RecursionDesired {
+-		s += " rd"
+-	}
+-	if h.RecursionAvailable {
+-		s += " ra"
+-	}
+-	if h.Zero { // Hmm
+-		s += " z"
+-	}
+-	if h.AuthenticatedData {
+-		s += " ad"
+-	}
+-	if h.CheckingDisabled {
+-		s += " cd"
+-	}
+-
+-	s += ";"
+-	return s
+-}
+-
+-// Pack packs a Msg: it is converted to to wire format.
+-// If the dns.Compress is true the message will be in compressed wire format.
+-func (dns *Msg) Pack() (msg []byte, err error) {
+-	return dns.PackBuffer(nil)
+-}
+-
+-// PackBuffer packs a Msg, using the given buffer buf. If buf is too small
+-// a new buffer is allocated.
+-func (dns *Msg) PackBuffer(buf []byte) (msg []byte, err error) {
+-	var dh Header
+-	var compression map[string]int
+-	if dns.Compress {
+-		compression = make(map[string]int) // Compression pointer mappings
+-	}
+-
+-	if dns.Rcode < 0 || dns.Rcode > 0xFFF {
+-		return nil, ErrRcode
+-	}
+-	if dns.Rcode > 0xF {
+-		// Regular RCODE field is 4 bits
+-		opt := dns.IsEdns0()
+-		if opt == nil {
+-			return nil, ErrExtendedRcode
+-		}
+-		opt.SetExtendedRcode(uint8(dns.Rcode >> 4))
+-		dns.Rcode &= 0xF
+-	}
+-
+-	// Convert convenient Msg into wire-like Header.
+-	dh.Id = dns.Id
+-	dh.Bits = uint16(dns.Opcode)<<11 | uint16(dns.Rcode)
+-	if dns.Response {
+-		dh.Bits |= _QR
+-	}
+-	if dns.Authoritative {
+-		dh.Bits |= _AA
+-	}
+-	if dns.Truncated {
+-		dh.Bits |= _TC
+-	}
+-	if dns.RecursionDesired {
+-		dh.Bits |= _RD
+-	}
+-	if dns.RecursionAvailable {
+-		dh.Bits |= _RA
+-	}
+-	if dns.Zero {
+-		dh.Bits |= _Z
+-	}
+-	if dns.AuthenticatedData {
+-		dh.Bits |= _AD
+-	}
+-	if dns.CheckingDisabled {
+-		dh.Bits |= _CD
+-	}
+-
+-	// Prepare variable sized arrays.
+-	question := dns.Question
+-	answer := dns.Answer
+-	ns := dns.Ns
+-	extra := dns.Extra
+-
+-	dh.Qdcount = uint16(len(question))
+-	dh.Ancount = uint16(len(answer))
+-	dh.Nscount = uint16(len(ns))
+-	dh.Arcount = uint16(len(extra))
+-
+-	// We need the uncompressed length here, because we first pack it and then compress it.
+-	msg = buf
+-	compress := dns.Compress
+-	dns.Compress = false
+-	if packLen := dns.Len() + 1; len(msg) < packLen {
+-		msg = make([]byte, packLen)
+-	}
+-	dns.Compress = compress
+-
+-	// Pack it in: header and then the pieces.
+-	off := 0
+-	off, err = packStructCompress(&dh, msg, off, compression, dns.Compress)
+-	if err != nil {
+-		return nil, err
+-	}
+-	for i := 0; i < len(question); i++ {
+-		off, err = packStructCompress(&question[i], msg, off, compression, dns.Compress)
+-		if err != nil {
+-			return nil, err
+-		}
+-	}
+-	for i := 0; i < len(answer); i++ {
+-		off, err = PackRR(answer[i], msg, off, compression, dns.Compress)
+-		if err != nil {
+-			return nil, err
+-		}
+-	}
+-	for i := 0; i < len(ns); i++ {
+-		off, err = PackRR(ns[i], msg, off, compression, dns.Compress)
+-		if err != nil {
+-			return nil, err
+-		}
+-	}
+-	for i := 0; i < len(extra); i++ {
+-		off, err = PackRR(extra[i], msg, off, compression, dns.Compress)
+-		if err != nil {
+-			return nil, err
+-		}
+-	}
+-	return msg[:off], nil
+-}
+-
+-// Unpack unpacks a binary message to a Msg structure.
+-func (dns *Msg) Unpack(msg []byte) (err error) {
+-	// Header.
+-	var dh Header
+-	off := 0
+-	if off, err = UnpackStruct(&dh, msg, off); err != nil {
+-		return err
+-	}
+-	dns.Id = dh.Id
+-	dns.Response = (dh.Bits & _QR) != 0
+-	dns.Opcode = int(dh.Bits>>11) & 0xF
+-	dns.Authoritative = (dh.Bits & _AA) != 0
+-	dns.Truncated = (dh.Bits & _TC) != 0
+-	dns.RecursionDesired = (dh.Bits & _RD) != 0
+-	dns.RecursionAvailable = (dh.Bits & _RA) != 0
+-	dns.Zero = (dh.Bits & _Z) != 0
+-	dns.AuthenticatedData = (dh.Bits & _AD) != 0
+-	dns.CheckingDisabled = (dh.Bits & _CD) != 0
+-	dns.Rcode = int(dh.Bits & 0xF)
+-
+-	// Arrays.
+-	dns.Question = make([]Question, dh.Qdcount)
+-	dns.Answer = make([]RR, dh.Ancount)
+-	dns.Ns = make([]RR, dh.Nscount)
+-	dns.Extra = make([]RR, dh.Arcount)
+-
+-	for i := 0; i < len(dns.Question); i++ {
+-		off, err = UnpackStruct(&dns.Question[i], msg, off)
+-		if err != nil {
+-			return err
+-		}
+-	}
+-	// If we see a TC bit being set we return here, without
+-	// an error, because technically it isn't an error. So return
+-	// without parsing the potentially corrupt packet and hitting an error.
+-	// TODO(miek): this isn't the best strategy!
+-	if dns.Truncated {
+-		dns.Answer = nil
+-		dns.Ns = nil
+-		dns.Extra = nil
+-		return nil
+-	}
+-	for i := 0; i < len(dns.Answer); i++ {
+-		dns.Answer[i], off, err = UnpackRR(msg, off)
+-		if err != nil {
+-			return err
+-		}
+-	}
+-	for i := 0; i < len(dns.Ns); i++ {
+-		dns.Ns[i], off, err = UnpackRR(msg, off)
+-		if err != nil {
+-			return err
+-		}
+-	}
+-	for i := 0; i < len(dns.Extra); i++ {
+-		dns.Extra[i], off, err = UnpackRR(msg, off)
+-		if err != nil {
+-			return err
+-		}
+-	}
+-	if off != len(msg) {
+-		// TODO(miek) make this an error?
+-		// use PackOpt to let people tell how detailed the error reporting should be?
+-		// println("dns: extra bytes in dns packet", off, "<", len(msg))
+-	}
+-	return nil
+-}
+-
+-// Convert a complete message to a string with dig-like output.
+-func (dns *Msg) String() string {
+-	if dns == nil {
+-		return "<nil> MsgHdr"
+-	}
+-	s := dns.MsgHdr.String() + " "
+-	s += "QUERY: " + strconv.Itoa(len(dns.Question)) + ", "
+-	s += "ANSWER: " + strconv.Itoa(len(dns.Answer)) + ", "
+-	s += "AUTHORITY: " + strconv.Itoa(len(dns.Ns)) + ", "
+-	s += "ADDITIONAL: " + strconv.Itoa(len(dns.Extra)) + "\n"
+-	if len(dns.Question) > 0 {
+-		s += "\n;; QUESTION SECTION:\n"
+-		for i := 0; i < len(dns.Question); i++ {
+-			s += dns.Question[i].String() + "\n"
+-		}
+-	}
+-	if len(dns.Answer) > 0 {
+-		s += "\n;; ANSWER SECTION:\n"
+-		for i := 0; i < len(dns.Answer); i++ {
+-			if dns.Answer[i] != nil {
+-				s += dns.Answer[i].String() + "\n"
+-			}
+-		}
+-	}
+-	if len(dns.Ns) > 0 {
+-		s += "\n;; AUTHORITY SECTION:\n"
+-		for i := 0; i < len(dns.Ns); i++ {
+-			if dns.Ns[i] != nil {
+-				s += dns.Ns[i].String() + "\n"
+-			}
+-		}
+-	}
+-	if len(dns.Extra) > 0 {
+-		s += "\n;; ADDITIONAL SECTION:\n"
+-		for i := 0; i < len(dns.Extra); i++ {
+-			if dns.Extra[i] != nil {
+-				s += dns.Extra[i].String() + "\n"
+-			}
+-		}
+-	}
+-	return s
+-}
+-
+-// Len returns the message length when in (un)compressed wire format.
+-// If dns.Compress is true compression it is taken into account. Len()
+-// is provided to be a faster way to get the size of the resulting packet,
+-// than packing it, measuring the size and discarding the buffer.
+-func (dns *Msg) Len() int {
+-	// We always return one more than needed.
+-	l := 12 // Message header is always 12 bytes
+-	var compression map[string]int
+-	if dns.Compress {
+-		compression = make(map[string]int)
+-	}
+-	for i := 0; i < len(dns.Question); i++ {
+-		l += dns.Question[i].len()
+-		if dns.Compress {
+-			compressionLenHelper(compression, dns.Question[i].Name)
+-		}
+-	}
+-	for i := 0; i < len(dns.Answer); i++ {
+-		l += dns.Answer[i].len()
+-		if dns.Compress {
+-			k, ok := compressionLenSearch(compression, dns.Answer[i].Header().Name)
+-			if ok {
+-				l += 1 - k
+-			}
+-			compressionLenHelper(compression, dns.Answer[i].Header().Name)
+-			k, ok = compressionLenSearchType(compression, dns.Answer[i])
+-			if ok {
+-				l += 1 - k
+-			}
+-			compressionLenHelperType(compression, dns.Answer[i])
+-		}
+-	}
+-	for i := 0; i < len(dns.Ns); i++ {
+-		l += dns.Ns[i].len()
+-		if dns.Compress {
+-			k, ok := compressionLenSearch(compression, dns.Ns[i].Header().Name)
+-			if ok {
+-				l += 1 - k
+-			}
+-			compressionLenHelper(compression, dns.Ns[i].Header().Name)
+-			k, ok = compressionLenSearchType(compression, dns.Ns[i])
+-			if ok {
+-				l += 1 - k
+-			}
+-			compressionLenHelperType(compression, dns.Ns[i])
+-		}
+-	}
+-	for i := 0; i < len(dns.Extra); i++ {
+-		l += dns.Extra[i].len()
+-		if dns.Compress {
+-			k, ok := compressionLenSearch(compression, dns.Extra[i].Header().Name)
+-			if ok {
+-				l += 1 - k
+-			}
+-			compressionLenHelper(compression, dns.Extra[i].Header().Name)
+-			k, ok = compressionLenSearchType(compression, dns.Extra[i])
+-			if ok {
+-				l += 1 - k
+-			}
+-			compressionLenHelperType(compression, dns.Extra[i])
+-		}
+-	}
+-	return l
+-}
+-
+-// Put the parts of the name in the compression map.
+-func compressionLenHelper(c map[string]int, s string) {
+-	pref := ""
+-	lbs := Split(s)
+-	for j := len(lbs) - 1; j >= 0; j-- {
+-		pref = s[lbs[j]:]
+-		if _, ok := c[pref]; !ok {
+-			c[pref] = len(pref)
+-		}
+-	}
+-}
+-
+-// Look for each part in the compression map and returns its length,
+-// keep on searching so we get the longest match.
+-func compressionLenSearch(c map[string]int, s string) (int, bool) {
+-	off := 0
+-	end := false
+-	if s == "" { // don't bork on bogus data
+-		return 0, false
+-	}
+-	for {
+-		if _, ok := c[s[off:]]; ok {
+-			return len(s[off:]), true
+-		}
+-		if end {
+-			break
+-		}
+-		off, end = NextLabel(s, off)
+-	}
+-	return 0, false
+-}
+-
+-// TODO(miek): should add all types, because the all can be *used* for compression.
+-func compressionLenHelperType(c map[string]int, r RR) {
+-	switch x := r.(type) {
+-	case *NS:
+-		compressionLenHelper(c, x.Ns)
+-	case *MX:
+-		compressionLenHelper(c, x.Mx)
+-	case *CNAME:
+-		compressionLenHelper(c, x.Target)
+-	case *PTR:
+-		compressionLenHelper(c, x.Ptr)
+-	case *SOA:
+-		compressionLenHelper(c, x.Ns)
+-		compressionLenHelper(c, x.Mbox)
+-	case *MB:
+-		compressionLenHelper(c, x.Mb)
+-	case *MG:
+-		compressionLenHelper(c, x.Mg)
+-	case *MR:
+-		compressionLenHelper(c, x.Mr)
+-	case *MF:
+-		compressionLenHelper(c, x.Mf)
+-	case *MD:
+-		compressionLenHelper(c, x.Md)
+-	case *RT:
+-		compressionLenHelper(c, x.Host)
+-	case *MINFO:
+-		compressionLenHelper(c, x.Rmail)
+-		compressionLenHelper(c, x.Email)
+-	case *AFSDB:
+-		compressionLenHelper(c, x.Hostname)
+-	}
+-}
+-
+-// Only search on compressing these types.
+-func compressionLenSearchType(c map[string]int, r RR) (int, bool) {
+-	switch x := r.(type) {
+-	case *NS:
+-		return compressionLenSearch(c, x.Ns)
+-	case *MX:
+-		return compressionLenSearch(c, x.Mx)
+-	case *CNAME:
+-		return compressionLenSearch(c, x.Target)
+-	case *PTR:
+-		return compressionLenSearch(c, x.Ptr)
+-	case *SOA:
+-		k, ok := compressionLenSearch(c, x.Ns)
+-		k1, ok1 := compressionLenSearch(c, x.Mbox)
+-		if !ok && !ok1 {
+-			return 0, false
+-		}
+-		return k + k1, true
+-	case *MB:
+-		return compressionLenSearch(c, x.Mb)
+-	case *MG:
+-		return compressionLenSearch(c, x.Mg)
+-	case *MR:
+-		return compressionLenSearch(c, x.Mr)
+-	case *MF:
+-		return compressionLenSearch(c, x.Mf)
+-	case *MD:
+-		return compressionLenSearch(c, x.Md)
+-	case *RT:
+-		return compressionLenSearch(c, x.Host)
+-	case *MINFO:
+-		k, ok := compressionLenSearch(c, x.Rmail)
+-		k1, ok1 := compressionLenSearch(c, x.Email)
+-		if !ok && !ok1 {
+-			return 0, false
+-		}
+-		return k + k1, true
+-	case *AFSDB:
+-		return compressionLenSearch(c, x.Hostname)
+-	}
+-	return 0, false
+-}
+-
+-// id returns a 16 bits random number to be used as a
+-// message id. The random provided should be good enough.
+-func id() uint16 {
+-	return uint16(rand.Int()) ^ uint16(time.Now().Nanosecond())
+-}
+-
+-// Copy returns a new RR which is a deep-copy of r.
+-func Copy(r RR) RR {
+-	r1 := r.copy()
+-	return r1
+-}
+-
+-// Copy returns a new *Msg which is a deep-copy of dns.
+-func (dns *Msg) Copy() *Msg {
+-	r1 := new(Msg)
+-	r1.MsgHdr = dns.MsgHdr
+-	r1.Compress = dns.Compress
+-
+-	if len(dns.Question) > 0 {
+-		r1.Question = make([]Question, len(dns.Question))
+-		copy(r1.Question, dns.Question) // TODO(miek): Question is an immutable value, ok to do a shallow-copy
+-	}
+-
+-	if len(dns.Answer) > 0 {
+-		r1.Answer = make([]RR, len(dns.Answer))
+-		for i := 0; i < len(dns.Answer); i++ {
+-			r1.Answer[i] = dns.Answer[i].copy()
+-		}
+-	}
+-
+-	if len(dns.Ns) > 0 {
+-		r1.Ns = make([]RR, len(dns.Ns))
+-		for i := 0; i < len(dns.Ns); i++ {
+-			r1.Ns[i] = dns.Ns[i].copy()
+-		}
+-	}
+-
+-	if len(dns.Extra) > 0 {
+-		r1.Extra = make([]RR, len(dns.Extra))
+-		for i := 0; i < len(dns.Extra); i++ {
+-			r1.Extra[i] = dns.Extra[i].copy()
+-		}
+-	}
+-
+-	return r1
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/nsecx.go b/Godeps/_workspace/src/github.com/miekg/dns/nsecx.go
+deleted file mode 100644
+index ac48da0..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/nsecx.go
++++ /dev/null
+@@ -1,110 +0,0 @@
+-package dns
+-
+-import (
+-	"crypto/sha1"
+-	"hash"
+-	"io"
+-	"strings"
+-)
+-
+-type saltWireFmt struct {
+-	Salt string `dns:"size-hex"`
+-}
+-
+-// HashName hashes a string (label) according to RFC 5155. It returns the hashed string in
+-// uppercase.
+-func HashName(label string, ha uint8, iter uint16, salt string) string {
+-	saltwire := new(saltWireFmt)
+-	saltwire.Salt = salt
+-	wire := make([]byte, DefaultMsgSize)
+-	n, err := PackStruct(saltwire, wire, 0)
+-	if err != nil {
+-		return ""
+-	}
+-	wire = wire[:n]
+-	name := make([]byte, 255)
+-	off, err := PackDomainName(strings.ToLower(label), name, 0, nil, false)
+-	if err != nil {
+-		return ""
+-	}
+-	name = name[:off]
+-	var s hash.Hash
+-	switch ha {
+-	case SHA1:
+-		s = sha1.New()
+-	default:
+-		return ""
+-	}
+-
+-	// k = 0
+-	name = append(name, wire...)
+-	io.WriteString(s, string(name))
+-	nsec3 := s.Sum(nil)
+-	// k > 0
+-	for k := uint16(0); k < iter; k++ {
+-		s.Reset()
+-		nsec3 = append(nsec3, wire...)
+-		io.WriteString(s, string(nsec3))
+-		nsec3 = s.Sum(nil)
+-	}
+-	return toBase32(nsec3)
+-}
+-
+-type Denialer interface {
+-	// Cover will check if the (unhashed) name is being covered by this NSEC or NSEC3.
+-	Cover(name string) bool
+-	// Match will check if the ownername matches the (unhashed) name for this NSEC3 or NSEC3.
+-	Match(name string) bool
+-}
+-
+-// Cover implements the Denialer interface.
+-func (rr *NSEC) Cover(name string) bool {
+-	return true
+-}
+-
+-// Match implements the Denialer interface.
+-func (rr *NSEC) Match(name string) bool {
+-	return true
+-}
+-
+-// Cover implements the Denialer interface.
+-func (rr *NSEC3) Cover(name string) bool {
+-	// FIXME(miek): check if the zones match
+-	// FIXME(miek): check if we're not dealing with parent nsec3
+-	hname := HashName(name, rr.Hash, rr.Iterations, rr.Salt)
+-	labels := Split(rr.Hdr.Name)
+-	if len(labels) < 2 {
+-		return false
+-	}
+-	hash := strings.ToUpper(rr.Hdr.Name[labels[0] : labels[1]-1]) // -1 to remove the dot
+-	if hash == rr.NextDomain {
+-		return false // empty interval
+-	}
+-	if hash > rr.NextDomain { // last name, points to apex
+-		// hname > hash
+-		// hname > rr.NextDomain
+-		// TODO(miek)
+-	}
+-	if hname <= hash {
+-		return false
+-	}
+-	if hname >= rr.NextDomain {
+-		return false
+-	}
+-	return true
+-}
+-
+-// Match implements the Denialer interface.
+-func (rr *NSEC3) Match(name string) bool {
+-	// FIXME(miek): Check if we are in the same zone
+-	hname := HashName(name, rr.Hash, rr.Iterations, rr.Salt)
+-	labels := Split(rr.Hdr.Name)
+-	if len(labels) < 2 {
+-		return false
+-	}
+-	hash := strings.ToUpper(rr.Hdr.Name[labels[0] : labels[1]-1]) // -1 to remove the .
+-	if hash == hname {
+-		return true
+-	}
+-	return false
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/nsecx_test.go b/Godeps/_workspace/src/github.com/miekg/dns/nsecx_test.go
+deleted file mode 100644
+index 72f641a..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/nsecx_test.go
++++ /dev/null
+@@ -1,33 +0,0 @@
+-package dns
+-
+-import (
+-	"testing"
+-)
+-
+-func TestPackNsec3(t *testing.T) {
+-	nsec3 := HashName("dnsex.nl.", SHA1, 0, "DEAD")
+-	if nsec3 != "ROCCJAE8BJJU7HN6T7NG3TNM8ACRS87J" {
+-		t.Logf("%v\n", nsec3)
+-		t.Fail()
+-	}
+-
+-	nsec3 = HashName("a.b.c.example.org.", SHA1, 2, "DEAD")
+-	if nsec3 != "6LQ07OAHBTOOEU2R9ANI2AT70K5O0RCG" {
+-		t.Logf("%v\n", nsec3)
+-		t.Fail()
+-	}
+-}
+-
+-func TestNsec3(t *testing.T) {
+-	// examples taken from .nl
+-	nsec3, _ := NewRR("39p91242oslggest5e6a7cci4iaeqvnk.nl. IN NSEC3 1 1 5 F10E9F7EA83FC8F3 39P99DCGG0MDLARTCRMCF6OFLLUL7PR6 NS DS RRSIG")
+-	if !nsec3.(*NSEC3).Cover("snasajsksasasa.nl.") { // 39p94jrinub66hnpem8qdpstrec86pg3
+-		t.Logf("39p94jrinub66hnpem8qdpstrec86pg3. should be covered by 39p91242oslggest5e6a7cci4iaeqvnk.nl. - 39P99DCGG0MDLARTCRMCF6OFLLUL7PR6")
+-		t.Fail()
+-	}
+-	nsec3, _ = NewRR("sk4e8fj94u78smusb40o1n0oltbblu2r.nl. IN NSEC3 1 1 5 F10E9F7EA83FC8F3 SK4F38CQ0ATIEI8MH3RGD0P5I4II6QAN NS SOA TXT RRSIG DNSKEY NSEC3PARAM")
+-	if !nsec3.(*NSEC3).Match("nl.") { // sk4e8fj94u78smusb40o1n0oltbblu2r.nl.
+-		t.Logf("sk4e8fj94u78smusb40o1n0oltbblu2r.nl. should match sk4e8fj94u78smusb40o1n0oltbblu2r.nl.")
+-		t.Fail()
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/parse_test.go b/Godeps/_workspace/src/github.com/miekg/dns/parse_test.go
+deleted file mode 100644
+index dd2799d..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/parse_test.go
++++ /dev/null
+@@ -1,1276 +0,0 @@
+-package dns
+-
+-import (
+-	"bytes"
+-	"crypto/rsa"
+-	"encoding/hex"
+-	"fmt"
+-	"math/rand"
+-	"net"
+-	"reflect"
+-	"strconv"
+-	"strings"
+-	"testing"
+-	"testing/quick"
+-	"time"
+-)
+-
+-func TestDotInName(t *testing.T) {
+-	buf := make([]byte, 20)
+-	PackDomainName("aa\\.bb.nl.", buf, 0, nil, false)
+-	// index 3 must be a real dot
+-	if buf[3] != '.' {
+-		t.Log("dot should be a real dot")
+-		t.Fail()
+-	}
+-
+-	if buf[6] != 2 {
+-		t.Log("this must have the value 2")
+-		t.Fail()
+-	}
+-	dom, _, _ := UnpackDomainName(buf, 0)
+-	// printing it should yield the backspace again
+-	if dom != "aa\\.bb.nl." {
+-		t.Log("dot should have been escaped: " + dom)
+-		t.Fail()
+-	}
+-}
+-
+-func TestDotLastInLabel(t *testing.T) {
+-	sample := "aa\\..au."
+-	buf := make([]byte, 20)
+-	_, err := PackDomainName(sample, buf, 0, nil, false)
+-	if err != nil {
+-		t.Fatalf("unexpected error packing domain: %s", err)
+-	}
+-	dom, _, _ := UnpackDomainName(buf, 0)
+-	if dom != sample {
+-		t.Fatalf("unpacked domain `%s' doesn't match packed domain", dom)
+-	}
+-}
+-
+-func TestTooLongDomainName(t *testing.T) {
+-	l := "aaabbbcccdddeeefffggghhhiiijjjkkklllmmmnnnooopppqqqrrrsssttt."
+-	dom := l + l + l + l + l + l + l
+-	_, e := NewRR(dom + " IN A 127.0.0.1")
+-	if e == nil {
+-		t.Log("should be too long")
+-		t.Fail()
+-	} else {
+-		t.Logf("error is %s", e.Error())
+-	}
+-	_, e = NewRR("..com. IN A 127.0.0.1")
+-	if e == nil {
+-		t.Log("should fail")
+-		t.Fail()
+-	} else {
+-		t.Logf("error is %s", e.Error())
+-	}
+-}
+-
+-func TestDomainName(t *testing.T) {
+-	tests := []string{"r\\.gieben.miek.nl.", "www\\.www.miek.nl.",
+-		"www.*.miek.nl.", "www.*.miek.nl.",
+-	}
+-	dbuff := make([]byte, 40)
+-
+-	for _, ts := range tests {
+-		if _, err := PackDomainName(ts, dbuff, 0, nil, false); err != nil {
+-			t.Log("not a valid domain name")
+-			t.Fail()
+-			continue
+-		}
+-		n, _, err := UnpackDomainName(dbuff, 0)
+-		if err != nil {
+-			t.Log("failed to unpack packed domain name")
+-			t.Fail()
+-			continue
+-		}
+-		if ts != n {
+-			t.Logf("must be equal: in: %s, out: %s\n", ts, n)
+-			t.Fail()
+-		}
+-	}
+-}
+-
+-func TestDomainNameAndTXTEscapes(t *testing.T) {
+-	tests := []byte{'.', '(', ')', ';', ' ', '@', '"', '\\', '\t', '\r', '\n', 0, 255}
+-	for _, b := range tests {
+-		rrbytes := []byte{
+-			1, b, 0, // owner
+-			byte(TypeTXT >> 8), byte(TypeTXT),
+-			byte(ClassINET >> 8), byte(ClassINET),
+-			0, 0, 0, 1, // TTL
+-			0, 2, 1, b, // Data
+-		}
+-		rr1, _, err := UnpackRR(rrbytes, 0)
+-		if err != nil {
+-			panic(err)
+-		}
+-		s := rr1.String()
+-		rr2, err := NewRR(s)
+-		if err != nil {
+-			t.Logf("Error parsing unpacked RR's string: %v", err)
+-			t.Logf(" Bytes: %v\n", rrbytes)
+-			t.Logf("String: %v\n", s)
+-			t.Fail()
+-		}
+-		repacked := make([]byte, len(rrbytes))
+-		if _, err := PackRR(rr2, repacked, 0, nil, false); err != nil {
+-			t.Logf("error packing parsed RR: %v", err)
+-			t.Logf(" original Bytes: %v\n", rrbytes)
+-			t.Logf("unpacked Struct: %V\n", rr1)
+-			t.Logf("  parsed Struct: %V\n", rr2)
+-			t.Fail()
+-		}
+-		if !bytes.Equal(repacked, rrbytes) {
+-			t.Log("packed bytes don't match original bytes")
+-			t.Logf(" original bytes: %v", rrbytes)
+-			t.Logf("   packed bytes: %v", repacked)
+-			t.Logf("unpacked struct: %V", rr1)
+-			t.Logf("  parsed struct: %V", rr2)
+-			t.Fail()
+-		}
+-	}
+-}
+-
+-func TestTXTEscapeParsing(t *testing.T) {
+-	test := [][]string{
+-		{`";"`, `";"`},
+-		{`\;`, `";"`},
+-		{`"\t"`, `"\t"`},
+-		{`"\r"`, `"\r"`},
+-		{`"\ "`, `" "`},
+-		{`"\;"`, `";"`},
+-		{`"\;\""`, `";\""`},
+-		{`"\(a\)"`, `"(a)"`},
+-		{`"\(a)"`, `"(a)"`},
+-		{`"(a\)"`, `"(a)"`},
+-		{`"(a)"`, `"(a)"`},
+-		{`"\048"`, `"0"`},
+-		{`"\` + "\n" + `"`, `"\n"`},
+-		{`"\` + "\r" + `"`, `"\r"`},
+-		{`"\` + "\x11" + `"`, `"\017"`},
+-		{`"\'"`, `"'"`},
+-	}
+-	for _, s := range test {
+-		rr, err := NewRR(fmt.Sprintf("example.com. IN TXT %v", s[0]))
+-		if err != nil {
+-			t.Errorf("Could not parse %v TXT: %s", s[0], err)
+-			continue
+-		}
+-
+-		txt := sprintTxt(rr.(*TXT).Txt)
+-		if txt != s[1] {
+-			t.Errorf("Mismatch after parsing `%v` TXT record: `%v` != `%v`", s[0], txt, s[1])
+-		}
+-	}
+-}
+-
+-func GenerateDomain(r *rand.Rand, size int) []byte {
+-	dnLen := size % 70 // artificially limit size so there's less to intrepret if a failure occurs
+-	var dn []byte
+-	done := false
+-	for i := 0; i < dnLen && !done; {
+-		max := dnLen - i
+-		if max > 63 {
+-			max = 63
+-		}
+-		lLen := max
+-		if lLen != 0 {
+-			lLen = int(r.Int31()) % max
+-		}
+-		done = lLen == 0
+-		if done {
+-			continue
+-		}
+-		l := make([]byte, lLen+1)
+-		l[0] = byte(lLen)
+-		for j := 0; j < lLen; j++ {
+-			l[j+1] = byte(rand.Int31())
+-		}
+-		dn = append(dn, l...)
+-		i += 1 + lLen
+-	}
+-	return append(dn, 0)
+-}
+-
+-func TestDomainQuick(t *testing.T) {
+-	r := rand.New(rand.NewSource(0))
+-	f := func(l int) bool {
+-		db := GenerateDomain(r, l)
+-		ds, _, err := UnpackDomainName(db, 0)
+-		if err != nil {
+-			panic(err)
+-		}
+-		buf := make([]byte, 255)
+-		off, err := PackDomainName(ds, buf, 0, nil, false)
+-		if err != nil {
+-			t.Logf("error packing domain: %s", err.Error())
+-			t.Logf(" bytes: %v\n", db)
+-			t.Logf("string: %v\n", ds)
+-			return false
+-		}
+-		if !bytes.Equal(db, buf[:off]) {
+-			t.Logf("repacked domain doesn't match original:")
+-			t.Logf("src bytes: %v", db)
+-			t.Logf("   string: %v", ds)
+-			t.Logf("out bytes: %v", buf[:off])
+-			return false
+-		}
+-		return true
+-	}
+-	if err := quick.Check(f, nil); err != nil {
+-		t.Error(err)
+-	}
+-}
+-
+-func GenerateTXT(r *rand.Rand, size int) []byte {
+-	rdLen := size % 300 // artificially limit size so there's less to intrepret if a failure occurs
+-	var rd []byte
+-	for i := 0; i < rdLen; {
+-		max := rdLen - 1
+-		if max > 255 {
+-			max = 255
+-		}
+-		sLen := max
+-		if max != 0 {
+-			sLen = int(r.Int31()) % max
+-		}
+-		s := make([]byte, sLen+1)
+-		s[0] = byte(sLen)
+-		for j := 0; j < sLen; j++ {
+-			s[j+1] = byte(rand.Int31())
+-		}
+-		rd = append(rd, s...)
+-		i += 1 + sLen
+-	}
+-	return rd
+-}
+-
+-func TestTXTRRQuick(t *testing.T) {
+-	s := rand.NewSource(0)
+-	r := rand.New(s)
+-	typeAndClass := []byte{
+-		byte(TypeTXT >> 8), byte(TypeTXT),
+-		byte(ClassINET >> 8), byte(ClassINET),
+-		0, 0, 0, 1, // TTL
+-	}
+-	f := func(l int) bool {
+-		owner := GenerateDomain(r, l)
+-		rdata := GenerateTXT(r, l)
+-		rrbytes := make([]byte, 0, len(owner)+2+2+4+2+len(rdata))
+-		rrbytes = append(rrbytes, owner...)
+-		rrbytes = append(rrbytes, typeAndClass...)
+-		rrbytes = append(rrbytes, byte(len(rdata)>>8))
+-		rrbytes = append(rrbytes, byte(len(rdata)))
+-		rrbytes = append(rrbytes, rdata...)
+-		rr, _, err := UnpackRR(rrbytes, 0)
+-		if err != nil {
+-			panic(err)
+-		}
+-		buf := make([]byte, len(rrbytes)*3)
+-		off, err := PackRR(rr, buf, 0, nil, false)
+-		if err != nil {
+-			t.Logf("pack Error: %s\nRR: %V", err.Error(), rr)
+-			return false
+-		}
+-		buf = buf[:off]
+-		if !bytes.Equal(buf, rrbytes) {
+-			t.Logf("packed bytes don't match original bytes")
+-			t.Logf("src bytes: %v", rrbytes)
+-			t.Logf("   struct: %V", rr)
+-			t.Logf("oUt bytes: %v", buf)
+-			return false
+-		}
+-		if len(rdata) == 0 {
+-			// string'ing won't produce any data to parse
+-			return true
+-		}
+-		rrString := rr.String()
+-		rr2, err := NewRR(rrString)
+-		if err != nil {
+-			t.Logf("error parsing own output: %s", err.Error())
+-			t.Logf("struct: %V", rr)
+-			t.Logf("string: %v", rrString)
+-			return false
+-		}
+-		if rr2.String() != rrString {
+-			t.Logf("parsed rr.String() doesn't match original string")
+-			t.Logf("original: %v", rrString)
+-			t.Logf("  parsed: %v", rr2.String())
+-			return false
+-		}
+-
+-		buf = make([]byte, len(rrbytes)*3)
+-		off, err = PackRR(rr2, buf, 0, nil, false)
+-		if err != nil {
+-			t.Logf("error packing parsed rr: %s", err.Error())
+-			t.Logf("unpacked Struct: %V", rr)
+-			t.Logf("         string: %v", rrString)
+-			t.Logf("  parsed Struct: %V", rr2)
+-			return false
+-		}
+-		buf = buf[:off]
+-		if !bytes.Equal(buf, rrbytes) {
+-			t.Logf("parsed packed bytes don't match original bytes")
+-			t.Logf("   source bytes: %v", rrbytes)
+-			t.Logf("unpacked struct: %V", rr)
+-			t.Logf("         string: %v", rrString)
+-			t.Logf("  parsed struct: %V", rr2)
+-			t.Logf(" repacked bytes: %v", buf)
+-			return false
+-		}
+-		return true
+-	}
+-	c := &quick.Config{MaxCountScale: 10}
+-	if err := quick.Check(f, c); err != nil {
+-		t.Error(err)
+-	}
+-}
+-
+-func TestParseDirectiveMisc(t *testing.T) {
+-	tests := map[string]string{
+-		"$ORIGIN miek.nl.\na IN NS b": "a.miek.nl.\t3600\tIN\tNS\tb.miek.nl.",
+-		"$TTL 2H\nmiek.nl. IN NS b.":  "miek.nl.\t7200\tIN\tNS\tb.",
+-		"miek.nl. 1D IN NS b.":        "miek.nl.\t86400\tIN\tNS\tb.",
+-		`name. IN SOA  a6.nstld.com. hostmaster.nic.name. (
+-        203362132 ; serial
+-        5m        ; refresh (5 minutes)
+-        5m        ; retry (5 minutes)
+-        2w        ; expire (2 weeks)
+-        300       ; minimum (5 minutes)
+-)`: "name.\t3600\tIN\tSOA\ta6.nstld.com. hostmaster.nic.name. 203362132 300 300 1209600 300",
+-		". 3600000  IN  NS ONE.MY-ROOTS.NET.":        ".\t3600000\tIN\tNS\tONE.MY-ROOTS.NET.",
+-		"ONE.MY-ROOTS.NET. 3600000 IN A 192.168.1.1": "ONE.MY-ROOTS.NET.\t3600000\tIN\tA\t192.168.1.1",
+-	}
+-	for i, o := range tests {
+-		rr, e := NewRR(i)
+-		if e != nil {
+-			t.Log("failed to parse RR: " + e.Error())
+-			t.Fail()
+-			continue
+-		}
+-		if rr.String() != o {
+-			t.Logf("`%s' should be equal to\n`%s', but is     `%s'\n", i, o, rr.String())
+-			t.Fail()
+-		} else {
+-			t.Logf("RR is OK: `%s'", rr.String())
+-		}
+-	}
+-}
+-
+-func TestNSEC(t *testing.T) {
+-	nsectests := map[string]string{
+-		"nl. IN NSEC3PARAM 1 0 5 30923C44C6CBBB8F":                                                                                                 "nl.\t3600\tIN\tNSEC3PARAM\t1 0 5 30923C44C6CBBB8F",
+-		"p2209hipbpnm681knjnu0m1febshlv4e.nl. IN NSEC3 1 1 5 30923C44C6CBBB8F P90DG1KE8QEAN0B01613LHQDG0SOJ0TA NS SOA TXT RRSIG DNSKEY NSEC3PARAM": "p2209hipbpnm681knjnu0m1febshlv4e.nl.\t3600\tIN\tNSEC3\t1 1 5 30923C44C6CBBB8F P90DG1KE8QEAN0B01613LHQDG0SOJ0TA NS SOA TXT RRSIG DNSKEY NSEC3PARAM",
+-		"localhost.dnssex.nl. IN NSEC www.dnssex.nl. A RRSIG NSEC":                                                                                 "localhost.dnssex.nl.\t3600\tIN\tNSEC\twww.dnssex.nl. A RRSIG NSEC",
+-		"localhost.dnssex.nl. IN NSEC www.dnssex.nl. A RRSIG NSEC TYPE65534":                                                                       "localhost.dnssex.nl.\t3600\tIN\tNSEC\twww.dnssex.nl. A RRSIG NSEC TYPE65534",
+-		"localhost.dnssex.nl. IN NSEC www.dnssex.nl. A RRSIG NSec Type65534":                                                                       "localhost.dnssex.nl.\t3600\tIN\tNSEC\twww.dnssex.nl. A RRSIG NSEC TYPE65534",
+-	}
+-	for i, o := range nsectests {
+-		rr, e := NewRR(i)
+-		if e != nil {
+-			t.Log("failed to parse RR: " + e.Error())
+-			t.Fail()
+-			continue
+-		}
+-		if rr.String() != o {
+-			t.Logf("`%s' should be equal to\n`%s', but is     `%s'\n", i, o, rr.String())
+-			t.Fail()
+-		} else {
+-			t.Logf("RR is OK: `%s'", rr.String())
+-		}
+-	}
+-}
+-
+-func TestParseLOC(t *testing.T) {
+-	lt := map[string]string{
+-		"SW1A2AA.find.me.uk.	LOC	51 30 12.748 N 00 07 39.611 W 0.00m 0.00m 0.00m 0.00m": "SW1A2AA.find.me.uk.\t3600\tIN\tLOC\t51 30 12.748 N 00 07 39.611 W 0m 0.00m 0.00m 0.00m",
+-		"SW1A2AA.find.me.uk.	LOC	51 0 0.0 N 00 07 39.611 W 0.00m 0.00m 0.00m 0.00m": "SW1A2AA.find.me.uk.\t3600\tIN\tLOC\t51 00 0.000 N 00 07 39.611 W 0m 0.00m 0.00m 0.00m",
+-	}
+-	for i, o := range lt {
+-		rr, e := NewRR(i)
+-		if e != nil {
+-			t.Log("failed to parse RR: " + e.Error())
+-			t.Fail()
+-			continue
+-		}
+-		if rr.String() != o {
+-			t.Logf("`%s' should be equal to\n`%s', but is     `%s'\n", i, o, rr.String())
+-			t.Fail()
+-		} else {
+-			t.Logf("RR is OK: `%s'", rr.String())
+-		}
+-	}
+-}
+-
+-func TestParseDS(t *testing.T) {
+-	dt := map[string]string{
+-		"example.net. 3600 IN DS 40692 12 3 22261A8B0E0D799183E35E24E2AD6BB58533CBA7E3B14D659E9CA09B 2071398F": "example.net.\t3600\tIN\tDS\t40692 12 3 22261A8B0E0D799183E35E24E2AD6BB58533CBA7E3B14D659E9CA09B2071398F",
+-	}
+-	for i, o := range dt {
+-		rr, e := NewRR(i)
+-		if e != nil {
+-			t.Log("failed to parse RR: " + e.Error())
+-			t.Fail()
+-			continue
+-		}
+-		if rr.String() != o {
+-			t.Logf("`%s' should be equal to\n`%s', but is     `%s'\n", i, o, rr.String())
+-			t.Fail()
+-		} else {
+-			t.Logf("RR is OK: `%s'", rr.String())
+-		}
+-	}
+-}
+-
+-func TestQuotes(t *testing.T) {
+-	tests := map[string]string{
+-		`t.example.com. IN TXT "a bc"`: "t.example.com.\t3600\tIN\tTXT\t\"a bc\"",
+-		`t.example.com. IN TXT "a
+- bc"`: "t.example.com.\t3600\tIN\tTXT\t\"a\\n bc\"",
+-		`t.example.com. IN TXT ""`:                                                           "t.example.com.\t3600\tIN\tTXT\t\"\"",
+-		`t.example.com. IN TXT "a"`:                                                          "t.example.com.\t3600\tIN\tTXT\t\"a\"",
+-		`t.example.com. IN TXT "aa"`:                                                         "t.example.com.\t3600\tIN\tTXT\t\"aa\"",
+-		`t.example.com. IN TXT "aaa" ;`:                                                      "t.example.com.\t3600\tIN\tTXT\t\"aaa\"",
+-		`t.example.com. IN TXT "abc" "DEF"`:                                                  "t.example.com.\t3600\tIN\tTXT\t\"abc\" \"DEF\"",
+-		`t.example.com. IN TXT "abc" ( "DEF" )`:                                              "t.example.com.\t3600\tIN\tTXT\t\"abc\" \"DEF\"",
+-		`t.example.com. IN TXT aaa ;`:                                                        "t.example.com.\t3600\tIN\tTXT\t\"aaa \"",
+-		`t.example.com. IN TXT aaa aaa;`:                                                     "t.example.com.\t3600\tIN\tTXT\t\"aaa aaa\"",
+-		`t.example.com. IN TXT aaa aaa`:                                                      "t.example.com.\t3600\tIN\tTXT\t\"aaa aaa\"",
+-		`t.example.com. IN TXT aaa`:                                                          "t.example.com.\t3600\tIN\tTXT\t\"aaa\"",
+-		"cid.urn.arpa. NAPTR 100 50 \"s\" \"z3950+I2L+I2C\"    \"\" _z3950._tcp.gatech.edu.": "cid.urn.arpa.\t3600\tIN\tNAPTR\t100 50 \"s\" \"z3950+I2L+I2C\" \"\" _z3950._tcp.gatech.edu.",
+-		"cid.urn.arpa. NAPTR 100 50 \"s\" \"rcds+I2C\"         \"\" _rcds._udp.gatech.edu.":  "cid.urn.arpa.\t3600\tIN\tNAPTR\t100 50 \"s\" \"rcds+I2C\" \"\" _rcds._udp.gatech.edu.",
+-		"cid.urn.arpa. NAPTR 100 50 \"s\" \"http+I2L+I2C+I2R\" \"\" _http._tcp.gatech.edu.":  "cid.urn.arpa.\t3600\tIN\tNAPTR\t100 50 \"s\" \"http+I2L+I2C+I2R\" \"\" _http._tcp.gatech.edu.",
+-		"cid.urn.arpa. NAPTR 100 10 \"\" \"\" \"/urn:cid:.+@([^\\.]+\\.)(.*)$/\\2/i\" .":     "cid.urn.arpa.\t3600\tIN\tNAPTR\t100 10 \"\" \"\" \"/urn:cid:.+@([^\\.]+\\.)(.*)$/\\2/i\" .",
+-	}
+-	for i, o := range tests {
+-		rr, e := NewRR(i)
+-		if e != nil {
+-			t.Log("failed to parse RR: " + e.Error())
+-			t.Fail()
+-			continue
+-		}
+-		if rr.String() != o {
+-			t.Logf("`%s' should be equal to\n`%s', but is\n`%s'\n", i, o, rr.String())
+-			t.Fail()
+-		} else {
+-			t.Logf("RR is OK: `%s'", rr.String())
+-		}
+-	}
+-}
+-
+-func TestParseClass(t *testing.T) {
+-	tests := map[string]string{
+-		"t.example.com. IN A 127.0.0.1": "t.example.com.	3600	IN	A	127.0.0.1",
+-		"t.example.com. CS A 127.0.0.1": "t.example.com.	3600	CS	A	127.0.0.1",
+-		"t.example.com. CH A 127.0.0.1": "t.example.com.	3600	CH	A	127.0.0.1",
+-		// ClassANY can not occur in zone files
+-		// "t.example.com. ANY A 127.0.0.1": "t.example.com.	3600	ANY	A	127.0.0.1",
+-		"t.example.com. NONE A 127.0.0.1": "t.example.com.	3600	NONE	A	127.0.0.1",
+-	}
+-	for i, o := range tests {
+-		rr, e := NewRR(i)
+-		if e != nil {
+-			t.Log("failed to parse RR: " + e.Error())
+-			t.Fail()
+-			continue
+-		}
+-		if rr.String() != o {
+-			t.Logf("`%s' should be equal to\n`%s', but is\n`%s'\n", i, o, rr.String())
+-			t.Fail()
+-		} else {
+-			t.Logf("RR is OK: `%s'", rr.String())
+-		}
+-	}
+-}
+-
+-func TestBrace(t *testing.T) {
+-	tests := map[string]string{
+-		"(miek.nl.) 3600 IN A 127.0.1.1":                 "miek.nl.\t3600\tIN\tA\t127.0.1.1",
+-		"miek.nl. (3600) IN MX (10) elektron.atoom.net.": "miek.nl.\t3600\tIN\tMX\t10 elektron.atoom.net.",
+-		`miek.nl. IN (
+-                        3600 A 127.0.0.1)`: "miek.nl.\t3600\tIN\tA\t127.0.0.1",
+-		"(miek.nl.) (A) (127.0.2.1)":                          "miek.nl.\t3600\tIN\tA\t127.0.2.1",
+-		"miek.nl A 127.0.3.1":                                 "miek.nl.\t3600\tIN\tA\t127.0.3.1",
+-		"_ssh._tcp.local. 60 IN (PTR) stora._ssh._tcp.local.": "_ssh._tcp.local.\t60\tIN\tPTR\tstora._ssh._tcp.local.",
+-		"miek.nl. NS ns.miek.nl":                              "miek.nl.\t3600\tIN\tNS\tns.miek.nl.",
+-		`(miek.nl.) (
+-                        (IN)
+-                        (AAAA)
+-                        (::1) )`: "miek.nl.\t3600\tIN\tAAAA\t::1",
+-		`(miek.nl.) (
+-                        (IN)
+-                        (AAAA)
+-                        (::1))`: "miek.nl.\t3600\tIN\tAAAA\t::1",
+-		"miek.nl. IN AAAA ::2": "miek.nl.\t3600\tIN\tAAAA\t::2",
+-		`((m)(i)ek.(n)l.) (SOA) (soa.) (soa.) (
+-                                2009032802 ; serial
+-                                21600      ; refresh (6 hours)
+-                                7(2)00       ; retry (2 hours)
+-                                604()800     ; expire (1 week)
+-                                3600       ; minimum (1 hour)
+-                        )`: "miek.nl.\t3600\tIN\tSOA\tsoa. soa. 2009032802 21600 7200 604800 3600",
+-		"miek\\.nl. IN A 127.0.0.10": "miek\\.nl.\t3600\tIN\tA\t127.0.0.10",
+-		"miek.nl. IN A 127.0.0.11":   "miek.nl.\t3600\tIN\tA\t127.0.0.11",
+-		"miek.nl. A 127.0.0.12":      "miek.nl.\t3600\tIN\tA\t127.0.0.12",
+-		`miek.nl.       86400 IN SOA elektron.atoom.net. miekg.atoom.net. (
+-                                2009032802 ; serial
+-                                21600      ; refresh (6 hours)
+-                                7200       ; retry (2 hours)
+-                                604800     ; expire (1 week)
+-                                3600       ; minimum (1 hour)
+-                        )`: "miek.nl.\t86400\tIN\tSOA\telektron.atoom.net. miekg.atoom.net. 2009032802 21600 7200 604800 3600",
+-	}
+-	for i, o := range tests {
+-		rr, e := NewRR(i)
+-		if e != nil {
+-			t.Log("failed to parse RR: " + e.Error() + "\n\t" + i)
+-			t.Fail()
+-			continue
+-		}
+-		if rr.String() != o {
+-			t.Logf("`%s' should be equal to\n`%s', but is     `%s'\n", i, o, rr.String())
+-			t.Fail()
+-		} else {
+-			t.Logf("RR is OK: `%s'", rr.String())
+-		}
+-	}
+-}
+-
+-func TestParseFailure(t *testing.T) {
+-	tests := []string{"miek.nl. IN A 327.0.0.1",
+-		"miek.nl. IN AAAA ::x",
+-		"miek.nl. IN MX a0 miek.nl.",
+-		"miek.nl aap IN MX mx.miek.nl.",
+-		"miek.nl 200 IN mxx 10 mx.miek.nl.",
+-		"miek.nl. inn MX 10 mx.miek.nl.",
+-		// "miek.nl. IN CNAME ", // actually valid nowadays, zero size rdata
+-		"miek.nl. IN CNAME ..",
+-		"miek.nl. PA MX 10 miek.nl.",
+-		"miek.nl. ) IN MX 10 miek.nl.",
+-	}
+-
+-	for _, s := range tests {
+-		_, err := NewRR(s)
+-		if err == nil {
+-			t.Logf("should have triggered an error: \"%s\"", s)
+-			t.Fail()
+-		}
+-	}
+-}
+-
+-func TestZoneParsing(t *testing.T) {
+-	// parse_test.db
+-	db := `
+-a.example.com.                IN A 127.0.0.1
+-8db7._openpgpkey.example.com. IN OPENPGPKEY mQCNAzIG
+-$ORIGIN a.example.com.
+-test                          IN A 127.0.0.1
+-$ORIGIN b.example.com.
+-test                          IN CNAME test.a.example.com.
+-`
+-	start := time.Now().UnixNano()
+-	to := ParseZone(strings.NewReader(db), "", "parse_test.db")
+-	var i int
+-	for x := range to {
+-		i++
+-		if x.Error != nil {
+-			t.Logf("%s\n", x.Error)
+-			t.Fail()
+-			continue
+-		}
+-		t.Logf("%s\n", x.RR)
+-	}
+-	delta := time.Now().UnixNano() - start
+-	t.Logf("%d RRs parsed in %.2f s (%.2f RR/s)", i, float32(delta)/1e9, float32(i)/(float32(delta)/1e9))
+-}
+-
+-func ExampleZone() {
+-	zone := `$ORIGIN .
+-$TTL 3600       ; 1 hour
+-name                    IN SOA  a6.nstld.com. hostmaster.nic.name. (
+-                                203362132  ; serial
+-                                300        ; refresh (5 minutes)
+-                                300        ; retry (5 minutes)
+-                                1209600    ; expire (2 weeks)
+-                                300        ; minimum (5 minutes)
+-                                )
+-$TTL 10800      ; 3 hours
+-name.	10800	IN	NS	name.
+-               IN       NS      g6.nstld.com.
+-               7200     NS      h6.nstld.com.
+-             3600 IN    NS      j6.nstld.com.
+-             IN 3600    NS      k6.nstld.com.
+-                        NS      l6.nstld.com.
+-                        NS      a6.nstld.com.
+-                        NS      c6.nstld.com.
+-                        NS      d6.nstld.com.
+-                        NS      f6.nstld.com.
+-                        NS      m6.nstld.com.
+-(
+-			NS	m7.nstld.com.
+-)
+-$ORIGIN name.
+-0-0onlus                NS      ns7.ehiweb.it.
+-                        NS      ns8.ehiweb.it.
+-0-g                     MX      10 mx01.nic
+-                        MX      10 mx02.nic
+-                        MX      10 mx03.nic
+-                        MX      10 mx04.nic
+-$ORIGIN 0-g.name
+-moutamassey             NS      ns01.yahoodomains.jp.
+-                        NS      ns02.yahoodomains.jp.
+-`
+-	to := ParseZone(strings.NewReader(zone), "", "testzone")
+-	for x := range to {
+-		fmt.Printf("%s\n", x.RR)
+-	}
+-	// Output:
+-	// name.	3600	IN	SOA	a6.nstld.com. hostmaster.nic.name. 203362132 300 300 1209600 300
+-	// name.	10800	IN	NS	name.
+-	// name.	10800	IN	NS	g6.nstld.com.
+-	// name.	7200	IN	NS	h6.nstld.com.
+-	// name.	3600	IN	NS	j6.nstld.com.
+-	// name.	3600	IN	NS	k6.nstld.com.
+-	// name.	10800	IN	NS	l6.nstld.com.
+-	// name.	10800	IN	NS	a6.nstld.com.
+-	// name.	10800	IN	NS	c6.nstld.com.
+-	// name.	10800	IN	NS	d6.nstld.com.
+-	// name.	10800	IN	NS	f6.nstld.com.
+-	// name.	10800	IN	NS	m6.nstld.com.
+-	// name.	10800	IN	NS	m7.nstld.com.
+-	// 0-0onlus.name.	10800	IN	NS	ns7.ehiweb.it.
+-	// 0-0onlus.name.	10800	IN	NS	ns8.ehiweb.it.
+-	// 0-g.name.	10800	IN	MX	10 mx01.nic.name.
+-	// 0-g.name.	10800	IN	MX	10 mx02.nic.name.
+-	// 0-g.name.	10800	IN	MX	10 mx03.nic.name.
+-	// 0-g.name.	10800	IN	MX	10 mx04.nic.name.
+-	// moutamassey.0-g.name.name.	10800	IN	NS	ns01.yahoodomains.jp.
+-	// moutamassey.0-g.name.name.	10800	IN	NS	ns02.yahoodomains.jp.
+-}
+-
+-func ExampleHIP() {
+-	h := `www.example.com     IN  HIP ( 2 200100107B1A74DF365639CC39F1D578
+-                AwEAAbdxyhNuSutc5EMzxTs9LBPCIkOFH8cIvM4p
+-9+LrV4e19WzK00+CI6zBCQTdtWsuxKbWIy87UOoJTwkUs7lBu+Upr1gsNrut79ryra+bSRGQ
+-b1slImA8YVJyuIDsj7kwzG7jnERNqnWxZ48AWkskmdHaVDP4BcelrTI3rMXdXF5D
+-        rvs.example.com. )`
+-	if hip, err := NewRR(h); err == nil {
+-		fmt.Printf("%s\n", hip.String())
+-	}
+-	// Output:
+-	// www.example.com.	3600	IN	HIP	2 200100107B1A74DF365639CC39F1D578 AwEAAbdxyhNuSutc5EMzxTs9LBPCIkOFH8cIvM4p9+LrV4e19WzK00+CI6zBCQTdtWsuxKbWIy87UOoJTwkUs7lBu+Upr1gsNrut79ryra+bSRGQb1slImA8YVJyuIDsj7kwzG7jnERNqnWxZ48AWkskmdHaVDP4BcelrTI3rMXdXF5D rvs.example.com.
+-}
+-
+-func TestHIP(t *testing.T) {
+-	h := `www.example.com.      IN  HIP ( 2 200100107B1A74DF365639CC39F1D578
+-                                AwEAAbdxyhNuSutc5EMzxTs9LBPCIkOFH8cIvM4p
+-9+LrV4e19WzK00+CI6zBCQTdtWsuxKbWIy87UOoJTwkUs7lBu+Upr1gsNrut79ryra+bSRGQ
+-b1slImA8YVJyuIDsj7kwzG7jnERNqnWxZ48AWkskmdHaVDP4BcelrTI3rMXdXF5D
+-                                rvs1.example.com.
+-                                rvs2.example.com. )`
+-	rr, err := NewRR(h)
+-	if err != nil {
+-		t.Fatalf("failed to parse RR: %s", err)
+-	}
+-	t.Logf("RR: %s", rr)
+-	msg := new(Msg)
+-	msg.Answer = []RR{rr, rr}
+-	bytes, err := msg.Pack()
+-	if err != nil {
+-		t.Fatalf("failed to pack msg: %s", err)
+-	}
+-	if err := msg.Unpack(bytes); err != nil {
+-		t.Fatalf("failed to unpack msg: %s", err)
+-	}
+-	if len(msg.Answer) != 2 {
+-		t.Fatalf("2 answers expected: %V", msg)
+-	}
+-	for i, rr := range msg.Answer {
+-		rr := rr.(*HIP)
+-		t.Logf("RR: %s", rr)
+-		if l := len(rr.RendezvousServers); l != 2 {
+-			t.Fatalf("2 servers expected, only %d in record %d:\n%V", l, i, msg)
+-		}
+-		for j, s := range []string{"rvs1.example.com.", "rvs2.example.com."} {
+-			if rr.RendezvousServers[j] != s {
+-				t.Fatalf("expected server %d of record %d to be %s:\n%V", j, i, s, msg)
+-			}
+-		}
+-	}
+-}
+-
+-func ExampleSOA() {
+-	s := "example.com. 1000 SOA master.example.com. admin.example.com. 1 4294967294 4294967293 4294967295 100"
+-	if soa, err := NewRR(s); err == nil {
+-		fmt.Printf("%s\n", soa.String())
+-	}
+-	// Output:
+-	// example.com.	1000	IN	SOA	master.example.com. admin.example.com. 1 4294967294 4294967293 4294967295 100
+-}
+-
+-func TestLineNumberError(t *testing.T) {
+-	s := "example.com. 1000 SOA master.example.com. admin.example.com. monkey 4294967294 4294967293 4294967295 100"
+-	if _, err := NewRR(s); err != nil {
+-		if err.Error() != "dns: bad SOA zone parameter: \"monkey\" at line: 1:68" {
+-			t.Logf("not expecting this error: " + err.Error())
+-			t.Fail()
+-		}
+-	}
+-}
+-
+-// Test with no known RR on the line
+-func TestLineNumberError2(t *testing.T) {
+-	tests := map[string]string{
+-		"example.com. 1000 SO master.example.com. admin.example.com. 1 4294967294 4294967293 4294967295 100": "dns: expecting RR type or class, not this...: \"SO\" at line: 1:21",
+-		"example.com 1000 IN TALINK a.example.com. b..example.com.":                                          "dns: bad TALINK NextName: \"b..example.com.\" at line: 1:57",
+-		"example.com 1000 IN TALINK ( a.example.com. b..example.com. )":                                      "dns: bad TALINK NextName: \"b..example.com.\" at line: 1:60",
+-		`example.com 1000 IN TALINK ( a.example.com.
+-	bb..example.com. )`: "dns: bad TALINK NextName: \"bb..example.com.\" at line: 2:18",
+-		// This is a bug, it should report an error on line 1, but the new is already processed.
+-		`example.com 1000 IN TALINK ( a.example.com.  b...example.com.
+-	)`: "dns: bad TALINK NextName: \"b...example.com.\" at line: 2:1"}
+-
+-	for in, err := range tests {
+-		_, e := NewRR(in)
+-		if e == nil {
+-			t.Fail()
+-		} else {
+-			if e.Error() != err {
+-				t.Logf("%s\n", in)
+-				t.Logf("error should be %s is %s\n", err, e.Error())
+-				t.Fail()
+-			}
+-		}
+-	}
+-}
+-
+-// Test if the calculations are correct
+-func TestRfc1982(t *testing.T) {
+-	// If the current time and the timestamp are more than 68 years apart
+-	// it means the date has wrapped. 0 is 1970
+-
+-	// fall in the current 68 year span
+-	strtests := []string{"20120525134203", "19700101000000", "20380119031408"}
+-	for _, v := range strtests {
+-		if x, _ := StringToTime(v); v != TimeToString(x) {
+-			t.Logf("1982 arithmetic string failure %s (%s:%d)", v, TimeToString(x), x)
+-			t.Fail()
+-		}
+-	}
+-
+-	inttests := map[uint32]string{0: "19700101000000",
+-		1 << 31:   "20380119031408",
+-		1<<32 - 1: "21060207062815",
+-	}
+-	for i, v := range inttests {
+-		if TimeToString(i) != v {
+-			t.Logf("1982 arithmetic int failure %d:%s (%s)", i, v, TimeToString(i))
+-			t.Fail()
+-		}
+-	}
+-
+-	// Future tests, these dates get parsed to a date within the current 136 year span
+-	future := map[string]string{"22680119031408": "20631123173144",
+-		"19010101121212": "20370206184028",
+-		"19210101121212": "20570206184028",
+-		"19500101121212": "20860206184028",
+-		"19700101000000": "19700101000000",
+-		"19690101000000": "21050207062816",
+-		"29210101121212": "21040522212236",
+-	}
+-	for from, to := range future {
+-		x, _ := StringToTime(from)
+-		y := TimeToString(x)
+-		if y != to {
+-			t.Logf("1982 arithmetic future failure %s:%s (%s)", from, to, y)
+-			t.Fail()
+-		}
+-	}
+-}
+-
+-func TestEmpty(t *testing.T) {
+-	for _ = range ParseZone(strings.NewReader(""), "", "") {
+-		t.Logf("should be empty")
+-		t.Fail()
+-	}
+-}
+-
+-func TestLowercaseTokens(t *testing.T) {
+-	var testrecords = []string{
+-		"example.org. 300 IN a 1.2.3.4",
+-		"example.org. 300 in A 1.2.3.4",
+-		"example.org. 300 in a 1.2.3.4",
+-		"example.org. 300 a 1.2.3.4",
+-		"example.org. 300 A 1.2.3.4",
+-		"example.org. IN a 1.2.3.4",
+-		"example.org. in A 1.2.3.4",
+-		"example.org. in a 1.2.3.4",
+-		"example.org. a 1.2.3.4",
+-		"example.org. A 1.2.3.4",
+-		"example.org. a 1.2.3.4",
+-		"$ORIGIN example.org.\n a 1.2.3.4",
+-		"$Origin example.org.\n a 1.2.3.4",
+-		"$origin example.org.\n a 1.2.3.4",
+-		"example.org. Class1 Type1 1.2.3.4",
+-	}
+-	for _, testrr := range testrecords {
+-		_, err := NewRR(testrr)
+-		if err != nil {
+-			t.Errorf("failed to parse %#v, got %s", testrr, err.Error())
+-		}
+-	}
+-}
+-
+-func ExampleGenerate() {
+-	// From the manual: http://www.bind9.net/manual/bind/9.3.2/Bv9ARM.ch06.html#id2566761
+-	zone := "$GENERATE 1-2 0 NS SERVER$.EXAMPLE.\n$GENERATE 1-8 $ CNAME $.0"
+-	to := ParseZone(strings.NewReader(zone), "0.0.192.IN-ADDR.ARPA.", "")
+-	for x := range to {
+-		if x.Error == nil {
+-			fmt.Printf("%s\n", x.RR.String())
+-		}
+-	}
+-	// Output:
+-	// 0.0.0.192.IN-ADDR.ARPA.	3600	IN	NS	SERVER1.EXAMPLE.
+-	// 0.0.0.192.IN-ADDR.ARPA.	3600	IN	NS	SERVER2.EXAMPLE.
+-	// 1.0.0.192.IN-ADDR.ARPA.	3600	IN	CNAME	1.0.0.0.192.IN-ADDR.ARPA.
+-	// 2.0.0.192.IN-ADDR.ARPA.	3600	IN	CNAME	2.0.0.0.192.IN-ADDR.ARPA.
+-	// 3.0.0.192.IN-ADDR.ARPA.	3600	IN	CNAME	3.0.0.0.192.IN-ADDR.ARPA.
+-	// 4.0.0.192.IN-ADDR.ARPA.	3600	IN	CNAME	4.0.0.0.192.IN-ADDR.ARPA.
+-	// 5.0.0.192.IN-ADDR.ARPA.	3600	IN	CNAME	5.0.0.0.192.IN-ADDR.ARPA.
+-	// 6.0.0.192.IN-ADDR.ARPA.	3600	IN	CNAME	6.0.0.0.192.IN-ADDR.ARPA.
+-	// 7.0.0.192.IN-ADDR.ARPA.	3600	IN	CNAME	7.0.0.0.192.IN-ADDR.ARPA.
+-	// 8.0.0.192.IN-ADDR.ARPA.	3600	IN	CNAME	8.0.0.0.192.IN-ADDR.ARPA.
+-}
+-
+-func TestSRVPacking(t *testing.T) {
+-	msg := Msg{}
+-
+-	things := []string{"1.2.3.4:8484",
+-		"45.45.45.45:8484",
+-		"84.84.84.84:8484",
+-	}
+-
+-	for i, n := range things {
+-		h, p, err := net.SplitHostPort(n)
+-		if err != nil {
+-			continue
+-		}
+-		port := 8484
+-		tmp, err := strconv.Atoi(p)
+-		if err == nil {
+-			port = tmp
+-		}
+-
+-		rr := &SRV{
+-			Hdr: RR_Header{Name: "somename.",
+-				Rrtype: TypeSRV,
+-				Class:  ClassINET,
+-				Ttl:    5},
+-			Priority: uint16(i),
+-			Weight:   5,
+-			Port:     uint16(port),
+-			Target:   h + ".",
+-		}
+-
+-		msg.Answer = append(msg.Answer, rr)
+-	}
+-
+-	_, err := msg.Pack()
+-	if err != nil {
+-		t.Fatalf("couldn't pack %v\n", msg)
+-	}
+-}
+-
+-func TestParseBackslash(t *testing.T) {
+-	if r, e := NewRR("nul\\000gap.test.globnix.net. 600 IN	A 192.0.2.10"); e != nil {
+-		t.Fatalf("could not create RR with \\000 in it")
+-	} else {
+-		t.Logf("parsed %s\n", r.String())
+-	}
+-	if r, e := NewRR(`nul\000gap.test.globnix.net. 600 IN TXT "Hello\123"`); e != nil {
+-		t.Fatalf("could not create RR with \\000 in it")
+-	} else {
+-		t.Logf("parsed %s\n", r.String())
+-	}
+-	if r, e := NewRR(`m\ @\ iek.nl. IN 3600 A 127.0.0.1`); e != nil {
+-		t.Fatalf("could not create RR with \\ and \\@ in it")
+-	} else {
+-		t.Logf("parsed %s\n", r.String())
+-	}
+-}
+-
+-func TestILNP(t *testing.T) {
+-	tests := []string{
+-		"host1.example.com.\t3600\tIN\tNID\t10 0014:4fff:ff20:ee64",
+-		"host1.example.com.\t3600\tIN\tNID\t20 0015:5fff:ff21:ee65",
+-		"host2.example.com.\t3600\tIN\tNID\t10 0016:6fff:ff22:ee66",
+-		"host1.example.com.\t3600\tIN\tL32\t10 10.1.2.0",
+-		"host1.example.com.\t3600\tIN\tL32\t20 10.1.4.0",
+-		"host2.example.com.\t3600\tIN\tL32\t10 10.1.8.0",
+-		"host1.example.com.\t3600\tIN\tL64\t10 2001:0DB8:1140:1000",
+-		"host1.example.com.\t3600\tIN\tL64\t20 2001:0DB8:2140:2000",
+-		"host2.example.com.\t3600\tIN\tL64\t10 2001:0DB8:4140:4000",
+-		"host1.example.com.\t3600\tIN\tLP\t10 l64-subnet1.example.com.",
+-		"host1.example.com.\t3600\tIN\tLP\t10 l64-subnet2.example.com.",
+-		"host1.example.com.\t3600\tIN\tLP\t20 l32-subnet1.example.com.",
+-	}
+-	for _, t1 := range tests {
+-		r, e := NewRR(t1)
+-		if e != nil {
+-			t.Fatalf("an error occured: %s\n", e.Error())
+-		} else {
+-			if t1 != r.String() {
+-				t.Fatalf("strings should be equal %s %s", t1, r.String())
+-			}
+-		}
+-	}
+-}
+-
+-func TestNsapGposEidNimloc(t *testing.T) {
+-	dt := map[string]string{
+-		"foo.bar.com.    IN  NSAP   21 47000580ffff000000321099991111222233334444": "foo.bar.com.\t3600\tIN\tNSAP\t21 47000580ffff000000321099991111222233334444",
+-		"host.school.de  IN  NSAP   17 39276f3100111100002222333344449876":         "host.school.de.\t3600\tIN\tNSAP\t17 39276f3100111100002222333344449876",
+-		"444433332222111199990123000000ff. NSAP-PTR foo.bar.com.":                  "444433332222111199990123000000ff.\t3600\tIN\tNSAP-PTR\tfoo.bar.com.",
+-		"lillee. IN  GPOS -32.6882 116.8652 10.0":                                  "lillee.\t3600\tIN\tGPOS\t-32.6882 116.8652 10.0",
+-		"hinault. IN GPOS -22.6882 116.8652 250.0":                                 "hinault.\t3600\tIN\tGPOS\t-22.6882 116.8652 250.0",
+-		"VENERA.   IN NIMLOC  75234159EAC457800920":                                "VENERA.\t3600\tIN\tNIMLOC\t75234159EAC457800920",
+-		"VAXA.     IN EID     3141592653589793":                                    "VAXA.\t3600\tIN\tEID\t3141592653589793",
+-	}
+-	for i, o := range dt {
+-		rr, e := NewRR(i)
+-		if e != nil {
+-			t.Log("failed to parse RR: " + e.Error())
+-			t.Fail()
+-			continue
+-		}
+-		if rr.String() != o {
+-			t.Logf("`%s' should be equal to\n`%s', but is     `%s'\n", i, o, rr.String())
+-			t.Fail()
+-		} else {
+-			t.Logf("RR is OK: `%s'", rr.String())
+-		}
+-	}
+-}
+-
+-func TestPX(t *testing.T) {
+-	dt := map[string]string{
+-		"*.net2.it. IN PX 10 net2.it. PRMD-net2.ADMD-p400.C-it.":      "*.net2.it.\t3600\tIN\tPX\t10 net2.it. PRMD-net2.ADMD-p400.C-it.",
+-		"ab.net2.it. IN PX 10 ab.net2.it. O-ab.PRMD-net2.ADMDb.C-it.": "ab.net2.it.\t3600\tIN\tPX\t10 ab.net2.it. O-ab.PRMD-net2.ADMDb.C-it.",
+-	}
+-	for i, o := range dt {
+-		rr, e := NewRR(i)
+-		if e != nil {
+-			t.Log("failed to parse RR: " + e.Error())
+-			t.Fail()
+-			continue
+-		}
+-		if rr.String() != o {
+-			t.Logf("`%s' should be equal to\n`%s', but is     `%s'\n", i, o, rr.String())
+-			t.Fail()
+-		} else {
+-			t.Logf("RR is OK: `%s'", rr.String())
+-		}
+-	}
+-}
+-
+-func TestComment(t *testing.T) {
+-	// Comments we must see
+-	comments := map[string]bool{"; this is comment 1": true,
+-		"; this is comment 4": true, "; this is comment 6": true,
+-		"; this is comment 7": true, "; this is comment 8": true}
+-	zone := `
+-foo. IN A 10.0.0.1 ; this is comment 1
+-foo. IN A (
+-	10.0.0.2 ; this is comment2
+-)
+-; this is comment3
+-foo. IN A 10.0.0.3
+-foo. IN A ( 10.0.0.4 ); this is comment 4
+-
+-foo. IN A 10.0.0.5
+-; this is comment5
+-
+-foo. IN A 10.0.0.6
+-
+-foo. IN DNSKEY 256 3 5 AwEAAb+8l ; this is comment 6
+-foo. IN NSEC miek.nl. TXT RRSIG NSEC; this is comment 7
+-foo. IN TXT "THIS IS TEXT MAN"; this is comment 8
+-`
+-	for x := range ParseZone(strings.NewReader(zone), ".", "") {
+-		if x.Error == nil {
+-			if x.Comment != "" {
+-				if _, ok := comments[x.Comment]; !ok {
+-					t.Logf("wrong comment %s", x.Comment)
+-					t.Fail()
+-				}
+-			}
+-		}
+-	}
+-}
+-
+-func TestEUIxx(t *testing.T) {
+-	tests := map[string]string{
+-		"host.example. IN EUI48 00-00-5e-90-01-2a":       "host.example.\t3600\tIN\tEUI48\t00-00-5e-90-01-2a",
+-		"host.example. IN EUI64 00-00-5e-ef-00-00-00-2a": "host.example.\t3600\tIN\tEUI64\t00-00-5e-ef-00-00-00-2a",
+-	}
+-	for i, o := range tests {
+-		r, e := NewRR(i)
+-		if e != nil {
+-			t.Logf("failed to parse %s: %s\n", i, e.Error())
+-			t.Fail()
+-		}
+-		if r.String() != o {
+-			t.Logf("want %s, got %s\n", o, r.String())
+-			t.Fail()
+-		}
+-	}
+-}
+-
+-func TestUserRR(t *testing.T) {
+-	tests := map[string]string{
+-		"host.example. IN UID 1234":              "host.example.\t3600\tIN\tUID\t1234",
+-		"host.example. IN GID 1234556":           "host.example.\t3600\tIN\tGID\t1234556",
+-		"host.example. IN UINFO \"Miek Gieben\"": "host.example.\t3600\tIN\tUINFO\t\"Miek Gieben\"",
+-	}
+-	for i, o := range tests {
+-		r, e := NewRR(i)
+-		if e != nil {
+-			t.Logf("failed to parse %s: %s\n", i, e.Error())
+-			t.Fail()
+-		}
+-		if r.String() != o {
+-			t.Logf("want %s, got %s\n", o, r.String())
+-			t.Fail()
+-		}
+-	}
+-}
+-
+-func TestTXT(t *testing.T) {
+-	// Test single entry TXT record
+-	rr, err := NewRR(`_raop._tcp.local. 60 IN TXT "single value"`)
+-	if err != nil {
+-		t.Error("failed to parse single value TXT record", err)
+-	} else if rr, ok := rr.(*TXT); !ok {
+-		t.Error("wrong type, record should be of type TXT")
+-	} else {
+-		if len(rr.Txt) != 1 {
+-			t.Error("bad size of TXT value:", len(rr.Txt))
+-		} else if rr.Txt[0] != "single value" {
+-			t.Error("bad single value")
+-		}
+-		if rr.String() != `_raop._tcp.local.	60	IN	TXT	"single value"` {
+-			t.Error("bad representation of TXT record:", rr.String())
+-		}
+-		if rr.len() != 28+1+12 {
+-			t.Error("bad size of serialized record:", rr.len())
+-		}
+-	}
+-
+-	// Test multi entries TXT record
+-	rr, err = NewRR(`_raop._tcp.local. 60 IN TXT "a=1" "b=2" "c=3" "d=4"`)
+-	if err != nil {
+-		t.Error("failed to parse multi-values TXT record", err)
+-	} else if rr, ok := rr.(*TXT); !ok {
+-		t.Error("wrong type, record should be of type TXT")
+-	} else {
+-		if len(rr.Txt) != 4 {
+-			t.Error("bad size of TXT multi-value:", len(rr.Txt))
+-		} else if rr.Txt[0] != "a=1" || rr.Txt[1] != "b=2" || rr.Txt[2] != "c=3" || rr.Txt[3] != "d=4" {
+-			t.Error("bad values in TXT records")
+-		}
+-		if rr.String() != `_raop._tcp.local.	60	IN	TXT	"a=1" "b=2" "c=3" "d=4"` {
+-			t.Error("bad representation of TXT multi value record:", rr.String())
+-		}
+-		if rr.len() != 28+1+3+1+3+1+3+1+3 {
+-			t.Error("bad size of serialized multi value record:", rr.len())
+-		}
+-	}
+-
+-	// Test empty-string in TXT record
+-	rr, err = NewRR(`_raop._tcp.local. 60 IN TXT ""`)
+-	if err != nil {
+-		t.Error("failed to parse empty-string TXT record", err)
+-	} else if rr, ok := rr.(*TXT); !ok {
+-		t.Error("wrong type, record should be of type TXT")
+-	} else {
+-		if len(rr.Txt) != 1 {
+-			t.Error("bad size of TXT empty-string value:", len(rr.Txt))
+-		} else if rr.Txt[0] != "" {
+-			t.Error("bad value for empty-string TXT record")
+-		}
+-		if rr.String() != `_raop._tcp.local.	60	IN	TXT	""` {
+-			t.Error("bad representation of empty-string TXT record:", rr.String())
+-		}
+-		if rr.len() != 28+1 {
+-			t.Error("bad size of serialized record:", rr.len())
+-		}
+-	}
+-}
+-
+-func TestTypeXXXX(t *testing.T) {
+-	_, err := NewRR("example.com IN TYPE1234 \\# 4 aabbccdd")
+-	if err != nil {
+-		t.Logf("failed to parse TYPE1234 RR: %s", err.Error())
+-		t.Fail()
+-	}
+-	_, err = NewRR("example.com IN TYPE655341 \\# 8 aabbccddaabbccdd")
+-	if err == nil {
+-		t.Logf("this should not work, for TYPE655341")
+-		t.Fail()
+-	}
+-	_, err = NewRR("example.com IN TYPE1 \\# 4 0a000001")
+-	if err == nil {
+-		t.Logf("this should not work")
+-		t.Fail()
+-	}
+-}
+-
+-func TestPTR(t *testing.T) {
+-	_, err := NewRR("144.2.0.192.in-addr.arpa. 900 IN PTR ilouse03146p0\\(.example.com.")
+-	if err != nil {
+-		t.Error("failed to parse ", err.Error())
+-	}
+-}
+-
+-func TestDigit(t *testing.T) {
+-	tests := map[string]byte{
+-		"miek\\000.nl. 100 IN TXT \"A\"": 0,
+-		"miek\\001.nl. 100 IN TXT \"A\"": 1,
+-		"miek\\254.nl. 100 IN TXT \"A\"": 254,
+-		"miek\\255.nl. 100 IN TXT \"A\"": 255,
+-		"miek\\256.nl. 100 IN TXT \"A\"": 0,
+-		"miek\\257.nl. 100 IN TXT \"A\"": 1,
+-		"miek\\004.nl. 100 IN TXT \"A\"": 4,
+-	}
+-	for s, i := range tests {
+-		r, e := NewRR(s)
+-		buf := make([]byte, 40)
+-		if e != nil {
+-			t.Fatalf("failed to parse %s\n", e.Error())
+-		}
+-		PackRR(r, buf, 0, nil, false)
+-		t.Logf("%v\n", buf)
+-		if buf[5] != i {
+-			t.Fatalf("5 pos must be %d, is %d", i, buf[5])
+-		}
+-		r1, _, _ := UnpackRR(buf, 0)
+-		if r1.Header().Ttl != 100 {
+-			t.Fatalf("TTL should %d, is %d", 100, r1.Header().Ttl)
+-		}
+-	}
+-}
+-
+-func TestParseRRSIGTimestamp(t *testing.T) {
+-	tests := map[string]bool{
+-		`miek.nl.  IN RRSIG SOA 8 2 43200 20140210031301 20140111031301 12051 miek.nl. MVZUyrYwq0iZhMFDDnVXD2BvuNiUJjSYlJAgzyAE6CF875BMvvZa+Sb0 RlSCL7WODQSQHhCx/fegHhVVF+Iz8N8kOLrmXD1+jO3Bm6Prl5UhcsPx WTBsg/kmxbp8sR1kvH4oZJtVfakG3iDerrxNaf0sQwhZzyfJQAqpC7pcBoc=`: true,
+-		`miek.nl.  IN RRSIG SOA 8 2 43200 315565800 4102477800 12051 miek.nl. MVZUyrYwq0iZhMFDDnVXD2BvuNiUJjSYlJAgzyAE6CF875BMvvZa+Sb0 RlSCL7WODQSQHhCx/fegHhVVF+Iz8N8kOLrmXD1+jO3Bm6Prl5UhcsPx WTBsg/kmxbp8sR1kvH4oZJtVfakG3iDerrxNaf0sQwhZzyfJQAqpC7pcBoc=`:          true,
+-	}
+-	for r, _ := range tests {
+-		_, e := NewRR(r)
+-		if e != nil {
+-			t.Fail()
+-			t.Logf("%s\n", e.Error())
+-		}
+-	}
+-}
+-
+-func TestTxtEqual(t *testing.T) {
+-	rr1 := new(TXT)
+-	rr1.Hdr = RR_Header{Name: ".", Rrtype: TypeTXT, Class: ClassINET, Ttl: 0}
+-	rr1.Txt = []string{"a\"a", "\"", "b"}
+-	rr2, _ := NewRR(rr1.String())
+-	if rr1.String() != rr2.String() {
+-		t.Logf("these two TXT records should match")
+-		t.Logf("\n%s\n%s\n", rr1.String(), rr2.String())
+-		t.Fail() // This is not an error, but keep this test.
+-	}
+-	t.Logf("\n%s\n%s\n", rr1.String(), rr2.String())
+-}
+-
+-func TestTxtLong(t *testing.T) {
+-	rr1 := new(TXT)
+-	rr1.Hdr = RR_Header{Name: ".", Rrtype: TypeTXT, Class: ClassINET, Ttl: 0}
+-	// Make a long txt record, this breaks when sending the packet,
+-	// but not earlier.
+-	rr1.Txt = []string{"start-"}
+-	for i := 0; i < 200; i++ {
+-		rr1.Txt[0] += "start-"
+-	}
+-	str := rr1.String()
+-	if len(str) < len(rr1.Txt[0]) {
+-		t.Logf("string conversion should work")
+-		t.Fail()
+-	}
+-}
+-
+-// Basically, don't crash.
+-func TestMalformedPackets(t *testing.T) {
+-	var packets = []string{
+-		"0021641c0000000100000000000078787878787878787878787303636f6d0000100001",
+-	}
+-
+-	// com = 63 6f 6d
+-	for _, packet := range packets {
+-		data, _ := hex.DecodeString(packet)
+-		//		for _, v := range data {
+-		//			t.Logf("%s ", string(v))
+-		//		}
+-		var msg Msg
+-		msg.Unpack(data)
+-		//		println(msg.String())
+-	}
+-}
+-
+-type algorithm struct {
+-	name uint8
+-	bits int
+-}
+-
+-func TestNewPrivateKey(t *testing.T) {
+-	if testing.Short() {
+-		t.Skip("skipping test in short mode.")
+-	}
+-	algorithms := []algorithm{
+-		algorithm{ECDSAP256SHA256, 256},
+-		algorithm{ECDSAP384SHA384, 384},
+-		algorithm{RSASHA1, 1024},
+-		algorithm{RSASHA256, 2048},
+-		algorithm{DSA, 1024},
+-	}
+-
+-	for _, algo := range algorithms {
+-		key := new(DNSKEY)
+-		key.Hdr.Rrtype = TypeDNSKEY
+-		key.Hdr.Name = "miek.nl."
+-		key.Hdr.Class = ClassINET
+-		key.Hdr.Ttl = 14400
+-		key.Flags = 256
+-		key.Protocol = 3
+-		key.Algorithm = algo.name
+-		privkey, err := key.Generate(algo.bits)
+-		if err != nil {
+-			t.Fatal(err.Error())
+-		}
+-
+-		newPrivKey, err := key.NewPrivateKey(key.PrivateKeyString(privkey))
+-		if err != nil {
+-			t.Log(key.String())
+-			t.Log(key.PrivateKeyString(privkey))
+-
+-			t.Fatal(err.Error())
+-		}
+-
+-		switch newPrivKey := newPrivKey.(type) {
+-		case *rsa.PrivateKey:
+-			newPrivKey.Precompute()
+-		}
+-
+-		if !reflect.DeepEqual(privkey, newPrivKey) {
+-			t.Errorf("[%v] Private keys differ:\n%#v\n%#v\n", AlgorithmToString[algo.name], privkey, newPrivKey)
+-		}
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/privaterr.go b/Godeps/_workspace/src/github.com/miekg/dns/privaterr.go
+deleted file mode 100644
+index 2257137..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/privaterr.go
++++ /dev/null
+@@ -1,122 +0,0 @@
+-/*
+-PRIVATE RR
+-
+-RFC 6895 sets aside a range of type codes for private use. This range
+-is 65,280 - 65,534 (0xFF00 - 0xFFFE). When experimenting with new Resource Records these
+-can be used, before requesting an official type code from IANA.
+-*/
+-package dns
+-
+-import (
+-	"fmt"
+-	"strings"
+-)
+-
+-// PrivateRdata is an interface used for implementing "Private Use" RR types, see
+-// RFC 6895. This allows one to experiment with new RR types, without requesting an
+-// official type code. Also see dns.PrivateHandle and dns.PrivateHandleRemove.
+-type PrivateRdata interface {
+-	// String returns the text presentaton of the Rdata of the Private RR.
+-	String() string
+-	// Parse parses the Rdata of the private RR.
+-	Parse([]string) error
+-	// Pack is used when packing a private RR into a buffer.
+-	Pack([]byte) (int, error)
+-	// Unpack is used when unpacking a private RR from a buffer.
+-	// TODO(miek): diff. signature than Pack, see edns0.go for instance.
+-	Unpack([]byte) (int, error)
+-	// Copy copies the Rdata.
+-	Copy(PrivateRdata) error
+-	// Len returns the length in octets of the Rdata.
+-	Len() int
+-}
+-
+-// PrivateRR represents an RR that uses a PrivateRdata user-defined type.
+-// It mocks normal RRs and implements dns.RR interface.
+-type PrivateRR struct {
+-	Hdr  RR_Header
+-	Data PrivateRdata
+-}
+-
+-func mkPrivateRR(rrtype uint16) *PrivateRR {
+-	// Panics if RR is not an instance of PrivateRR.
+-	rrfunc, ok := typeToRR[rrtype]
+-	if !ok {
+-		panic(fmt.Sprintf("dns: invalid operation with Private RR type %d", rrtype))
+-	}
+-
+-	anyrr := rrfunc()
+-	switch rr := anyrr.(type) {
+-	case *PrivateRR:
+-		return rr
+-	}
+-	panic(fmt.Sprintf("dns: RR is not a PrivateRR, typeToRR[%d] generator returned %T", rrtype, anyrr))
+-}
+-
+-func (r *PrivateRR) Header() *RR_Header { return &r.Hdr }
+-func (r *PrivateRR) String() string     { return r.Hdr.String() + r.Data.String() }
+-
+-// Private len and copy parts to satisfy RR interface.
+-func (r *PrivateRR) len() int { return r.Hdr.len() + r.Data.Len() }
+-func (r *PrivateRR) copy() RR {
+-	// make new RR like this:
+-	rr := mkPrivateRR(r.Hdr.Rrtype)
+-	newh := r.Hdr.copyHeader()
+-	rr.Hdr = *newh
+-
+-	err := r.Data.Copy(rr.Data)
+-	if err != nil {
+-		panic("dns: got value that could not be used to copy Private rdata")
+-	}
+-	return rr
+-}
+-
+-// PrivateHandle registers a private resource record type. It requires
+-// string and numeric representation of private RR type and generator function as argument.
+-func PrivateHandle(rtypestr string, rtype uint16, generator func() PrivateRdata) {
+-	rtypestr = strings.ToUpper(rtypestr)
+-
+-	typeToRR[rtype] = func() RR { return &PrivateRR{RR_Header{}, generator()} }
+-	TypeToString[rtype] = rtypestr
+-	StringToType[rtypestr] = rtype
+-
+-	setPrivateRR := func(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-		rr := mkPrivateRR(h.Rrtype)
+-		rr.Hdr = h
+-
+-		var l lex
+-		text := make([]string, 0, 2) // could be 0..N elements, median is probably 1
+-	FETCH:
+-		for {
+-			// TODO(miek): we could also be returning _QUOTE, this might or might not
+-			// be an issue (basically parsing TXT becomes hard)
+-			switch l = <-c; l.value {
+-			case _NEWLINE, _EOF:
+-				break FETCH
+-			case _STRING:
+-				text = append(text, l.token)
+-			}
+-		}
+-
+-		err := rr.Data.Parse(text)
+-		if err != nil {
+-			return nil, &ParseError{f, err.Error(), l}, ""
+-		}
+-
+-		return rr, nil, ""
+-	}
+-
+-	typeToparserFunc[rtype] = parserFunc{setPrivateRR, true}
+-}
+-
+-// PrivateHandleRemove removes defenitions required to support private RR type.
+-func PrivateHandleRemove(rtype uint16) {
+-	rtypestr, ok := TypeToString[rtype]
+-	if ok {
+-		delete(typeToRR, rtype)
+-		delete(TypeToString, rtype)
+-		delete(typeToparserFunc, rtype)
+-		delete(StringToType, rtypestr)
+-	}
+-	return
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/privaterr_test.go b/Godeps/_workspace/src/github.com/miekg/dns/privaterr_test.go
+deleted file mode 100644
+index 6f1dff8..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/privaterr_test.go
++++ /dev/null
+@@ -1,169 +0,0 @@
+-package dns_test
+-
+-import (
+-	"github.com/miekg/dns"
+-	"strings"
+-	"testing"
+-)
+-
+-const TypeISBN uint16 = 0x0F01
+-
+-// A crazy new RR type :)
+-type ISBN struct {
+-	x string // rdata with 10 or 13 numbers, dashes or spaces allowed
+-}
+-
+-func NewISBN() dns.PrivateRdata { return &ISBN{""} }
+-
+-func (rd *ISBN) Len() int       { return len([]byte(rd.x)) }
+-func (rd *ISBN) String() string { return rd.x }
+-
+-func (rd *ISBN) Parse(txt []string) error {
+-	rd.x = strings.TrimSpace(strings.Join(txt, " "))
+-	return nil
+-}
+-
+-func (rd *ISBN) Pack(buf []byte) (int, error) {
+-	b := []byte(rd.x)
+-	n := copy(buf, b)
+-	if n != len(b) {
+-		return n, dns.ErrBuf
+-	}
+-	return n, nil
+-}
+-
+-func (rd *ISBN) Unpack(buf []byte) (int, error) {
+-	rd.x = string(buf)
+-	return len(buf), nil
+-}
+-
+-func (rd *ISBN) Copy(dest dns.PrivateRdata) error {
+-	isbn, ok := dest.(*ISBN)
+-	if !ok {
+-		return dns.ErrRdata
+-	}
+-	isbn.x = rd.x
+-	return nil
+-}
+-
+-var testrecord = strings.Join([]string{"example.org.", "3600", "IN", "ISBN", "12-3 456789-0-123"}, "\t")
+-
+-func TestPrivateText(t *testing.T) {
+-	dns.PrivateHandle("ISBN", TypeISBN, NewISBN)
+-	defer dns.PrivateHandleRemove(TypeISBN)
+-
+-	rr, err := dns.NewRR(testrecord)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if rr.String() != testrecord {
+-		t.Errorf("record string representation did not match original %#v != %#v", rr.String(), testrecord)
+-	} else {
+-		t.Log(rr.String())
+-	}
+-}
+-
+-func TestPrivateByteSlice(t *testing.T) {
+-	dns.PrivateHandle("ISBN", TypeISBN, NewISBN)
+-	defer dns.PrivateHandleRemove(TypeISBN)
+-
+-	rr, err := dns.NewRR(testrecord)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	buf := make([]byte, 100)
+-	off, err := dns.PackRR(rr, buf, 0, nil, false)
+-	if err != nil {
+-		t.Errorf("got error packing ISBN: %s", err)
+-	}
+-
+-	custrr := rr.(*dns.PrivateRR)
+-	if ln := custrr.Data.Len() + len(custrr.Header().Name) + 11; ln != off {
+-		t.Errorf("offset is not matching to length of Private RR: %d!=%d", off, ln)
+-	}
+-
+-	rr1, off1, err := dns.UnpackRR(buf[:off], 0)
+-	if err != nil {
+-		t.Errorf("got error unpacking ISBN: %s", err)
+-	}
+-
+-	if off1 != off {
+-		t.Errorf("Offset after unpacking differs: %d != %d", off1, off)
+-	}
+-
+-	if rr1.String() != testrecord {
+-		t.Errorf("Record string representation did not match original %#v != %#v", rr1.String(), testrecord)
+-	} else {
+-		t.Log(rr1.String())
+-	}
+-}
+-
+-const TypeVERSION uint16 = 0x0F02
+-
+-type VERSION struct {
+-	x string
+-}
+-
+-func NewVersion() dns.PrivateRdata { return &VERSION{""} }
+-
+-func (rd *VERSION) String() string { return rd.x }
+-func (rd *VERSION) Parse(txt []string) error {
+-	rd.x = strings.TrimSpace(strings.Join(txt, " "))
+-	return nil
+-}
+-
+-func (rd *VERSION) Pack(buf []byte) (int, error) {
+-	b := []byte(rd.x)
+-	n := copy(buf, b)
+-	if n != len(b) {
+-		return n, dns.ErrBuf
+-	}
+-	return n, nil
+-}
+-
+-func (rd *VERSION) Unpack(buf []byte) (int, error) {
+-	rd.x = string(buf)
+-	return len(buf), nil
+-}
+-
+-func (rd *VERSION) Copy(dest dns.PrivateRdata) error {
+-	isbn, ok := dest.(*VERSION)
+-	if !ok {
+-		return dns.ErrRdata
+-	}
+-	isbn.x = rd.x
+-	return nil
+-}
+-
+-func (rd *VERSION) Len() int {
+-	return len([]byte(rd.x))
+-}
+-
+-var smallzone = `$ORIGIN example.org.
+-@ SOA	sns.dns.icann.org. noc.dns.icann.org. (
+-		2014091518 7200 3600 1209600 3600
+-)
+-    A   1.2.3.4
+-ok ISBN 1231-92110-12
+-go VERSION (
+-	1.3.1 ; comment
+-)
+-www ISBN 1231-92110-16
+-*  CNAME @
+-`
+-
+-func TestPrivateZoneParser(t *testing.T) {
+-	dns.PrivateHandle("ISBN", TypeISBN, NewISBN)
+-	dns.PrivateHandle("VERSION", TypeVERSION, NewVersion)
+-	defer dns.PrivateHandleRemove(TypeISBN)
+-	defer dns.PrivateHandleRemove(TypeVERSION)
+-
+-	r := strings.NewReader(smallzone)
+-	for x := range dns.ParseZone(r, ".", "") {
+-		if err := x.Error; err != nil {
+-			t.Fatal(err)
+-		}
+-		t.Log(x.RR)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/rawmsg.go b/Godeps/_workspace/src/github.com/miekg/dns/rawmsg.go
+deleted file mode 100644
+index f138b77..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/rawmsg.go
++++ /dev/null
+@@ -1,95 +0,0 @@
+-package dns
+-
+-// These raw* functions do not use reflection, they directly set the values
+-// in the buffer. There are faster than their reflection counterparts.
+-
+-// RawSetId sets the message id in buf.
+-func rawSetId(msg []byte, i uint16) bool {
+-	if len(msg) < 2 {
+-		return false
+-	}
+-	msg[0], msg[1] = packUint16(i)
+-	return true
+-}
+-
+-// rawSetQuestionLen sets the length of the question section.
+-func rawSetQuestionLen(msg []byte, i uint16) bool {
+-	if len(msg) < 6 {
+-		return false
+-	}
+-	msg[4], msg[5] = packUint16(i)
+-	return true
+-}
+-
+-// rawSetAnswerLen sets the lenght of the answer section.
+-func rawSetAnswerLen(msg []byte, i uint16) bool {
+-	if len(msg) < 8 {
+-		return false
+-	}
+-	msg[6], msg[7] = packUint16(i)
+-	return true
+-}
+-
+-// rawSetsNsLen sets the lenght of the authority section.
+-func rawSetNsLen(msg []byte, i uint16) bool {
+-	if len(msg) < 10 {
+-		return false
+-	}
+-	msg[8], msg[9] = packUint16(i)
+-	return true
+-}
+-
+-// rawSetExtraLen sets the lenght of the additional section.
+-func rawSetExtraLen(msg []byte, i uint16) bool {
+-	if len(msg) < 12 {
+-		return false
+-	}
+-	msg[10], msg[11] = packUint16(i)
+-	return true
+-}
+-
+-// rawSetRdlength sets the rdlength in the header of
+-// the RR. The offset 'off' must be positioned at the
+-// start of the header of the RR, 'end' must be the
+-// end of the RR.
+-func rawSetRdlength(msg []byte, off, end int) bool {
+-	l := len(msg)
+-Loop:
+-	for {
+-		if off+1 > l {
+-			return false
+-		}
+-		c := int(msg[off])
+-		off++
+-		switch c & 0xC0 {
+-		case 0x00:
+-			if c == 0x00 {
+-				// End of the domainname
+-				break Loop
+-			}
+-			if off+c > l {
+-				return false
+-			}
+-			off += c
+-
+-		case 0xC0:
+-			// pointer, next byte included, ends domainname
+-			off++
+-			break Loop
+-		}
+-	}
+-	// The domainname has been seen, we at the start of the fixed part in the header.
+-	// Type is 2 bytes, class is 2 bytes, ttl 4 and then 2 bytes for the length.
+-	off += 2 + 2 + 4
+-	if off+2 > l {
+-		return false
+-	}
+-	//off+1 is the end of the header, 'end' is the end of the rr
+-	//so 'end' - 'off+2' is the length of the rdata
+-	rdatalen := end - (off + 2)
+-	if rdatalen > 0xFFFF {
+-		return false
+-	}
+-	msg[off], msg[off+1] = packUint16(uint16(rdatalen))
+-	return true
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/scanner.go b/Godeps/_workspace/src/github.com/miekg/dns/scanner.go
+deleted file mode 100644
+index c29bc2f..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/scanner.go
++++ /dev/null
+@@ -1,43 +0,0 @@
+-package dns
+-
+-// Implement a simple scanner, return a byte stream from an io reader.
+-
+-import (
+-	"bufio"
+-	"io"
+-	"text/scanner"
+-)
+-
+-type scan struct {
+-	src      *bufio.Reader
+-	position scanner.Position
+-	eof      bool // Have we just seen a eof
+-}
+-
+-func scanInit(r io.Reader) *scan {
+-	s := new(scan)
+-	s.src = bufio.NewReader(r)
+-	s.position.Line = 1
+-	return s
+-}
+-
+-// tokenText returns the next byte from the input
+-func (s *scan) tokenText() (byte, error) {
+-	c, err := s.src.ReadByte()
+-	if err != nil {
+-		return c, err
+-	}
+-	// delay the newline handling until the next token is delivered,
+-	// fixes off-by-one errors when reporting a parse error.
+-	if s.eof == true {
+-		s.position.Line++
+-		s.position.Column = 0
+-		s.eof = false
+-	}
+-	if c == '\n' {
+-		s.eof = true
+-		return c, nil
+-	}
+-	s.position.Column++
+-	return c, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/server.go b/Godeps/_workspace/src/github.com/miekg/dns/server.go
+deleted file mode 100644
+index c250ccc..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/server.go
++++ /dev/null
+@@ -1,626 +0,0 @@
+-// DNS server implementation.
+-
+-package dns
+-
+-import (
+-	"bytes"
+-	"io"
+-	"net"
+-	"sync"
+-	"time"
+-)
+-
+-type Handler interface {
+-	ServeDNS(w ResponseWriter, r *Msg)
+-}
+-
+-// A ResponseWriter interface is used by an DNS handler to
+-// construct an DNS response.
+-type ResponseWriter interface {
+-	// LocalAddr returns the net.Addr of the server
+-	LocalAddr() net.Addr
+-	// RemoteAddr returns the net.Addr of the client that sent the current request.
+-	RemoteAddr() net.Addr
+-	// WriteMsg writes a reply back to the client.
+-	WriteMsg(*Msg) error
+-	// Write writes a raw buffer back to the client.
+-	Write([]byte) (int, error)
+-	// Close closes the connection.
+-	Close() error
+-	// TsigStatus returns the status of the Tsig.
+-	TsigStatus() error
+-	// TsigTimersOnly sets the tsig timers only boolean.
+-	TsigTimersOnly(bool)
+-	// Hijack lets the caller take over the connection.
+-	// After a call to Hijack(), the DNS package will not do anything with the connection.
+-	Hijack()
+-}
+-
+-type response struct {
+-	hijacked       bool // connection has been hijacked by handler
+-	tsigStatus     error
+-	tsigTimersOnly bool
+-	tsigRequestMAC string
+-	tsigSecret     map[string]string // the tsig secrets
+-	udp            *net.UDPConn      // i/o connection if UDP was used
+-	tcp            *net.TCPConn      // i/o connection if TCP was used
+-	udpSession     *sessionUDP       // oob data to get egress interface right
+-	remoteAddr     net.Addr          // address of the client
+-}
+-
+-// ServeMux is an DNS request multiplexer. It matches the
+-// zone name of each incoming request against a list of
+-// registered patterns add calls the handler for the pattern
+-// that most closely matches the zone name. ServeMux is DNSSEC aware, meaning
+-// that queries for the DS record are redirected to the parent zone (if that
+-// is also registered), otherwise the child gets the query.
+-// ServeMux is also safe for concurrent access from multiple goroutines.
+-type ServeMux struct {
+-	z map[string]Handler
+-	m *sync.RWMutex
+-}
+-
+-// NewServeMux allocates and returns a new ServeMux.
+-func NewServeMux() *ServeMux { return &ServeMux{z: make(map[string]Handler), m: new(sync.RWMutex)} }
+-
+-// DefaultServeMux is the default ServeMux used by Serve.
+-var DefaultServeMux = NewServeMux()
+-
+-// The HandlerFunc type is an adapter to allow the use of
+-// ordinary functions as DNS handlers.  If f is a function
+-// with the appropriate signature, HandlerFunc(f) is a
+-// Handler object that calls f.
+-type HandlerFunc func(ResponseWriter, *Msg)
+-
+-// ServerDNS calls f(w, r)
+-func (f HandlerFunc) ServeDNS(w ResponseWriter, r *Msg) {
+-	f(w, r)
+-}
+-
+-// FailedHandler returns a HandlerFunc that returns SERVFAIL for every request it gets.
+-func HandleFailed(w ResponseWriter, r *Msg) {
+-	m := new(Msg)
+-	m.SetRcode(r, RcodeServerFailure)
+-	// does not matter if this write fails
+-	w.WriteMsg(m)
+-}
+-
+-func failedHandler() Handler { return HandlerFunc(HandleFailed) }
+-
+-// ListenAndServe Starts a server on addresss and network speficied. Invoke handler
+-// for incoming queries.
+-func ListenAndServe(addr string, network string, handler Handler) error {
+-	server := &Server{Addr: addr, Net: network, Handler: handler}
+-	return server.ListenAndServe()
+-}
+-
+-// ActivateAndServe activates a server with a listener from systemd,
+-// l and p should not both be non-nil.
+-// If both l and p are not nil only p will be used.
+-// Invoke handler for incoming queries.
+-func ActivateAndServe(l net.Listener, p net.PacketConn, handler Handler) error {
+-	server := &Server{Listener: l, PacketConn: p, Handler: handler}
+-	return server.ActivateAndServe()
+-}
+-
+-func (mux *ServeMux) match(q string, t uint16) Handler {
+-	mux.m.RLock()
+-	defer mux.m.RUnlock()
+-	var handler Handler
+-	b := make([]byte, len(q)) // worst case, one label of length q
+-	off := 0
+-	end := false
+-	for {
+-		l := len(q[off:])
+-		for i := 0; i < l; i++ {
+-			b[i] = q[off+i]
+-			if b[i] >= 'A' && b[i] <= 'Z' {
+-				b[i] |= ('a' - 'A')
+-			}
+-		}
+-		if h, ok := mux.z[string(b[:l])]; ok { // 'causes garbage, might want to change the map key
+-			if t != TypeDS {
+-				return h
+-			} else {
+-				// Continue for DS to see if we have a parent too, if so delegeate to the parent
+-				handler = h
+-			}
+-		}
+-		off, end = NextLabel(q, off)
+-		if end {
+-			break
+-		}
+-	}
+-	// Wildcard match, if we have found nothing try the root zone as a last resort.
+-	if h, ok := mux.z["."]; ok {
+-		return h
+-	}
+-	return handler
+-}
+-
+-// Handle adds a handler to the ServeMux for pattern.
+-func (mux *ServeMux) Handle(pattern string, handler Handler) {
+-	if pattern == "" {
+-		panic("dns: invalid pattern " + pattern)
+-	}
+-	mux.m.Lock()
+-	mux.z[Fqdn(pattern)] = handler
+-	mux.m.Unlock()
+-}
+-
+-// Handle adds a handler to the ServeMux for pattern.
+-func (mux *ServeMux) HandleFunc(pattern string, handler func(ResponseWriter, *Msg)) {
+-	mux.Handle(pattern, HandlerFunc(handler))
+-}
+-
+-// HandleRemove deregistrars the handler specific for pattern from the ServeMux.
+-func (mux *ServeMux) HandleRemove(pattern string) {
+-	if pattern == "" {
+-		panic("dns: invalid pattern " + pattern)
+-	}
+-	// don't need a mutex here, because deleting is OK, even if the
+-	// entry is note there.
+-	delete(mux.z, Fqdn(pattern))
+-}
+-
+-// ServeDNS dispatches the request to the handler whose
+-// pattern most closely matches the request message. If DefaultServeMux
+-// is used the correct thing for DS queries is done: a possible parent
+-// is sought.
+-// If no handler is found a standard SERVFAIL message is returned
+-// If the request message does not have exactly one question in the
+-// question section a SERVFAIL is returned, unlesss Unsafe is true.
+-func (mux *ServeMux) ServeDNS(w ResponseWriter, request *Msg) {
+-	var h Handler
+-	if len(request.Question) < 1 { // allow more than one question
+-		h = failedHandler()
+-	} else {
+-		if h = mux.match(request.Question[0].Name, request.Question[0].Qtype); h == nil {
+-			h = failedHandler()
+-		}
+-	}
+-	h.ServeDNS(w, request)
+-}
+-
+-// Handle registers the handler with the given pattern
+-// in the DefaultServeMux. The documentation for
+-// ServeMux explains how patterns are matched.
+-func Handle(pattern string, handler Handler) { DefaultServeMux.Handle(pattern, handler) }
+-
+-// HandleRemove deregisters the handle with the given pattern
+-// in the DefaultServeMux.
+-func HandleRemove(pattern string) { DefaultServeMux.HandleRemove(pattern) }
+-
+-// HandleFunc registers the handler function with the given pattern
+-// in the DefaultServeMux.
+-func HandleFunc(pattern string, handler func(ResponseWriter, *Msg)) {
+-	DefaultServeMux.HandleFunc(pattern, handler)
+-}
+-
+-// A Server defines parameters for running an DNS server.
+-type Server struct {
+-	// Address to listen on, ":dns" if empty.
+-	Addr string
+-	// if "tcp" it will invoke a TCP listener, otherwise an UDP one.
+-	Net string
+-	// TCP Listener to use, this is to aid in systemd's socket activation.
+-	Listener net.Listener
+-	// UDP "Listener" to use, this is to aid in systemd's socket activation.
+-	PacketConn net.PacketConn
+-	// Handler to invoke, dns.DefaultServeMux if nil.
+-	Handler Handler
+-	// Default buffer size to use to read incoming UDP messages. If not set
+-	// it defaults to MinMsgSize (512 B).
+-	UDPSize int
+-	// The net.Conn.SetReadTimeout value for new connections, defaults to 2 * time.Second.
+-	ReadTimeout time.Duration
+-	// The net.Conn.SetWriteTimeout value for new connections, defaults to 2 * time.Second.
+-	WriteTimeout time.Duration
+-	// TCP idle timeout for multiple queries, if nil, defaults to 8 * time.Second (RFC 5966).
+-	IdleTimeout func() time.Duration
+-	// Secret(s) for Tsig map[<zonename>]<base64 secret>.
+-	TsigSecret map[string]string
+-	// Unsafe instructs the server to disregard any sanity checks and directly hand the message to
+-	// the handler. It will specfically not check if the query has the QR bit not set.
+-	Unsafe bool
+-	// If NotifyStartedFunc is set is is called, once the server has started listening. 
+-	NotifyStartedFunc func()
+-
+-	// For graceful shutdown.
+-	stopUDP chan bool
+-	stopTCP chan bool
+-	wgUDP   sync.WaitGroup
+-	wgTCP   sync.WaitGroup
+-
+-	// make start/shutdown not racy
+-	lock    sync.Mutex
+-	started bool
+-}
+-
+-// ListenAndServe starts a nameserver on the configured address in *Server.
+-func (srv *Server) ListenAndServe() error {
+-	srv.lock.Lock()
+-	if srv.started {
+-		return &Error{err: "server already started"}
+-	}
+-	srv.stopUDP, srv.stopTCP = make(chan bool), make(chan bool)
+-	srv.started = true
+-	srv.lock.Unlock()
+-	addr := srv.Addr
+-	if addr == "" {
+-		addr = ":domain"
+-	}
+-	if srv.UDPSize == 0 {
+-		srv.UDPSize = MinMsgSize
+-	}
+-	switch srv.Net {
+-	case "tcp", "tcp4", "tcp6":
+-		a, e := net.ResolveTCPAddr(srv.Net, addr)
+-		if e != nil {
+-			return e
+-		}
+-		l, e := net.ListenTCP(srv.Net, a)
+-		if e != nil {
+-			return e
+-		}
+-		return srv.serveTCP(l)
+-	case "udp", "udp4", "udp6":
+-		a, e := net.ResolveUDPAddr(srv.Net, addr)
+-		if e != nil {
+-			return e
+-		}
+-		l, e := net.ListenUDP(srv.Net, a)
+-		if e != nil {
+-			return e
+-		}
+-		if e := setUDPSocketOptions(l); e != nil {
+-			return e
+-		}
+-		return srv.serveUDP(l)
+-	}
+-	return &Error{err: "bad network"}
+-}
+-
+-// ActivateAndServe starts a nameserver with the PacketConn or Listener
+-// configured in *Server. Its main use is to start a server from systemd.
+-func (srv *Server) ActivateAndServe() error {
+-	srv.lock.Lock()
+-	if srv.started {
+-		return &Error{err: "server already started"}
+-	}
+-	srv.stopUDP, srv.stopTCP = make(chan bool), make(chan bool)
+-	srv.started = true
+-	srv.lock.Unlock()
+-	if srv.PacketConn != nil {
+-		if srv.UDPSize == 0 {
+-			srv.UDPSize = MinMsgSize
+-		}
+-		if t, ok := srv.PacketConn.(*net.UDPConn); ok {
+-			if e := setUDPSocketOptions(t); e != nil {
+-				return e
+-			}
+-			return srv.serveUDP(t)
+-		}
+-	}
+-	if srv.Listener != nil {
+-		if t, ok := srv.Listener.(*net.TCPListener); ok {
+-			return srv.serveTCP(t)
+-		}
+-	}
+-	return &Error{err: "bad listeners"}
+-}
+-
+-// Shutdown gracefully shuts down a server. After a call to Shutdown, ListenAndServe and
+-// ActivateAndServe will return. All in progress queries are completed before the server
+-// is taken down. If the Shutdown is taking longer than the reading timeout and error
+-// is returned.
+-func (srv *Server) Shutdown() error {
+-	srv.lock.Lock()
+-	if !srv.started {
+-		return &Error{err: "server not started"}
+-	}
+-	srv.started = false
+-	srv.lock.Unlock()
+-	net, addr := srv.Net, srv.Addr
+-	switch {
+-	case srv.Listener != nil:
+-		a := srv.Listener.Addr()
+-		net, addr = a.Network(), a.String()
+-	case srv.PacketConn != nil:
+-		a := srv.PacketConn.LocalAddr()
+-		net, addr = a.Network(), a.String()
+-	}
+-
+-	fin := make(chan bool)
+-	switch net {
+-	case "tcp", "tcp4", "tcp6":
+-		go func() {
+-			srv.stopTCP <- true
+-			srv.wgTCP.Wait()
+-			fin <- true
+-		}()
+-
+-	case "udp", "udp4", "udp6":
+-		go func() {
+-			srv.stopUDP <- true
+-			srv.wgUDP.Wait()
+-			fin <- true
+-		}()
+-	}
+-
+-	c := &Client{Net: net}
+-	go c.Exchange(new(Msg), addr) // extra query to help ReadXXX loop to pass
+-
+-	select {
+-	case <-time.After(srv.getReadTimeout()):
+-		return &Error{err: "server shutdown is pending"}
+-	case <-fin:
+-		return nil
+-	}
+-}
+-
+-// getReadTimeout is a helper func to use system timeout if server did not intend to change it.
+-func (srv *Server) getReadTimeout() time.Duration {
+-	rtimeout := dnsTimeout
+-	if srv.ReadTimeout != 0 {
+-		rtimeout = srv.ReadTimeout
+-	}
+-	return rtimeout
+-}
+-
+-// serveTCP starts a TCP listener for the server.
+-// Each request is handled in a seperate goroutine.
+-func (srv *Server) serveTCP(l *net.TCPListener) error {
+-	defer l.Close()
+-
+-	if srv.NotifyStartedFunc != nil {
+-		srv.NotifyStartedFunc()
+-	}
+-
+-	handler := srv.Handler
+-	if handler == nil {
+-		handler = DefaultServeMux
+-	}
+-	rtimeout := srv.getReadTimeout()
+-	// deadline is not used here
+-	for {
+-		rw, e := l.AcceptTCP()
+-		if e != nil {
+-			continue
+-		}
+-		m, e := srv.readTCP(rw, rtimeout)
+-		select {
+-		case <-srv.stopTCP:
+-			return nil
+-		default:
+-		}
+-		if e != nil {
+-			continue
+-		}
+-		srv.wgTCP.Add(1)
+-		go srv.serve(rw.RemoteAddr(), handler, m, nil, nil, rw)
+-	}
+-	panic("dns: not reached")
+-}
+-
+-// serveUDP starts a UDP listener for the server.
+-// Each request is handled in a seperate goroutine.
+-func (srv *Server) serveUDP(l *net.UDPConn) error {
+-	defer l.Close()
+-
+-	if srv.NotifyStartedFunc != nil {
+-		srv.NotifyStartedFunc()
+-	}
+-
+-	handler := srv.Handler
+-	if handler == nil {
+-		handler = DefaultServeMux
+-	}
+-	rtimeout := srv.getReadTimeout()
+-	// deadline is not used here
+-	for {
+-		m, s, e := srv.readUDP(l, rtimeout)
+-		select {
+-		case <-srv.stopUDP:
+-			return nil
+-		default:
+-		}
+-		if e != nil {
+-			continue
+-		}
+-		srv.wgUDP.Add(1)
+-		go srv.serve(s.RemoteAddr(), handler, m, l, s, nil)
+-	}
+-	panic("dns: not reached")
+-}
+-
+-// Serve a new connection.
+-func (srv *Server) serve(a net.Addr, h Handler, m []byte, u *net.UDPConn, s *sessionUDP, t *net.TCPConn) {
+-	w := &response{tsigSecret: srv.TsigSecret, udp: u, tcp: t, remoteAddr: a, udpSession: s}
+-	q := 0
+-	defer func() {
+-		if u != nil {
+-			srv.wgUDP.Done()
+-		}
+-		if t != nil {
+-			srv.wgTCP.Done()
+-		}
+-	}()
+-Redo:
+-	// Ideally we want use isMsg here before we allocate memory to actually parse the packet.
+-	req := new(Msg)
+-	err := req.Unpack(m)
+-	if err != nil { // Send a FormatError back
+-		x := new(Msg)
+-		x.SetRcodeFormatError(req)
+-		w.WriteMsg(x)
+-		goto Exit
+-	}
+-	if !srv.Unsafe && req.Response {
+-		goto Exit
+-	}
+-
+-	w.tsigStatus = nil
+-	if w.tsigSecret != nil {
+-		if t := req.IsTsig(); t != nil {
+-			secret := t.Hdr.Name
+-			if _, ok := w.tsigSecret[secret]; !ok {
+-				w.tsigStatus = ErrKeyAlg
+-			}
+-			w.tsigStatus = TsigVerify(m, w.tsigSecret[secret], "", false)
+-			w.tsigTimersOnly = false
+-			w.tsigRequestMAC = req.Extra[len(req.Extra)-1].(*TSIG).MAC
+-		}
+-	}
+-	h.ServeDNS(w, req) // Writes back to the client
+-
+-Exit:
+-	if w.hijacked {
+-		return // client calls Close()
+-	}
+-	if u != nil { // UDP, "close" and return
+-		w.Close()
+-		return
+-	}
+-	idleTimeout := tcpIdleTimeout
+-	if srv.IdleTimeout != nil {
+-		idleTimeout = srv.IdleTimeout()
+-	}
+-	m, e := srv.readTCP(w.tcp, idleTimeout)
+-	if e == nil {
+-		q++
+-		// TODO(miek): make this number configurable?
+-		if q > 128 { // close socket after this many queries
+-			w.Close()
+-			return
+-		}
+-		goto Redo
+-	}
+-	w.Close()
+-	return
+-}
+-
+-func (srv *Server) readTCP(conn *net.TCPConn, timeout time.Duration) ([]byte, error) {
+-	conn.SetReadDeadline(time.Now().Add(timeout))
+-	l := make([]byte, 2)
+-	n, err := conn.Read(l)
+-	if err != nil || n != 2 {
+-		if err != nil {
+-			return nil, err
+-		}
+-		return nil, ErrShortRead
+-	}
+-	length, _ := unpackUint16(l, 0)
+-	if length == 0 {
+-		return nil, ErrShortRead
+-	}
+-	m := make([]byte, int(length))
+-	n, err = conn.Read(m[:int(length)])
+-	if err != nil || n == 0 {
+-		if err != nil {
+-			return nil, err
+-		}
+-		return nil, ErrShortRead
+-	}
+-	i := n
+-	for i < int(length) {
+-		j, err := conn.Read(m[i:int(length)])
+-		if err != nil {
+-			return nil, err
+-		}
+-		i += j
+-	}
+-	n = i
+-	m = m[:n]
+-	return m, nil
+-}
+-
+-func (srv *Server) readUDP(conn *net.UDPConn, timeout time.Duration) ([]byte, *sessionUDP, error) {
+-	conn.SetReadDeadline(time.Now().Add(timeout))
+-	m := make([]byte, srv.UDPSize)
+-	n, s, e := readFromSessionUDP(conn, m)
+-	if e != nil || n == 0 {
+-		if e != nil {
+-			return nil, nil, e
+-		}
+-		return nil, nil, ErrShortRead
+-	}
+-	m = m[:n]
+-	return m, s, nil
+-}
+-
+-// WriteMsg implements the ResponseWriter.WriteMsg method.
+-func (w *response) WriteMsg(m *Msg) (err error) {
+-	var data []byte
+-	if w.tsigSecret != nil { // if no secrets, dont check for the tsig (which is a longer check)
+-		if t := m.IsTsig(); t != nil {
+-			data, w.tsigRequestMAC, err = TsigGenerate(m, w.tsigSecret[t.Hdr.Name], w.tsigRequestMAC, w.tsigTimersOnly)
+-			if err != nil {
+-				return err
+-			}
+-			_, err = w.Write(data)
+-			return err
+-		}
+-	}
+-	data, err = m.Pack()
+-	if err != nil {
+-		return err
+-	}
+-	_, err = w.Write(data)
+-	return err
+-}
+-
+-// Write implements the ResponseWriter.Write method.
+-func (w *response) Write(m []byte) (int, error) {
+-	switch {
+-	case w.udp != nil:
+-		n, err := writeToSessionUDP(w.udp, m, w.udpSession)
+-		return n, err
+-	case w.tcp != nil:
+-		lm := len(m)
+-		if lm < 2 {
+-			return 0, io.ErrShortBuffer
+-		}
+-		if lm > MaxMsgSize {
+-			return 0, &Error{err: "message too large"}
+-		}
+-		l := make([]byte, 2, 2+lm)
+-		l[0], l[1] = packUint16(uint16(lm))
+-		m = append(l, m...)
+-
+-		n, err := io.Copy(w.tcp, bytes.NewReader(m))
+-		return int(n), err
+-	}
+-	panic("not reached")
+-}
+-
+-// LocalAddr implements the ResponseWriter.LocalAddr method.
+-func (w *response) LocalAddr() net.Addr {
+-	if w.tcp != nil {
+-		return w.tcp.LocalAddr()
+-	}
+-	return w.udp.LocalAddr()
+-}
+-
+-// RemoteAddr implements the ResponseWriter.RemoteAddr method.
+-func (w *response) RemoteAddr() net.Addr { return w.remoteAddr }
+-
+-// TsigStatus implements the ResponseWriter.TsigStatus method.
+-func (w *response) TsigStatus() error { return w.tsigStatus }
+-
+-// TsigTimersOnly implements the ResponseWriter.TsigTimersOnly method.
+-func (w *response) TsigTimersOnly(b bool) { w.tsigTimersOnly = b }
+-
+-// Hijack implements the ResponseWriter.Hijack method.
+-func (w *response) Hijack() { w.hijacked = true }
+-
+-// Close implements the ResponseWriter.Close method
+-func (w *response) Close() error {
+-	// Can't close the udp conn, as that is actually the listener.
+-	if w.tcp != nil {
+-		e := w.tcp.Close()
+-		w.tcp = nil
+-		return e
+-	}
+-	return nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/server_test.go b/Godeps/_workspace/src/github.com/miekg/dns/server_test.go
+deleted file mode 100644
+index 5efb1cf..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/server_test.go
++++ /dev/null
+@@ -1,401 +0,0 @@
+-package dns
+-
+-import (
+-	"fmt"
+-	"net"
+-	"runtime"
+-	"sync"
+-	"testing"
+-)
+-
+-func HelloServer(w ResponseWriter, req *Msg) {
+-	m := new(Msg)
+-	m.SetReply(req)
+-
+-	m.Extra = make([]RR, 1)
+-	m.Extra[0] = &TXT{Hdr: RR_Header{Name: m.Question[0].Name, Rrtype: TypeTXT, Class: ClassINET, Ttl: 0}, Txt: []string{"Hello world"}}
+-	w.WriteMsg(m)
+-}
+-
+-func AnotherHelloServer(w ResponseWriter, req *Msg) {
+-	m := new(Msg)
+-	m.SetReply(req)
+-
+-	m.Extra = make([]RR, 1)
+-	m.Extra[0] = &TXT{Hdr: RR_Header{Name: m.Question[0].Name, Rrtype: TypeTXT, Class: ClassINET, Ttl: 0}, Txt: []string{"Hello example"}}
+-	w.WriteMsg(m)
+-}
+-
+-func RunLocalUDPServer(laddr string) (*Server, string, error) {
+-	pc, err := net.ListenPacket("udp", laddr)
+-	if err != nil {
+-		return nil, "", err
+-	}
+-	server := &Server{PacketConn: pc}
+-
+-	waitLock := sync.Mutex{}
+-	waitLock.Lock()
+-	server.NotifyStartedFunc = waitLock.Unlock
+-
+-	go func() {
+-		server.ActivateAndServe()
+-		pc.Close()
+-	}()
+-
+-	waitLock.Lock()
+-	return server, pc.LocalAddr().String(), nil
+-}
+-
+-func RunLocalUDPServerUnsafe(laddr string) (*Server, string, error) {
+-	pc, err := net.ListenPacket("udp", laddr)
+-	if err != nil {
+-		return nil, "", err
+-	}
+-	server := &Server{PacketConn: pc, Unsafe: true}
+-
+-	waitLock := sync.Mutex{}
+-	waitLock.Lock()
+-	server.NotifyStartedFunc = waitLock.Unlock
+-
+-	go func() {
+-		server.ActivateAndServe()
+-		pc.Close()
+-	}()
+-
+-	waitLock.Lock()
+-	return server, pc.LocalAddr().String(), nil
+-}
+-
+-func RunLocalTCPServer(laddr string) (*Server, string, error) {
+-	l, err := net.Listen("tcp", laddr)
+-	if err != nil {
+-		return nil, "", err
+-	}
+-
+-	server := &Server{Listener: l}
+-
+-	waitLock := sync.Mutex{}
+-	waitLock.Lock()
+-	server.NotifyStartedFunc = waitLock.Unlock
+-
+-	go func() {
+-		server.ActivateAndServe()
+-		l.Close()
+-	}()
+-
+-	waitLock.Lock()
+-	return server, l.Addr().String(), nil
+-}
+-
+-func TestServing(t *testing.T) {
+-	HandleFunc("miek.nl.", HelloServer)
+-	HandleFunc("example.com.", AnotherHelloServer)
+-	defer HandleRemove("miek.nl.")
+-	defer HandleRemove("example.com.")
+-
+-	s, addrstr, err := RunLocalUDPServer("127.0.0.1:0")
+-	if err != nil {
+-		t.Fatalf("Unable to run test server: %s", err)
+-	}
+-	defer s.Shutdown()
+-
+-	c := new(Client)
+-	m := new(Msg)
+-	m.SetQuestion("miek.nl.", TypeTXT)
+-	r, _, err := c.Exchange(m, addrstr)
+-	if err != nil || len(r.Extra) == 0 {
+-		t.Log("failed to exchange miek.nl", err)
+-		t.Fatal()
+-	}
+-	txt := r.Extra[0].(*TXT).Txt[0]
+-	if txt != "Hello world" {
+-		t.Log("Unexpected result for miek.nl", txt, "!= Hello world")
+-		t.Fail()
+-	}
+-
+-	m.SetQuestion("example.com.", TypeTXT)
+-	r, _, err = c.Exchange(m, addrstr)
+-	if err != nil {
+-		t.Log("failed to exchange example.com", err)
+-		t.Fatal()
+-	}
+-	txt = r.Extra[0].(*TXT).Txt[0]
+-	if txt != "Hello example" {
+-		t.Log("Unexpected result for example.com", txt, "!= Hello example")
+-		t.Fail()
+-	}
+-
+-	// Test Mixes cased as noticed by Ask.
+-	m.SetQuestion("eXaMplE.cOm.", TypeTXT)
+-	r, _, err = c.Exchange(m, addrstr)
+-	if err != nil {
+-		t.Log("failed to exchange eXaMplE.cOm", err)
+-		t.Fail()
+-	}
+-	txt = r.Extra[0].(*TXT).Txt[0]
+-	if txt != "Hello example" {
+-		t.Log("Unexpected result for example.com", txt, "!= Hello example")
+-		t.Fail()
+-	}
+-}
+-
+-func BenchmarkServe(b *testing.B) {
+-	b.StopTimer()
+-	HandleFunc("miek.nl.", HelloServer)
+-	defer HandleRemove("miek.nl.")
+-	a := runtime.GOMAXPROCS(4)
+-
+-	s, addrstr, err := RunLocalUDPServer("127.0.0.1:0")
+-	if err != nil {
+-		b.Fatalf("Unable to run test server: %s", err)
+-	}
+-	defer s.Shutdown()
+-
+-	c := new(Client)
+-	m := new(Msg)
+-	m.SetQuestion("miek.nl", TypeSOA)
+-
+-	b.StartTimer()
+-	for i := 0; i < b.N; i++ {
+-		c.Exchange(m, addrstr)
+-	}
+-	runtime.GOMAXPROCS(a)
+-}
+-
+-func benchmarkServe6(b *testing.B) {
+-	b.StopTimer()
+-	HandleFunc("miek.nl.", HelloServer)
+-	defer HandleRemove("miek.nl.")
+-	a := runtime.GOMAXPROCS(4)
+-	s, addrstr, err := RunLocalUDPServer("[::1]:0")
+-	if err != nil {
+-		b.Fatalf("Unable to run test server: %s", err)
+-	}
+-	defer s.Shutdown()
+-
+-	c := new(Client)
+-	m := new(Msg)
+-	m.SetQuestion("miek.nl", TypeSOA)
+-
+-	b.StartTimer()
+-	for i := 0; i < b.N; i++ {
+-		c.Exchange(m, addrstr)
+-	}
+-	runtime.GOMAXPROCS(a)
+-}
+-
+-func HelloServerCompress(w ResponseWriter, req *Msg) {
+-	m := new(Msg)
+-	m.SetReply(req)
+-	m.Extra = make([]RR, 1)
+-	m.Extra[0] = &TXT{Hdr: RR_Header{Name: m.Question[0].Name, Rrtype: TypeTXT, Class: ClassINET, Ttl: 0}, Txt: []string{"Hello world"}}
+-	m.Compress = true
+-	w.WriteMsg(m)
+-}
+-
+-func BenchmarkServeCompress(b *testing.B) {
+-	b.StopTimer()
+-	HandleFunc("miek.nl.", HelloServerCompress)
+-	defer HandleRemove("miek.nl.")
+-	a := runtime.GOMAXPROCS(4)
+-	s, addrstr, err := RunLocalUDPServer("127.0.0.1:0")
+-	if err != nil {
+-		b.Fatalf("Unable to run test server: %s", err)
+-	}
+-	defer s.Shutdown()
+-
+-	c := new(Client)
+-	m := new(Msg)
+-	m.SetQuestion("miek.nl", TypeSOA)
+-	b.StartTimer()
+-	for i := 0; i < b.N; i++ {
+-		c.Exchange(m, addrstr)
+-	}
+-	runtime.GOMAXPROCS(a)
+-}
+-
+-func TestDotAsCatchAllWildcard(t *testing.T) {
+-	mux := NewServeMux()
+-	mux.Handle(".", HandlerFunc(HelloServer))
+-	mux.Handle("example.com.", HandlerFunc(AnotherHelloServer))
+-
+-	handler := mux.match("www.miek.nl.", TypeTXT)
+-	if handler == nil {
+-		t.Error("wildcard match failed")
+-	}
+-
+-	handler = mux.match("www.example.com.", TypeTXT)
+-	if handler == nil {
+-		t.Error("example.com match failed")
+-	}
+-
+-	handler = mux.match("a.www.example.com.", TypeTXT)
+-	if handler == nil {
+-		t.Error("a.www.example.com match failed")
+-	}
+-
+-	handler = mux.match("boe.", TypeTXT)
+-	if handler == nil {
+-		t.Error("boe. match failed")
+-	}
+-}
+-
+-func TestCaseFolding(t *testing.T) {
+-	mux := NewServeMux()
+-	mux.Handle("_udp.example.com.", HandlerFunc(HelloServer))
+-
+-	handler := mux.match("_dns._udp.example.com.", TypeSRV)
+-	if handler == nil {
+-		t.Error("case sensitive characters folded")
+-	}
+-
+-	handler = mux.match("_DNS._UDP.EXAMPLE.COM.", TypeSRV)
+-	if handler == nil {
+-		t.Error("case insensitive characters not folded")
+-	}
+-}
+-
+-func TestRootServer(t *testing.T) {
+-	mux := NewServeMux()
+-	mux.Handle(".", HandlerFunc(HelloServer))
+-
+-	handler := mux.match(".", TypeNS)
+-	if handler == nil {
+-		t.Error("root match failed")
+-	}
+-}
+-
+-type maxRec struct {
+-	max int
+-	sync.RWMutex
+-}
+-
+-var M = new(maxRec)
+-
+-func HelloServerLargeResponse(resp ResponseWriter, req *Msg) {
+-	m := new(Msg)
+-	m.SetReply(req)
+-	m.Authoritative = true
+-	m1 := 0
+-	M.RLock()
+-	m1 = M.max
+-	M.RUnlock()
+-	for i := 0; i < m1; i++ {
+-		aRec := &A{
+-			Hdr: RR_Header{
+-				Name:   req.Question[0].Name,
+-				Rrtype: TypeA,
+-				Class:  ClassINET,
+-				Ttl:    0,
+-			},
+-			A: net.ParseIP(fmt.Sprintf("127.0.0.%d", i+1)).To4(),
+-		}
+-		m.Answer = append(m.Answer, aRec)
+-	}
+-	resp.WriteMsg(m)
+-}
+-
+-func TestServingLargeResponses(t *testing.T) {
+-	HandleFunc("example.", HelloServerLargeResponse)
+-	defer HandleRemove("example.")
+-
+-	s, addrstr, err := RunLocalUDPServer("127.0.0.1:0")
+-	if err != nil {
+-		t.Fatalf("Unable to run test server: %s", err)
+-	}
+-	defer s.Shutdown()
+-
+-	// Create request
+-	m := new(Msg)
+-	m.SetQuestion("web.service.example.", TypeANY)
+-
+-	c := new(Client)
+-	c.Net = "udp"
+-	M.Lock()
+-	M.max = 2
+-	M.Unlock()
+-	_, _, err = c.Exchange(m, addrstr)
+-	if err != nil {
+-		t.Logf("failed to exchange: %s", err.Error())
+-		t.Fail()
+-	}
+-	// This must fail
+-	M.Lock()
+-	M.max = 20
+-	M.Unlock()
+-	_, _, err = c.Exchange(m, addrstr)
+-	if err == nil {
+-		t.Logf("failed to fail exchange, this should generate packet error")
+-		t.Fail()
+-	}
+-	// But this must work again
+-	c.UDPSize = 7000
+-	_, _, err = c.Exchange(m, addrstr)
+-	if err != nil {
+-		t.Logf("failed to exchange: %s", err.Error())
+-		t.Fail()
+-	}
+-}
+-
+-func TestServingResponse(t *testing.T) {
+-	if testing.Short() {
+-		t.Skip("skipping test in short mode.")
+-	}
+-	HandleFunc("miek.nl.", HelloServer)
+-	s, addrstr, err := RunLocalUDPServer("127.0.0.1:0")
+-	if err != nil {
+-		t.Fatalf("Unable to run test server: %s", err)
+-	}
+-
+-	c := new(Client)
+-	m := new(Msg)
+-	m.SetQuestion("miek.nl.", TypeTXT)
+-	m.Response = false
+-	_, _, err = c.Exchange(m, addrstr)
+-	if err != nil {
+-		t.Log("failed to exchange", err)
+-		t.Fatal()
+-	}
+-	m.Response = true
+-	_, _, err = c.Exchange(m, addrstr)
+-	if err == nil {
+-		t.Log("exchanged response message")
+-		t.Fatal()
+-	}
+-
+-	s.Shutdown()
+-	s, addrstr, err = RunLocalUDPServerUnsafe("127.0.0.1:0")
+-	if err != nil {
+-		t.Fatalf("Unable to run test server: %s", err)
+-	}
+-	defer s.Shutdown()
+-
+-	m.Response = true
+-	_, _, err = c.Exchange(m, addrstr)
+-	if err != nil {
+-		t.Log("could exchanged response message in Unsafe mode")
+-		t.Fatal()
+-	}
+-}
+-
+-func TestShutdownTCP(t *testing.T) {
+-	s, _, err := RunLocalTCPServer("127.0.0.1:0")
+-	if err != nil {
+-		t.Fatalf("Unable to run test server: %s", err)
+-	}
+-	err = s.Shutdown()
+-	if err != nil {
+-		t.Errorf("Could not shutdown test TCP server, %s", err)
+-	}
+-}
+-
+-func TestShutdownUDP(t *testing.T) {
+-	s, _, err := RunLocalUDPServer("127.0.0.1:0")
+-	if err != nil {
+-		t.Fatalf("Unable to run test server: %s", err)
+-	}
+-	err = s.Shutdown()
+-	if err != nil {
+-		t.Errorf("Could not shutdown test UDP server, %s", err)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/sig0.go b/Godeps/_workspace/src/github.com/miekg/dns/sig0.go
+deleted file mode 100644
+index d96b31b..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/sig0.go
++++ /dev/null
+@@ -1,262 +0,0 @@
+-// SIG(0)
+-//
+-// From RFC 2931:
+-//
+-//     SIG(0) provides protection for DNS transactions and requests ....
+-//     ... protection for glue records, DNS requests, protection for message headers
+-//     on requests and responses, and protection of the overall integrity of a response.
+-//
+-// It works like TSIG, except that SIG(0) uses public key cryptography, instead of the shared
+-// secret approach in TSIG.
+-// Supported algorithms: DSA, ECDSAP256SHA256, ECDSAP384SHA384, RSASHA1, RSASHA256 and
+-// RSASHA512.
+-//
+-// Signing subsequent messages in multi-message sessions is not implemented.
+-//
+-package dns
+-
+-import (
+-	"crypto"
+-	"crypto/dsa"
+-	"crypto/ecdsa"
+-	"crypto/rand"
+-	"crypto/rsa"
+-	"math/big"
+-	"strings"
+-	"time"
+-)
+-
+-// Sign signs a dns.Msg. It fills the signature with the appropriate data.
+-// The SIG record should have the SignerName, KeyTag, Algorithm, Inception
+-// and Expiration set.
+-func (rr *SIG) Sign(k PrivateKey, m *Msg) ([]byte, error) {
+-	if k == nil {
+-		return nil, ErrPrivKey
+-	}
+-	if rr.KeyTag == 0 || len(rr.SignerName) == 0 || rr.Algorithm == 0 {
+-		return nil, ErrKey
+-	}
+-	rr.Header().Rrtype = TypeSIG
+-	rr.Header().Class = ClassANY
+-	rr.Header().Ttl = 0
+-	rr.Header().Name = "."
+-	rr.OrigTtl = 0
+-	rr.TypeCovered = 0
+-	rr.Labels = 0
+-
+-	buf := make([]byte, m.Len()+rr.len())
+-	mbuf, err := m.PackBuffer(buf)
+-	if err != nil {
+-		return nil, err
+-	}
+-	if &buf[0] != &mbuf[0] {
+-		return nil, ErrBuf
+-	}
+-	off, err := PackRR(rr, buf, len(mbuf), nil, false)
+-	if err != nil {
+-		return nil, err
+-	}
+-	buf = buf[:off:cap(buf)]
+-	var hash crypto.Hash
+-	var intlen int
+-	switch rr.Algorithm {
+-	case DSA, RSASHA1:
+-		hash = crypto.SHA1
+-	case RSASHA256, ECDSAP256SHA256:
+-		hash = crypto.SHA256
+-		intlen = 32
+-	case ECDSAP384SHA384:
+-		hash = crypto.SHA384
+-		intlen = 48
+-	case RSASHA512:
+-		hash = crypto.SHA512
+-	default:
+-		return nil, ErrAlg
+-	}
+-	hasher := hash.New()
+-	// Write SIG rdata
+-	hasher.Write(buf[len(mbuf)+1+2+2+4+2:])
+-	// Write message
+-	hasher.Write(buf[:len(mbuf)])
+-	hashed := hasher.Sum(nil)
+-
+-	var sig []byte
+-	switch p := k.(type) {
+-	case *dsa.PrivateKey:
+-		t := divRoundUp(divRoundUp(p.PublicKey.Y.BitLen(), 8)-64, 8)
+-		r1, s1, err := dsa.Sign(rand.Reader, p, hashed)
+-		if err != nil {
+-			return nil, err
+-		}
+-		sig = append(sig, byte(t))
+-		sig = append(sig, intToBytes(r1, 20)...)
+-		sig = append(sig, intToBytes(s1, 20)...)
+-	case *rsa.PrivateKey:
+-		sig, err = rsa.SignPKCS1v15(rand.Reader, p, hash, hashed)
+-		if err != nil {
+-			return nil, err
+-		}
+-	case *ecdsa.PrivateKey:
+-		r1, s1, err := ecdsa.Sign(rand.Reader, p, hashed)
+-		if err != nil {
+-			return nil, err
+-		}
+-		sig = intToBytes(r1, intlen)
+-		sig = append(sig, intToBytes(s1, intlen)...)
+-	default:
+-		return nil, ErrAlg
+-	}
+-	rr.Signature = toBase64(sig)
+-	buf = append(buf, sig...)
+-	if len(buf) > int(^uint16(0)) {
+-		return nil, ErrBuf
+-	}
+-	// Adjust sig data length
+-	rdoff := len(mbuf) + 1 + 2 + 2 + 4
+-	rdlen, _ := unpackUint16(buf, rdoff)
+-	rdlen += uint16(len(sig))
+-	buf[rdoff], buf[rdoff+1] = packUint16(rdlen)
+-	// Adjust additional count
+-	adc, _ := unpackUint16(buf, 10)
+-	adc += 1
+-	buf[10], buf[11] = packUint16(adc)
+-	return buf, nil
+-}
+-
+-// Verify validates the message buf using the key k.
+-// It's assumed that buf is a valid message from which rr was unpacked.
+-func (rr *SIG) Verify(k *KEY, buf []byte) error {
+-	if k == nil {
+-		return ErrKey
+-	}
+-	if rr.KeyTag == 0 || len(rr.SignerName) == 0 || rr.Algorithm == 0 {
+-		return ErrKey
+-	}
+-
+-	var hash crypto.Hash
+-	switch rr.Algorithm {
+-	case DSA, RSASHA1:
+-		hash = crypto.SHA1
+-	case RSASHA256, ECDSAP256SHA256:
+-		hash = crypto.SHA256
+-	case ECDSAP384SHA384:
+-		hash = crypto.SHA384
+-	case RSASHA512:
+-		hash = crypto.SHA512
+-	default:
+-		return ErrAlg
+-	}
+-	hasher := hash.New()
+-
+-	buflen := len(buf)
+-	qdc, _ := unpackUint16(buf, 4)
+-	anc, _ := unpackUint16(buf, 6)
+-	auc, _ := unpackUint16(buf, 8)
+-	adc, offset := unpackUint16(buf, 10)
+-	var err error
+-	for i := uint16(0); i < qdc && offset < buflen; i++ {
+-		_, offset, err = UnpackDomainName(buf, offset)
+-		if err != nil {
+-			return err
+-		}
+-		// Skip past Type and Class
+-		offset += 2 + 2
+-	}
+-	for i := uint16(1); i < anc+auc+adc && offset < buflen; i++ {
+-		_, offset, err = UnpackDomainName(buf, offset)
+-		if err != nil {
+-			return err
+-		}
+-		// Skip past Type, Class and TTL
+-		offset += 2 + 2 + 4
+-		if offset+1 >= buflen {
+-			continue
+-		}
+-		var rdlen uint16
+-		rdlen, offset = unpackUint16(buf, offset)
+-		offset += int(rdlen)
+-	}
+-	if offset >= buflen {
+-		return &Error{err: "overflowing unpacking signed message"}
+-	}
+-
+-	// offset should be just prior to SIG
+-	bodyend := offset
+-	// owner name SHOULD be root
+-	_, offset, err = UnpackDomainName(buf, offset)
+-	if err != nil {
+-		return err
+-	}
+-	// Skip Type, Class, TTL, RDLen
+-	offset += 2 + 2 + 4 + 2
+-	sigstart := offset
+-	// Skip Type Covered, Algorithm, Labels, Original TTL
+-	offset += 2 + 1 + 1 + 4
+-	if offset+4+4 >= buflen {
+-		return &Error{err: "overflow unpacking signed message"}
+-	}
+-	expire := uint32(buf[offset])<<24 | uint32(buf[offset+1])<<16 | uint32(buf[offset+2])<<8 | uint32(buf[offset+3])
+-	offset += 4
+-	incept := uint32(buf[offset])<<24 | uint32(buf[offset+1])<<16 | uint32(buf[offset+2])<<8 | uint32(buf[offset+3])
+-	offset += 4
+-	now := uint32(time.Now().Unix())
+-	if now < incept || now > expire {
+-		return ErrTime
+-	}
+-	// Skip key tag
+-	offset += 2
+-	var signername string
+-	signername, offset, err = UnpackDomainName(buf, offset)
+-	if err != nil {
+-		return err
+-	}
+-	// If key has come from the DNS name compression might
+-	// have mangled the case of the name
+-	if strings.ToLower(signername) != strings.ToLower(k.Header().Name) {
+-		return &Error{err: "signer name doesn't match key name"}
+-	}
+-	sigend := offset
+-	hasher.Write(buf[sigstart:sigend])
+-	hasher.Write(buf[:10])
+-	hasher.Write([]byte{
+-		byte((adc - 1) << 8),
+-		byte(adc - 1),
+-	})
+-	hasher.Write(buf[12:bodyend])
+-
+-	hashed := hasher.Sum(nil)
+-	sig := buf[sigend:]
+-	switch k.Algorithm {
+-	case DSA:
+-		pk := k.publicKeyDSA()
+-		sig = sig[1:]
+-		r := big.NewInt(0)
+-		r.SetBytes(sig[:len(sig)/2])
+-		s := big.NewInt(0)
+-		s.SetBytes(sig[len(sig)/2:])
+-		if pk != nil {
+-			if dsa.Verify(pk, hashed, r, s) {
+-				return nil
+-			}
+-			return ErrSig
+-		}
+-	case RSASHA1, RSASHA256, RSASHA512:
+-		pk := k.publicKeyRSA()
+-		if pk != nil {
+-			return rsa.VerifyPKCS1v15(pk, hash, hashed, sig)
+-		}
+-	case ECDSAP256SHA256, ECDSAP384SHA384:
+-		pk := k.publicKeyCurve()
+-		r := big.NewInt(0)
+-		r.SetBytes(sig[:len(sig)/2])
+-		s := big.NewInt(0)
+-		s.SetBytes(sig[len(sig)/2:])
+-		if pk != nil {
+-			if ecdsa.Verify(pk, hashed, r, s) {
+-				return nil
+-			}
+-			return ErrSig
+-		}
+-	}
+-	return ErrKeyAlg
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/sig0_test.go b/Godeps/_workspace/src/github.com/miekg/dns/sig0_test.go
+deleted file mode 100644
+index 6ca76fb..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/sig0_test.go
++++ /dev/null
+@@ -1,96 +0,0 @@
+-package dns
+-
+-import (
+-	"testing"
+-	"time"
+-)
+-
+-func TestSIG0(t *testing.T) {
+-	if testing.Short() {
+-		t.Skip("skipping test in short mode.")
+-	}
+-	m := new(Msg)
+-	m.SetQuestion("example.org.", TypeSOA)
+-	for _, alg := range []uint8{DSA, ECDSAP256SHA256, ECDSAP384SHA384, RSASHA1, RSASHA256, RSASHA512} {
+-		algstr := AlgorithmToString[alg]
+-		keyrr := new(KEY)
+-		keyrr.Hdr.Name = algstr + "."
+-		keyrr.Hdr.Rrtype = TypeKEY
+-		keyrr.Hdr.Class = ClassINET
+-		keyrr.Algorithm = alg
+-		keysize := 1024
+-		switch alg {
+-		case ECDSAP256SHA256:
+-			keysize = 256
+-		case ECDSAP384SHA384:
+-			keysize = 384
+-		}
+-		pk, err := keyrr.Generate(keysize)
+-		if err != nil {
+-			t.Logf("Failed to generate key for “%s”: %v", algstr, err)
+-			t.Fail()
+-			continue
+-		}
+-		now := uint32(time.Now().Unix())
+-		sigrr := new(SIG)
+-		sigrr.Hdr.Name = "."
+-		sigrr.Hdr.Rrtype = TypeSIG
+-		sigrr.Hdr.Class = ClassANY
+-		sigrr.Algorithm = alg
+-		sigrr.Expiration = now + 300
+-		sigrr.Inception = now - 300
+-		sigrr.KeyTag = keyrr.KeyTag()
+-		sigrr.SignerName = keyrr.Hdr.Name
+-		mb, err := sigrr.Sign(pk, m)
+-		if err != nil {
+-			t.Logf("Failed to sign message using “%s”: %v", algstr, err)
+-			t.Fail()
+-			continue
+-		}
+-		m := new(Msg)
+-		if err := m.Unpack(mb); err != nil {
+-			t.Logf("Failed to unpack message signed using “%s”: %v", algstr, err)
+-			t.Fail()
+-			continue
+-		}
+-		if len(m.Extra) != 1 {
+-			t.Logf("Missing SIG for message signed using “%s”", algstr)
+-			t.Fail()
+-			continue
+-		}
+-		var sigrrwire *SIG
+-		switch rr := m.Extra[0].(type) {
+-		case *SIG:
+-			sigrrwire = rr
+-		default:
+-			t.Logf("Expected SIG RR, instead: %v", rr)
+-			t.Fail()
+-			continue
+-		}
+-		for _, rr := range []*SIG{sigrr, sigrrwire} {
+-			id := "sigrr"
+-			if rr == sigrrwire {
+-				id = "sigrrwire"
+-			}
+-			if err := rr.Verify(keyrr, mb); err != nil {
+-				t.Logf("Failed to verify “%s” signed SIG(%s): %v", algstr, id, err)
+-				t.Fail()
+-				continue
+-			}
+-		}
+-		mb[13]++
+-		if err := sigrr.Verify(keyrr, mb); err == nil {
+-			t.Logf("Verify succeeded on an altered message using “%s”", algstr)
+-			t.Fail()
+-			continue
+-		}
+-		sigrr.Expiration = 2
+-		sigrr.Inception = 1
+-		mb, _ = sigrr.Sign(pk, m)
+-		if err := sigrr.Verify(keyrr, mb); err == nil {
+-			t.Logf("Verify succeeded on an expired message using “%s”", algstr)
+-			t.Fail()
+-			continue
+-		}
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/singleinflight.go b/Godeps/_workspace/src/github.com/miekg/dns/singleinflight.go
+deleted file mode 100644
+index 9573c7d..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/singleinflight.go
++++ /dev/null
+@@ -1,57 +0,0 @@
+-// Copyright 2013 The Go Authors.  All rights reserved.
+-// Use of this source code is governed by a BSD-style
+-// license that can be found in the LICENSE file.
+-
+-// Adapted for dns package usage by Miek Gieben.
+-
+-package dns
+-
+-import "sync"
+-import "time"
+-
+-// call is an in-flight or completed singleflight.Do call
+-type call struct {
+-	wg   sync.WaitGroup
+-	val  *Msg
+-	rtt  time.Duration
+-	err  error
+-	dups int
+-}
+-
+-// singleflight represents a class of work and forms a namespace in
+-// which units of work can be executed with duplicate suppression.
+-type singleflight struct {
+-	sync.Mutex                  // protects m
+-	m          map[string]*call // lazily initialized
+-}
+-
+-// Do executes and returns the results of the given function, making
+-// sure that only one execution is in-flight for a given key at a
+-// time. If a duplicate comes in, the duplicate caller waits for the
+-// original to complete and receives the same results.
+-// The return value shared indicates whether v was given to multiple callers.
+-func (g *singleflight) Do(key string, fn func() (*Msg, time.Duration, error)) (v *Msg, rtt time.Duration, err error, shared bool) {
+-	g.Lock()
+-	if g.m == nil {
+-		g.m = make(map[string]*call)
+-	}
+-	if c, ok := g.m[key]; ok {
+-		c.dups++
+-		g.Unlock()
+-		c.wg.Wait()
+-		return c.val, c.rtt, c.err, true
+-	}
+-	c := new(call)
+-	c.wg.Add(1)
+-	g.m[key] = c
+-	g.Unlock()
+-
+-	c.val, c.rtt, c.err = fn()
+-	c.wg.Done()
+-
+-	g.Lock()
+-	delete(g.m, key)
+-	g.Unlock()
+-
+-	return c.val, c.rtt, c.err, c.dups > 0
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/tlsa.go b/Godeps/_workspace/src/github.com/miekg/dns/tlsa.go
+deleted file mode 100644
+index d3bc3b0..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/tlsa.go
++++ /dev/null
+@@ -1,84 +0,0 @@
+-package dns
+-
+-import (
+-	"crypto/sha256"
+-	"crypto/sha512"
+-	"crypto/x509"
+-	"encoding/hex"
+-	"errors"
+-	"io"
+-	"net"
+-	"strconv"
+-)
+-
+-// CertificateToDANE converts a certificate to a hex string as used in the TLSA record.
+-func CertificateToDANE(selector, matchingType uint8, cert *x509.Certificate) (string, error) {
+-	switch matchingType {
+-	case 0:
+-		switch selector {
+-		case 0:
+-			return hex.EncodeToString(cert.Raw), nil
+-		case 1:
+-			return hex.EncodeToString(cert.RawSubjectPublicKeyInfo), nil
+-		}
+-	case 1:
+-		h := sha256.New()
+-		switch selector {
+-		case 0:
+-			return hex.EncodeToString(cert.Raw), nil
+-		case 1:
+-			io.WriteString(h, string(cert.RawSubjectPublicKeyInfo))
+-			return hex.EncodeToString(h.Sum(nil)), nil
+-		}
+-	case 2:
+-		h := sha512.New()
+-		switch selector {
+-		case 0:
+-			return hex.EncodeToString(cert.Raw), nil
+-		case 1:
+-			io.WriteString(h, string(cert.RawSubjectPublicKeyInfo))
+-			return hex.EncodeToString(h.Sum(nil)), nil
+-		}
+-	}
+-	return "", errors.New("dns: bad TLSA MatchingType or TLSA Selector")
+-}
+-
+-// Sign creates a TLSA record from an SSL certificate.
+-func (r *TLSA) Sign(usage, selector, matchingType int, cert *x509.Certificate) (err error) {
+-	r.Hdr.Rrtype = TypeTLSA
+-	r.Usage = uint8(usage)
+-	r.Selector = uint8(selector)
+-	r.MatchingType = uint8(matchingType)
+-
+-	r.Certificate, err = CertificateToDANE(r.Selector, r.MatchingType, cert)
+-	if err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-// Verify verifies a TLSA record against an SSL certificate. If it is OK
+-// a nil error is returned.
+-func (r *TLSA) Verify(cert *x509.Certificate) error {
+-	c, err := CertificateToDANE(r.Selector, r.MatchingType, cert)
+-	if err != nil {
+-		return err // Not also ErrSig?
+-	}
+-	if r.Certificate == c {
+-		return nil
+-	}
+-	return ErrSig // ErrSig, really?
+-}
+-
+-// TLSAName returns the ownername of a TLSA resource record as per the
+-// rules specified in RFC 6698, Section 3.
+-func TLSAName(name, service, network string) (string, error) {
+-	if !IsFqdn(name) {
+-		return "", ErrFqdn
+-	}
+-	p, e := net.LookupPort(network, service)
+-	if e != nil {
+-		return "", e
+-	}
+-	return "_" + strconv.Itoa(p) + "_" + network + "." + name, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/tsig.go b/Godeps/_workspace/src/github.com/miekg/dns/tsig.go
+deleted file mode 100644
+index 2c64ee8..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/tsig.go
++++ /dev/null
+@@ -1,378 +0,0 @@
+-// TRANSACTION SIGNATURE
+-//
+-// An TSIG or transaction signature adds a HMAC TSIG record to each message sent.
+-// The supported algorithms include: HmacMD5, HmacSHA1 and HmacSHA256.
+-//
+-// Basic use pattern when querying with a TSIG name "axfr." (note that these key names
+-// must be fully qualified - as they are domain names) and the base64 secret
+-// "so6ZGir4GPAqINNh9U5c3A==":
+-//
+-//	c := new(dns.Client)
+-//	c.TsigSecret = map[string]string{"axfr.": "so6ZGir4GPAqINNh9U5c3A=="}
+-//	m := new(dns.Msg)
+-//	m.SetQuestion("miek.nl.", dns.TypeMX)
+-//	m.SetTsig("axfr.", dns.HmacMD5, 300, time.Now().Unix())
+-//	...
+-//	// When sending the TSIG RR is calculated and filled in before sending
+-//
+-// When requesting an zone transfer (almost all TSIG usage is when requesting zone transfers), with
+-// TSIG, this is the basic use pattern. In this example we request an AXFR for
+-// miek.nl. with TSIG key named "axfr." and secret "so6ZGir4GPAqINNh9U5c3A=="
+-// and using the server 176.58.119.54:
+-//
+-//	t := new(dns.Transfer)
+-//	m := new(dns.Msg)
+-//	t.TsigSecret = map[string]string{"axfr.": "so6ZGir4GPAqINNh9U5c3A=="}
+-//	m.SetAxfr("miek.nl.")
+-//	m.SetTsig("axfr.", dns.HmacMD5, 300, time.Now().Unix())
+-//	c, err := t.In(m, "176.58.119.54:53")
+-//	for r := range c { /* r.RR */ }
+-//
+-// You can now read the records from the transfer as they come in. Each envelope is checked with TSIG.
+-// If something is not correct an error is returned.
+-//
+-// Basic use pattern validating and replying to a message that has TSIG set.
+-//
+-//	server := &dns.Server{Addr: ":53", Net: "udp"}
+-//	server.TsigSecret = map[string]string{"axfr.": "so6ZGir4GPAqINNh9U5c3A=="}
+-//	go server.ListenAndServe()
+-//	dns.HandleFunc(".", handleRequest)
+-//
+-// 	func handleRequest(w dns.ResponseWriter, r *dns.Msg) {
+-//		m := new(Msg)
+-//		m.SetReply(r)
+-//		if r.IsTsig() {
+-//			if w.TsigStatus() == nil {
+-//				// *Msg r has an TSIG record and it was validated
+-//				m.SetTsig("axfr.", dns.HmacMD5, 300, time.Now().Unix())
+-//			} else {
+-//				// *Msg r has an TSIG records and it was not valided
+-//			}
+-//		}
+-//		w.WriteMsg(m)
+-//	}
+-package dns
+-
+-import (
+-	"crypto/hmac"
+-	"crypto/md5"
+-	"crypto/sha1"
+-	"crypto/sha256"
+-	"encoding/hex"
+-	"hash"
+-	"io"
+-	"strconv"
+-	"strings"
+-	"time"
+-)
+-
+-// HMAC hashing codes. These are transmitted as domain names.
+-const (
+-	HmacMD5    = "hmac-md5.sig-alg.reg.int."
+-	HmacSHA1   = "hmac-sha1."
+-	HmacSHA256 = "hmac-sha256."
+-)
+-
+-type TSIG struct {
+-	Hdr        RR_Header
+-	Algorithm  string `dns:"domain-name"`
+-	TimeSigned uint64 `dns:"uint48"`
+-	Fudge      uint16
+-	MACSize    uint16
+-	MAC        string `dns:"size-hex"`
+-	OrigId     uint16
+-	Error      uint16
+-	OtherLen   uint16
+-	OtherData  string `dns:"size-hex"`
+-}
+-
+-func (rr *TSIG) Header() *RR_Header {
+-	return &rr.Hdr
+-}
+-
+-// TSIG has no official presentation format, but this will suffice.
+-
+-func (rr *TSIG) String() string {
+-	s := "\n;; TSIG PSEUDOSECTION:\n"
+-	s += rr.Hdr.String() +
+-		" " + rr.Algorithm +
+-		" " + tsigTimeToString(rr.TimeSigned) +
+-		" " + strconv.Itoa(int(rr.Fudge)) +
+-		" " + strconv.Itoa(int(rr.MACSize)) +
+-		" " + strings.ToUpper(rr.MAC) +
+-		" " + strconv.Itoa(int(rr.OrigId)) +
+-		" " + strconv.Itoa(int(rr.Error)) + // BIND prints NOERROR
+-		" " + strconv.Itoa(int(rr.OtherLen)) +
+-		" " + rr.OtherData
+-	return s
+-}
+-
+-func (rr *TSIG) len() int {
+-	return rr.Hdr.len() + len(rr.Algorithm) + 1 + 6 +
+-		4 + len(rr.MAC)/2 + 1 + 6 + len(rr.OtherData)/2 + 1
+-}
+-
+-func (rr *TSIG) copy() RR {
+-	return &TSIG{*rr.Hdr.copyHeader(), rr.Algorithm, rr.TimeSigned, rr.Fudge, rr.MACSize, rr.MAC, rr.OrigId, rr.Error, rr.OtherLen, rr.OtherData}
+-}
+-
+-// The following values must be put in wireformat, so that the MAC can be calculated.
+-// RFC 2845, section 3.4.2. TSIG Variables.
+-type tsigWireFmt struct {
+-	// From RR_Header
+-	Name  string `dns:"domain-name"`
+-	Class uint16
+-	Ttl   uint32
+-	// Rdata of the TSIG
+-	Algorithm  string `dns:"domain-name"`
+-	TimeSigned uint64 `dns:"uint48"`
+-	Fudge      uint16
+-	// MACSize, MAC and OrigId excluded
+-	Error     uint16
+-	OtherLen  uint16
+-	OtherData string `dns:"size-hex"`
+-}
+-
+-// If we have the MAC use this type to convert it to wiredata.
+-// Section 3.4.3. Request MAC
+-type macWireFmt struct {
+-	MACSize uint16
+-	MAC     string `dns:"size-hex"`
+-}
+-
+-// 3.3. Time values used in TSIG calculations
+-type timerWireFmt struct {
+-	TimeSigned uint64 `dns:"uint48"`
+-	Fudge      uint16
+-}
+-
+-// TsigGenerate fills out the TSIG record attached to the message.
+-// The message should contain
+-// a "stub" TSIG RR with the algorithm, key name (owner name of the RR),
+-// time fudge (defaults to 300 seconds) and the current time
+-// The TSIG MAC is saved in that Tsig RR.
+-// When TsigGenerate is called for the first time requestMAC is set to the empty string and
+-// timersOnly is false.
+-// If something goes wrong an error is returned, otherwise it is nil.
+-func TsigGenerate(m *Msg, secret, requestMAC string, timersOnly bool) ([]byte, string, error) {
+-	if m.IsTsig() == nil {
+-		panic("dns: TSIG not last RR in additional")
+-	}
+-	// If we barf here, the caller is to blame
+-	rawsecret, err := fromBase64([]byte(secret))
+-	if err != nil {
+-		return nil, "", err
+-	}
+-
+-	rr := m.Extra[len(m.Extra)-1].(*TSIG)
+-	m.Extra = m.Extra[0 : len(m.Extra)-1] // kill the TSIG from the msg
+-	mbuf, err := m.Pack()
+-	if err != nil {
+-		return nil, "", err
+-	}
+-	buf := tsigBuffer(mbuf, rr, requestMAC, timersOnly)
+-
+-	t := new(TSIG)
+-	var h hash.Hash
+-	switch rr.Algorithm {
+-	case HmacMD5:
+-		h = hmac.New(md5.New, []byte(rawsecret))
+-	case HmacSHA1:
+-		h = hmac.New(sha1.New, []byte(rawsecret))
+-	case HmacSHA256:
+-		h = hmac.New(sha256.New, []byte(rawsecret))
+-	default:
+-		return nil, "", ErrKeyAlg
+-	}
+-	io.WriteString(h, string(buf))
+-	t.MAC = hex.EncodeToString(h.Sum(nil))
+-	t.MACSize = uint16(len(t.MAC) / 2) // Size is half!
+-
+-	t.Hdr = RR_Header{Name: rr.Hdr.Name, Rrtype: TypeTSIG, Class: ClassANY, Ttl: 0}
+-	t.Fudge = rr.Fudge
+-	t.TimeSigned = rr.TimeSigned
+-	t.Algorithm = rr.Algorithm
+-	t.OrigId = m.Id
+-
+-	tbuf := make([]byte, t.len())
+-	if off, err := PackRR(t, tbuf, 0, nil, false); err == nil {
+-		tbuf = tbuf[:off] // reset to actual size used
+-	} else {
+-		return nil, "", err
+-	}
+-	mbuf = append(mbuf, tbuf...)
+-	rawSetExtraLen(mbuf, uint16(len(m.Extra)+1))
+-	return mbuf, t.MAC, nil
+-}
+-
+-// TsigVerify verifies the TSIG on a message.
+-// If the signature does not validate err contains the
+-// error, otherwise it is nil.
+-func TsigVerify(msg []byte, secret, requestMAC string, timersOnly bool) error {
+-	rawsecret, err := fromBase64([]byte(secret))
+-	if err != nil {
+-		return err
+-	}
+-	// Strip the TSIG from the incoming msg
+-	stripped, tsig, err := stripTsig(msg)
+-	if err != nil {
+-		return err
+-	}
+-
+-	msgMAC, err := hex.DecodeString(tsig.MAC)
+-	if err != nil {
+-		return err
+-	}
+-
+-	buf := tsigBuffer(stripped, tsig, requestMAC, timersOnly)
+-
+-	// Fudge factor works both ways. A message can arrive before it was signed because
+-	// of clock skew.
+-	now := uint64(time.Now().Unix())
+-	ti := now - tsig.TimeSigned
+-	if now < tsig.TimeSigned {
+-		ti = tsig.TimeSigned - now
+-	}
+-	if uint64(tsig.Fudge) < ti {
+-		return ErrTime
+-	}
+-
+-	var h hash.Hash
+-	switch tsig.Algorithm {
+-	case HmacMD5:
+-		h = hmac.New(md5.New, rawsecret)
+-	case HmacSHA1:
+-		h = hmac.New(sha1.New, rawsecret)
+-	case HmacSHA256:
+-		h = hmac.New(sha256.New, rawsecret)
+-	default:
+-		return ErrKeyAlg
+-	}
+-	h.Write(buf)
+-	if !hmac.Equal(h.Sum(nil), msgMAC) {
+-		return ErrSig
+-	}
+-	return nil
+-}
+-
+-// Create a wiredata buffer for the MAC calculation.
+-func tsigBuffer(msgbuf []byte, rr *TSIG, requestMAC string, timersOnly bool) []byte {
+-	var buf []byte
+-	if rr.TimeSigned == 0 {
+-		rr.TimeSigned = uint64(time.Now().Unix())
+-	}
+-	if rr.Fudge == 0 {
+-		rr.Fudge = 300 // Standard (RFC) default.
+-	}
+-
+-	if requestMAC != "" {
+-		m := new(macWireFmt)
+-		m.MACSize = uint16(len(requestMAC) / 2)
+-		m.MAC = requestMAC
+-		buf = make([]byte, len(requestMAC)) // long enough
+-		n, _ := PackStruct(m, buf, 0)
+-		buf = buf[:n]
+-	}
+-
+-	tsigvar := make([]byte, DefaultMsgSize)
+-	if timersOnly {
+-		tsig := new(timerWireFmt)
+-		tsig.TimeSigned = rr.TimeSigned
+-		tsig.Fudge = rr.Fudge
+-		n, _ := PackStruct(tsig, tsigvar, 0)
+-		tsigvar = tsigvar[:n]
+-	} else {
+-		tsig := new(tsigWireFmt)
+-		tsig.Name = strings.ToLower(rr.Hdr.Name)
+-		tsig.Class = ClassANY
+-		tsig.Ttl = rr.Hdr.Ttl
+-		tsig.Algorithm = strings.ToLower(rr.Algorithm)
+-		tsig.TimeSigned = rr.TimeSigned
+-		tsig.Fudge = rr.Fudge
+-		tsig.Error = rr.Error
+-		tsig.OtherLen = rr.OtherLen
+-		tsig.OtherData = rr.OtherData
+-		n, _ := PackStruct(tsig, tsigvar, 0)
+-		tsigvar = tsigvar[:n]
+-	}
+-
+-	if requestMAC != "" {
+-		x := append(buf, msgbuf...)
+-		buf = append(x, tsigvar...)
+-	} else {
+-		buf = append(msgbuf, tsigvar...)
+-	}
+-	return buf
+-}
+-
+-// Strip the TSIG from the raw message.
+-func stripTsig(msg []byte) ([]byte, *TSIG, error) {
+-	// Copied from msg.go's Unpack()
+-	// Header.
+-	var dh Header
+-	var err error
+-	dns := new(Msg)
+-	rr := new(TSIG)
+-	off := 0
+-	tsigoff := 0
+-	if off, err = UnpackStruct(&dh, msg, off); err != nil {
+-		return nil, nil, err
+-	}
+-	if dh.Arcount == 0 {
+-		return nil, nil, ErrNoSig
+-	}
+-	// Rcode, see msg.go Unpack()
+-	if int(dh.Bits&0xF) == RcodeNotAuth {
+-		return nil, nil, ErrAuth
+-	}
+-
+-	// Arrays.
+-	dns.Question = make([]Question, dh.Qdcount)
+-	dns.Answer = make([]RR, dh.Ancount)
+-	dns.Ns = make([]RR, dh.Nscount)
+-	dns.Extra = make([]RR, dh.Arcount)
+-
+-	for i := 0; i < len(dns.Question); i++ {
+-		off, err = UnpackStruct(&dns.Question[i], msg, off)
+-		if err != nil {
+-			return nil, nil, err
+-		}
+-	}
+-	for i := 0; i < len(dns.Answer); i++ {
+-		dns.Answer[i], off, err = UnpackRR(msg, off)
+-		if err != nil {
+-			return nil, nil, err
+-		}
+-	}
+-	for i := 0; i < len(dns.Ns); i++ {
+-		dns.Ns[i], off, err = UnpackRR(msg, off)
+-		if err != nil {
+-			return nil, nil, err
+-		}
+-	}
+-	for i := 0; i < len(dns.Extra); i++ {
+-		tsigoff = off
+-		dns.Extra[i], off, err = UnpackRR(msg, off)
+-		if err != nil {
+-			return nil, nil, err
+-		}
+-		if dns.Extra[i].Header().Rrtype == TypeTSIG {
+-			rr = dns.Extra[i].(*TSIG)
+-			// Adjust Arcount.
+-			arcount, _ := unpackUint16(msg, 10)
+-			msg[10], msg[11] = packUint16(arcount - 1)
+-			break
+-		}
+-	}
+-	if rr == nil {
+-		return nil, nil, ErrNoSig
+-	}
+-	return msg[:tsigoff], rr, nil
+-}
+-
+-// Translate the TSIG time signed into a date. There is no
+-// need for RFC1982 calculations as this date is 48 bits.
+-func tsigTimeToString(t uint64) string {
+-	ti := time.Unix(int64(t), 0).UTC()
+-	return ti.Format("20060102150405")
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/types.go b/Godeps/_workspace/src/github.com/miekg/dns/types.go
+deleted file mode 100644
+index 16bb181..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/types.go
++++ /dev/null
+@@ -1,1697 +0,0 @@
+-package dns
+-
+-import (
+-	"encoding/base64"
+-	"fmt"
+-	"net"
+-	"strconv"
+-	"strings"
+-	"time"
+-)
+-
+-type (
+-	Type  uint16 // Type is a DNS type.
+-	Class uint16 // Class is a DNS class.
+-	Name  string // Name is a DNS domain name.
+-)
+-
+-// Packet formats
+-
+-// Wire constants and supported types.
+-const (
+-	// valid RR_Header.Rrtype and Question.qtype
+-	TypeNone       uint16 = 0
+-	TypeA          uint16 = 1
+-	TypeNS         uint16 = 2
+-	TypeMD         uint16 = 3
+-	TypeMF         uint16 = 4
+-	TypeCNAME      uint16 = 5
+-	TypeSOA        uint16 = 6
+-	TypeMB         uint16 = 7
+-	TypeMG         uint16 = 8
+-	TypeMR         uint16 = 9
+-	TypeNULL       uint16 = 10
+-	TypeWKS        uint16 = 11
+-	TypePTR        uint16 = 12
+-	TypeHINFO      uint16 = 13
+-	TypeMINFO      uint16 = 14
+-	TypeMX         uint16 = 15
+-	TypeTXT        uint16 = 16
+-	TypeRP         uint16 = 17
+-	TypeAFSDB      uint16 = 18
+-	TypeX25        uint16 = 19
+-	TypeISDN       uint16 = 20
+-	TypeRT         uint16 = 21
+-	TypeNSAP       uint16 = 22
+-	TypeNSAPPTR    uint16 = 23
+-	TypeSIG        uint16 = 24
+-	TypeKEY        uint16 = 25
+-	TypePX         uint16 = 26
+-	TypeGPOS       uint16 = 27
+-	TypeAAAA       uint16 = 28
+-	TypeLOC        uint16 = 29
+-	TypeNXT        uint16 = 30
+-	TypeEID        uint16 = 31
+-	TypeNIMLOC     uint16 = 32
+-	TypeSRV        uint16 = 33
+-	TypeATMA       uint16 = 34
+-	TypeNAPTR      uint16 = 35
+-	TypeKX         uint16 = 36
+-	TypeCERT       uint16 = 37
+-	TypeDNAME      uint16 = 39
+-	TypeOPT        uint16 = 41 // EDNS
+-	TypeDS         uint16 = 43
+-	TypeSSHFP      uint16 = 44
+-	TypeIPSECKEY   uint16 = 45
+-	TypeRRSIG      uint16 = 46
+-	TypeNSEC       uint16 = 47
+-	TypeDNSKEY     uint16 = 48
+-	TypeDHCID      uint16 = 49
+-	TypeNSEC3      uint16 = 50
+-	TypeNSEC3PARAM uint16 = 51
+-	TypeTLSA       uint16 = 52
+-	TypeHIP        uint16 = 55
+-	TypeNINFO      uint16 = 56
+-	TypeRKEY       uint16 = 57
+-	TypeTALINK     uint16 = 58
+-	TypeCDS        uint16 = 59
+-	TypeCDNSKEY    uint16 = 60
+-	TypeOPENPGPKEY uint16 = 61
+-	TypeSPF        uint16 = 99
+-	TypeUINFO      uint16 = 100
+-	TypeUID        uint16 = 101
+-	TypeGID        uint16 = 102
+-	TypeUNSPEC     uint16 = 103
+-	TypeNID        uint16 = 104
+-	TypeL32        uint16 = 105
+-	TypeL64        uint16 = 106
+-	TypeLP         uint16 = 107
+-	TypeEUI48      uint16 = 108
+-	TypeEUI64      uint16 = 109
+-
+-	TypeTKEY uint16 = 249
+-	TypeTSIG uint16 = 250
+-	// valid Question.Qtype only
+-	TypeIXFR  uint16 = 251
+-	TypeAXFR  uint16 = 252
+-	TypeMAILB uint16 = 253
+-	TypeMAILA uint16 = 254
+-	TypeANY   uint16 = 255
+-
+-	TypeURI      uint16 = 256
+-	TypeCAA      uint16 = 257
+-	TypeTA       uint16 = 32768
+-	TypeDLV      uint16 = 32769
+-	TypeReserved uint16 = 65535
+-
+-	// valid Question.Qclass
+-	ClassINET   = 1
+-	ClassCSNET  = 2
+-	ClassCHAOS  = 3
+-	ClassHESIOD = 4
+-	ClassNONE   = 254
+-	ClassANY    = 255
+-
+-	// Msg.rcode
+-	RcodeSuccess        = 0
+-	RcodeFormatError    = 1
+-	RcodeServerFailure  = 2
+-	RcodeNameError      = 3
+-	RcodeNotImplemented = 4
+-	RcodeRefused        = 5
+-	RcodeYXDomain       = 6
+-	RcodeYXRrset        = 7
+-	RcodeNXRrset        = 8
+-	RcodeNotAuth        = 9
+-	RcodeNotZone        = 10
+-	RcodeBadSig         = 16 // TSIG
+-	RcodeBadVers        = 16 // EDNS0
+-	RcodeBadKey         = 17
+-	RcodeBadTime        = 18
+-	RcodeBadMode        = 19 // TKEY
+-	RcodeBadName        = 20
+-	RcodeBadAlg         = 21
+-	RcodeBadTrunc       = 22 // TSIG
+-
+-	// Opcode
+-	OpcodeQuery  = 0
+-	OpcodeIQuery = 1
+-	OpcodeStatus = 2
+-	// There is no 3
+-	OpcodeNotify = 4
+-	OpcodeUpdate = 5
+-)
+-
+-// The wire format for the DNS packet header.
+-type Header struct {
+-	Id                                 uint16
+-	Bits                               uint16
+-	Qdcount, Ancount, Nscount, Arcount uint16
+-}
+-
+-const (
+-	// Header.Bits
+-	_QR = 1 << 15 // query/response (response=1)
+-	_AA = 1 << 10 // authoritative
+-	_TC = 1 << 9  // truncated
+-	_RD = 1 << 8  // recursion desired
+-	_RA = 1 << 7  // recursion available
+-	_Z  = 1 << 6  // Z
+-	_AD = 1 << 5  // authticated data
+-	_CD = 1 << 4  // checking disabled
+-
+-	LOC_EQUATOR       = 1 << 31 // RFC 1876, Section 2.
+-	LOC_PRIMEMERIDIAN = 1 << 31 // RFC 1876, Section 2.
+-
+-	LOC_HOURS   = 60 * 1000
+-	LOC_DEGREES = 60 * LOC_HOURS
+-
+-	LOC_ALTITUDEBASE = 100000
+-)
+-
+-// RFC 4398, Section 2.1
+-const (
+-	CertPKIX = 1 + iota
+-	CertSPKI
+-	CertPGP
+-	CertIPIX
+-	CertISPKI
+-	CertIPGP
+-	CertACPKIX
+-	CertIACPKIX
+-	CertURI = 253
+-	CertOID = 254
+-)
+-
+-var CertTypeToString = map[uint16]string{
+-	CertPKIX:    "PKIX",
+-	CertSPKI:    "SPKI",
+-	CertPGP:     "PGP",
+-	CertIPIX:    "IPIX",
+-	CertISPKI:   "ISPKI",
+-	CertIPGP:    "IPGP",
+-	CertACPKIX:  "ACPKIX",
+-	CertIACPKIX: "IACPKIX",
+-	CertURI:     "URI",
+-	CertOID:     "OID",
+-}
+-
+-var StringToCertType = reverseInt16(CertTypeToString)
+-
+-// DNS queries.
+-type Question struct {
+-	Name   string `dns:"cdomain-name"` // "cdomain-name" specifies encoding (and may be compressed)
+-	Qtype  uint16
+-	Qclass uint16
+-}
+-
+-func (q *Question) String() (s string) {
+-	// prefix with ; (as in dig)
+-	s = ";" + sprintName(q.Name) + "\t"
+-	s += Class(q.Qclass).String() + "\t"
+-	s += " " + Type(q.Qtype).String()
+-	return s
+-}
+-
+-func (q *Question) len() int {
+-	l := len(q.Name) + 1
+-	return l + 4
+-}
+-
+-type ANY struct {
+-	Hdr RR_Header
+-	// Does not have any rdata
+-}
+-
+-func (rr *ANY) Header() *RR_Header { return &rr.Hdr }
+-func (rr *ANY) copy() RR           { return &ANY{*rr.Hdr.copyHeader()} }
+-func (rr *ANY) String() string     { return rr.Hdr.String() }
+-func (rr *ANY) len() int           { return rr.Hdr.len() }
+-
+-type CNAME struct {
+-	Hdr    RR_Header
+-	Target string `dns:"cdomain-name"`
+-}
+-
+-func (rr *CNAME) Header() *RR_Header { return &rr.Hdr }
+-func (rr *CNAME) copy() RR           { return &CNAME{*rr.Hdr.copyHeader(), sprintName(rr.Target)} }
+-func (rr *CNAME) String() string     { return rr.Hdr.String() + rr.Target }
+-func (rr *CNAME) len() int           { return rr.Hdr.len() + len(rr.Target) + 1 }
+-
+-type HINFO struct {
+-	Hdr RR_Header
+-	Cpu string
+-	Os  string
+-}
+-
+-func (rr *HINFO) Header() *RR_Header { return &rr.Hdr }
+-func (rr *HINFO) copy() RR           { return &HINFO{*rr.Hdr.copyHeader(), rr.Cpu, rr.Os} }
+-func (rr *HINFO) String() string     { return rr.Hdr.String() + rr.Cpu + " " + rr.Os }
+-func (rr *HINFO) len() int           { return rr.Hdr.len() + len(rr.Cpu) + len(rr.Os) }
+-
+-type MB struct {
+-	Hdr RR_Header
+-	Mb  string `dns:"cdomain-name"`
+-}
+-
+-func (rr *MB) Header() *RR_Header { return &rr.Hdr }
+-func (rr *MB) copy() RR           { return &MB{*rr.Hdr.copyHeader(), sprintName(rr.Mb)} }
+-
+-func (rr *MB) String() string { return rr.Hdr.String() + rr.Mb }
+-func (rr *MB) len() int       { return rr.Hdr.len() + len(rr.Mb) + 1 }
+-
+-type MG struct {
+-	Hdr RR_Header
+-	Mg  string `dns:"cdomain-name"`
+-}
+-
+-func (rr *MG) Header() *RR_Header { return &rr.Hdr }
+-func (rr *MG) copy() RR           { return &MG{*rr.Hdr.copyHeader(), rr.Mg} }
+-func (rr *MG) len() int           { l := len(rr.Mg) + 1; return rr.Hdr.len() + l }
+-func (rr *MG) String() string     { return rr.Hdr.String() + sprintName(rr.Mg) }
+-
+-type MINFO struct {
+-	Hdr   RR_Header
+-	Rmail string `dns:"cdomain-name"`
+-	Email string `dns:"cdomain-name"`
+-}
+-
+-func (rr *MINFO) Header() *RR_Header { return &rr.Hdr }
+-func (rr *MINFO) copy() RR           { return &MINFO{*rr.Hdr.copyHeader(), rr.Rmail, rr.Email} }
+-
+-func (rr *MINFO) String() string {
+-	return rr.Hdr.String() + sprintName(rr.Rmail) + " " + sprintName(rr.Email)
+-}
+-
+-func (rr *MINFO) len() int {
+-	l := len(rr.Rmail) + 1
+-	n := len(rr.Email) + 1
+-	return rr.Hdr.len() + l + n
+-}
+-
+-type MR struct {
+-	Hdr RR_Header
+-	Mr  string `dns:"cdomain-name"`
+-}
+-
+-func (rr *MR) Header() *RR_Header { return &rr.Hdr }
+-func (rr *MR) copy() RR           { return &MR{*rr.Hdr.copyHeader(), rr.Mr} }
+-func (rr *MR) len() int           { l := len(rr.Mr) + 1; return rr.Hdr.len() + l }
+-
+-func (rr *MR) String() string {
+-	return rr.Hdr.String() + sprintName(rr.Mr)
+-}
+-
+-type MF struct {
+-	Hdr RR_Header
+-	Mf  string `dns:"cdomain-name"`
+-}
+-
+-func (rr *MF) Header() *RR_Header { return &rr.Hdr }
+-func (rr *MF) copy() RR           { return &MF{*rr.Hdr.copyHeader(), rr.Mf} }
+-func (rr *MF) len() int           { return rr.Hdr.len() + len(rr.Mf) + 1 }
+-
+-func (rr *MF) String() string {
+-	return rr.Hdr.String() + sprintName(rr.Mf)
+-}
+-
+-type MD struct {
+-	Hdr RR_Header
+-	Md  string `dns:"cdomain-name"`
+-}
+-
+-func (rr *MD) Header() *RR_Header { return &rr.Hdr }
+-func (rr *MD) copy() RR           { return &MD{*rr.Hdr.copyHeader(), rr.Md} }
+-func (rr *MD) len() int           { return rr.Hdr.len() + len(rr.Md) + 1 }
+-
+-func (rr *MD) String() string {
+-	return rr.Hdr.String() + sprintName(rr.Md)
+-}
+-
+-type MX struct {
+-	Hdr        RR_Header
+-	Preference uint16
+-	Mx         string `dns:"cdomain-name"`
+-}
+-
+-func (rr *MX) Header() *RR_Header { return &rr.Hdr }
+-func (rr *MX) copy() RR           { return &MX{*rr.Hdr.copyHeader(), rr.Preference, rr.Mx} }
+-func (rr *MX) len() int           { l := len(rr.Mx) + 1; return rr.Hdr.len() + l + 2 }
+-
+-func (rr *MX) String() string {
+-	return rr.Hdr.String() + strconv.Itoa(int(rr.Preference)) + " " + sprintName(rr.Mx)
+-}
+-
+-type AFSDB struct {
+-	Hdr      RR_Header
+-	Subtype  uint16
+-	Hostname string `dns:"cdomain-name"`
+-}
+-
+-func (rr *AFSDB) Header() *RR_Header { return &rr.Hdr }
+-func (rr *AFSDB) copy() RR           { return &AFSDB{*rr.Hdr.copyHeader(), rr.Subtype, rr.Hostname} }
+-func (rr *AFSDB) len() int           { l := len(rr.Hostname) + 1; return rr.Hdr.len() + l + 2 }
+-
+-func (rr *AFSDB) String() string {
+-	return rr.Hdr.String() + strconv.Itoa(int(rr.Subtype)) + " " + sprintName(rr.Hostname)
+-}
+-
+-type X25 struct {
+-	Hdr         RR_Header
+-	PSDNAddress string
+-}
+-
+-func (rr *X25) Header() *RR_Header { return &rr.Hdr }
+-func (rr *X25) copy() RR           { return &X25{*rr.Hdr.copyHeader(), rr.PSDNAddress} }
+-func (rr *X25) len() int           { return rr.Hdr.len() + len(rr.PSDNAddress) + 1 }
+-
+-func (rr *X25) String() string {
+-	return rr.Hdr.String() + rr.PSDNAddress
+-}
+-
+-type RT struct {
+-	Hdr        RR_Header
+-	Preference uint16
+-	Host       string `dns:"cdomain-name"`
+-}
+-
+-func (rr *RT) Header() *RR_Header { return &rr.Hdr }
+-func (rr *RT) copy() RR           { return &RT{*rr.Hdr.copyHeader(), rr.Preference, rr.Host} }
+-func (rr *RT) len() int           { l := len(rr.Host) + 1; return rr.Hdr.len() + l + 2 }
+-
+-func (rr *RT) String() string {
+-	return rr.Hdr.String() + strconv.Itoa(int(rr.Preference)) + " " + sprintName(rr.Host)
+-}
+-
+-type NS struct {
+-	Hdr RR_Header
+-	Ns  string `dns:"cdomain-name"`
+-}
+-
+-func (rr *NS) Header() *RR_Header { return &rr.Hdr }
+-func (rr *NS) len() int           { l := len(rr.Ns) + 1; return rr.Hdr.len() + l }
+-func (rr *NS) copy() RR           { return &NS{*rr.Hdr.copyHeader(), rr.Ns} }
+-
+-func (rr *NS) String() string {
+-	return rr.Hdr.String() + sprintName(rr.Ns)
+-}
+-
+-type PTR struct {
+-	Hdr RR_Header
+-	Ptr string `dns:"cdomain-name"`
+-}
+-
+-func (rr *PTR) Header() *RR_Header { return &rr.Hdr }
+-func (rr *PTR) copy() RR           { return &PTR{*rr.Hdr.copyHeader(), rr.Ptr} }
+-func (rr *PTR) len() int           { l := len(rr.Ptr) + 1; return rr.Hdr.len() + l }
+-
+-func (rr *PTR) String() string {
+-	return rr.Hdr.String() + sprintName(rr.Ptr)
+-}
+-
+-type RP struct {
+-	Hdr  RR_Header
+-	Mbox string `dns:"domain-name"`
+-	Txt  string `dns:"domain-name"`
+-}
+-
+-func (rr *RP) Header() *RR_Header { return &rr.Hdr }
+-func (rr *RP) copy() RR           { return &RP{*rr.Hdr.copyHeader(), rr.Mbox, rr.Txt} }
+-func (rr *RP) len() int           { return rr.Hdr.len() + len(rr.Mbox) + 1 + len(rr.Txt) + 1 }
+-
+-func (rr *RP) String() string {
+-	return rr.Hdr.String() + rr.Mbox + " " + sprintTxt([]string{rr.Txt})
+-}
+-
+-type SOA struct {
+-	Hdr     RR_Header
+-	Ns      string `dns:"cdomain-name"`
+-	Mbox    string `dns:"cdomain-name"`
+-	Serial  uint32
+-	Refresh uint32
+-	Retry   uint32
+-	Expire  uint32
+-	Minttl  uint32
+-}
+-
+-func (rr *SOA) Header() *RR_Header { return &rr.Hdr }
+-func (rr *SOA) copy() RR {
+-	return &SOA{*rr.Hdr.copyHeader(), rr.Ns, rr.Mbox, rr.Serial, rr.Refresh, rr.Retry, rr.Expire, rr.Minttl}
+-}
+-
+-func (rr *SOA) String() string {
+-	return rr.Hdr.String() + sprintName(rr.Ns) + " " + sprintName(rr.Mbox) +
+-		" " + strconv.FormatInt(int64(rr.Serial), 10) +
+-		" " + strconv.FormatInt(int64(rr.Refresh), 10) +
+-		" " + strconv.FormatInt(int64(rr.Retry), 10) +
+-		" " + strconv.FormatInt(int64(rr.Expire), 10) +
+-		" " + strconv.FormatInt(int64(rr.Minttl), 10)
+-}
+-
+-func (rr *SOA) len() int {
+-	l := len(rr.Ns) + 1
+-	n := len(rr.Mbox) + 1
+-	return rr.Hdr.len() + l + n + 20
+-}
+-
+-type TXT struct {
+-	Hdr RR_Header
+-	Txt []string `dns:"txt"`
+-}
+-
+-func (rr *TXT) Header() *RR_Header { return &rr.Hdr }
+-func (rr *TXT) copy() RR {
+-	cp := make([]string, len(rr.Txt), cap(rr.Txt))
+-	copy(cp, rr.Txt)
+-	return &TXT{*rr.Hdr.copyHeader(), cp}
+-}
+-
+-func (rr *TXT) String() string { return rr.Hdr.String() + sprintTxt(rr.Txt) }
+-
+-func sprintName(s string) string {
+-	src := []byte(s)
+-	dst := make([]byte, 0, len(src))
+-	for i := 0; i < len(src); {
+-		if i+1 < len(src) && src[i] == '\\' && src[i+1] == '.' {
+-			dst = append(dst, src[i:i+2]...)
+-			i += 2
+-		} else {
+-			b, n := nextByte(src, i)
+-			if n == 0 {
+-				i++ // dangling back slash
+-			} else if b == '.' {
+-				dst = append(dst, b)
+-			} else {
+-				dst = appendDomainNameByte(dst, b)
+-			}
+-			i += n
+-		}
+-	}
+-	return string(dst)
+-}
+-
+-func sprintTxt(txt []string) string {
+-	var out []byte
+-	for i, s := range txt {
+-		if i > 0 {
+-			out = append(out, ` "`...)
+-		} else {
+-			out = append(out, '"')
+-		}
+-		bs := []byte(s)
+-		for j := 0; j < len(bs); {
+-			b, n := nextByte(bs, j)
+-			if n == 0 {
+-				break
+-			}
+-			out = appendTXTStringByte(out, b)
+-			j += n
+-		}
+-		out = append(out, '"')
+-	}
+-	return string(out)
+-}
+-
+-func appendDomainNameByte(s []byte, b byte) []byte {
+-	switch b {
+-	case '.', ' ', '\'', '@', ';', '(', ')': // additional chars to escape
+-		return append(s, '\\', b)
+-	}
+-	return appendTXTStringByte(s, b)
+-}
+-
+-func appendTXTStringByte(s []byte, b byte) []byte {
+-	switch b {
+-	case '\t':
+-		return append(s, '\\', 't')
+-	case '\r':
+-		return append(s, '\\', 'r')
+-	case '\n':
+-		return append(s, '\\', 'n')
+-	case '"', '\\':
+-		return append(s, '\\', b)
+-	}
+-	if b < ' ' || b > '~' {
+-		var buf [3]byte
+-		bufs := strconv.AppendInt(buf[:0], int64(b), 10)
+-		s = append(s, '\\')
+-		for i := 0; i < 3-len(bufs); i++ {
+-			s = append(s, '0')
+-		}
+-		for _, r := range bufs {
+-			s = append(s, r)
+-		}
+-		return s
+-
+-	}
+-	return append(s, b)
+-}
+-
+-func nextByte(b []byte, offset int) (byte, int) {
+-	if offset >= len(b) {
+-		return 0, 0
+-	}
+-	if b[offset] != '\\' {
+-		// not an escape sequence
+-		return b[offset], 1
+-	}
+-	switch len(b) - offset {
+-	case 1: // dangling escape
+-		return 0, 0
+-	case 2, 3: // too short to be \ddd
+-	default: // maybe \ddd
+-		if isDigit(b[offset+1]) && isDigit(b[offset+2]) && isDigit(b[offset+3]) {
+-			return dddToByte(b[offset+1:]), 4
+-		}
+-	}
+-	// not \ddd, maybe a control char
+-	switch b[offset+1] {
+-	case 't':
+-		return '\t', 2
+-	case 'r':
+-		return '\r', 2
+-	case 'n':
+-		return '\n', 2
+-	default:
+-		return b[offset+1], 2
+-	}
+-}
+-
+-func (rr *TXT) len() int {
+-	l := rr.Hdr.len()
+-	for _, t := range rr.Txt {
+-		l += len(t) + 1
+-	}
+-	return l
+-}
+-
+-type SPF struct {
+-	Hdr RR_Header
+-	Txt []string `dns:"txt"`
+-}
+-
+-func (rr *SPF) Header() *RR_Header { return &rr.Hdr }
+-func (rr *SPF) copy() RR {
+-	cp := make([]string, len(rr.Txt), cap(rr.Txt))
+-	copy(cp, rr.Txt)
+-	return &SPF{*rr.Hdr.copyHeader(), cp}
+-}
+-
+-func (rr *SPF) String() string { return rr.Hdr.String() + sprintTxt(rr.Txt) }
+-
+-func (rr *SPF) len() int {
+-	l := rr.Hdr.len()
+-	for _, t := range rr.Txt {
+-		l += len(t) + 1
+-	}
+-	return l
+-}
+-
+-type SRV struct {
+-	Hdr      RR_Header
+-	Priority uint16
+-	Weight   uint16
+-	Port     uint16
+-	Target   string `dns:"domain-name"`
+-}
+-
+-func (rr *SRV) Header() *RR_Header { return &rr.Hdr }
+-func (rr *SRV) len() int           { l := len(rr.Target) + 1; return rr.Hdr.len() + l + 6 }
+-func (rr *SRV) copy() RR {
+-	return &SRV{*rr.Hdr.copyHeader(), rr.Priority, rr.Weight, rr.Port, rr.Target}
+-}
+-
+-func (rr *SRV) String() string {
+-	return rr.Hdr.String() +
+-		strconv.Itoa(int(rr.Priority)) + " " +
+-		strconv.Itoa(int(rr.Weight)) + " " +
+-		strconv.Itoa(int(rr.Port)) + " " + sprintName(rr.Target)
+-}
+-
+-type NAPTR struct {
+-	Hdr         RR_Header
+-	Order       uint16
+-	Preference  uint16
+-	Flags       string
+-	Service     string
+-	Regexp      string
+-	Replacement string `dns:"domain-name"`
+-}
+-
+-func (rr *NAPTR) Header() *RR_Header { return &rr.Hdr }
+-func (rr *NAPTR) copy() RR {
+-	return &NAPTR{*rr.Hdr.copyHeader(), rr.Order, rr.Preference, rr.Flags, rr.Service, rr.Regexp, rr.Replacement}
+-}
+-
+-func (rr *NAPTR) String() string {
+-	return rr.Hdr.String() +
+-		strconv.Itoa(int(rr.Order)) + " " +
+-		strconv.Itoa(int(rr.Preference)) + " " +
+-		"\"" + rr.Flags + "\" " +
+-		"\"" + rr.Service + "\" " +
+-		"\"" + rr.Regexp + "\" " +
+-		rr.Replacement
+-}
+-
+-func (rr *NAPTR) len() int {
+-	return rr.Hdr.len() + 4 + len(rr.Flags) + 1 + len(rr.Service) + 1 +
+-		len(rr.Regexp) + 1 + len(rr.Replacement) + 1
+-}
+-
+-// See RFC 4398.
+-type CERT struct {
+-	Hdr         RR_Header
+-	Type        uint16
+-	KeyTag      uint16
+-	Algorithm   uint8
+-	Certificate string `dns:"base64"`
+-}
+-
+-func (rr *CERT) Header() *RR_Header { return &rr.Hdr }
+-func (rr *CERT) copy() RR {
+-	return &CERT{*rr.Hdr.copyHeader(), rr.Type, rr.KeyTag, rr.Algorithm, rr.Certificate}
+-}
+-
+-func (rr *CERT) String() string {
+-	var (
+-		ok                  bool
+-		certtype, algorithm string
+-	)
+-	if certtype, ok = CertTypeToString[rr.Type]; !ok {
+-		certtype = strconv.Itoa(int(rr.Type))
+-	}
+-	if algorithm, ok = AlgorithmToString[rr.Algorithm]; !ok {
+-		algorithm = strconv.Itoa(int(rr.Algorithm))
+-	}
+-	return rr.Hdr.String() + certtype +
+-		" " + strconv.Itoa(int(rr.KeyTag)) +
+-		" " + algorithm +
+-		" " + rr.Certificate
+-}
+-
+-func (rr *CERT) len() int {
+-	return rr.Hdr.len() + 5 +
+-		base64.StdEncoding.DecodedLen(len(rr.Certificate))
+-}
+-
+-// See RFC 2672.
+-type DNAME struct {
+-	Hdr    RR_Header
+-	Target string `dns:"domain-name"`
+-}
+-
+-func (rr *DNAME) Header() *RR_Header { return &rr.Hdr }
+-func (rr *DNAME) copy() RR           { return &DNAME{*rr.Hdr.copyHeader(), rr.Target} }
+-func (rr *DNAME) len() int           { l := len(rr.Target) + 1; return rr.Hdr.len() + l }
+-
+-func (rr *DNAME) String() string {
+-	return rr.Hdr.String() + sprintName(rr.Target)
+-}
+-
+-type A struct {
+-	Hdr RR_Header
+-	A   net.IP `dns:"a"`
+-}
+-
+-func (rr *A) Header() *RR_Header { return &rr.Hdr }
+-func (rr *A) copy() RR           { return &A{*rr.Hdr.copyHeader(), copyIP(rr.A)} }
+-func (rr *A) len() int           { return rr.Hdr.len() + net.IPv4len }
+-
+-func (rr *A) String() string {
+-	if rr.A == nil {
+-		return rr.Hdr.String()
+-	}
+-	return rr.Hdr.String() + rr.A.String()
+-}
+-
+-type AAAA struct {
+-	Hdr  RR_Header
+-	AAAA net.IP `dns:"aaaa"`
+-}
+-
+-func (rr *AAAA) Header() *RR_Header { return &rr.Hdr }
+-func (rr *AAAA) copy() RR           { return &AAAA{*rr.Hdr.copyHeader(), copyIP(rr.AAAA)} }
+-func (rr *AAAA) len() int           { return rr.Hdr.len() + net.IPv6len }
+-
+-func (rr *AAAA) String() string {
+-	if rr.AAAA == nil {
+-		return rr.Hdr.String()
+-	}
+-	return rr.Hdr.String() + rr.AAAA.String()
+-}
+-
+-type PX struct {
+-	Hdr        RR_Header
+-	Preference uint16
+-	Map822     string `dns:"domain-name"`
+-	Mapx400    string `dns:"domain-name"`
+-}
+-
+-func (rr *PX) Header() *RR_Header { return &rr.Hdr }
+-func (rr *PX) copy() RR           { return &PX{*rr.Hdr.copyHeader(), rr.Preference, rr.Map822, rr.Mapx400} }
+-func (rr *PX) String() string {
+-	return rr.Hdr.String() + strconv.Itoa(int(rr.Preference)) + " " + sprintName(rr.Map822) + " " + sprintName(rr.Mapx400)
+-}
+-func (rr *PX) len() int { return rr.Hdr.len() + 2 + len(rr.Map822) + 1 + len(rr.Mapx400) + 1 }
+-
+-type GPOS struct {
+-	Hdr       RR_Header
+-	Longitude string
+-	Latitude  string
+-	Altitude  string
+-}
+-
+-func (rr *GPOS) Header() *RR_Header { return &rr.Hdr }
+-func (rr *GPOS) copy() RR           { return &GPOS{*rr.Hdr.copyHeader(), rr.Longitude, rr.Latitude, rr.Altitude} }
+-func (rr *GPOS) len() int {
+-	return rr.Hdr.len() + len(rr.Longitude) + len(rr.Latitude) + len(rr.Altitude) + 3
+-}
+-func (rr *GPOS) String() string {
+-	return rr.Hdr.String() + rr.Longitude + " " + rr.Latitude + " " + rr.Altitude
+-}
+-
+-type LOC struct {
+-	Hdr       RR_Header
+-	Version   uint8
+-	Size      uint8
+-	HorizPre  uint8
+-	VertPre   uint8
+-	Latitude  uint32
+-	Longitude uint32
+-	Altitude  uint32
+-}
+-
+-func (rr *LOC) Header() *RR_Header { return &rr.Hdr }
+-func (rr *LOC) len() int           { return rr.Hdr.len() + 4 + 12 }
+-func (rr *LOC) copy() RR {
+-	return &LOC{*rr.Hdr.copyHeader(), rr.Version, rr.Size, rr.HorizPre, rr.VertPre, rr.Latitude, rr.Longitude, rr.Altitude}
+-}
+-
+-// cmToM takes a cm value expressed in RFC1876 SIZE mantissa/exponent
+-// format and returns a string in m (two decimals for the cm)
+-func cmToM(m, e uint8) string {
+-	if e < 2 {
+-		if e == 1 {
+-			m *= 10
+-		}
+-
+-		return fmt.Sprintf("0.%02d", m)
+-	}
+-
+-	s := fmt.Sprintf("%d", m)
+-	for e > 2 {
+-		s += "0"
+-		e -= 1
+-	}
+-	return s
+-}
+-
+-// String returns a string version of a LOC
+-func (rr *LOC) String() string {
+-	s := rr.Hdr.String()
+-
+-	lat := rr.Latitude
+-	ns := "N"
+-	if lat > LOC_EQUATOR {
+-		lat = lat - LOC_EQUATOR
+-	} else {
+-		ns = "S"
+-		lat = LOC_EQUATOR - lat
+-	}
+-	h := lat / LOC_DEGREES
+-	lat = lat % LOC_DEGREES
+-	m := lat / LOC_HOURS
+-	lat = lat % LOC_HOURS
+-	s += fmt.Sprintf("%02d %02d %0.3f %s ", h, m, (float64(lat) / 1000), ns)
+-
+-	lon := rr.Longitude
+-	ew := "E"
+-	if lon > LOC_PRIMEMERIDIAN {
+-		lon = lon - LOC_PRIMEMERIDIAN
+-	} else {
+-		ew = "W"
+-		lon = LOC_PRIMEMERIDIAN - lon
+-	}
+-	h = lon / LOC_DEGREES
+-	lon = lon % LOC_DEGREES
+-	m = lon / LOC_HOURS
+-	lon = lon % LOC_HOURS
+-	s += fmt.Sprintf("%02d %02d %0.3f %s ", h, m, (float64(lon) / 1000), ew)
+-
+-	var alt float64 = float64(rr.Altitude) / 100
+-	alt -= LOC_ALTITUDEBASE
+-	if rr.Altitude%100 != 0 {
+-		s += fmt.Sprintf("%.2fm ", alt)
+-	} else {
+-		s += fmt.Sprintf("%.0fm ", alt)
+-	}
+-
+-	s += cmToM((rr.Size&0xf0)>>4, rr.Size&0x0f) + "m "
+-	s += cmToM((rr.HorizPre&0xf0)>>4, rr.HorizPre&0x0f) + "m "
+-	s += cmToM((rr.VertPre&0xf0)>>4, rr.VertPre&0x0f) + "m"
+-
+-	return s
+-}
+-
+-// SIG is identical to RRSIG and nowadays only used for SIG(0), RFC2931.
+-type SIG struct {
+-	RRSIG
+-}
+-
+-type RRSIG struct {
+-	Hdr         RR_Header
+-	TypeCovered uint16
+-	Algorithm   uint8
+-	Labels      uint8
+-	OrigTtl     uint32
+-	Expiration  uint32
+-	Inception   uint32
+-	KeyTag      uint16
+-	SignerName  string `dns:"domain-name"`
+-	Signature   string `dns:"base64"`
+-}
+-
+-func (rr *RRSIG) Header() *RR_Header { return &rr.Hdr }
+-func (rr *RRSIG) copy() RR {
+-	return &RRSIG{*rr.Hdr.copyHeader(), rr.TypeCovered, rr.Algorithm, rr.Labels, rr.OrigTtl, rr.Expiration, rr.Inception, rr.KeyTag, rr.SignerName, rr.Signature}
+-}
+-
+-func (rr *RRSIG) String() string {
+-	s := rr.Hdr.String()
+-	s += Type(rr.TypeCovered).String()
+-	s += " " + strconv.Itoa(int(rr.Algorithm)) +
+-		" " + strconv.Itoa(int(rr.Labels)) +
+-		" " + strconv.FormatInt(int64(rr.OrigTtl), 10) +
+-		" " + TimeToString(rr.Expiration) +
+-		" " + TimeToString(rr.Inception) +
+-		" " + strconv.Itoa(int(rr.KeyTag)) +
+-		" " + sprintName(rr.SignerName) +
+-		" " + rr.Signature
+-	return s
+-}
+-
+-func (rr *RRSIG) len() int {
+-	return rr.Hdr.len() + len(rr.SignerName) + 1 +
+-		base64.StdEncoding.DecodedLen(len(rr.Signature)) + 18
+-}
+-
+-type NSEC struct {
+-	Hdr        RR_Header
+-	NextDomain string   `dns:"domain-name"`
+-	TypeBitMap []uint16 `dns:"nsec"`
+-}
+-
+-func (rr *NSEC) Header() *RR_Header { return &rr.Hdr }
+-func (rr *NSEC) copy() RR {
+-	cp := make([]uint16, len(rr.TypeBitMap), cap(rr.TypeBitMap))
+-	copy(cp, rr.TypeBitMap)
+-	return &NSEC{*rr.Hdr.copyHeader(), rr.NextDomain, cp}
+-}
+-
+-func (rr *NSEC) String() string {
+-	s := rr.Hdr.String() + sprintName(rr.NextDomain)
+-	for i := 0; i < len(rr.TypeBitMap); i++ {
+-		s += " " + Type(rr.TypeBitMap[i]).String()
+-	}
+-	return s
+-}
+-
+-func (rr *NSEC) len() int {
+-	l := rr.Hdr.len() + len(rr.NextDomain) + 1
+-	lastwindow := uint32(2 ^ 32 + 1)
+-	for _, t := range rr.TypeBitMap {
+-		window := t / 256
+-		if uint32(window) != lastwindow {
+-			l += 1 + 32
+-		}
+-		lastwindow = uint32(window)
+-	}
+-	return l
+-}
+-
+-type DLV struct {
+-	DS
+-}
+-
+-type CDS struct {
+-	DS
+-}
+-
+-type DS struct {
+-	Hdr        RR_Header
+-	KeyTag     uint16
+-	Algorithm  uint8
+-	DigestType uint8
+-	Digest     string `dns:"hex"`
+-}
+-
+-func (rr *DS) Header() *RR_Header { return &rr.Hdr }
+-func (rr *DS) len() int           { return rr.Hdr.len() + 4 + len(rr.Digest)/2 }
+-func (rr *DS) copy() RR {
+-	return &DS{*rr.Hdr.copyHeader(), rr.KeyTag, rr.Algorithm, rr.DigestType, rr.Digest}
+-}
+-
+-func (rr *DS) String() string {
+-	return rr.Hdr.String() + strconv.Itoa(int(rr.KeyTag)) +
+-		" " + strconv.Itoa(int(rr.Algorithm)) +
+-		" " + strconv.Itoa(int(rr.DigestType)) +
+-		" " + strings.ToUpper(rr.Digest)
+-}
+-
+-type KX struct {
+-	Hdr        RR_Header
+-	Preference uint16
+-	Exchanger  string `dns:"domain-name"`
+-}
+-
+-func (rr *KX) Header() *RR_Header { return &rr.Hdr }
+-func (rr *KX) len() int           { return rr.Hdr.len() + 2 + len(rr.Exchanger) + 1 }
+-func (rr *KX) copy() RR           { return &KX{*rr.Hdr.copyHeader(), rr.Preference, rr.Exchanger} }
+-
+-func (rr *KX) String() string {
+-	return rr.Hdr.String() + strconv.Itoa(int(rr.Preference)) +
+-		" " + sprintName(rr.Exchanger)
+-}
+-
+-type TA struct {
+-	Hdr        RR_Header
+-	KeyTag     uint16
+-	Algorithm  uint8
+-	DigestType uint8
+-	Digest     string `dns:"hex"`
+-}
+-
+-func (rr *TA) Header() *RR_Header { return &rr.Hdr }
+-func (rr *TA) len() int           { return rr.Hdr.len() + 4 + len(rr.Digest)/2 }
+-func (rr *TA) copy() RR {
+-	return &TA{*rr.Hdr.copyHeader(), rr.KeyTag, rr.Algorithm, rr.DigestType, rr.Digest}
+-}
+-
+-func (rr *TA) String() string {
+-	return rr.Hdr.String() + strconv.Itoa(int(rr.KeyTag)) +
+-		" " + strconv.Itoa(int(rr.Algorithm)) +
+-		" " + strconv.Itoa(int(rr.DigestType)) +
+-		" " + strings.ToUpper(rr.Digest)
+-}
+-
+-type TALINK struct {
+-	Hdr          RR_Header
+-	PreviousName string `dns:"domain-name"`
+-	NextName     string `dns:"domain-name"`
+-}
+-
+-func (rr *TALINK) Header() *RR_Header { return &rr.Hdr }
+-func (rr *TALINK) copy() RR           { return &TALINK{*rr.Hdr.copyHeader(), rr.PreviousName, rr.NextName} }
+-func (rr *TALINK) len() int           { return rr.Hdr.len() + len(rr.PreviousName) + len(rr.NextName) + 2 }
+-
+-func (rr *TALINK) String() string {
+-	return rr.Hdr.String() +
+-		sprintName(rr.PreviousName) + " " + sprintName(rr.NextName)
+-}
+-
+-type SSHFP struct {
+-	Hdr         RR_Header
+-	Algorithm   uint8
+-	Type        uint8
+-	FingerPrint string `dns:"hex"`
+-}
+-
+-func (rr *SSHFP) Header() *RR_Header { return &rr.Hdr }
+-func (rr *SSHFP) len() int           { return rr.Hdr.len() + 2 + len(rr.FingerPrint)/2 }
+-func (rr *SSHFP) copy() RR {
+-	return &SSHFP{*rr.Hdr.copyHeader(), rr.Algorithm, rr.Type, rr.FingerPrint}
+-}
+-
+-func (rr *SSHFP) String() string {
+-	return rr.Hdr.String() + strconv.Itoa(int(rr.Algorithm)) +
+-		" " + strconv.Itoa(int(rr.Type)) +
+-		" " + strings.ToUpper(rr.FingerPrint)
+-}
+-
+-type IPSECKEY struct {
+-	Hdr         RR_Header
+-	Precedence  uint8
+-	GatewayType uint8
+-	Algorithm   uint8
+-	Gateway     string `dns:"ipseckey"`
+-	PublicKey   string `dns:"base64"`
+-}
+-
+-func (rr *IPSECKEY) Header() *RR_Header { return &rr.Hdr }
+-func (rr *IPSECKEY) copy() RR {
+-	return &IPSECKEY{*rr.Hdr.copyHeader(), rr.Precedence, rr.GatewayType, rr.Algorithm, rr.Gateway, rr.PublicKey}
+-}
+-
+-func (rr *IPSECKEY) String() string {
+-	return rr.Hdr.String() + strconv.Itoa(int(rr.Precedence)) +
+-		" " + strconv.Itoa(int(rr.GatewayType)) +
+-		" " + strconv.Itoa(int(rr.Algorithm)) +
+-		" " + rr.Gateway +
+-		" " + rr.PublicKey
+-}
+-
+-func (rr *IPSECKEY) len() int {
+-	return rr.Hdr.len() + 3 + len(rr.Gateway) + 1 +
+-		base64.StdEncoding.DecodedLen(len(rr.PublicKey))
+-}
+-
+-type KEY struct {
+-	DNSKEY
+-}
+-
+-type CDNSKEY struct {
+-	DNSKEY
+-}
+-
+-type DNSKEY struct {
+-	Hdr       RR_Header
+-	Flags     uint16
+-	Protocol  uint8
+-	Algorithm uint8
+-	PublicKey string `dns:"base64"`
+-}
+-
+-func (rr *DNSKEY) Header() *RR_Header { return &rr.Hdr }
+-func (rr *DNSKEY) len() int {
+-	return rr.Hdr.len() + 4 + base64.StdEncoding.DecodedLen(len(rr.PublicKey))
+-}
+-func (rr *DNSKEY) copy() RR {
+-	return &DNSKEY{*rr.Hdr.copyHeader(), rr.Flags, rr.Protocol, rr.Algorithm, rr.PublicKey}
+-}
+-
+-func (rr *DNSKEY) String() string {
+-	return rr.Hdr.String() + strconv.Itoa(int(rr.Flags)) +
+-		" " + strconv.Itoa(int(rr.Protocol)) +
+-		" " + strconv.Itoa(int(rr.Algorithm)) +
+-		" " + rr.PublicKey
+-}
+-
+-type RKEY struct {
+-	Hdr       RR_Header
+-	Flags     uint16
+-	Protocol  uint8
+-	Algorithm uint8
+-	PublicKey string `dns:"base64"`
+-}
+-
+-func (rr *RKEY) Header() *RR_Header { return &rr.Hdr }
+-func (rr *RKEY) len() int           { return rr.Hdr.len() + 4 + base64.StdEncoding.DecodedLen(len(rr.PublicKey)) }
+-func (rr *RKEY) copy() RR {
+-	return &RKEY{*rr.Hdr.copyHeader(), rr.Flags, rr.Protocol, rr.Algorithm, rr.PublicKey}
+-}
+-
+-func (rr *RKEY) String() string {
+-	return rr.Hdr.String() + strconv.Itoa(int(rr.Flags)) +
+-		" " + strconv.Itoa(int(rr.Protocol)) +
+-		" " + strconv.Itoa(int(rr.Algorithm)) +
+-		" " + rr.PublicKey
+-}
+-
+-type NSAP struct {
+-	Hdr    RR_Header
+-	Length uint8
+-	Nsap   string
+-}
+-
+-func (rr *NSAP) Header() *RR_Header { return &rr.Hdr }
+-func (rr *NSAP) copy() RR           { return &NSAP{*rr.Hdr.copyHeader(), rr.Length, rr.Nsap} }
+-func (rr *NSAP) String() string     { return rr.Hdr.String() + strconv.Itoa(int(rr.Length)) + " " + rr.Nsap }
+-func (rr *NSAP) len() int           { return rr.Hdr.len() + 1 + len(rr.Nsap) + 1 }
+-
+-type NSAPPTR struct {
+-	Hdr RR_Header
+-	Ptr string `dns:"domain-name"`
+-}
+-
+-func (rr *NSAPPTR) Header() *RR_Header { return &rr.Hdr }
+-func (rr *NSAPPTR) copy() RR           { return &NSAPPTR{*rr.Hdr.copyHeader(), rr.Ptr} }
+-func (rr *NSAPPTR) String() string     { return rr.Hdr.String() + sprintName(rr.Ptr) }
+-func (rr *NSAPPTR) len() int           { return rr.Hdr.len() + len(rr.Ptr) }
+-
+-type NSEC3 struct {
+-	Hdr        RR_Header
+-	Hash       uint8
+-	Flags      uint8
+-	Iterations uint16
+-	SaltLength uint8
+-	Salt       string `dns:"size-hex"`
+-	HashLength uint8
+-	NextDomain string   `dns:"size-base32"`
+-	TypeBitMap []uint16 `dns:"nsec"`
+-}
+-
+-func (rr *NSEC3) Header() *RR_Header { return &rr.Hdr }
+-func (rr *NSEC3) copy() RR {
+-	cp := make([]uint16, len(rr.TypeBitMap), cap(rr.TypeBitMap))
+-	copy(cp, rr.TypeBitMap)
+-	return &NSEC3{*rr.Hdr.copyHeader(), rr.Hash, rr.Flags, rr.Iterations, rr.SaltLength, rr.Salt, rr.HashLength, rr.NextDomain, cp}
+-}
+-
+-func (rr *NSEC3) String() string {
+-	s := rr.Hdr.String()
+-	s += strconv.Itoa(int(rr.Hash)) +
+-		" " + strconv.Itoa(int(rr.Flags)) +
+-		" " + strconv.Itoa(int(rr.Iterations)) +
+-		" " + saltToString(rr.Salt) +
+-		" " + rr.NextDomain
+-	for i := 0; i < len(rr.TypeBitMap); i++ {
+-		s += " " + Type(rr.TypeBitMap[i]).String()
+-	}
+-	return s
+-}
+-
+-func (rr *NSEC3) len() int {
+-	l := rr.Hdr.len() + 6 + len(rr.Salt)/2 + 1 + len(rr.NextDomain) + 1
+-	lastwindow := uint32(2 ^ 32 + 1)
+-	for _, t := range rr.TypeBitMap {
+-		window := t / 256
+-		if uint32(window) != lastwindow {
+-			l += 1 + 32
+-		}
+-		lastwindow = uint32(window)
+-	}
+-	return l
+-}
+-
+-type NSEC3PARAM struct {
+-	Hdr        RR_Header
+-	Hash       uint8
+-	Flags      uint8
+-	Iterations uint16
+-	SaltLength uint8
+-	Salt       string `dns:"hex"`
+-}
+-
+-func (rr *NSEC3PARAM) Header() *RR_Header { return &rr.Hdr }
+-func (rr *NSEC3PARAM) len() int           { return rr.Hdr.len() + 2 + 4 + 1 + len(rr.Salt)/2 }
+-func (rr *NSEC3PARAM) copy() RR {
+-	return &NSEC3PARAM{*rr.Hdr.copyHeader(), rr.Hash, rr.Flags, rr.Iterations, rr.SaltLength, rr.Salt}
+-}
+-
+-func (rr *NSEC3PARAM) String() string {
+-	s := rr.Hdr.String()
+-	s += strconv.Itoa(int(rr.Hash)) +
+-		" " + strconv.Itoa(int(rr.Flags)) +
+-		" " + strconv.Itoa(int(rr.Iterations)) +
+-		" " + saltToString(rr.Salt)
+-	return s
+-}
+-
+-type TKEY struct {
+-	Hdr        RR_Header
+-	Algorithm  string `dns:"domain-name"`
+-	Inception  uint32
+-	Expiration uint32
+-	Mode       uint16
+-	Error      uint16
+-	KeySize    uint16
+-	Key        string
+-	OtherLen   uint16
+-	OtherData  string
+-}
+-
+-func (rr *TKEY) Header() *RR_Header { return &rr.Hdr }
+-func (rr *TKEY) copy() RR {
+-	return &TKEY{*rr.Hdr.copyHeader(), rr.Algorithm, rr.Inception, rr.Expiration, rr.Mode, rr.Error, rr.KeySize, rr.Key, rr.OtherLen, rr.OtherData}
+-}
+-
+-func (rr *TKEY) String() string {
+-	// It has no presentation format
+-	return ""
+-}
+-
+-func (rr *TKEY) len() int {
+-	return rr.Hdr.len() + len(rr.Algorithm) + 1 + 4 + 4 + 6 +
+-		len(rr.Key) + 2 + len(rr.OtherData)
+-}
+-
+-// RFC3597 represents an unknown/generic RR.
+-type RFC3597 struct {
+-	Hdr   RR_Header
+-	Rdata string `dns:"hex"`
+-}
+-
+-func (rr *RFC3597) Header() *RR_Header { return &rr.Hdr }
+-func (rr *RFC3597) copy() RR           { return &RFC3597{*rr.Hdr.copyHeader(), rr.Rdata} }
+-func (rr *RFC3597) len() int           { return rr.Hdr.len() + len(rr.Rdata)/2 + 2 }
+-
+-func (rr *RFC3597) String() string {
+-	// Let's call it a hack
+-	s := rfc3597Header(rr.Hdr)
+-
+-	s += "\\# " + strconv.Itoa(len(rr.Rdata)/2) + " " + rr.Rdata
+-	return s
+-}
+-
+-func rfc3597Header(h RR_Header) string {
+-	var s string
+-
+-	s += sprintName(h.Name) + "\t"
+-	s += strconv.FormatInt(int64(h.Ttl), 10) + "\t"
+-	s += "CLASS" + strconv.Itoa(int(h.Class)) + "\t"
+-	s += "TYPE" + strconv.Itoa(int(h.Rrtype)) + "\t"
+-	return s
+-}
+-
+-type URI struct {
+-	Hdr      RR_Header
+-	Priority uint16
+-	Weight   uint16
+-	Target   []string `dns:"txt"`
+-}
+-
+-func (rr *URI) Header() *RR_Header { return &rr.Hdr }
+-func (rr *URI) copy() RR {
+-	cp := make([]string, len(rr.Target), cap(rr.Target))
+-	copy(cp, rr.Target)
+-	return &URI{*rr.Hdr.copyHeader(), rr.Weight, rr.Priority, cp}
+-}
+-
+-func (rr *URI) String() string {
+-	return rr.Hdr.String() + strconv.Itoa(int(rr.Priority)) +
+-		" " + strconv.Itoa(int(rr.Weight)) + sprintTxt(rr.Target)
+-}
+-
+-func (rr *URI) len() int {
+-	l := rr.Hdr.len() + 4
+-	for _, t := range rr.Target {
+-		l += len(t) + 1
+-	}
+-	return l
+-}
+-
+-type DHCID struct {
+-	Hdr    RR_Header
+-	Digest string `dns:"base64"`
+-}
+-
+-func (rr *DHCID) Header() *RR_Header { return &rr.Hdr }
+-func (rr *DHCID) copy() RR           { return &DHCID{*rr.Hdr.copyHeader(), rr.Digest} }
+-func (rr *DHCID) String() string     { return rr.Hdr.String() + rr.Digest }
+-func (rr *DHCID) len() int           { return rr.Hdr.len() + base64.StdEncoding.DecodedLen(len(rr.Digest)) }
+-
+-type TLSA struct {
+-	Hdr          RR_Header
+-	Usage        uint8
+-	Selector     uint8
+-	MatchingType uint8
+-	Certificate  string `dns:"hex"`
+-}
+-
+-func (rr *TLSA) Header() *RR_Header { return &rr.Hdr }
+-func (rr *TLSA) len() int           { return rr.Hdr.len() + 3 + len(rr.Certificate)/2 }
+-
+-func (rr *TLSA) copy() RR {
+-	return &TLSA{*rr.Hdr.copyHeader(), rr.Usage, rr.Selector, rr.MatchingType, rr.Certificate}
+-}
+-
+-func (rr *TLSA) String() string {
+-	return rr.Hdr.String() +
+-		strconv.Itoa(int(rr.Usage)) +
+-		" " + strconv.Itoa(int(rr.Selector)) +
+-		" " + strconv.Itoa(int(rr.MatchingType)) +
+-		" " + rr.Certificate
+-}
+-
+-type HIP struct {
+-	Hdr                RR_Header
+-	HitLength          uint8
+-	PublicKeyAlgorithm uint8
+-	PublicKeyLength    uint16
+-	Hit                string   `dns:"hex"`
+-	PublicKey          string   `dns:"base64"`
+-	RendezvousServers  []string `dns:"domain-name"`
+-}
+-
+-func (rr *HIP) Header() *RR_Header { return &rr.Hdr }
+-func (rr *HIP) copy() RR {
+-	cp := make([]string, len(rr.RendezvousServers), cap(rr.RendezvousServers))
+-	copy(cp, rr.RendezvousServers)
+-	return &HIP{*rr.Hdr.copyHeader(), rr.HitLength, rr.PublicKeyAlgorithm, rr.PublicKeyLength, rr.Hit, rr.PublicKey, cp}
+-}
+-
+-func (rr *HIP) String() string {
+-	s := rr.Hdr.String() +
+-		strconv.Itoa(int(rr.PublicKeyAlgorithm)) +
+-		" " + rr.Hit +
+-		" " + rr.PublicKey
+-	for _, d := range rr.RendezvousServers {
+-		s += " " + sprintName(d)
+-	}
+-	return s
+-}
+-
+-func (rr *HIP) len() int {
+-	l := rr.Hdr.len() + 4 +
+-		len(rr.Hit)/2 +
+-		base64.StdEncoding.DecodedLen(len(rr.PublicKey))
+-	for _, d := range rr.RendezvousServers {
+-		l += len(d) + 1
+-	}
+-	return l
+-}
+-
+-type NINFO struct {
+-	Hdr    RR_Header
+-	ZSData []string `dns:"txt"`
+-}
+-
+-func (rr *NINFO) Header() *RR_Header { return &rr.Hdr }
+-func (rr *NINFO) copy() RR {
+-	cp := make([]string, len(rr.ZSData), cap(rr.ZSData))
+-	copy(cp, rr.ZSData)
+-	return &NINFO{*rr.Hdr.copyHeader(), cp}
+-}
+-
+-func (rr *NINFO) String() string { return rr.Hdr.String() + sprintTxt(rr.ZSData) }
+-
+-func (rr *NINFO) len() int {
+-	l := rr.Hdr.len()
+-	for _, t := range rr.ZSData {
+-		l += len(t) + 1
+-	}
+-	return l
+-}
+-
+-type WKS struct {
+-	Hdr      RR_Header
+-	Address  net.IP `dns:"a"`
+-	Protocol uint8
+-	BitMap   []uint16 `dns:"wks"`
+-}
+-
+-func (rr *WKS) Header() *RR_Header { return &rr.Hdr }
+-func (rr *WKS) len() int           { return rr.Hdr.len() + net.IPv4len + 1 }
+-
+-func (rr *WKS) copy() RR {
+-	cp := make([]uint16, len(rr.BitMap), cap(rr.BitMap))
+-	copy(cp, rr.BitMap)
+-	return &WKS{*rr.Hdr.copyHeader(), copyIP(rr.Address), rr.Protocol, cp}
+-}
+-
+-func (rr *WKS) String() (s string) {
+-	s = rr.Hdr.String()
+-	if rr.Address != nil {
+-		s += rr.Address.String()
+-	}
+-	for i := 0; i < len(rr.BitMap); i++ {
+-		// should lookup the port
+-		s += " " + strconv.Itoa(int(rr.BitMap[i]))
+-	}
+-	return s
+-}
+-
+-type NID struct {
+-	Hdr        RR_Header
+-	Preference uint16
+-	NodeID     uint64
+-}
+-
+-func (rr *NID) Header() *RR_Header { return &rr.Hdr }
+-func (rr *NID) copy() RR           { return &NID{*rr.Hdr.copyHeader(), rr.Preference, rr.NodeID} }
+-func (rr *NID) len() int           { return rr.Hdr.len() + 2 + 8 }
+-
+-func (rr *NID) String() string {
+-	s := rr.Hdr.String() + strconv.Itoa(int(rr.Preference))
+-	node := fmt.Sprintf("%0.16x", rr.NodeID)
+-	s += " " + node[0:4] + ":" + node[4:8] + ":" + node[8:12] + ":" + node[12:16]
+-	return s
+-}
+-
+-type L32 struct {
+-	Hdr        RR_Header
+-	Preference uint16
+-	Locator32  net.IP `dns:"a"`
+-}
+-
+-func (rr *L32) Header() *RR_Header { return &rr.Hdr }
+-func (rr *L32) copy() RR           { return &L32{*rr.Hdr.copyHeader(), rr.Preference, copyIP(rr.Locator32)} }
+-func (rr *L32) len() int           { return rr.Hdr.len() + net.IPv4len }
+-
+-func (rr *L32) String() string {
+-	if rr.Locator32 == nil {
+-		return rr.Hdr.String() + strconv.Itoa(int(rr.Preference))
+-	}
+-	return rr.Hdr.String() + strconv.Itoa(int(rr.Preference)) +
+-		" " + rr.Locator32.String()
+-}
+-
+-type L64 struct {
+-	Hdr        RR_Header
+-	Preference uint16
+-	Locator64  uint64
+-}
+-
+-func (rr *L64) Header() *RR_Header { return &rr.Hdr }
+-func (rr *L64) copy() RR           { return &L64{*rr.Hdr.copyHeader(), rr.Preference, rr.Locator64} }
+-func (rr *L64) len() int           { return rr.Hdr.len() + 2 + 8 }
+-
+-func (rr *L64) String() string {
+-	s := rr.Hdr.String() + strconv.Itoa(int(rr.Preference))
+-	node := fmt.Sprintf("%0.16X", rr.Locator64)
+-	s += " " + node[0:4] + ":" + node[4:8] + ":" + node[8:12] + ":" + node[12:16]
+-	return s
+-}
+-
+-type LP struct {
+-	Hdr        RR_Header
+-	Preference uint16
+-	Fqdn       string `dns:"domain-name"`
+-}
+-
+-func (rr *LP) Header() *RR_Header { return &rr.Hdr }
+-func (rr *LP) copy() RR           { return &LP{*rr.Hdr.copyHeader(), rr.Preference, rr.Fqdn} }
+-func (rr *LP) len() int           { return rr.Hdr.len() + 2 + len(rr.Fqdn) + 1 }
+-
+-func (rr *LP) String() string {
+-	return rr.Hdr.String() + strconv.Itoa(int(rr.Preference)) + " " + sprintName(rr.Fqdn)
+-}
+-
+-type EUI48 struct {
+-	Hdr     RR_Header
+-	Address uint64 `dns:"uint48"`
+-}
+-
+-func (rr *EUI48) Header() *RR_Header { return &rr.Hdr }
+-func (rr *EUI48) copy() RR           { return &EUI48{*rr.Hdr.copyHeader(), rr.Address} }
+-func (rr *EUI48) String() string     { return rr.Hdr.String() + euiToString(rr.Address, 48) }
+-func (rr *EUI48) len() int           { return rr.Hdr.len() + 6 }
+-
+-type EUI64 struct {
+-	Hdr     RR_Header
+-	Address uint64
+-}
+-
+-func (rr *EUI64) Header() *RR_Header { return &rr.Hdr }
+-func (rr *EUI64) copy() RR           { return &EUI64{*rr.Hdr.copyHeader(), rr.Address} }
+-func (rr *EUI64) String() string     { return rr.Hdr.String() + euiToString(rr.Address, 64) }
+-func (rr *EUI64) len() int           { return rr.Hdr.len() + 8 }
+-
+-// Support in incomplete - just handle it as unknown record
+-/*
+-type CAA struct {
+-	Hdr   RR_Header
+-	Flag  uint8
+-	Tag   string
+-	Value string `dns:"octet"`
+-}
+-
+-func (rr *CAA) Header() *RR_Header { return &rr.Hdr }
+-func (rr *CAA) copy() RR           { return &CAA{*rr.Hdr.copyHeader(), rr.Flag, rr.Tag, rr.Value} }
+-func (rr *CAA) len() int           { return rr.Hdr.len() + 1 + len(rr.Tag) + 1 + len(rr.Value) }
+-
+-func (rr *CAA) String() string {
+-	s := rr.Hdr.String() + strconv.FormatInt(int64(rr.Flag), 10) + " " + rr.Tag
+-	s += strconv.QuoteToASCII(rr.Value)
+-	return s
+-}
+-*/
+-
+-type UID struct {
+-	Hdr RR_Header
+-	Uid uint32
+-}
+-
+-func (rr *UID) Header() *RR_Header { return &rr.Hdr }
+-func (rr *UID) copy() RR           { return &UID{*rr.Hdr.copyHeader(), rr.Uid} }
+-func (rr *UID) String() string     { return rr.Hdr.String() + strconv.FormatInt(int64(rr.Uid), 10) }
+-func (rr *UID) len() int           { return rr.Hdr.len() + 4 }
+-
+-type GID struct {
+-	Hdr RR_Header
+-	Gid uint32
+-}
+-
+-func (rr *GID) Header() *RR_Header { return &rr.Hdr }
+-func (rr *GID) copy() RR           { return &GID{*rr.Hdr.copyHeader(), rr.Gid} }
+-func (rr *GID) String() string     { return rr.Hdr.String() + strconv.FormatInt(int64(rr.Gid), 10) }
+-func (rr *GID) len() int           { return rr.Hdr.len() + 4 }
+-
+-type UINFO struct {
+-	Hdr   RR_Header
+-	Uinfo string
+-}
+-
+-func (rr *UINFO) Header() *RR_Header { return &rr.Hdr }
+-func (rr *UINFO) copy() RR           { return &UINFO{*rr.Hdr.copyHeader(), rr.Uinfo} }
+-func (rr *UINFO) String() string     { return rr.Hdr.String() + sprintTxt([]string{rr.Uinfo}) }
+-func (rr *UINFO) len() int           { return rr.Hdr.len() + len(rr.Uinfo) + 1 }
+-
+-type EID struct {
+-	Hdr      RR_Header
+-	Endpoint string `dns:"hex"`
+-}
+-
+-func (rr *EID) Header() *RR_Header { return &rr.Hdr }
+-func (rr *EID) copy() RR           { return &EID{*rr.Hdr.copyHeader(), rr.Endpoint} }
+-func (rr *EID) String() string     { return rr.Hdr.String() + strings.ToUpper(rr.Endpoint) }
+-func (rr *EID) len() int           { return rr.Hdr.len() + len(rr.Endpoint)/2 }
+-
+-type NIMLOC struct {
+-	Hdr     RR_Header
+-	Locator string `dns:"hex"`
+-}
+-
+-func (rr *NIMLOC) Header() *RR_Header { return &rr.Hdr }
+-func (rr *NIMLOC) copy() RR           { return &NIMLOC{*rr.Hdr.copyHeader(), rr.Locator} }
+-func (rr *NIMLOC) String() string     { return rr.Hdr.String() + strings.ToUpper(rr.Locator) }
+-func (rr *NIMLOC) len() int           { return rr.Hdr.len() + len(rr.Locator)/2 }
+-
+-type OPENPGPKEY struct {
+-	Hdr       RR_Header
+-	PublicKey string `dns:"base64"`
+-}
+-
+-func (rr *OPENPGPKEY) Header() *RR_Header { return &rr.Hdr }
+-func (rr *OPENPGPKEY) copy() RR           { return &OPENPGPKEY{*rr.Hdr.copyHeader(), rr.PublicKey} }
+-func (rr *OPENPGPKEY) String() string     { return rr.Hdr.String() + rr.PublicKey }
+-func (rr *OPENPGPKEY) len() int {
+-	return rr.Hdr.len() + base64.StdEncoding.DecodedLen(len(rr.PublicKey))
+-}
+-
+-// TimeToString translates the RRSIG's incep. and expir. times to the
+-// string representation used when printing the record.
+-// It takes serial arithmetic (RFC 1982) into account.
+-func TimeToString(t uint32) string {
+-	mod := ((int64(t) - time.Now().Unix()) / year68) - 1
+-	if mod < 0 {
+-		mod = 0
+-	}
+-	ti := time.Unix(int64(t)-(mod*year68), 0).UTC()
+-	return ti.Format("20060102150405")
+-}
+-
+-// StringToTime translates the RRSIG's incep. and expir. times from
+-// string values like "20110403154150" to an 32 bit integer.
+-// It takes serial arithmetic (RFC 1982) into account.
+-func StringToTime(s string) (uint32, error) {
+-	t, e := time.Parse("20060102150405", s)
+-	if e != nil {
+-		return 0, e
+-	}
+-	mod := (t.Unix() / year68) - 1
+-	if mod < 0 {
+-		mod = 0
+-	}
+-	return uint32(t.Unix() - (mod * year68)), nil
+-}
+-
+-// saltToString converts a NSECX salt to uppercase and
+-// returns "-" when it is empty
+-func saltToString(s string) string {
+-	if len(s) == 0 {
+-		return "-"
+-	}
+-	return strings.ToUpper(s)
+-}
+-
+-func euiToString(eui uint64, bits int) (hex string) {
+-	switch bits {
+-	case 64:
+-		hex = fmt.Sprintf("%16.16x", eui)
+-		hex = hex[0:2] + "-" + hex[2:4] + "-" + hex[4:6] + "-" + hex[6:8] +
+-			"-" + hex[8:10] + "-" + hex[10:12] + "-" + hex[12:14] + "-" + hex[14:16]
+-	case 48:
+-		hex = fmt.Sprintf("%12.12x", eui)
+-		hex = hex[0:2] + "-" + hex[2:4] + "-" + hex[4:6] + "-" + hex[6:8] +
+-			"-" + hex[8:10] + "-" + hex[10:12]
+-	}
+-	return
+-}
+-
+-// copyIP returns a copy of ip.
+-func copyIP(ip net.IP) net.IP {
+-	p := make(net.IP, len(ip))
+-	copy(p, ip)
+-	return p
+-}
+-
+-// Map of constructors for each RR type.
+-var typeToRR = map[uint16]func() RR{
+-	TypeA:     func() RR { return new(A) },
+-	TypeAAAA:  func() RR { return new(AAAA) },
+-	TypeAFSDB: func() RR { return new(AFSDB) },
+-	//	TypeCAA:        func() RR { return new(CAA) },
+-	TypeCDS:        func() RR { return new(CDS) },
+-	TypeCERT:       func() RR { return new(CERT) },
+-	TypeCNAME:      func() RR { return new(CNAME) },
+-	TypeDHCID:      func() RR { return new(DHCID) },
+-	TypeDLV:        func() RR { return new(DLV) },
+-	TypeDNAME:      func() RR { return new(DNAME) },
+-	TypeKEY:        func() RR { return new(KEY) },
+-	TypeDNSKEY:     func() RR { return new(DNSKEY) },
+-	TypeDS:         func() RR { return new(DS) },
+-	TypeEUI48:      func() RR { return new(EUI48) },
+-	TypeEUI64:      func() RR { return new(EUI64) },
+-	TypeGID:        func() RR { return new(GID) },
+-	TypeGPOS:       func() RR { return new(GPOS) },
+-	TypeEID:        func() RR { return new(EID) },
+-	TypeHINFO:      func() RR { return new(HINFO) },
+-	TypeHIP:        func() RR { return new(HIP) },
+-	TypeKX:         func() RR { return new(KX) },
+-	TypeL32:        func() RR { return new(L32) },
+-	TypeL64:        func() RR { return new(L64) },
+-	TypeLOC:        func() RR { return new(LOC) },
+-	TypeLP:         func() RR { return new(LP) },
+-	TypeMB:         func() RR { return new(MB) },
+-	TypeMD:         func() RR { return new(MD) },
+-	TypeMF:         func() RR { return new(MF) },
+-	TypeMG:         func() RR { return new(MG) },
+-	TypeMINFO:      func() RR { return new(MINFO) },
+-	TypeMR:         func() RR { return new(MR) },
+-	TypeMX:         func() RR { return new(MX) },
+-	TypeNAPTR:      func() RR { return new(NAPTR) },
+-	TypeNID:        func() RR { return new(NID) },
+-	TypeNINFO:      func() RR { return new(NINFO) },
+-	TypeNIMLOC:     func() RR { return new(NIMLOC) },
+-	TypeNS:         func() RR { return new(NS) },
+-	TypeNSAP:       func() RR { return new(NSAP) },
+-	TypeNSAPPTR:    func() RR { return new(NSAPPTR) },
+-	TypeNSEC3:      func() RR { return new(NSEC3) },
+-	TypeNSEC3PARAM: func() RR { return new(NSEC3PARAM) },
+-	TypeNSEC:       func() RR { return new(NSEC) },
+-	TypeOPENPGPKEY: func() RR { return new(OPENPGPKEY) },
+-	TypeOPT:        func() RR { return new(OPT) },
+-	TypePTR:        func() RR { return new(PTR) },
+-	TypeRKEY:       func() RR { return new(RKEY) },
+-	TypeRP:         func() RR { return new(RP) },
+-	TypePX:         func() RR { return new(PX) },
+-	TypeSIG:        func() RR { return new(SIG) },
+-	TypeRRSIG:      func() RR { return new(RRSIG) },
+-	TypeRT:         func() RR { return new(RT) },
+-	TypeSOA:        func() RR { return new(SOA) },
+-	TypeSPF:        func() RR { return new(SPF) },
+-	TypeSRV:        func() RR { return new(SRV) },
+-	TypeSSHFP:      func() RR { return new(SSHFP) },
+-	TypeTA:         func() RR { return new(TA) },
+-	TypeTALINK:     func() RR { return new(TALINK) },
+-	TypeTKEY:       func() RR { return new(TKEY) },
+-	TypeTLSA:       func() RR { return new(TLSA) },
+-	TypeTSIG:       func() RR { return new(TSIG) },
+-	TypeTXT:        func() RR { return new(TXT) },
+-	TypeUID:        func() RR { return new(UID) },
+-	TypeUINFO:      func() RR { return new(UINFO) },
+-	TypeURI:        func() RR { return new(URI) },
+-	TypeWKS:        func() RR { return new(WKS) },
+-	TypeX25:        func() RR { return new(X25) },
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/types_test.go b/Godeps/_workspace/src/github.com/miekg/dns/types_test.go
+deleted file mode 100644
+index 1186129..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/types_test.go
++++ /dev/null
+@@ -1,42 +0,0 @@
+-package dns
+-
+-import (
+-	"testing"
+-)
+-
+-func TestCmToM(t *testing.T) {
+-	s := cmToM(0, 0)
+-	if s != "0.00" {
+-		t.Error("0, 0")
+-	}
+-
+-	s = cmToM(1, 0)
+-	if s != "0.01" {
+-		t.Error("1, 0")
+-	}
+-
+-	s = cmToM(3, 1)
+-	if s != "0.30" {
+-		t.Error("3, 1")
+-	}
+-
+-	s = cmToM(4, 2)
+-	if s != "4" {
+-		t.Error("4, 2")
+-	}
+-
+-	s = cmToM(5, 3)
+-	if s != "50" {
+-		t.Error("5, 3")
+-	}
+-
+-	s = cmToM(7, 5)
+-	if s != "7000" {
+-		t.Error("7, 5")
+-	}
+-
+-	s = cmToM(9, 9)
+-	if s != "90000000" {
+-		t.Error("9, 9")
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/udp.go b/Godeps/_workspace/src/github.com/miekg/dns/udp.go
+deleted file mode 100644
+index 0342543..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/udp.go
++++ /dev/null
+@@ -1,55 +0,0 @@
+-// +build !windows
+-
+-package dns
+-
+-import (
+-	"net"
+-	"syscall"
+-)
+-
+-type sessionUDP struct {
+-	raddr   *net.UDPAddr
+-	context []byte
+-}
+-
+-func (s *sessionUDP) RemoteAddr() net.Addr { return s.raddr }
+-
+-// setUDPSocketOptions sets the UDP socket options.
+-// This function is implemented on a per platform basis. See udp_*.go for more details
+-func setUDPSocketOptions(conn *net.UDPConn) error {
+-	sa, err := getUDPSocketName(conn)
+-	if err != nil {
+-		return err
+-	}
+-	switch sa.(type) {
+-	case *syscall.SockaddrInet6:
+-		v6only, err := getUDPSocketOptions6Only(conn)
+-		if err != nil {
+-			return err
+-		}
+-		setUDPSocketOptions6(conn)
+-		if !v6only {
+-			setUDPSocketOptions4(conn)
+-		}
+-	case *syscall.SockaddrInet4:
+-		setUDPSocketOptions4(conn)
+-	}
+-	return nil
+-}
+-
+-// readFromSessionUDP acts just like net.UDPConn.ReadFrom(), but returns a session object instead of a
+-// net.UDPAddr.
+-func readFromSessionUDP(conn *net.UDPConn, b []byte) (int, *sessionUDP, error) {
+-	oob := make([]byte, 40)
+-	n, oobn, _, raddr, err := conn.ReadMsgUDP(b, oob)
+-	if err != nil {
+-		return n, nil, err
+-	}
+-	return n, &sessionUDP{raddr, oob[:oobn]}, err
+-}
+-
+-// writeToSessionUDP acts just like net.UDPConn.WritetTo(), but uses a *sessionUDP instead of a net.Addr.
+-func writeToSessionUDP(conn *net.UDPConn, b []byte, session *sessionUDP) (int, error) {
+-	n, _, err := conn.WriteMsgUDP(b, session.context, session.raddr)
+-	return n, err
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/udp_linux.go b/Godeps/_workspace/src/github.com/miekg/dns/udp_linux.go
+deleted file mode 100644
+index 7a10785..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/udp_linux.go
++++ /dev/null
+@@ -1,63 +0,0 @@
+-// +build linux
+-
+-package dns
+-
+-// See:
+-// * http://stackoverflow.com/questions/3062205/setting-the-source-ip-for-a-udp-socket and
+-// * http://blog.powerdns.com/2012/10/08/on-binding-datagram-udp-sockets-to-the-any-addresses/
+-//
+-// Why do we need this: When listening on 0.0.0.0 with UDP so kernel decides what is the outgoing
+-// interface, this might not always be the correct one. This code will make sure the egress
+-// packet's interface matched the ingress' one.
+-
+-import (
+-	"net"
+-	"syscall"
+-)
+-
+-// setUDPSocketOptions4 prepares the v4 socket for sessions.
+-func setUDPSocketOptions4(conn *net.UDPConn) error {
+-	file, err := conn.File()
+-	if err != nil {
+-		return err
+-	}
+-	if err := syscall.SetsockoptInt(int(file.Fd()), syscall.IPPROTO_IP, syscall.IP_PKTINFO, 1); err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-// setUDPSocketOptions6 prepares the v6 socket for sessions.
+-func setUDPSocketOptions6(conn *net.UDPConn) error {
+-	file, err := conn.File()
+-	if err != nil {
+-		return err
+-	}
+-	if err := syscall.SetsockoptInt(int(file.Fd()), syscall.IPPROTO_IPV6, syscall.IPV6_RECVPKTINFO, 1); err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-// getUDPSocketOption6Only return true if the socket is v6 only and false when it is v4/v6 combined
+-// (dualstack).
+-func getUDPSocketOptions6Only(conn *net.UDPConn) (bool, error) {
+-	file, err := conn.File()
+-	if err != nil {
+-		return false, err
+-	}
+-	// dual stack. See http://stackoverflow.com/questions/1618240/how-to-support-both-ipv4-and-ipv6-connections
+-	v6only, err := syscall.GetsockoptInt(int(file.Fd()), syscall.IPPROTO_IPV6, syscall.IPV6_V6ONLY)
+-	if err != nil {
+-		return false, err
+-	}
+-	return v6only == 1, nil
+-}
+-
+-func getUDPSocketName(conn *net.UDPConn) (syscall.Sockaddr, error) {
+-	file, err := conn.File()
+-	if err != nil {
+-		return nil, err
+-	}
+-	return syscall.Getsockname(int(file.Fd()))
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/udp_other.go b/Godeps/_workspace/src/github.com/miekg/dns/udp_other.go
+deleted file mode 100644
+index c38dd3e..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/udp_other.go
++++ /dev/null
+@@ -1,17 +0,0 @@
+-// +build !linux
+-
+-package dns
+-
+-import (
+-	"net"
+-	"syscall"
+-)
+-
+-// These do nothing. See udp_linux.go for an example of how to implement this.
+-
+-// We tried to adhire to some kind of naming scheme.
+-
+-func setUDPSocketOptions4(conn *net.UDPConn) error                 { return nil }
+-func setUDPSocketOptions6(conn *net.UDPConn) error                 { return nil }
+-func getUDPSocketOptions6Only(conn *net.UDPConn) (bool, error)     { return false, nil }
+-func getUDPSocketName(conn *net.UDPConn) (syscall.Sockaddr, error) { return nil, nil }
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/udp_windows.go b/Godeps/_workspace/src/github.com/miekg/dns/udp_windows.go
+deleted file mode 100644
+index 4c48723..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/udp_windows.go
++++ /dev/null
+@@ -1,34 +0,0 @@
+-// +build windows
+-
+-package dns
+-
+-import "net"
+-
+-type sessionUDP struct {
+-	raddr *net.UDPAddr
+-}
+-
+-// readFromSessionUDP acts just like net.UDPConn.ReadFrom(), but returns a session object instead of a
+-// net.UDPAddr.
+-func readFromSessionUDP(conn *net.UDPConn, b []byte) (int, *sessionUDP, error) {
+-	n, raddr, err := conn.ReadFrom(b)
+-	if err != nil {
+-		return n, nil, err
+-	}
+-	session := &sessionUDP{raddr.(*net.UDPAddr)}
+-	return n, session, err
+-}
+-
+-// writeToSessionUDP acts just like net.UDPConn.WritetTo(), but uses a *sessionUDP instead of a net.Addr.
+-func writeToSessionUDP(conn *net.UDPConn, b []byte, session *sessionUDP) (int, error) {
+-	n, err := conn.WriteTo(b, session.raddr)
+-	return n, err
+-}
+-
+-func (s *sessionUDP) RemoteAddr() net.Addr { return s.raddr }
+-
+-// setUDPSocketOptions sets the UDP socket options.
+-// This function is implemented on a per platform basis. See udp_*.go for more details
+-func setUDPSocketOptions(conn *net.UDPConn) error {
+-	return nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/update.go b/Godeps/_workspace/src/github.com/miekg/dns/update.go
+deleted file mode 100644
+index 275d4e6..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/update.go
++++ /dev/null
+@@ -1,138 +0,0 @@
+-// DYNAMIC UPDATES
+-//
+-// Dynamic updates reuses the DNS message format, but renames three of
+-// the sections. Question is Zone, Answer is Prerequisite, Authority is
+-// Update, only the Additional is not renamed. See RFC 2136 for the gory details.
+-//
+-// You can set a rather complex set of rules for the existence of absence of
+-// certain resource records or names in a zone to specify if resource records
+-// should be added or removed. The table from RFC 2136 supplemented with the Go
+-// DNS function shows which functions exist to specify the prerequisites.
+-//
+-// 3.2.4 - Table Of Metavalues Used In Prerequisite Section
+-//
+-//   CLASS    TYPE     RDATA    Meaning                    Function
+-//   --------------------------------------------------------------
+-//   ANY      ANY      empty    Name is in use             dns.NameUsed
+-//   ANY      rrset    empty    RRset exists (value indep) dns.RRsetUsed
+-//   NONE     ANY      empty    Name is not in use         dns.NameNotUsed
+-//   NONE     rrset    empty    RRset does not exist       dns.RRsetNotUsed
+-//   zone     rrset    rr       RRset exists (value dep)   dns.Used
+-//
+-// The prerequisite section can also be left empty.
+-// If you have decided on the prerequisites you can tell what RRs should
+-// be added or deleted. The next table shows the options you have and
+-// what functions to call.
+-//
+-// 3.4.2.6 - Table Of Metavalues Used In Update Section
+-//
+-//   CLASS    TYPE     RDATA    Meaning                     Function
+-//   ---------------------------------------------------------------
+-//   ANY      ANY      empty    Delete all RRsets from name dns.RemoveName
+-//   ANY      rrset    empty    Delete an RRset             dns.RemoveRRset
+-//   NONE     rrset    rr       Delete an RR from RRset     dns.Remove
+-//   zone     rrset    rr       Add to an RRset             dns.Insert
+-//
+-package dns
+-
+-// NameUsed sets the RRs in the prereq section to
+-// "Name is in use" RRs. RFC 2136 section 2.4.4.
+-func (u *Msg) NameUsed(rr []RR) {
+-	u.Answer = make([]RR, len(rr))
+-	for i, r := range rr {
+-		u.Answer[i] = &ANY{Hdr: RR_Header{Name: r.Header().Name, Ttl: 0, Rrtype: TypeANY, Class: ClassANY}}
+-	}
+-}
+-
+-// NameNotUsed sets the RRs in the prereq section to
+-// "Name is in not use" RRs. RFC 2136 section 2.4.5.
+-func (u *Msg) NameNotUsed(rr []RR) {
+-	u.Answer = make([]RR, len(rr))
+-	for i, r := range rr {
+-		u.Answer[i] = &ANY{Hdr: RR_Header{Name: r.Header().Name, Ttl: 0, Rrtype: TypeANY, Class: ClassNONE}}
+-	}
+-}
+-
+-// Used sets the RRs in the prereq section to
+-// "RRset exists (value dependent -- with rdata)" RRs. RFC 2136 section 2.4.2.
+-func (u *Msg) Used(rr []RR) {
+-	if len(u.Question) == 0 {
+-		panic("dns: empty question section")
+-	}
+-	u.Answer = make([]RR, len(rr))
+-	for i, r := range rr {
+-		u.Answer[i] = r
+-		u.Answer[i].Header().Class = u.Question[0].Qclass
+-	}
+-}
+-
+-// RRsetUsed sets the RRs in the prereq section to
+-// "RRset exists (value independent -- no rdata)" RRs. RFC 2136 section 2.4.1.
+-func (u *Msg) RRsetUsed(rr []RR) {
+-	u.Answer = make([]RR, len(rr))
+-	for i, r := range rr {
+-		u.Answer[i] = r
+-		u.Answer[i].Header().Class = ClassANY
+-		u.Answer[i].Header().Ttl = 0
+-		u.Answer[i].Header().Rdlength = 0
+-	}
+-}
+-
+-// RRsetNotUsed sets the RRs in the prereq section to
+-// "RRset does not exist" RRs. RFC 2136 section 2.4.3.
+-func (u *Msg) RRsetNotUsed(rr []RR) {
+-	u.Answer = make([]RR, len(rr))
+-	for i, r := range rr {
+-		u.Answer[i] = r
+-		u.Answer[i].Header().Class = ClassNONE
+-		u.Answer[i].Header().Rdlength = 0
+-		u.Answer[i].Header().Ttl = 0
+-	}
+-}
+-
+-// Insert creates a dynamic update packet that adds an complete RRset, see RFC 2136 section 2.5.1.
+-func (u *Msg) Insert(rr []RR) {
+-	if len(u.Question) == 0 {
+-		panic("dns: empty question section")
+-	}
+-	u.Ns = make([]RR, len(rr))
+-	for i, r := range rr {
+-		u.Ns[i] = r
+-		u.Ns[i].Header().Class = u.Question[0].Qclass
+-	}
+-}
+-
+-// RemoveRRset creates a dynamic update packet that deletes an RRset, see RFC 2136 section 2.5.2.
+-func (u *Msg) RemoveRRset(rr []RR) {
+-	m := make(map[RR_Header]struct{})
+-	u.Ns = make([]RR, 0, len(rr))
+-	for _, r := range rr {
+-		h := *r.Header().copyHeader()
+-		h.Class = ClassANY
+-		h.Ttl = 0
+-		h.Rdlength = 0
+-		if _, ok := m[h]; ok {
+-			continue
+-		}
+-		m[h] = struct{}{}
+-		u.Ns = append(u.Ns, &ANY{h})
+-	}
+-}
+-
+-// RemoveName creates a dynamic update packet that deletes all RRsets of a name, see RFC 2136 section 2.5.3
+-func (u *Msg) RemoveName(rr []RR) {
+-	u.Ns = make([]RR, len(rr))
+-	for i, r := range rr {
+-		u.Ns[i] = &ANY{Hdr: RR_Header{Name: r.Header().Name, Ttl: 0, Rrtype: TypeANY, Class: ClassANY}}
+-	}
+-}
+-
+-// Remove creates a dynamic update packet deletes RR from the RRSset, see RFC 2136 section 2.5.4
+-func (u *Msg) Remove(rr []RR) {
+-	u.Ns = make([]RR, len(rr))
+-	for i, r := range rr {
+-		u.Ns[i] = r
+-		u.Ns[i].Header().Class = ClassNONE
+-		u.Ns[i].Header().Ttl = 0
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/update_test.go b/Godeps/_workspace/src/github.com/miekg/dns/update_test.go
+deleted file mode 100644
+index fc22536..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/update_test.go
++++ /dev/null
+@@ -1,105 +0,0 @@
+-package dns
+-
+-import (
+-	"bytes"
+-	"testing"
+-)
+-
+-func TestDynamicUpdateParsing(t *testing.T) {
+-	prefix := "example.com. IN "
+-	for _, typ := range TypeToString {
+-		if typ == "CAA" || typ == "OPT" || typ == "AXFR" || typ == "IXFR" || typ == "ANY" || typ == "TKEY" ||
+-			typ == "TSIG" || typ == "ISDN" || typ == "UNSPEC" || typ == "NULL" || typ == "ATMA" {
+-			continue
+-		}
+-		r, e := NewRR(prefix + typ)
+-		if e != nil {
+-			t.Log("failure to parse: " + prefix + typ)
+-			t.Fail()
+-		} else {
+-			t.Logf("parsed: %s", r.String())
+-		}
+-	}
+-}
+-
+-func TestDynamicUpdateUnpack(t *testing.T) {
+-	// From https://github.com/miekg/dns/issues/150#issuecomment-62296803
+-	// It should be an update message for the zone "example.",
+-	// deleting the A RRset "example." and then adding an A record at "example.".
+-	// class ANY, TYPE A
+-	buf := []byte{171, 68, 40, 0, 0, 1, 0, 0, 0, 2, 0, 0, 7, 101, 120, 97, 109, 112, 108, 101, 0, 0, 6, 0, 1, 192, 12, 0, 1, 0, 255, 0, 0, 0, 0, 0, 0, 192, 12, 0, 1, 0, 1, 0, 0, 0, 0, 0, 4, 127, 0, 0, 1}
+-	msg := new(Msg)
+-	err := msg.Unpack(buf)
+-	if err != nil {
+-		t.Log("failed to unpack: " + err.Error() + "\n" + msg.String())
+-		t.Fail()
+-	}
+-}
+-
+-func TestDynamicUpdateZeroRdataUnpack(t *testing.T) {
+-	m := new(Msg)
+-	rr := &RR_Header{Name: ".", Rrtype: 0, Class: 1, Ttl: ^uint32(0), Rdlength: 0}
+-	m.Answer = []RR{rr, rr, rr, rr, rr}
+-	m.Ns = m.Answer
+-	for n, s := range TypeToString {
+-		rr.Rrtype = n
+-		bytes, err := m.Pack()
+-		if err != nil {
+-			t.Logf("failed to pack %s: %v", s, err)
+-			t.Fail()
+-			continue
+-		}
+-		if err := new(Msg).Unpack(bytes); err != nil {
+-			t.Logf("failed to unpack %s: %v", s, err)
+-			t.Fail()
+-		}
+-	}
+-}
+-
+-func TestRemoveRRset(t *testing.T) {
+-	// Should add a zero data RR in Class ANY with a TTL of 0
+-	// for each set mentioned in the RRs provided to it.
+-	rr, err := NewRR(". 100 IN A 127.0.0.1")
+-	if err != nil {
+-		t.Fatalf("Error constructing RR: %v", err)
+-	}
+-	m := new(Msg)
+-	m.Ns = []RR{&RR_Header{Name: ".", Rrtype: TypeA, Class: ClassANY, Ttl: 0, Rdlength: 0}}
+-	expectstr := m.String()
+-	expect, err := m.Pack()
+-	if err != nil {
+-		t.Fatalf("Error packing expected msg: %v", err)
+-	}
+-
+-	m.Ns = nil
+-	m.RemoveRRset([]RR{rr})
+-	actual, err := m.Pack()
+-	if err != nil {
+-		t.Fatalf("Error packing actual msg: %v", err)
+-	}
+-	if !bytes.Equal(actual, expect) {
+-		tmp := new(Msg)
+-		if err := tmp.Unpack(actual); err != nil {
+-			t.Fatalf("Error unpacking actual msg: %v", err)
+-		}
+-		t.Logf("Expected msg:\n%s", expectstr)
+-		t.Logf("Actual msg:\n%v", tmp)
+-		t.Fail()
+-	}
+-
+-	m.Ns = nil
+-	m.RemoveRRset([]RR{rr, rr})
+-	actual, err = m.Pack()
+-	if err != nil {
+-		t.Fatalf("Error packing actual msg: %v", err)
+-	}
+-	if !bytes.Equal(actual, expect) {
+-		tmp := new(Msg)
+-		if err := tmp.Unpack(actual); err != nil {
+-			t.Fatalf("Error unpacking actual msg: %v", err)
+-		}
+-		t.Logf("Expected msg:\n%v", expectstr)
+-		t.Logf("Actual msg:\n%v", tmp)
+-		t.Fail()
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/xfr.go b/Godeps/_workspace/src/github.com/miekg/dns/xfr.go
+deleted file mode 100644
+index 57bfb16..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/xfr.go
++++ /dev/null
+@@ -1,236 +0,0 @@
+-package dns
+-
+-import (
+-	"time"
+-)
+-
+-// Envelope is used when doing a zone transfer with a remote server.
+-type Envelope struct {
+-	RR    []RR  // The set of RRs in the answer section of the xfr reply message.
+-	Error error // If something went wrong, this contains the error.
+-}
+-
+-// A Transfer defines parameters that are used during a zone transfer.
+-type Transfer struct {
+-	*Conn
+-	DialTimeout    time.Duration     // net.DialTimeout (ns), defaults to 2 * 1e9
+-	ReadTimeout    time.Duration     // net.Conn.SetReadTimeout value for connections (ns), defaults to 2 * 1e9
+-	WriteTimeout   time.Duration     // net.Conn.SetWriteTimeout value for connections (ns), defaults to 2 * 1e9
+-	TsigSecret     map[string]string // Secret(s) for Tsig map[<zonename>]<base64 secret>, zonename must be fully qualified
+-	tsigTimersOnly bool
+-}
+-
+-// Think we need to away to stop the transfer
+-
+-// In performs an incoming transfer with the server in a.
+-func (t *Transfer) In(q *Msg, a string) (env chan *Envelope, err error) {
+-	timeout := dnsTimeout
+-	if t.DialTimeout != 0 {
+-		timeout = t.DialTimeout
+-	}
+-	t.Conn, err = DialTimeout("tcp", a, timeout)
+-	if err != nil {
+-		return nil, err
+-	}
+-	if err := t.WriteMsg(q); err != nil {
+-		return nil, err
+-	}
+-	env = make(chan *Envelope)
+-	go func() {
+-		if q.Question[0].Qtype == TypeAXFR {
+-			go t.inAxfr(q.Id, env)
+-			return
+-		}
+-		if q.Question[0].Qtype == TypeIXFR {
+-			go t.inIxfr(q.Id, env)
+-			return
+-		}
+-	}()
+-	return env, nil
+-}
+-
+-func (t *Transfer) inAxfr(id uint16, c chan *Envelope) {
+-	first := true
+-	defer t.Close()
+-	defer close(c)
+-	timeout := dnsTimeout
+-	if t.ReadTimeout != 0 {
+-		timeout = t.ReadTimeout
+-	}
+-	for {
+-		t.Conn.SetReadDeadline(time.Now().Add(timeout))
+-		in, err := t.ReadMsg()
+-		if err != nil {
+-			c <- &Envelope{nil, err}
+-			return
+-		}
+-		if id != in.Id {
+-			c <- &Envelope{in.Answer, ErrId}
+-			return
+-		}
+-		if first {
+-			if !isSOAFirst(in) {
+-				c <- &Envelope{in.Answer, ErrSoa}
+-				return
+-			}
+-			first = !first
+-			// only one answer that is SOA, receive more
+-			if len(in.Answer) == 1 {
+-				t.tsigTimersOnly = true
+-				c <- &Envelope{in.Answer, nil}
+-				continue
+-			}
+-		}
+-
+-		if !first {
+-			t.tsigTimersOnly = true // Subsequent envelopes use this.
+-			if isSOALast(in) {
+-				c <- &Envelope{in.Answer, nil}
+-				return
+-			}
+-			c <- &Envelope{in.Answer, nil}
+-		}
+-	}
+-	panic("dns: not reached")
+-}
+-
+-func (t *Transfer) inIxfr(id uint16, c chan *Envelope) {
+-	serial := uint32(0) // The first serial seen is the current server serial
+-	first := true
+-	defer t.Close()
+-	defer close(c)
+-	timeout := dnsTimeout
+-	if t.ReadTimeout != 0 {
+-		timeout = t.ReadTimeout
+-	}
+-	for {
+-		t.SetReadDeadline(time.Now().Add(timeout))
+-		in, err := t.ReadMsg()
+-		if err != nil {
+-			c <- &Envelope{in.Answer, err}
+-			return
+-		}
+-		if id != in.Id {
+-			c <- &Envelope{in.Answer, ErrId}
+-			return
+-		}
+-		if first {
+-			// A single SOA RR signals "no changes"
+-			if len(in.Answer) == 1 && isSOAFirst(in) {
+-				c <- &Envelope{in.Answer, nil}
+-				return
+-			}
+-
+-			// Check if the returned answer is ok
+-			if !isSOAFirst(in) {
+-				c <- &Envelope{in.Answer, ErrSoa}
+-				return
+-			}
+-			// This serial is important
+-			serial = in.Answer[0].(*SOA).Serial
+-			first = !first
+-		}
+-
+-		// Now we need to check each message for SOA records, to see what we need to do
+-		if !first {
+-			t.tsigTimersOnly = true
+-			// If the last record in the IXFR contains the servers' SOA,  we should quit
+-			if v, ok := in.Answer[len(in.Answer)-1].(*SOA); ok {
+-				if v.Serial == serial {
+-					c <- &Envelope{in.Answer, nil}
+-					return
+-				}
+-			}
+-			c <- &Envelope{in.Answer, nil}
+-		}
+-	}
+-}
+-
+-// Out performs an outgoing transfer with the client connecting in w.
+-// Basic use pattern:
+-//
+-//	ch := make(chan *dns.Envelope)
+-//	tr := new(dns.Transfer)
+-//	tr.Out(w, r, ch)
+-//	c <- &dns.Envelope{RR: []dns.RR{soa, rr1, rr2, rr3, soa}}
+-//	close(ch)
+-//	w.Hijack()
+-//	// w.Close() // Client closes connection
+-//
+-// The server is responsible for sending the correct sequence of RRs through the
+-// channel ch.
+-func (t *Transfer) Out(w ResponseWriter, q *Msg, ch chan *Envelope) error {
+-	r := new(Msg)
+-	// Compress?
+-	r.SetReply(q)
+-	r.Authoritative = true
+-
+-	go func() {
+-		for x := range ch {
+-			// assume it fits TODO(miek): fix
+-			r.Answer = append(r.Answer, x.RR...)
+-			if err := w.WriteMsg(r); err != nil {
+-				return
+-			}
+-		}
+-		w.TsigTimersOnly(true)
+-		r.Answer = nil
+-	}()
+-	return nil
+-}
+-
+-// ReadMsg reads a message from the transfer connection t.
+-func (t *Transfer) ReadMsg() (*Msg, error) {
+-	m := new(Msg)
+-	p := make([]byte, MaxMsgSize)
+-	n, err := t.Read(p)
+-	if err != nil && n == 0 {
+-		return nil, err
+-	}
+-	p = p[:n]
+-	if err := m.Unpack(p); err != nil {
+-		return nil, err
+-	}
+-	if ts := m.IsTsig(); ts != nil && t.TsigSecret != nil {
+-		if _, ok := t.TsigSecret[ts.Hdr.Name]; !ok {
+-			return m, ErrSecret
+-		}
+-		// Need to work on the original message p, as that was used to calculate the tsig.
+-		err = TsigVerify(p, t.TsigSecret[ts.Hdr.Name], t.tsigRequestMAC, t.tsigTimersOnly)
+-	}
+-	return m, err
+-}
+-
+-// WriteMsg writes a message through the transfer connection t.
+-func (t *Transfer) WriteMsg(m *Msg) (err error) {
+-	var out []byte
+-	if ts := m.IsTsig(); ts != nil && t.TsigSecret != nil {
+-		if _, ok := t.TsigSecret[ts.Hdr.Name]; !ok {
+-			return ErrSecret
+-		}
+-		out, t.tsigRequestMAC, err = TsigGenerate(m, t.TsigSecret[ts.Hdr.Name], t.tsigRequestMAC, t.tsigTimersOnly)
+-	} else {
+-		out, err = m.Pack()
+-	}
+-	if err != nil {
+-		return err
+-	}
+-	if _, err = t.Write(out); err != nil {
+-		return err
+-	}
+-	return nil
+-}
+-
+-func isSOAFirst(in *Msg) bool {
+-	if len(in.Answer) > 0 {
+-		return in.Answer[0].Header().Rrtype == TypeSOA
+-	}
+-	return false
+-}
+-
+-func isSOALast(in *Msg) bool {
+-	if len(in.Answer) > 0 {
+-		return in.Answer[len(in.Answer)-1].Header().Rrtype == TypeSOA
+-	}
+-	return false
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/zgenerate.go b/Godeps/_workspace/src/github.com/miekg/dns/zgenerate.go
+deleted file mode 100644
+index 7f1183e..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/zgenerate.go
++++ /dev/null
+@@ -1,157 +0,0 @@
+-package dns
+-
+-import (
+-	"fmt"
+-	"strconv"
+-	"strings"
+-)
+-
+-// Parse the $GENERATE statement as used in BIND9 zones.
+-// See http://www.zytrax.com/books/dns/ch8/generate.html for instance.
+-// We are called after '$GENERATE '. After which we expect:
+-// * the range (12-24/2)
+-// * lhs (ownername)
+-// * [[ttl][class]]
+-// * type
+-// * rhs (rdata)
+-// But we are lazy here, only the range is parsed *all* occurences
+-// of $ after that are interpreted.
+-// Any error are returned as a string value, the empty string signals
+-// "no error".
+-func generate(l lex, c chan lex, t chan *Token, o string) string {
+-	step := 1
+-	if i := strings.IndexAny(l.token, "/"); i != -1 {
+-		if i+1 == len(l.token) {
+-			return "bad step in $GENERATE range"
+-		}
+-		if s, e := strconv.Atoi(l.token[i+1:]); e != nil {
+-			return "bad step in $GENERATE range"
+-		} else {
+-			if s < 0 {
+-				return "bad step in $GENERATE range"
+-			}
+-			step = s
+-		}
+-		l.token = l.token[:i]
+-	}
+-	sx := strings.SplitN(l.token, "-", 2)
+-	if len(sx) != 2 {
+-		return "bad start-stop in $GENERATE range"
+-	}
+-	start, err := strconv.Atoi(sx[0])
+-	if err != nil {
+-		return "bad start in $GENERATE range"
+-	}
+-	end, err := strconv.Atoi(sx[1])
+-	if err != nil {
+-		return "bad stop in $GENERATE range"
+-	}
+-	if end < 0 || start < 0 || end <= start {
+-		return "bad range in $GENERATE range"
+-	}
+-
+-	<-c // _BLANK
+-	// Create a complete new string, which we then parse again.
+-	s := ""
+-BuildRR:
+-	l = <-c
+-	if l.value != _NEWLINE && l.value != _EOF {
+-		s += l.token
+-		goto BuildRR
+-	}
+-	for i := start; i <= end; i += step {
+-		var (
+-			escape bool
+-			dom    string
+-			mod    string
+-			err    string
+-			offset int
+-		)
+-
+-		for j := 0; j < len(s); j++ { // No 'range' because we need to jump around
+-			switch s[j] {
+-			case '\\':
+-				if escape {
+-					dom += "\\"
+-					escape = false
+-					continue
+-				}
+-				escape = true
+-			case '$':
+-				mod = "%d"
+-				offset = 0
+-				if escape {
+-					dom += "$"
+-					escape = false
+-					continue
+-				}
+-				escape = false
+-				if j+1 >= len(s) { // End of the string
+-					dom += fmt.Sprintf(mod, i+offset)
+-					continue
+-				} else {
+-					if s[j+1] == '$' {
+-						dom += "$"
+-						j++
+-						continue
+-					}
+-				}
+-				// Search for { and }
+-				if s[j+1] == '{' { // Modifier block
+-					sep := strings.Index(s[j+2:], "}")
+-					if sep == -1 {
+-						return "bad modifier in $GENERATE"
+-					}
+-					mod, offset, err = modToPrintf(s[j+2 : j+2+sep])
+-					if err != "" {
+-						return err
+-					}
+-					j += 2 + sep // Jump to it
+-				}
+-				dom += fmt.Sprintf(mod, i+offset)
+-			default:
+-				if escape { // Pretty useless here
+-					escape = false
+-					continue
+-				}
+-				dom += string(s[j])
+-			}
+-		}
+-		// Re-parse the RR and send it on the current channel t
+-		rx, e := NewRR("$ORIGIN " + o + "\n" + dom)
+-		if e != nil {
+-			return e.(*ParseError).err
+-		}
+-		t <- &Token{RR: rx}
+-		// Its more efficient to first built the rrlist and then parse it in
+-		// one go! But is this a problem?
+-	}
+-	return ""
+-}
+-
+-// Convert a $GENERATE modifier 0,0,d to something Printf can deal with.
+-func modToPrintf(s string) (string, int, string) {
+-	xs := strings.SplitN(s, ",", 3)
+-	if len(xs) != 3 {
+-		return "", 0, "bad modifier in $GENERATE"
+-	}
+-	// xs[0] is offset, xs[1] is width, xs[2] is base
+-	if xs[2] != "o" && xs[2] != "d" && xs[2] != "x" && xs[2] != "X" {
+-		return "", 0, "bad base in $GENERATE"
+-	}
+-	offset, err := strconv.Atoi(xs[0])
+-	if err != nil {
+-		return "", 0, "bad offset in $GENERATE"
+-	}
+-	width, err := strconv.Atoi(xs[1])
+-	if err != nil {
+-		return "", offset, "bad width in $GENERATE"
+-	}
+-	switch {
+-	case width < 0:
+-		return "", offset, "bad width in $GENERATE"
+-	case width == 0:
+-		return "%" + xs[1] + xs[2], offset, ""
+-	}
+-	return "%0" + xs[1] + xs[2], offset, ""
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/zscan.go b/Godeps/_workspace/src/github.com/miekg/dns/zscan.go
+deleted file mode 100644
+index 7ba5198..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/zscan.go
++++ /dev/null
+@@ -1,956 +0,0 @@
+-package dns
+-
+-import (
+-	"io"
+-	"log"
+-	"os"
+-	"strconv"
+-	"strings"
+-)
+-
+-type debugging bool
+-
+-const debug debugging = false
+-
+-func (d debugging) Printf(format string, args ...interface{}) {
+-	if d {
+-		log.Printf(format, args...)
+-	}
+-}
+-
+-const maxTok = 2048 // Largest token we can return.
+-const maxUint16 = 1<<16 - 1
+-
+-// Tokinize a RFC 1035 zone file. The tokenizer will normalize it:
+-// * Add ownernames if they are left blank;
+-// * Suppress sequences of spaces;
+-// * Make each RR fit on one line (_NEWLINE is send as last)
+-// * Handle comments: ;
+-// * Handle braces - anywhere.
+-const (
+-	// Zonefile
+-	_EOF = iota
+-	_STRING
+-	_BLANK
+-	_QUOTE
+-	_NEWLINE
+-	_RRTYPE
+-	_OWNER
+-	_CLASS
+-	_DIRORIGIN   // $ORIGIN
+-	_DIRTTL      // $TTL
+-	_DIRINCLUDE  // $INCLUDE
+-	_DIRGENERATE // $GENERATE
+-
+-	// Privatekey file
+-	_VALUE
+-	_KEY
+-
+-	_EXPECT_OWNER_DIR      // Ownername
+-	_EXPECT_OWNER_BL       // Whitespace after the ownername
+-	_EXPECT_ANY            // Expect rrtype, ttl or class
+-	_EXPECT_ANY_NOCLASS    // Expect rrtype or ttl
+-	_EXPECT_ANY_NOCLASS_BL // The whitespace after _EXPECT_ANY_NOCLASS
+-	_EXPECT_ANY_NOTTL      // Expect rrtype or class
+-	_EXPECT_ANY_NOTTL_BL   // Whitespace after _EXPECT_ANY_NOTTL
+-	_EXPECT_RRTYPE         // Expect rrtype
+-	_EXPECT_RRTYPE_BL      // Whitespace BEFORE rrtype
+-	_EXPECT_RDATA          // The first element of the rdata
+-	_EXPECT_DIRTTL_BL      // Space after directive $TTL
+-	_EXPECT_DIRTTL         // Directive $TTL
+-	_EXPECT_DIRORIGIN_BL   // Space after directive $ORIGIN
+-	_EXPECT_DIRORIGIN      // Directive $ORIGIN
+-	_EXPECT_DIRINCLUDE_BL  // Space after directive $INCLUDE
+-	_EXPECT_DIRINCLUDE     // Directive $INCLUDE
+-	_EXPECT_DIRGENERATE    // Directive $GENERATE
+-	_EXPECT_DIRGENERATE_BL // Space after directive $GENERATE
+-)
+-
+-// ParseError is a parsing error. It contains the parse error and the location in the io.Reader
+-// where the error occured.
+-type ParseError struct {
+-	file string
+-	err  string
+-	lex  lex
+-}
+-
+-func (e *ParseError) Error() (s string) {
+-	if e.file != "" {
+-		s = e.file + ": "
+-	}
+-	s += "dns: " + e.err + ": " + strconv.QuoteToASCII(e.lex.token) + " at line: " +
+-		strconv.Itoa(e.lex.line) + ":" + strconv.Itoa(e.lex.column)
+-	return
+-}
+-
+-type lex struct {
+-	token      string // text of the token
+-	tokenUpper string // uppercase text of the token
+-	length     int    // lenght of the token
+-	err        bool   // when true, token text has lexer error
+-	value      uint8  // value: _STRING, _BLANK, etc.
+-	line       int    // line in the file
+-	column     int    // column in the file
+-	torc       uint16 // type or class as parsed in the lexer, we only need to look this up in the grammar
+-	comment    string // any comment text seen
+-}
+-
+-// *Tokens are returned when a zone file is parsed.
+-type Token struct {
+-	RR                  // the scanned resource record when error is not nil
+-	Error   *ParseError // when an error occured, this has the error specifics
+-	Comment string      // a potential comment positioned after the RR and on the same line
+-}
+-
+-// NewRR reads the RR contained in the string s. Only the first RR is returned.
+-// The class defaults to IN and TTL defaults to 3600. The full zone file
+-// syntax like $TTL, $ORIGIN, etc. is supported.
+-// All fields of the returned RR are set, except RR.Header().Rdlength which is set to 0.
+-func NewRR(s string) (RR, error) {
+-	if s[len(s)-1] != '\n' { // We need a closing newline
+-		return ReadRR(strings.NewReader(s+"\n"), "")
+-	}
+-	return ReadRR(strings.NewReader(s), "")
+-}
+-
+-// ReadRR reads the RR contained in q.
+-// See NewRR for more documentation.
+-func ReadRR(q io.Reader, filename string) (RR, error) {
+-	r := <-parseZoneHelper(q, ".", filename, 1)
+-	if r.Error != nil {
+-		return nil, r.Error
+-	}
+-	return r.RR, nil
+-}
+-
+-// ParseZone reads a RFC 1035 style one from r. It returns *Tokens on the
+-// returned channel, which consist out the parsed RR, a potential comment or an error.
+-// If there is an error the RR is nil. The string file is only used
+-// in error reporting. The string origin is used as the initial origin, as
+-// if the file would start with: $ORIGIN origin  .
+-// The directives $INCLUDE, $ORIGIN, $TTL and $GENERATE are supported.
+-// The channel t is closed by ParseZone when the end of r is reached.
+-//
+-// Basic usage pattern when reading from a string (z) containing the
+-// zone data:
+-//
+-//	for x := range dns.ParseZone(strings.NewReader(z), "", "") {
+-//		if x.Error != nil {
+-//			// Do something with x.RR
+-//		}
+-//	}
+-//
+-// Comments specified after an RR (and on the same line!) are returned too:
+-//
+-//	foo. IN A 10.0.0.1 ; this is a comment
+-//
+-// The text "; this is comment" is returned in Token.Comment . Comments inside the
+-// RR are discarded. Comments on a line by themselves are discarded too.
+-func ParseZone(r io.Reader, origin, file string) chan *Token {
+-	return parseZoneHelper(r, origin, file, 10000)
+-}
+-
+-func parseZoneHelper(r io.Reader, origin, file string, chansize int) chan *Token {
+-	t := make(chan *Token, chansize)
+-	go parseZone(r, origin, file, t, 0)
+-	return t
+-}
+-
+-func parseZone(r io.Reader, origin, f string, t chan *Token, include int) {
+-	defer func() {
+-		if include == 0 {
+-			close(t)
+-		}
+-	}()
+-	s := scanInit(r)
+-	c := make(chan lex, 1000)
+-	// Start the lexer
+-	go zlexer(s, c)
+-	// 6 possible beginnings of a line, _ is a space
+-	// 0. _RRTYPE                              -> all omitted until the rrtype
+-	// 1. _OWNER _ _RRTYPE                     -> class/ttl omitted
+-	// 2. _OWNER _ _STRING _ _RRTYPE           -> class omitted
+-	// 3. _OWNER _ _STRING _ _CLASS  _ _RRTYPE -> ttl/class
+-	// 4. _OWNER _ _CLASS  _ _RRTYPE           -> ttl omitted
+-	// 5. _OWNER _ _CLASS  _ _STRING _ _RRTYPE -> class/ttl (reversed)
+-	// After detecting these, we know the _RRTYPE so we can jump to functions
+-	// handling the rdata for each of these types.
+-
+-	if origin == "" {
+-		origin = "."
+-	}
+-	origin = Fqdn(origin)
+-	if _, ok := IsDomainName(origin); !ok {
+-		t <- &Token{Error: &ParseError{f, "bad initial origin name", lex{}}}
+-		return
+-	}
+-
+-	st := _EXPECT_OWNER_DIR // initial state
+-	var h RR_Header
+-	var defttl uint32 = defaultTtl
+-	var prevName string
+-	for l := range c {
+-		// Lexer spotted an error already
+-		if l.err == true {
+-			t <- &Token{Error: &ParseError{f, l.token, l}}
+-			return
+-
+-		}
+-		switch st {
+-		case _EXPECT_OWNER_DIR:
+-			// We can also expect a directive, like $TTL or $ORIGIN
+-			h.Ttl = defttl
+-			h.Class = ClassINET
+-			switch l.value {
+-			case _NEWLINE: // Empty line
+-				st = _EXPECT_OWNER_DIR
+-			case _OWNER:
+-				h.Name = l.token
+-				if l.token[0] == '@' {
+-					h.Name = origin
+-					prevName = h.Name
+-					st = _EXPECT_OWNER_BL
+-					break
+-				}
+-				if h.Name[l.length-1] != '.' {
+-					h.Name = appendOrigin(h.Name, origin)
+-				}
+-				_, ok := IsDomainName(l.token)
+-				if !ok {
+-					t <- &Token{Error: &ParseError{f, "bad owner name", l}}
+-					return
+-				}
+-				prevName = h.Name
+-				st = _EXPECT_OWNER_BL
+-			case _DIRTTL:
+-				st = _EXPECT_DIRTTL_BL
+-			case _DIRORIGIN:
+-				st = _EXPECT_DIRORIGIN_BL
+-			case _DIRINCLUDE:
+-				st = _EXPECT_DIRINCLUDE_BL
+-			case _DIRGENERATE:
+-				st = _EXPECT_DIRGENERATE_BL
+-			case _RRTYPE: // Everthing has been omitted, this is the first thing on the line
+-				h.Name = prevName
+-				h.Rrtype = l.torc
+-				st = _EXPECT_RDATA
+-			case _CLASS: // First thing on the line is the class
+-				h.Name = prevName
+-				h.Class = l.torc
+-				st = _EXPECT_ANY_NOCLASS_BL
+-			case _BLANK:
+-				// Discard, can happen when there is nothing on the
+-				// line except the RR type
+-			case _STRING: // First thing on the is the ttl
+-				if ttl, ok := stringToTtl(l.token); !ok {
+-					t <- &Token{Error: &ParseError{f, "not a TTL", l}}
+-					return
+-				} else {
+-					h.Ttl = ttl
+-					// Don't about the defttl, we should take the $TTL value
+-					// defttl = ttl
+-				}
+-				st = _EXPECT_ANY_NOTTL_BL
+-
+-			default:
+-				t <- &Token{Error: &ParseError{f, "syntax error at beginning", l}}
+-				return
+-			}
+-		case _EXPECT_DIRINCLUDE_BL:
+-			if l.value != _BLANK {
+-				t <- &Token{Error: &ParseError{f, "no blank after $INCLUDE-directive", l}}
+-				return
+-			}
+-			st = _EXPECT_DIRINCLUDE
+-		case _EXPECT_DIRINCLUDE:
+-			if l.value != _STRING {
+-				t <- &Token{Error: &ParseError{f, "expecting $INCLUDE value, not this...", l}}
+-				return
+-			}
+-			neworigin := origin // There may be optionally a new origin set after the filename, if not use current one
+-			l := <-c
+-			switch l.value {
+-			case _BLANK:
+-				l := <-c
+-				if l.value == _STRING {
+-					if _, ok := IsDomainName(l.token); !ok {
+-						t <- &Token{Error: &ParseError{f, "bad origin name", l}}
+-						return
+-					}
+-					// a new origin is specified.
+-					if l.token[l.length-1] != '.' {
+-						if origin != "." { // Prevent .. endings
+-							neworigin = l.token + "." + origin
+-						} else {
+-							neworigin = l.token + origin
+-						}
+-					} else {
+-						neworigin = l.token
+-					}
+-				}
+-			case _NEWLINE, _EOF:
+-				// Ok
+-			default:
+-				t <- &Token{Error: &ParseError{f, "garbage after $INCLUDE", l}}
+-				return
+-			}
+-			// Start with the new file
+-			r1, e1 := os.Open(l.token)
+-			if e1 != nil {
+-				t <- &Token{Error: &ParseError{f, "failed to open `" + l.token + "'", l}}
+-				return
+-			}
+-			if include+1 > 7 {
+-				t <- &Token{Error: &ParseError{f, "too deeply nested $INCLUDE", l}}
+-				return
+-			}
+-			parseZone(r1, l.token, neworigin, t, include+1)
+-			st = _EXPECT_OWNER_DIR
+-		case _EXPECT_DIRTTL_BL:
+-			if l.value != _BLANK {
+-				t <- &Token{Error: &ParseError{f, "no blank after $TTL-directive", l}}
+-				return
+-			}
+-			st = _EXPECT_DIRTTL
+-		case _EXPECT_DIRTTL:
+-			if l.value != _STRING {
+-				t <- &Token{Error: &ParseError{f, "expecting $TTL value, not this...", l}}
+-				return
+-			}
+-			if e, _ := slurpRemainder(c, f); e != nil {
+-				t <- &Token{Error: e}
+-				return
+-			}
+-			if ttl, ok := stringToTtl(l.token); !ok {
+-				t <- &Token{Error: &ParseError{f, "expecting $TTL value, not this...", l}}
+-				return
+-			} else {
+-				defttl = ttl
+-			}
+-			st = _EXPECT_OWNER_DIR
+-		case _EXPECT_DIRORIGIN_BL:
+-			if l.value != _BLANK {
+-				t <- &Token{Error: &ParseError{f, "no blank after $ORIGIN-directive", l}}
+-				return
+-			}
+-			st = _EXPECT_DIRORIGIN
+-		case _EXPECT_DIRORIGIN:
+-			if l.value != _STRING {
+-				t <- &Token{Error: &ParseError{f, "expecting $ORIGIN value, not this...", l}}
+-				return
+-			}
+-			if e, _ := slurpRemainder(c, f); e != nil {
+-				t <- &Token{Error: e}
+-			}
+-			if _, ok := IsDomainName(l.token); !ok {
+-				t <- &Token{Error: &ParseError{f, "bad origin name", l}}
+-				return
+-			}
+-			if l.token[l.length-1] != '.' {
+-				if origin != "." { // Prevent .. endings
+-					origin = l.token + "." + origin
+-				} else {
+-					origin = l.token + origin
+-				}
+-			} else {
+-				origin = l.token
+-			}
+-			st = _EXPECT_OWNER_DIR
+-		case _EXPECT_DIRGENERATE_BL:
+-			if l.value != _BLANK {
+-				t <- &Token{Error: &ParseError{f, "no blank after $GENERATE-directive", l}}
+-				return
+-			}
+-			st = _EXPECT_DIRGENERATE
+-		case _EXPECT_DIRGENERATE:
+-			if l.value != _STRING {
+-				t <- &Token{Error: &ParseError{f, "expecting $GENERATE value, not this...", l}}
+-				return
+-			}
+-			if e := generate(l, c, t, origin); e != "" {
+-				t <- &Token{Error: &ParseError{f, e, l}}
+-				return
+-			}
+-			st = _EXPECT_OWNER_DIR
+-		case _EXPECT_OWNER_BL:
+-			if l.value != _BLANK {
+-				t <- &Token{Error: &ParseError{f, "no blank after owner", l}}
+-				return
+-			}
+-			st = _EXPECT_ANY
+-		case _EXPECT_ANY:
+-			switch l.value {
+-			case _RRTYPE:
+-				h.Rrtype = l.torc
+-				st = _EXPECT_RDATA
+-			case _CLASS:
+-				h.Class = l.torc
+-				st = _EXPECT_ANY_NOCLASS_BL
+-			case _STRING: // TTL is this case
+-				if ttl, ok := stringToTtl(l.token); !ok {
+-					t <- &Token{Error: &ParseError{f, "not a TTL", l}}
+-					return
+-				} else {
+-					h.Ttl = ttl
+-					// defttl = ttl // don't set the defttl here
+-				}
+-				st = _EXPECT_ANY_NOTTL_BL
+-			default:
+-				t <- &Token{Error: &ParseError{f, "expecting RR type, TTL or class, not this...", l}}
+-				return
+-			}
+-		case _EXPECT_ANY_NOCLASS_BL:
+-			if l.value != _BLANK {
+-				t <- &Token{Error: &ParseError{f, "no blank before class", l}}
+-				return
+-			}
+-			st = _EXPECT_ANY_NOCLASS
+-		case _EXPECT_ANY_NOTTL_BL:
+-			if l.value != _BLANK {
+-				t <- &Token{Error: &ParseError{f, "no blank before TTL", l}}
+-				return
+-			}
+-			st = _EXPECT_ANY_NOTTL
+-		case _EXPECT_ANY_NOTTL:
+-			switch l.value {
+-			case _CLASS:
+-				h.Class = l.torc
+-				st = _EXPECT_RRTYPE_BL
+-			case _RRTYPE:
+-				h.Rrtype = l.torc
+-				st = _EXPECT_RDATA
+-			default:
+-				t <- &Token{Error: &ParseError{f, "expecting RR type or class, not this...", l}}
+-				return
+-			}
+-		case _EXPECT_ANY_NOCLASS:
+-			switch l.value {
+-			case _STRING: // TTL
+-				if ttl, ok := stringToTtl(l.token); !ok {
+-					t <- &Token{Error: &ParseError{f, "not a TTL", l}}
+-					return
+-				} else {
+-					h.Ttl = ttl
+-					// defttl = ttl // don't set the def ttl anymore
+-				}
+-				st = _EXPECT_RRTYPE_BL
+-			case _RRTYPE:
+-				h.Rrtype = l.torc
+-				st = _EXPECT_RDATA
+-			default:
+-				t <- &Token{Error: &ParseError{f, "expecting RR type or TTL, not this...", l}}
+-				return
+-			}
+-		case _EXPECT_RRTYPE_BL:
+-			if l.value != _BLANK {
+-				t <- &Token{Error: &ParseError{f, "no blank before RR type", l}}
+-				return
+-			}
+-			st = _EXPECT_RRTYPE
+-		case _EXPECT_RRTYPE:
+-			if l.value != _RRTYPE {
+-				t <- &Token{Error: &ParseError{f, "unknown RR type", l}}
+-				return
+-			}
+-			h.Rrtype = l.torc
+-			st = _EXPECT_RDATA
+-		case _EXPECT_RDATA:
+-			r, e, c1 := setRR(h, c, origin, f)
+-			if e != nil {
+-				// If e.lex is nil than we have encounter a unknown RR type
+-				// in that case we substitute our current lex token
+-				if e.lex.token == "" && e.lex.value == 0 {
+-					e.lex = l // Uh, dirty
+-				}
+-				t <- &Token{Error: e}
+-				return
+-			}
+-			t <- &Token{RR: r, Comment: c1}
+-			st = _EXPECT_OWNER_DIR
+-		}
+-	}
+-	// If we get here, we and the h.Rrtype is still zero, we haven't parsed anything, this
+-	// is not an error, because an empty zone file is still a zone file.
+-}
+-
+-// zlexer scans the sourcefile and returns tokens on the channel c.
+-func zlexer(s *scan, c chan lex) {
+-	var l lex
+-	str := make([]byte, maxTok) // Should be enough for any token
+-	stri := 0                   // Offset in str (0 means empty)
+-	com := make([]byte, maxTok) // Hold comment text
+-	comi := 0
+-	quote := false
+-	escape := false
+-	space := false
+-	commt := false
+-	rrtype := false
+-	owner := true
+-	brace := 0
+-	x, err := s.tokenText()
+-	defer close(c)
+-	for err == nil {
+-		l.column = s.position.Column
+-		l.line = s.position.Line
+-		if stri > maxTok {
+-			l.token = "token length insufficient for parsing"
+-			l.err = true
+-			debug.Printf("[%+v]", l.token)
+-			c <- l
+-			return
+-		}
+-		if comi > maxTok {
+-			l.token = "comment length insufficient for parsing"
+-			l.err = true
+-			debug.Printf("[%+v]", l.token)
+-			c <- l
+-			return
+-		}
+-
+-		switch x {
+-		case ' ', '\t':
+-			if escape {
+-				escape = false
+-				str[stri] = x
+-				stri++
+-				break
+-			}
+-			if quote {
+-				// Inside quotes this is legal
+-				str[stri] = x
+-				stri++
+-				break
+-			}
+-			if commt {
+-				com[comi] = x
+-				comi++
+-				break
+-			}
+-			if stri == 0 {
+-				// Space directly in the beginning, handled in the grammar
+-			} else if owner {
+-				// If we have a string and its the first, make it an owner
+-				l.value = _OWNER
+-				l.token = string(str[:stri])
+-				l.tokenUpper = strings.ToUpper(l.token)
+-				l.length = stri
+-				// escape $... start with a \ not a $, so this will work
+-				switch l.tokenUpper {
+-				case "$TTL":
+-					l.value = _DIRTTL
+-				case "$ORIGIN":
+-					l.value = _DIRORIGIN
+-				case "$INCLUDE":
+-					l.value = _DIRINCLUDE
+-				case "$GENERATE":
+-					l.value = _DIRGENERATE
+-				}
+-				debug.Printf("[7 %+v]", l.token)
+-				c <- l
+-			} else {
+-				l.value = _STRING
+-				l.token = string(str[:stri])
+-				l.tokenUpper = strings.ToUpper(l.token)
+-				l.length = stri
+-				if !rrtype {
+-					if t, ok := StringToType[l.tokenUpper]; ok {
+-						l.value = _RRTYPE
+-						l.torc = t
+-						rrtype = true
+-					} else {
+-						if strings.HasPrefix(l.tokenUpper, "TYPE") {
+-							if t, ok := typeToInt(l.token); !ok {
+-								l.token = "unknown RR type"
+-								l.err = true
+-								c <- l
+-								return
+-							} else {
+-								l.value = _RRTYPE
+-								l.torc = t
+-							}
+-						}
+-					}
+-					if t, ok := StringToClass[l.tokenUpper]; ok {
+-						l.value = _CLASS
+-						l.torc = t
+-					} else {
+-						if strings.HasPrefix(l.tokenUpper, "CLASS") {
+-							if t, ok := classToInt(l.token); !ok {
+-								l.token = "unknown class"
+-								l.err = true
+-								c <- l
+-								return
+-							} else {
+-								l.value = _CLASS
+-								l.torc = t
+-							}
+-						}
+-					}
+-				}
+-				debug.Printf("[6 %+v]", l.token)
+-				c <- l
+-			}
+-			stri = 0
+-			// I reverse space stuff here
+-			if !space && !commt {
+-				l.value = _BLANK
+-				l.token = " "
+-				l.length = 1
+-				debug.Printf("[5 %+v]", l.token)
+-				c <- l
+-			}
+-			owner = false
+-			space = true
+-		case ';':
+-			if escape {
+-				escape = false
+-				str[stri] = x
+-				stri++
+-				break
+-			}
+-			if quote {
+-				// Inside quotes this is legal
+-				str[stri] = x
+-				stri++
+-				break
+-			}
+-			if stri > 0 {
+-				l.value = _STRING
+-				l.token = string(str[:stri])
+-				l.length = stri
+-				debug.Printf("[4 %+v]", l.token)
+-				c <- l
+-				stri = 0
+-			}
+-			commt = true
+-			com[comi] = ';'
+-			comi++
+-		case '\r':
+-			escape = false
+-			if quote {
+-				str[stri] = x
+-				stri++
+-				break
+-			}
+-			// discard if outside of quotes
+-		case '\n':
+-			escape = false
+-			// Escaped newline
+-			if quote {
+-				str[stri] = x
+-				stri++
+-				break
+-			}
+-			// inside quotes this is legal
+-			if commt {
+-				// Reset a comment
+-				commt = false
+-				rrtype = false
+-				stri = 0
+-				// If not in a brace this ends the comment AND the RR
+-				if brace == 0 {
+-					owner = true
+-					owner = true
+-					l.value = _NEWLINE
+-					l.token = "\n"
+-					l.length = 1
+-					l.comment = string(com[:comi])
+-					debug.Printf("[3 %+v %+v]", l.token, l.comment)
+-					c <- l
+-					l.comment = ""
+-					comi = 0
+-					break
+-				}
+-				com[comi] = ' ' // convert newline to space
+-				comi++
+-				break
+-			}
+-
+-			if brace == 0 {
+-				// If there is previous text, we should output it here
+-				if stri != 0 {
+-					l.value = _STRING
+-					l.token = string(str[:stri])
+-					l.tokenUpper = strings.ToUpper(l.token)
+-
+-					l.length = stri
+-					if !rrtype {
+-						if t, ok := StringToType[l.tokenUpper]; ok {
+-							l.value = _RRTYPE
+-							l.torc = t
+-							rrtype = true
+-						}
+-					}
+-					debug.Printf("[2 %+v]", l.token)
+-					c <- l
+-				}
+-				l.value = _NEWLINE
+-				l.token = "\n"
+-				l.length = 1
+-				debug.Printf("[1 %+v]", l.token)
+-				c <- l
+-				stri = 0
+-				commt = false
+-				rrtype = false
+-				owner = true
+-				comi = 0
+-			}
+-		case '\\':
+-			// comments do not get escaped chars, everything is copied
+-			if commt {
+-				com[comi] = x
+-				comi++
+-				break
+-			}
+-			// something already escaped must be in string
+-			if escape {
+-				str[stri] = x
+-				stri++
+-				escape = false
+-				break
+-			}
+-			// something escaped outside of string gets added to string
+-			str[stri] = x
+-			stri++
+-			escape = true
+-		case '"':
+-			if commt {
+-				com[comi] = x
+-				comi++
+-				break
+-			}
+-			if escape {
+-				str[stri] = x
+-				stri++
+-				escape = false
+-				break
+-			}
+-			space = false
+-			// send previous gathered text and the quote
+-			if stri != 0 {
+-				l.value = _STRING
+-				l.token = string(str[:stri])
+-				l.length = stri
+-
+-				debug.Printf("[%+v]", l.token)
+-				c <- l
+-				stri = 0
+-			}
+-
+-			// send quote itself as separate token
+-			l.value = _QUOTE
+-			l.token = "\""
+-			l.length = 1
+-			c <- l
+-			quote = !quote
+-		case '(', ')':
+-			if commt {
+-				com[comi] = x
+-				comi++
+-				break
+-			}
+-			if escape {
+-				str[stri] = x
+-				stri++
+-				escape = false
+-				break
+-			}
+-			if quote {
+-				str[stri] = x
+-				stri++
+-				break
+-			}
+-			switch x {
+-			case ')':
+-				brace--
+-				if brace < 0 {
+-					l.token = "extra closing brace"
+-					l.err = true
+-					debug.Printf("[%+v]", l.token)
+-					c <- l
+-					return
+-				}
+-			case '(':
+-				brace++
+-			}
+-		default:
+-			escape = false
+-			if commt {
+-				com[comi] = x
+-				comi++
+-				break
+-			}
+-			str[stri] = x
+-			stri++
+-			space = false
+-		}
+-		x, err = s.tokenText()
+-	}
+-	if stri > 0 {
+-		// Send remainder
+-		l.token = string(str[:stri])
+-		l.length = stri
+-		l.value = _STRING
+-		debug.Printf("[%+v]", l.token)
+-		c <- l
+-	}
+-}
+-
+-// Extract the class number from CLASSxx
+-func classToInt(token string) (uint16, bool) {
+-	class, ok := strconv.Atoi(token[5:])
+-	if ok != nil || class > maxUint16 {
+-		return 0, false
+-	}
+-	return uint16(class), true
+-}
+-
+-// Extract the rr number from TYPExxx
+-func typeToInt(token string) (uint16, bool) {
+-	typ, ok := strconv.Atoi(token[4:])
+-	if ok != nil || typ > maxUint16 {
+-		return 0, false
+-	}
+-	return uint16(typ), true
+-}
+-
+-// Parse things like 2w, 2m, etc, Return the time in seconds.
+-func stringToTtl(token string) (uint32, bool) {
+-	s := uint32(0)
+-	i := uint32(0)
+-	for _, c := range token {
+-		switch c {
+-		case 's', 'S':
+-			s += i
+-			i = 0
+-		case 'm', 'M':
+-			s += i * 60
+-			i = 0
+-		case 'h', 'H':
+-			s += i * 60 * 60
+-			i = 0
+-		case 'd', 'D':
+-			s += i * 60 * 60 * 24
+-			i = 0
+-		case 'w', 'W':
+-			s += i * 60 * 60 * 24 * 7
+-			i = 0
+-		case '0', '1', '2', '3', '4', '5', '6', '7', '8', '9':
+-			i *= 10
+-			i += uint32(c) - '0'
+-		default:
+-			return 0, false
+-		}
+-	}
+-	return s + i, true
+-}
+-
+-// Parse LOC records' <digits>[.<digits>][mM] into a
+-// mantissa exponent format. Token should contain the entire
+-// string (i.e. no spaces allowed)
+-func stringToCm(token string) (e, m uint8, ok bool) {
+-	if token[len(token)-1] == 'M' || token[len(token)-1] == 'm' {
+-		token = token[0 : len(token)-1]
+-	}
+-	s := strings.SplitN(token, ".", 2)
+-	var meters, cmeters, val int
+-	var err error
+-	switch len(s) {
+-	case 2:
+-		if cmeters, err = strconv.Atoi(s[1]); err != nil {
+-			return
+-		}
+-		fallthrough
+-	case 1:
+-		if meters, err = strconv.Atoi(s[0]); err != nil {
+-			return
+-		}
+-	case 0:
+-		// huh?
+-		return 0, 0, false
+-	}
+-	ok = true
+-	if meters > 0 {
+-		e = 2
+-		val = meters
+-	} else {
+-		e = 0
+-		val = cmeters
+-	}
+-	for val > 10 {
+-		e++
+-		val /= 10
+-	}
+-	if e > 9 {
+-		ok = false
+-	}
+-	m = uint8(val)
+-	return
+-}
+-
+-func appendOrigin(name, origin string) string {
+-	if origin == "." {
+-		return name + origin
+-	}
+-	return name + "." + origin
+-}
+-
+-// LOC record helper function
+-func locCheckNorth(token string, latitude uint32) (uint32, bool) {
+-	switch token {
+-	case "n", "N":
+-		return LOC_EQUATOR + latitude, true
+-	case "s", "S":
+-		return LOC_EQUATOR - latitude, true
+-	}
+-	return latitude, false
+-}
+-
+-// LOC record helper function
+-func locCheckEast(token string, longitude uint32) (uint32, bool) {
+-	switch token {
+-	case "e", "E":
+-		return LOC_EQUATOR + longitude, true
+-	case "w", "W":
+-		return LOC_EQUATOR - longitude, true
+-	}
+-	return longitude, false
+-}
+-
+-// "Eat" the rest of the "line". Return potential comments
+-func slurpRemainder(c chan lex, f string) (*ParseError, string) {
+-	l := <-c
+-	com := ""
+-	switch l.value {
+-	case _BLANK:
+-		l = <-c
+-		com = l.comment
+-		if l.value != _NEWLINE && l.value != _EOF {
+-			return &ParseError{f, "garbage after rdata", l}, ""
+-		}
+-	case _NEWLINE:
+-		com = l.comment
+-	case _EOF:
+-	default:
+-		return &ParseError{f, "garbage after rdata", l}, ""
+-	}
+-	return nil, com
+-}
+-
+-// Parse a 64 bit-like ipv6 address: "0014:4fff:ff20:ee64"
+-// Used for NID and L64 record.
+-func stringToNodeID(l lex) (uint64, *ParseError) {
+-	if len(l.token) < 19 {
+-		return 0, &ParseError{l.token, "bad NID/L64 NodeID/Locator64", l}
+-	}
+-	// There must be three colons at fixes postitions, if not its a parse error
+-	if l.token[4] != ':' && l.token[9] != ':' && l.token[14] != ':' {
+-		return 0, &ParseError{l.token, "bad NID/L64 NodeID/Locator64", l}
+-	}
+-	s := l.token[0:4] + l.token[5:9] + l.token[10:14] + l.token[15:19]
+-	u, e := strconv.ParseUint(s, 16, 64)
+-	if e != nil {
+-		return 0, &ParseError{l.token, "bad NID/L64 NodeID/Locator64", l}
+-	}
+-	return u, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/miekg/dns/zscan_rr.go b/Godeps/_workspace/src/github.com/miekg/dns/zscan_rr.go
+deleted file mode 100644
+index 5088cdb..0000000
+--- a/Godeps/_workspace/src/github.com/miekg/dns/zscan_rr.go
++++ /dev/null
+@@ -1,2155 +0,0 @@
+-package dns
+-
+-import (
+-	"encoding/base64"
+-	"net"
+-	"strconv"
+-	"strings"
+-)
+-
+-type parserFunc struct {
+-	// Func defines the function that parses the tokens and returns the RR
+-	// or an error. The last string contains any comments in the line as
+-	// they returned by the lexer as well.
+-	Func func(h RR_Header, c chan lex, origin string, file string) (RR, *ParseError, string)
+-	// Signals if the RR ending is of variable length, like TXT or records
+-	// that have Hexadecimal or Base64 as their last element in the Rdata. Records
+-	// that have a fixed ending or for instance A, AAAA, SOA and etc.
+-	Variable bool
+-}
+-
+-// Parse the rdata of each rrtype.
+-// All data from the channel c is either _STRING or _BLANK.
+-// After the rdata there may come a _BLANK and then a _NEWLINE
+-// or immediately a _NEWLINE. If this is not the case we flag
+-// an *ParseError: garbage after rdata.
+-func setRR(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	parserfunc, ok := typeToparserFunc[h.Rrtype]
+-	if ok {
+-		r, e, cm := parserfunc.Func(h, c, o, f)
+-		if parserfunc.Variable {
+-			return r, e, cm
+-		}
+-		if e != nil {
+-			return nil, e, ""
+-		}
+-		e, cm = slurpRemainder(c, f)
+-		if e != nil {
+-			return nil, e, ""
+-		}
+-		return r, nil, cm
+-	}
+-	// RFC3957 RR (Unknown RR handling)
+-	return setRFC3597(h, c, o, f)
+-}
+-
+-// A remainder of the rdata with embedded spaces, return the parsed string (sans the spaces)
+-// or an error
+-func endingToString(c chan lex, errstr, f string) (string, *ParseError, string) {
+-	s := ""
+-	l := <-c // _STRING
+-	for l.value != _NEWLINE && l.value != _EOF {
+-		switch l.value {
+-		case _STRING:
+-			s += l.token
+-		case _BLANK: // Ok
+-		default:
+-			return "", &ParseError{f, errstr, l}, ""
+-		}
+-		l = <-c
+-	}
+-	return s, nil, l.comment
+-}
+-
+-// A remainder of the rdata with embedded spaces, return the parsed string slice (sans the spaces)
+-// or an error
+-func endingToTxtSlice(c chan lex, errstr, f string) ([]string, *ParseError, string) {
+-	// Get the remaining data until we see a NEWLINE
+-	quote := false
+-	l := <-c
+-	var s []string
+-	switch l.value == _QUOTE {
+-	case true: // A number of quoted string
+-		s = make([]string, 0)
+-		empty := true
+-		for l.value != _NEWLINE && l.value != _EOF {
+-			switch l.value {
+-			case _STRING:
+-				empty = false
+-				s = append(s, l.token)
+-			case _BLANK:
+-				if quote {
+-					// _BLANK can only be seen in between txt parts.
+-					return nil, &ParseError{f, errstr, l}, ""
+-				}
+-			case _QUOTE:
+-				if empty && quote {
+-					s = append(s, "")
+-				}
+-				quote = !quote
+-				empty = true
+-			default:
+-				return nil, &ParseError{f, errstr, l}, ""
+-			}
+-			l = <-c
+-		}
+-		if quote {
+-			return nil, &ParseError{f, errstr, l}, ""
+-		}
+-	case false: // Unquoted text record
+-		s = make([]string, 1)
+-		for l.value != _NEWLINE && l.value != _EOF {
+-			s[0] += l.token
+-			l = <-c
+-		}
+-	}
+-	return s, nil, l.comment
+-}
+-
+-func setA(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(A)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 { // Dynamic updates.
+-		return rr, nil, ""
+-	}
+-	rr.A = net.ParseIP(l.token)
+-	if rr.A == nil {
+-		return nil, &ParseError{f, "bad A A", l}, ""
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setAAAA(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(AAAA)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	rr.AAAA = net.ParseIP(l.token)
+-	if rr.AAAA == nil {
+-		return nil, &ParseError{f, "bad AAAA AAAA", l}, ""
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setNS(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(NS)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	rr.Ns = l.token
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if l.token == "@" {
+-		rr.Ns = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok {
+-		return nil, &ParseError{f, "bad NS Ns", l}, ""
+-	}
+-	if rr.Ns[l.length-1] != '.' {
+-		rr.Ns = appendOrigin(rr.Ns, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setPTR(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(PTR)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	rr.Ptr = l.token
+-	if l.length == 0 { // dynamic update rr.
+-		return rr, nil, ""
+-	}
+-	if l.token == "@" {
+-		rr.Ptr = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok {
+-		return nil, &ParseError{f, "bad PTR Ptr", l}, ""
+-	}
+-	if rr.Ptr[l.length-1] != '.' {
+-		rr.Ptr = appendOrigin(rr.Ptr, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setNSAPPTR(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(NSAPPTR)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	rr.Ptr = l.token
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if l.token == "@" {
+-		rr.Ptr = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok {
+-		return nil, &ParseError{f, "bad NSAP-PTR Ptr", l}, ""
+-	}
+-	if rr.Ptr[l.length-1] != '.' {
+-		rr.Ptr = appendOrigin(rr.Ptr, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setRP(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(RP)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	rr.Mbox = l.token
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if l.token == "@" {
+-		rr.Mbox = o
+-	} else {
+-		_, ok := IsDomainName(l.token)
+-		if !ok {
+-			return nil, &ParseError{f, "bad RP Mbox", l}, ""
+-		}
+-		if rr.Mbox[l.length-1] != '.' {
+-			rr.Mbox = appendOrigin(rr.Mbox, o)
+-		}
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	rr.Txt = l.token
+-	if l.token == "@" {
+-		rr.Txt = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok {
+-		return nil, &ParseError{f, "bad RP Txt", l}, ""
+-	}
+-	if rr.Txt[l.length-1] != '.' {
+-		rr.Txt = appendOrigin(rr.Txt, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setMR(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(MR)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	rr.Mr = l.token
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if l.token == "@" {
+-		rr.Mr = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok {
+-		return nil, &ParseError{f, "bad MR Mr", l}, ""
+-	}
+-	if rr.Mr[l.length-1] != '.' {
+-		rr.Mr = appendOrigin(rr.Mr, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setMB(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(MB)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	rr.Mb = l.token
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if l.token == "@" {
+-		rr.Mb = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok {
+-		return nil, &ParseError{f, "bad MB Mb", l}, ""
+-	}
+-	if rr.Mb[l.length-1] != '.' {
+-		rr.Mb = appendOrigin(rr.Mb, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setMG(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(MG)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	rr.Mg = l.token
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if l.token == "@" {
+-		rr.Mg = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok {
+-		return nil, &ParseError{f, "bad MG Mg", l}, ""
+-	}
+-	if rr.Mg[l.length-1] != '.' {
+-		rr.Mg = appendOrigin(rr.Mg, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setHINFO(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(HINFO)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	rr.Cpu = l.token
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	rr.Os = l.token
+-
+-	return rr, nil, ""
+-}
+-
+-func setMINFO(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(MINFO)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	rr.Rmail = l.token
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if l.token == "@" {
+-		rr.Rmail = o
+-	} else {
+-		_, ok := IsDomainName(l.token)
+-		if !ok {
+-			return nil, &ParseError{f, "bad MINFO Rmail", l}, ""
+-		}
+-		if rr.Rmail[l.length-1] != '.' {
+-			rr.Rmail = appendOrigin(rr.Rmail, o)
+-		}
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	rr.Email = l.token
+-	if l.token == "@" {
+-		rr.Email = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok {
+-		return nil, &ParseError{f, "bad MINFO Email", l}, ""
+-	}
+-	if rr.Email[l.length-1] != '.' {
+-		rr.Email = appendOrigin(rr.Email, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setMF(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(MF)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	rr.Mf = l.token
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if l.token == "@" {
+-		rr.Mf = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok {
+-		return nil, &ParseError{f, "bad MF Mf", l}, ""
+-	}
+-	if rr.Mf[l.length-1] != '.' {
+-		rr.Mf = appendOrigin(rr.Mf, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setMD(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(MD)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	rr.Md = l.token
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if l.token == "@" {
+-		rr.Md = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok {
+-		return nil, &ParseError{f, "bad MD Md", l}, ""
+-	}
+-	if rr.Md[l.length-1] != '.' {
+-		rr.Md = appendOrigin(rr.Md, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setMX(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(MX)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad MX Pref", l}, ""
+-	} else {
+-		rr.Preference = uint16(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	rr.Mx = l.token
+-	if l.token == "@" {
+-		rr.Mx = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok || l.length == 0 {
+-		return nil, &ParseError{f, "bad MX Mx", l}, ""
+-	}
+-	if rr.Mx[l.length-1] != '.' {
+-		rr.Mx = appendOrigin(rr.Mx, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setRT(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(RT)
+-	rr.Hdr = h
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad RT Preference", l}, ""
+-	} else {
+-		rr.Preference = uint16(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	rr.Host = l.token
+-	if l.token == "@" {
+-		rr.Host = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok || l.length == 0 {
+-		return nil, &ParseError{f, "bad RT Host", l}, ""
+-	}
+-	if rr.Host[l.length-1] != '.' {
+-		rr.Host = appendOrigin(rr.Host, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setAFSDB(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(AFSDB)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad AFSDB Subtype", l}, ""
+-	} else {
+-		rr.Subtype = uint16(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	rr.Hostname = l.token
+-	if l.token == "@" {
+-		rr.Hostname = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok || l.length == 0 {
+-		return nil, &ParseError{f, "bad AFSDB Hostname", l}, ""
+-	}
+-	if rr.Hostname[l.length-1] != '.' {
+-		rr.Hostname = appendOrigin(rr.Hostname, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setX25(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(X25)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	rr.PSDNAddress = l.token
+-	return rr, nil, ""
+-}
+-
+-func setKX(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(KX)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad KX Pref", l}, ""
+-	} else {
+-		rr.Preference = uint16(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	rr.Exchanger = l.token
+-	if l.token == "@" {
+-		rr.Exchanger = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok || l.length == 0 {
+-		return nil, &ParseError{f, "bad KX Exchanger", l}, ""
+-	}
+-	if rr.Exchanger[l.length-1] != '.' {
+-		rr.Exchanger = appendOrigin(rr.Exchanger, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setCNAME(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(CNAME)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	rr.Target = l.token
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if l.token == "@" {
+-		rr.Target = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok || l.length == 0 {
+-		return nil, &ParseError{f, "bad CNAME Target", l}, ""
+-	}
+-	if rr.Target[l.length-1] != '.' {
+-		rr.Target = appendOrigin(rr.Target, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setDNAME(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(DNAME)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	rr.Target = l.token
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if l.token == "@" {
+-		rr.Target = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok {
+-		return nil, &ParseError{f, "bad CNAME Target", l}, ""
+-	}
+-	if rr.Target[l.length-1] != '.' {
+-		rr.Target = appendOrigin(rr.Target, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setSOA(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(SOA)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	rr.Ns = l.token
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	<-c // _BLANK
+-	if l.token == "@" {
+-		rr.Ns = o
+-	} else {
+-		_, ok := IsDomainName(l.token)
+-		if !ok {
+-			return nil, &ParseError{f, "bad SOA Ns", l}, ""
+-		}
+-		if rr.Ns[l.length-1] != '.' {
+-			rr.Ns = appendOrigin(rr.Ns, o)
+-		}
+-	}
+-
+-	l = <-c
+-	rr.Mbox = l.token
+-	if l.token == "@" {
+-		rr.Mbox = o
+-	} else {
+-		_, ok := IsDomainName(l.token)
+-		if !ok || l.length == 0 {
+-			return nil, &ParseError{f, "bad SOA Mbox", l}, ""
+-		}
+-		if rr.Mbox[l.length-1] != '.' {
+-			rr.Mbox = appendOrigin(rr.Mbox, o)
+-		}
+-	}
+-	<-c // _BLANK
+-
+-	var (
+-		v  uint32
+-		ok bool
+-	)
+-	for i := 0; i < 5; i++ {
+-		l = <-c
+-		if j, e := strconv.Atoi(l.token); e != nil {
+-			if i == 0 {
+-				// Serial should be a number
+-				return nil, &ParseError{f, "bad SOA zone parameter", l}, ""
+-			}
+-			if v, ok = stringToTtl(l.token); !ok {
+-				return nil, &ParseError{f, "bad SOA zone parameter", l}, ""
+-
+-			}
+-		} else {
+-			v = uint32(j)
+-		}
+-		switch i {
+-		case 0:
+-			rr.Serial = v
+-			<-c // _BLANK
+-		case 1:
+-			rr.Refresh = v
+-			<-c // _BLANK
+-		case 2:
+-			rr.Retry = v
+-			<-c // _BLANK
+-		case 3:
+-			rr.Expire = v
+-			<-c // _BLANK
+-		case 4:
+-			rr.Minttl = v
+-		}
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setSRV(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(SRV)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad SRV Priority", l}, ""
+-	} else {
+-		rr.Priority = uint16(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad SRV Weight", l}, ""
+-	} else {
+-		rr.Weight = uint16(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad SRV Port", l}, ""
+-	} else {
+-		rr.Port = uint16(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	rr.Target = l.token
+-	if l.token == "@" {
+-		rr.Target = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok || l.length == 0 {
+-		return nil, &ParseError{f, "bad SRV Target", l}, ""
+-	}
+-	if rr.Target[l.length-1] != '.' {
+-		rr.Target = appendOrigin(rr.Target, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setNAPTR(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(NAPTR)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad NAPTR Order", l}, ""
+-	} else {
+-		rr.Order = uint16(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad NAPTR Preference", l}, ""
+-	} else {
+-		rr.Preference = uint16(i)
+-	}
+-	// Flags
+-	<-c     // _BLANK
+-	l = <-c // _QUOTE
+-	if l.value != _QUOTE {
+-		return nil, &ParseError{f, "bad NAPTR Flags", l}, ""
+-	}
+-	l = <-c // Either String or Quote
+-	if l.value == _STRING {
+-		rr.Flags = l.token
+-		l = <-c // _QUOTE
+-		if l.value != _QUOTE {
+-			return nil, &ParseError{f, "bad NAPTR Flags", l}, ""
+-		}
+-	} else if l.value == _QUOTE {
+-		rr.Flags = ""
+-	} else {
+-		return nil, &ParseError{f, "bad NAPTR Flags", l}, ""
+-	}
+-
+-	// Service
+-	<-c     // _BLANK
+-	l = <-c // _QUOTE
+-	if l.value != _QUOTE {
+-		return nil, &ParseError{f, "bad NAPTR Service", l}, ""
+-	}
+-	l = <-c // Either String or Quote
+-	if l.value == _STRING {
+-		rr.Service = l.token
+-		l = <-c // _QUOTE
+-		if l.value != _QUOTE {
+-			return nil, &ParseError{f, "bad NAPTR Service", l}, ""
+-		}
+-	} else if l.value == _QUOTE {
+-		rr.Service = ""
+-	} else {
+-		return nil, &ParseError{f, "bad NAPTR Service", l}, ""
+-	}
+-
+-	// Regexp
+-	<-c     // _BLANK
+-	l = <-c // _QUOTE
+-	if l.value != _QUOTE {
+-		return nil, &ParseError{f, "bad NAPTR Regexp", l}, ""
+-	}
+-	l = <-c // Either String or Quote
+-	if l.value == _STRING {
+-		rr.Regexp = l.token
+-		l = <-c // _QUOTE
+-		if l.value != _QUOTE {
+-			return nil, &ParseError{f, "bad NAPTR Regexp", l}, ""
+-		}
+-	} else if l.value == _QUOTE {
+-		rr.Regexp = ""
+-	} else {
+-		return nil, &ParseError{f, "bad NAPTR Regexp", l}, ""
+-	}
+-	// After quote no space??
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	rr.Replacement = l.token
+-	if l.token == "@" {
+-		rr.Replacement = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok || l.length == 0 {
+-		return nil, &ParseError{f, "bad NAPTR Replacement", l}, ""
+-	}
+-	if rr.Replacement[l.length-1] != '.' {
+-		rr.Replacement = appendOrigin(rr.Replacement, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setTALINK(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(TALINK)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	rr.PreviousName = l.token
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if l.token == "@" {
+-		rr.PreviousName = o
+-	} else {
+-		_, ok := IsDomainName(l.token)
+-		if !ok {
+-			return nil, &ParseError{f, "bad TALINK PreviousName", l}, ""
+-		}
+-		if rr.PreviousName[l.length-1] != '.' {
+-			rr.PreviousName = appendOrigin(rr.PreviousName, o)
+-		}
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	rr.NextName = l.token
+-	if l.token == "@" {
+-		rr.NextName = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok || l.length == 0 {
+-		return nil, &ParseError{f, "bad TALINK NextName", l}, ""
+-	}
+-	if rr.NextName[l.length-1] != '.' {
+-		rr.NextName = appendOrigin(rr.NextName, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setLOC(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(LOC)
+-	rr.Hdr = h
+-	// Non zero defaults for LOC record, see RFC 1876, Section 3.
+-	rr.HorizPre = 165 // 10000
+-	rr.VertPre = 162  // 10
+-	rr.Size = 18      // 1
+-	ok := false
+-	// North
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad LOC Latitude", l}, ""
+-	} else {
+-		rr.Latitude = 1000 * 60 * 60 * uint32(i)
+-	}
+-	<-c // _BLANK
+-	// Either number, 'N' or 'S'
+-	l = <-c
+-	if rr.Latitude, ok = locCheckNorth(l.token, rr.Latitude); ok {
+-		goto East
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad LOC Latitude minutes", l}, ""
+-	} else {
+-		rr.Latitude += 1000 * 60 * uint32(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, e := strconv.ParseFloat(l.token, 32); e != nil {
+-		return nil, &ParseError{f, "bad LOC Latitude seconds", l}, ""
+-	} else {
+-		rr.Latitude += uint32(1000 * i)
+-	}
+-	<-c // _BLANK
+-	// Either number, 'N' or 'S'
+-	l = <-c
+-	if rr.Latitude, ok = locCheckNorth(l.token, rr.Latitude); ok {
+-		goto East
+-	}
+-	// If still alive, flag an error
+-	return nil, &ParseError{f, "bad LOC Latitude North/South", l}, ""
+-
+-East:
+-	// East
+-	<-c // _BLANK
+-	l = <-c
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad LOC Longitude", l}, ""
+-	} else {
+-		rr.Longitude = 1000 * 60 * 60 * uint32(i)
+-	}
+-	<-c // _BLANK
+-	// Either number, 'E' or 'W'
+-	l = <-c
+-	if rr.Longitude, ok = locCheckEast(l.token, rr.Longitude); ok {
+-		goto Altitude
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad LOC Longitude minutes", l}, ""
+-	} else {
+-		rr.Longitude += 1000 * 60 * uint32(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, e := strconv.ParseFloat(l.token, 32); e != nil {
+-		return nil, &ParseError{f, "bad LOC Longitude seconds", l}, ""
+-	} else {
+-		rr.Longitude += uint32(1000 * i)
+-	}
+-	<-c // _BLANK
+-	// Either number, 'E' or 'W'
+-	l = <-c
+-	if rr.Longitude, ok = locCheckEast(l.token, rr.Longitude); ok {
+-		goto Altitude
+-	}
+-	// If still alive, flag an error
+-	return nil, &ParseError{f, "bad LOC Longitude East/West", l}, ""
+-
+-Altitude:
+-	<-c // _BLANK
+-	l = <-c
+-	if l.token[len(l.token)-1] == 'M' || l.token[len(l.token)-1] == 'm' {
+-		l.token = l.token[0 : len(l.token)-1]
+-	}
+-	if i, e := strconv.ParseFloat(l.token, 32); e != nil {
+-		return nil, &ParseError{f, "bad LOC Altitude", l}, ""
+-	} else {
+-		rr.Altitude = uint32(i*100.0 + 10000000.0 + 0.5)
+-	}
+-
+-	// And now optionally the other values
+-	l = <-c
+-	count := 0
+-	for l.value != _NEWLINE && l.value != _EOF {
+-		switch l.value {
+-		case _STRING:
+-			switch count {
+-			case 0: // Size
+-				if e, m, ok := stringToCm(l.token); !ok {
+-					return nil, &ParseError{f, "bad LOC Size", l}, ""
+-				} else {
+-					rr.Size = (e & 0x0f) | (m << 4 & 0xf0)
+-				}
+-			case 1: // HorizPre
+-				if e, m, ok := stringToCm(l.token); !ok {
+-					return nil, &ParseError{f, "bad LOC HorizPre", l}, ""
+-				} else {
+-					rr.HorizPre = (e & 0x0f) | (m << 4 & 0xf0)
+-				}
+-			case 2: // VertPre
+-				if e, m, ok := stringToCm(l.token); !ok {
+-					return nil, &ParseError{f, "bad LOC VertPre", l}, ""
+-				} else {
+-					rr.VertPre = (e & 0x0f) | (m << 4 & 0xf0)
+-				}
+-			}
+-			count++
+-		case _BLANK:
+-			// Ok
+-		default:
+-			return nil, &ParseError{f, "bad LOC Size, HorizPre or VertPre", l}, ""
+-		}
+-		l = <-c
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setHIP(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(HIP)
+-	rr.Hdr = h
+-
+-	// HitLength is not represented
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, l.comment
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad HIP PublicKeyAlgorithm", l}, ""
+-	} else {
+-		rr.PublicKeyAlgorithm = uint8(i)
+-	}
+-	<-c              // _BLANK
+-	l = <-c          // _STRING
+-	rr.Hit = l.token // This can not contain spaces, see RFC 5205 Section 6.
+-	rr.HitLength = uint8(len(rr.Hit)) / 2
+-
+-	<-c                    // _BLANK
+-	l = <-c                // _STRING
+-	rr.PublicKey = l.token // This cannot contain spaces
+-	rr.PublicKeyLength = uint16(base64.StdEncoding.DecodedLen(len(rr.PublicKey)))
+-
+-	// RendezvousServers (if any)
+-	l = <-c
+-	xs := make([]string, 0)
+-	for l.value != _NEWLINE && l.value != _EOF {
+-		switch l.value {
+-		case _STRING:
+-			if l.token == "@" {
+-				xs = append(xs, o)
+-				continue
+-			}
+-			_, ok := IsDomainName(l.token)
+-			if !ok || l.length == 0 {
+-				return nil, &ParseError{f, "bad HIP RendezvousServers", l}, ""
+-			}
+-			if l.token[l.length-1] != '.' {
+-				l.token = appendOrigin(l.token, o)
+-			}
+-			xs = append(xs, l.token)
+-		case _BLANK:
+-			// Ok
+-		default:
+-			return nil, &ParseError{f, "bad HIP RendezvousServers", l}, ""
+-		}
+-		l = <-c
+-	}
+-	rr.RendezvousServers = xs
+-	return rr, nil, l.comment
+-}
+-
+-func setCERT(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(CERT)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, l.comment
+-	}
+-	if v, ok := StringToCertType[l.token]; ok {
+-		rr.Type = v
+-	} else if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad CERT Type", l}, ""
+-	} else {
+-		rr.Type = uint16(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad CERT KeyTag", l}, ""
+-	} else {
+-		rr.KeyTag = uint16(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	if v, ok := StringToAlgorithm[l.token]; ok {
+-		rr.Algorithm = v
+-	} else if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad CERT Algorithm", l}, ""
+-	} else {
+-		rr.Algorithm = uint8(i)
+-	}
+-	s, e, c1 := endingToString(c, "bad CERT Certificate", f)
+-	if e != nil {
+-		return nil, e, c1
+-	}
+-	rr.Certificate = s
+-	return rr, nil, c1
+-}
+-
+-func setOPENPGPKEY(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(OPENPGPKEY)
+-	rr.Hdr = h
+-
+-	s, e, c1 := endingToString(c, "bad OPENPGPKEY PublicKey", f)
+-	if e != nil {
+-		return nil, e, c1
+-	}
+-	rr.PublicKey = s
+-	return rr, nil, c1
+-}
+-
+-func setSIG(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	r, e, s := setRRSIG(h, c, o, f)
+-	if r != nil {
+-		return &SIG{*r.(*RRSIG)}, e, s
+-	}
+-	return nil, e, s
+-}
+-
+-func setRRSIG(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(RRSIG)
+-	rr.Hdr = h
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, l.comment
+-	}
+-	if t, ok := StringToType[l.tokenUpper]; !ok {
+-		if strings.HasPrefix(l.tokenUpper, "TYPE") {
+-			if t, ok = typeToInt(l.tokenUpper); !ok {
+-				return nil, &ParseError{f, "bad RRSIG Typecovered", l}, ""
+-			} else {
+-				rr.TypeCovered = t
+-			}
+-		} else {
+-			return nil, &ParseError{f, "bad RRSIG Typecovered", l}, ""
+-		}
+-	} else {
+-		rr.TypeCovered = t
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, err := strconv.Atoi(l.token); err != nil {
+-		return nil, &ParseError{f, "bad RRSIG Algorithm", l}, ""
+-	} else {
+-		rr.Algorithm = uint8(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, err := strconv.Atoi(l.token); err != nil {
+-		return nil, &ParseError{f, "bad RRSIG Labels", l}, ""
+-	} else {
+-		rr.Labels = uint8(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, err := strconv.Atoi(l.token); err != nil {
+-		return nil, &ParseError{f, "bad RRSIG OrigTtl", l}, ""
+-	} else {
+-		rr.OrigTtl = uint32(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, err := StringToTime(l.token); err != nil {
+-		// Try to see if all numeric and use it as epoch
+-		if i, err := strconv.ParseInt(l.token, 10, 64); err == nil {
+-			// TODO(miek): error out on > MAX_UINT32, same below
+-			rr.Expiration = uint32(i)
+-		} else {
+-			return nil, &ParseError{f, "bad RRSIG Expiration", l}, ""
+-		}
+-	} else {
+-		rr.Expiration = i
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, err := StringToTime(l.token); err != nil {
+-		if i, err := strconv.ParseInt(l.token, 10, 64); err == nil {
+-			rr.Inception = uint32(i)
+-		} else {
+-			return nil, &ParseError{f, "bad RRSIG Inception", l}, ""
+-		}
+-	} else {
+-		rr.Inception = i
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, err := strconv.Atoi(l.token); err != nil {
+-		return nil, &ParseError{f, "bad RRSIG KeyTag", l}, ""
+-	} else {
+-		rr.KeyTag = uint16(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	rr.SignerName = l.token
+-	if l.token == "@" {
+-		rr.SignerName = o
+-	} else {
+-		_, ok := IsDomainName(l.token)
+-		if !ok || l.length == 0 {
+-			return nil, &ParseError{f, "bad RRSIG SignerName", l}, ""
+-		}
+-		if rr.SignerName[l.length-1] != '.' {
+-			rr.SignerName = appendOrigin(rr.SignerName, o)
+-		}
+-	}
+-	s, e, c1 := endingToString(c, "bad RRSIG Signature", f)
+-	if e != nil {
+-		return nil, e, c1
+-	}
+-	rr.Signature = s
+-	return rr, nil, c1
+-}
+-
+-func setNSEC(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(NSEC)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	rr.NextDomain = l.token
+-	if l.length == 0 {
+-		return rr, nil, l.comment
+-	}
+-	if l.token == "@" {
+-		rr.NextDomain = o
+-	} else {
+-		_, ok := IsDomainName(l.token)
+-		if !ok {
+-			return nil, &ParseError{f, "bad NSEC NextDomain", l}, ""
+-		}
+-		if rr.NextDomain[l.length-1] != '.' {
+-			rr.NextDomain = appendOrigin(rr.NextDomain, o)
+-		}
+-	}
+-
+-	rr.TypeBitMap = make([]uint16, 0)
+-	var (
+-		k  uint16
+-		ok bool
+-	)
+-	l = <-c
+-	for l.value != _NEWLINE && l.value != _EOF {
+-		switch l.value {
+-		case _BLANK:
+-			// Ok
+-		case _STRING:
+-			if k, ok = StringToType[l.tokenUpper]; !ok {
+-				if k, ok = typeToInt(l.tokenUpper); !ok {
+-					return nil, &ParseError{f, "bad NSEC TypeBitMap", l}, ""
+-				}
+-			}
+-			rr.TypeBitMap = append(rr.TypeBitMap, k)
+-		default:
+-			return nil, &ParseError{f, "bad NSEC TypeBitMap", l}, ""
+-		}
+-		l = <-c
+-	}
+-	return rr, nil, l.comment
+-}
+-
+-func setNSEC3(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(NSEC3)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, l.comment
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad NSEC3 Hash", l}, ""
+-	} else {
+-		rr.Hash = uint8(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad NSEC3 Flags", l}, ""
+-	} else {
+-		rr.Flags = uint8(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad NSEC3 Iterations", l}, ""
+-	} else {
+-		rr.Iterations = uint16(i)
+-	}
+-	<-c
+-	l = <-c
+-	if len(l.token) == 0 {
+-		return nil, &ParseError{f, "bad NSEC3 Salt", l}, ""
+-	}
+-	rr.SaltLength = uint8(len(l.token)) / 2
+-	rr.Salt = l.token
+-
+-	<-c
+-	l = <-c
+-	rr.HashLength = 20 // Fix for NSEC3 (sha1 160 bits)
+-	rr.NextDomain = l.token
+-
+-	rr.TypeBitMap = make([]uint16, 0)
+-	var (
+-		k  uint16
+-		ok bool
+-	)
+-	l = <-c
+-	for l.value != _NEWLINE && l.value != _EOF {
+-		switch l.value {
+-		case _BLANK:
+-			// Ok
+-		case _STRING:
+-			if k, ok = StringToType[l.tokenUpper]; !ok {
+-				if k, ok = typeToInt(l.tokenUpper); !ok {
+-					return nil, &ParseError{f, "bad NSEC3 TypeBitMap", l}, ""
+-				}
+-			}
+-			rr.TypeBitMap = append(rr.TypeBitMap, k)
+-		default:
+-			return nil, &ParseError{f, "bad NSEC3 TypeBitMap", l}, ""
+-		}
+-		l = <-c
+-	}
+-	return rr, nil, l.comment
+-}
+-
+-func setNSEC3PARAM(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(NSEC3PARAM)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad NSEC3PARAM Hash", l}, ""
+-	} else {
+-		rr.Hash = uint8(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad NSEC3PARAM Flags", l}, ""
+-	} else {
+-		rr.Flags = uint8(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad NSEC3PARAM Iterations", l}, ""
+-	} else {
+-		rr.Iterations = uint16(i)
+-	}
+-	<-c
+-	l = <-c
+-	rr.SaltLength = uint8(len(l.token))
+-	rr.Salt = l.token
+-	return rr, nil, ""
+-}
+-
+-func setEUI48(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(EUI48)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if l.length != 17 {
+-		return nil, &ParseError{f, "bad EUI48 Address", l}, ""
+-	}
+-	addr := make([]byte, 12)
+-	dash := 0
+-	for i := 0; i < 10; i += 2 {
+-		addr[i] = l.token[i+dash]
+-		addr[i+1] = l.token[i+1+dash]
+-		dash++
+-		if l.token[i+1+dash] != '-' {
+-			return nil, &ParseError{f, "bad EUI48 Address", l}, ""
+-		}
+-	}
+-	addr[10] = l.token[15]
+-	addr[11] = l.token[16]
+-
+-	if i, e := strconv.ParseUint(string(addr), 16, 48); e != nil {
+-		return nil, &ParseError{f, "bad EUI48 Address", l}, ""
+-	} else {
+-		rr.Address = i
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setEUI64(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(EUI64)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if l.length != 23 {
+-		return nil, &ParseError{f, "bad EUI64 Address", l}, ""
+-	}
+-	addr := make([]byte, 16)
+-	dash := 0
+-	for i := 0; i < 14; i += 2 {
+-		addr[i] = l.token[i+dash]
+-		addr[i+1] = l.token[i+1+dash]
+-		dash++
+-		if l.token[i+1+dash] != '-' {
+-			return nil, &ParseError{f, "bad EUI64 Address", l}, ""
+-		}
+-	}
+-	addr[14] = l.token[21]
+-	addr[15] = l.token[22]
+-
+-	if i, e := strconv.ParseUint(string(addr), 16, 64); e != nil {
+-		return nil, &ParseError{f, "bad EUI68 Address", l}, ""
+-	} else {
+-		rr.Address = uint64(i)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setWKS(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(WKS)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, l.comment
+-	}
+-	rr.Address = net.ParseIP(l.token)
+-	if rr.Address == nil {
+-		return nil, &ParseError{f, "bad WKS Address", l}, ""
+-	}
+-
+-	<-c // _BLANK
+-	l = <-c
+-	proto := "tcp"
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad WKS Protocol", l}, ""
+-	} else {
+-		rr.Protocol = uint8(i)
+-		switch rr.Protocol {
+-		case 17:
+-			proto = "udp"
+-		case 6:
+-			proto = "tcp"
+-		default:
+-			return nil, &ParseError{f, "bad WKS Protocol", l}, ""
+-		}
+-	}
+-
+-	<-c
+-	l = <-c
+-	rr.BitMap = make([]uint16, 0)
+-	var (
+-		k   int
+-		err error
+-	)
+-	for l.value != _NEWLINE && l.value != _EOF {
+-		switch l.value {
+-		case _BLANK:
+-			// Ok
+-		case _STRING:
+-			if k, err = net.LookupPort(proto, l.token); err != nil {
+-				if i, e := strconv.Atoi(l.token); e != nil { // If a number use that
+-					rr.BitMap = append(rr.BitMap, uint16(i))
+-				} else {
+-					return nil, &ParseError{f, "bad WKS BitMap", l}, ""
+-				}
+-			}
+-			rr.BitMap = append(rr.BitMap, uint16(k))
+-		default:
+-			return nil, &ParseError{f, "bad WKS BitMap", l}, ""
+-		}
+-		l = <-c
+-	}
+-	return rr, nil, l.comment
+-}
+-
+-func setSSHFP(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(SSHFP)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad SSHFP Algorithm", l}, ""
+-	} else {
+-		rr.Algorithm = uint8(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad SSHFP Type", l}, ""
+-	} else {
+-		rr.Type = uint8(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	rr.FingerPrint = l.token
+-	return rr, nil, ""
+-}
+-
+-func setDNSKEYs(h RR_Header, c chan lex, o, f, typ string) (RR, *ParseError, string) {
+-	rr := new(DNSKEY)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, l.comment
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad " + typ + " Flags", l}, ""
+-	} else {
+-		rr.Flags = uint16(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad " + typ + " Protocol", l}, ""
+-	} else {
+-		rr.Protocol = uint8(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad " + typ + " Algorithm", l}, ""
+-	} else {
+-		rr.Algorithm = uint8(i)
+-	}
+-	s, e, c1 := endingToString(c, "bad "+typ+" PublicKey", f)
+-	if e != nil {
+-		return nil, e, c1
+-	}
+-	rr.PublicKey = s
+-	return rr, nil, c1
+-}
+-
+-func setKEY(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	r, e, s := setDNSKEYs(h, c, o, f, "KEY")
+-	if r != nil {
+-		return &KEY{*r.(*DNSKEY)}, e, s
+-	}
+-	return nil, e, s
+-}
+-
+-func setDNSKEY(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	r, e, s := setDNSKEYs(h, c, o, f, "DNSKEY")
+-	return r, e, s
+-}
+-
+-func setCDNSKEY(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	r, e, s := setDNSKEYs(h, c, o, f, "CDNSKEY")
+-	if r != nil {
+-		return &CDNSKEY{*r.(*DNSKEY)}, e, s
+-	}
+-	return nil, e, s
+-}
+-
+-func setRKEY(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(RKEY)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, l.comment
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad RKEY Flags", l}, ""
+-	} else {
+-		rr.Flags = uint16(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad RKEY Protocol", l}, ""
+-	} else {
+-		rr.Protocol = uint8(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad RKEY Algorithm", l}, ""
+-	} else {
+-		rr.Algorithm = uint8(i)
+-	}
+-	s, e, c1 := endingToString(c, "bad RKEY PublicKey", f)
+-	if e != nil {
+-		return nil, e, c1
+-	}
+-	rr.PublicKey = s
+-	return rr, nil, c1
+-}
+-
+-func setEID(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(EID)
+-	rr.Hdr = h
+-	s, e, c1 := endingToString(c, "bad EID Endpoint", f)
+-	if e != nil {
+-		return nil, e, c1
+-	}
+-	rr.Endpoint = s
+-	return rr, nil, c1
+-}
+-
+-func setNIMLOC(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(NIMLOC)
+-	rr.Hdr = h
+-	s, e, c1 := endingToString(c, "bad NIMLOC Locator", f)
+-	if e != nil {
+-		return nil, e, c1
+-	}
+-	rr.Locator = s
+-	return rr, nil, c1
+-}
+-
+-func setNSAP(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(NSAP)
+-	rr.Hdr = h
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, l.comment
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad NSAP Length", l}, ""
+-	} else {
+-		rr.Length = uint8(i)
+-	}
+-	<-c // _BLANK
+-	s, e, c1 := endingToString(c, "bad NSAP Nsap", f)
+-	if e != nil {
+-		return nil, e, c1
+-	}
+-	rr.Nsap = s
+-	return rr, nil, c1
+-}
+-
+-func setGPOS(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(GPOS)
+-	rr.Hdr = h
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if _, e := strconv.ParseFloat(l.token, 64); e != nil {
+-		return nil, &ParseError{f, "bad GPOS Longitude", l}, ""
+-	} else {
+-		rr.Longitude = l.token
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if _, e := strconv.ParseFloat(l.token, 64); e != nil {
+-		return nil, &ParseError{f, "bad GPOS Latitude", l}, ""
+-	} else {
+-		rr.Latitude = l.token
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if _, e := strconv.ParseFloat(l.token, 64); e != nil {
+-		return nil, &ParseError{f, "bad GPOS Altitude", l}, ""
+-	} else {
+-		rr.Altitude = l.token
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setDSs(h RR_Header, c chan lex, o, f, typ string) (RR, *ParseError, string) {
+-	rr := new(DS)
+-	rr.Hdr = h
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, l.comment
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad " + typ + " KeyTag", l}, ""
+-	} else {
+-		rr.KeyTag = uint16(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		if i, ok := StringToAlgorithm[l.tokenUpper]; !ok {
+-			return nil, &ParseError{f, "bad " + typ + " Algorithm", l}, ""
+-		} else {
+-			rr.Algorithm = i
+-		}
+-	} else {
+-		rr.Algorithm = uint8(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad " + typ + " DigestType", l}, ""
+-	} else {
+-		rr.DigestType = uint8(i)
+-	}
+-	s, e, c1 := endingToString(c, "bad "+typ+" Digest", f)
+-	if e != nil {
+-		return nil, e, c1
+-	}
+-	rr.Digest = s
+-	return rr, nil, c1
+-}
+-
+-func setDS(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	r, e, s := setDSs(h, c, o, f, "DS")
+-	return r, e, s
+-}
+-
+-func setDLV(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	r, e, s := setDSs(h, c, o, f, "DLV")
+-	if r != nil {
+-		return &DLV{*r.(*DS)}, e, s
+-	}
+-	return nil, e, s
+-}
+-
+-func setCDS(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	r, e, s := setDSs(h, c, o, f, "DLV")
+-	if r != nil {
+-		return &CDS{*r.(*DS)}, e, s
+-	}
+-	return nil, e, s
+-}
+-
+-func setTA(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(TA)
+-	rr.Hdr = h
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, l.comment
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad TA KeyTag", l}, ""
+-	} else {
+-		rr.KeyTag = uint16(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		if i, ok := StringToAlgorithm[l.tokenUpper]; !ok {
+-			return nil, &ParseError{f, "bad TA Algorithm", l}, ""
+-		} else {
+-			rr.Algorithm = i
+-		}
+-	} else {
+-		rr.Algorithm = uint8(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad TA DigestType", l}, ""
+-	} else {
+-		rr.DigestType = uint8(i)
+-	}
+-	s, e, c1 := endingToString(c, "bad TA Digest", f)
+-	if e != nil {
+-		return nil, e, c1
+-	}
+-	rr.Digest = s
+-	return rr, nil, c1
+-}
+-
+-func setTLSA(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(TLSA)
+-	rr.Hdr = h
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, l.comment
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad TLSA Usage", l}, ""
+-	} else {
+-		rr.Usage = uint8(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad TLSA Selector", l}, ""
+-	} else {
+-		rr.Selector = uint8(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad TLSA MatchingType", l}, ""
+-	} else {
+-		rr.MatchingType = uint8(i)
+-	}
+-	s, e, c1 := endingToString(c, "bad TLSA Certificate", f)
+-	if e != nil {
+-		return nil, e, c1
+-	}
+-	rr.Certificate = s
+-	return rr, nil, c1
+-}
+-
+-func setRFC3597(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(RFC3597)
+-	rr.Hdr = h
+-	l := <-c
+-	if l.token != "\\#" {
+-		return nil, &ParseError{f, "bad RFC3597 Rdata", l}, ""
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	rdlength, e := strconv.Atoi(l.token)
+-	if e != nil {
+-		return nil, &ParseError{f, "bad RFC3597 Rdata ", l}, ""
+-	}
+-
+-	s, e1, c1 := endingToString(c, "bad RFC3597 Rdata", f)
+-	if e1 != nil {
+-		return nil, e1, c1
+-	}
+-	if rdlength*2 != len(s) {
+-		return nil, &ParseError{f, "bad RFC3597 Rdata", l}, ""
+-	}
+-	rr.Rdata = s
+-	return rr, nil, c1
+-}
+-
+-func setSPF(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(SPF)
+-	rr.Hdr = h
+-
+-	s, e, c1 := endingToTxtSlice(c, "bad SPF Txt", f)
+-	if e != nil {
+-		return nil, e, ""
+-	}
+-	rr.Txt = s
+-	return rr, nil, c1
+-}
+-
+-func setTXT(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(TXT)
+-	rr.Hdr = h
+-
+-	// No _BLANK reading here, because this is all rdata is TXT
+-	s, e, c1 := endingToTxtSlice(c, "bad TXT Txt", f)
+-	if e != nil {
+-		return nil, e, ""
+-	}
+-	rr.Txt = s
+-	return rr, nil, c1
+-}
+-
+-// identical to setTXT
+-func setNINFO(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(NINFO)
+-	rr.Hdr = h
+-
+-	s, e, c1 := endingToTxtSlice(c, "bad NINFO ZSData", f)
+-	if e != nil {
+-		return nil, e, ""
+-	}
+-	rr.ZSData = s
+-	return rr, nil, c1
+-}
+-
+-func setURI(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(URI)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, l.comment
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad URI Priority", l}, ""
+-	} else {
+-		rr.Priority = uint16(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad URI Weight", l}, ""
+-	} else {
+-		rr.Weight = uint16(i)
+-	}
+-
+-	<-c // _BLANK
+-	s, e, c1 := endingToTxtSlice(c, "bad URI Target", f)
+-	if e != nil {
+-		return nil, e, ""
+-	}
+-	rr.Target = s
+-	return rr, nil, c1
+-}
+-
+-func setIPSECKEY(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(IPSECKEY)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, l.comment
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad IPSECKEY Precedence", l}, ""
+-	} else {
+-		rr.Precedence = uint8(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad IPSECKEY GatewayType", l}, ""
+-	} else {
+-		rr.GatewayType = uint8(i)
+-	}
+-	<-c // _BLANK
+-	l = <-c
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad IPSECKEY Algorithm", l}, ""
+-	} else {
+-		rr.Algorithm = uint8(i)
+-	}
+-	<-c
+-	l = <-c
+-	rr.Gateway = l.token
+-	s, e, c1 := endingToString(c, "bad IPSECKEY PublicKey", f)
+-	if e != nil {
+-		return nil, e, c1
+-	}
+-	rr.PublicKey = s
+-	return rr, nil, c1
+-}
+-
+-func setDHCID(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	// awesome record to parse!
+-	rr := new(DHCID)
+-	rr.Hdr = h
+-
+-	s, e, c1 := endingToString(c, "bad DHCID Digest", f)
+-	if e != nil {
+-		return nil, e, c1
+-	}
+-	rr.Digest = s
+-	return rr, nil, c1
+-}
+-
+-func setNID(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(NID)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad NID Preference", l}, ""
+-	} else {
+-		rr.Preference = uint16(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	u, err := stringToNodeID(l)
+-	if err != nil {
+-		return nil, err, ""
+-	}
+-	rr.NodeID = u
+-	return rr, nil, ""
+-}
+-
+-func setL32(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(L32)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad L32 Preference", l}, ""
+-	} else {
+-		rr.Preference = uint16(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	rr.Locator32 = net.ParseIP(l.token)
+-	if rr.Locator32 == nil {
+-		return nil, &ParseError{f, "bad L32 Locator", l}, ""
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setLP(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(LP)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad LP Preference", l}, ""
+-	} else {
+-		rr.Preference = uint16(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	rr.Fqdn = l.token
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if l.token == "@" {
+-		rr.Fqdn = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok || l.length == 0 {
+-		return nil, &ParseError{f, "bad LP Fqdn", l}, ""
+-	}
+-	if rr.Fqdn[l.length-1] != '.' {
+-		rr.Fqdn = appendOrigin(rr.Fqdn, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setL64(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(L64)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad L64 Preference", l}, ""
+-	} else {
+-		rr.Preference = uint16(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	u, err := stringToNodeID(l)
+-	if err != nil {
+-		return nil, err, ""
+-	}
+-	rr.Locator64 = u
+-	return rr, nil, ""
+-}
+-
+-func setUID(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(UID)
+-	rr.Hdr = h
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad UID Uid", l}, ""
+-	} else {
+-		rr.Uid = uint32(i)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setGID(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(GID)
+-	rr.Hdr = h
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad GID Gid", l}, ""
+-	} else {
+-		rr.Gid = uint32(i)
+-	}
+-	return rr, nil, ""
+-}
+-
+-func setUINFO(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(UINFO)
+-	rr.Hdr = h
+-	s, e, c1 := endingToTxtSlice(c, "bad UINFO Uinfo", f)
+-	if e != nil {
+-		return nil, e, ""
+-	}
+-	rr.Uinfo = s[0] // silently discard anything above
+-	return rr, nil, c1
+-}
+-
+-func setPX(h RR_Header, c chan lex, o, f string) (RR, *ParseError, string) {
+-	rr := new(PX)
+-	rr.Hdr = h
+-
+-	l := <-c
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if i, e := strconv.Atoi(l.token); e != nil {
+-		return nil, &ParseError{f, "bad PX Preference", l}, ""
+-	} else {
+-		rr.Preference = uint16(i)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	rr.Map822 = l.token
+-	if l.length == 0 {
+-		return rr, nil, ""
+-	}
+-	if l.token == "@" {
+-		rr.Map822 = o
+-		return rr, nil, ""
+-	}
+-	_, ok := IsDomainName(l.token)
+-	if !ok {
+-		return nil, &ParseError{f, "bad PX Map822", l}, ""
+-	}
+-	if rr.Map822[l.length-1] != '.' {
+-		rr.Map822 = appendOrigin(rr.Map822, o)
+-	}
+-	<-c     // _BLANK
+-	l = <-c // _STRING
+-	rr.Mapx400 = l.token
+-	if l.token == "@" {
+-		rr.Mapx400 = o
+-		return rr, nil, ""
+-	}
+-	_, ok = IsDomainName(l.token)
+-	if !ok || l.length == 0 {
+-		return nil, &ParseError{f, "bad PX Mapx400", l}, ""
+-	}
+-	if rr.Mapx400[l.length-1] != '.' {
+-		rr.Mapx400 = appendOrigin(rr.Mapx400, o)
+-	}
+-	return rr, nil, ""
+-}
+-
+-var typeToparserFunc = map[uint16]parserFunc{
+-	TypeAAAA:       parserFunc{setAAAA, false},
+-	TypeAFSDB:      parserFunc{setAFSDB, false},
+-	TypeA:          parserFunc{setA, false},
+-	TypeCDS:        parserFunc{setCDS, true},
+-	TypeCDNSKEY:    parserFunc{setCDNSKEY, true},
+-	TypeCERT:       parserFunc{setCERT, true},
+-	TypeCNAME:      parserFunc{setCNAME, false},
+-	TypeDHCID:      parserFunc{setDHCID, true},
+-	TypeDLV:        parserFunc{setDLV, true},
+-	TypeDNAME:      parserFunc{setDNAME, false},
+-	TypeKEY:        parserFunc{setKEY, true},
+-	TypeDNSKEY:     parserFunc{setDNSKEY, true},
+-	TypeDS:         parserFunc{setDS, true},
+-	TypeEID:        parserFunc{setEID, true},
+-	TypeEUI48:      parserFunc{setEUI48, false},
+-	TypeEUI64:      parserFunc{setEUI64, false},
+-	TypeGID:        parserFunc{setGID, false},
+-	TypeGPOS:       parserFunc{setGPOS, false},
+-	TypeHINFO:      parserFunc{setHINFO, false},
+-	TypeHIP:        parserFunc{setHIP, true},
+-	TypeIPSECKEY:   parserFunc{setIPSECKEY, true},
+-	TypeKX:         parserFunc{setKX, false},
+-	TypeL32:        parserFunc{setL32, false},
+-	TypeL64:        parserFunc{setL64, false},
+-	TypeLOC:        parserFunc{setLOC, true},
+-	TypeLP:         parserFunc{setLP, false},
+-	TypeMB:         parserFunc{setMB, false},
+-	TypeMD:         parserFunc{setMD, false},
+-	TypeMF:         parserFunc{setMF, false},
+-	TypeMG:         parserFunc{setMG, false},
+-	TypeMINFO:      parserFunc{setMINFO, false},
+-	TypeMR:         parserFunc{setMR, false},
+-	TypeMX:         parserFunc{setMX, false},
+-	TypeNAPTR:      parserFunc{setNAPTR, false},
+-	TypeNID:        parserFunc{setNID, false},
+-	TypeNIMLOC:     parserFunc{setNIMLOC, true},
+-	TypeNINFO:      parserFunc{setNINFO, true},
+-	TypeNSAP:       parserFunc{setNSAP, true},
+-	TypeNSAPPTR:    parserFunc{setNSAPPTR, false},
+-	TypeNSEC3PARAM: parserFunc{setNSEC3PARAM, false},
+-	TypeNSEC3:      parserFunc{setNSEC3, true},
+-	TypeNSEC:       parserFunc{setNSEC, true},
+-	TypeNS:         parserFunc{setNS, false},
+-	TypeOPENPGPKEY: parserFunc{setOPENPGPKEY, true},
+-	TypePTR:        parserFunc{setPTR, false},
+-	TypePX:         parserFunc{setPX, false},
+-	TypeSIG:        parserFunc{setSIG, true},
+-	TypeRKEY:       parserFunc{setRKEY, true},
+-	TypeRP:         parserFunc{setRP, false},
+-	TypeRRSIG:      parserFunc{setRRSIG, true},
+-	TypeRT:         parserFunc{setRT, false},
+-	TypeSOA:        parserFunc{setSOA, false},
+-	TypeSPF:        parserFunc{setSPF, true},
+-	TypeSRV:        parserFunc{setSRV, false},
+-	TypeSSHFP:      parserFunc{setSSHFP, false},
+-	TypeTALINK:     parserFunc{setTALINK, false},
+-	TypeTA:         parserFunc{setTA, true},
+-	TypeTLSA:       parserFunc{setTLSA, true},
+-	TypeTXT:        parserFunc{setTXT, true},
+-	TypeUID:        parserFunc{setUID, false},
+-	TypeUINFO:      parserFunc{setUINFO, true},
+-	TypeURI:        parserFunc{setURI, true},
+-	TypeWKS:        parserFunc{setWKS, true},
+-	TypeX25:        parserFunc{setX25, false},
+-}
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/attempt.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/attempt.go
+deleted file mode 100644
+index c0654f5..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/attempt.go
++++ /dev/null
+@@ -1,74 +0,0 @@
+-package aws
+-
+-import (
+-	"time"
+-)
+-
+-// AttemptStrategy represents a strategy for waiting for an action
+-// to complete successfully. This is an internal type used by the
+-// implementation of other goamz packages.
+-type AttemptStrategy struct {
+-	Total time.Duration // total duration of attempt.
+-	Delay time.Duration // interval between each try in the burst.
+-	Min   int           // minimum number of retries; overrides Total
+-}
+-
+-type Attempt struct {
+-	strategy AttemptStrategy
+-	last     time.Time
+-	end      time.Time
+-	force    bool
+-	count    int
+-}
+-
+-// Start begins a new sequence of attempts for the given strategy.
+-func (s AttemptStrategy) Start() *Attempt {
+-	now := time.Now()
+-	return &Attempt{
+-		strategy: s,
+-		last:     now,
+-		end:      now.Add(s.Total),
+-		force:    true,
+-	}
+-}
+-
+-// Next waits until it is time to perform the next attempt or returns
+-// false if it is time to stop trying.
+-func (a *Attempt) Next() bool {
+-	now := time.Now()
+-	sleep := a.nextSleep(now)
+-	if !a.force && !now.Add(sleep).Before(a.end) && a.strategy.Min <= a.count {
+-		return false
+-	}
+-	a.force = false
+-	if sleep > 0 && a.count > 0 {
+-		time.Sleep(sleep)
+-		now = time.Now()
+-	}
+-	a.count++
+-	a.last = now
+-	return true
+-}
+-
+-func (a *Attempt) nextSleep(now time.Time) time.Duration {
+-	sleep := a.strategy.Delay - now.Sub(a.last)
+-	if sleep < 0 {
+-		return 0
+-	}
+-	return sleep
+-}
+-
+-// HasNext returns whether another attempt will be made if the current
+-// one fails. If it returns true, the following call to Next is
+-// guaranteed to return true.
+-func (a *Attempt) HasNext() bool {
+-	if a.force || a.strategy.Min > a.count {
+-		return true
+-	}
+-	now := time.Now()
+-	if now.Add(a.nextSleep(now)).Before(a.end) {
+-		a.force = true
+-		return true
+-	}
+-	return false
+-}
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/attempt_test.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/attempt_test.go
+deleted file mode 100644
+index 1fda5bf..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/attempt_test.go
++++ /dev/null
+@@ -1,57 +0,0 @@
+-package aws_test
+-
+-import (
+-	"github.com/mitchellh/goamz/aws"
+-	. "github.com/motain/gocheck"
+-	"time"
+-)
+-
+-func (S) TestAttemptTiming(c *C) {
+-	testAttempt := aws.AttemptStrategy{
+-		Total: 0.25e9,
+-		Delay: 0.1e9,
+-	}
+-	want := []time.Duration{0, 0.1e9, 0.2e9, 0.2e9}
+-	got := make([]time.Duration, 0, len(want)) // avoid allocation when testing timing
+-	t0 := time.Now()
+-	for a := testAttempt.Start(); a.Next(); {
+-		got = append(got, time.Now().Sub(t0))
+-	}
+-	got = append(got, time.Now().Sub(t0))
+-	c.Assert(got, HasLen, len(want))
+-	const margin = 0.01e9
+-	for i, got := range want {
+-		lo := want[i] - margin
+-		hi := want[i] + margin
+-		if got < lo || got > hi {
+-			c.Errorf("attempt %d want %g got %g", i, want[i].Seconds(), got.Seconds())
+-		}
+-	}
+-}
+-
+-func (S) TestAttemptNextHasNext(c *C) {
+-	a := aws.AttemptStrategy{}.Start()
+-	c.Assert(a.Next(), Equals, true)
+-	c.Assert(a.Next(), Equals, false)
+-
+-	a = aws.AttemptStrategy{}.Start()
+-	c.Assert(a.Next(), Equals, true)
+-	c.Assert(a.HasNext(), Equals, false)
+-	c.Assert(a.Next(), Equals, false)
+-
+-	a = aws.AttemptStrategy{Total: 2e8}.Start()
+-	c.Assert(a.Next(), Equals, true)
+-	c.Assert(a.HasNext(), Equals, true)
+-	time.Sleep(2e8)
+-	c.Assert(a.HasNext(), Equals, true)
+-	c.Assert(a.Next(), Equals, true)
+-	c.Assert(a.Next(), Equals, false)
+-
+-	a = aws.AttemptStrategy{Total: 1e8, Min: 2}.Start()
+-	time.Sleep(1e8)
+-	c.Assert(a.Next(), Equals, true)
+-	c.Assert(a.HasNext(), Equals, true)
+-	c.Assert(a.Next(), Equals, true)
+-	c.Assert(a.HasNext(), Equals, false)
+-	c.Assert(a.Next(), Equals, false)
+-}
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/aws.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/aws.go
+deleted file mode 100644
+index c304d55..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/aws.go
++++ /dev/null
+@@ -1,423 +0,0 @@
+-//
+-// goamz - Go packages to interact with the Amazon Web Services.
+-//
+-//   https://wiki.ubuntu.com/goamz
+-//
+-// Copyright (c) 2011 Canonical Ltd.
+-//
+-// Written by Gustavo Niemeyer <gustavo.niemeyer at canonical.com>
+-//
+-package aws
+-
+-import (
+-	"encoding/json"
+-	"errors"
+-	"fmt"
+-	"github.com/vaughan0/go-ini"
+-	"io/ioutil"
+-	"os"
+-)
+-
+-// Region defines the URLs where AWS services may be accessed.
+-//
+-// See http://goo.gl/d8BP1 for more details.
+-type Region struct {
+-	Name                 string // the canonical name of this region.
+-	EC2Endpoint          string
+-	S3Endpoint           string
+-	S3BucketEndpoint     string // Not needed by AWS S3. Use ${bucket} for bucket name.
+-	S3LocationConstraint bool   // true if this region requires a LocationConstraint declaration.
+-	S3LowercaseBucket    bool   // true if the region requires bucket names to be lower case.
+-	SDBEndpoint          string
+-	SNSEndpoint          string
+-	SQSEndpoint          string
+-	IAMEndpoint          string
+-	ELBEndpoint          string
+-	AutoScalingEndpoint  string
+-	RdsEndpoint          string
+-	Route53Endpoint      string
+-}
+-
+-var USGovWest = Region{
+-	"us-gov-west-1",
+-	"https://ec2.us-gov-west-1.amazonaws.com",
+-	"https://s3-fips-us-gov-west-1.amazonaws.com",
+-	"",
+-	true,
+-	true,
+-	"",
+-	"https://sns.us-gov-west-1.amazonaws.com",
+-	"https://sqs.us-gov-west-1.amazonaws.com",
+-	"https://iam.us-gov.amazonaws.com",
+-	"https://elasticloadbalancing.us-gov-west-1.amazonaws.com",
+-	"https://autoscaling.us-gov-west-1.amazonaws.com",
+-	"https://rds.us-gov-west-1.amazonaws.com",
+-	"https://route53.amazonaws.com",
+-}
+-
+-var USEast = Region{
+-	"us-east-1",
+-	"https://ec2.us-east-1.amazonaws.com",
+-	"https://s3.amazonaws.com",
+-	"",
+-	false,
+-	false,
+-	"https://sdb.amazonaws.com",
+-	"https://sns.us-east-1.amazonaws.com",
+-	"https://sqs.us-east-1.amazonaws.com",
+-	"https://iam.amazonaws.com",
+-	"https://elasticloadbalancing.us-east-1.amazonaws.com",
+-	"https://autoscaling.us-east-1.amazonaws.com",
+-	"https://rds.us-east-1.amazonaws.com",
+-	"https://route53.amazonaws.com",
+-}
+-
+-var USWest = Region{
+-	"us-west-1",
+-	"https://ec2.us-west-1.amazonaws.com",
+-	"https://s3-us-west-1.amazonaws.com",
+-	"",
+-	true,
+-	true,
+-	"https://sdb.us-west-1.amazonaws.com",
+-	"https://sns.us-west-1.amazonaws.com",
+-	"https://sqs.us-west-1.amazonaws.com",
+-	"https://iam.amazonaws.com",
+-	"https://elasticloadbalancing.us-west-1.amazonaws.com",
+-	"https://autoscaling.us-west-1.amazonaws.com",
+-	"https://rds.us-west-1.amazonaws.com",
+-	"https://route53.amazonaws.com",
+-}
+-
+-var USWest2 = Region{
+-	"us-west-2",
+-	"https://ec2.us-west-2.amazonaws.com",
+-	"https://s3-us-west-2.amazonaws.com",
+-	"",
+-	true,
+-	true,
+-	"https://sdb.us-west-2.amazonaws.com",
+-	"https://sns.us-west-2.amazonaws.com",
+-	"https://sqs.us-west-2.amazonaws.com",
+-	"https://iam.amazonaws.com",
+-	"https://elasticloadbalancing.us-west-2.amazonaws.com",
+-	"https://autoscaling.us-west-2.amazonaws.com",
+-	"https://rds.us-west-2.amazonaws.com",
+-	"https://route53.amazonaws.com",
+-}
+-
+-var EUWest = Region{
+-	"eu-west-1",
+-	"https://ec2.eu-west-1.amazonaws.com",
+-	"https://s3-eu-west-1.amazonaws.com",
+-	"",
+-	true,
+-	true,
+-	"https://sdb.eu-west-1.amazonaws.com",
+-	"https://sns.eu-west-1.amazonaws.com",
+-	"https://sqs.eu-west-1.amazonaws.com",
+-	"https://iam.amazonaws.com",
+-	"https://elasticloadbalancing.eu-west-1.amazonaws.com",
+-	"https://autoscaling.eu-west-1.amazonaws.com",
+-	"https://rds.eu-west-1.amazonaws.com",
+-	"https://route53.amazonaws.com",
+-}
+-
+-var APSoutheast = Region{
+-	"ap-southeast-1",
+-	"https://ec2.ap-southeast-1.amazonaws.com",
+-	"https://s3-ap-southeast-1.amazonaws.com",
+-	"",
+-	true,
+-	true,
+-	"https://sdb.ap-southeast-1.amazonaws.com",
+-	"https://sns.ap-southeast-1.amazonaws.com",
+-	"https://sqs.ap-southeast-1.amazonaws.com",
+-	"https://iam.amazonaws.com",
+-	"https://elasticloadbalancing.ap-southeast-1.amazonaws.com",
+-	"https://autoscaling.ap-southeast-1.amazonaws.com",
+-	"https://rds.ap-southeast-1.amazonaws.com",
+-	"https://route53.amazonaws.com",
+-}
+-
+-var APSoutheast2 = Region{
+-	"ap-southeast-2",
+-	"https://ec2.ap-southeast-2.amazonaws.com",
+-	"https://s3-ap-southeast-2.amazonaws.com",
+-	"",
+-	true,
+-	true,
+-	"https://sdb.ap-southeast-2.amazonaws.com",
+-	"https://sns.ap-southeast-2.amazonaws.com",
+-	"https://sqs.ap-southeast-2.amazonaws.com",
+-	"https://iam.amazonaws.com",
+-	"https://elasticloadbalancing.ap-southeast-2.amazonaws.com",
+-	"https://autoscaling.ap-southeast-2.amazonaws.com",
+-	"https://rds.ap-southeast-2.amazonaws.com",
+-	"https://route53.amazonaws.com",
+-}
+-
+-var APNortheast = Region{
+-	"ap-northeast-1",
+-	"https://ec2.ap-northeast-1.amazonaws.com",
+-	"https://s3-ap-northeast-1.amazonaws.com",
+-	"",
+-	true,
+-	true,
+-	"https://sdb.ap-northeast-1.amazonaws.com",
+-	"https://sns.ap-northeast-1.amazonaws.com",
+-	"https://sqs.ap-northeast-1.amazonaws.com",
+-	"https://iam.amazonaws.com",
+-	"https://elasticloadbalancing.ap-northeast-1.amazonaws.com",
+-	"https://autoscaling.ap-northeast-1.amazonaws.com",
+-	"https://rds.ap-northeast-1.amazonaws.com",
+-	"https://route53.amazonaws.com",
+-}
+-
+-var SAEast = Region{
+-	"sa-east-1",
+-	"https://ec2.sa-east-1.amazonaws.com",
+-	"https://s3-sa-east-1.amazonaws.com",
+-	"",
+-	true,
+-	true,
+-	"https://sdb.sa-east-1.amazonaws.com",
+-	"https://sns.sa-east-1.amazonaws.com",
+-	"https://sqs.sa-east-1.amazonaws.com",
+-	"https://iam.amazonaws.com",
+-	"https://elasticloadbalancing.sa-east-1.amazonaws.com",
+-	"https://autoscaling.sa-east-1.amazonaws.com",
+-	"https://rds.sa-east-1.amazonaws.com",
+-	"https://route53.amazonaws.com",
+-}
+-
+-var CNNorth = Region{
+-	"cn-north-1",
+-	"https://ec2.cn-north-1.amazonaws.com.cn",
+-	"https://s3.cn-north-1.amazonaws.com.cn",
+-	"",
+-	true,
+-	true,
+-	"",
+-	"https://sns.cn-north-1.amazonaws.com.cn",
+-	"https://sqs.cn-north-1.amazonaws.com.cn",
+-	"https://iam.cn-north-1.amazonaws.com.cn",
+-	"https://elasticloadbalancing.cn-north-1.amazonaws.com.cn",
+-	"https://autoscaling.cn-north-1.amazonaws.com.cn",
+-	"https://rds.cn-north-1.amazonaws.com.cn",
+-	"https://route53.amazonaws.com",
+-}
+-
+-var Regions = map[string]Region{
+-	APNortheast.Name:  APNortheast,
+-	APSoutheast.Name:  APSoutheast,
+-	APSoutheast2.Name: APSoutheast2,
+-	EUWest.Name:       EUWest,
+-	USEast.Name:       USEast,
+-	USWest.Name:       USWest,
+-	USWest2.Name:      USWest2,
+-	SAEast.Name:       SAEast,
+-	USGovWest.Name:    USGovWest,
+-	CNNorth.Name:      CNNorth,
+-}
+-
+-type Auth struct {
+-	AccessKey, SecretKey, Token string
+-}
+-
+-var unreserved = make([]bool, 128)
+-var hex = "0123456789ABCDEF"
+-
+-func init() {
+-	// RFC3986
+-	u := "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz01234567890-_.~"
+-	for _, c := range u {
+-		unreserved[c] = true
+-	}
+-}
+-
+-type credentials struct {
+-	Code            string
+-	LastUpdated     string
+-	Type            string
+-	AccessKeyId     string
+-	SecretAccessKey string
+-	Token           string
+-	Expiration      string
+-}
+-
+-// GetMetaData retrieves instance metadata about the current machine.
+-//
+-// See http://docs.aws.amazon.com/AWSEC2/latest/UserGuide/AESDG-chapter-instancedata.html for more details.
+-func GetMetaData(path string) (contents []byte, err error) {
+-	url := "http://169.254.169.254/latest/meta-data/" + path
+-
+-	resp, err := RetryingClient.Get(url)
+-	if err != nil {
+-		return
+-	}
+-	defer resp.Body.Close()
+-
+-	if resp.StatusCode != 200 {
+-		err = fmt.Errorf("Code %d returned for url %s", resp.StatusCode, url)
+-		return
+-	}
+-
+-	body, err := ioutil.ReadAll(resp.Body)
+-	if err != nil {
+-		return
+-	}
+-	return []byte(body), err
+-}
+-
+-func getInstanceCredentials() (cred credentials, err error) {
+-	credentialPath := "iam/security-credentials/"
+-
+-	// Get the instance role
+-	role, err := GetMetaData(credentialPath)
+-	if err != nil {
+-		return
+-	}
+-
+-	// Get the instance role credentials
+-	credentialJSON, err := GetMetaData(credentialPath + string(role))
+-	if err != nil {
+-		return
+-	}
+-
+-	err = json.Unmarshal([]byte(credentialJSON), &cred)
+-	return
+-}
+-
+-// GetAuth creates an Auth based on either passed in credentials,
+-// environment information or instance based role credentials.
+-func GetAuth(accessKey string, secretKey string) (auth Auth, err error) {
+-	// First try passed in credentials
+-	if accessKey != "" && secretKey != "" {
+-		return Auth{accessKey, secretKey, ""}, nil
+-	}
+-
+-	// Next try to get auth from the environment
+-	auth, err = SharedAuth()
+-	if err == nil {
+-		// Found auth, return
+-		return
+-	}
+-
+-	// Next try to get auth from the environment
+-	auth, err = EnvAuth()
+-	if err == nil {
+-		// Found auth, return
+-		return
+-	}
+-
+-	// Next try getting auth from the instance role
+-	cred, err := getInstanceCredentials()
+-	if err == nil {
+-		// Found auth, return
+-		auth.AccessKey = cred.AccessKeyId
+-		auth.SecretKey = cred.SecretAccessKey
+-		auth.Token = cred.Token
+-		return
+-	}
+-	err = errors.New("No valid AWS authentication found")
+-	return
+-}
+-
+-// SharedAuth creates an Auth based on shared credentials stored in
+-// $HOME/.aws/credentials. The AWS_PROFILE environment variables is used to
+-// select the profile.
+-func SharedAuth() (auth Auth, err error) {
+-	var profileName = os.Getenv("AWS_PROFILE")
+-
+-	if profileName == "" {
+-		profileName = "default"
+-	}
+-
+-	var homeDir = os.Getenv("HOME")
+-	if homeDir == "" {
+-		err = errors.New("Could not get HOME")
+-		return
+-	}
+-
+-	var credentialsFile = homeDir + "/.aws/credentials"
+-	file, err := ini.LoadFile(credentialsFile)
+-	if err != nil {
+-		err = errors.New("Couldn't parse AWS credentials file")
+-		return
+-	}
+-
+-	var profile = file[profileName]
+-	if profile == nil {
+-		err = errors.New("Couldn't find profile in AWS credentials file")
+-		return
+-	}
+-
+-	auth.AccessKey = profile["aws_access_key_id"]
+-	auth.SecretKey = profile["aws_secret_access_key"]
+-
+-	if auth.AccessKey == "" {
+-		err = errors.New("AWS_ACCESS_KEY_ID not found in environment in credentials file")
+-	}
+-	if auth.SecretKey == "" {
+-		err = errors.New("AWS_SECRET_ACCESS_KEY not found in credentials file")
+-	}
+-	return
+-}
+-
+-// EnvAuth creates an Auth based on environment information.
+-// The AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment
+-// For accounts that require a security token, it is read from AWS_SECURITY_TOKEN
+-// variables are used.
+-func EnvAuth() (auth Auth, err error) {
+-	auth.AccessKey = os.Getenv("AWS_ACCESS_KEY_ID")
+-	if auth.AccessKey == "" {
+-		auth.AccessKey = os.Getenv("AWS_ACCESS_KEY")
+-	}
+-
+-	auth.SecretKey = os.Getenv("AWS_SECRET_ACCESS_KEY")
+-	if auth.SecretKey == "" {
+-		auth.SecretKey = os.Getenv("AWS_SECRET_KEY")
+-	}
+-
+-	auth.Token = os.Getenv("AWS_SECURITY_TOKEN")
+-
+-	if auth.AccessKey == "" {
+-		err = errors.New("AWS_ACCESS_KEY_ID or AWS_ACCESS_KEY not found in environment")
+-	}
+-	if auth.SecretKey == "" {
+-		err = errors.New("AWS_SECRET_ACCESS_KEY or AWS_SECRET_KEY not found in environment")
+-	}
+-	return
+-}
+-
+-// Encode takes a string and URI-encodes it in a way suitable
+-// to be used in AWS signatures.
+-func Encode(s string) string {
+-	encode := false
+-	for i := 0; i != len(s); i++ {
+-		c := s[i]
+-		if c > 127 || !unreserved[c] {
+-			encode = true
+-			break
+-		}
+-	}
+-	if !encode {
+-		return s
+-	}
+-	e := make([]byte, len(s)*3)
+-	ei := 0
+-	for i := 0; i != len(s); i++ {
+-		c := s[i]
+-		if c > 127 || !unreserved[c] {
+-			e[ei] = '%'
+-			e[ei+1] = hex[c>>4]
+-			e[ei+2] = hex[c&0xF]
+-			ei += 3
+-		} else {
+-			e[ei] = c
+-			ei += 1
+-		}
+-	}
+-	return string(e[:ei])
+-}
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/aws_test.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/aws_test.go
+deleted file mode 100644
+index 78cbbaf..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/aws_test.go
++++ /dev/null
+@@ -1,203 +0,0 @@
+-package aws_test
+-
+-import (
+-	"github.com/mitchellh/goamz/aws"
+-	. "github.com/motain/gocheck"
+-	"io/ioutil"
+-	"os"
+-	"strings"
+-	"testing"
+-)
+-
+-func Test(t *testing.T) {
+-	TestingT(t)
+-}
+-
+-var _ = Suite(&S{})
+-
+-type S struct {
+-	environ []string
+-}
+-
+-func (s *S) SetUpSuite(c *C) {
+-	s.environ = os.Environ()
+-}
+-
+-func (s *S) TearDownTest(c *C) {
+-	os.Clearenv()
+-	for _, kv := range s.environ {
+-		l := strings.SplitN(kv, "=", 2)
+-		os.Setenv(l[0], l[1])
+-	}
+-}
+-
+-func (s *S) TestSharedAuthNoHome(c *C) {
+-	os.Clearenv()
+-	os.Setenv("AWS_PROFILE", "foo")
+-	_, err := aws.SharedAuth()
+-	c.Assert(err, ErrorMatches, "Could not get HOME")
+-}
+-
+-func (s *S) TestSharedAuthNoCredentialsFile(c *C) {
+-	os.Clearenv()
+-	os.Setenv("AWS_PROFILE", "foo")
+-	os.Setenv("HOME", "/tmp")
+-	_, err := aws.SharedAuth()
+-	c.Assert(err, ErrorMatches, "Couldn't parse AWS credentials file")
+-}
+-
+-func (s *S) TestSharedAuthNoProfileInFile(c *C) {
+-	os.Clearenv()
+-	os.Setenv("AWS_PROFILE", "foo")
+-
+-	d, err := ioutil.TempDir("", "")
+-	if err != nil {
+-		panic(err)
+-	}
+-	defer os.RemoveAll(d)
+-
+-	err = os.Mkdir(d+"/.aws", 0755)
+-	if err != nil {
+-		panic(err)
+-	}
+-
+-	ioutil.WriteFile(d+"/.aws/credentials", []byte("[bar]\n"), 0644)
+-	os.Setenv("HOME", d)
+-
+-	_, err = aws.SharedAuth()
+-	c.Assert(err, ErrorMatches, "Couldn't find profile in AWS credentials file")
+-}
+-
+-func (s *S) TestSharedAuthNoKeysInProfile(c *C) {
+-	os.Clearenv()
+-	os.Setenv("AWS_PROFILE", "bar")
+-
+-	d, err := ioutil.TempDir("", "")
+-	if err != nil {
+-		panic(err)
+-	}
+-	defer os.RemoveAll(d)
+-
+-	err = os.Mkdir(d+"/.aws", 0755)
+-	if err != nil {
+-		panic(err)
+-	}
+-
+-	ioutil.WriteFile(d+"/.aws/credentials", []byte("[bar]\nawsaccesskeyid = AK.."), 0644)
+-	os.Setenv("HOME", d)
+-
+-	_, err = aws.SharedAuth()
+-	c.Assert(err, ErrorMatches, "AWS_SECRET_ACCESS_KEY not found in credentials file")
+-}
+-
+-func (s *S) TestSharedAuthDefaultCredentials(c *C) {
+-	os.Clearenv()
+-
+-	d, err := ioutil.TempDir("", "")
+-	if err != nil {
+-		panic(err)
+-	}
+-	defer os.RemoveAll(d)
+-
+-	err = os.Mkdir(d+"/.aws", 0755)
+-	if err != nil {
+-		panic(err)
+-	}
+-
+-	ioutil.WriteFile(d+"/.aws/credentials", []byte("[default]\naws_access_key_id = access\naws_secret_access_key = secret\n"), 0644)
+-	os.Setenv("HOME", d)
+-
+-	auth, err := aws.SharedAuth()
+-	c.Assert(err, IsNil)
+-	c.Assert(auth, Equals, aws.Auth{SecretKey: "secret", AccessKey: "access"})
+-}
+-
+-func (s *S) TestSharedAuth(c *C) {
+-	os.Clearenv()
+-	os.Setenv("AWS_PROFILE", "bar")
+-
+-	d, err := ioutil.TempDir("", "")
+-	if err != nil {
+-		panic(err)
+-	}
+-	defer os.RemoveAll(d)
+-
+-	err = os.Mkdir(d+"/.aws", 0755)
+-	if err != nil {
+-		panic(err)
+-	}
+-
+-	ioutil.WriteFile(d+"/.aws/credentials", []byte("[bar]\naws_access_key_id = access\naws_secret_access_key = secret\n"), 0644)
+-	os.Setenv("HOME", d)
+-
+-	auth, err := aws.SharedAuth()
+-	c.Assert(err, IsNil)
+-	c.Assert(auth, Equals, aws.Auth{SecretKey: "secret", AccessKey: "access"})
+-}
+-
+-func (s *S) TestEnvAuthNoSecret(c *C) {
+-	os.Clearenv()
+-	_, err := aws.EnvAuth()
+-	c.Assert(err, ErrorMatches, "AWS_SECRET_ACCESS_KEY or AWS_SECRET_KEY not found in environment")
+-}
+-
+-func (s *S) TestEnvAuthNoAccess(c *C) {
+-	os.Clearenv()
+-	os.Setenv("AWS_SECRET_ACCESS_KEY", "foo")
+-	_, err := aws.EnvAuth()
+-	c.Assert(err, ErrorMatches, "AWS_ACCESS_KEY_ID or AWS_ACCESS_KEY not found in environment")
+-}
+-
+-func (s *S) TestEnvAuth(c *C) {
+-	os.Clearenv()
+-	os.Setenv("AWS_SECRET_ACCESS_KEY", "secret")
+-	os.Setenv("AWS_ACCESS_KEY_ID", "access")
+-	auth, err := aws.EnvAuth()
+-	c.Assert(err, IsNil)
+-	c.Assert(auth, Equals, aws.Auth{SecretKey: "secret", AccessKey: "access"})
+-}
+-
+-func (s *S) TestEnvAuthWithToken(c *C) {
+-	os.Clearenv()
+-	os.Setenv("AWS_SECRET_ACCESS_KEY", "secret")
+-	os.Setenv("AWS_ACCESS_KEY_ID", "access")
+-	os.Setenv("AWS_SECURITY_TOKEN", "token")
+-	auth, err := aws.EnvAuth()
+-	c.Assert(err, IsNil)
+-	c.Assert(auth, Equals, aws.Auth{SecretKey: "secret", AccessKey: "access", Token: "token"})
+-}
+-
+-func (s *S) TestEnvAuthAlt(c *C) {
+-	os.Clearenv()
+-	os.Setenv("AWS_SECRET_KEY", "secret")
+-	os.Setenv("AWS_ACCESS_KEY", "access")
+-	auth, err := aws.EnvAuth()
+-	c.Assert(err, IsNil)
+-	c.Assert(auth, Equals, aws.Auth{SecretKey: "secret", AccessKey: "access"})
+-}
+-
+-func (s *S) TestGetAuthStatic(c *C) {
+-	auth, err := aws.GetAuth("access", "secret")
+-	c.Assert(err, IsNil)
+-	c.Assert(auth, Equals, aws.Auth{SecretKey: "secret", AccessKey: "access"})
+-}
+-
+-func (s *S) TestGetAuthEnv(c *C) {
+-	os.Clearenv()
+-	os.Setenv("AWS_SECRET_ACCESS_KEY", "secret")
+-	os.Setenv("AWS_ACCESS_KEY_ID", "access")
+-	auth, err := aws.GetAuth("", "")
+-	c.Assert(err, IsNil)
+-	c.Assert(auth, Equals, aws.Auth{SecretKey: "secret", AccessKey: "access"})
+-}
+-
+-func (s *S) TestEncode(c *C) {
+-	c.Assert(aws.Encode("foo"), Equals, "foo")
+-	c.Assert(aws.Encode("/"), Equals, "%2F")
+-}
+-
+-func (s *S) TestRegionsAreNamed(c *C) {
+-	for n, r := range aws.Regions {
+-		c.Assert(n, Equals, r.Name)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/client.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/client.go
+deleted file mode 100644
+index ee53238..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/client.go
++++ /dev/null
+@@ -1,125 +0,0 @@
+-package aws
+-
+-import (
+-	"math"
+-	"net"
+-	"net/http"
+-	"time"
+-)
+-
+-type RetryableFunc func(*http.Request, *http.Response, error) bool
+-type WaitFunc func(try int)
+-type DeadlineFunc func() time.Time
+-
+-type ResilientTransport struct {
+-	// Timeout is the maximum amount of time a dial will wait for
+-	// a connect to complete.
+-	//
+-	// The default is no timeout.
+-	//
+-	// With or without a timeout, the operating system may impose
+-	// its own earlier timeout. For instance, TCP timeouts are
+-	// often around 3 minutes.
+-	DialTimeout time.Duration
+-
+-	// MaxTries, if non-zero, specifies the number of times we will retry on
+-	// failure. Retries are only attempted for temporary network errors or known
+-	// safe failures.
+-	MaxTries    int
+-	Deadline    DeadlineFunc
+-	ShouldRetry RetryableFunc
+-	Wait        WaitFunc
+-	transport   *http.Transport
+-}
+-
+-// Convenience method for creating an http client
+-func NewClient(rt *ResilientTransport) *http.Client {
+-	rt.transport = &http.Transport{
+-		Dial: func(netw, addr string) (net.Conn, error) {
+-			c, err := net.DialTimeout(netw, addr, rt.DialTimeout)
+-			if err != nil {
+-				return nil, err
+-			}
+-			c.SetDeadline(rt.Deadline())
+-			return c, nil
+-		},
+-		DisableKeepAlives: true,
+-		Proxy:             http.ProxyFromEnvironment,
+-	}
+-	// TODO: Would be nice is ResilientTransport allowed clients to initialize
+-	// with http.Transport attributes.
+-	return &http.Client{
+-		Transport: rt,
+-	}
+-}
+-
+-var retryingTransport = &ResilientTransport{
+-	Deadline: func() time.Time {
+-		return time.Now().Add(5 * time.Second)
+-	},
+-	DialTimeout: 10 * time.Second,
+-	MaxTries:    3,
+-	ShouldRetry: awsRetry,
+-	Wait:        ExpBackoff,
+-}
+-
+-// Exported default client
+-var RetryingClient = NewClient(retryingTransport)
+-
+-func (t *ResilientTransport) RoundTrip(req *http.Request) (*http.Response, error) {
+-	return t.tries(req)
+-}
+-
+-// Retry a request a maximum of t.MaxTries times.
+-// We'll only retry if the proper criteria are met.
+-// If a wait function is specified, wait that amount of time
+-// In between requests.
+-func (t *ResilientTransport) tries(req *http.Request) (res *http.Response, err error) {
+-	for try := 0; try < t.MaxTries; try += 1 {
+-		res, err = t.transport.RoundTrip(req)
+-
+-		if !t.ShouldRetry(req, res, err) {
+-			break
+-		}
+-		if res != nil {
+-			res.Body.Close()
+-		}
+-		if t.Wait != nil {
+-			t.Wait(try)
+-		}
+-	}
+-
+-	return
+-}
+-
+-func ExpBackoff(try int) {
+-	time.Sleep(100 * time.Millisecond *
+-		time.Duration(math.Exp2(float64(try))))
+-}
+-
+-func LinearBackoff(try int) {
+-	time.Sleep(time.Duration(try*100) * time.Millisecond)
+-}
+-
+-// Decide if we should retry a request.
+-// In general, the criteria for retrying a request is described here
+-// http://docs.aws.amazon.com/general/latest/gr/api-retries.html
+-func awsRetry(req *http.Request, res *http.Response, err error) bool {
+-	retry := false
+-
+-	// Retry if there's a temporary network error.
+-	if neterr, ok := err.(net.Error); ok {
+-		if neterr.Temporary() {
+-			retry = true
+-		}
+-	}
+-
+-	// Retry if we get a 5xx series error.
+-	if res != nil {
+-		if res.StatusCode >= 500 && res.StatusCode < 600 {
+-			retry = true
+-		}
+-	}
+-
+-	return retry
+-}
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/client_test.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/client_test.go
+deleted file mode 100644
+index 2f6b39c..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/client_test.go
++++ /dev/null
+@@ -1,121 +0,0 @@
+-package aws_test
+-
+-import (
+-	"fmt"
+-	"github.com/mitchellh/goamz/aws"
+-	"io/ioutil"
+-	"net/http"
+-	"net/http/httptest"
+-	"strings"
+-	"testing"
+-	"time"
+-)
+-
+-// Retrieve the response from handler using aws.RetryingClient
+-func serveAndGet(handler http.HandlerFunc) (body string, err error) {
+-	ts := httptest.NewServer(handler)
+-	defer ts.Close()
+-	resp, err := aws.RetryingClient.Get(ts.URL)
+-	if err != nil {
+-		return
+-	}
+-	if resp.StatusCode != 200 {
+-		return "", fmt.Errorf("Bad status code: %d", resp.StatusCode)
+-	}
+-	greeting, err := ioutil.ReadAll(resp.Body)
+-	resp.Body.Close()
+-	if err != nil {
+-		return
+-	}
+-	return strings.TrimSpace(string(greeting)), nil
+-}
+-
+-func TestClient_expected(t *testing.T) {
+-	body := "foo bar"
+-
+-	resp, err := serveAndGet(func(w http.ResponseWriter, r *http.Request) {
+-		fmt.Fprintln(w, body)
+-	})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if resp != body {
+-		t.Fatal("Body not as expected.")
+-	}
+-}
+-
+-func TestClient_delay(t *testing.T) {
+-	body := "baz"
+-	wait := 4
+-	resp, err := serveAndGet(func(w http.ResponseWriter, r *http.Request) {
+-		if wait < 0 {
+-			// If we dipped to zero delay and still failed.
+-			t.Fatal("Never succeeded.")
+-		}
+-		wait -= 1
+-		time.Sleep(time.Second * time.Duration(wait))
+-		fmt.Fprintln(w, body)
+-	})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if resp != body {
+-		t.Fatal("Body not as expected.", resp)
+-	}
+-}
+-
+-func TestClient_no4xxRetry(t *testing.T) {
+-	tries := 0
+-
+-	// Fail once before succeeding.
+-	_, err := serveAndGet(func(w http.ResponseWriter, r *http.Request) {
+-		tries += 1
+-		http.Error(w, "error", 404)
+-	})
+-
+-	if err == nil {
+-		t.Fatal("should have error")
+-	}
+-
+-	if tries != 1 {
+-		t.Fatalf("should only try once: %d", tries)
+-	}
+-}
+-
+-func TestClient_retries(t *testing.T) {
+-	body := "biz"
+-	failed := false
+-	// Fail once before succeeding.
+-	resp, err := serveAndGet(func(w http.ResponseWriter, r *http.Request) {
+-		if !failed {
+-			http.Error(w, "error", 500)
+-			failed = true
+-		} else {
+-			fmt.Fprintln(w, body)
+-		}
+-	})
+-	if failed != true {
+-		t.Error("We didn't retry!")
+-	}
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if resp != body {
+-		t.Fatal("Body not as expected.")
+-	}
+-}
+-
+-func TestClient_fails(t *testing.T) {
+-	tries := 0
+-	// Fail 3 times and return the last error.
+-	_, err := serveAndGet(func(w http.ResponseWriter, r *http.Request) {
+-		tries += 1
+-		http.Error(w, "error", 500)
+-	})
+-	if err == nil {
+-		t.Fatal(err)
+-	}
+-	if tries != 3 {
+-		t.Fatal("Didn't retry enough")
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2.go
+deleted file mode 100644
+index 8f94ad5..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2.go
++++ /dev/null
+@@ -1,2599 +0,0 @@
+-//
+-// goamz - Go packages to interact with the Amazon Web Services.
+-//
+-//   https://wiki.ubuntu.com/goamz
+-//
+-// Copyright (c) 2011 Canonical Ltd.
+-//
+-// Written by Gustavo Niemeyer <gustavo.niemeyer at canonical.com>
+-//
+-
+-package ec2
+-
+-import (
+-	"crypto/rand"
+-	"encoding/base64"
+-	"encoding/hex"
+-	"encoding/xml"
+-	"fmt"
+-	"log"
+-	"net/http"
+-	"net/http/httputil"
+-	"net/url"
+-	"sort"
+-	"strconv"
+-	"strings"
+-	"time"
+-
+-	"github.com/mitchellh/goamz/aws"
+-)
+-
+-const debug = false
+-
+-// The EC2 type encapsulates operations with a specific EC2 region.
+-type EC2 struct {
+-	aws.Auth
+-	aws.Region
+-	httpClient *http.Client
+-	private    byte // Reserve the right of using private data.
+-}
+-
+-// New creates a new EC2.
+-func NewWithClient(auth aws.Auth, region aws.Region, client *http.Client) *EC2 {
+-	return &EC2{auth, region, client, 0}
+-}
+-
+-func New(auth aws.Auth, region aws.Region) *EC2 {
+-	return NewWithClient(auth, region, aws.RetryingClient)
+-}
+-
+-// ----------------------------------------------------------------------------
+-// Filtering helper.
+-
+-// Filter builds filtering parameters to be used in an EC2 query which supports
+-// filtering.  For example:
+-//
+-//     filter := NewFilter()
+-//     filter.Add("architecture", "i386")
+-//     filter.Add("launch-index", "0")
+-//     resp, err := ec2.Instances(nil, filter)
+-//
+-type Filter struct {
+-	m map[string][]string
+-}
+-
+-// NewFilter creates a new Filter.
+-func NewFilter() *Filter {
+-	return &Filter{make(map[string][]string)}
+-}
+-
+-// Add appends a filtering parameter with the given name and value(s).
+-func (f *Filter) Add(name string, value ...string) {
+-	f.m[name] = append(f.m[name], value...)
+-}
+-
+-func (f *Filter) addParams(params map[string]string) {
+-	if f != nil {
+-		a := make([]string, len(f.m))
+-		i := 0
+-		for k := range f.m {
+-			a[i] = k
+-			i++
+-		}
+-		sort.StringSlice(a).Sort()
+-		for i, k := range a {
+-			prefix := "Filter." + strconv.Itoa(i+1)
+-			params[prefix+".Name"] = k
+-			for j, v := range f.m[k] {
+-				params[prefix+".Value."+strconv.Itoa(j+1)] = v
+-			}
+-		}
+-	}
+-}
+-
+-// ----------------------------------------------------------------------------
+-// Request dispatching logic.
+-
+-// Error encapsulates an error returned by EC2.
+-//
+-// See http://goo.gl/VZGuC for more details.
+-type Error struct {
+-	// HTTP status code (200, 403, ...)
+-	StatusCode int
+-	// EC2 error code ("UnsupportedOperation", ...)
+-	Code string
+-	// The human-oriented error message
+-	Message   string
+-	RequestId string `xml:"RequestID"`
+-}
+-
+-func (err *Error) Error() string {
+-	if err.Code == "" {
+-		return err.Message
+-	}
+-
+-	return fmt.Sprintf("%s (%s)", err.Message, err.Code)
+-}
+-
+-// For now a single error inst is being exposed. In the future it may be useful
+-// to provide access to all of them, but rather than doing it as an array/slice,
+-// use a *next pointer, so that it's backward compatible and it continues to be
+-// easy to handle the first error, which is what most people will want.
+-type xmlErrors struct {
+-	RequestId string  `xml:"RequestID"`
+-	Errors    []Error `xml:"Errors>Error"`
+-}
+-
+-var timeNow = time.Now
+-
+-func (ec2 *EC2) query(params map[string]string, resp interface{}) error {
+-	params["Version"] = "2014-05-01"
+-	params["Timestamp"] = timeNow().In(time.UTC).Format(time.RFC3339)
+-	endpoint, err := url.Parse(ec2.Region.EC2Endpoint)
+-	if err != nil {
+-		return err
+-	}
+-	if endpoint.Path == "" {
+-		endpoint.Path = "/"
+-	}
+-	sign(ec2.Auth, "GET", endpoint.Path, params, endpoint.Host)
+-	endpoint.RawQuery = multimap(params).Encode()
+-	if debug {
+-		log.Printf("get { %v } -> {\n", endpoint.String())
+-	}
+-
+-	r, err := ec2.httpClient.Get(endpoint.String())
+-	if err != nil {
+-		return err
+-	}
+-	defer r.Body.Close()
+-
+-	if debug {
+-		dump, _ := httputil.DumpResponse(r, true)
+-		log.Printf("response:\n")
+-		log.Printf("%v\n}\n", string(dump))
+-	}
+-	if r.StatusCode != 200 {
+-		return buildError(r)
+-	}
+-	err = xml.NewDecoder(r.Body).Decode(resp)
+-	return err
+-}
+-
+-func multimap(p map[string]string) url.Values {
+-	q := make(url.Values, len(p))
+-	for k, v := range p {
+-		q[k] = []string{v}
+-	}
+-	return q
+-}
+-
+-func buildError(r *http.Response) error {
+-	errors := xmlErrors{}
+-	xml.NewDecoder(r.Body).Decode(&errors)
+-	var err Error
+-	if len(errors.Errors) > 0 {
+-		err = errors.Errors[0]
+-	}
+-	err.RequestId = errors.RequestId
+-	err.StatusCode = r.StatusCode
+-	if err.Message == "" {
+-		err.Message = r.Status
+-	}
+-	return &err
+-}
+-
+-func makeParams(action string) map[string]string {
+-	params := make(map[string]string)
+-	params["Action"] = action
+-	return params
+-}
+-
+-func addParamsList(params map[string]string, label string, ids []string) {
+-	for i, id := range ids {
+-		params[label+"."+strconv.Itoa(i+1)] = id
+-	}
+-}
+-
+-func addBlockDeviceParams(prename string, params map[string]string, blockdevices []BlockDeviceMapping) {
+-	for i, k := range blockdevices {
+-		// Fixup index since Amazon counts these from 1
+-		prefix := prename + "BlockDeviceMapping." + strconv.Itoa(i+1) + "."
+-
+-		if k.DeviceName != "" {
+-			params[prefix+"DeviceName"] = k.DeviceName
+-		}
+-		if k.VirtualName != "" {
+-			params[prefix+"VirtualName"] = k.VirtualName
+-		}
+-		if k.SnapshotId != "" {
+-			params[prefix+"Ebs.SnapshotId"] = k.SnapshotId
+-		}
+-		if k.VolumeType != "" {
+-			params[prefix+"Ebs.VolumeType"] = k.VolumeType
+-		}
+-		if k.IOPS != 0 {
+-			params[prefix+"Ebs.Iops"] = strconv.FormatInt(k.IOPS, 10)
+-		}
+-		if k.VolumeSize != 0 {
+-			params[prefix+"Ebs.VolumeSize"] = strconv.FormatInt(k.VolumeSize, 10)
+-		}
+-		if k.DeleteOnTermination {
+-			params[prefix+"Ebs.DeleteOnTermination"] = "true"
+-		}
+-		if k.Encrypted {
+-			params[prefix+"Ebs.Encrypted"] = "true"
+-		}
+-		if k.NoDevice {
+-			params[prefix+"NoDevice"] = ""
+-		}
+-	}
+-}
 -
--examples/restful-hello-world
+-// ----------------------------------------------------------------------------
+-// Instance management functions and types.
 -
--examples/restful-resource-functions
+-// The RunInstances type encapsulates options for the respective request in EC2.
+-//
+-// See http://goo.gl/Mcm3b for more details.
+-type RunInstances struct {
+-	ImageId                  string
+-	MinCount                 int
+-	MaxCount                 int
+-	KeyName                  string
+-	InstanceType             string
+-	SecurityGroups           []SecurityGroup
+-	IamInstanceProfile       string
+-	KernelId                 string
+-	RamdiskId                string
+-	UserData                 []byte
+-	AvailZone                string
+-	PlacementGroupName       string
+-	Monitoring               bool
+-	SubnetId                 string
+-	AssociatePublicIpAddress bool
+-	DisableAPITermination    bool
+-	ShutdownBehavior         string
+-	PrivateIPAddress         string
+-	BlockDevices             []BlockDeviceMapping
+-}
 -
--examples/restful-serve-static
+-// Response to a RunInstances request.
+-//
+-// See http://goo.gl/Mcm3b for more details.
+-type RunInstancesResp struct {
+-	RequestId      string          `xml:"requestId"`
+-	ReservationId  string          `xml:"reservationId"`
+-	OwnerId        string          `xml:"ownerId"`
+-	SecurityGroups []SecurityGroup `xml:"groupSet>item"`
+-	Instances      []Instance      `xml:"instancesSet>item"`
+-}
 -
--examples/restful-user-service
+-// Instance encapsulates a running instance in EC2.
+-//
+-// See http://goo.gl/OCH8a for more details.
+-type Instance struct {
+-	InstanceId         string          `xml:"instanceId"`
+-	InstanceType       string          `xml:"instanceType"`
+-	ImageId            string          `xml:"imageId"`
+-	PrivateDNSName     string          `xml:"privateDnsName"`
+-	DNSName            string          `xml:"dnsName"`
+-	KeyName            string          `xml:"keyName"`
+-	AMILaunchIndex     int             `xml:"amiLaunchIndex"`
+-	Hypervisor         string          `xml:"hypervisor"`
+-	VirtType           string          `xml:"virtualizationType"`
+-	Monitoring         string          `xml:"monitoring>state"`
+-	AvailZone          string          `xml:"placement>availabilityZone"`
+-	PlacementGroupName string          `xml:"placement>groupName"`
+-	State              InstanceState   `xml:"instanceState"`
+-	Tags               []Tag           `xml:"tagSet>item"`
+-	VpcId              string          `xml:"vpcId"`
+-	SubnetId           string          `xml:"subnetId"`
+-	IamInstanceProfile string          `xml:"iamInstanceProfile"`
+-	PrivateIpAddress   string          `xml:"privateIpAddress"`
+-	PublicIpAddress    string          `xml:"ipAddress"`
+-	Architecture       string          `xml:"architecture"`
+-	LaunchTime         time.Time       `xml:"launchTime"`
+-	SourceDestCheck    bool            `xml:"sourceDestCheck"`
+-	SecurityGroups     []SecurityGroup `xml:"groupSet>item"`
+-}
 -
--*.DS_Store
--examples/restful-user-resource
+-// RunInstances starts new instances in EC2.
+-// If options.MinCount and options.MaxCount are both zero, a single instance
+-// will be started; otherwise if options.MaxCount is zero, options.MinCount
+-// will be used insteead.
+-//
+-// See http://goo.gl/Mcm3b for more details.
+-func (ec2 *EC2) RunInstances(options *RunInstances) (resp *RunInstancesResp, err error) {
+-	params := makeParams("RunInstances")
+-	params["ImageId"] = options.ImageId
+-	params["InstanceType"] = options.InstanceType
+-	var min, max int
+-	if options.MinCount == 0 && options.MaxCount == 0 {
+-		min = 1
+-		max = 1
+-	} else if options.MaxCount == 0 {
+-		min = options.MinCount
+-		max = min
+-	} else {
+-		min = options.MinCount
+-		max = options.MaxCount
+-	}
+-	params["MinCount"] = strconv.Itoa(min)
+-	params["MaxCount"] = strconv.Itoa(max)
+-	token, err := clientToken()
+-	if err != nil {
+-		return nil, err
+-	}
+-	params["ClientToken"] = token
 -
--examples/restful-multi-containers
+-	if options.KeyName != "" {
+-		params["KeyName"] = options.KeyName
+-	}
+-	if options.KernelId != "" {
+-		params["KernelId"] = options.KernelId
+-	}
+-	if options.RamdiskId != "" {
+-		params["RamdiskId"] = options.RamdiskId
+-	}
+-	if options.UserData != nil {
+-		userData := make([]byte, b64.EncodedLen(len(options.UserData)))
+-		b64.Encode(userData, options.UserData)
+-		params["UserData"] = string(userData)
+-	}
+-	if options.AvailZone != "" {
+-		params["Placement.AvailabilityZone"] = options.AvailZone
+-	}
+-	if options.PlacementGroupName != "" {
+-		params["Placement.GroupName"] = options.PlacementGroupName
+-	}
+-	if options.Monitoring {
+-		params["Monitoring.Enabled"] = "true"
+-	}
+-	if options.SubnetId != "" && options.AssociatePublicIpAddress {
+-		// If we have a non-default VPC / Subnet specified, we can flag
+-		// AssociatePublicIpAddress to get a Public IP assigned. By default these are not provided.
+-		// You cannot specify both SubnetId and the NetworkInterface.0.* parameters though, otherwise
+-		// you get: Network interfaces and an instance-level subnet ID may not be specified on the same request
+-		// You also need to attach Security Groups to the NetworkInterface instead of the instance,
+-		// to avoid: Network interfaces and an instance-level security groups may not be specified on
+-		// the same request
+-		params["NetworkInterface.0.DeviceIndex"] = "0"
+-		params["NetworkInterface.0.AssociatePublicIpAddress"] = "true"
+-		params["NetworkInterface.0.SubnetId"] = options.SubnetId
 -
--examples/restful-form-handling
+-		i := 1
+-		for _, g := range options.SecurityGroups {
+-			// We only have SecurityGroupId's on NetworkInterface's, no SecurityGroup params.
+-			if g.Id != "" {
+-				params["NetworkInterface.0.SecurityGroupId."+strconv.Itoa(i)] = g.Id
+-				i++
+-			}
+-		}
+-	} else {
+-		if options.SubnetId != "" {
+-			params["SubnetId"] = options.SubnetId
+-		}
 -
--examples/restful-CORS-filter
+-		i, j := 1, 1
+-		for _, g := range options.SecurityGroups {
+-			if g.Id != "" {
+-				params["SecurityGroupId."+strconv.Itoa(i)] = g.Id
+-				i++
+-			} else {
+-				params["SecurityGroup."+strconv.Itoa(j)] = g.Name
+-				j++
+-			}
+-		}
+-	}
+-	if options.IamInstanceProfile != "" {
+-		params["IamInstanceProfile.Name"] = options.IamInstanceProfile
+-	}
+-	if options.DisableAPITermination {
+-		params["DisableApiTermination"] = "true"
+-	}
+-	if options.ShutdownBehavior != "" {
+-		params["InstanceInitiatedShutdownBehavior"] = options.ShutdownBehavior
+-	}
+-	if options.PrivateIPAddress != "" {
+-		params["PrivateIpAddress"] = options.PrivateIPAddress
+-	}
+-	addBlockDeviceParams("", params, options.BlockDevices)
 -
--examples/restful-options-filter
+-	resp = &RunInstancesResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return
+-}
 -
--examples/restful-curly-router
+-func clientToken() (string, error) {
+-	// Maximum EC2 client token size is 64 bytes.
+-	// Each byte expands to two when hex encoded.
+-	buf := make([]byte, 32)
+-	_, err := rand.Read(buf)
+-	if err != nil {
+-		return "", err
+-	}
+-	return hex.EncodeToString(buf), nil
+-}
 -
--examples/restful-cpuprofiler-service
+-// ----------------------------------------------------------------------------
+-// Spot Instance management functions and types.
 -
--examples/restful-pre-post-filters
+-// The RequestSpotInstances type encapsulates options for the respective request in EC2.
+-//
+-// See http://goo.gl/GRZgCD for more details.
+-type RequestSpotInstances struct {
+-	SpotPrice                string
+-	InstanceCount            int
+-	Type                     string
+-	ImageId                  string
+-	KeyName                  string
+-	InstanceType             string
+-	SecurityGroups           []SecurityGroup
+-	IamInstanceProfile       string
+-	KernelId                 string
+-	RamdiskId                string
+-	UserData                 []byte
+-	AvailZone                string
+-	PlacementGroupName       string
+-	Monitoring               bool
+-	SubnetId                 string
+-	AssociatePublicIpAddress bool
+-	PrivateIPAddress         string
+-	BlockDevices             []BlockDeviceMapping
+-}
 -
--curly.prof
+-type SpotInstanceSpec struct {
+-	ImageId                  string
+-	KeyName                  string
+-	InstanceType             string
+-	SecurityGroups           []SecurityGroup
+-	IamInstanceProfile       string
+-	KernelId                 string
+-	RamdiskId                string
+-	UserData                 []byte
+-	AvailZone                string
+-	PlacementGroupName       string
+-	Monitoring               bool
+-	SubnetId                 string
+-	AssociatePublicIpAddress bool
+-	PrivateIPAddress         string
+-	BlockDevices             []BlockDeviceMapping
+-}
 -
--examples/restful-NCSA-logging
+-type SpotLaunchSpec struct {
+-	ImageId            string               `xml:"imageId"`
+-	KeyName            string               `xml:"keyName"`
+-	InstanceType       string               `xml:"instanceType"`
+-	SecurityGroups     []SecurityGroup      `xml:"groupSet>item"`
+-	IamInstanceProfile string               `xml:"iamInstanceProfile"`
+-	KernelId           string               `xml:"kernelId"`
+-	RamdiskId          string               `xml:"ramdiskId"`
+-	PlacementGroupName string               `xml:"placement>groupName"`
+-	Monitoring         bool                 `xml:"monitoring>enabled"`
+-	SubnetId           string               `xml:"subnetId"`
+-	BlockDevices       []BlockDeviceMapping `xml:"blockDeviceMapping>item"`
+-}
 -
--examples/restful-html-template
+-type SpotStatus struct {
+-	Code       string `xml:"code"`
+-	UpdateTime string `xml:"updateTime"`
+-	Message    string `xml:"message"`
+-}
 -
--s.html
--restful-path-tail
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/CHANGES.md b/Godeps/_workspace/src/github.com/emicklei/go-restful/CHANGES.md
-deleted file mode 100644
-index 9c6de61..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/CHANGES.md
-+++ /dev/null
-@@ -1,130 +0,0 @@
--Change history of go-restful
--=
--2014-11-27
--- (api add) PrettyPrint per response. (as proposed in #167)
+-type SpotRequestResult struct {
+-	SpotRequestId  string         `xml:"spotInstanceRequestId"`
+-	SpotPrice      string         `xml:"spotPrice"`
+-	Type           string         `xml:"type"`
+-	AvailZone      string         `xml:"launchedAvailabilityZone"`
+-	InstanceId     string         `xml:"instanceId"`
+-	State          string         `xml:"state"`
+-	Status         SpotStatus     `xml:"status"`
+-	SpotLaunchSpec SpotLaunchSpec `xml:"launchSpecification"`
+-	CreateTime     string         `xml:"createTime"`
+-	Tags           []Tag          `xml:"tagSet>item"`
+-}
 -
--2014-11-12
--- (api add) ApiVersion(.) for documentation in Swagger UI
+-// Response to a RequestSpotInstances request.
+-//
+-// See http://goo.gl/GRZgCD for more details.
+-type RequestSpotInstancesResp struct {
+-	RequestId          string              `xml:"requestId"`
+-	SpotRequestResults []SpotRequestResult `xml:"spotInstanceRequestSet>item"`
+-}
 -
--2014-11-10
--- (api change) struct fields tagged with "description" show up in Swagger UI
+-// RequestSpotInstances requests a new spot instances in EC2.
+-func (ec2 *EC2) RequestSpotInstances(options *RequestSpotInstances) (resp *RequestSpotInstancesResp, err error) {
+-	params := makeParams("RequestSpotInstances")
+-	prefix := "LaunchSpecification" + "."
 -
--2014-10-31
--- (api change) ReturnsError -> Returns
--- (api add)    RouteBuilder.Do(aBuilder) for DRY use of RouteBuilder
--- fix swagger nested structs
--- sort Swagger response messages by code
+-	params["SpotPrice"] = options.SpotPrice
+-	params[prefix+"ImageId"] = options.ImageId
+-	params[prefix+"InstanceType"] = options.InstanceType
 -
--2014-10-23
--- (api add) ReturnsError allows you to document Http codes in swagger
--- fixed problem with greedy CurlyRouter
--- (api add) Access-Control-Max-Age in CORS
--- add tracing functionality (injectable) for debugging purposes
--- support JSON parse 64bit int 
--- fix empty parameters for swagger
--- WebServicesUrl is now optional for swagger
--- fixed duplicate AccessControlAllowOrigin in CORS
--- (api change) expose ServeMux in container
--- (api add) added AllowedDomains in CORS
--- (api add) ParameterNamed for detailed documentation
+-	if options.InstanceCount != 0 {
+-		params["InstanceCount"] = strconv.Itoa(options.InstanceCount)
+-	}
+-	if options.KeyName != "" {
+-		params[prefix+"KeyName"] = options.KeyName
+-	}
+-	if options.KernelId != "" {
+-		params[prefix+"KernelId"] = options.KernelId
+-	}
+-	if options.RamdiskId != "" {
+-		params[prefix+"RamdiskId"] = options.RamdiskId
+-	}
+-	if options.UserData != nil {
+-		userData := make([]byte, b64.EncodedLen(len(options.UserData)))
+-		b64.Encode(userData, options.UserData)
+-		params[prefix+"UserData"] = string(userData)
+-	}
+-	if options.AvailZone != "" {
+-		params[prefix+"Placement.AvailabilityZone"] = options.AvailZone
+-	}
+-	if options.PlacementGroupName != "" {
+-		params[prefix+"Placement.GroupName"] = options.PlacementGroupName
+-	}
+-	if options.Monitoring {
+-		params[prefix+"Monitoring.Enabled"] = "true"
+-	}
+-	if options.SubnetId != "" && options.AssociatePublicIpAddress {
+-		// If we have a non-default VPC / Subnet specified, we can flag
+-		// AssociatePublicIpAddress to get a Public IP assigned. By default these are not provided.
+-		// You cannot specify both SubnetId and the NetworkInterface.0.* parameters though, otherwise
+-		// you get: Network interfaces and an instance-level subnet ID may not be specified on the same request
+-		// You also need to attach Security Groups to the NetworkInterface instead of the instance,
+-		// to avoid: Network interfaces and an instance-level security groups may not be specified on
+-		// the same request
+-		params[prefix+"NetworkInterface.0.DeviceIndex"] = "0"
+-		params[prefix+"NetworkInterface.0.AssociatePublicIpAddress"] = "true"
+-		params[prefix+"NetworkInterface.0.SubnetId"] = options.SubnetId
 -
--2014-04-16
--- (api add) expose constructor of Request for testing.
+-		i := 1
+-		for _, g := range options.SecurityGroups {
+-			// We only have SecurityGroupId's on NetworkInterface's, no SecurityGroup params.
+-			if g.Id != "" {
+-				params[prefix+"NetworkInterface.0.SecurityGroupId."+strconv.Itoa(i)] = g.Id
+-				i++
+-			}
+-		}
+-	} else {
+-		if options.SubnetId != "" {
+-			params[prefix+"SubnetId"] = options.SubnetId
+-		}
 -
--2014-06-27
--- (api add) ParameterNamed gives access to a Parameter definition and its data (for further specification).
--- (api add) SetCacheReadEntity allow scontrol over whether or not the request body is being cached (default true for compatibility reasons).
+-		i, j := 1, 1
+-		for _, g := range options.SecurityGroups {
+-			if g.Id != "" {
+-				params[prefix+"SecurityGroupId."+strconv.Itoa(i)] = g.Id
+-				i++
+-			} else {
+-				params[prefix+"SecurityGroup."+strconv.Itoa(j)] = g.Name
+-				j++
+-			}
+-		}
+-	}
+-	if options.IamInstanceProfile != "" {
+-		params[prefix+"IamInstanceProfile.Name"] = options.IamInstanceProfile
+-	}
+-	if options.PrivateIPAddress != "" {
+-		params[prefix+"PrivateIpAddress"] = options.PrivateIPAddress
+-	}
+-	addBlockDeviceParams(prefix, params, options.BlockDevices)
 -
--2014-07-03
--- (api add) CORS can be configured with a list of allowed domains
+-	resp = &RequestSpotInstancesResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return
+-}
 -
--2014-03-12
--- (api add) Route path parameters can use wildcard or regular expressions. (requires CurlyRouter)
+-// Response to a DescribeSpotInstanceRequests request.
+-//
+-// See http://goo.gl/KsKJJk for more details.
+-type SpotRequestsResp struct {
+-	RequestId          string              `xml:"requestId"`
+-	SpotRequestResults []SpotRequestResult `xml:"spotInstanceRequestSet>item"`
+-}
 -
--2014-02-26
--- (api add) Request now provides information about the matched Route, see method SelectedRoutePath 
+-// DescribeSpotInstanceRequests returns details about spot requests in EC2.  Both parameters
+-// are optional, and if provided will limit the spot requests returned to those
+-// matching the given spot request ids or filtering rules.
+-//
+-// See http://goo.gl/KsKJJk for more details.
+-func (ec2 *EC2) DescribeSpotRequests(spotrequestIds []string, filter *Filter) (resp *SpotRequestsResp, err error) {
+-	params := makeParams("DescribeSpotInstanceRequests")
+-	addParamsList(params, "SpotInstanceRequestId", spotrequestIds)
+-	filter.addParams(params)
+-	resp = &SpotRequestsResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return
+-}
 -
--2014-02-17
--- (api change) renamed parameter constants (go-lint checks)
+-// Response to a CancelSpotInstanceRequests request.
+-//
+-// See http://goo.gl/3BKHj for more details.
+-type CancelSpotRequestResult struct {
+-	SpotRequestId string `xml:"spotInstanceRequestId"`
+-	State         string `xml:"state"`
+-}
+-type CancelSpotRequestsResp struct {
+-	RequestId                string                    `xml:"requestId"`
+-	CancelSpotRequestResults []CancelSpotRequestResult `xml:"spotInstanceRequestSet>item"`
+-}
 -
--2014-01-10
-- - (api add) support for CloseNotify, see http://golang.org/pkg/net/http/#CloseNotifier
+-// CancelSpotRequests requests the cancellation of spot requests when the given ids.
+-//
+-// See http://goo.gl/3BKHj for more details.
+-func (ec2 *EC2) CancelSpotRequests(spotrequestIds []string) (resp *CancelSpotRequestsResp, err error) {
+-	params := makeParams("CancelSpotInstanceRequests")
+-	addParamsList(params, "SpotInstanceRequestId", spotrequestIds)
+-	resp = &CancelSpotRequestsResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return
+-}
 -
--2014-01-07
-- - (api change) Write* methods in Response now return the error or nil.
-- - added example of serving HTML from a Go template.
-- - fixed comparing Allowed headers in CORS (is now case-insensitive)
+-// Response to a TerminateInstances request.
+-//
+-// See http://goo.gl/3BKHj for more details.
+-type TerminateInstancesResp struct {
+-	RequestId    string                `xml:"requestId"`
+-	StateChanges []InstanceStateChange `xml:"instancesSet>item"`
+-}
 -
--2013-11-13
-- - (api add) Response knows how many bytes are written to the response body.
+-// InstanceState encapsulates the state of an instance in EC2.
+-//
+-// See http://goo.gl/y3ZBq for more details.
+-type InstanceState struct {
+-	Code int    `xml:"code"` // Watch out, bits 15-8 have unpublished meaning.
+-	Name string `xml:"name"`
+-}
 -
--2013-10-29
-- - (api add) RecoverHandler(handler RecoverHandleFunction) to change how panic recovery is handled. Default behavior is to log and return a stacktrace. This may be a security issue as it exposes sourcecode information.
+-// InstanceStateChange informs of the previous and current states
+-// for an instance when a state change is requested.
+-type InstanceStateChange struct {
+-	InstanceId    string        `xml:"instanceId"`
+-	CurrentState  InstanceState `xml:"currentState"`
+-	PreviousState InstanceState `xml:"previousState"`
+-}
 -
--2013-10-04
-- - (api add) Response knows what HTTP status has been written
-- - (api add) Request can have attributes (map of string->interface, also called request-scoped variables
+-// TerminateInstances requests the termination of instances when the given ids.
+-//
+-// See http://goo.gl/3BKHj for more details.
+-func (ec2 *EC2) TerminateInstances(instIds []string) (resp *TerminateInstancesResp, err error) {
+-	params := makeParams("TerminateInstances")
+-	addParamsList(params, "InstanceId", instIds)
+-	resp = &TerminateInstancesResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return
+-}
 -
--2013-09-12
-- - (api change) Router interface simplified
-- - Implemented CurlyRouter, a Router that does not use|allow regular expressions in paths
+-// Response to a DescribeInstances request.
+-//
+-// See http://goo.gl/mLbmw for more details.
+-type InstancesResp struct {
+-	RequestId    string        `xml:"requestId"`
+-	Reservations []Reservation `xml:"reservationSet>item"`
+-}
 -
--2013-08-05
-- - add OPTIONS support
-- - add CORS support
+-// Reservation represents details about a reservation in EC2.
+-//
+-// See http://goo.gl/0ItPT for more details.
+-type Reservation struct {
+-	ReservationId  string          `xml:"reservationId"`
+-	OwnerId        string          `xml:"ownerId"`
+-	RequesterId    string          `xml:"requesterId"`
+-	SecurityGroups []SecurityGroup `xml:"groupSet>item"`
+-	Instances      []Instance      `xml:"instancesSet>item"`
+-}
 -
--2013-08-27
-- - fixed some reported issues (see github)
-- - (api change) deprecated use of WriteError; use WriteErrorString instead
+-// Instances returns details about instances in EC2.  Both parameters
+-// are optional, and if provided will limit the instances returned to those
+-// matching the given instance ids or filtering rules.
+-//
+-// See http://goo.gl/4No7c for more details.
+-func (ec2 *EC2) Instances(instIds []string, filter *Filter) (resp *InstancesResp, err error) {
+-	params := makeParams("DescribeInstances")
+-	addParamsList(params, "InstanceId", instIds)
+-	filter.addParams(params)
+-	resp = &InstancesResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return
+-}
 -
--2014-04-15
-- - (fix) v1.0.1 tag: fix Issue 111: WriteErrorString
+-// ----------------------------------------------------------------------------
+-// Volume management
 -
--2013-08-08
-- - (api add) Added implementation Container: a WebServices collection with its own http.ServeMux allowing multiple endpoints per program. Existing uses of go-restful will register their services to the DefaultContainer.
-- - (api add) the swagger package has be extended to have a UI per container.
-- - if panic is detected then a small stack trace is printed (thanks to runner-mei)
-- - (api add) WriteErrorString to Response
+-// The CreateVolume request parameters
+-//
+-// See http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-CreateVolume.html
+-type CreateVolume struct {
+-	AvailZone  string
+-	Size       int64
+-	SnapshotId string
+-	VolumeType string
+-	IOPS       int64
+-	Encrypted  bool
+-}
+-
+-// Response to an AttachVolume request
+-type AttachVolumeResp struct {
+-	RequestId  string `xml:"requestId"`
+-	VolumeId   string `xml:"volumeId"`
+-	InstanceId string `xml:"instanceId"`
+-	Device     string `xml:"device"`
+-	Status     string `xml:"status"`
+-	AttachTime string `xml:"attachTime"`
+-}
+-
+-// Response to a CreateVolume request
+-type CreateVolumeResp struct {
+-	RequestId  string `xml:"requestId"`
+-	VolumeId   string `xml:"volumeId"`
+-	Size       int64  `xml:"size"`
+-	SnapshotId string `xml:"snapshotId"`
+-	AvailZone  string `xml:"availabilityZone"`
+-	Status     string `xml:"status"`
+-	CreateTime string `xml:"createTime"`
+-	VolumeType string `xml:"volumeType"`
+-	IOPS       int64  `xml:"iops"`
+-	Encrypted  bool   `xml:"encrypted"`
+-}
+-
+-// Volume is a single volume.
+-type Volume struct {
+-	VolumeId    string             `xml:"volumeId"`
+-	Size        string             `xml:"size"`
+-	SnapshotId  string             `xml:"snapshotId"`
+-	AvailZone   string             `xml:"availabilityZone"`
+-	Status      string             `xml:"status"`
+-	Attachments []VolumeAttachment `xml:"attachmentSet>item"`
+-	VolumeType  string             `xml:"volumeType"`
+-	IOPS        int64              `xml:"iops"`
+-	Encrypted   bool               `xml:"encrypted"`
+-	Tags        []Tag              `xml:"tagSet>item"`
+-}
+-
+-type VolumeAttachment struct {
+-	VolumeId   string `xml:"volumeId"`
+-	InstanceId string `xml:"instanceId"`
+-	Device     string `xml:"device"`
+-	Status     string `xml:"status"`
+-}
+-
+-// Response to a DescribeVolumes request
+-type VolumesResp struct {
+-	RequestId string   `xml:"requestId"`
+-	Volumes   []Volume `xml:"volumeSet>item"`
+-}
+-
+-// Attach a volume.
+-func (ec2 *EC2) AttachVolume(volumeId string, instanceId string, device string) (resp *AttachVolumeResp, err error) {
+-	params := makeParams("AttachVolume")
+-	params["VolumeId"] = volumeId
+-	params["InstanceId"] = instanceId
+-	params["Device"] = device
+-
+-	resp = &AttachVolumeResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	return
+-}
+-
+-// Create a new volume.
+-func (ec2 *EC2) CreateVolume(options *CreateVolume) (resp *CreateVolumeResp, err error) {
+-	params := makeParams("CreateVolume")
+-	params["AvailabilityZone"] = options.AvailZone
+-	if options.Size > 0 {
+-		params["Size"] = strconv.FormatInt(options.Size, 10)
+-	}
+-
+-	if options.SnapshotId != "" {
+-		params["SnapshotId"] = options.SnapshotId
+-	}
+-
+-	if options.VolumeType != "" {
+-		params["VolumeType"] = options.VolumeType
+-	}
+-
+-	if options.IOPS > 0 {
+-		params["Iops"] = strconv.FormatInt(options.IOPS, 10)
+-	}
+-
+-	if options.Encrypted {
+-		params["Encrypted"] = "true"
+-	}
+-
+-	resp = &CreateVolumeResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	return
+-}
+-
+-// Delete an EBS volume.
+-func (ec2 *EC2) DeleteVolume(id string) (resp *SimpleResp, err error) {
+-	params := makeParams("DeleteVolume")
+-	params["VolumeId"] = id
+-
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return
+-}
+-
+-// Detaches an EBS volume.
+-func (ec2 *EC2) DetachVolume(id string) (resp *SimpleResp, err error) {
+-	params := makeParams("DetachVolume")
+-	params["VolumeId"] = id
+-
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return
+-}
+-
+-// Finds or lists all volumes.
+-func (ec2 *EC2) Volumes(volIds []string, filter *Filter) (resp *VolumesResp, err error) {
+-	params := makeParams("DescribeVolumes")
+-	addParamsList(params, "VolumeId", volIds)
+-	filter.addParams(params)
+-	resp = &VolumesResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return
+-}
+-
+-// ----------------------------------------------------------------------------
+-// ElasticIp management (for VPC)
+-
+-// The AllocateAddress request parameters
+-//
+-// see http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-AllocateAddress.html
+-type AllocateAddress struct {
+-	Domain string
+-}
+-
+-// Response to an AllocateAddress request
+-type AllocateAddressResp struct {
+-	RequestId    string `xml:"requestId"`
+-	PublicIp     string `xml:"publicIp"`
+-	Domain       string `xml:"domain"`
+-	AllocationId string `xml:"allocationId"`
+-}
+-
+-// The AssociateAddress request parameters
+-//
+-// http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-AssociateAddress.html
+-type AssociateAddress struct {
+-	InstanceId         string
+-	PublicIp           string
+-	AllocationId       string
+-	AllowReassociation bool
+-}
+-
+-// Response to an AssociateAddress request
+-type AssociateAddressResp struct {
+-	RequestId     string `xml:"requestId"`
+-	Return        bool   `xml:"return"`
+-	AssociationId string `xml:"associationId"`
+-}
+-
+-// Address represents an Elastic IP Address
+-// See http://goo.gl/uxCjp7 for more details
+-type Address struct {
+-	PublicIp                string `xml:"publicIp"`
+-	AllocationId            string `xml:"allocationId"`
+-	Domain                  string `xml:"domain"`
+-	InstanceId              string `xml:"instanceId"`
+-	AssociationId           string `xml:"associationId"`
+-	NetworkInterfaceId      string `xml:"networkInterfaceId"`
+-	NetworkInterfaceOwnerId string `xml:"networkInterfaceOwnerId"`
+-	PrivateIpAddress        string `xml:"privateIpAddress"`
+-}
+-
+-type DescribeAddressesResp struct {
+-	RequestId string    `xml:"requestId"`
+-	Addresses []Address `xml:"addressesSet>item"`
+-}
+-
+-// Allocate a new Elastic IP.
+-func (ec2 *EC2) AllocateAddress(options *AllocateAddress) (resp *AllocateAddressResp, err error) {
+-	params := makeParams("AllocateAddress")
+-	params["Domain"] = options.Domain
+-
+-	resp = &AllocateAddressResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	return
+-}
+-
+-// Release an Elastic IP (VPC).
+-func (ec2 *EC2) ReleaseAddress(id string) (resp *SimpleResp, err error) {
+-	params := makeParams("ReleaseAddress")
+-	params["AllocationId"] = id
+-
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	return
+-}
+-
+-// Release an Elastic IP (Public)
+-func (ec2 *EC2) ReleasePublicAddress(publicIp string) (resp *SimpleResp, err error) {
+-	params := makeParams("ReleaseAddress")
+-	params["PublicIp"] = publicIp
+-
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	return
+-}
+-
+-// Associate an address with a VPC instance.
+-func (ec2 *EC2) AssociateAddress(options *AssociateAddress) (resp *AssociateAddressResp, err error) {
+-	params := makeParams("AssociateAddress")
+-	params["InstanceId"] = options.InstanceId
+-	if options.PublicIp != "" {
+-		params["PublicIp"] = options.PublicIp
+-	}
+-	if options.AllocationId != "" {
+-		params["AllocationId"] = options.AllocationId
+-	}
+-	if options.AllowReassociation {
+-		params["AllowReassociation"] = "true"
+-	}
+-
+-	resp = &AssociateAddressResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	return
+-}
+-
+-// Disassociate an address from a VPC instance.
+-func (ec2 *EC2) DisassociateAddress(id string) (resp *SimpleResp, err error) {
+-	params := makeParams("DisassociateAddress")
+-	params["AssociationId"] = id
+-
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	return
+-}
+-
+-// DescribeAddresses returns details about one or more
+-// Elastic IP Addresses. Returned addresses can be
+-// filtered by Public IP, Allocation ID or multiple filters
+-//
+-// See http://goo.gl/zW7J4p for more details.
+-func (ec2 *EC2) Addresses(publicIps []string, allocationIds []string, filter *Filter) (resp *DescribeAddressesResp, err error) {
+-	params := makeParams("DescribeAddresses")
+-	addParamsList(params, "PublicIp", publicIps)
+-	addParamsList(params, "AllocationId", allocationIds)
+-	filter.addParams(params)
+-	resp = &DescribeAddressesResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return
+-}
+-
+-// ----------------------------------------------------------------------------
+-// Image and snapshot management functions and types.
+-
+-// The CreateImage request parameters.
+-//
+-// See http://goo.gl/cxU41 for more details.
+-type CreateImage struct {
+-	InstanceId   string
+-	Name         string
+-	Description  string
+-	NoReboot     bool
+-	BlockDevices []BlockDeviceMapping
+-}
+-
+-// Response to a CreateImage request.
+-//
+-// See http://goo.gl/cxU41 for more details.
+-type CreateImageResp struct {
+-	RequestId string `xml:"requestId"`
+-	ImageId   string `xml:"imageId"`
+-}
+-
+-// Response to a DescribeImages request.
+-//
+-// See http://goo.gl/hLnyg for more details.
+-type ImagesResp struct {
+-	RequestId string  `xml:"requestId"`
+-	Images    []Image `xml:"imagesSet>item"`
+-}
+-
+-// Response to a DescribeImageAttribute request.
+-//
+-// See http://goo.gl/bHO3zT for more details.
+-type ImageAttributeResp struct {
+-	RequestId    string               `xml:"requestId"`
+-	ImageId      string               `xml:"imageId"`
+-	Kernel       string               `xml:"kernel>value"`
+-	RamDisk      string               `xml:"ramdisk>value"`
+-	Description  string               `xml:"description>value"`
+-	Group        string               `xml:"launchPermission>item>group"`
+-	UserIds      []string             `xml:"launchPermission>item>userId"`
+-	ProductCodes []string             `xml:"productCodes>item>productCode"`
+-	BlockDevices []BlockDeviceMapping `xml:"blockDeviceMapping>item"`
+-}
+-
+-// The RegisterImage request parameters.
+-type RegisterImage struct {
+-	ImageLocation   string
+-	Name            string
+-	Description     string
+-	Architecture    string
+-	KernelId        string
+-	RamdiskId       string
+-	RootDeviceName  string
+-	VirtType        string
+-	SriovNetSupport string
+-	BlockDevices    []BlockDeviceMapping
+-}
+-
+-// Response to a RegisterImage request.
+-type RegisterImageResp struct {
+-	RequestId string `xml:"requestId"`
+-	ImageId   string `xml:"imageId"`
+-}
+-
+-// Response to a DegisterImage request.
+-//
+-// See http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DeregisterImage.html
+-type DeregisterImageResp struct {
+-	RequestId string `xml:"requestId"`
+-	Return    bool   `xml:"return"`
+-}
+-
+-// BlockDeviceMapping represents the association of a block device with an image.
+-//
+-// See http://goo.gl/wnDBf for more details.
+-type BlockDeviceMapping struct {
+-	DeviceName          string `xml:"deviceName"`
+-	VirtualName         string `xml:"virtualName"`
+-	SnapshotId          string `xml:"ebs>snapshotId"`
+-	VolumeType          string `xml:"ebs>volumeType"`
+-	VolumeSize          int64  `xml:"ebs>volumeSize"`
+-	DeleteOnTermination bool   `xml:"ebs>deleteOnTermination"`
+-	Encrypted           bool   `xml:"ebs>encrypted"`
+-	NoDevice            bool   `xml:"noDevice"`
+-
+-	// The number of I/O operations per second (IOPS) that the volume supports.
+-	IOPS int64 `xml:"ebs>iops"`
+-}
+-
+-// Image represents details about an image.
+-//
+-// See http://goo.gl/iSqJG for more details.
+-type Image struct {
+-	Id                 string               `xml:"imageId"`
+-	Name               string               `xml:"name"`
+-	Description        string               `xml:"description"`
+-	Type               string               `xml:"imageType"`
+-	State              string               `xml:"imageState"`
+-	Location           string               `xml:"imageLocation"`
+-	Public             bool                 `xml:"isPublic"`
+-	Architecture       string               `xml:"architecture"`
+-	Platform           string               `xml:"platform"`
+-	ProductCodes       []string             `xml:"productCode>item>productCode"`
+-	KernelId           string               `xml:"kernelId"`
+-	RamdiskId          string               `xml:"ramdiskId"`
+-	StateReason        string               `xml:"stateReason"`
+-	OwnerId            string               `xml:"imageOwnerId"`
+-	OwnerAlias         string               `xml:"imageOwnerAlias"`
+-	RootDeviceType     string               `xml:"rootDeviceType"`
+-	RootDeviceName     string               `xml:"rootDeviceName"`
+-	VirtualizationType string               `xml:"virtualizationType"`
+-	Hypervisor         string               `xml:"hypervisor"`
+-	BlockDevices       []BlockDeviceMapping `xml:"blockDeviceMapping>item"`
+-	Tags               []Tag                `xml:"tagSet>item"`
+-}
+-
+-// The ModifyImageAttribute request parameters.
+-type ModifyImageAttribute struct {
+-	AddUsers     []string
+-	RemoveUsers  []string
+-	AddGroups    []string
+-	RemoveGroups []string
+-	ProductCodes []string
+-	Description  string
+-}
+-
+-// The CopyImage request parameters.
+-//
+-// See http://goo.gl/hQwPCK for more details.
+-type CopyImage struct {
+-	SourceRegion  string
+-	SourceImageId string
+-	Name          string
+-	Description   string
+-	ClientToken   string
+-}
+-
+-// Response to a CopyImage request.
+-//
+-// See http://goo.gl/hQwPCK for more details.
+-type CopyImageResp struct {
+-	RequestId string `xml:"requestId"`
+-	ImageId   string `xml:"imageId"`
+-}
+-
+-// Creates an Amazon EBS-backed AMI from an Amazon EBS-backed instance
+-// that is either running or stopped.
+-//
+-// See http://goo.gl/cxU41 for more details.
+-func (ec2 *EC2) CreateImage(options *CreateImage) (resp *CreateImageResp, err error) {
+-	params := makeParams("CreateImage")
+-	params["InstanceId"] = options.InstanceId
+-	params["Name"] = options.Name
+-	if options.Description != "" {
+-		params["Description"] = options.Description
+-	}
+-	if options.NoReboot {
+-		params["NoReboot"] = "true"
+-	}
+-	addBlockDeviceParams("", params, options.BlockDevices)
+-
+-	resp = &CreateImageResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
 -
--Important API changes:
+-	return
+-}
 -
-- - (api remove) package variable DoNotRecover no longer works ; use restful.DefaultContainer.DoNotRecover(true) instead.
-- - (api remove) package variable EnableContentEncoding no longer works ; use restful.DefaultContainer.EnableContentEncoding(true) instead.
-- 
-- 
--2013-07-06
+-// Images returns details about available images.
+-// The ids and filter parameters, if provided, will limit the images returned.
+-// For example, to get all the private images associated with this account set
+-// the boolean filter "is-public" to 0.
+-// For list of filters: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeImages.html
+-//
+-// Note: calling this function with nil ids and filter parameters will result in
+-// a very large number of images being returned.
+-//
+-// See http://goo.gl/SRBhW for more details.
+-func (ec2 *EC2) Images(ids []string, filter *Filter) (resp *ImagesResp, err error) {
+-	params := makeParams("DescribeImages")
+-	for i, id := range ids {
+-		params["ImageId."+strconv.Itoa(i+1)] = id
+-	}
+-	filter.addParams(params)
 -
-- - (api add) Added support for response encoding (gzip and deflate(zlib)). This feature is disabled on default (for backwards compatibility). Use restful.EnableContentEncoding = true in your initialization to enable this feature.
+-	resp = &ImagesResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return
+-}
 -
--2013-06-19
+-// ImagesByOwners returns details about available images.
+-// The ids, owners, and filter parameters, if provided, will limit the images returned.
+-// For example, to get all the private images associated with this account set
+-// the boolean filter "is-public" to 0.
+-// For list of filters: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeImages.html
+-//
+-// Note: calling this function with nil ids and filter parameters will result in
+-// a very large number of images being returned.
+-//
+-// See http://goo.gl/SRBhW for more details.
+-func (ec2 *EC2) ImagesByOwners(ids []string, owners []string, filter *Filter) (resp *ImagesResp, err error) {
+-	params := makeParams("DescribeImages")
+-	for i, id := range ids {
+-		params["ImageId."+strconv.Itoa(i+1)] = id
+-	}
+-	for i, owner := range owners {
+-		params[fmt.Sprintf("Owner.%d", i+1)] = owner
+-	}
 -
-- - (improve) DoNotRecover option, moved request body closer, improved ReadEntity
+-	filter.addParams(params)
 -
--2013-06-03
+-	resp = &ImagesResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return
+-}
 -
-- - (api change) removed Dispatcher interface, hide PathExpression
-- - changed receiver names of type functions to be more idiomatic Go
+-// ImageAttribute describes an attribute of an AMI.
+-// You can specify only one attribute at a time.
+-// Valid attributes are:
+-//    description | kernel | ramdisk | launchPermission | productCodes | blockDeviceMapping
+-//
+-// See http://goo.gl/bHO3zT for more details.
+-func (ec2 *EC2) ImageAttribute(imageId, attribute string) (resp *ImageAttributeResp, err error) {
+-	params := makeParams("DescribeImageAttribute")
+-	params["ImageId"] = imageId
+-	params["Attribute"] = attribute
 -
--2013-06-02
+-	resp = &ImageAttributeResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return
+-}
 -
-- - (optimize) Cache the RegExp compilation of Paths.
+-// ModifyImageAttribute sets attributes for an image.
+-//
+-// See http://goo.gl/YUjO4G for more details.
+-func (ec2 *EC2) ModifyImageAttribute(imageId string, options *ModifyImageAttribute) (resp *SimpleResp, err error) {
+-	params := makeParams("ModifyImageAttribute")
+-	params["ImageId"] = imageId
+-	if options.Description != "" {
+-		params["Description.Value"] = options.Description
+-	}
 -
--2013-05-22
--	
-- - (api add) Added support for request/response filter functions
+-	if options.AddUsers != nil {
+-		for i, user := range options.AddUsers {
+-			p := fmt.Sprintf("LaunchPermission.Add.%d.UserId", i+1)
+-			params[p] = user
+-		}
+-	}
 -
--2013-05-18
+-	if options.RemoveUsers != nil {
+-		for i, user := range options.RemoveUsers {
+-			p := fmt.Sprintf("LaunchPermission.Remove.%d.UserId", i+1)
+-			params[p] = user
+-		}
+-	}
 -
+-	if options.AddGroups != nil {
+-		for i, group := range options.AddGroups {
+-			p := fmt.Sprintf("LaunchPermission.Add.%d.Group", i+1)
+-			params[p] = group
+-		}
+-	}
 -
-- - (api add) Added feature to change the default Http Request Dispatch function (travis cline)
-- - (api change) Moved Swagger Webservice to swagger package (see example restful-user)
+-	if options.RemoveGroups != nil {
+-		for i, group := range options.RemoveGroups {
+-			p := fmt.Sprintf("LaunchPermission.Remove.%d.Group", i+1)
+-			params[p] = group
+-		}
+-	}
 -
--[2012-11-14 .. 2013-05-18>
-- 
-- - See https://github.com/emicklei/go-restful/commits
+-	if options.ProductCodes != nil {
+-		addParamsList(params, "ProductCode", options.ProductCodes)
+-	}
 -
--2012-11-14
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		resp = nil
+-	}
 -
-- - Initial commit
+-	return
+-}
 -
+-// Registers a new AMI with EC2.
+-//
+-// See: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-RegisterImage.html
+-func (ec2 *EC2) RegisterImage(options *RegisterImage) (resp *RegisterImageResp, err error) {
+-	params := makeParams("RegisterImage")
+-	params["Name"] = options.Name
+-	if options.ImageLocation != "" {
+-		params["ImageLocation"] = options.ImageLocation
+-	}
 -
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/LICENSE b/Godeps/_workspace/src/github.com/emicklei/go-restful/LICENSE
-deleted file mode 100644
-index ece7ec6..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/LICENSE
-+++ /dev/null
-@@ -1,22 +0,0 @@
--Copyright (c) 2012,2013 Ernest Micklei
+-	if options.Description != "" {
+-		params["Description"] = options.Description
+-	}
 -
--MIT License
+-	if options.Architecture != "" {
+-		params["Architecture"] = options.Architecture
+-	}
 -
--Permission is hereby granted, free of charge, to any person obtaining
--a copy of this software and associated documentation files (the
--"Software"), to deal in the Software without restriction, including
--without limitation the rights to use, copy, modify, merge, publish,
--distribute, sublicense, and/or sell copies of the Software, and to
--permit persons to whom the Software is furnished to do so, subject to
--the following conditions:
+-	if options.KernelId != "" {
+-		params["KernelId"] = options.KernelId
+-	}
 -
--The above copyright notice and this permission notice shall be
--included in all copies or substantial portions of the Software.
+-	if options.RamdiskId != "" {
+-		params["RamdiskId"] = options.RamdiskId
+-	}
 -
--THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
--EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
--MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
--NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
--LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
--OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
--WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-\ No newline at end of file
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/README.md b/Godeps/_workspace/src/github.com/emicklei/go-restful/README.md
-deleted file mode 100644
-index 8af137d..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/README.md
-+++ /dev/null
-@@ -1,70 +0,0 @@
--go-restful
--==========
+-	if options.RootDeviceName != "" {
+-		params["RootDeviceName"] = options.RootDeviceName
+-	}
 -
--package for building REST-style Web Services using Google Go
+-	if options.VirtType != "" {
+-		params["VirtualizationType"] = options.VirtType
+-	}
 -
--REST asks developers to use HTTP methods explicitly and in a way that's consistent with the protocol definition. This basic REST design principle establishes a one-to-one mapping between create, read, update, and delete (CRUD) operations and HTTP methods. According to this mapping:
+-	if options.SriovNetSupport != "" {
+-		params["SriovNetSupport"] = "simple"
+-	}
 -
--- GET = Retrieve a representation of a resource
--- POST = Create if you are sending content to the server to create a subordinate of the specified resource collection, using some server-side algorithm.
--- PUT = Create if you are sending the full content of the specified resource (URI).
--- PUT = Update if you are updating the full content of the specified resource.
--- DELETE = Delete if you are requesting the server to delete the resource
--- PATCH = Update partial content of a resource
--- OPTIONS = Get information about the communication options for the request URI
--    
--### Example
+-	addBlockDeviceParams("", params, options.BlockDevices)
 -
--```Go
--ws := new(restful.WebService)
--ws.
--	Path("/users").
--	Consumes(restful.MIME_XML, restful.MIME_JSON).
--	Produces(restful.MIME_JSON, restful.MIME_XML)
+-	resp = &RegisterImageResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
 -
--ws.Route(ws.GET("/{user-id}").To(u.findUser).
--	Doc("get a user").
--	Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")).
--	Writes(User{}))		
--...
--	
--func (u UserResource) findUser(request *restful.Request, response *restful.Response) {
--	id := request.PathParameter("user-id")
--	...
+-	return
 -}
--```
--	
--[Full API of a UserResource](https://github.com/emicklei/go-restful/tree/master/examples/restful-user-resource.go) 
--		
--### Features
 -
--- Routes for request &#8594; function mapping with path parameter (e.g. {id}) support
--- Configurable router:
--	- Routing algorithm after [JSR311](http://jsr311.java.net/nonav/releases/1.1/spec/spec.html) that is implemented using (but doest **not** accept) regular expressions (See RouterJSR311 which is used by default)
--	- Fast routing algorithm that allows static elements, regular expressions and dynamic parameters in the URL path (e.g. /meetings/{id} or /static/{subpath:*}, See CurlyRouter)
--- Request API for reading structs from JSON/XML and accesing parameters (path,query,header)
--- Response API for writing structs to JSON/XML and setting headers
--- Filters for intercepting the request &#8594; response flow on Service or Route level
--- Request-scoped variables using attributes
--- Containers for WebServices on different HTTP endpoints
--- Content encoding (gzip,deflate) of responses
--- Automatic responses on OPTIONS (using a filter)
--- Automatic CORS request handling (using a filter)
--- API declaration for Swagger UI (see swagger package)
--- Panic recovery to produce HTTP 500, customizable using RecoverHandler(...)
--	
--### Resources
+-// Degisters an image. Note that this does not delete the backing stores of the AMI.
+-//
+-// See http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DeregisterImage.html
+-func (ec2 *EC2) DeregisterImage(imageId string) (resp *DeregisterImageResp, err error) {
+-	params := makeParams("DeregisterImage")
+-	params["ImageId"] = imageId
 -
--- [Documentation on godoc.org](http://godoc.org/github.com/emicklei/go-restful)
--- [Code examples](https://github.com/emicklei/go-restful/tree/master/examples)
--- [Example posted on blog](http://ernestmicklei.com/2012/11/24/go-restful-first-working-example/)
--- [Design explained on blog](http://ernestmicklei.com/2012/11/11/go-restful-api-design/)
--- [sourcegraph](https://sourcegraph.com/github.com/emicklei/go-restful)
--- [gopkg.in](https://gopkg.in/emicklei/go-restful.v1)
--- [showcase: Mora - MongoDB REST Api server](https://github.com/emicklei/mora)
+-	resp = &DeregisterImageResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
 -
--[![Build Status](https://drone.io/github.com/emicklei/go-restful/status.png)](https://drone.io/github.com/emicklei/go-restful/latest)[![library users](https://sourcegraph.com/api/repos/github.com/emicklei/go-restful/badges/library-users.png)](https://sourcegraph.com/github.com/emicklei/go-restful) [![authors](https://sourcegraph.com/api/repos/github.com/emicklei/go-restful/badges/authors.png)](https://sourcegraph.com/github.com/emicklei/go-restful) [![xrefs](https://sourcegraph.com/api/repos/github.com/emicklei/go-restful/badges/xrefs.png)](https://sourcegraph.com/github.com/emicklei/go-restful)
+-	return
+-}
 -
--(c) 2012 - 2014, http://ernestmicklei.com. MIT License
+-// Copy and Image from one region to another.
+-//
+-// See http://goo.gl/hQwPCK for more details.
+-func (ec2 *EC2) CopyImage(options *CopyImage) (resp *CopyImageResp, err error) {
+-	params := makeParams("CopyImage")
 -
--Type ```git shortlog -s``` for a full list of contributors.
-\ No newline at end of file
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/Srcfile b/Godeps/_workspace/src/github.com/emicklei/go-restful/Srcfile
-deleted file mode 100644
-index 16fd186..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/Srcfile
-+++ /dev/null
-@@ -1 +0,0 @@
--{"SkipDirs": ["examples"]}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/bench_curly_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/bench_curly_test.go
-deleted file mode 100644
-index db6a1a7..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/bench_curly_test.go
-+++ /dev/null
-@@ -1,51 +0,0 @@
--package restful
+-	if options.SourceRegion != "" {
+-		params["SourceRegion"] = options.SourceRegion
+-	}
 -
--import (
--	"fmt"
--	"net/http"
--	"net/http/httptest"
--	"testing"
--)
+-	if options.SourceImageId != "" {
+-		params["SourceImageId"] = options.SourceImageId
+-	}
 -
--func setupCurly(container *Container) []string {
--	wsCount := 26
--	rtCount := 26
--	urisCurly := []string{}
+-	if options.Name != "" {
+-		params["Name"] = options.Name
+-	}
 -
--	container.Router(CurlyRouter{})
--	for i := 0; i < wsCount; i++ {
--		root := fmt.Sprintf("/%s/{%s}/", string(i+97), string(i+97))
--		ws := new(WebService).Path(root)
--		for j := 0; j < rtCount; j++ {
--			sub := fmt.Sprintf("/%s2/{%s2}", string(j+97), string(j+97))
--			ws.Route(ws.GET(sub).Consumes("application/xml").Produces("application/xml").To(echoCurly))
--		}
--		container.Add(ws)
--		for _, each := range ws.Routes() {
--			urisCurly = append(urisCurly, "http://bench.com"+each.Path)
--		}
+-	if options.Description != "" {
+-		params["Description"] = options.Description
 -	}
--	return urisCurly
--}
 -
--func echoCurly(req *Request, resp *Response) {}
+-	if options.ClientToken != "" {
+-		params["ClientToken"] = options.ClientToken
+-	}
 -
--func BenchmarkManyCurly(b *testing.B) {
--	container := NewContainer()
--	urisCurly := setupCurly(container)
--	b.ResetTimer()
--	for t := 0; t < b.N; t++ {
--		for r := 0; r < 1000; r++ {
--			for _, each := range urisCurly {
--				sendNoReturnTo(each, container, t)
--			}
--		}
+-	resp = &CopyImageResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
--}
 -
--func sendNoReturnTo(address string, container *Container, t int) {
--	httpRequest, _ := http.NewRequest("GET", address, nil)
--	httpRequest.Header.Set("Accept", "application/xml")
--	httpWriter := httptest.NewRecorder()
--	container.dispatch(httpWriter, httpRequest)
+-	return
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/bench_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/bench_test.go
-deleted file mode 100644
-index 3e77c2d..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/bench_test.go
-+++ /dev/null
-@@ -1,43 +0,0 @@
--package restful
--
--import (
--	"fmt"
--	"io"
--	"testing"
--)
 -
--var uris = []string{}
+-// Response to a CreateSnapshot request.
+-//
+-// See http://goo.gl/ttcda for more details.
+-type CreateSnapshotResp struct {
+-	RequestId string `xml:"requestId"`
+-	Snapshot
+-}
 -
--func setup(container *Container) {
--	wsCount := 26
--	rtCount := 26
+-// CreateSnapshot creates a volume snapshot and stores it in S3.
+-//
+-// See http://goo.gl/ttcda for more details.
+-func (ec2 *EC2) CreateSnapshot(volumeId, description string) (resp *CreateSnapshotResp, err error) {
+-	params := makeParams("CreateSnapshot")
+-	params["VolumeId"] = volumeId
+-	params["Description"] = description
 -
--	for i := 0; i < wsCount; i++ {
--		root := fmt.Sprintf("/%s/{%s}/", string(i+97), string(i+97))
--		ws := new(WebService).Path(root)
--		for j := 0; j < rtCount; j++ {
--			sub := fmt.Sprintf("/%s2/{%s2}", string(j+97), string(j+97))
--			ws.Route(ws.GET(sub).To(echo))
--		}
--		container.Add(ws)
--		for _, each := range ws.Routes() {
--			uris = append(uris, "http://bench.com"+each.Path)
--		}
+-	resp = &CreateSnapshotResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
+-	return
 -}
 -
--func echo(req *Request, resp *Response) {
--	io.WriteString(resp.ResponseWriter, "echo")
--}
+-// DeleteSnapshots deletes the volume snapshots with the given ids.
+-//
+-// Note: If you make periodic snapshots of a volume, the snapshots are
+-// incremental so that only the blocks on the device that have changed
+-// since your last snapshot are incrementally saved in the new snapshot.
+-// Even though snapshots are saved incrementally, the snapshot deletion
+-// process is designed so that you need to retain only the most recent
+-// snapshot in order to restore the volume.
+-//
+-// See http://goo.gl/vwU1y for more details.
+-func (ec2 *EC2) DeleteSnapshots(ids []string) (resp *SimpleResp, err error) {
+-	params := makeParams("DeleteSnapshot")
+-	for i, id := range ids {
+-		params["SnapshotId."+strconv.Itoa(i+1)] = id
+-	}
 -
--func BenchmarkMany(b *testing.B) {
--	container := NewContainer()
--	setup(container)
--	b.ResetTimer()
--	for t := 0; t < b.N; t++ {
--		for _, each := range uris {
--			// println(each)
--			sendItTo(each, container)
--		}
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
+-	return
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/bench_test.sh b/Godeps/_workspace/src/github.com/emicklei/go-restful/bench_test.sh
-deleted file mode 100644
-index 47ffbe4..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/bench_test.sh
-+++ /dev/null
-@@ -1,10 +0,0 @@
--#go test -run=none -file bench_test.go -test.bench . -cpuprofile=bench_test.out
--
--go test -c
--./go-restful.test -test.run=none -test.cpuprofile=tmp.prof -test.bench=BenchmarkMany
--./go-restful.test -test.run=none -test.cpuprofile=curly.prof -test.bench=BenchmarkManyCurly
--
--#go tool pprof go-restful.test tmp.prof
--go tool pprof go-restful.test curly.prof
--
--
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/compress.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/compress.go
-deleted file mode 100644
-index c4dcca0..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/compress.go
-+++ /dev/null
-@@ -1,89 +0,0 @@
--package restful
 -
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
+-// Response to a DescribeSnapshots request.
+-//
+-// See http://goo.gl/nClDT for more details.
+-type SnapshotsResp struct {
+-	RequestId string     `xml:"requestId"`
+-	Snapshots []Snapshot `xml:"snapshotSet>item"`
+-}
 -
--import (
--	"compress/gzip"
--	"compress/zlib"
--	"errors"
--	"io"
--	"net/http"
--	"strings"
--)
+-// Snapshot represents details about a volume snapshot.
+-//
+-// See http://goo.gl/nkovs for more details.
+-type Snapshot struct {
+-	Id          string `xml:"snapshotId"`
+-	VolumeId    string `xml:"volumeId"`
+-	VolumeSize  string `xml:"volumeSize"`
+-	Status      string `xml:"status"`
+-	StartTime   string `xml:"startTime"`
+-	Description string `xml:"description"`
+-	Progress    string `xml:"progress"`
+-	OwnerId     string `xml:"ownerId"`
+-	OwnerAlias  string `xml:"ownerAlias"`
+-	Encrypted   bool   `xml:"encrypted"`
+-	Tags        []Tag  `xml:"tagSet>item"`
+-}
 -
--// OBSOLETE : use restful.DefaultContainer.EnableContentEncoding(true) to change this setting.
--var EnableContentEncoding = false
+-// Snapshots returns details about volume snapshots available to the user.
+-// The ids and filter parameters, if provided, limit the snapshots returned.
+-//
+-// See http://goo.gl/ogJL4 for more details.
+-func (ec2 *EC2) Snapshots(ids []string, filter *Filter) (resp *SnapshotsResp, err error) {
+-	params := makeParams("DescribeSnapshots")
+-	for i, id := range ids {
+-		params["SnapshotId."+strconv.Itoa(i+1)] = id
+-	}
+-	filter.addParams(params)
 -
--// CompressingResponseWriter is a http.ResponseWriter that can perform content encoding (gzip and zlib)
--type CompressingResponseWriter struct {
--	writer     http.ResponseWriter
--	compressor io.WriteCloser
+-	resp = &SnapshotsResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return
 -}
 -
--// Header is part of http.ResponseWriter interface
--func (c *CompressingResponseWriter) Header() http.Header {
--	return c.writer.Header()
--}
+-// ----------------------------------------------------------------------------
+-// KeyPair management functions and types.
 -
--// WriteHeader is part of http.ResponseWriter interface
--func (c *CompressingResponseWriter) WriteHeader(status int) {
--	c.writer.WriteHeader(status)
+-type KeyPair struct {
+-	Name        string `xml:"keyName"`
+-	Fingerprint string `xml:"keyFingerprint"`
 -}
 -
--// Write is part of http.ResponseWriter interface
--// It is passed through the compressor
--func (c *CompressingResponseWriter) Write(bytes []byte) (int, error) {
--	return c.compressor.Write(bytes)
+-type KeyPairsResp struct {
+-	RequestId string    `xml:"requestId"`
+-	Keys      []KeyPair `xml:"keySet>item"`
 -}
 -
--// CloseNotify is part of http.CloseNotifier interface
--func (c *CompressingResponseWriter) CloseNotify() <-chan bool {
--	return c.writer.(http.CloseNotifier).CloseNotify()
+-type CreateKeyPairResp struct {
+-	RequestId      string `xml:"requestId"`
+-	KeyName        string `xml:"keyName"`
+-	KeyFingerprint string `xml:"keyFingerprint"`
+-	KeyMaterial    string `xml:"keyMaterial"`
 -}
 -
--// Close the underlying compressor
--func (c *CompressingResponseWriter) Close() {
--	c.compressor.Close()
+-type ImportKeyPairResponse struct {
+-	RequestId      string `xml:"requestId"`
+-	KeyName        string `xml:"keyName"`
+-	KeyFingerprint string `xml:"keyFingerprint"`
 -}
 -
--// WantsCompressedResponse reads the Accept-Encoding header to see if and which encoding is requested.
--func wantsCompressedResponse(httpRequest *http.Request) (bool, string) {
--	header := httpRequest.Header.Get(HEADER_AcceptEncoding)
--	gi := strings.Index(header, ENCODING_GZIP)
--	zi := strings.Index(header, ENCODING_DEFLATE)
--	// use in order of appearance
--	if gi == -1 {
--		return zi != -1, ENCODING_DEFLATE
--	} else if zi == -1 {
--		return gi != -1, ENCODING_GZIP
--	} else {
--		if gi < zi {
--			return true, ENCODING_GZIP
--		}
--		return true, ENCODING_DEFLATE
--	}
--}
+-// CreateKeyPair creates a new key pair and returns the private key contents.
+-//
+-// See http://goo.gl/0S6hV
+-func (ec2 *EC2) CreateKeyPair(keyName string) (resp *CreateKeyPairResp, err error) {
+-	params := makeParams("CreateKeyPair")
+-	params["KeyName"] = keyName
 -
--// NewCompressingResponseWriter create a CompressingResponseWriter for a known encoding = {gzip,deflate}
--func NewCompressingResponseWriter(httpWriter http.ResponseWriter, encoding string) (*CompressingResponseWriter, error) {
--	httpWriter.Header().Set(HEADER_ContentEncoding, encoding)
--	c := new(CompressingResponseWriter)
--	c.writer = httpWriter
--	var err error
--	if ENCODING_GZIP == encoding {
--		c.compressor, err = gzip.NewWriterLevel(httpWriter, gzip.BestSpeed)
--		if err != nil {
--			return nil, err
--		}
--	} else if ENCODING_DEFLATE == encoding {
--		c.compressor, err = zlib.NewWriterLevel(httpWriter, zlib.BestSpeed)
--		if err != nil {
--			return nil, err
--		}
--	} else {
--		return nil, errors.New("Unknown encoding:" + encoding)
+-	resp = &CreateKeyPairResp{}
+-	err = ec2.query(params, resp)
+-	if err == nil {
+-		resp.KeyFingerprint = strings.TrimSpace(resp.KeyFingerprint)
 -	}
--	return c, err
+-	return
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/compress_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/compress_test.go
-deleted file mode 100644
-index 332fb22..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/compress_test.go
-+++ /dev/null
-@@ -1,53 +0,0 @@
--package restful
 -
--import (
--	"net/http"
--	"net/http/httptest"
--	"testing"
--)
+-// DeleteKeyPair deletes a key pair.
+-//
+-// See http://goo.gl/0bqok
+-func (ec2 *EC2) DeleteKeyPair(name string) (resp *SimpleResp, err error) {
+-	params := makeParams("DeleteKeyPair")
+-	params["KeyName"] = name
 -
--func TestGzip(t *testing.T) {
--	EnableContentEncoding = true
--	httpRequest, _ := http.NewRequest("GET", "/test", nil)
--	httpRequest.Header.Set("Accept-Encoding", "gzip,deflate")
--	httpWriter := httptest.NewRecorder()
--	wanted, encoding := wantsCompressedResponse(httpRequest)
--	if !wanted {
--		t.Fatal("should accept gzip")
--	}
--	if encoding != "gzip" {
--		t.Fatal("expected gzip")
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	return
+-}
+-
+-// KeyPairs returns list of key pairs for this account
+-//
+-// See http://goo.gl/Apzsfz
+-func (ec2 *EC2) KeyPairs(keynames []string, filter *Filter) (resp *KeyPairsResp, err error) {
+-	params := makeParams("DescribeKeyPairs")
+-	for i, name := range keynames {
+-		params["KeyName."+strconv.Itoa(i)] = name
 -	}
--	c, err := NewCompressingResponseWriter(httpWriter, encoding)
+-	filter.addParams(params)
+-
+-	resp = &KeyPairsResp{}
+-	err = ec2.query(params, resp)
 -	if err != nil {
--		t.Fatal(err.Error())
--	}
--	c.Write([]byte("Hello World"))
--	c.Close()
--	if httpWriter.Header().Get("Content-Encoding") != "gzip" {
--		t.Fatal("Missing gzip header")
+-		return nil, err
 -	}
+-
+-	return resp, nil
 -}
 -
--func TestDeflate(t *testing.T) {
--	EnableContentEncoding = true
--	httpRequest, _ := http.NewRequest("GET", "/test", nil)
--	httpRequest.Header.Set("Accept-Encoding", "deflate,gzip")
--	httpWriter := httptest.NewRecorder()
--	wanted, encoding := wantsCompressedResponse(httpRequest)
--	if !wanted {
--		t.Fatal("should accept deflate")
--	}
--	if encoding != "deflate" {
--		t.Fatal("expected deflate")
--	}
--	c, err := NewCompressingResponseWriter(httpWriter, encoding)
+-// ImportKeyPair imports a key into AWS
+-//
+-// See http://goo.gl/NbZUvw
+-func (ec2 *EC2) ImportKeyPair(keyname string, key string) (resp *ImportKeyPairResponse, err error) {
+-	params := makeParams("ImportKeyPair")
+-	params["KeyName"] = keyname
+-
+-	// Oddly, AWS requires the key material to be base64-encoded, even if it was
+-	// already encoded. So, we force another round of encoding...
+-	// c.f. https://groups.google.com/forum/?fromgroups#!topic/boto-dev/IczrStO9Q8M
+-	params["PublicKeyMaterial"] = base64.StdEncoding.EncodeToString([]byte(key))
+-
+-	resp = &ImportKeyPairResponse{}
+-	err = ec2.query(params, resp)
 -	if err != nil {
--		t.Fatal(err.Error())
--	}
--	c.Write([]byte("Hello World"))
--	c.Close()
--	if httpWriter.Header().Get("Content-Encoding") != "deflate" {
--		t.Fatal("Missing deflate header")
+-		return nil, err
 -	}
+-	return resp, nil
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/constants.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/constants.go
-deleted file mode 100644
-index 5e564d0..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/constants.go
-+++ /dev/null
-@@ -1,29 +0,0 @@
--package restful
 -
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
--
--const (
--	MIME_XML  = "application/xml"  // Accept or Content-Type used in Consumes() and/or Produces()
--	MIME_JSON = "application/json" // Accept or Content-Type used in Consumes() and/or Produces()
+-// ----------------------------------------------------------------------------
+-// Security group management functions and types.
 -
--	HEADER_Allow                         = "Allow"
--	HEADER_Accept                        = "Accept"
--	HEADER_Origin                        = "Origin"
--	HEADER_ContentType                   = "Content-Type"
--	HEADER_LastModified                  = "Last-Modified"
--	HEADER_AcceptEncoding                = "Accept-Encoding"
--	HEADER_ContentEncoding               = "Content-Encoding"
--	HEADER_AccessControlExposeHeaders    = "Access-Control-Expose-Headers"
--	HEADER_AccessControlRequestMethod    = "Access-Control-Request-Method"
--	HEADER_AccessControlRequestHeaders   = "Access-Control-Request-Headers"
--	HEADER_AccessControlAllowMethods     = "Access-Control-Allow-Methods"
--	HEADER_AccessControlAllowOrigin      = "Access-Control-Allow-Origin"
--	HEADER_AccessControlAllowCredentials = "Access-Control-Allow-Credentials"
--	HEADER_AccessControlAllowHeaders     = "Access-Control-Allow-Headers"
--	HEADER_AccessControlMaxAge           = "Access-Control-Max-Age"
+-// SimpleResp represents a response to an EC2 request which on success will
+-// return no other information besides a request id.
+-type SimpleResp struct {
+-	XMLName   xml.Name
+-	RequestId string `xml:"requestId"`
+-}
 -
--	ENCODING_GZIP    = "gzip"
--	ENCODING_DEFLATE = "deflate"
--)
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/container.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/container.go
-deleted file mode 100644
-index 7aae565..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/container.go
-+++ /dev/null
-@@ -1,261 +0,0 @@
--package restful
+-// CreateSecurityGroupResp represents a response to a CreateSecurityGroup request.
+-type CreateSecurityGroupResp struct {
+-	SecurityGroup
+-	RequestId string `xml:"requestId"`
+-}
 -
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
+-// CreateSecurityGroup run a CreateSecurityGroup request in EC2, with the provided
+-// name and description.
+-//
+-// See http://goo.gl/Eo7Yl for more details.
+-func (ec2 *EC2) CreateSecurityGroup(group SecurityGroup) (resp *CreateSecurityGroupResp, err error) {
+-	params := makeParams("CreateSecurityGroup")
+-	params["GroupName"] = group.Name
+-	params["GroupDescription"] = group.Description
+-	if group.VpcId != "" {
+-		params["VpcId"] = group.VpcId
+-	}
 -
--import (
--	"bytes"
--	"fmt"
--	"log"
--	"net/http"
--	"runtime"
--	"strings"
--)
+-	resp = &CreateSecurityGroupResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	resp.Name = group.Name
+-	return resp, nil
+-}
 -
--// Container holds a collection of WebServices and a http.ServeMux to dispatch http requests.
--// The requests are further dispatched to routes of WebServices using a RouteSelector
--type Container struct {
--	webServices            []*WebService
--	ServeMux               *http.ServeMux
--	isRegisteredOnRoot     bool
--	containerFilters       []FilterFunction
--	doNotRecover           bool // default is false
--	recoverHandleFunc      RecoverHandleFunction
--	router                 RouteSelector // default is a RouterJSR311, CurlyRouter is the faster alternative
--	contentEncodingEnabled bool          // default is false
+-// SecurityGroupsResp represents a response to a DescribeSecurityGroups
+-// request in EC2.
+-//
+-// See http://goo.gl/k12Uy for more details.
+-type SecurityGroupsResp struct {
+-	RequestId string              `xml:"requestId"`
+-	Groups    []SecurityGroupInfo `xml:"securityGroupInfo>item"`
 -}
 -
--// NewContainer creates a new Container using a new ServeMux and default router (RouterJSR311)
--func NewContainer() *Container {
--	return &Container{
--		webServices:            []*WebService{},
--		ServeMux:               http.NewServeMux(),
--		isRegisteredOnRoot:     false,
--		containerFilters:       []FilterFunction{},
--		doNotRecover:           false,
--		recoverHandleFunc:      logStackOnRecover,
--		router:                 RouterJSR311{},
--		contentEncodingEnabled: false}
+-// SecurityGroup encapsulates details for a security group in EC2.
+-//
+-// See http://goo.gl/CIdyP for more details.
+-type SecurityGroupInfo struct {
+-	SecurityGroup
+-	OwnerId     string   `xml:"ownerId"`
+-	Description string   `xml:"groupDescription"`
+-	IPPerms     []IPPerm `xml:"ipPermissions>item"`
 -}
 -
--// RecoverHandleFunction declares functions that can be used to handle a panic situation.
--// The first argument is what recover() returns. The second must be used to communicate an error response.
--type RecoverHandleFunction func(interface{}, http.ResponseWriter)
+-// IPPerm represents an allowance within an EC2 security group.
+-//
+-// See http://goo.gl/4oTxv for more details.
+-type IPPerm struct {
+-	Protocol     string              `xml:"ipProtocol"`
+-	FromPort     int                 `xml:"fromPort"`
+-	ToPort       int                 `xml:"toPort"`
+-	SourceIPs    []string            `xml:"ipRanges>item>cidrIp"`
+-	SourceGroups []UserSecurityGroup `xml:"groups>item"`
+-}
 -
--// RecoverHandler changes the default function (logStackOnRecover) to be called
--// when a panic is detected. DoNotRecover must be have its default value (=false).
--func (c *Container) RecoverHandler(handler RecoverHandleFunction) {
--	c.recoverHandleFunc = handler
+-// UserSecurityGroup holds a security group and the owner
+-// of that group.
+-type UserSecurityGroup struct {
+-	Id      string `xml:"groupId"`
+-	Name    string `xml:"groupName"`
+-	OwnerId string `xml:"userId"`
 -}
 -
--// DoNotRecover controls whether panics will be caught to return HTTP 500.
--// If set to true, Route functions are responsible for handling any error situation.
--// Default value is false = recover from panics. This has performance implications.
--func (c *Container) DoNotRecover(doNot bool) {
--	c.doNotRecover = doNot
+-// SecurityGroup represents an EC2 security group.
+-// If SecurityGroup is used as a parameter, then one of Id or Name
+-// may be empty. If both are set, then Id is used.
+-type SecurityGroup struct {
+-	Id          string `xml:"groupId"`
+-	Name        string `xml:"groupName"`
+-	Description string `xml:"groupDescription"`
+-	VpcId       string `xml:"vpcId"`
 -}
 -
--// Router changes the default Router (currently RouterJSR311)
--func (c *Container) Router(aRouter RouteSelector) {
--	c.router = aRouter
+-// SecurityGroupNames is a convenience function that
+-// returns a slice of security groups with the given names.
+-func SecurityGroupNames(names ...string) []SecurityGroup {
+-	g := make([]SecurityGroup, len(names))
+-	for i, name := range names {
+-		g[i] = SecurityGroup{Name: name}
+-	}
+-	return g
 -}
 -
--// EnableContentEncoding (default=false) allows for GZIP or DEFLATE encoding of responses.
--func (c *Container) EnableContentEncoding(enabled bool) {
--	c.contentEncodingEnabled = enabled
+-// SecurityGroupNames is a convenience function that
+-// returns a slice of security groups with the given ids.
+-func SecurityGroupIds(ids ...string) []SecurityGroup {
+-	g := make([]SecurityGroup, len(ids))
+-	for i, id := range ids {
+-		g[i] = SecurityGroup{Id: id}
+-	}
+-	return g
 -}
 -
--// Add a WebService to the Container. It will detect duplicate root paths and panic in that case.
--func (c *Container) Add(service *WebService) *Container {
--	// If registered on root then no additional specific mapping is needed
--	if !c.isRegisteredOnRoot {
--		pattern := c.fixedPrefixPath(service.RootPath())
--		// check if root path registration is needed
--		if "/" == pattern || "" == pattern {
--			c.ServeMux.HandleFunc("/", c.dispatch)
--			c.isRegisteredOnRoot = true
+-// SecurityGroups returns details about security groups in EC2.  Both parameters
+-// are optional, and if provided will limit the security groups returned to those
+-// matching the given groups or filtering rules.
+-//
+-// See http://goo.gl/k12Uy for more details.
+-func (ec2 *EC2) SecurityGroups(groups []SecurityGroup, filter *Filter) (resp *SecurityGroupsResp, err error) {
+-	params := makeParams("DescribeSecurityGroups")
+-	i, j := 1, 1
+-	for _, g := range groups {
+-		if g.Id != "" {
+-			params["GroupId."+strconv.Itoa(i)] = g.Id
+-			i++
 -		} else {
--			// detect if registration already exists
--			alreadyMapped := false
--			for _, each := range c.webServices {
--				if each.RootPath() == service.RootPath() {
--					alreadyMapped = true
--					break
--				}
--			}
--			if !alreadyMapped {
--				c.ServeMux.HandleFunc(pattern, c.dispatch)
--				if !strings.HasSuffix(pattern, "/") {
--					c.ServeMux.HandleFunc(pattern+"/", c.dispatch)
--				}
--			}
--		}
--	}
--	// cannot have duplicate root paths
--	for _, each := range c.webServices {
--		if each.RootPath() == service.RootPath() {
--			log.Fatalf("[restful] WebService with duplicate root path detected:['%v']", each)
+-			params["GroupName."+strconv.Itoa(j)] = g.Name
+-			j++
 -		}
 -	}
--	// if rootPath was not set then lazy initialize it
--	if len(service.rootPath) == 0 {
--		service.Path("/")
+-	filter.addParams(params)
+-
+-	resp = &SecurityGroupsResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
--	c.webServices = append(c.webServices, service)
--	return c
+-	return resp, nil
 -}
 -
--// logStackOnRecover is the default RecoverHandleFunction and is called
--// when DoNotRecover is false and the recoverHandleFunc is not set for the container.
--// Default implementation logs the stacktrace and writes the stacktrace on the response.
--// This may be a security issue as it exposes sourcecode information.
--func logStackOnRecover(panicReason interface{}, httpWriter http.ResponseWriter) {
--	var buffer bytes.Buffer
--	buffer.WriteString(fmt.Sprintf("[restful] recover from panic situation: - %v\r\n", panicReason))
--	for i := 2; ; i += 1 {
--		_, file, line, ok := runtime.Caller(i)
--		if !ok {
--			break
--		}
--		buffer.WriteString(fmt.Sprintf("    %s:%d\r\n", file, line))
+-// DeleteSecurityGroup removes the given security group in EC2.
+-//
+-// See http://goo.gl/QJJDO for more details.
+-func (ec2 *EC2) DeleteSecurityGroup(group SecurityGroup) (resp *SimpleResp, err error) {
+-	params := makeParams("DeleteSecurityGroup")
+-	if group.Id != "" {
+-		params["GroupId"] = group.Id
+-	} else {
+-		params["GroupName"] = group.Name
 -	}
--	log.Println(buffer.String())
--	httpWriter.WriteHeader(http.StatusInternalServerError)
--	httpWriter.Write(buffer.Bytes())
+-
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return resp, nil
 -}
 -
--// Dispatch the incoming Http Request to a matching WebService.
--func (c *Container) dispatch(httpWriter http.ResponseWriter, httpRequest *http.Request) {
--	// Instal panic recovery unless told otherwise
--	if !c.doNotRecover { // catch all for 500 response
--		defer func() {
--			if r := recover(); r != nil {
--				c.recoverHandleFunc(r, httpWriter)
--				return
--			}
--		}()
+-// AuthorizeSecurityGroup creates an allowance for clients matching the provided
+-// rules to access instances within the given security group.
+-//
+-// See http://goo.gl/u2sDJ for more details.
+-func (ec2 *EC2) AuthorizeSecurityGroup(group SecurityGroup, perms []IPPerm) (resp *SimpleResp, err error) {
+-	return ec2.authOrRevoke("AuthorizeSecurityGroupIngress", group, perms)
+-}
+-
+-// AuthorizeSecurityGroupEgress creates an allowance for clients matching the provided
+-// rules for egress access.
+-//
+-// See http://goo.gl/UHnH4L for more details.
+-func (ec2 *EC2) AuthorizeSecurityGroupEgress(group SecurityGroup, perms []IPPerm) (resp *SimpleResp, err error) {
+-	return ec2.authOrRevoke("AuthorizeSecurityGroupEgress", group, perms)
+-}
+-
+-// RevokeSecurityGroup revokes permissions from a group.
+-//
+-// See http://goo.gl/ZgdxA for more details.
+-func (ec2 *EC2) RevokeSecurityGroup(group SecurityGroup, perms []IPPerm) (resp *SimpleResp, err error) {
+-	return ec2.authOrRevoke("RevokeSecurityGroupIngress", group, perms)
+-}
+-
+-func (ec2 *EC2) authOrRevoke(op string, group SecurityGroup, perms []IPPerm) (resp *SimpleResp, err error) {
+-	params := makeParams(op)
+-	if group.Id != "" {
+-		params["GroupId"] = group.Id
+-	} else {
+-		params["GroupName"] = group.Name
 -	}
--	// Install closing the request body (if any)
--	defer func() {
--		if nil != httpRequest.Body {
--			httpRequest.Body.Close()
--		}
--	}()
 -
--	// Detect if compression is needed
--	// assume without compression, test for override
--	writer := httpWriter
--	if c.contentEncodingEnabled {
--		doCompress, encoding := wantsCompressedResponse(httpRequest)
--		if doCompress {
--			var err error
--			writer, err = NewCompressingResponseWriter(httpWriter, encoding)
--			if err != nil {
--				log.Println("[restful] unable to install compressor:", err)
--				httpWriter.WriteHeader(http.StatusInternalServerError)
--				return
+-	for i, perm := range perms {
+-		prefix := "IpPermissions." + strconv.Itoa(i+1)
+-		params[prefix+".IpProtocol"] = perm.Protocol
+-		params[prefix+".FromPort"] = strconv.Itoa(perm.FromPort)
+-		params[prefix+".ToPort"] = strconv.Itoa(perm.ToPort)
+-		for j, ip := range perm.SourceIPs {
+-			params[prefix+".IpRanges."+strconv.Itoa(j+1)+".CidrIp"] = ip
+-		}
+-		for j, g := range perm.SourceGroups {
+-			subprefix := prefix + ".Groups." + strconv.Itoa(j+1)
+-			if g.OwnerId != "" {
+-				params[subprefix+".UserId"] = g.OwnerId
+-			}
+-			if g.Id != "" {
+-				params[subprefix+".GroupId"] = g.Id
+-			} else {
+-				params[subprefix+".GroupName"] = g.Name
 -			}
--			defer func() {
--				writer.(*CompressingResponseWriter).Close()
--			}()
 -		}
 -	}
--	// Find best match Route ; err is non nil if no match was found
--	webService, route, err := c.router.SelectRoute(
--		c.webServices,
--		httpRequest)
+-
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
 -	if err != nil {
--		// a non-200 response has already been written
--		// run container filters anyway ; they should not touch the response...
--		chain := FilterChain{Filters: c.containerFilters, Target: func(req *Request, resp *Response) {
--			switch err.(type) {
--			case ServiceError:
--				ser := err.(ServiceError)
--				resp.WriteErrorString(ser.Code, ser.Message)
--			}
--			// TODO
--		}}
--		chain.ProcessFilter(NewRequest(httpRequest), NewResponse(writer))
--		return
--	}
--	wrappedRequest, wrappedResponse := route.wrapRequestResponse(writer, httpRequest)
--	// pass through filters (if any)
--	if len(c.containerFilters)+len(webService.filters)+len(route.Filters) > 0 {
--		// compose filter chain
--		allFilters := []FilterFunction{}
--		allFilters = append(allFilters, c.containerFilters...)
--		allFilters = append(allFilters, webService.filters...)
--		allFilters = append(allFilters, route.Filters...)
--		chain := FilterChain{Filters: allFilters, Target: func(req *Request, resp *Response) {
--			// handle request by route after passing all filters
--			route.Function(wrappedRequest, wrappedResponse)
--		}}
--		chain.ProcessFilter(wrappedRequest, wrappedResponse)
--	} else {
--		// no filters, handle request by route
--		route.Function(wrappedRequest, wrappedResponse)
+-		return nil, err
 -	}
+-	return resp, nil
 -}
 -
--// fixedPrefixPath returns the fixed part of the partspec ; it may include template vars {}
--func (c Container) fixedPrefixPath(pathspec string) string {
--	varBegin := strings.Index(pathspec, "{")
--	if -1 == varBegin {
--		return pathspec
+-// ResourceTag represents key-value metadata used to classify and organize
+-// EC2 instances.
+-//
+-// See http://goo.gl/bncl3 for more details
+-type Tag struct {
+-	Key   string `xml:"key"`
+-	Value string `xml:"value"`
+-}
+-
+-// CreateTags adds or overwrites one or more tags for the specified taggable resources.
+-// For a list of tagable resources, see: http://docs.aws.amazon.com/AWSEC2/latest/UserGuide/Using_Tags.html
+-//
+-// See http://goo.gl/Vmkqc for more details
+-func (ec2 *EC2) CreateTags(resourceIds []string, tags []Tag) (resp *SimpleResp, err error) {
+-	params := makeParams("CreateTags")
+-	addParamsList(params, "ResourceId", resourceIds)
+-
+-	for j, tag := range tags {
+-		params["Tag."+strconv.Itoa(j+1)+".Key"] = tag.Key
+-		params["Tag."+strconv.Itoa(j+1)+".Value"] = tag.Value
 -	}
--	return pathspec[:varBegin]
+-
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return resp, nil
 -}
 -
--// ServeHTTP implements net/http.Handler therefore a Container can be a Handler in a http.Server
--func (c Container) ServeHTTP(httpwriter http.ResponseWriter, httpRequest *http.Request) {
--	c.ServeMux.ServeHTTP(httpwriter, httpRequest)
+-type TagsResp struct {
+-	RequestId string        `xml:"requestId"`
+-	Tags      []ResourceTag `xml:"tagSet>item"`
 -}
 -
--// Handle registers the handler for the given pattern. If a handler already exists for pattern, Handle panics.
--func (c Container) Handle(pattern string, handler http.Handler) {
--	c.ServeMux.Handle(pattern, handler)
+-type ResourceTag struct {
+-	Tag
+-	ResourceId   string `xml:"resourceId"`
+-	ResourceType string `xml:"resourceType"`
 -}
 -
--// Filter appends a container FilterFunction. These are called before dispatching
--// a http.Request to a WebService from the container
--func (c *Container) Filter(filter FilterFunction) {
--	c.containerFilters = append(c.containerFilters, filter)
+-func (ec2 *EC2) Tags(filter *Filter) (*TagsResp, error) {
+-	params := makeParams("DescribeTags")
+-	filter.addParams(params)
+-
+-	resp := &TagsResp{}
+-	if err := ec2.query(params, resp); err != nil {
+-		return nil, err
+-	}
+-
+-	return resp, nil
 -}
 -
--// RegisteredWebServices returns the collections of added WebServices
--func (c Container) RegisteredWebServices() []*WebService {
--	return c.webServices
+-// Response to a StartInstances request.
+-//
+-// See http://goo.gl/awKeF for more details.
+-type StartInstanceResp struct {
+-	RequestId    string                `xml:"requestId"`
+-	StateChanges []InstanceStateChange `xml:"instancesSet>item"`
 -}
 -
--// computeAllowedMethods returns a list of HTTP methods that are valid for a Request
--func (c Container) computeAllowedMethods(req *Request) []string {
--	// Go through all RegisteredWebServices() and all its Routes to collect the options
--	methods := []string{}
--	requestPath := req.Request.URL.Path
--	for _, ws := range c.RegisteredWebServices() {
--		matches := ws.pathExpr.Matcher.FindStringSubmatch(requestPath)
--		if matches != nil {
--			finalMatch := matches[len(matches)-1]
--			for _, rt := range ws.Routes() {
--				matches := rt.pathExpr.Matcher.FindStringSubmatch(finalMatch)
--				if matches != nil {
--					lastMatch := matches[len(matches)-1]
--					if lastMatch == "" || lastMatch == "/" { // do not include if value is neither empty nor ‘/’.
--						methods = append(methods, rt.Method)
--					}
--				}
--			}
--		}
+-// Response to a StopInstances request.
+-//
+-// See http://goo.gl/436dJ for more details.
+-type StopInstanceResp struct {
+-	RequestId    string                `xml:"requestId"`
+-	StateChanges []InstanceStateChange `xml:"instancesSet>item"`
+-}
+-
+-// StartInstances starts an Amazon EBS-backed AMI that you've previously stopped.
+-//
+-// See http://goo.gl/awKeF for more details.
+-func (ec2 *EC2) StartInstances(ids ...string) (resp *StartInstanceResp, err error) {
+-	params := makeParams("StartInstances")
+-	addParamsList(params, "InstanceId", ids)
+-	resp = &StartInstanceResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
--	// methods = append(methods, "OPTIONS")  not sure about this
--	return methods
+-	return resp, nil
 -}
 -
--// newBasicRequestResponse creates a pair of Request,Response from its http versions.
--// It is basic because no parameter or (produces) content-type information is given.
--func newBasicRequestResponse(httpWriter http.ResponseWriter, httpRequest *http.Request) (*Request, *Response) {
--	resp := NewResponse(httpWriter)
--	resp.requestAccept = httpRequest.Header.Get(HEADER_Accept)
--	return NewRequest(httpRequest), resp
+-// StopInstances requests stopping one or more Amazon EBS-backed instances.
+-//
+-// See http://goo.gl/436dJ for more details.
+-func (ec2 *EC2) StopInstances(ids ...string) (resp *StopInstanceResp, err error) {
+-	params := makeParams("StopInstances")
+-	addParamsList(params, "InstanceId", ids)
+-	resp = &StopInstanceResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return resp, nil
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/cors_filter.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/cors_filter.go
-deleted file mode 100644
-index ae166b6..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/cors_filter.go
-+++ /dev/null
-@@ -1,170 +0,0 @@
--package restful
 -
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
+-// RebootInstance requests a reboot of one or more instances. This operation is asynchronous;
+-// it only queues a request to reboot the specified instance(s). The operation will succeed
+-// if the instances are valid and belong to you.
+-//
+-// Requests to reboot terminated instances are ignored.
+-//
+-// See http://goo.gl/baoUf for more details.
+-func (ec2 *EC2) RebootInstances(ids ...string) (resp *SimpleResp, err error) {
+-	params := makeParams("RebootInstances")
+-	addParamsList(params, "InstanceId", ids)
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return resp, nil
+-}
 -
--import (
--	"strconv"
--	"strings"
--)
+-// The ModifyInstanceAttribute request parameters.
+-type ModifyInstance struct {
+-	InstanceType          string
+-	BlockDevices          []BlockDeviceMapping
+-	DisableAPITermination bool
+-	EbsOptimized          bool
+-	SecurityGroups        []SecurityGroup
+-	ShutdownBehavior      string
+-	KernelId              string
+-	RamdiskId             string
+-	SourceDestCheck       bool
+-	SriovNetSupport       bool
+-	UserData              []byte
 -
--// CrossOriginResourceSharing is used to create a Container Filter that implements CORS.
--// Cross-origin resource sharing (CORS) is a mechanism that allows JavaScript on a web page
--// to make XMLHttpRequests to another domain, not the domain the JavaScript originated from.
+-	SetSourceDestCheck bool
+-}
+-
+-// Response to a ModifyInstanceAttribute request.
 -//
--// http://en.wikipedia.org/wiki/Cross-origin_resource_sharing
--// http://enable-cors.org/server.html
--// http://www.html5rocks.com/en/tutorials/cors/#toc-handling-a-not-so-simple-request
--type CrossOriginResourceSharing struct {
--	ExposeHeaders  []string // list of Header names
--	AllowedHeaders []string // list of Header names
--	AllowedDomains []string // list of allowed values for Http Origin. If empty all are allowed.
--	AllowedMethods []string
--	MaxAge         int // number of seconds before requiring new Options request
--	CookiesAllowed bool
--	Container      *Container
+-// http://goo.gl/icuXh5 for more details.
+-type ModifyInstanceResp struct {
+-	RequestId string `xml:"requestId"`
+-	Return    bool   `xml:"return"`
 -}
 -
--// Filter is a filter function that implements the CORS flow as documented on http://enable-cors.org/server.html
--// and http://www.html5rocks.com/static/images/cors_server_flowchart.png
--func (c CrossOriginResourceSharing) Filter(req *Request, resp *Response, chain *FilterChain) {
--	origin := req.Request.Header.Get(HEADER_Origin)
--	if len(origin) == 0 {
--		if trace {
--			traceLogger.Println("no Http header Origin set")
--		}
--		chain.ProcessFilter(req, resp)
--		return
--	}
--	if len(c.AllowedDomains) > 0 { // if provided then origin must be included
--		included := false
--		for _, each := range c.AllowedDomains {
--			if each == origin {
--				included = true
--				break
--			}
--		}
--		if !included {
--			if trace {
--				traceLogger.Println("HTTP Origin:%s is not part of %v", origin, c.AllowedDomains)
--			}
--			chain.ProcessFilter(req, resp)
--			return
--		}
+-// ModifyImageAttribute modifies the specified attribute of the specified instance.
+-// You can specify only one attribute at a time. To modify some attributes, the
+-// instance must be stopped.
+-//
+-// See http://goo.gl/icuXh5 for more details.
+-func (ec2 *EC2) ModifyInstance(instId string, options *ModifyInstance) (resp *ModifyInstanceResp, err error) {
+-	params := makeParams("ModifyInstanceAttribute")
+-	params["InstanceId"] = instId
+-	addBlockDeviceParams("", params, options.BlockDevices)
+-
+-	if options.InstanceType != "" {
+-		params["InstanceType.Value"] = options.InstanceType
 -	}
--	if req.Request.Method != "OPTIONS" {
--		c.doActualRequest(req, resp)
--		chain.ProcessFilter(req, resp)
--		return
+-
+-	if options.DisableAPITermination {
+-		params["DisableApiTermination.Value"] = "true"
 -	}
--	if acrm := req.Request.Header.Get(HEADER_AccessControlRequestMethod); acrm != "" {
--		c.doPreflightRequest(req, resp)
--	} else {
--		c.doActualRequest(req, resp)
+-
+-	if options.EbsOptimized {
+-		params["EbsOptimized"] = "true"
 -	}
--}
 -
--func (c CrossOriginResourceSharing) doActualRequest(req *Request, resp *Response) {
--	c.setOptionsHeaders(req, resp)
--	// continue processing the response
--}
+-	if options.ShutdownBehavior != "" {
+-		params["InstanceInitiatedShutdownBehavior.Value"] = options.ShutdownBehavior
+-	}
 -
--func (c CrossOriginResourceSharing) doPreflightRequest(req *Request, resp *Response) {
--	if len(c.AllowedMethods) == 0 {
--		c.AllowedMethods = c.Container.computeAllowedMethods(req)
+-	if options.KernelId != "" {
+-		params["Kernel.Value"] = options.KernelId
 -	}
 -
--	acrm := req.Request.Header.Get(HEADER_AccessControlRequestMethod)
--	if !c.isValidAccessControlRequestMethod(acrm, c.AllowedMethods) {
--		if trace {
--			traceLogger.Printf("Http header %s:%s is not in %v",
--				HEADER_AccessControlRequestMethod,
--				acrm,
--				c.AllowedMethods)
--		}
--		return
+-	if options.RamdiskId != "" {
+-		params["Ramdisk.Value"] = options.RamdiskId
 -	}
--	acrhs := req.Request.Header.Get(HEADER_AccessControlRequestHeaders)
--	if len(acrhs) > 0 {
--		for _, each := range strings.Split(acrhs, ",") {
--			if !c.isValidAccessControlRequestHeader(strings.Trim(each, " ")) {
--				if trace {
--					traceLogger.Printf("Http header %s:%s is not in %v",
--						HEADER_AccessControlRequestHeaders,
--						acrhs,
--						c.AllowedHeaders)
--				}
--				return
--			}
+-
+-	if options.SourceDestCheck || options.SetSourceDestCheck {
+-		if options.SourceDestCheck {
+-			params["SourceDestCheck.Value"] = "true"
+-		} else {
+-			params["SourceDestCheck.Value"] = "false"
 -		}
 -	}
--	resp.AddHeader(HEADER_AccessControlAllowMethods, strings.Join(c.AllowedMethods, ","))
--	resp.AddHeader(HEADER_AccessControlAllowHeaders, acrhs)
--	c.setOptionsHeaders(req, resp)
--
--	// return http 200 response, no body
--}
 -
--func (c CrossOriginResourceSharing) setOptionsHeaders(req *Request, resp *Response) {
--	c.checkAndSetExposeHeaders(resp)
--	c.setAllowOriginHeader(req, resp)
--	c.checkAndSetAllowCredentials(resp)
--	if c.MaxAge > 0 {
--		resp.AddHeader(HEADER_AccessControlMaxAge, strconv.Itoa(c.MaxAge))
+-	if options.SriovNetSupport {
+-		params["SriovNetSupport.Value"] = "simple"
 -	}
--}
 -
--func (c CrossOriginResourceSharing) isOriginAllowed(origin string) bool {
--	if len(origin) == 0 {
--		return false
--	}
--	if len(c.AllowedDomains) == 0 {
--		return true
+-	if options.UserData != nil {
+-		userData := make([]byte, b64.EncodedLen(len(options.UserData)))
+-		b64.Encode(userData, options.UserData)
+-		params["UserData"] = string(userData)
 -	}
--	allowed := false
--	for _, each := range c.AllowedDomains {
--		if each == origin {
--			allowed = true
--			break
+-
+-	i := 1
+-	for _, g := range options.SecurityGroups {
+-		if g.Id != "" {
+-			params["GroupId."+strconv.Itoa(i)] = g.Id
+-			i++
 -		}
 -	}
--	return allowed
--}
 -
--func (c CrossOriginResourceSharing) setAllowOriginHeader(req *Request, resp *Response) {
--	origin := req.Request.Header.Get(HEADER_Origin)
--	if c.isOriginAllowed(origin) {
--		resp.AddHeader(HEADER_AccessControlAllowOrigin, origin)
+-	resp = &ModifyInstanceResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		resp = nil
 -	}
+-	return
 -}
 -
--func (c CrossOriginResourceSharing) checkAndSetExposeHeaders(resp *Response) {
--	if len(c.ExposeHeaders) > 0 {
--		resp.AddHeader(HEADER_AccessControlExposeHeaders, strings.Join(c.ExposeHeaders, ","))
--	}
--}
+-// ----------------------------------------------------------------------------
+-// VPC management functions and types.
 -
--func (c CrossOriginResourceSharing) checkAndSetAllowCredentials(resp *Response) {
--	if c.CookiesAllowed {
--		resp.AddHeader(HEADER_AccessControlAllowCredentials, "true")
--	}
+-// The CreateVpc request parameters
+-//
+-// See http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-CreateVpc.html
+-type CreateVpc struct {
+-	CidrBlock       string
+-	InstanceTenancy string
 -}
 -
--func (c CrossOriginResourceSharing) isValidAccessControlRequestMethod(method string, allowedMethods []string) bool {
--	for _, each := range allowedMethods {
--		if each == method {
--			return true
--		}
--	}
--	return false
+-// Response to a CreateVpc request
+-type CreateVpcResp struct {
+-	RequestId string `xml:"requestId"`
+-	VPC       VPC    `xml:"vpc"`
 -}
 -
--func (c CrossOriginResourceSharing) isValidAccessControlRequestHeader(header string) bool {
--	for _, each := range c.AllowedHeaders {
--		if strings.ToLower(each) == strings.ToLower(header) {
--			return true
--		}
--	}
--	return false
+-// The ModifyVpcAttribute request parameters.
+-//
+-// See http://docs.amazonwebservices.com/AWSEC2/latest/APIReference/index.html?ApiReference-query-DescribeVpcAttribute.html for more details.
+-type ModifyVpcAttribute struct {
+-	EnableDnsSupport   bool
+-	EnableDnsHostnames bool
+-
+-	SetEnableDnsSupport   bool
+-	SetEnableDnsHostnames bool
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/cors_filter_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/cors_filter_test.go
-deleted file mode 100644
-index 9b47230..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/cors_filter_test.go
-+++ /dev/null
-@@ -1,125 +0,0 @@
--package restful
 -
--import (
--	"net/http"
--	"net/http/httptest"
--	"testing"
--)
+-// Response to a DescribeVpcAttribute request.
+-//
+-// See http://docs.amazonwebservices.com/AWSEC2/latest/APIReference/index.html?ApiReference-query-DescribeVpcAttribute.html for more details.
+-type VpcAttributeResp struct {
+-	RequestId          string `xml:"requestId"`
+-	VpcId              string `xml:"vpcId"`
+-	EnableDnsSupport   bool   `xml:"enableDnsSupport>value"`
+-	EnableDnsHostnames bool   `xml:"enableDnsHostnames>value"`
+-}
 -
--// go test -v -test.run TestCORSFilter_Preflight ...restful
--// http://www.html5rocks.com/en/tutorials/cors/#toc-handling-a-not-so-simple-request
--func TestCORSFilter_Preflight(t *testing.T) {
--	tearDown()
--	ws := new(WebService)
--	ws.Route(ws.PUT("/cors").To(dummy))
--	Add(ws)
+-// CreateInternetGateway request parameters.
+-//
+-// http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-CreateInternetGateway.html
+-type CreateInternetGateway struct{}
 -
--	cors := CrossOriginResourceSharing{
--		ExposeHeaders:  []string{"X-Custom-Header"},
--		AllowedHeaders: []string{"X-Custom-Header", "X-Additional-Header"},
--		CookiesAllowed: true,
--		Container:      DefaultContainer}
--	Filter(cors.Filter)
+-// CreateInternetGateway response
+-type CreateInternetGatewayResp struct {
+-	RequestId       string          `xml:"requestId"`
+-	InternetGateway InternetGateway `xml:"internetGateway"`
+-}
 -
--	// Preflight
--	httpRequest, _ := http.NewRequest("OPTIONS", "http://api.alice.com/cors", nil)
--	httpRequest.Method = "OPTIONS"
--	httpRequest.Header.Set(HEADER_Origin, "http://api.bob.com")
--	httpRequest.Header.Set(HEADER_AccessControlRequestMethod, "PUT")
--	httpRequest.Header.Set(HEADER_AccessControlRequestHeaders, "X-Custom-Header, X-Additional-Header")
+-// The CreateRouteTable request parameters.
+-//
+-// http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-CreateRouteTable.html
+-type CreateRouteTable struct {
+-	VpcId string
+-}
 -
--	httpWriter := httptest.NewRecorder()
--	DefaultContainer.dispatch(httpWriter, httpRequest)
+-// Response to a CreateRouteTable request.
+-type CreateRouteTableResp struct {
+-	RequestId  string     `xml:"requestId"`
+-	RouteTable RouteTable `xml:"routeTable"`
+-}
 -
--	actual := httpWriter.Header().Get(HEADER_AccessControlAllowOrigin)
--	if "http://api.bob.com" != actual {
--		t.Fatal("expected: http://api.bob.com but got:" + actual)
--	}
--	actual = httpWriter.Header().Get(HEADER_AccessControlAllowMethods)
--	if "PUT" != actual {
--		t.Fatal("expected: PUT but got:" + actual)
--	}
--	actual = httpWriter.Header().Get(HEADER_AccessControlAllowHeaders)
--	if "X-Custom-Header, X-Additional-Header" != actual {
--		t.Fatal("expected: X-Custom-Header, X-Additional-Header but got:" + actual)
--	}
+-// CreateRoute request parameters
+-//
+-// http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-CreateRoute.html
+-type CreateRoute struct {
+-	RouteTableId           string
+-	DestinationCidrBlock   string
+-	GatewayId              string
+-	InstanceId             string
+-	NetworkInterfaceId     string
+-	VpcPeeringConnectionId string
+-}
+-type ReplaceRoute struct {
+-	RouteTableId           string
+-	DestinationCidrBlock   string
+-	GatewayId              string
+-	InstanceId             string
+-	NetworkInterfaceId     string
+-	VpcPeeringConnectionId string
+-}
 -
--	if !cors.isOriginAllowed("somewhere") {
--		t.Fatal("origin expected to be allowed")
--	}
--	cors.AllowedDomains = []string{"overthere.com"}
--	if cors.isOriginAllowed("somewhere") {
--		t.Fatal("origin [somewhere] expected NOT to be allowed")
--	}
--	if !cors.isOriginAllowed("overthere.com") {
--		t.Fatal("origin [overthere] expected to be allowed")
--	}
+-type AssociateRouteTableResp struct {
+-	RequestId     string `xml:"requestId"`
+-	AssociationId string `xml:"associationId"`
+-}
+-type ReassociateRouteTableResp struct {
+-	RequestId     string `xml:"requestId"`
+-	AssociationId string `xml:"newAssociationId"`
+-}
 -
+-// The CreateSubnet request parameters
+-//
+-// http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-CreateSubnet.html
+-type CreateSubnet struct {
+-	VpcId            string
+-	CidrBlock        string
+-	AvailabilityZone string
 -}
 -
--// go test -v -test.run TestCORSFilter_Actual ...restful
--// http://www.html5rocks.com/en/tutorials/cors/#toc-handling-a-not-so-simple-request
--func TestCORSFilter_Actual(t *testing.T) {
--	tearDown()
--	ws := new(WebService)
--	ws.Route(ws.PUT("/cors").To(dummy))
--	Add(ws)
+-// Response to a CreateSubnet request
+-type CreateSubnetResp struct {
+-	RequestId string `xml:"requestId"`
+-	Subnet    Subnet `xml:"subnet"`
+-}
 -
--	cors := CrossOriginResourceSharing{
--		ExposeHeaders:  []string{"X-Custom-Header"},
--		AllowedHeaders: []string{"X-Custom-Header", "X-Additional-Header"},
--		CookiesAllowed: true,
--		Container:      DefaultContainer}
--	Filter(cors.Filter)
+-// Response to a DescribeInternetGateways request.
+-type InternetGatewaysResp struct {
+-	RequestId        string            `xml:"requestId"`
+-	InternetGateways []InternetGateway `xml:"internetGatewaySet>item"`
+-}
 -
--	// Actual
--	httpRequest, _ := http.NewRequest("PUT", "http://api.alice.com/cors", nil)
--	httpRequest.Header.Set(HEADER_Origin, "http://api.bob.com")
--	httpRequest.Header.Set("X-Custom-Header", "value")
+-// Response to a DescribeRouteTables request.
+-type RouteTablesResp struct {
+-	RequestId   string       `xml:"requestId"`
+-	RouteTables []RouteTable `xml:"routeTableSet>item"`
+-}
 -
--	httpWriter := httptest.NewRecorder()
--	DefaultContainer.dispatch(httpWriter, httpRequest)
--	actual := httpWriter.Header().Get(HEADER_AccessControlAllowOrigin)
--	if "http://api.bob.com" != actual {
--		t.Fatal("expected: http://api.bob.com but got:" + actual)
--	}
--	if httpWriter.Body.String() != "dummy" {
--		t.Fatal("expected: dummy but got:" + httpWriter.Body.String())
--	}
+-// Response to a DescribeVpcs request.
+-type VpcsResp struct {
+-	RequestId string `xml:"requestId"`
+-	VPCs      []VPC  `xml:"vpcSet>item"`
 -}
 -
--var allowedDomainInput = []struct {
--	domains  []string
--	origin   string
--	accepted bool
--}{
--	{[]string{}, "http://anything.com", true},
+-// Internet Gateway
+-type InternetGateway struct {
+-	InternetGatewayId string                      `xml:"internetGatewayId"`
+-	Attachments       []InternetGatewayAttachment `xml:"attachmentSet>item"`
+-	Tags              []Tag                       `xml:"tagSet>item"`
 -}
 -
--// go test -v -test.run TestCORSFilter_AllowedDomains ...restful
--func TestCORSFilter_AllowedDomains(t *testing.T) {
--	for _, each := range allowedDomainInput {
--		tearDown()
--		ws := new(WebService)
--		ws.Route(ws.PUT("/cors").To(dummy))
--		Add(ws)
+-type InternetGatewayAttachment struct {
+-	VpcId string `xml:"vpcId"`
+-	State string `xml:"state"`
+-}
 -
--		cors := CrossOriginResourceSharing{
--			AllowedDomains: each.domains,
--			CookiesAllowed: true,
--			Container:      DefaultContainer}
--		Filter(cors.Filter)
+-// Routing Table
+-type RouteTable struct {
+-	RouteTableId string                  `xml:"routeTableId"`
+-	VpcId        string                  `xml:"vpcId"`
+-	Associations []RouteTableAssociation `xml:"associationSet>item"`
+-	Routes       []Route                 `xml:"routeSet>item"`
+-	Tags         []Tag                   `xml:"tagSet>item"`
+-}
 -
--		httpRequest, _ := http.NewRequest("PUT", "http://api.his.com/cors", nil)
--		httpRequest.Header.Set(HEADER_Origin, each.origin)
--		httpWriter := httptest.NewRecorder()
--		DefaultContainer.dispatch(httpWriter, httpRequest)
--		actual := httpWriter.Header().Get(HEADER_AccessControlAllowOrigin)
--		if actual != each.origin && each.accepted {
--			t.Fatal("expected to be accepted")
--		}
--		if actual == each.origin && !each.accepted {
--			t.Fatal("did not expect to be accepted")
--		}
--	}
+-type RouteTableAssociation struct {
+-	AssociationId string `xml:"routeTableAssociationId"`
+-	RouteTableId  string `xml:"routeTableId"`
+-	SubnetId      string `xml:"subnetId"`
+-	Main          bool   `xml:"main"`
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/coverage.sh b/Godeps/_workspace/src/github.com/emicklei/go-restful/coverage.sh
-deleted file mode 100644
-index e27dbf1..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/coverage.sh
-+++ /dev/null
-@@ -1,2 +0,0 @@
--go test -coverprofile=coverage.out
--go tool cover -html=coverage.out
-\ No newline at end of file
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/curly.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/curly.go
-deleted file mode 100644
-index ce284f7..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/curly.go
-+++ /dev/null
-@@ -1,162 +0,0 @@
--package restful
 -
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
+-type Route struct {
+-	DestinationCidrBlock   string `xml:"destinationCidrBlock"`
+-	GatewayId              string `xml:"gatewayId"`
+-	InstanceId             string `xml:"instanceId"`
+-	InstanceOwnerId        string `xml:"instanceOwnerId"`
+-	NetworkInterfaceId     string `xml:"networkInterfaceId"`
+-	State                  string `xml:"state"`
+-	Origin                 string `xml:"origin"`
+-	VpcPeeringConnectionId string `xml:"vpcPeeringConnectionId"`
+-}
 -
--import (
--	"net/http"
--	"regexp"
--	"sort"
--	"strings"
--)
+-// Subnet
+-type Subnet struct {
+-	SubnetId                string `xml:"subnetId"`
+-	State                   string `xml:"state"`
+-	VpcId                   string `xml:"vpcId"`
+-	CidrBlock               string `xml:"cidrBlock"`
+-	AvailableIpAddressCount int    `xml:"availableIpAddressCount"`
+-	AvailabilityZone        string `xml:"availabilityZone"`
+-	DefaultForAZ            bool   `xml:"defaultForAz"`
+-	MapPublicIpOnLaunch     bool   `xml:"mapPublicIpOnLaunch"`
+-	Tags                    []Tag  `xml:"tagSet>item"`
+-}
 -
--// CurlyRouter expects Routes with paths that contain zero or more parameters in curly brackets.
--type CurlyRouter struct{}
+-// VPC represents a single VPC.
+-type VPC struct {
+-	VpcId           string `xml:"vpcId"`
+-	State           string `xml:"state"`
+-	CidrBlock       string `xml:"cidrBlock"`
+-	DHCPOptionsID   string `xml:"dhcpOptionsId"`
+-	InstanceTenancy string `xml:"instanceTenancy"`
+-	IsDefault       bool   `xml:"isDefault"`
+-	Tags            []Tag  `xml:"tagSet>item"`
+-}
 -
--// SelectRoute is part of the Router interface and returns the best match
--// for the WebService and its Route for the given Request.
--func (c CurlyRouter) SelectRoute(
--	webServices []*WebService,
--	httpRequest *http.Request) (selectedService *WebService, selected *Route, err error) {
+-// Response to a DescribeSubnets request.
+-type SubnetsResp struct {
+-	RequestId string   `xml:"requestId"`
+-	Subnets   []Subnet `xml:"subnetSet>item"`
+-}
 -
--	requestTokens := tokenizePath(httpRequest.URL.Path)
+-// Create a new VPC.
+-func (ec2 *EC2) CreateVpc(options *CreateVpc) (resp *CreateVpcResp, err error) {
+-	params := makeParams("CreateVpc")
+-	params["CidrBlock"] = options.CidrBlock
 -
--	detectedService := c.detectWebService(requestTokens, webServices)
--	if detectedService == nil {
--		if trace {
--			traceLogger.Printf("no WebService was found to match URL path:%s\n", httpRequest.URL.Path)
--		}
--		return nil, nil, NewError(http.StatusNotFound, "404: Page Not Found")
--	}
--	candidateRoutes := c.selectRoutes(detectedService, requestTokens)
--	if len(candidateRoutes) == 0 {
--		if trace {
--			traceLogger.Printf("no Route in WebService with path %s was found to match URL path:%s\n", detectedService.rootPath, httpRequest.URL.Path)
--		}
--		return detectedService, nil, NewError(http.StatusNotFound, "404: Page Not Found")
+-	if options.InstanceTenancy != "" {
+-		params["InstanceTenancy"] = options.InstanceTenancy
 -	}
--	selectedRoute, err := c.detectRoute(candidateRoutes, httpRequest)
--	if selectedRoute == nil {
--		return detectedService, nil, err
+-
+-	resp = &CreateVpcResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
--	return detectedService, selectedRoute, nil
+-
+-	return
 -}
 -
--// selectRoutes return a collection of Route from a WebService that matches the path tokens from the request.
--func (c CurlyRouter) selectRoutes(ws *WebService, requestTokens []string) []Route {
--	candidates := &sortableCurlyRoutes{[]*curlyRoute{}}
--	for _, each := range ws.routes {
--		matches, paramCount, staticCount := c.matchesRouteByPathTokens(each.pathParts, requestTokens)
--		if matches {
--			candidates.add(&curlyRoute{each, paramCount, staticCount}) // TODO make sure Routes() return pointers?
--		}
+-// Delete a VPC.
+-func (ec2 *EC2) DeleteVpc(id string) (resp *SimpleResp, err error) {
+-	params := makeParams("DeleteVpc")
+-	params["VpcId"] = id
+-
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
--	sort.Sort(sort.Reverse(candidates))
--	return candidates.routes()
+-	return
 -}
 -
--// matchesRouteByPathTokens computes whether it matches, howmany parameters do match and what the number of static path elements are.
--func (c CurlyRouter) matchesRouteByPathTokens(routeTokens, requestTokens []string) (matches bool, paramCount int, staticCount int) {
--	if len(routeTokens) < len(requestTokens) {
--		// proceed in matching only if last routeToken is wildcard
--		count := len(routeTokens)
--		if count == 0 || !strings.HasSuffix(routeTokens[count-1], "*}") {
--			return false, 0, 0
--		}
--		// proceed
--	}
--	for i, routeToken := range routeTokens {
--		if i == len(requestTokens) {
--			// reached end of request path
--			return false, 0, 0
--		}
--		requestToken := requestTokens[i]
--		if strings.HasPrefix(routeToken, "{") {
--			paramCount++
--			if colon := strings.Index(routeToken, ":"); colon != -1 {
--				// match by regex
--				matchesToken, matchesRemainder := c.regularMatchesPathToken(routeToken, colon, requestToken)
--				if !matchesToken {
--					return false, 0, 0
--				}
--				if matchesRemainder {
--					break
--				}
--			}
--		} else { // no { prefix
--			if requestToken != routeToken {
--				return false, 0, 0
--			}
--			staticCount++
--		}
+-// DescribeVpcs
+-//
+-// See http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeVpcs.html
+-func (ec2 *EC2) DescribeVpcs(ids []string, filter *Filter) (resp *VpcsResp, err error) {
+-	params := makeParams("DescribeVpcs")
+-	addParamsList(params, "VpcId", ids)
+-	filter.addParams(params)
+-	resp = &VpcsResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
--	return true, paramCount, staticCount
+-
+-	return
 -}
 -
--// regularMatchesPathToken tests whether the regular expression part of routeToken matches the requestToken or all remaining tokens
--// format routeToken is {someVar:someExpression}, e.g. {zipcode:[\d][\d][\d][\d][A-Z][A-Z]}
--func (c CurlyRouter) regularMatchesPathToken(routeToken string, colon int, requestToken string) (matchesToken bool, matchesRemainder bool) {
--	regPart := routeToken[colon+1 : len(routeToken)-1]
--	if regPart == "*" {
--		if trace {
--			traceLogger.Printf("wildcard parameter detected in route token %s that matches %s\n", routeToken, requestToken)
--		}
--		return true, true
+-// VpcAttribute describes an attribute of a VPC.
+-// You can specify only one attribute at a time.
+-// Valid attributes are:
+-//    enableDnsSupport | enableDnsHostnames
+-//
+-// See http://docs.amazonwebservices.com/AWSEC2/latest/APIReference/index.html?ApiReference-query-DescribeVpcAttribute.html for more details.
+-func (ec2 *EC2) VpcAttribute(vpcId, attribute string) (resp *VpcAttributeResp, err error) {
+-	params := makeParams("DescribeVpcAttribute")
+-	params["VpcId"] = vpcId
+-	params["Attribute"] = attribute
+-
+-	resp = &VpcAttributeResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
--	matched, err := regexp.MatchString(regPart, requestToken)
--	return (matched && err == nil), false
+-	return
 -}
 -
--// detectRoute selectes from a list of Route the first match by inspecting both the Accept and Content-Type
--// headers of the Request. See also RouterJSR311 in jsr311.go
--func (c CurlyRouter) detectRoute(candidateRoutes []Route, httpRequest *http.Request) (*Route, error) {
--	// tracing is done inside detectRoute
--	return RouterJSR311{}.detectRoute(candidateRoutes, httpRequest)
--}
+-// ModifyVpcAttribute modifies the specified attribute of the specified VPC.
+-//
+-// See http://docs.amazonwebservices.com/AWSEC2/latest/APIReference/index.html?ApiReference-query-ModifyVpcAttribute.html for more details.
+-func (ec2 *EC2) ModifyVpcAttribute(vpcId string, options *ModifyVpcAttribute) (*SimpleResp, error) {
+-	params := makeParams("ModifyVpcAttribute")
 -
--// detectWebService returns the best matching webService given the list of path tokens.
--// see also computeWebserviceScore
--func (c CurlyRouter) detectWebService(requestTokens []string, webServices []*WebService) *WebService {
--	var best *WebService
--	score := -1
--	for _, each := range webServices {
--		matches, eachScore := c.computeWebserviceScore(requestTokens, each.pathExpr.tokens)
--		if matches && (eachScore > score) {
--			best = each
--			score = eachScore
--		}
+-	params["VpcId"] = vpcId
+-
+-	if options.SetEnableDnsSupport {
+-		params["EnableDnsSupport.Value"] = strconv.FormatBool(options.EnableDnsSupport)
 -	}
--	return best
--}
 -
--// computeWebserviceScore returns whether tokens match and
--// the weighted score of the longest matching consecutive tokens from the beginning.
--func (c CurlyRouter) computeWebserviceScore(requestTokens []string, tokens []string) (bool, int) {
--	if len(tokens) > len(requestTokens) {
--		return false, 0
+-	if options.SetEnableDnsHostnames {
+-		params["EnableDnsHostnames.Value"] = strconv.FormatBool(options.EnableDnsHostnames)
 -	}
--	score := 0
--	for i := 0; i < len(tokens); i++ {
--		each := requestTokens[i]
--		other := tokens[i]
--		if len(each) == 0 && len(other) == 0 {
--			score++
--			continue
--		}
--		if len(other) > 0 && strings.HasPrefix(other, "{") {
--			// no empty match
--			if len(each) == 0 {
--				return false, score
--			}
--			score += 1
--		} else {
--			// not a parameter
--			if each != other {
--				return false, score
--			}
--			score += (len(tokens) - i) * 10 //fuzzy
--		}
+-
+-	resp := &SimpleResp{}
+-	if err := ec2.query(params, resp); err != nil {
+-		return nil, err
 -	}
--	return true, score
+-
+-	return resp, nil
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/curly_route.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/curly_route.go
-deleted file mode 100644
-index 3edab72..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/curly_route.go
-+++ /dev/null
-@@ -1,54 +0,0 @@
--package restful
 -
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
+-// Create a new subnet.
+-func (ec2 *EC2) CreateSubnet(options *CreateSubnet) (resp *CreateSubnetResp, err error) {
+-	params := makeParams("CreateSubnet")
+-	params["AvailabilityZone"] = options.AvailabilityZone
+-	params["CidrBlock"] = options.CidrBlock
+-	params["VpcId"] = options.VpcId
 -
--// curlyRoute exits for sorting Routes by the CurlyRouter based on number of parameters and number of static path elements.
--type curlyRoute struct {
--	route       Route
--	paramCount  int
--	staticCount int
--}
+-	resp = &CreateSubnetResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
 -
--type sortableCurlyRoutes struct {
--	candidates []*curlyRoute
+-	return
 -}
 -
--func (s *sortableCurlyRoutes) add(route *curlyRoute) {
--	s.candidates = append(s.candidates, route)
--}
+-// Delete a Subnet.
+-func (ec2 *EC2) DeleteSubnet(id string) (resp *SimpleResp, err error) {
+-	params := makeParams("DeleteSubnet")
+-	params["SubnetId"] = id
 -
--func (s *sortableCurlyRoutes) routes() (routes []Route) {
--	for _, each := range s.candidates {
--		routes = append(routes, each.route) // TODO change return type
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
--	return routes
+-	return
 -}
 -
--func (s *sortableCurlyRoutes) Len() int {
--	return len(s.candidates)
--}
--func (s *sortableCurlyRoutes) Swap(i, j int) {
--	s.candidates[i], s.candidates[j] = s.candidates[j], s.candidates[i]
--}
--func (s *sortableCurlyRoutes) Less(i, j int) bool {
--	ci := s.candidates[i]
--	cj := s.candidates[j]
+-// DescribeSubnets
+-//
+-// http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeSubnets.html
+-func (ec2 *EC2) DescribeSubnets(ids []string, filter *Filter) (resp *SubnetsResp, err error) {
+-	params := makeParams("DescribeSubnets")
+-	addParamsList(params, "SubnetId", ids)
+-	filter.addParams(params)
 -
--	// primary key
--	if ci.staticCount < cj.staticCount {
--		return true
--	}
--	if ci.staticCount > cj.staticCount {
--		return false
--	}
--	// secundary key
--	if ci.paramCount < cj.paramCount {
--		return true
+-	resp = &SubnetsResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
--	if ci.paramCount > cj.paramCount {
--		return false
+-
+-	return
+-}
+-
+-// Create a new internet gateway.
+-func (ec2 *EC2) CreateInternetGateway(
+-	options *CreateInternetGateway) (resp *CreateInternetGatewayResp, err error) {
+-	params := makeParams("CreateInternetGateway")
+-
+-	resp = &CreateInternetGatewayResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
--	return ci.route.Path < cj.route.Path
+-
+-	return
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/curly_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/curly_test.go
-deleted file mode 100644
-index 31d66dc..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/curly_test.go
-+++ /dev/null
-@@ -1,231 +0,0 @@
--package restful
 -
--import (
--	"io"
--	"net/http"
--	"testing"
--)
+-// Attach an InternetGateway.
+-func (ec2 *EC2) AttachInternetGateway(id, vpcId string) (resp *SimpleResp, err error) {
+-	params := makeParams("AttachInternetGateway")
+-	params["InternetGatewayId"] = id
+-	params["VpcId"] = vpcId
 -
--var requestPaths = []struct {
--	// url with path (1) is handled by service with root (2) and remainder has value final (3)
--	path, root string
--}{
--	{"/", "/"},
--	{"/p", "/p"},
--	{"/p/x", "/p/{q}"},
--	{"/q/x", "/q"},
--	{"/p/x/", "/p/{q}"},
--	{"/p/x/y", "/p/{q}"},
--	{"/q/x/y", "/q"},
--	{"/z/q", "/{p}/q"},
--	{"/a/b/c/q", "/"},
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return
 -}
 -
--// go test -v -test.run TestCurlyDetectWebService ...restful
--func TestCurlyDetectWebService(t *testing.T) {
--	ws1 := new(WebService).Path("/")
--	ws2 := new(WebService).Path("/p")
--	ws3 := new(WebService).Path("/q")
--	ws4 := new(WebService).Path("/p/q")
--	ws5 := new(WebService).Path("/p/{q}")
--	ws7 := new(WebService).Path("/{p}/q")
--	var wss = []*WebService{ws1, ws2, ws3, ws4, ws5, ws7}
+-// Detach an InternetGateway.
+-func (ec2 *EC2) DetachInternetGateway(id, vpcId string) (resp *SimpleResp, err error) {
+-	params := makeParams("DetachInternetGateway")
+-	params["InternetGatewayId"] = id
+-	params["VpcId"] = vpcId
 -
--	for _, each := range wss {
--		t.Logf("path=%s,toks=%v\n", each.pathExpr.Source, each.pathExpr.tokens)
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
+-	return
+-}
 -
--	router := CurlyRouter{}
+-// Delete an InternetGateway.
+-func (ec2 *EC2) DeleteInternetGateway(id string) (resp *SimpleResp, err error) {
+-	params := makeParams("DeleteInternetGateway")
+-	params["InternetGatewayId"] = id
 -
--	ok := true
--	for i, fixture := range requestPaths {
--		requestTokens := tokenizePath(fixture.path)
--		who := router.detectWebService(requestTokens, wss)
--		if who != nil && who.RootPath() != fixture.root {
--			t.Logf("[line:%v] Unexpected dispatcher, expected:%v, actual:%v", i, fixture.root, who.RootPath())
--			ok = false
--		}
--	}
--	if !ok {
--		t.Fail()
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
+-	return
 -}
 -
--var serviceDetects = []struct {
--	path  string
--	found bool
--	root  string
--}{
--	{"/a/b", true, "/{p}/{q}/{r}"},
--	{"/p/q", true, "/p/q"},
--	{"/q/p", true, "/q"},
--	{"/", true, "/"},
--	{"/p/q/r", true, "/p/q"},
+-// DescribeInternetGateways
+-//
+-// http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInternetGateways.html
+-func (ec2 *EC2) DescribeInternetGateways(ids []string, filter *Filter) (resp *InternetGatewaysResp, err error) {
+-	params := makeParams("DescribeInternetGateways")
+-	addParamsList(params, "InternetGatewayId", ids)
+-	filter.addParams(params)
+-
+-	resp = &InternetGatewaysResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	return
 -}
 -
--// go test -v -test.run Test_detectWebService ...restful
--func Test_detectWebService(t *testing.T) {
--	router := CurlyRouter{}
--	ws1 := new(WebService).Path("/")
--	ws2 := new(WebService).Path("/p")
--	ws3 := new(WebService).Path("/q")
--	ws4 := new(WebService).Path("/p/q")
--	ws5 := new(WebService).Path("/p/{q}")
--	ws6 := new(WebService).Path("/p/{q}/")
--	ws7 := new(WebService).Path("/{p}/q")
--	ws8 := new(WebService).Path("/{p}/{q}/{r}")
--	var wss = []*WebService{ws8, ws7, ws6, ws5, ws4, ws3, ws2, ws1}
--	for _, fix := range serviceDetects {
--		requestPath := fix.path
--		requestTokens := tokenizePath(requestPath)
--		for _, ws := range wss {
--			serviceTokens := ws.pathExpr.tokens
--			matches, score := router.computeWebserviceScore(requestTokens, serviceTokens)
--			t.Logf("req=%s,toks:%v,ws=%s,toks:%v,score=%d,matches=%v", requestPath, requestTokens, ws.RootPath(), serviceTokens, score, matches)
--		}
--		best := router.detectWebService(requestTokens, wss)
--		if best != nil {
--			if fix.found {
--				t.Logf("best=%s", best.RootPath())
--			} else {
--				t.Fatalf("should have found:%s", fix.root)
--			}
--		}
+-// Create a new routing table.
+-func (ec2 *EC2) CreateRouteTable(
+-	options *CreateRouteTable) (resp *CreateRouteTableResp, err error) {
+-	params := makeParams("CreateRouteTable")
+-	params["VpcId"] = options.VpcId
+-
+-	resp = &CreateRouteTableResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
+-
+-	return
 -}
 -
--var routeMatchers = []struct {
--	route       string
--	path        string
--	matches     bool
--	paramCount  int
--	staticCount int
--}{
--	// route, request-path
--	{"/a", "/a", true, 0, 1},
--	{"/a", "/b", false, 0, 0},
--	{"/a", "/b", false, 0, 0},
--	{"/a/{b}/c/", "/a/2/c", true, 1, 2},
--	{"/{a}/{b}/{c}/", "/a/b", false, 0, 0},
--	{"/{x:*}", "/", false, 0, 0},
--	{"/{x:*}", "/a", true, 1, 0},
--	{"/{x:*}", "/a/b", true, 1, 0},
--	{"/a/{x:*}", "/a/b", true, 1, 1},
--	{"/a/{x:[A-Z][A-Z]}", "/a/ZX", true, 1, 1},
--	{"/basepath/{resource:*}", "/basepath/some/other/location/test.xml", true, 1, 1},
+-// Delete a RouteTable.
+-func (ec2 *EC2) DeleteRouteTable(id string) (resp *SimpleResp, err error) {
+-	params := makeParams("DeleteRouteTable")
+-	params["RouteTableId"] = id
+-
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return
 -}
 -
--// clear && go test -v -test.run Test_matchesRouteByPathTokens ...restful
--func Test_matchesRouteByPathTokens(t *testing.T) {
--	router := CurlyRouter{}
--	for i, each := range routeMatchers {
--		routeToks := tokenizePath(each.route)
--		reqToks := tokenizePath(each.path)
--		matches, pCount, sCount := router.matchesRouteByPathTokens(routeToks, reqToks)
--		if matches != each.matches {
--			t.Fatalf("[%d] unexpected matches outcome route:%s, path:%s, matches:%v", i, each.route, each.path, matches)
--		}
--		if pCount != each.paramCount {
--			t.Fatalf("[%d] unexpected paramCount got:%d want:%d ", i, pCount, each.paramCount)
--		}
--		if sCount != each.staticCount {
--			t.Fatalf("[%d] unexpected staticCount got:%d want:%d ", i, sCount, each.staticCount)
--		}
+-// DescribeRouteTables
+-//
+-// http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeRouteTables.html
+-func (ec2 *EC2) DescribeRouteTables(ids []string, filter *Filter) (resp *RouteTablesResp, err error) {
+-	params := makeParams("DescribeRouteTables")
+-	addParamsList(params, "RouteTableId", ids)
+-	filter.addParams(params)
+-
+-	resp = &RouteTablesResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
+-
+-	return
 -}
 -
--// clear && go test -v -test.run TestExtractParameters_Wildcard1 ...restful
--func TestExtractParameters_Wildcard1(t *testing.T) {
--	params := doExtractParams("/fixed/{var:*}", 2, "/fixed/remainder", t)
--	if params["var"] != "remainder" {
--		t.Errorf("parameter mismatch var: %s", params["var"])
+-// Associate a routing table.
+-func (ec2 *EC2) AssociateRouteTable(id, subnetId string) (*AssociateRouteTableResp, error) {
+-	params := makeParams("AssociateRouteTable")
+-	params["RouteTableId"] = id
+-	params["SubnetId"] = subnetId
+-
+-	resp := &AssociateRouteTableResp{}
+-	err := ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
+-	return resp, nil
 -}
 -
--// clear && go test -v -test.run TestExtractParameters_Wildcard2 ...restful
--func TestExtractParameters_Wildcard2(t *testing.T) {
--	params := doExtractParams("/fixed/{var:*}", 2, "/fixed/remain/der", t)
--	if params["var"] != "remain/der" {
--		t.Errorf("parameter mismatch var: %s", params["var"])
+-// Disassociate a routing table.
+-func (ec2 *EC2) DisassociateRouteTable(id string) (*SimpleResp, error) {
+-	params := makeParams("DisassociateRouteTable")
+-	params["AssociationId"] = id
+-
+-	resp := &SimpleResp{}
+-	err := ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
+-	return resp, nil
 -}
 -
--// clear && go test -v -test.run TestExtractParameters_Wildcard3 ...restful
--func TestExtractParameters_Wildcard3(t *testing.T) {
--	params := doExtractParams("/static/{var:*}", 2, "/static/test/sub/hi.html", t)
--	if params["var"] != "test/sub/hi.html" {
--		t.Errorf("parameter mismatch var: %s", params["var"])
+-// Re-associate a routing table.
+-func (ec2 *EC2) ReassociateRouteTable(id, routeTableId string) (*ReassociateRouteTableResp, error) {
+-	params := makeParams("ReplaceRouteTableAssociation")
+-	params["AssociationId"] = id
+-	params["RouteTableId"] = routeTableId
+-
+-	resp := &ReassociateRouteTableResp{}
+-	err := ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
+-	return resp, nil
 -}
 -
--// clear && go test -v -test.run TestCurly_ISSUE_34 ...restful
--func TestCurly_ISSUE_34(t *testing.T) {
--	ws1 := new(WebService).Path("/")
--	ws1.Route(ws1.GET("/{type}/{id}").To(curlyDummy))
--	ws1.Route(ws1.GET("/network/{id}").To(curlyDummy))
--	routes := CurlyRouter{}.selectRoutes(ws1, tokenizePath("/network/12"))
--	if len(routes) != 2 {
--		t.Fatal("expected 2 routes")
+-// Create a new route.
+-func (ec2 *EC2) CreateRoute(options *CreateRoute) (resp *SimpleResp, err error) {
+-	params := makeParams("CreateRoute")
+-	params["RouteTableId"] = options.RouteTableId
+-	params["DestinationCidrBlock"] = options.DestinationCidrBlock
+-
+-	if v := options.GatewayId; v != "" {
+-		params["GatewayId"] = v
 -	}
--	if routes[0].Path != "/network/{id}" {
--		t.Error("first is", routes[0].Path)
+-	if v := options.InstanceId; v != "" {
+-		params["InstanceId"] = v
+-	}
+-	if v := options.NetworkInterfaceId; v != "" {
+-		params["NetworkInterfaceId"] = v
+-	}
+-	if v := options.VpcPeeringConnectionId; v != "" {
+-		params["VpcPeeringConnectionId"] = v
 -	}
--}
 -
--// clear && go test -v -test.run TestCurly_ISSUE_34_2 ...restful
--func TestCurly_ISSUE_34_2(t *testing.T) {
--	ws1 := new(WebService)
--	ws1.Route(ws1.GET("/network/{id}").To(curlyDummy))
--	ws1.Route(ws1.GET("/{type}/{id}").To(curlyDummy))
--	routes := CurlyRouter{}.selectRoutes(ws1, tokenizePath("/network/12"))
--	if len(routes) != 2 {
--		t.Fatal("expected 2 routes")
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
--	if routes[0].Path != "/network/{id}" {
--		t.Error("first is", routes[0].Path)
+-	return
+-}
+-
+-// Delete a Route.
+-func (ec2 *EC2) DeleteRoute(routeTableId, cidr string) (resp *SimpleResp, err error) {
+-	params := makeParams("DeleteRoute")
+-	params["RouteTableId"] = routeTableId
+-	params["DestinationCidrBlock"] = cidr
+-
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
+-	return
 -}
 -
--// clear && go test -v -test.run TestCurly_JsonHtml ...restful
--func TestCurly_JsonHtml(t *testing.T) {
--	ws1 := new(WebService)
--	ws1.Path("/")
--	ws1.Route(ws1.GET("/some.html").To(curlyDummy).Consumes("*/*").Produces("text/html"))
--	req, _ := http.NewRequest("GET", "/some.html", nil)
--	req.Header.Set("Accept", "application/json")
--	_, route, err := CurlyRouter{}.SelectRoute([]*WebService{ws1}, req)
--	if err == nil {
--		t.Error("error expected")
+-// Replace a new route.
+-func (ec2 *EC2) ReplaceRoute(options *ReplaceRoute) (resp *SimpleResp, err error) {
+-	params := makeParams("ReplaceRoute")
+-	params["RouteTableId"] = options.RouteTableId
+-	params["DestinationCidrBlock"] = options.DestinationCidrBlock
+-
+-	if v := options.GatewayId; v != "" {
+-		params["GatewayId"] = v
 -	}
--	if route != nil {
--		t.Error("no route expected")
+-	if v := options.InstanceId; v != "" {
+-		params["InstanceId"] = v
+-	}
+-	if v := options.NetworkInterfaceId; v != "" {
+-		params["NetworkInterfaceId"] = v
+-	}
+-	if v := options.VpcPeeringConnectionId; v != "" {
+-		params["VpcPeeringConnectionId"] = v
 -	}
--}
 -
--// go test -v -test.run TestCurly_ISSUE_137 ...restful
--func TestCurly_ISSUE_137(t *testing.T) {
--	ws1 := new(WebService)
--	ws1.Route(ws1.GET("/hello").To(curlyDummy))
--	ws1.Path("/")
--	req, _ := http.NewRequest("GET", "/", nil)
--	_, route, _ := CurlyRouter{}.SelectRoute([]*WebService{ws1}, req)
--	t.Log(route)
--	if route != nil {
--		t.Error("no route expected")
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
 -	}
+-	return
 -}
 -
--// go test -v -test.run TestCurly_ISSUE_137_2 ...restful
--func TestCurly_ISSUE_137_2(t *testing.T) {
--	ws1 := new(WebService)
--	ws1.Route(ws1.GET("/hello").To(curlyDummy))
--	ws1.Path("/")
--	req, _ := http.NewRequest("GET", "/hello/bob", nil)
--	_, route, _ := CurlyRouter{}.SelectRoute([]*WebService{ws1}, req)
--	t.Log(route)
--	if route != nil {
--		t.Errorf("no route expected, got %v", route)
--	}
+-// The ResetImageAttribute request parameters.
+-type ResetImageAttribute struct {
+-	Attribute string
 -}
 -
--func curlyDummy(req *Request, resp *Response) { io.WriteString(resp.ResponseWriter, "curlyDummy") }
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/doc.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/doc.go
+-// ResetImageAttribute resets an attribute of an AMI to its default value.
+-//
+-// http://goo.gl/r6ZCPm for more details.
+-func (ec2 *EC2) ResetImageAttribute(imageId string, options *ResetImageAttribute) (resp *SimpleResp, err error) {
+-	params := makeParams("ResetImageAttribute")
+-	params["ImageId"] = imageId
+-
+-	if options.Attribute != "" {
+-		params["Attribute"] = options.Attribute
+-	}
+-
+-	resp = &SimpleResp{}
+-	err = ec2.query(params, resp)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return
+-}
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2_test.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2_test.go
 deleted file mode 100644
-index c095566..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/doc.go
+index 849bfe2..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2_test.go
 +++ /dev/null
-@@ -1,184 +0,0 @@
--/*
--Package restful, a lean package for creating REST-style WebServices without magic.
+@@ -1,1243 +0,0 @@
+-package ec2_test
 -
--WebServices and Routes
+-import (
+-	"testing"
 -
--A WebService has a collection of Route objects that dispatch incoming Http Requests to a function calls.
--Typically, a WebService has a root path (e.g. /users) and defines common MIME types for its routes.
--WebServices must be added to a container (see below) in order to handler Http requests from a server.
+-	"github.com/mitchellh/goamz/aws"
+-	"github.com/mitchellh/goamz/ec2"
+-	"github.com/mitchellh/goamz/testutil"
+-	. "github.com/motain/gocheck"
+-)
 -
--A Route is defined by a HTTP method, an URL path and (optionally) the MIME types it consumes (Content-Type) and produces (Accept).
--This package has the logic to find the best matching Route and if found, call its Function.
+-func Test(t *testing.T) {
+-	TestingT(t)
+-}
 -
--	ws := new(restful.WebService)
--	ws.
--		Path("/users").
--		Consumes(restful.MIME_JSON, restful.MIME_XML).
--		Produces(restful.MIME_JSON, restful.MIME_XML)
+-var _ = Suite(&S{})
 -
--	ws.Route(ws.GET("/{user-id}").To(u.findUser))  // u is a UserResource
+-type S struct {
+-	ec2 *ec2.EC2
+-}
 -
--	...
+-var testServer = testutil.NewHTTPServer()
 -
--	// GET http://localhost:8080/users/1
--	func (u UserResource) findUser(request *restful.Request, response *restful.Response) {
--		id := request.PathParameter("user-id")
--		...
+-func (s *S) SetUpSuite(c *C) {
+-	testServer.Start()
+-	auth := aws.Auth{"abc", "123", ""}
+-	s.ec2 = ec2.NewWithClient(
+-		auth,
+-		aws.Region{EC2Endpoint: testServer.URL},
+-		testutil.DefaultClient,
+-	)
+-}
+-
+-func (s *S) TearDownTest(c *C) {
+-	testServer.Flush()
+-}
+-
+-func (s *S) TestRunInstancesErrorDump(c *C) {
+-	testServer.Response(400, nil, ErrorDump)
+-
+-	options := ec2.RunInstances{
+-		ImageId:      "ami-a6f504cf", // Ubuntu Maverick, i386, instance store
+-		InstanceType: "t1.micro",     // Doesn't work with micro, results in 400.
 -	}
 -
--The (*Request, *Response) arguments provide functions for reading information from the request and writing information back to the response.
+-	msg := `AMIs with an instance-store root device are not supported for the instance type 't1\.micro'\.`
 -
--See the example https://github.com/emicklei/go-restful/blob/master/examples/restful-user-resource.go with a full implementation.
+-	resp, err := s.ec2.RunInstances(&options)
 -
--Regular expression matching Routes
+-	testServer.WaitRequest()
 -
--A Route parameter can be specified using the format "uri/{var[:regexp]}" or the special version "uri/{var:*}" for matching the tail of the path.
--For example, /persons/{name:[A-Z][A-Z]} can be used to restrict values for the parameter "name" to only contain capital alphabetic characters.
--Regular expressions must use the standard Go syntax as described in the regexp package. (https://code.google.com/p/re2/wiki/Syntax)
--This feature requires the use of a CurlyRouter.
+-	c.Assert(resp, IsNil)
+-	c.Assert(err, ErrorMatches, msg+` \(UnsupportedOperation\)`)
 -
--Containers
+-	ec2err, ok := err.(*ec2.Error)
+-	c.Assert(ok, Equals, true)
+-	c.Assert(ec2err.StatusCode, Equals, 400)
+-	c.Assert(ec2err.Code, Equals, "UnsupportedOperation")
+-	c.Assert(ec2err.Message, Matches, msg)
+-	c.Assert(ec2err.RequestId, Equals, "0503f4e9-bbd6-483c-b54f-c4ae9f3b30f4")
+-}
 -
--A Container holds a collection of WebServices, Filters and a http.ServeMux for multiplexing http requests.
--Using the statements "restful.Add(...) and restful.Filter(...)" will register WebServices and Filters to the Default Container.
--The Default container of go-restful uses the http.DefaultServeMux.
--You can create your own Container and create a new http.Server for that particular container.
+-func (s *S) TestRequestSpotInstancesErrorDump(c *C) {
+-	testServer.Response(400, nil, ErrorDump)
 -
--	container := restful.NewContainer()
--	server := &http.Server{Addr: ":8081", Handler: container}
+-	options := ec2.RequestSpotInstances{
+-		SpotPrice:    "0.01",
+-		ImageId:      "ami-a6f504cf", // Ubuntu Maverick, i386, instance store
+-		InstanceType: "t1.micro",     // Doesn't work with micro, results in 400.
+-	}
 -
--Filters
+-	msg := `AMIs with an instance-store root device are not supported for the instance type 't1\.micro'\.`
 -
--A filter dynamically intercepts requests and responses to transform or use the information contained in the requests or responses.
--You can use filters to perform generic logging, measurement, authentication, redirect, set response headers etc.
--In the restful package there are three hooks into the request,response flow where filters can be added.
--Each filter must define a FilterFunction:
+-	resp, err := s.ec2.RequestSpotInstances(&options)
 -
--	func (req *restful.Request, resp *restful.Response, chain *restful.FilterChain)
+-	testServer.WaitRequest()
 -
--Use the following statement to pass the request,response pair to the next filter or RouteFunction
+-	c.Assert(resp, IsNil)
+-	c.Assert(err, ErrorMatches, msg+` \(UnsupportedOperation\)`)
 -
--	chain.ProcessFilter(req, resp)
+-	ec2err, ok := err.(*ec2.Error)
+-	c.Assert(ok, Equals, true)
+-	c.Assert(ec2err.StatusCode, Equals, 400)
+-	c.Assert(ec2err.Code, Equals, "UnsupportedOperation")
+-	c.Assert(ec2err.Message, Matches, msg)
+-	c.Assert(ec2err.RequestId, Equals, "0503f4e9-bbd6-483c-b54f-c4ae9f3b30f4")
+-}
 -
--Container Filters
+-func (s *S) TestRunInstancesErrorWithoutXML(c *C) {
+-	testServer.Responses(5, 500, nil, "")
+-	options := ec2.RunInstances{ImageId: "image-id"}
 -
--These are processed before any registered WebService.
+-	resp, err := s.ec2.RunInstances(&options)
 -
--	// install a (global) filter for the default container (processed before any webservice)
--	restful.Filter(globalLogging)
+-	testServer.WaitRequest()
 -
--WebService Filters
+-	c.Assert(resp, IsNil)
+-	c.Assert(err, ErrorMatches, "500 Internal Server Error")
 -
--These are processed before any Route of a WebService.
+-	ec2err, ok := err.(*ec2.Error)
+-	c.Assert(ok, Equals, true)
+-	c.Assert(ec2err.StatusCode, Equals, 500)
+-	c.Assert(ec2err.Code, Equals, "")
+-	c.Assert(ec2err.Message, Equals, "500 Internal Server Error")
+-	c.Assert(ec2err.RequestId, Equals, "")
+-}
 -
--	// install a webservice filter (processed before any route)
--	ws.Filter(webserviceLogging).Filter(measureTime)
+-func (s *S) TestRequestSpotInstancesErrorWithoutXML(c *C) {
+-	testServer.Responses(5, 500, nil, "")
+-	options := ec2.RequestSpotInstances{SpotPrice: "spot-price", ImageId: "image-id"}
 -
+-	resp, err := s.ec2.RequestSpotInstances(&options)
 -
--Route Filters
+-	testServer.WaitRequest()
 -
--These are processed before calling the function associated with the Route.
+-	c.Assert(resp, IsNil)
+-	c.Assert(err, ErrorMatches, "500 Internal Server Error")
 -
--	// install 2 chained route filters (processed before calling findUser)
--	ws.Route(ws.GET("/{user-id}").Filter(routeLogging).Filter(NewCountFilter().routeCounter).To(findUser))
+-	ec2err, ok := err.(*ec2.Error)
+-	c.Assert(ok, Equals, true)
+-	c.Assert(ec2err.StatusCode, Equals, 500)
+-	c.Assert(ec2err.Code, Equals, "")
+-	c.Assert(ec2err.Message, Equals, "500 Internal Server Error")
+-	c.Assert(ec2err.RequestId, Equals, "")
+-}
 -
--See the example https://github.com/emicklei/go-restful/blob/master/examples/restful-filters.go with full implementations.
+-func (s *S) TestRunInstancesExample(c *C) {
+-	testServer.Response(200, nil, RunInstancesExample)
 -
--Response Encoding
+-	options := ec2.RunInstances{
+-		KeyName:               "my-keys",
+-		ImageId:               "image-id",
+-		InstanceType:          "inst-type",
+-		SecurityGroups:        []ec2.SecurityGroup{{Name: "g1"}, {Id: "g2"}, {Name: "g3"}, {Id: "g4"}},
+-		UserData:              []byte("1234"),
+-		KernelId:              "kernel-id",
+-		RamdiskId:             "ramdisk-id",
+-		AvailZone:             "zone",
+-		PlacementGroupName:    "group",
+-		Monitoring:            true,
+-		SubnetId:              "subnet-id",
+-		DisableAPITermination: true,
+-		ShutdownBehavior:      "terminate",
+-		PrivateIPAddress:      "10.0.0.25",
+-		BlockDevices: []ec2.BlockDeviceMapping{
+-			{DeviceName: "/dev/sdb", VirtualName: "ephemeral0"},
+-			{DeviceName: "/dev/sdc", SnapshotId: "snap-a08912c9", DeleteOnTermination: true},
+-		},
+-	}
+-	resp, err := s.ec2.RunInstances(&options)
 -
--Two encodings are supported: gzip and deflate. To enable this for all responses:
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"RunInstances"})
+-	c.Assert(req.Form["ImageId"], DeepEquals, []string{"image-id"})
+-	c.Assert(req.Form["MinCount"], DeepEquals, []string{"1"})
+-	c.Assert(req.Form["MaxCount"], DeepEquals, []string{"1"})
+-	c.Assert(req.Form["KeyName"], DeepEquals, []string{"my-keys"})
+-	c.Assert(req.Form["InstanceType"], DeepEquals, []string{"inst-type"})
+-	c.Assert(req.Form["SecurityGroup.1"], DeepEquals, []string{"g1"})
+-	c.Assert(req.Form["SecurityGroup.2"], DeepEquals, []string{"g3"})
+-	c.Assert(req.Form["SecurityGroupId.1"], DeepEquals, []string{"g2"})
+-	c.Assert(req.Form["SecurityGroupId.2"], DeepEquals, []string{"g4"})
+-	c.Assert(req.Form["UserData"], DeepEquals, []string{"MTIzNA=="})
+-	c.Assert(req.Form["KernelId"], DeepEquals, []string{"kernel-id"})
+-	c.Assert(req.Form["RamdiskId"], DeepEquals, []string{"ramdisk-id"})
+-	c.Assert(req.Form["Placement.AvailabilityZone"], DeepEquals, []string{"zone"})
+-	c.Assert(req.Form["Placement.GroupName"], DeepEquals, []string{"group"})
+-	c.Assert(req.Form["Monitoring.Enabled"], DeepEquals, []string{"true"})
+-	c.Assert(req.Form["SubnetId"], DeepEquals, []string{"subnet-id"})
+-	c.Assert(req.Form["DisableApiTermination"], DeepEquals, []string{"true"})
+-	c.Assert(req.Form["InstanceInitiatedShutdownBehavior"], DeepEquals, []string{"terminate"})
+-	c.Assert(req.Form["PrivateIpAddress"], DeepEquals, []string{"10.0.0.25"})
+-	c.Assert(req.Form["BlockDeviceMapping.1.DeviceName"], DeepEquals, []string{"/dev/sdb"})
+-	c.Assert(req.Form["BlockDeviceMapping.1.VirtualName"], DeepEquals, []string{"ephemeral0"})
+-	c.Assert(req.Form["BlockDeviceMapping.2.Ebs.SnapshotId"], DeepEquals, []string{"snap-a08912c9"})
+-	c.Assert(req.Form["BlockDeviceMapping.2.Ebs.DeleteOnTermination"], DeepEquals, []string{"true"})
 -
--	restful.DefaultContainer.EnableContentEncoding(true)
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	c.Assert(resp.ReservationId, Equals, "r-47a5402e")
+-	c.Assert(resp.OwnerId, Equals, "999988887777")
+-	c.Assert(resp.SecurityGroups, DeepEquals, []ec2.SecurityGroup{{Name: "default", Id: "sg-67ad940e"}})
+-	c.Assert(resp.Instances, HasLen, 3)
 -
--If a Http request includes the Accept-Encoding header then the response content will be compressed using the specified encoding.
--Alternatively, you can create a Filter that performs the encoding and install it per WebService or Route.
+-	i0 := resp.Instances[0]
+-	c.Assert(i0.InstanceId, Equals, "i-2ba64342")
+-	c.Assert(i0.InstanceType, Equals, "m1.small")
+-	c.Assert(i0.ImageId, Equals, "ami-60a54009")
+-	c.Assert(i0.Monitoring, Equals, "enabled")
+-	c.Assert(i0.KeyName, Equals, "example-key-name")
+-	c.Assert(i0.AMILaunchIndex, Equals, 0)
+-	c.Assert(i0.VirtType, Equals, "paravirtual")
+-	c.Assert(i0.Hypervisor, Equals, "xen")
 -
--See the example https://github.com/emicklei/go-restful/blob/master/examples/restful-encoding-filter.go
+-	i1 := resp.Instances[1]
+-	c.Assert(i1.InstanceId, Equals, "i-2bc64242")
+-	c.Assert(i1.InstanceType, Equals, "m1.small")
+-	c.Assert(i1.ImageId, Equals, "ami-60a54009")
+-	c.Assert(i1.Monitoring, Equals, "enabled")
+-	c.Assert(i1.KeyName, Equals, "example-key-name")
+-	c.Assert(i1.AMILaunchIndex, Equals, 1)
+-	c.Assert(i1.VirtType, Equals, "paravirtual")
+-	c.Assert(i1.Hypervisor, Equals, "xen")
 -
--OPTIONS support
+-	i2 := resp.Instances[2]
+-	c.Assert(i2.InstanceId, Equals, "i-2be64332")
+-	c.Assert(i2.InstanceType, Equals, "m1.small")
+-	c.Assert(i2.ImageId, Equals, "ami-60a54009")
+-	c.Assert(i2.Monitoring, Equals, "enabled")
+-	c.Assert(i2.KeyName, Equals, "example-key-name")
+-	c.Assert(i2.AMILaunchIndex, Equals, 2)
+-	c.Assert(i2.VirtType, Equals, "paravirtual")
+-	c.Assert(i2.Hypervisor, Equals, "xen")
+-}
 -
--By installing a pre-defined container filter, your Webservice(s) can respond to the OPTIONS Http request.
+-func (s *S) TestRequestSpotInstancesExample(c *C) {
+-	testServer.Response(200, nil, RequestSpotInstancesExample)
 -
--	Filter(OPTIONSFilter())
+-	options := ec2.RequestSpotInstances{
+-		SpotPrice:          "0.5",
+-		KeyName:            "my-keys",
+-		ImageId:            "image-id",
+-		InstanceType:       "inst-type",
+-		SecurityGroups:     []ec2.SecurityGroup{{Name: "g1"}, {Id: "g2"}, {Name: "g3"}, {Id: "g4"}},
+-		UserData:           []byte("1234"),
+-		KernelId:           "kernel-id",
+-		RamdiskId:          "ramdisk-id",
+-		AvailZone:          "zone",
+-		PlacementGroupName: "group",
+-		Monitoring:         true,
+-		SubnetId:           "subnet-id",
+-		PrivateIPAddress:   "10.0.0.25",
+-		BlockDevices: []ec2.BlockDeviceMapping{
+-			{DeviceName: "/dev/sdb", VirtualName: "ephemeral0"},
+-			{DeviceName: "/dev/sdc", SnapshotId: "snap-a08912c9", DeleteOnTermination: true},
+-		},
+-	}
+-	resp, err := s.ec2.RequestSpotInstances(&options)
 -
--CORS
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"RequestSpotInstances"})
+-	c.Assert(req.Form["SpotPrice"], DeepEquals, []string{"0.5"})
+-	c.Assert(req.Form["LaunchSpecification.ImageId"], DeepEquals, []string{"image-id"})
+-	c.Assert(req.Form["LaunchSpecification.KeyName"], DeepEquals, []string{"my-keys"})
+-	c.Assert(req.Form["LaunchSpecification.InstanceType"], DeepEquals, []string{"inst-type"})
+-	c.Assert(req.Form["LaunchSpecification.SecurityGroup.1"], DeepEquals, []string{"g1"})
+-	c.Assert(req.Form["LaunchSpecification.SecurityGroup.2"], DeepEquals, []string{"g3"})
+-	c.Assert(req.Form["LaunchSpecification.SecurityGroupId.1"], DeepEquals, []string{"g2"})
+-	c.Assert(req.Form["LaunchSpecification.SecurityGroupId.2"], DeepEquals, []string{"g4"})
+-	c.Assert(req.Form["LaunchSpecification.UserData"], DeepEquals, []string{"MTIzNA=="})
+-	c.Assert(req.Form["LaunchSpecification.KernelId"], DeepEquals, []string{"kernel-id"})
+-	c.Assert(req.Form["LaunchSpecification.RamdiskId"], DeepEquals, []string{"ramdisk-id"})
+-	c.Assert(req.Form["LaunchSpecification.Placement.AvailabilityZone"], DeepEquals, []string{"zone"})
+-	c.Assert(req.Form["LaunchSpecification.Placement.GroupName"], DeepEquals, []string{"group"})
+-	c.Assert(req.Form["LaunchSpecification.Monitoring.Enabled"], DeepEquals, []string{"true"})
+-	c.Assert(req.Form["LaunchSpecification.SubnetId"], DeepEquals, []string{"subnet-id"})
+-	c.Assert(req.Form["LaunchSpecification.PrivateIpAddress"], DeepEquals, []string{"10.0.0.25"})
+-	c.Assert(req.Form["LaunchSpecification.BlockDeviceMapping.1.DeviceName"], DeepEquals, []string{"/dev/sdb"})
+-	c.Assert(req.Form["LaunchSpecification.BlockDeviceMapping.1.VirtualName"], DeepEquals, []string{"ephemeral0"})
+-	c.Assert(req.Form["LaunchSpecification.BlockDeviceMapping.2.Ebs.SnapshotId"], DeepEquals, []string{"snap-a08912c9"})
+-	c.Assert(req.Form["LaunchSpecification.BlockDeviceMapping.2.Ebs.DeleteOnTermination"], DeepEquals, []string{"true"})
 -
--By installing the filter of a CrossOriginResourceSharing (CORS), your WebService(s) can handle CORS requests.
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	c.Assert(resp.SpotRequestResults[0].SpotRequestId, Equals, "sir-1a2b3c4d")
+-	c.Assert(resp.SpotRequestResults[0].SpotPrice, Equals, "0.5")
+-	c.Assert(resp.SpotRequestResults[0].State, Equals, "open")
+-	c.Assert(resp.SpotRequestResults[0].SpotLaunchSpec.ImageId, Equals, "ami-1a2b3c4d")
+-	c.Assert(resp.SpotRequestResults[0].Status.Code, Equals, "pending-evaluation")
+-	c.Assert(resp.SpotRequestResults[0].Status.UpdateTime, Equals, "2008-05-07T12:51:50.000Z")
+-	c.Assert(resp.SpotRequestResults[0].Status.Message, Equals, "Your Spot request has been submitted for review, and is pending evaluation.")
+-}
 -
--	cors := CrossOriginResourceSharing{ExposeHeaders: []string{"X-My-Header"}, CookiesAllowed: false, Container: DefaultContainer}
--	Filter(cors.Filter)
+-func (s *S) TestCancelSpotRequestsExample(c *C) {
+-	testServer.Response(200, nil, CancelSpotRequestsExample)
 -
--Error Handling
+-	resp, err := s.ec2.CancelSpotRequests([]string{"s-1", "s-2"})
 -
--Unexpected things happen. If a request cannot be processed because of a failure, your service needs to tell via the response what happened and why.
--For this reason HTTP status codes exist and it is important to use the correct code in every exceptional situation.
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"CancelSpotInstanceRequests"})
+-	c.Assert(req.Form["SpotInstanceRequestId.1"], DeepEquals, []string{"s-1"})
+-	c.Assert(req.Form["SpotInstanceRequestId.2"], DeepEquals, []string{"s-2"})
 -
--	400: Bad Request
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	c.Assert(resp.CancelSpotRequestResults[0].SpotRequestId, Equals, "sir-1a2b3c4d")
+-	c.Assert(resp.CancelSpotRequestResults[0].State, Equals, "cancelled")
+-}
 -
--If path or query parameters are not valid (content or type) then use http.StatusBadRequest.
+-func (s *S) TestTerminateInstancesExample(c *C) {
+-	testServer.Response(200, nil, TerminateInstancesExample)
 -
--	404: Not Found
+-	resp, err := s.ec2.TerminateInstances([]string{"i-1", "i-2"})
 -
--Despite a valid URI, the resource requested may not be available
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"TerminateInstances"})
+-	c.Assert(req.Form["InstanceId.1"], DeepEquals, []string{"i-1"})
+-	c.Assert(req.Form["InstanceId.2"], DeepEquals, []string{"i-2"})
+-	c.Assert(req.Form["UserData"], IsNil)
+-	c.Assert(req.Form["KernelId"], IsNil)
+-	c.Assert(req.Form["RamdiskId"], IsNil)
+-	c.Assert(req.Form["Placement.AvailabilityZone"], IsNil)
+-	c.Assert(req.Form["Placement.GroupName"], IsNil)
+-	c.Assert(req.Form["Monitoring.Enabled"], IsNil)
+-	c.Assert(req.Form["SubnetId"], IsNil)
+-	c.Assert(req.Form["DisableApiTermination"], IsNil)
+-	c.Assert(req.Form["InstanceInitiatedShutdownBehavior"], IsNil)
+-	c.Assert(req.Form["PrivateIpAddress"], IsNil)
 -
--	500: Internal Server Error
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	c.Assert(resp.StateChanges, HasLen, 1)
+-	c.Assert(resp.StateChanges[0].InstanceId, Equals, "i-3ea74257")
+-	c.Assert(resp.StateChanges[0].CurrentState.Code, Equals, 32)
+-	c.Assert(resp.StateChanges[0].CurrentState.Name, Equals, "shutting-down")
+-	c.Assert(resp.StateChanges[0].PreviousState.Code, Equals, 16)
+-	c.Assert(resp.StateChanges[0].PreviousState.Name, Equals, "running")
+-}
 -
--If the application logic could not process the request (or write the response) then use http.StatusInternalServerError.
+-func (s *S) TestDescribeSpotRequestsExample(c *C) {
+-	testServer.Response(200, nil, DescribeSpotRequestsExample)
 -
--	405: Method Not Allowed
+-	filter := ec2.NewFilter()
+-	filter.Add("key1", "value1")
+-	filter.Add("key2", "value2", "value3")
 -
--The request has a valid URL but the method (GET,PUT,POST,...) is not allowed.
+-	resp, err := s.ec2.DescribeSpotRequests([]string{"s-1", "s-2"}, filter)
 -
--	406: Not Acceptable
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeSpotInstanceRequests"})
+-	c.Assert(req.Form["SpotInstanceRequestId.1"], DeepEquals, []string{"s-1"})
+-	c.Assert(req.Form["SpotInstanceRequestId.2"], DeepEquals, []string{"s-2"})
 -
--The request does not have or has an unknown Accept Header set for this operation.
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "b1719f2a-5334-4479-b2f1-26926EXAMPLE")
+-	c.Assert(resp.SpotRequestResults[0].SpotRequestId, Equals, "sir-1a2b3c4d")
+-	c.Assert(resp.SpotRequestResults[0].State, Equals, "active")
+-	c.Assert(resp.SpotRequestResults[0].SpotPrice, Equals, "0.5")
+-	c.Assert(resp.SpotRequestResults[0].SpotLaunchSpec.ImageId, Equals, "ami-1a2b3c4d")
+-	c.Assert(resp.SpotRequestResults[0].Status.Code, Equals, "fulfilled")
+-	c.Assert(resp.SpotRequestResults[0].Status.UpdateTime, Equals, "2008-05-07T12:51:50.000Z")
+-	c.Assert(resp.SpotRequestResults[0].Status.Message, Equals, "Your Spot request is fulfilled.")
+-}
 -
--	415: Unsupported Media Type
+-func (s *S) TestDescribeInstancesExample1(c *C) {
+-	testServer.Response(200, nil, DescribeInstancesExample1)
 -
--The request does not have or has an unknown Content-Type Header set for this operation.
+-	filter := ec2.NewFilter()
+-	filter.Add("key1", "value1")
+-	filter.Add("key2", "value2", "value3")
 -
--ServiceError
+-	resp, err := s.ec2.Instances([]string{"i-1", "i-2"}, nil)
 -
--In addition to setting the correct (error) Http status code, you can choose to write a ServiceError message on the response.
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeInstances"})
+-	c.Assert(req.Form["InstanceId.1"], DeepEquals, []string{"i-1"})
+-	c.Assert(req.Form["InstanceId.2"], DeepEquals, []string{"i-2"})
 -
--Performance options
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "98e3c9a4-848c-4d6d-8e8a-b1bdEXAMPLE")
+-	c.Assert(resp.Reservations, HasLen, 2)
 -
--This package has several options that affect the performance of your service. It is important to understand them and how you can change it.
+-	r0 := resp.Reservations[0]
+-	c.Assert(r0.ReservationId, Equals, "r-b27e30d9")
+-	c.Assert(r0.OwnerId, Equals, "999988887777")
+-	c.Assert(r0.RequesterId, Equals, "854251627541")
+-	c.Assert(r0.SecurityGroups, DeepEquals, []ec2.SecurityGroup{{Name: "default", Id: "sg-67ad940e"}})
+-	c.Assert(r0.Instances, HasLen, 1)
 -
--	restful.DefaultContainer.Router(CurlyRouter{})
+-	r0i := r0.Instances[0]
+-	c.Assert(r0i.InstanceId, Equals, "i-c5cd56af")
+-	c.Assert(r0i.PrivateDNSName, Equals, "domU-12-31-39-10-56-34.compute-1.internal")
+-	c.Assert(r0i.DNSName, Equals, "ec2-174-129-165-232.compute-1.amazonaws.com")
+-	c.Assert(r0i.AvailZone, Equals, "us-east-1b")
+-}
 -
--The default router is the RouterJSR311 which is an implementation of its spec (http://jsr311.java.net/nonav/releases/1.1/spec/spec.html).
--However, it uses regular expressions for all its routes which, depending on your usecase, may consume a significant amount of time.
--The CurlyRouter implementation is more lightweight that also allows you to use wildcards and expressions, but only if needed.
+-func (s *S) TestDescribeInstancesExample2(c *C) {
+-	testServer.Response(200, nil, DescribeInstancesExample2)
 -
--	restful.DefaultContainer.DoNotRecover(true)
+-	filter := ec2.NewFilter()
+-	filter.Add("key1", "value1")
+-	filter.Add("key2", "value2", "value3")
 -
--DoNotRecover controls whether panics will be caught to return HTTP 500.
--If set to true, Route functions are responsible for handling any error situation.
--Default value is false; it will recover from panics. This has performance implications.
+-	resp, err := s.ec2.Instances([]string{"i-1", "i-2"}, filter)
 -
--	restful.SetCacheReadEntity(false)
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeInstances"})
+-	c.Assert(req.Form["InstanceId.1"], DeepEquals, []string{"i-1"})
+-	c.Assert(req.Form["InstanceId.2"], DeepEquals, []string{"i-2"})
+-	c.Assert(req.Form["Filter.1.Name"], DeepEquals, []string{"key1"})
+-	c.Assert(req.Form["Filter.1.Value.1"], DeepEquals, []string{"value1"})
+-	c.Assert(req.Form["Filter.1.Value.2"], IsNil)
+-	c.Assert(req.Form["Filter.2.Name"], DeepEquals, []string{"key2"})
+-	c.Assert(req.Form["Filter.2.Value.1"], DeepEquals, []string{"value2"})
+-	c.Assert(req.Form["Filter.2.Value.2"], DeepEquals, []string{"value3"})
 -
--SetCacheReadEntity controls whether the response data ([]byte) is cached such that ReadEntity is repeatable.
--If you expect to read large amounts of payload data, and you do not use this feature, you should set it to false.
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	c.Assert(resp.Reservations, HasLen, 1)
 -
--Trouble shooting
+-	r0 := resp.Reservations[0]
+-	r0i := r0.Instances[0]
+-	c.Assert(r0i.State.Code, Equals, 16)
+-	c.Assert(r0i.State.Name, Equals, "running")
 -
--This package has the means to produce detail logging of the complete Http request matching process and filter invocation.
--Enabling this feature requires you to set a log.Logger instance such as:
+-	r0t0 := r0i.Tags[0]
+-	r0t1 := r0i.Tags[1]
+-	c.Assert(r0t0.Key, Equals, "webserver")
+-	c.Assert(r0t0.Value, Equals, "")
+-	c.Assert(r0t1.Key, Equals, "stack")
+-	c.Assert(r0t1.Value, Equals, "Production")
+-}
 -
--	restful.TraceLogger(log.New(os.Stdout, "[restful] ", log.LstdFlags|log.Lshortfile))
+-func (s *S) TestCreateImageExample(c *C) {
+-	testServer.Response(200, nil, CreateImageExample)
 -
--Resources
+-	options := &ec2.CreateImage{
+-		InstanceId:  "i-123456",
+-		Name:        "foo",
+-		Description: "Test CreateImage",
+-		NoReboot:    true,
+-		BlockDevices: []ec2.BlockDeviceMapping{
+-			{DeviceName: "/dev/sdb", VirtualName: "ephemeral0"},
+-			{DeviceName: "/dev/sdc", SnapshotId: "snap-a08912c9", DeleteOnTermination: true},
+-		},
+-	}
 -
--[project]: https://github.com/emicklei/go-restful
+-	resp, err := s.ec2.CreateImage(options)
 -
--[examples]: https://github.com/emicklei/go-restful/blob/master/examples
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"CreateImage"})
+-	c.Assert(req.Form["InstanceId"], DeepEquals, []string{options.InstanceId})
+-	c.Assert(req.Form["Name"], DeepEquals, []string{options.Name})
+-	c.Assert(req.Form["Description"], DeepEquals, []string{options.Description})
+-	c.Assert(req.Form["NoReboot"], DeepEquals, []string{"true"})
+-	c.Assert(req.Form["BlockDeviceMapping.1.DeviceName"], DeepEquals, []string{"/dev/sdb"})
+-	c.Assert(req.Form["BlockDeviceMapping.1.VirtualName"], DeepEquals, []string{"ephemeral0"})
+-	c.Assert(req.Form["BlockDeviceMapping.2.DeviceName"], DeepEquals, []string{"/dev/sdc"})
+-	c.Assert(req.Form["BlockDeviceMapping.2.Ebs.SnapshotId"], DeepEquals, []string{"snap-a08912c9"})
+-	c.Assert(req.Form["BlockDeviceMapping.2.Ebs.DeleteOnTermination"], DeepEquals, []string{"true"})
 -
--[design]:  http://ernestmicklei.com/2012/11/11/go-restful-api-design/
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	c.Assert(resp.ImageId, Equals, "ami-4fa54026")
+-}
 -
--[showcases]: https://github.com/emicklei/mora, https://github.com/emicklei/landskape
+-func (s *S) TestDescribeImagesExample(c *C) {
+-	testServer.Response(200, nil, DescribeImagesExample)
 -
--(c) 2012-2014, http://ernestmicklei.com. MIT License
--*/
--package restful
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/doc_examples_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/doc_examples_test.go
-deleted file mode 100644
-index e1a2f3b..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/doc_examples_test.go
-+++ /dev/null
-@@ -1,35 +0,0 @@
--package restful
+-	filter := ec2.NewFilter()
+-	filter.Add("key1", "value1")
+-	filter.Add("key2", "value2", "value3")
 -
--import "net/http"
+-	resp, err := s.ec2.Images([]string{"ami-1", "ami-2"}, filter)
 -
--func ExampleOPTIONSFilter() {
--	// Install the OPTIONS filter on the default Container
--	Filter(OPTIONSFilter())
--}
--func ExampleContainer_OPTIONSFilter() {
--	// Install the OPTIONS filter on a Container
--	myContainer := new(Container)
--	myContainer.Filter(myContainer.OPTIONSFilter)
--}
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeImages"})
+-	c.Assert(req.Form["ImageId.1"], DeepEquals, []string{"ami-1"})
+-	c.Assert(req.Form["ImageId.2"], DeepEquals, []string{"ami-2"})
+-	c.Assert(req.Form["Filter.1.Name"], DeepEquals, []string{"key1"})
+-	c.Assert(req.Form["Filter.1.Value.1"], DeepEquals, []string{"value1"})
+-	c.Assert(req.Form["Filter.1.Value.2"], IsNil)
+-	c.Assert(req.Form["Filter.2.Name"], DeepEquals, []string{"key2"})
+-	c.Assert(req.Form["Filter.2.Value.1"], DeepEquals, []string{"value2"})
+-	c.Assert(req.Form["Filter.2.Value.2"], DeepEquals, []string{"value3"})
 -
--func ExampleContainer() {
--	// The Default container of go-restful uses the http.DefaultServeMux.
--	// You can create your own Container using restful.NewContainer() and create a new http.Server for that particular container
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "4a4a27a2-2e7c-475d-b35b-ca822EXAMPLE")
+-	c.Assert(resp.Images, HasLen, 1)
 -
--	ws := new(WebService)
--	wsContainer := NewContainer()
--	wsContainer.Add(ws)
--	server := &http.Server{Addr: ":8080", Handler: wsContainer}
--	server.ListenAndServe()
--}
+-	i0 := resp.Images[0]
+-	c.Assert(i0.Id, Equals, "ami-a2469acf")
+-	c.Assert(i0.Type, Equals, "machine")
+-	c.Assert(i0.Name, Equals, "example-marketplace-amzn-ami.1")
+-	c.Assert(i0.Description, Equals, "Amazon Linux AMI i386 EBS")
+-	c.Assert(i0.Location, Equals, "aws-marketplace/example-marketplace-amzn-ami.1")
+-	c.Assert(i0.State, Equals, "available")
+-	c.Assert(i0.Public, Equals, true)
+-	c.Assert(i0.OwnerId, Equals, "123456789999")
+-	c.Assert(i0.OwnerAlias, Equals, "aws-marketplace")
+-	c.Assert(i0.Architecture, Equals, "i386")
+-	c.Assert(i0.KernelId, Equals, "aki-805ea7e9")
+-	c.Assert(i0.RootDeviceType, Equals, "ebs")
+-	c.Assert(i0.RootDeviceName, Equals, "/dev/sda1")
+-	c.Assert(i0.VirtualizationType, Equals, "paravirtual")
+-	c.Assert(i0.Hypervisor, Equals, "xen")
 -
--func ExampleCrossOriginResourceSharing() {
--	// To install this filter on the Default Container use:
--	cors := CrossOriginResourceSharing{ExposeHeaders: []string{"X-My-Header"}, CookiesAllowed: false, Container: DefaultContainer}
--	Filter(cors.Filter)
--}
+-	c.Assert(i0.BlockDevices, HasLen, 1)
+-	c.Assert(i0.BlockDevices[0].DeviceName, Equals, "/dev/sda1")
+-	c.Assert(i0.BlockDevices[0].SnapshotId, Equals, "snap-787e9403")
+-	c.Assert(i0.BlockDevices[0].VolumeSize, Equals, int64(8))
+-	c.Assert(i0.BlockDevices[0].DeleteOnTermination, Equals, true)
 -
--func ExampleServiceError() {
--	resp := new(Response)
--	resp.WriteEntity(NewError(http.StatusBadRequest, "Non-integer {id} path parameter"))
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/.goconvey b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/.goconvey
-deleted file mode 100644
-index 8485e98..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/.goconvey
-+++ /dev/null
-@@ -1 +0,0 @@
--ignore
-\ No newline at end of file
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/.goconvey b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/.goconvey
-deleted file mode 100644
-index 8485e98..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/.goconvey
-+++ /dev/null
-@@ -1 +0,0 @@
--ignore
-\ No newline at end of file
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/app.yaml b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/app.yaml
-deleted file mode 100644
-index 362db6b..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/app.yaml
-+++ /dev/null
-@@ -1,20 +0,0 @@
--#
--# Include your application ID here
--#
--application: <your_app_id>
--version: 1
--runtime: go
--api_version: go1
+-	testServer.Response(200, nil, DescribeImagesExample)
+-	resp2, err := s.ec2.ImagesByOwners([]string{"ami-1", "ami-2"}, []string{"123456789999", "id2"}, filter)
 -
--handlers:
--#
--# Regex for all swagger files to make as static content.
--# You should create the folder static/swagger and copy
--# swagger-ui into it.
--#
--- url: /apidocs/(.*?)/(.*\.(js|html|css))
--  static_files: static/swagger/\1/\2
--  upload: static/swagger/(.*?)/(.*\.(js|html|css))
+-	req2 := testServer.WaitRequest()
+-	c.Assert(req2.Form["Action"], DeepEquals, []string{"DescribeImages"})
+-	c.Assert(req2.Form["ImageId.1"], DeepEquals, []string{"ami-1"})
+-	c.Assert(req2.Form["ImageId.2"], DeepEquals, []string{"ami-2"})
+-	c.Assert(req2.Form["Owner.1"], DeepEquals, []string{"123456789999"})
+-	c.Assert(req2.Form["Owner.2"], DeepEquals, []string{"id2"})
+-	c.Assert(req2.Form["Filter.1.Name"], DeepEquals, []string{"key1"})
+-	c.Assert(req2.Form["Filter.1.Value.1"], DeepEquals, []string{"value1"})
+-	c.Assert(req2.Form["Filter.1.Value.2"], IsNil)
+-	c.Assert(req2.Form["Filter.2.Name"], DeepEquals, []string{"key2"})
+-	c.Assert(req2.Form["Filter.2.Value.1"], DeepEquals, []string{"value2"})
+-	c.Assert(req2.Form["Filter.2.Value.2"], DeepEquals, []string{"value3"})
 -
--- url: /.*
--  script: _go_app
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/datastore/.goconvey b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/datastore/.goconvey
-deleted file mode 100644
-index 8485e98..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/datastore/.goconvey
-+++ /dev/null
-@@ -1 +0,0 @@
--ignore
-\ No newline at end of file
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/datastore/app.yaml b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/datastore/app.yaml
-deleted file mode 100644
-index 33883d1..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/datastore/app.yaml
-+++ /dev/null
-@@ -1,18 +0,0 @@
--application: datastore-example
--version: 1
--runtime: go
--api_version: go1
+-	c.Assert(err, IsNil)
+-	c.Assert(resp2.RequestId, Equals, "4a4a27a2-2e7c-475d-b35b-ca822EXAMPLE")
+-	c.Assert(resp2.Images, HasLen, 1)
 -
--handlers:
--# Regex for all swagger files to make as static content.
--# You should create the folder static/swagger and copy
--# swagger-ui into it.
--#
--- url: /apidocs/(.*?)/(.*\.(js|html|css))
--  static_files: static/swagger/\1/\2
--  upload: static/swagger/(.*?)/(.*\.(js|html|css))
+-	i1 := resp2.Images[0]
+-	c.Assert(i1.Id, Equals, "ami-a2469acf")
+-	c.Assert(i1.Type, Equals, "machine")
+-	c.Assert(i1.Name, Equals, "example-marketplace-amzn-ami.1")
+-	c.Assert(i1.Description, Equals, "Amazon Linux AMI i386 EBS")
+-	c.Assert(i1.Location, Equals, "aws-marketplace/example-marketplace-amzn-ami.1")
+-	c.Assert(i1.State, Equals, "available")
+-	c.Assert(i1.Public, Equals, true)
+-	c.Assert(i1.OwnerId, Equals, "123456789999")
+-	c.Assert(i1.OwnerAlias, Equals, "aws-marketplace")
+-	c.Assert(i1.Architecture, Equals, "i386")
+-	c.Assert(i1.KernelId, Equals, "aki-805ea7e9")
+-	c.Assert(i1.RootDeviceType, Equals, "ebs")
+-	c.Assert(i1.RootDeviceName, Equals, "/dev/sda1")
+-	c.Assert(i1.VirtualizationType, Equals, "paravirtual")
+-	c.Assert(i1.Hypervisor, Equals, "xen")
 -
--# Catch all.
--- url: /.*
--  script: _go_app
--  login: required
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/datastore/main.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/datastore/main.go
-deleted file mode 100644
-index cf832ef..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/datastore/main.go
-+++ /dev/null
-@@ -1,266 +0,0 @@
--package main
+-	c.Assert(i1.BlockDevices, HasLen, 1)
+-	c.Assert(i1.BlockDevices[0].DeviceName, Equals, "/dev/sda1")
+-	c.Assert(i1.BlockDevices[0].SnapshotId, Equals, "snap-787e9403")
+-	c.Assert(i1.BlockDevices[0].VolumeSize, Equals, int64(8))
+-	c.Assert(i1.BlockDevices[0].DeleteOnTermination, Equals, true)
+-}
 -
--import (
--	"appengine"
--	"appengine/datastore"
--	"appengine/user"
--	"github.com/emicklei/go-restful"
--	"github.com/emicklei/go-restful/swagger"
--	"net/http"
--	"time"
--)
+-func (s *S) TestImageAttributeExample(c *C) {
+-	testServer.Response(200, nil, ImageAttributeExample)
 -
--// This example demonstrates a reasonably complete suite of RESTful operations backed
--// by DataStore on Google App Engine.
+-	resp, err := s.ec2.ImageAttribute("ami-61a54008", "launchPermission")
 -
--// Our simple example struct.
--type Profile struct {
--	LastModified time.Time `json:"-" xml:"-"`
--	Email        string    `json:"-" xml:"-"`
--	FirstName    string    `json:"first_name" xml:"first-name"`
--	NickName     string    `json:"nick_name" xml:"nick-name"`
--	LastName     string    `json:"last_name" xml:"last-name"`
--}
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeImageAttribute"})
 -
--type ProfileApi struct {
--	Path string
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	c.Assert(resp.ImageId, Equals, "ami-61a54008")
+-	c.Assert(resp.Group, Equals, "all")
+-	c.Assert(resp.UserIds[0], Equals, "495219933132")
 -}
 -
--func gaeUrl() string {
--	if appengine.IsDevAppServer() {
--		return "http://localhost:8080"
--	} else {
--		// Include your URL on App Engine here.
--		// I found no way to get AppID without appengine.Context and this always
--		// based on a http.Request.
--		return "http://federatedservices.appspot.com"
--	}
+-func (s *S) TestCreateSnapshotExample(c *C) {
+-	testServer.Response(200, nil, CreateSnapshotExample)
+-
+-	resp, err := s.ec2.CreateSnapshot("vol-4d826724", "Daily Backup")
+-
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"CreateSnapshot"})
+-	c.Assert(req.Form["VolumeId"], DeepEquals, []string{"vol-4d826724"})
+-	c.Assert(req.Form["Description"], DeepEquals, []string{"Daily Backup"})
+-
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	c.Assert(resp.Snapshot.Id, Equals, "snap-78a54011")
+-	c.Assert(resp.Snapshot.VolumeId, Equals, "vol-4d826724")
+-	c.Assert(resp.Snapshot.Status, Equals, "pending")
+-	c.Assert(resp.Snapshot.StartTime, Equals, "2008-05-07T12:51:50.000Z")
+-	c.Assert(resp.Snapshot.Progress, Equals, "60%")
+-	c.Assert(resp.Snapshot.OwnerId, Equals, "111122223333")
+-	c.Assert(resp.Snapshot.VolumeSize, Equals, "10")
+-	c.Assert(resp.Snapshot.Description, Equals, "Daily Backup")
 -}
 -
--func init() {
--	u := ProfileApi{Path: "/profiles"}
--	u.register()
+-func (s *S) TestDeleteSnapshotsExample(c *C) {
+-	testServer.Response(200, nil, DeleteSnapshotExample)
 -
--	// Optionally, you can install the Swagger Service which provides a nice Web UI on your REST API
--	// You need to download the Swagger HTML5 assets and change the FilePath location in the config below.
--	// Open <your_app_id>.appspot.com/apidocs and enter
--	// Place the Swagger UI files into a folder called static/swagger if you wish to use Swagger
--	// http://<your_app_id>.appspot.com/apidocs.json in the api input field.
--	// For testing, you can use http://localhost:8080/apidocs.json
--	config := swagger.Config{
--		// You control what services are visible
--		WebServices:    restful.RegisteredWebServices(),
--		WebServicesUrl: gaeUrl(),
--		ApiPath:        "/apidocs.json",
+-	resp, err := s.ec2.DeleteSnapshots([]string{"snap-78a54011"})
 -
--		// Optionally, specifiy where the UI is located
--		SwaggerPath: "/apidocs/",
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"DeleteSnapshot"})
+-	c.Assert(req.Form["SnapshotId.1"], DeepEquals, []string{"snap-78a54011"})
 -
--		// GAE support static content which is configured in your app.yaml.
--		// This example expect the swagger-ui in static/swagger so you should place it there :)
--		SwaggerFilePath: "static/swagger"}
--	swagger.InstallSwaggerService(config)
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
 -}
 -
--func (u ProfileApi) register() {
--	ws := new(restful.WebService)
+-func (s *S) TestDescribeSnapshotsExample(c *C) {
+-	testServer.Response(200, nil, DescribeSnapshotsExample)
 -
--	ws.
--		Path(u.Path).
--		// You can specify consumes and produces per route as well.
--		Consumes(restful.MIME_JSON, restful.MIME_XML).
--		Produces(restful.MIME_JSON, restful.MIME_XML)
+-	filter := ec2.NewFilter()
+-	filter.Add("key1", "value1")
+-	filter.Add("key2", "value2", "value3")
 -
--	ws.Route(ws.POST("").To(u.insert).
--		// Swagger documentation.
--		Doc("insert a new profile").
--		Param(ws.BodyParameter("Profile", "representation of a profile").DataType("main.Profile")).
--		Reads(Profile{}))
+-	resp, err := s.ec2.Snapshots([]string{"snap-1", "snap-2"}, filter)
 -
--	ws.Route(ws.GET("/{profile-id}").To(u.read).
--		// Swagger documentation.
--		Doc("read a profile").
--		Param(ws.PathParameter("profile-id", "identifier for a profile").DataType("string")).
--		Writes(Profile{}))
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeSnapshots"})
+-	c.Assert(req.Form["SnapshotId.1"], DeepEquals, []string{"snap-1"})
+-	c.Assert(req.Form["SnapshotId.2"], DeepEquals, []string{"snap-2"})
+-	c.Assert(req.Form["Filter.1.Name"], DeepEquals, []string{"key1"})
+-	c.Assert(req.Form["Filter.1.Value.1"], DeepEquals, []string{"value1"})
+-	c.Assert(req.Form["Filter.1.Value.2"], IsNil)
+-	c.Assert(req.Form["Filter.2.Name"], DeepEquals, []string{"key2"})
+-	c.Assert(req.Form["Filter.2.Value.1"], DeepEquals, []string{"value2"})
+-	c.Assert(req.Form["Filter.2.Value.2"], DeepEquals, []string{"value3"})
 -
--	ws.Route(ws.PUT("/{profile-id}").To(u.update).
--		// Swagger documentation.
--		Doc("update an existing profile").
--		Param(ws.PathParameter("profile-id", "identifier for a profile").DataType("string")).
--		Param(ws.BodyParameter("Profile", "representation of a profile").DataType("main.Profile")).
--		Reads(Profile{}))
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	c.Assert(resp.Snapshots, HasLen, 1)
 -
--	ws.Route(ws.DELETE("/{profile-id}").To(u.remove).
--		// Swagger documentation.
--		Doc("remove a profile").
--		Param(ws.PathParameter("profile-id", "identifier for a profile").DataType("string")))
+-	s0 := resp.Snapshots[0]
+-	c.Assert(s0.Id, Equals, "snap-1a2b3c4d")
+-	c.Assert(s0.VolumeId, Equals, "vol-8875daef")
+-	c.Assert(s0.VolumeSize, Equals, "15")
+-	c.Assert(s0.Status, Equals, "pending")
+-	c.Assert(s0.StartTime, Equals, "2010-07-29T04:12:01.000Z")
+-	c.Assert(s0.Progress, Equals, "30%")
+-	c.Assert(s0.OwnerId, Equals, "111122223333")
+-	c.Assert(s0.Description, Equals, "Daily Backup")
 -
--	restful.Add(ws)
+-	c.Assert(s0.Tags, HasLen, 1)
+-	c.Assert(s0.Tags[0].Key, Equals, "Purpose")
+-	c.Assert(s0.Tags[0].Value, Equals, "demo_db_14_backup")
 -}
 -
--// POST http://localhost:8080/profiles
--// {"first_name": "Ivan", "nick_name": "Socks", "last_name": "Hawkes"}
--//
--func (u *ProfileApi) insert(r *restful.Request, w *restful.Response) {
--	c := appengine.NewContext(r.Request)
+-func (s *S) TestModifyImageAttributeExample(c *C) {
+-	testServer.Response(200, nil, ModifyImageAttributeExample)
 -
--	// Marshall the entity from the request into a struct.
--	p := new(Profile)
--	err := r.ReadEntity(&p)
--	if err != nil {
--		w.WriteError(http.StatusNotAcceptable, err)
--		return
+-	options := ec2.ModifyImageAttribute{
+-		Description: "Test Description",
 -	}
 -
--	// Ensure we start with a sensible value for this field.
--	p.LastModified = time.Now()
--
--	// The profile belongs to this user.
--	p.Email = user.Current(c).String()
--
--	k, err := datastore.Put(c, datastore.NewIncompleteKey(c, "profiles", nil), p)
--	if err != nil {
--		http.Error(w, err.Error(), http.StatusInternalServerError)
--		return
--	}
+-	resp, err := s.ec2.ModifyImageAttribute("ami-4fa54026", &options)
 -
--	// Let them know the location of the newly created resource.
--	// TODO: Use a safe Url path append function.
--	w.AddHeader("Location", u.Path+"/"+k.Encode())
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"ModifyImageAttribute"})
 -
--	// Return the resultant entity.
--	w.WriteHeader(http.StatusCreated)
--	w.WriteEntity(p)
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
 -}
 -
--// GET http://localhost:8080/profiles/ahdkZXZ-ZmVkZXJhdGlvbi1zZXJ2aWNlc3IVCxIIcHJvZmlsZXMYgICAgICAgAoM
--//
--func (u ProfileApi) read(r *restful.Request, w *restful.Response) {
--	c := appengine.NewContext(r.Request)
+-func (s *S) TestModifyImageAttributeExample_complex(c *C) {
+-	testServer.Response(200, nil, ModifyImageAttributeExample)
 -
--	// Decode the request parameter to determine the key for the entity.
--	k, err := datastore.DecodeKey(r.PathParameter("profile-id"))
--	if err != nil {
--		http.Error(w, err.Error(), http.StatusBadRequest)
--		return
+-	options := ec2.ModifyImageAttribute{
+-		AddUsers:     []string{"u1", "u2"},
+-		RemoveUsers:  []string{"u3"},
+-		AddGroups:    []string{"g1", "g3"},
+-		RemoveGroups: []string{"g2"},
+-		Description:  "Test Description",
 -	}
 -
--	// Retrieve the entity from the datastore.
--	p := Profile{}
--	if err := datastore.Get(c, k, &p); err != nil {
--		if err.Error() == "datastore: no such entity" {
--			http.Error(w, err.Error(), http.StatusNotFound)
--		} else {
--			http.Error(w, err.Error(), http.StatusInternalServerError)
--		}
--		return
--	}
+-	resp, err := s.ec2.ModifyImageAttribute("ami-4fa54026", &options)
 -
--	// Check we own the profile before allowing them to view it.
--	// Optionally, return a 404 instead to help prevent guessing ids.
--	// TODO: Allow admins access.
--	if p.Email != user.Current(c).String() {
--		http.Error(w, "You do not have access to this resource", http.StatusForbidden)
--		return
--	}
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"ModifyImageAttribute"})
+-	c.Assert(req.Form["LaunchPermission.Add.1.UserId"], DeepEquals, []string{"u1"})
+-	c.Assert(req.Form["LaunchPermission.Add.2.UserId"], DeepEquals, []string{"u2"})
+-	c.Assert(req.Form["LaunchPermission.Remove.1.UserId"], DeepEquals, []string{"u3"})
+-	c.Assert(req.Form["LaunchPermission.Add.1.Group"], DeepEquals, []string{"g1"})
+-	c.Assert(req.Form["LaunchPermission.Add.2.Group"], DeepEquals, []string{"g3"})
+-	c.Assert(req.Form["LaunchPermission.Remove.1.Group"], DeepEquals, []string{"g2"})
 -
--	w.WriteEntity(p)
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
 -}
 -
--// PUT http://localhost:8080/profiles/ahdkZXZ-ZmVkZXJhdGlvbi1zZXJ2aWNlc3IVCxIIcHJvZmlsZXMYgICAgICAgAoM
--// {"first_name": "Ivan", "nick_name": "Socks", "last_name": "Hawkes"}
--//
--func (u *ProfileApi) update(r *restful.Request, w *restful.Response) {
--	c := appengine.NewContext(r.Request)
+-func (s *S) TestCopyImageExample(c *C) {
+-	testServer.Response(200, nil, CopyImageExample)
 -
--	// Decode the request parameter to determine the key for the entity.
--	k, err := datastore.DecodeKey(r.PathParameter("profile-id"))
--	if err != nil {
--		http.Error(w, err.Error(), http.StatusBadRequest)
--		return
+-	options := ec2.CopyImage{
+-		SourceRegion:  "us-west-2",
+-		SourceImageId: "ami-1a2b3c4d",
+-		Description:   "Test Description",
 -	}
 -
--	// Marshall the entity from the request into a struct.
--	p := new(Profile)
--	err = r.ReadEntity(&p)
--	if err != nil {
--		w.WriteError(http.StatusNotAcceptable, err)
--		return
--	}
+-	resp, err := s.ec2.CopyImage(&options)
 -
--	// Retrieve the old entity from the datastore.
--	old := Profile{}
--	if err := datastore.Get(c, k, &old); err != nil {
--		if err.Error() == "datastore: no such entity" {
--			http.Error(w, err.Error(), http.StatusNotFound)
--		} else {
--			http.Error(w, err.Error(), http.StatusInternalServerError)
--		}
--		return
--	}
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"CopyImage"})
 -
--	// Check we own the profile before allowing them to update it.
--	// Optionally, return a 404 instead to help prevent guessing ids.
--	// TODO: Allow admins access.
--	if old.Email != user.Current(c).String() {
--		http.Error(w, "You do not have access to this resource", http.StatusForbidden)
--		return
--	}
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "60bc441d-fa2c-494d-b155-5d6a3EXAMPLE")
+-}
 -
--	// Since the whole entity is re-written, we need to assign any invariant fields again
--	// e.g. the owner of the entity.
--	p.Email = user.Current(c).String()
+-func (s *S) TestCreateKeyPairExample(c *C) {
+-	testServer.Response(200, nil, CreateKeyPairExample)
 -
--	// Keep track of the last modification date.
--	p.LastModified = time.Now()
+-	resp, err := s.ec2.CreateKeyPair("foo")
 -
--	// Attempt to overwrite the old entity.
--	_, err = datastore.Put(c, k, p)
--	if err != nil {
--		http.Error(w, err.Error(), http.StatusInternalServerError)
--		return
--	}
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"CreateKeyPair"})
+-	c.Assert(req.Form["KeyName"], DeepEquals, []string{"foo"})
 -
--	// Let them know it succeeded.
--	w.WriteHeader(http.StatusNoContent)
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	c.Assert(resp.KeyName, Equals, "foo")
+-	c.Assert(resp.KeyFingerprint, Equals, "00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00")
 -}
 -
--// DELETE http://localhost:8080/profiles/ahdkZXZ-ZmVkZXJhdGlvbi1zZXJ2aWNlc3IVCxIIcHJvZmlsZXMYgICAgICAgAoM
--//
--func (u *ProfileApi) remove(r *restful.Request, w *restful.Response) {
--	c := appengine.NewContext(r.Request)
+-func (s *S) TestDeleteKeyPairExample(c *C) {
+-	testServer.Response(200, nil, DeleteKeyPairExample)
 -
--	// Decode the request parameter to determine the key for the entity.
--	k, err := datastore.DecodeKey(r.PathParameter("profile-id"))
--	if err != nil {
--		http.Error(w, err.Error(), http.StatusBadRequest)
--		return
--	}
+-	resp, err := s.ec2.DeleteKeyPair("foo")
 -
--	// Retrieve the old entity from the datastore.
--	old := Profile{}
--	if err := datastore.Get(c, k, &old); err != nil {
--		if err.Error() == "datastore: no such entity" {
--			http.Error(w, err.Error(), http.StatusNotFound)
--		} else {
--			http.Error(w, err.Error(), http.StatusInternalServerError)
--		}
--		return
--	}
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"DeleteKeyPair"})
+-	c.Assert(req.Form["KeyName"], DeepEquals, []string{"foo"})
 -
--	// Check we own the profile before allowing them to delete it.
--	// Optionally, return a 404 instead to help prevent guessing ids.
--	// TODO: Allow admins access.
--	if old.Email != user.Current(c).String() {
--		http.Error(w, "You do not have access to this resource", http.StatusForbidden)
--		return
--	}
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-}
 -
--	// Delete the entity.
--	if err := datastore.Delete(c, k); err != nil {
--		http.Error(w, err.Error(), http.StatusInternalServerError)
--	}
+-func (s *S) TestCreateSecurityGroupExample(c *C) {
+-	testServer.Response(200, nil, CreateSecurityGroupExample)
 -
--	// Success notification.
--	w.WriteHeader(http.StatusNoContent)
+-	resp, err := s.ec2.CreateSecurityGroup(ec2.SecurityGroup{Name: "websrv", Description: "Web Servers"})
+-
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"CreateSecurityGroup"})
+-	c.Assert(req.Form["GroupName"], DeepEquals, []string{"websrv"})
+-	c.Assert(req.Form["GroupDescription"], DeepEquals, []string{"Web Servers"})
+-
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	c.Assert(resp.Name, Equals, "websrv")
+-	c.Assert(resp.Id, Equals, "sg-67ad940e")
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/restful-appstats-integration.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/restful-appstats-integration.go
-deleted file mode 100644
-index b3261ee..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/restful-appstats-integration.go
-+++ /dev/null
-@@ -1,13 +0,0 @@
--package main
 -
--import (
--	"github.com/mjibson/appstats"
--)
+-func (s *S) TestDescribeSecurityGroupsExample(c *C) {
+-	testServer.Response(200, nil, DescribeSecurityGroupsExample)
 -
+-	resp, err := s.ec2.SecurityGroups([]ec2.SecurityGroup{{Name: "WebServers"}, {Name: "RangedPortsBySource"}}, nil)
 -
--func stats(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
--	c := appstats.NewContext(req.Request)
--	chain.ProcessFilter(req, resp)
--	c.Stats.Status = resp.StatusCode()
--	c.Save()
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/restful-user-service.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/restful-user-service.go
-deleted file mode 100644
-index e97ba2e..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/google_app_engine/restful-user-service.go
-+++ /dev/null
-@@ -1,161 +0,0 @@
--package main
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeSecurityGroups"})
+-	c.Assert(req.Form["GroupName.1"], DeepEquals, []string{"WebServers"})
+-	c.Assert(req.Form["GroupName.2"], DeepEquals, []string{"RangedPortsBySource"})
 -
--import (
--	"appengine"
--	"appengine/memcache"
--	"github.com/emicklei/go-restful"
--	"github.com/emicklei/go-restful/swagger"
--	"net/http"
--)
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	c.Assert(resp.Groups, HasLen, 2)
 -
--// This example is functionally the same as ../restful-user-service.go
--// but it`s supposed to run on Goole App Engine (GAE)
--//
--// contributed by ivanhawkes
+-	g0 := resp.Groups[0]
+-	c.Assert(g0.OwnerId, Equals, "999988887777")
+-	c.Assert(g0.Name, Equals, "WebServers")
+-	c.Assert(g0.Id, Equals, "sg-67ad940e")
+-	c.Assert(g0.Description, Equals, "Web Servers")
+-	c.Assert(g0.IPPerms, HasLen, 1)
 -
--type User struct {
--	Id, Name string
--}
+-	g0ipp := g0.IPPerms[0]
+-	c.Assert(g0ipp.Protocol, Equals, "tcp")
+-	c.Assert(g0ipp.FromPort, Equals, 80)
+-	c.Assert(g0ipp.ToPort, Equals, 80)
+-	c.Assert(g0ipp.SourceIPs, DeepEquals, []string{"0.0.0.0/0"})
 -
--type UserService struct {
--	// normally one would use DAO (data access object)
--	// but in this example we simple use memcache.
+-	g1 := resp.Groups[1]
+-	c.Assert(g1.OwnerId, Equals, "999988887777")
+-	c.Assert(g1.Name, Equals, "RangedPortsBySource")
+-	c.Assert(g1.Id, Equals, "sg-76abc467")
+-	c.Assert(g1.Description, Equals, "Group A")
+-	c.Assert(g1.IPPerms, HasLen, 1)
+-
+-	g1ipp := g1.IPPerms[0]
+-	c.Assert(g1ipp.Protocol, Equals, "tcp")
+-	c.Assert(g1ipp.FromPort, Equals, 6000)
+-	c.Assert(g1ipp.ToPort, Equals, 7000)
+-	c.Assert(g1ipp.SourceIPs, IsNil)
 -}
 -
--func (u UserService) Register() {
--	ws := new(restful.WebService)
+-func (s *S) TestDescribeSecurityGroupsExampleWithFilter(c *C) {
+-	testServer.Response(200, nil, DescribeSecurityGroupsExample)
 -
--	ws.
--		Path("/users").
--		Consumes(restful.MIME_XML, restful.MIME_JSON).
--		Produces(restful.MIME_JSON, restful.MIME_XML) // you can specify this per route as well
+-	filter := ec2.NewFilter()
+-	filter.Add("ip-permission.protocol", "tcp")
+-	filter.Add("ip-permission.from-port", "22")
+-	filter.Add("ip-permission.to-port", "22")
+-	filter.Add("ip-permission.group-name", "app_server_group", "database_group")
 -
--	ws.Route(ws.GET("/{user-id}").To(u.findUser).
--		// docs
--		Doc("get a user").
--		Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")).
--		Writes(User{})) // on the response
+-	_, err := s.ec2.SecurityGroups(nil, filter)
 -
--	ws.Route(ws.PATCH("").To(u.updateUser).
--		// docs
--		Doc("update a user").
--		Reads(User{})) // from the request
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeSecurityGroups"})
+-	c.Assert(req.Form["Filter.1.Name"], DeepEquals, []string{"ip-permission.from-port"})
+-	c.Assert(req.Form["Filter.1.Value.1"], DeepEquals, []string{"22"})
+-	c.Assert(req.Form["Filter.2.Name"], DeepEquals, []string{"ip-permission.group-name"})
+-	c.Assert(req.Form["Filter.2.Value.1"], DeepEquals, []string{"app_server_group"})
+-	c.Assert(req.Form["Filter.2.Value.2"], DeepEquals, []string{"database_group"})
+-	c.Assert(req.Form["Filter.3.Name"], DeepEquals, []string{"ip-permission.protocol"})
+-	c.Assert(req.Form["Filter.3.Value.1"], DeepEquals, []string{"tcp"})
+-	c.Assert(req.Form["Filter.4.Name"], DeepEquals, []string{"ip-permission.to-port"})
+-	c.Assert(req.Form["Filter.4.Value.1"], DeepEquals, []string{"22"})
 -
--	ws.Route(ws.PUT("/{user-id}").To(u.createUser).
--		// docs
--		Doc("create a user").
--		Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")).
--		Reads(User{})) // from the request
+-	c.Assert(err, IsNil)
+-}
 -
--	ws.Route(ws.DELETE("/{user-id}").To(u.removeUser).
--		// docs
--		Doc("delete a user").
--		Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")))
+-func (s *S) TestDescribeSecurityGroupsDumpWithGroup(c *C) {
+-	testServer.Response(200, nil, DescribeSecurityGroupsDump)
 -
--	restful.Add(ws)
--}
+-	resp, err := s.ec2.SecurityGroups(nil, nil)
 -
--// GET http://localhost:8080/users/1
--//
--func (u UserService) findUser(request *restful.Request, response *restful.Response) {
--	c := appengine.NewContext(request.Request)
--	id := request.PathParameter("user-id")
--	usr := new(User)
--	_, err := memcache.Gob.Get(c, id, &usr)
--	if err != nil || len(usr.Id) == 0 {
--		response.WriteErrorString(http.StatusNotFound, "User could not be found.")
--	} else {
--		response.WriteEntity(usr)
--	}
--}
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeSecurityGroups"})
+-	c.Assert(err, IsNil)
+-	c.Check(resp.Groups, HasLen, 1)
+-	c.Check(resp.Groups[0].IPPerms, HasLen, 2)
 -
--// PATCH http://localhost:8080/users
--// <User><Id>1</Id><Name>Melissa Raspberry</Name></User>
--//
--func (u *UserService) updateUser(request *restful.Request, response *restful.Response) {
--	c := appengine.NewContext(request.Request)
--	usr := new(User)
--	err := request.ReadEntity(&usr)
--	if err == nil {
--		item := &memcache.Item{
--			Key:    usr.Id,
--			Object: &usr,
--		}
--		err = memcache.Gob.Set(c, item)
--		if err != nil {
--			response.WriteError(http.StatusInternalServerError, err)
--			return
--		}
--		response.WriteEntity(usr)
--	} else {
--		response.WriteError(http.StatusInternalServerError, err)
--	}
--}
+-	ipp0 := resp.Groups[0].IPPerms[0]
+-	c.Assert(ipp0.SourceIPs, IsNil)
+-	c.Check(ipp0.Protocol, Equals, "icmp")
+-	c.Assert(ipp0.SourceGroups, HasLen, 1)
+-	c.Check(ipp0.SourceGroups[0].OwnerId, Equals, "12345")
+-	c.Check(ipp0.SourceGroups[0].Name, Equals, "default")
+-	c.Check(ipp0.SourceGroups[0].Id, Equals, "sg-67ad940e")
 -
--// PUT http://localhost:8080/users/1
--// <User><Id>1</Id><Name>Melissa</Name></User>
--//
--func (u *UserService) createUser(request *restful.Request, response *restful.Response) {
--	c := appengine.NewContext(request.Request)
--	usr := User{Id: request.PathParameter("user-id")}
--	err := request.ReadEntity(&usr)
--	if err == nil {
--		item := &memcache.Item{
--			Key:    usr.Id,
--			Object: &usr,
--		}
--		err = memcache.Gob.Add(c, item)
--		if err != nil {
--			response.WriteError(http.StatusInternalServerError, err)
--			return
--		}
--		response.WriteHeader(http.StatusCreated)
--		response.WriteEntity(usr)
--	} else {
--		response.WriteError(http.StatusInternalServerError, err)
--	}
+-	ipp1 := resp.Groups[0].IPPerms[1]
+-	c.Check(ipp1.Protocol, Equals, "tcp")
+-	c.Assert(ipp0.SourceIPs, IsNil)
+-	c.Assert(ipp0.SourceGroups, HasLen, 1)
+-	c.Check(ipp1.SourceGroups[0].Id, Equals, "sg-76abc467")
+-	c.Check(ipp1.SourceGroups[0].OwnerId, Equals, "12345")
+-	c.Check(ipp1.SourceGroups[0].Name, Equals, "other")
 -}
 -
--// DELETE http://localhost:8080/users/1
--//
--func (u *UserService) removeUser(request *restful.Request, response *restful.Response) {
--	c := appengine.NewContext(request.Request)
--	id := request.PathParameter("user-id")
--	err := memcache.Delete(c, id)
--	if err != nil {
--		response.WriteError(http.StatusInternalServerError, err)
--	}
--}
+-func (s *S) TestDeleteSecurityGroupExample(c *C) {
+-	testServer.Response(200, nil, DeleteSecurityGroupExample)
 -
--func getGaeURL() string {
--	if appengine.IsDevAppServer() {
--		return "http://localhost:8080"
--	} else {
--		/**
--		 * Include your URL on App Engine here.
--		 * I found no way to get AppID without appengine.Context and this always
--		 * based on a http.Request.
--		 */
--		return "http://<your_app_id>.appspot.com"
--	}
+-	resp, err := s.ec2.DeleteSecurityGroup(ec2.SecurityGroup{Name: "websrv"})
+-	req := testServer.WaitRequest()
+-
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"DeleteSecurityGroup"})
+-	c.Assert(req.Form["GroupName"], DeepEquals, []string{"websrv"})
+-	c.Assert(req.Form["GroupId"], IsNil)
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
 -}
 -
--func init() {
--	u := UserService{}
--	u.Register()
+-func (s *S) TestDeleteSecurityGroupExampleWithId(c *C) {
+-	testServer.Response(200, nil, DeleteSecurityGroupExample)
 -
--	// Optionally, you can install the Swagger Service which provides a nice Web UI on your REST API
--	// You need to download the Swagger HTML5 assets and change the FilePath location in the config below.
--	// Open <your_app_id>.appspot.com/apidocs and enter http://<your_app_id>.appspot.com/apidocs.json in the api input field.
--	config := swagger.Config{
--		WebServices:    restful.RegisteredWebServices(), // you control what services are visible
--		WebServicesUrl: getGaeURL(),
--		ApiPath:        "/apidocs.json",
+-	// ignore return and error - we're only want to check the parameter handling.
+-	s.ec2.DeleteSecurityGroup(ec2.SecurityGroup{Id: "sg-67ad940e", Name: "ignored"})
+-	req := testServer.WaitRequest()
 -
--		// Optionally, specifiy where the UI is located
--		SwaggerPath: "/apidocs/",
--		// GAE support static content which is configured in your app.yaml.
--		// This example expect the swagger-ui in static/swagger so you should place it there :)
--		SwaggerFilePath: "static/swagger"}
--	swagger.InstallSwaggerService(config)
+-	c.Assert(req.Form["GroupName"], IsNil)
+-	c.Assert(req.Form["GroupId"], DeepEquals, []string{"sg-67ad940e"})
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/home.html b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/home.html
-deleted file mode 100644
-index e5d49b4..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/home.html
-+++ /dev/null
-@@ -1,7 +0,0 @@
--<!DOCTYPE html>
 -
--<html>
--<body>
--	<h1>{{.Text}}</h1>
--</body>
--</html>
-\ No newline at end of file
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-CORS-filter.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-CORS-filter.go
-deleted file mode 100644
-index aacaa3d..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-CORS-filter.go
-+++ /dev/null
-@@ -1,67 +0,0 @@
--package main
+-func (s *S) TestAuthorizeSecurityGroupExample1(c *C) {
+-	testServer.Response(200, nil, AuthorizeSecurityGroupIngressExample)
 -
--import (
--	"io"
--	"log"
--	"net/http"
+-	perms := []ec2.IPPerm{{
+-		Protocol:  "tcp",
+-		FromPort:  80,
+-		ToPort:    80,
+-		SourceIPs: []string{"205.192.0.0/16", "205.159.0.0/16"},
+-	}}
+-	resp, err := s.ec2.AuthorizeSecurityGroup(ec2.SecurityGroup{Name: "websrv"}, perms)
 -
--	"github.com/emicklei/go-restful"
--)
+-	req := testServer.WaitRequest()
 -
--// Cross-origin resource sharing (CORS) is a mechanism that allows JavaScript on a web page
--// to make XMLHttpRequests to another domain, not the domain the JavaScript originated from.
--//
--// http://en.wikipedia.org/wiki/Cross-origin_resource_sharing
--// http://enable-cors.org/server.html
--//
--// GET http://localhost:8080/users
--//
--// GET http://localhost:8080/users/1
--//
--// PUT http://localhost:8080/users/1
--//
--// DELETE http://localhost:8080/users/1
--//
--// OPTIONS http://localhost:8080/users/1  with Header "Origin" set to some domain and
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"AuthorizeSecurityGroupIngress"})
+-	c.Assert(req.Form["GroupName"], DeepEquals, []string{"websrv"})
+-	c.Assert(req.Form["IpPermissions.1.IpProtocol"], DeepEquals, []string{"tcp"})
+-	c.Assert(req.Form["IpPermissions.1.FromPort"], DeepEquals, []string{"80"})
+-	c.Assert(req.Form["IpPermissions.1.ToPort"], DeepEquals, []string{"80"})
+-	c.Assert(req.Form["IpPermissions.1.IpRanges.1.CidrIp"], DeepEquals, []string{"205.192.0.0/16"})
+-	c.Assert(req.Form["IpPermissions.1.IpRanges.2.CidrIp"], DeepEquals, []string{"205.159.0.0/16"})
 -
--type UserResource struct{}
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-}
 -
--func (u UserResource) RegisterTo(container *restful.Container) {
--	ws := new(restful.WebService)
--	ws.
--		Path("/users").
--		Consumes("*/*").
--		Produces("*/*")
+-func (s *S) TestAuthorizeSecurityGroupEgress(c *C) {
+-	testServer.Response(200, nil, AuthorizeSecurityGroupEgressExample)
 -
--	ws.Route(ws.GET("/{user-id}").To(u.nop))
--	ws.Route(ws.POST("").To(u.nop))
--	ws.Route(ws.PUT("/{user-id}").To(u.nop))
--	ws.Route(ws.DELETE("/{user-id}").To(u.nop))
+-	perms := []ec2.IPPerm{{
+-		Protocol:  "tcp",
+-		FromPort:  80,
+-		ToPort:    80,
+-		SourceIPs: []string{"205.192.0.0/16", "205.159.0.0/16"},
+-	}}
+-	resp, err := s.ec2.AuthorizeSecurityGroupEgress(ec2.SecurityGroup{Name: "websrv"}, perms)
 -
--	container.Add(ws)
--}
+-	req := testServer.WaitRequest()
 -
--func (u UserResource) nop(request *restful.Request, response *restful.Response) {
--	io.WriteString(response.ResponseWriter, "this would be a normal response")
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"AuthorizeSecurityGroupEgress"})
+-	c.Assert(req.Form["GroupName"], DeepEquals, []string{"websrv"})
+-	c.Assert(req.Form["IpPermissions.1.IpProtocol"], DeepEquals, []string{"tcp"})
+-	c.Assert(req.Form["IpPermissions.1.FromPort"], DeepEquals, []string{"80"})
+-	c.Assert(req.Form["IpPermissions.1.ToPort"], DeepEquals, []string{"80"})
+-	c.Assert(req.Form["IpPermissions.1.IpRanges.1.CidrIp"], DeepEquals, []string{"205.192.0.0/16"})
+-	c.Assert(req.Form["IpPermissions.1.IpRanges.2.CidrIp"], DeepEquals, []string{"205.159.0.0/16"})
+-
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
 -}
 -
--func main() {
--	wsContainer := restful.NewContainer()
--	u := UserResource{}
--	u.RegisterTo(wsContainer)
+-func (s *S) TestAuthorizeSecurityGroupExample1WithId(c *C) {
+-	testServer.Response(200, nil, AuthorizeSecurityGroupIngressExample)
 -
--	// Add container filter to enable CORS
--	cors := restful.CrossOriginResourceSharing{
--		ExposeHeaders:  []string{"X-My-Header"},
--		AllowedHeaders: []string{"Content-Type"},
--		CookiesAllowed: false,
--		Container:      wsContainer}
--	wsContainer.Filter(cors.Filter)
+-	perms := []ec2.IPPerm{{
+-		Protocol:  "tcp",
+-		FromPort:  80,
+-		ToPort:    80,
+-		SourceIPs: []string{"205.192.0.0/16", "205.159.0.0/16"},
+-	}}
+-	// ignore return and error - we're only want to check the parameter handling.
+-	s.ec2.AuthorizeSecurityGroup(ec2.SecurityGroup{Id: "sg-67ad940e", Name: "ignored"}, perms)
 -
--	// Add container filter to respond to OPTIONS
--	wsContainer.Filter(wsContainer.OPTIONSFilter)
+-	req := testServer.WaitRequest()
 -
--	log.Printf("start listening on localhost:8080")
--	server := &http.Server{Addr: ":8080", Handler: wsContainer}
--	log.Fatal(server.ListenAndServe())
+-	c.Assert(req.Form["GroupName"], IsNil)
+-	c.Assert(req.Form["GroupId"], DeepEquals, []string{"sg-67ad940e"})
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-NCSA-logging.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-NCSA-logging.go
-deleted file mode 100644
-index 0cda50d..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-NCSA-logging.go
-+++ /dev/null
-@@ -1,54 +0,0 @@
--package main
 -
--import (
--	"github.com/emicklei/go-restful"
--	"io"
--	"log"
--	"net/http"
--	"os"
--	"strings"
--	"time"
--)
+-func (s *S) TestAuthorizeSecurityGroupExample2(c *C) {
+-	testServer.Response(200, nil, AuthorizeSecurityGroupIngressExample)
 -
--// This example shows how to create a filter that produces log lines
--// according to the Common Log Format, also known as the NCSA standard.
--//
--// kindly contributed by leehambley
--//
--// GET http://localhost:8080/ping
+-	perms := []ec2.IPPerm{{
+-		Protocol: "tcp",
+-		FromPort: 80,
+-		ToPort:   81,
+-		SourceGroups: []ec2.UserSecurityGroup{
+-			{OwnerId: "999988887777", Name: "OtherAccountGroup"},
+-			{Id: "sg-67ad940e"},
+-		},
+-	}}
+-	resp, err := s.ec2.AuthorizeSecurityGroup(ec2.SecurityGroup{Name: "websrv"}, perms)
 -
--var logger *log.Logger = log.New(os.Stdout, "", 0)
+-	req := testServer.WaitRequest()
 -
--func NCSACommonLogFormatLogger() restful.FilterFunction {
--	return func(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
--		var username = "-"
--		if req.Request.URL.User != nil {
--			if name := req.Request.URL.User.Username(); name != "" {
--				username = name
--			}
--		}
--		chain.ProcessFilter(req, resp)
--		logger.Printf("%s - %s [%s] \"%s %s %s\" %d %d",
--			strings.Split(req.Request.RemoteAddr, ":")[0],
--			username,
--			time.Now().Format("02/Jan/2006:15:04:05 -0700"),
--			req.Request.Method,
--			req.Request.URL.RequestURI(),
--			req.Request.Proto,
--			resp.StatusCode(),
--			resp.ContentLength(),
--		)
--	}
--}
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"AuthorizeSecurityGroupIngress"})
+-	c.Assert(req.Form["GroupName"], DeepEquals, []string{"websrv"})
+-	c.Assert(req.Form["IpPermissions.1.IpProtocol"], DeepEquals, []string{"tcp"})
+-	c.Assert(req.Form["IpPermissions.1.FromPort"], DeepEquals, []string{"80"})
+-	c.Assert(req.Form["IpPermissions.1.ToPort"], DeepEquals, []string{"81"})
+-	c.Assert(req.Form["IpPermissions.1.Groups.1.UserId"], DeepEquals, []string{"999988887777"})
+-	c.Assert(req.Form["IpPermissions.1.Groups.1.GroupName"], DeepEquals, []string{"OtherAccountGroup"})
+-	c.Assert(req.Form["IpPermissions.1.Groups.2.UserId"], IsNil)
+-	c.Assert(req.Form["IpPermissions.1.Groups.2.GroupName"], IsNil)
+-	c.Assert(req.Form["IpPermissions.1.Groups.2.GroupId"], DeepEquals, []string{"sg-67ad940e"})
 -
--func main() {
--	ws := new(restful.WebService)
--	ws.Filter(NCSACommonLogFormatLogger())
--	ws.Route(ws.GET("/ping").To(hello))
--	restful.Add(ws)
--	http.ListenAndServe(":8080", nil)
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
 -}
 -
--func hello(req *restful.Request, resp *restful.Response) {
--	io.WriteString(resp, "pong")
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-basic-authentication.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-basic-authentication.go
-deleted file mode 100644
-index 5dd3067..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-basic-authentication.go
-+++ /dev/null
-@@ -1,35 +0,0 @@
--package main
+-func (s *S) TestRevokeSecurityGroupExample(c *C) {
+-	// RevokeSecurityGroup is implemented by the same code as AuthorizeSecurityGroup
+-	// so there's no need to duplicate all the tests.
+-	testServer.Response(200, nil, RevokeSecurityGroupIngressExample)
 -
--import (
--	"github.com/emicklei/go-restful"
--	"io"
--	"net/http"
--)
+-	resp, err := s.ec2.RevokeSecurityGroup(ec2.SecurityGroup{Name: "websrv"}, nil)
 -
--// This example shows how to create a (Route) Filter that performs Basic Authentication on the Http request.
--//
--// GET http://localhost:8080/secret
--// and use admin,admin for the credentials
+-	req := testServer.WaitRequest()
 -
--func main() {
--	ws := new(restful.WebService)
--	ws.Route(ws.GET("/secret").Filter(basicAuthenticate).To(secret))
--	restful.Add(ws)
--	http.ListenAndServe(":8080", nil)
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"RevokeSecurityGroupIngress"})
+-	c.Assert(req.Form["GroupName"], DeepEquals, []string{"websrv"})
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
 -}
 -
--func basicAuthenticate(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
--	encoded := req.Request.Header.Get("Authorization")
--	// usr/pwd = admin/admin
--	// real code does some decoding
--	if len(encoded) == 0 || "Basic YWRtaW46YWRtaW4=" != encoded {
--		resp.AddHeader("WWW-Authenticate", "Basic realm=Protected Area")
--		resp.WriteErrorString(401, "401: Not Authorized")
--		return
--	}
--	chain.ProcessFilter(req, resp)
--}
+-func (s *S) TestCreateTags(c *C) {
+-	testServer.Response(200, nil, CreateTagsExample)
 -
--func secret(req *restful.Request, resp *restful.Response) {
--	io.WriteString(resp, "42")
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-cpuprofiler-service.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-cpuprofiler-service.go
-deleted file mode 100644
-index 9148213..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-cpuprofiler-service.go
-+++ /dev/null
-@@ -1,65 +0,0 @@
--package main
+-	resp, err := s.ec2.CreateTags([]string{"ami-1a2b3c4d", "i-7f4d3a2b"}, []ec2.Tag{{"webserver", ""}, {"stack", "Production"}})
 -
--import (
--	"github.com/emicklei/go-restful"
--	"io"
--	"log"
--	"os"
--	"runtime/pprof"
--)
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["ResourceId.1"], DeepEquals, []string{"ami-1a2b3c4d"})
+-	c.Assert(req.Form["ResourceId.2"], DeepEquals, []string{"i-7f4d3a2b"})
+-	c.Assert(req.Form["Tag.1.Key"], DeepEquals, []string{"webserver"})
+-	c.Assert(req.Form["Tag.1.Value"], DeepEquals, []string{""})
+-	c.Assert(req.Form["Tag.2.Key"], DeepEquals, []string{"stack"})
+-	c.Assert(req.Form["Tag.2.Value"], DeepEquals, []string{"Production"})
 -
--// ProfilingService is a WebService that can start/stop a CPU profile and write results to a file
--// 	GET /{rootPath}/start will activate CPU profiling
--//	GET /{rootPath}/stop will stop profiling
--//
--// NewProfileService("/profiler", "ace.prof").AddWebServiceTo(restful.DefaultContainer)
--//
--type ProfilingService struct {
--	rootPath   string   // the base (root) of the service, e.g. /profiler
--	cpuprofile string   // the output filename to write profile results, e.g. myservice.prof
--	cpufile    *os.File // if not nil, then profiling is active
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
 -}
 -
--func NewProfileService(rootPath string, outputFilename string) *ProfilingService {
--	ps := new(ProfilingService)
--	ps.rootPath = rootPath
--	ps.cpuprofile = outputFilename
--	return ps
--}
+-func (s *S) TestStartInstances(c *C) {
+-	testServer.Response(200, nil, StartInstancesExample)
 -
--// Add this ProfileService to a restful Container
--func (p ProfilingService) AddWebServiceTo(container *restful.Container) {
--	ws := new(restful.WebService)
--	ws.Path(p.rootPath).Consumes("*/*").Produces(restful.MIME_JSON)
--	ws.Route(ws.GET("/start").To(p.startProfiler))
--	ws.Route(ws.GET("/stop").To(p.stopProfiler))
--	container.Add(ws)
--}
+-	resp, err := s.ec2.StartInstances("i-10a64379")
+-	req := testServer.WaitRequest()
 -
--func (p *ProfilingService) startProfiler(req *restful.Request, resp *restful.Response) {
--	if p.cpufile != nil {
--		io.WriteString(resp.ResponseWriter, "[restful] CPU profiling already running")
--		return // error?
--	}
--	cpufile, err := os.Create(p.cpuprofile)
--	if err != nil {
--		log.Fatal(err)
--	}
--	// remember for close
--	p.cpufile = cpufile
--	pprof.StartCPUProfile(cpufile)
--	io.WriteString(resp.ResponseWriter, "[restful] CPU profiling started, writing on:"+p.cpuprofile)
--}
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"StartInstances"})
+-	c.Assert(req.Form["InstanceId.1"], DeepEquals, []string{"i-10a64379"})
 -
--func (p *ProfilingService) stopProfiler(req *restful.Request, resp *restful.Response) {
--	if p.cpufile == nil {
--		io.WriteString(resp.ResponseWriter, "[restful] CPU profiling not active")
--		return // error?
--	}
--	pprof.StopCPUProfile()
--	p.cpufile.Close()
--	p.cpufile = nil
--	io.WriteString(resp.ResponseWriter, "[restful] CPU profiling stopped, closing:"+p.cpuprofile)
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-
+-	s0 := resp.StateChanges[0]
+-	c.Assert(s0.InstanceId, Equals, "i-10a64379")
+-	c.Assert(s0.CurrentState.Code, Equals, 0)
+-	c.Assert(s0.CurrentState.Name, Equals, "pending")
+-	c.Assert(s0.PreviousState.Code, Equals, 80)
+-	c.Assert(s0.PreviousState.Name, Equals, "stopped")
 -}
 -
--func main() {} // exists for example compilation only
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-curly-router.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-curly-router.go
-deleted file mode 100644
-index 1b95dd0..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-curly-router.go
-+++ /dev/null
-@@ -1,107 +0,0 @@
--package main
+-func (s *S) TestStopInstances(c *C) {
+-	testServer.Response(200, nil, StopInstancesExample)
 -
--import (
--	"github.com/emicklei/go-restful"
--	"log"
--	"net/http"
--)
+-	resp, err := s.ec2.StopInstances("i-10a64379")
+-	req := testServer.WaitRequest()
 -
--// This example has the same service definition as restful-user-resource
--// but uses a different router (CurlyRouter) that does not use regular expressions
--//
--// POST http://localhost:8080/users
--// <User><Id>1</Id><Name>Melissa Raspberry</Name></User>
--//
--// GET http://localhost:8080/users/1
--//
--// PUT http://localhost:8080/users/1
--// <User><Id>1</Id><Name>Melissa</Name></User>
--//
--// DELETE http://localhost:8080/users/1
--//
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"StopInstances"})
+-	c.Assert(req.Form["InstanceId.1"], DeepEquals, []string{"i-10a64379"})
 -
--type User struct {
--	Id, Name string
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-
+-	s0 := resp.StateChanges[0]
+-	c.Assert(s0.InstanceId, Equals, "i-10a64379")
+-	c.Assert(s0.CurrentState.Code, Equals, 64)
+-	c.Assert(s0.CurrentState.Name, Equals, "stopping")
+-	c.Assert(s0.PreviousState.Code, Equals, 16)
+-	c.Assert(s0.PreviousState.Name, Equals, "running")
 -}
 -
--type UserResource struct {
--	// normally one would use DAO (data access object)
--	users map[string]User
+-func (s *S) TestRebootInstances(c *C) {
+-	testServer.Response(200, nil, RebootInstancesExample)
+-
+-	resp, err := s.ec2.RebootInstances("i-10a64379")
+-	req := testServer.WaitRequest()
+-
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"RebootInstances"})
+-	c.Assert(req.Form["InstanceId.1"], DeepEquals, []string{"i-10a64379"})
+-
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
 -}
 -
--func (u UserResource) Register(container *restful.Container) {
--	ws := new(restful.WebService)
--	ws.
--		Path("/users").
--		Consumes(restful.MIME_XML, restful.MIME_JSON).
--		Produces(restful.MIME_JSON, restful.MIME_XML) // you can specify this per route as well
+-func (s *S) TestSignatureWithEndpointPath(c *C) {
+-	ec2.FakeTime(true)
+-	defer ec2.FakeTime(false)
 -
--	ws.Route(ws.GET("/{user-id}").To(u.findUser))
--	ws.Route(ws.POST("").To(u.updateUser))
--	ws.Route(ws.PUT("/{user-id}").To(u.createUser))
--	ws.Route(ws.DELETE("/{user-id}").To(u.removeUser))
+-	testServer.Response(200, nil, RebootInstancesExample)
+-
+-	// https://bugs.launchpad.net/goamz/+bug/1022749
+-	ec2 := ec2.NewWithClient(s.ec2.Auth, aws.Region{EC2Endpoint: testServer.URL + "/services/Cloud"}, testutil.DefaultClient)
+-
+-	_, err := ec2.RebootInstances("i-10a64379")
+-	c.Assert(err, IsNil)
 -
--	container.Add(ws)
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Signature"], DeepEquals, []string{"QmvgkYGn19WirCuCz/jRp3RmRgFwWR5WRkKZ5AZnyXQ="})
 -}
 -
--// GET http://localhost:8080/users/1
--//
--func (u UserResource) findUser(request *restful.Request, response *restful.Response) {
--	id := request.PathParameter("user-id")
--	usr := u.users[id]
--	if len(usr.Id) == 0 {
--		response.AddHeader("Content-Type", "text/plain")
--		response.WriteErrorString(http.StatusNotFound, "User could not be found.")
--	} else {
--		response.WriteEntity(usr)
--	}
--}
+-func (s *S) TestAllocateAddressExample(c *C) {
+-	testServer.Response(200, nil, AllocateAddressExample)
 -
--// POST http://localhost:8080/users
--// <User><Id>1</Id><Name>Melissa Raspberry</Name></User>
--//
--func (u *UserResource) updateUser(request *restful.Request, response *restful.Response) {
--	usr := new(User)
--	err := request.ReadEntity(&usr)
--	if err == nil {
--		u.users[usr.Id] = *usr
--		response.WriteEntity(usr)
--	} else {
--		response.AddHeader("Content-Type", "text/plain")
--		response.WriteErrorString(http.StatusInternalServerError, err.Error())
+-	options := &ec2.AllocateAddress{
+-		Domain: "vpc",
 -	}
--}
 -
--// PUT http://localhost:8080/users/1
--// <User><Id>1</Id><Name>Melissa</Name></User>
--//
--func (u *UserResource) createUser(request *restful.Request, response *restful.Response) {
--	usr := User{Id: request.PathParameter("user-id")}
--	err := request.ReadEntity(&usr)
--	if err == nil {
--		u.users[usr.Id] = usr
--		response.WriteHeader(http.StatusCreated)
--		response.WriteEntity(usr)
--	} else {
--		response.AddHeader("Content-Type", "text/plain")
--		response.WriteErrorString(http.StatusInternalServerError, err.Error())
--	}
--}
+-	resp, err := s.ec2.AllocateAddress(options)
 -
--// DELETE http://localhost:8080/users/1
--//
--func (u *UserResource) removeUser(request *restful.Request, response *restful.Response) {
--	id := request.PathParameter("user-id")
--	delete(u.users, id)
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"AllocateAddress"})
+-	c.Assert(req.Form["Domain"], DeepEquals, []string{"vpc"})
+-
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	c.Assert(resp.PublicIp, Equals, "198.51.100.1")
+-	c.Assert(resp.Domain, Equals, "vpc")
+-	c.Assert(resp.AllocationId, Equals, "eipalloc-5723d13e")
 -}
 -
--func main() {
--	wsContainer := restful.NewContainer()
--	wsContainer.Router(restful.CurlyRouter{})
--	u := UserResource{map[string]User{}}
--	u.Register(wsContainer)
+-func (s *S) TestReleaseAddressExample(c *C) {
+-	testServer.Response(200, nil, ReleaseAddressExample)
 -
--	log.Printf("start listening on localhost:8080")
--	server := &http.Server{Addr: ":8080", Handler: wsContainer}
--	log.Fatal(server.ListenAndServe())
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-encoding-filter.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-encoding-filter.go
-deleted file mode 100644
-index 6094c49..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-encoding-filter.go
-+++ /dev/null
-@@ -1,61 +0,0 @@
--package main
+-	resp, err := s.ec2.ReleaseAddress("eipalloc-5723d13e")
 -
--import (
--	"github.com/emicklei/go-restful"
--	"log"
--	"net/http"
--)
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"ReleaseAddress"})
+-	c.Assert(req.Form["AllocationId"], DeepEquals, []string{"eipalloc-5723d13e"})
 -
--type User struct {
--	Id, Name string
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
 -}
 -
--type UserList struct {
--	Users []User
--}
+-func (s *S) TestAssociateAddressExample(c *C) {
+-	testServer.Response(200, nil, AssociateAddressExample)
 -
--//
--// This example shows how to use the CompressingResponseWriter by a Filter
--// such that encoding can be enabled per WebService or per Route (instead of per container)
--// Using restful.DefaultContainer.EnableContentEncoding(true) will encode all responses served by WebServices in the DefaultContainer.
--//
--// Set Accept-Encoding to gzip or deflate
--// GET http://localhost:8080/users/42
--// and look at the response headers
+-	options := &ec2.AssociateAddress{
+-		InstanceId:         "i-4fd2431a",
+-		AllocationId:       "eipalloc-5723d13e",
+-		AllowReassociation: true,
+-	}
 -
--func main() {
--	restful.Add(NewUserService())
--	log.Printf("start listening on localhost:8080")
--	log.Fatal(http.ListenAndServe(":8080", nil))
--}
+-	resp, err := s.ec2.AssociateAddress(options)
 -
--func NewUserService() *restful.WebService {
--	ws := new(restful.WebService)
--	ws.
--		Path("/users").
--		Consumes(restful.MIME_XML, restful.MIME_JSON).
--		Produces(restful.MIME_JSON, restful.MIME_XML)
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"AssociateAddress"})
+-	c.Assert(req.Form["InstanceId"], DeepEquals, []string{"i-4fd2431a"})
+-	c.Assert(req.Form["AllocationId"], DeepEquals, []string{"eipalloc-5723d13e"})
+-	c.Assert(req.Form["AllowReassociation"], DeepEquals, []string{"true"})
 -
--	// install a response encoding filter
--	ws.Route(ws.GET("/{user-id}").Filter(encodingFilter).To(findUser))
--	return ws
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	c.Assert(resp.AssociationId, Equals, "eipassoc-fc5ca095")
 -}
 -
--// Route Filter (defines FilterFunction)
--func encodingFilter(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
--	log.Printf("[encoding-filter] %s,%s\n", req.Request.Method, req.Request.URL)
--	// wrap responseWriter into a compressing one
--	compress, _ := restful.NewCompressingResponseWriter(resp.ResponseWriter, restful.ENCODING_GZIP)
--	resp.ResponseWriter = compress
--	defer func() {
--		compress.Close()
--	}()
--	chain.ProcessFilter(req, resp)
--}
+-func (s *S) TestDisassociateAddressExample(c *C) {
+-	testServer.Response(200, nil, DisassociateAddressExample)
 -
--// GET http://localhost:8080/users/42
--//
--func findUser(request *restful.Request, response *restful.Response) {
--	log.Printf("findUser")
--	response.WriteEntity(User{"42", "Gandalf"})
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-filters.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-filters.go
-deleted file mode 100644
-index 47e1146..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-filters.go
-+++ /dev/null
-@@ -1,114 +0,0 @@
--package main
+-	resp, err := s.ec2.DisassociateAddress("eipassoc-aa7486c3")
 -
--import (
--	"github.com/emicklei/go-restful"
--	"log"
--	"net/http"
--	"time"
--)
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"DisassociateAddress"})
+-	c.Assert(req.Form["AssociationId"], DeepEquals, []string{"eipassoc-aa7486c3"})
 -
--type User struct {
--	Id, Name string
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
 -}
 -
--type UserList struct {
--	Users []User
--}
+-func (s *S) TestModifyInstance(c *C) {
+-	testServer.Response(200, nil, ModifyInstanceExample)
 -
--// This example show how to create and use the three different Filters (Container,WebService and Route)
--// When applied to the restful.DefaultContainer, we refer to them as a global filter.
--//
--// GET  http://locahost:8080/users/42
--// and see the logging per filter (try repeating this request)
+-	options := ec2.ModifyInstance{
+-		InstanceType:          "m1.small",
+-		DisableAPITermination: true,
+-		EbsOptimized:          true,
+-		SecurityGroups:        []ec2.SecurityGroup{{Id: "g1"}, {Id: "g2"}},
+-		ShutdownBehavior:      "terminate",
+-		KernelId:              "kernel-id",
+-		RamdiskId:             "ramdisk-id",
+-		SourceDestCheck:       true,
+-		SriovNetSupport:       true,
+-		UserData:              []byte("1234"),
+-		BlockDevices: []ec2.BlockDeviceMapping{
+-			{DeviceName: "/dev/sda1", SnapshotId: "snap-a08912c9", DeleteOnTermination: true},
+-		},
+-	}
 -
--func main() {
--	// install a global (=DefaultContainer) filter (processed before any webservice in the DefaultContainer)
--	restful.Filter(globalLogging)
+-	resp, err := s.ec2.ModifyInstance("i-2ba64342", &options)
+-	req := testServer.WaitRequest()
 -
--	restful.Add(NewUserService())
--	log.Printf("start listening on localhost:8080")
--	log.Fatal(http.ListenAndServe(":8080", nil))
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"ModifyInstanceAttribute"})
+-	c.Assert(req.Form["InstanceId"], DeepEquals, []string{"i-2ba64342"})
+-	c.Assert(req.Form["InstanceType.Value"], DeepEquals, []string{"m1.small"})
+-	c.Assert(req.Form["BlockDeviceMapping.1.DeviceName"], DeepEquals, []string{"/dev/sda1"})
+-	c.Assert(req.Form["BlockDeviceMapping.1.Ebs.SnapshotId"], DeepEquals, []string{"snap-a08912c9"})
+-	c.Assert(req.Form["BlockDeviceMapping.1.Ebs.DeleteOnTermination"], DeepEquals, []string{"true"})
+-	c.Assert(req.Form["DisableApiTermination.Value"], DeepEquals, []string{"true"})
+-	c.Assert(req.Form["EbsOptimized"], DeepEquals, []string{"true"})
+-	c.Assert(req.Form["GroupId.1"], DeepEquals, []string{"g1"})
+-	c.Assert(req.Form["GroupId.2"], DeepEquals, []string{"g2"})
+-	c.Assert(req.Form["InstanceInitiatedShutdownBehavior.Value"], DeepEquals, []string{"terminate"})
+-	c.Assert(req.Form["Kernel.Value"], DeepEquals, []string{"kernel-id"})
+-	c.Assert(req.Form["Ramdisk.Value"], DeepEquals, []string{"ramdisk-id"})
+-	c.Assert(req.Form["SourceDestCheck.Value"], DeepEquals, []string{"true"})
+-	c.Assert(req.Form["SriovNetSupport.Value"], DeepEquals, []string{"simple"})
+-	c.Assert(req.Form["UserData"], DeepEquals, []string{"MTIzNA=="})
+-
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
 -}
 -
--func NewUserService() *restful.WebService {
--	ws := new(restful.WebService)
--	ws.
--		Path("/users").
--		Consumes(restful.MIME_XML, restful.MIME_JSON).
--		Produces(restful.MIME_JSON, restful.MIME_XML)
+-func (s *S) TestCreateVpc(c *C) {
+-	testServer.Response(200, nil, CreateVpcExample)
 -
--	// install a webservice filter (processed before any route)
--	ws.Filter(webserviceLogging).Filter(measureTime)
+-	options := &ec2.CreateVpc{
+-		CidrBlock: "foo",
+-	}
 -
--	// install a counter filter
--	ws.Route(ws.GET("").Filter(NewCountFilter().routeCounter).To(getAllUsers))
+-	resp, err := s.ec2.CreateVpc(options)
 -
--	// install 2 chained route filters (processed before calling findUser)
--	ws.Route(ws.GET("/{user-id}").Filter(routeLogging).Filter(NewCountFilter().routeCounter).To(findUser))
--	return ws
--}
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["CidrBlock"], DeepEquals, []string{"foo"})
 -
--// Global Filter
--func globalLogging(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
--	log.Printf("[global-filter (logger)] %s,%s\n", req.Request.Method, req.Request.URL)
--	chain.ProcessFilter(req, resp)
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "7a62c49f-347e-4fc4-9331-6e8eEXAMPLE")
+-	c.Assert(resp.VPC.VpcId, Equals, "vpc-1a2b3c4d")
+-	c.Assert(resp.VPC.State, Equals, "pending")
+-	c.Assert(resp.VPC.CidrBlock, Equals, "10.0.0.0/16")
+-	c.Assert(resp.VPC.DHCPOptionsID, Equals, "dopt-1a2b3c4d2")
+-	c.Assert(resp.VPC.InstanceTenancy, Equals, "default")
 -}
 -
--// WebService Filter
--func webserviceLogging(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
--	log.Printf("[webservice-filter (logger)] %s,%s\n", req.Request.Method, req.Request.URL)
--	chain.ProcessFilter(req, resp)
--}
+-func (s *S) TestDescribeVpcs(c *C) {
+-	testServer.Response(200, nil, DescribeVpcsExample)
 -
--// WebService (post-process) Filter (as a struct that defines a FilterFunction)
--func measureTime(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
--	now := time.Now()
--	chain.ProcessFilter(req, resp)
--	log.Printf("[webservice-filter (timer)] %v\n", time.Now().Sub(now))
--}
+-	filter := ec2.NewFilter()
+-	filter.Add("key1", "value1")
+-	filter.Add("key2", "value2", "value3")
 -
--// Route Filter (defines FilterFunction)
--func routeLogging(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
--	log.Printf("[route-filter (logger)] %s,%s\n", req.Request.Method, req.Request.URL)
--	chain.ProcessFilter(req, resp)
--}
+-	resp, err := s.ec2.DescribeVpcs([]string{"id1", "id2"}, filter)
 -
--// Route Filter (as a struct that defines a FilterFunction)
--// CountFilter implements a FilterFunction for counting requests.
--type CountFilter struct {
--	count   int
--	counter chan int // for go-routine safe count increments
--}
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeVpcs"})
+-	c.Assert(req.Form["VpcId.1"], DeepEquals, []string{"id1"})
+-	c.Assert(req.Form["VpcId.2"], DeepEquals, []string{"id2"})
+-	c.Assert(req.Form["Filter.1.Name"], DeepEquals, []string{"key1"})
+-	c.Assert(req.Form["Filter.1.Value.1"], DeepEquals, []string{"value1"})
+-	c.Assert(req.Form["Filter.1.Value.2"], IsNil)
+-	c.Assert(req.Form["Filter.2.Name"], DeepEquals, []string{"key2"})
+-	c.Assert(req.Form["Filter.2.Value.1"], DeepEquals, []string{"value2"})
+-	c.Assert(req.Form["Filter.2.Value.2"], DeepEquals, []string{"value3"})
 -
--// NewCountFilter creates and initializes a new CountFilter.
--func NewCountFilter() *CountFilter {
--	c := new(CountFilter)
--	c.counter = make(chan int)
--	go func() {
--		for {
--			c.count += <-c.counter
--		}
--	}()
--	return c
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "7a62c49f-347e-4fc4-9331-6e8eEXAMPLE")
+-	c.Assert(resp.VPCs, HasLen, 1)
 -}
 -
--// routeCounter increments the count of the filter (through a channel)
--func (c *CountFilter) routeCounter(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
--	c.counter <- 1
--	log.Printf("[route-filter (counter)] count:%d", c.count)
--	chain.ProcessFilter(req, resp)
--}
+-func (s *S) TestCreateSubnet(c *C) {
+-	testServer.Response(200, nil, CreateSubnetExample)
 -
--// GET http://localhost:8080/users
--//
--func getAllUsers(request *restful.Request, response *restful.Response) {
--	log.Printf("getAllUsers")
--	response.WriteEntity(UserList{[]User{User{"42", "Gandalf"}, User{"3.14", "Pi"}}})
+-	options := &ec2.CreateSubnet{
+-		AvailabilityZone: "baz",
+-		CidrBlock:        "foo",
+-		VpcId:            "bar",
+-	}
+-
+-	resp, err := s.ec2.CreateSubnet(options)
+-
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["VpcId"], DeepEquals, []string{"bar"})
+-	c.Assert(req.Form["CidrBlock"], DeepEquals, []string{"foo"})
+-	c.Assert(req.Form["AvailabilityZone"], DeepEquals, []string{"baz"})
+-
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "7a62c49f-347e-4fc4-9331-6e8eEXAMPLE")
+-	c.Assert(resp.Subnet.SubnetId, Equals, "subnet-9d4a7b6c")
+-	c.Assert(resp.Subnet.State, Equals, "pending")
+-	c.Assert(resp.Subnet.VpcId, Equals, "vpc-1a2b3c4d")
+-	c.Assert(resp.Subnet.CidrBlock, Equals, "10.0.1.0/24")
+-	c.Assert(resp.Subnet.AvailableIpAddressCount, Equals, 251)
 -}
 -
--// GET http://localhost:8080/users/42
--//
--func findUser(request *restful.Request, response *restful.Response) {
--	log.Printf("findUser")
--	response.WriteEntity(User{"42", "Gandalf"})
+-func (s *S) TestResetImageAttribute(c *C) {
+-	testServer.Response(200, nil, ResetImageAttributeExample)
+-
+-	options := ec2.ResetImageAttribute{Attribute: "launchPermission"}
+-	resp, err := s.ec2.ResetImageAttribute("i-2ba64342", &options)
+-
+-	req := testServer.WaitRequest()
+-	c.Assert(req.Form["Action"], DeepEquals, []string{"ResetImageAttribute"})
+-
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-form-handling.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-form-handling.go
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2i_test.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2i_test.go
 deleted file mode 100644
-index a83db44..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-form-handling.go
+index 3773041..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2i_test.go
 +++ /dev/null
-@@ -1,62 +0,0 @@
--package main
+@@ -1,203 +0,0 @@
+-package ec2_test
 -
 -import (
+-	"crypto/rand"
 -	"fmt"
--	"github.com/emicklei/go-restful"
--	"github.com/gorilla/schema"
--	"io"
--	"net/http"
+-	"github.com/mitchellh/goamz/aws"
+-	"github.com/mitchellh/goamz/ec2"
+-	"github.com/mitchellh/goamz/testutil"
+-	. "github.com/motain/gocheck"
 -)
 -
--// This example shows how to handle a POST of a HTML form that uses the standard x-www-form-urlencoded content-type.
--// It uses the gorilla web tool kit schema package to decode the form data into a struct.
--//
--// GET http://localhost:8080/profiles
--//
--
--type Profile struct {
--	Name string
--	Age  int
--}
--
--var decoder *schema.Decoder
--
--func main() {
--	decoder = schema.NewDecoder()
--	ws := new(restful.WebService)
--	ws.Route(ws.POST("/profiles").Consumes("application/x-www-form-urlencoded").To(postAdddress))
--	ws.Route(ws.GET("/profiles").To(addresssForm))
--	restful.Add(ws)
--	http.ListenAndServe(":8080", nil)
+-// AmazonServer represents an Amazon EC2 server.
+-type AmazonServer struct {
+-	auth aws.Auth
 -}
 -
--func postAdddress(req *restful.Request, resp *restful.Response) {
--	err := req.Request.ParseForm()
--	if err != nil {
--		resp.WriteErrorString(http.StatusBadRequest, err.Error())
--		return
--	}
--	p := new(Profile)
--	err = decoder.Decode(p, req.Request.PostForm)
+-func (s *AmazonServer) SetUp(c *C) {
+-	auth, err := aws.EnvAuth()
 -	if err != nil {
--		resp.WriteErrorString(http.StatusBadRequest, err.Error())
--		return
+-		c.Fatal(err.Error())
 -	}
--	io.WriteString(resp.ResponseWriter, fmt.Sprintf("<html><body>Name=%s, Age=%d</body></html>", p.Name, p.Age))
--}
--
--func addresssForm(req *restful.Request, resp *restful.Response) {
--	io.WriteString(resp.ResponseWriter,
--		`<html>
--		<body>
--		<h1>Enter Profile</h1>
--		<form method="post">
--		    <label>Name:</label>
--			<input type="text" name="Name"/>
--			<label>Age:</label>
--		    <input type="text" name="Age"/>
--			<input type="Submit" />
--		</form>
--		</body>
--		</html>`)
+-	s.auth = auth
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-hello-world.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-hello-world.go
-deleted file mode 100644
-index a21c2a6..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-hello-world.go
-+++ /dev/null
-@@ -1,22 +0,0 @@
--package main
 -
--import (
--	"github.com/emicklei/go-restful"
--	"io"
--	"net/http"
--)
+-// Suite cost per run: 0.02 USD
+-var _ = Suite(&AmazonClientSuite{})
 -
--// This example shows the minimal code needed to get a restful.WebService working.
--//
--// GET http://localhost:8080/hello
+-// AmazonClientSuite tests the client against a live EC2 server.
+-type AmazonClientSuite struct {
+-	srv AmazonServer
+-	ClientTests
+-}
 -
--func main() {
--	ws := new(restful.WebService)
--	ws.Route(ws.GET("/hello").To(hello))
--	restful.Add(ws)
--	http.ListenAndServe(":8080", nil)
+-func (s *AmazonClientSuite) SetUpSuite(c *C) {
+-	if !testutil.Amazon {
+-		c.Skip("AmazonClientSuite tests not enabled")
+-	}
+-	s.srv.SetUp(c)
+-	s.ec2 = ec2.NewWithClient(s.srv.auth, aws.USEast, testutil.DefaultClient)
 -}
 -
--func hello(req *restful.Request, resp *restful.Response) {
--	io.WriteString(resp, "world")
+-// ClientTests defines integration tests designed to test the client.
+-// It is not used as a test suite in itself, but embedded within
+-// another type.
+-type ClientTests struct {
+-	ec2 *ec2.EC2
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-html-template.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-html-template.go
-deleted file mode 100644
-index de51c59..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-html-template.go
-+++ /dev/null
-@@ -1,35 +0,0 @@
--package main
 -
--import (
--	"log"
--	"net/http"
--	"text/template"
+-var imageId = "ami-ccf405a5" // Ubuntu Maverick, i386, EBS store
 -
--	"github.com/emicklei/go-restful"
--)
+-// Cost: 0.00 USD
+-func (s *ClientTests) TestRunInstancesError(c *C) {
+-	options := ec2.RunInstances{
+-		ImageId:      "ami-a6f504cf", // Ubuntu Maverick, i386, instance store
+-		InstanceType: "t1.micro",     // Doesn't work with micro, results in 400.
+-	}
 -
--// This example shows how to serve a HTML page using the standard Go template engine.
--//
--// GET http://localhost:8080/
+-	resp, err := s.ec2.RunInstances(&options)
 -
--func main() {
--	ws := new(restful.WebService)
--	ws.Route(ws.GET("/").To(home))
--	restful.Add(ws)
--	print("open browser on http://localhost:8080/\n")
--	http.ListenAndServe(":8080", nil)
--}
+-	c.Assert(resp, IsNil)
+-	c.Assert(err, ErrorMatches, "AMI.*root device.*not supported.*")
 -
--type Message struct {
--	Text string
+-	ec2err, ok := err.(*ec2.Error)
+-	c.Assert(ok, Equals, true)
+-	c.Assert(ec2err.StatusCode, Equals, 400)
+-	c.Assert(ec2err.Code, Equals, "UnsupportedOperation")
+-	c.Assert(ec2err.Message, Matches, "AMI.*root device.*not supported.*")
+-	c.Assert(ec2err.RequestId, Matches, ".+")
 -}
 -
--func home(req *restful.Request, resp *restful.Response) {
--	p := &Message{"restful-html-template demo"}
--	// you might want to cache compiled templates
--	t, err := template.ParseFiles("home.html")
--	if err != nil {
--		log.Fatalf("Template gave: %s", err)
+-// Cost: 0.02 USD
+-func (s *ClientTests) TestRunAndTerminate(c *C) {
+-	options := ec2.RunInstances{
+-		ImageId:      imageId,
+-		InstanceType: "t1.micro",
 -	}
--	t.Execute(resp.ResponseWriter, p)
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-multi-containers.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-multi-containers.go
-deleted file mode 100644
-index 3f1650b..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-multi-containers.go
-+++ /dev/null
-@@ -1,43 +0,0 @@
--package main
--
--import (
--	"github.com/emicklei/go-restful"
--	"io"
--	"log"
--	"net/http"
--)
+-	resp1, err := s.ec2.RunInstances(&options)
+-	c.Assert(err, IsNil)
+-	c.Check(resp1.ReservationId, Matches, "r-[0-9a-f]*")
+-	c.Check(resp1.OwnerId, Matches, "[0-9]+")
+-	c.Check(resp1.Instances, HasLen, 1)
+-	c.Check(resp1.Instances[0].InstanceType, Equals, "t1.micro")
 -
--// This example shows how to have a program with 2 WebServices containers
--// each having a http server listening on its own port.
--//
--// The first "hello" is added to the restful.DefaultContainer (and uses DefaultServeMux)
--// For the second "hello", a new container and ServeMux is created
--// and requires a new http.Server with the container being the Handler.
--// This first server is spawn in its own go-routine such that the program proceeds to create the second.
--//
--// GET http://localhost:8080/hello
--// GET http://localhost:8081/hello
+-	instId := resp1.Instances[0].InstanceId
 -
--func main() {
--	ws := new(restful.WebService)
--	ws.Route(ws.GET("/hello").To(hello))
--	restful.Add(ws)
--	go func() {
--		http.ListenAndServe(":8080", nil)
--	}()
+-	resp2, err := s.ec2.Instances([]string{instId}, nil)
+-	c.Assert(err, IsNil)
+-	if c.Check(resp2.Reservations, HasLen, 1) && c.Check(len(resp2.Reservations[0].Instances), Equals, 1) {
+-		inst := resp2.Reservations[0].Instances[0]
+-		c.Check(inst.InstanceId, Equals, instId)
+-	}
 -
--	container2 := restful.NewContainer()
--	ws2 := new(restful.WebService)
--	ws2.Route(ws2.GET("/hello").To(hello2))
--	container2.Add(ws2)
--	server := &http.Server{Addr: ":8081", Handler: container2}
--	log.Fatal(server.ListenAndServe())
+-	resp3, err := s.ec2.TerminateInstances([]string{instId})
+-	c.Assert(err, IsNil)
+-	c.Check(resp3.StateChanges, HasLen, 1)
+-	c.Check(resp3.StateChanges[0].InstanceId, Equals, instId)
+-	c.Check(resp3.StateChanges[0].CurrentState.Name, Equals, "shutting-down")
+-	c.Check(resp3.StateChanges[0].CurrentState.Code, Equals, 32)
 -}
 -
--func hello(req *restful.Request, resp *restful.Response) {
--	io.WriteString(resp, "default world")
--}
+-// Cost: 0.00 USD
+-func (s *ClientTests) TestSecurityGroups(c *C) {
+-	name := "goamz-test"
+-	descr := "goamz security group for tests"
 -
--func hello2(req *restful.Request, resp *restful.Response) {
--	io.WriteString(resp, "second world")
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-options-filter.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-options-filter.go
-deleted file mode 100644
-index 73dc3cf..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-options-filter.go
-+++ /dev/null
-@@ -1,51 +0,0 @@
--package main
+-	// Clean it up, if a previous test left it around and avoid leaving it around.
+-	s.ec2.DeleteSecurityGroup(ec2.SecurityGroup{Name: name})
+-	defer s.ec2.DeleteSecurityGroup(ec2.SecurityGroup{Name: name})
 -
--import (
--	"github.com/emicklei/go-restful"
--	"io"
--	"log"
--	"net/http"
--)
+-	resp1, err := s.ec2.CreateSecurityGroup(ec2.SecurityGroup{Name: name, Description: descr})
+-	c.Assert(err, IsNil)
+-	c.Assert(resp1.RequestId, Matches, ".+")
+-	c.Assert(resp1.Name, Equals, name)
+-	c.Assert(resp1.Id, Matches, ".+")
 -
--// This example shows how to use the OPTIONSFilter on a Container
--//
--// OPTIONS http://localhost:8080/users
--//
--// OPTIONS http://localhost:8080/users/1
+-	resp1, err = s.ec2.CreateSecurityGroup(ec2.SecurityGroup{Name: name, Description: descr})
+-	ec2err, _ := err.(*ec2.Error)
+-	c.Assert(resp1, IsNil)
+-	c.Assert(ec2err, NotNil)
+-	c.Assert(ec2err.Code, Equals, "InvalidGroup.Duplicate")
 -
--type UserResource struct{}
+-	perms := []ec2.IPPerm{{
+-		Protocol:  "tcp",
+-		FromPort:  0,
+-		ToPort:    1024,
+-		SourceIPs: []string{"127.0.0.1/24"},
+-	}}
 -
--func (u UserResource) RegisterTo(container *restful.Container) {
--	ws := new(restful.WebService)
--	ws.
--		Path("/users").
--		Consumes("*/*").
--		Produces("*/*")
+-	resp2, err := s.ec2.AuthorizeSecurityGroup(ec2.SecurityGroup{Name: name}, perms)
+-	c.Assert(err, IsNil)
+-	c.Assert(resp2.RequestId, Matches, ".+")
 -
--	ws.Route(ws.GET("/{user-id}").To(u.nop))
--	ws.Route(ws.POST("").To(u.nop))
--	ws.Route(ws.PUT("/{user-id}").To(u.nop))
--	ws.Route(ws.DELETE("/{user-id}").To(u.nop))
+-	resp3, err := s.ec2.SecurityGroups(ec2.SecurityGroupNames(name), nil)
+-	c.Assert(err, IsNil)
+-	c.Assert(resp3.RequestId, Matches, ".+")
+-	c.Assert(resp3.Groups, HasLen, 1)
 -
--	container.Add(ws)
--}
+-	g0 := resp3.Groups[0]
+-	c.Assert(g0.Name, Equals, name)
+-	c.Assert(g0.Description, Equals, descr)
+-	c.Assert(g0.IPPerms, HasLen, 1)
+-	c.Assert(g0.IPPerms[0].Protocol, Equals, "tcp")
+-	c.Assert(g0.IPPerms[0].FromPort, Equals, 0)
+-	c.Assert(g0.IPPerms[0].ToPort, Equals, 1024)
+-	c.Assert(g0.IPPerms[0].SourceIPs, DeepEquals, []string{"127.0.0.1/24"})
 -
--func (u UserResource) nop(request *restful.Request, response *restful.Response) {
--	io.WriteString(response.ResponseWriter, "this would be a normal response")
+-	resp2, err = s.ec2.DeleteSecurityGroup(ec2.SecurityGroup{Name: name})
+-	c.Assert(err, IsNil)
+-	c.Assert(resp2.RequestId, Matches, ".+")
 -}
 -
--func main() {
--	wsContainer := restful.NewContainer()
--	u := UserResource{}
--	u.RegisterTo(wsContainer)
+-var sessionId = func() string {
+-	buf := make([]byte, 8)
+-	// if we have no randomness, we'll just make do, so ignore the error.
+-	rand.Read(buf)
+-	return fmt.Sprintf("%x", buf)
+-}()
 -
--	// Add container filter to respond to OPTIONS
--	wsContainer.Filter(wsContainer.OPTIONSFilter)
+-// sessionName reutrns a name that is probably
+-// unique to this test session.
+-func sessionName(prefix string) string {
+-	return prefix + "-" + sessionId
+-}
 -
--	// For use on the default container, you can write
--	// restful.Filter(restful.OPTIONSFilter())
+-var allRegions = []aws.Region{
+-	aws.USEast,
+-	aws.USWest,
+-	aws.EUWest,
+-	aws.APSoutheast,
+-	aws.APNortheast,
+-}
 -
--	log.Printf("start listening on localhost:8080")
--	server := &http.Server{Addr: ":8080", Handler: wsContainer}
--	log.Fatal(server.ListenAndServe())
+-// Communicate with all EC2 endpoints to see if they are alive.
+-func (s *ClientTests) TestRegions(c *C) {
+-	name := sessionName("goamz-region-test")
+-	perms := []ec2.IPPerm{{
+-		Protocol:  "tcp",
+-		FromPort:  80,
+-		ToPort:    80,
+-		SourceIPs: []string{"127.0.0.1/32"},
+-	}}
+-	errs := make(chan error, len(allRegions))
+-	for _, region := range allRegions {
+-		go func(r aws.Region) {
+-			e := ec2.NewWithClient(s.ec2.Auth, r, testutil.DefaultClient)
+-			_, err := e.AuthorizeSecurityGroup(ec2.SecurityGroup{Name: name}, perms)
+-			errs <- err
+-		}(region)
+-	}
+-	for _ = range allRegions {
+-		err := <-errs
+-		if err != nil {
+-			ec2_err, ok := err.(*ec2.Error)
+-			if ok {
+-				c.Check(ec2_err.Code, Matches, "InvalidGroup.NotFound")
+-			} else {
+-				c.Errorf("Non-EC2 error: %s", err)
+-			}
+-		} else {
+-			c.Errorf("Test should have errored but it seems to have succeeded")
+-		}
+-	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-path-tail.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-path-tail.go
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2t_test.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2t_test.go
 deleted file mode 100644
-index 8488a23..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-path-tail.go
+index fe50356..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2t_test.go
 +++ /dev/null
-@@ -1,26 +0,0 @@
--package main
+@@ -1,580 +0,0 @@
+-package ec2_test
 -
 -import (
--	"io"
--	"net/http"
--	. "github.com/emicklei/go-restful"
+-	"fmt"
+-	"github.com/mitchellh/goamz/aws"
+-	"github.com/mitchellh/goamz/ec2"
+-	"github.com/mitchellh/goamz/ec2/ec2test"
+-	"github.com/mitchellh/goamz/testutil"
+-	. "github.com/motain/gocheck"
+-	"regexp"
+-	"sort"
 -)
 -
--// This example shows how to a Route that matches the "tail" of a path.
--// Requires the use of a CurlyRouter and the star "*" path parameter pattern.
--//
--// GET http://localhost:8080/basepath/some/other/location/test.xml
+-// LocalServer represents a local ec2test fake server.
+-type LocalServer struct {
+-	auth   aws.Auth
+-	region aws.Region
+-	srv    *ec2test.Server
+-}
 -
--func main() {
--	DefaultContainer.Router(CurlyRouter{})
--	ws := new(WebService)
--	ws.Route(ws.GET("/basepath/{resource:*}").To(staticFromPathParam))
--	Add(ws)
+-func (s *LocalServer) SetUp(c *C) {
+-	srv, err := ec2test.NewServer()
+-	c.Assert(err, IsNil)
+-	c.Assert(srv, NotNil)
 -
--	println("[go-restful] serve path tails from http://localhost:8080/basepath")
--	http.ListenAndServe(":8080", nil)
+-	s.srv = srv
+-	s.region = aws.Region{EC2Endpoint: srv.URL()}
 -}
 -
--func staticFromPathParam(req *Request, resp *Response) {
--	io.WriteString(resp, "Tail="+req.PathParameter("resource"))
+-// LocalServerSuite defines tests that will run
+-// against the local ec2test server. It includes
+-// selected tests from ClientTests;
+-// when the ec2test functionality is sufficient, it should
+-// include all of them, and ClientTests can be simply embedded.
+-type LocalServerSuite struct {
+-	srv LocalServer
+-	ServerTests
+-	clientTests ClientTests
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-pre-post-filters.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-pre-post-filters.go
-deleted file mode 100644
-index 0b55f14..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-pre-post-filters.go
-+++ /dev/null
-@@ -1,98 +0,0 @@
--package main
--
--import (
--	"github.com/emicklei/go-restful"
--	"io"
--	"log"
--	"net/http"
--)
 -
--// This example shows how the different types of filters are called in the request-response flow.
--// The call chain is logged on the console when sending an http request.
--//
--// GET http://localhost:8080/1
--// GET http://localhost:8080/2
+-var _ = Suite(&LocalServerSuite{})
 -
--var indentLevel int
+-func (s *LocalServerSuite) SetUpSuite(c *C) {
+-	s.srv.SetUp(c)
+-	s.ServerTests.ec2 = ec2.NewWithClient(s.srv.auth, s.srv.region, testutil.DefaultClient)
+-	s.clientTests.ec2 = ec2.NewWithClient(s.srv.auth, s.srv.region, testutil.DefaultClient)
+-}
 -
--func container_filter_A(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
--	log.Printf("url path:%v\n", req.Request.URL)
--	trace("container_filter_A: before", 1)
--	chain.ProcessFilter(req, resp)
--	trace("container_filter_A: after", -1)
+-func (s *LocalServerSuite) TestRunAndTerminate(c *C) {
+-	s.clientTests.TestRunAndTerminate(c)
 -}
 -
--func container_filter_B(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
--	trace("container_filter_B: before", 1)
--	chain.ProcessFilter(req, resp)
--	trace("container_filter_B: after", -1)
+-func (s *LocalServerSuite) TestSecurityGroups(c *C) {
+-	s.clientTests.TestSecurityGroups(c)
 -}
 -
--func service_filter_A(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
--	trace("service_filter_A: before", 1)
--	chain.ProcessFilter(req, resp)
--	trace("service_filter_A: after", -1)
+-// TestUserData is not defined on ServerTests because it
+-// requires the ec2test server to function.
+-func (s *LocalServerSuite) TestUserData(c *C) {
+-	data := make([]byte, 256)
+-	for i := range data {
+-		data[i] = byte(i)
+-	}
+-	inst, err := s.ec2.RunInstances(&ec2.RunInstances{
+-		ImageId:      imageId,
+-		InstanceType: "t1.micro",
+-		UserData:     data,
+-	})
+-	c.Assert(err, IsNil)
+-	c.Assert(inst, NotNil)
+-	c.Assert(inst.Instances[0].DNSName, Equals, inst.Instances[0].InstanceId+".example.com")
+-
+-	id := inst.Instances[0].InstanceId
+-
+-	defer s.ec2.TerminateInstances([]string{id})
+-
+-	tinst := s.srv.srv.Instance(id)
+-	c.Assert(tinst, NotNil)
+-	c.Assert(tinst.UserData, DeepEquals, data)
 -}
 -
--func service_filter_B(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
--	trace("service_filter_B: before", 1)
--	chain.ProcessFilter(req, resp)
--	trace("service_filter_B: after", -1)
+-// AmazonServerSuite runs the ec2test server tests against a live EC2 server.
+-// It will only be activated if the -all flag is specified.
+-type AmazonServerSuite struct {
+-	srv AmazonServer
+-	ServerTests
 -}
 -
--func route_filter_A(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
--	trace("route_filter_A: before", 1)
--	chain.ProcessFilter(req, resp)
--	trace("route_filter_A: after", -1)
+-var _ = Suite(&AmazonServerSuite{})
+-
+-func (s *AmazonServerSuite) SetUpSuite(c *C) {
+-	if !testutil.Amazon {
+-		c.Skip("AmazonServerSuite tests not enabled")
+-	}
+-	s.srv.SetUp(c)
+-	s.ServerTests.ec2 = ec2.NewWithClient(s.srv.auth, aws.USEast, testutil.DefaultClient)
 -}
 -
--func route_filter_B(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
--	trace("route_filter_B: before", 1)
--	chain.ProcessFilter(req, resp)
--	trace("route_filter_B: after", -1)
+-// ServerTests defines a set of tests designed to test
+-// the ec2test local fake ec2 server.
+-// It is not used as a test suite in itself, but embedded within
+-// another type.
+-type ServerTests struct {
+-	ec2 *ec2.EC2
 -}
 -
--func trace(what string, delta int) {
--	indented := what
--	if delta < 0 {
--		indentLevel += delta
--	}
--	for t := 0; t < indentLevel; t++ {
--		indented = "." + indented
+-func terminateInstances(c *C, e *ec2.EC2, insts []*ec2.Instance) {
+-	var ids []string
+-	for _, inst := range insts {
+-		if inst != nil {
+-			ids = append(ids, inst.InstanceId)
+-		}
 -	}
--	log.Printf("%s", indented)
--	if delta > 0 {
--		indentLevel += delta
+-	_, err := e.TerminateInstances(ids)
+-	c.Check(err, IsNil, Commentf("%d INSTANCES LEFT RUNNING!!!", len(ids)))
+-}
+-
+-func (s *ServerTests) makeTestGroup(c *C, name, descr string) ec2.SecurityGroup {
+-	// Clean it up if a previous test left it around.
+-	_, err := s.ec2.DeleteSecurityGroup(ec2.SecurityGroup{Name: name})
+-	if err != nil && err.(*ec2.Error).Code != "InvalidGroup.NotFound" {
+-		c.Fatalf("delete security group: %v", err)
 -	}
+-
+-	resp, err := s.ec2.CreateSecurityGroup(ec2.SecurityGroup{Name: name, Description: descr})
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.Name, Equals, name)
+-	return resp.SecurityGroup
 -}
 -
--func main() {
--	restful.Filter(container_filter_A)
--	restful.Filter(container_filter_B)
+-func (s *ServerTests) TestIPPerms(c *C) {
+-	g0 := s.makeTestGroup(c, "goamz-test0", "ec2test group 0")
+-	defer s.ec2.DeleteSecurityGroup(g0)
 -
--	ws1 := new(restful.WebService)
--	ws1.Path("/1")
--	ws1.Filter(service_filter_A)
--	ws1.Filter(service_filter_B)
--	ws1.Route(ws1.GET("").To(doit1).Filter(route_filter_A).Filter(route_filter_B))
+-	g1 := s.makeTestGroup(c, "goamz-test1", "ec2test group 1")
+-	defer s.ec2.DeleteSecurityGroup(g1)
 -
--	ws2 := new(restful.WebService)
--	ws2.Path("/2")
--	ws2.Filter(service_filter_A)
--	ws2.Filter(service_filter_B)
--	ws2.Route(ws2.GET("").To(doit2).Filter(route_filter_A).Filter(route_filter_B))
+-	resp, err := s.ec2.SecurityGroups([]ec2.SecurityGroup{g0, g1}, nil)
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.Groups, HasLen, 2)
+-	c.Assert(resp.Groups[0].IPPerms, HasLen, 0)
+-	c.Assert(resp.Groups[1].IPPerms, HasLen, 0)
 -
--	restful.Add(ws1)
--	restful.Add(ws2)
+-	ownerId := resp.Groups[0].OwnerId
 -
--	log.Print("go-restful example listing on http://localhost:8080/1 and http://localhost:8080/2")
--	log.Fatal(http.ListenAndServe(":8080", nil))
--}
+-	// test some invalid parameters
+-	// TODO more
+-	_, err = s.ec2.AuthorizeSecurityGroup(g0, []ec2.IPPerm{{
+-		Protocol:  "tcp",
+-		FromPort:  0,
+-		ToPort:    1024,
+-		SourceIPs: []string{"z127.0.0.1/24"},
+-	}})
+-	c.Assert(err, NotNil)
+-	c.Check(err.(*ec2.Error).Code, Equals, "InvalidPermission.Malformed")
 -
--func doit1(req *restful.Request, resp *restful.Response) {
--	io.WriteString(resp, "nothing to see in 1")
--}
+-	// Check that AuthorizeSecurityGroup adds the correct authorizations.
+-	_, err = s.ec2.AuthorizeSecurityGroup(g0, []ec2.IPPerm{{
+-		Protocol:  "tcp",
+-		FromPort:  2000,
+-		ToPort:    2001,
+-		SourceIPs: []string{"127.0.0.0/24"},
+-		SourceGroups: []ec2.UserSecurityGroup{{
+-			Name: g1.Name,
+-		}, {
+-			Id: g0.Id,
+-		}},
+-	}, {
+-		Protocol:  "tcp",
+-		FromPort:  2000,
+-		ToPort:    2001,
+-		SourceIPs: []string{"200.1.1.34/32"},
+-	}})
+-	c.Assert(err, IsNil)
 -
--func doit2(req *restful.Request, resp *restful.Response) {
--	io.WriteString(resp, "nothing to see in 2")
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-resource-functions.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-resource-functions.go
-deleted file mode 100644
-index fb1012a..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-resource-functions.go
-+++ /dev/null
-@@ -1,63 +0,0 @@
--package main
+-	resp, err = s.ec2.SecurityGroups([]ec2.SecurityGroup{g0}, nil)
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.Groups, HasLen, 1)
+-	c.Assert(resp.Groups[0].IPPerms, HasLen, 1)
+-
+-	perm := resp.Groups[0].IPPerms[0]
+-	srcg := perm.SourceGroups
+-	c.Assert(srcg, HasLen, 2)
+-
+-	// Normalize so we don't care about returned order.
+-	if srcg[0].Name == g1.Name {
+-		srcg[0], srcg[1] = srcg[1], srcg[0]
+-	}
+-	c.Check(srcg[0].Name, Equals, g0.Name)
+-	c.Check(srcg[0].Id, Equals, g0.Id)
+-	c.Check(srcg[0].OwnerId, Equals, ownerId)
+-	c.Check(srcg[1].Name, Equals, g1.Name)
+-	c.Check(srcg[1].Id, Equals, g1.Id)
+-	c.Check(srcg[1].OwnerId, Equals, ownerId)
+-
+-	sort.Strings(perm.SourceIPs)
+-	c.Check(perm.SourceIPs, DeepEquals, []string{"127.0.0.0/24", "200.1.1.34/32"})
+-
+-	// Check that we can't delete g1 (because g0 is using it)
+-	_, err = s.ec2.DeleteSecurityGroup(g1)
+-	c.Assert(err, NotNil)
+-	c.Check(err.(*ec2.Error).Code, Equals, "InvalidGroup.InUse")
+-
+-	_, err = s.ec2.RevokeSecurityGroup(g0, []ec2.IPPerm{{
+-		Protocol:     "tcp",
+-		FromPort:     2000,
+-		ToPort:       2001,
+-		SourceGroups: []ec2.UserSecurityGroup{{Id: g1.Id}},
+-	}, {
+-		Protocol:  "tcp",
+-		FromPort:  2000,
+-		ToPort:    2001,
+-		SourceIPs: []string{"200.1.1.34/32"},
+-	}})
+-	c.Assert(err, IsNil)
+-
+-	resp, err = s.ec2.SecurityGroups([]ec2.SecurityGroup{g0}, nil)
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.Groups, HasLen, 1)
+-	c.Assert(resp.Groups[0].IPPerms, HasLen, 1)
+-
+-	perm = resp.Groups[0].IPPerms[0]
+-	srcg = perm.SourceGroups
+-	c.Assert(srcg, HasLen, 1)
+-	c.Check(srcg[0].Name, Equals, g0.Name)
+-	c.Check(srcg[0].Id, Equals, g0.Id)
+-	c.Check(srcg[0].OwnerId, Equals, ownerId)
 -
--import (
--	"github.com/emicklei/go-restful"
--	"log"
--	"net/http"
--)
+-	c.Check(perm.SourceIPs, DeepEquals, []string{"127.0.0.0/24"})
 -
--// This example shows how to use methods as RouteFunctions for WebServices.
--// The ProductResource has a Register() method that creates and initializes
--// a WebService to expose its methods as REST operations.
--// The WebService is added to the restful.DefaultContainer.
--// A ProductResource is typically created using some data access object.
--//
--// GET http://localhost:8080/products/1
--// POST http://localhost:8080/products
--// <Product><Id>1</Id><Title>The First</Title></Product>
+-	// We should be able to delete g1 now because we've removed its only use.
+-	_, err = s.ec2.DeleteSecurityGroup(g1)
+-	c.Assert(err, IsNil)
 -
--type Product struct {
--	Id, Title string
--}
+-	_, err = s.ec2.DeleteSecurityGroup(g0)
+-	c.Assert(err, IsNil)
 -
--type ProductResource struct {
--	// typically reference a DAO (data-access-object)
+-	f := ec2.NewFilter()
+-	f.Add("group-id", g0.Id, g1.Id)
+-	resp, err = s.ec2.SecurityGroups(nil, f)
+-	c.Assert(err, IsNil)
+-	c.Assert(resp.Groups, HasLen, 0)
 -}
 -
--func (p ProductResource) getOne(req *restful.Request, resp *restful.Response) {
--	id := req.PathParameter("id")
--	log.Println("getting product with id:" + id)
--	resp.WriteEntity(Product{Id: id, Title: "test"})
--}
+-func (s *ServerTests) TestDuplicateIPPerm(c *C) {
+-	name := "goamz-test"
+-	descr := "goamz security group for tests"
 -
--func (p ProductResource) postOne(req *restful.Request, resp *restful.Response) {
--	updatedProduct := new(Product)
--	err := req.ReadEntity(updatedProduct)
--	if err != nil { // bad request
--		resp.WriteErrorString(http.StatusBadRequest, err.Error())
--		return
--	}
--	log.Println("updating product with id:" + updatedProduct.Id)
--}
+-	// Clean it up, if a previous test left it around and avoid leaving it around.
+-	s.ec2.DeleteSecurityGroup(ec2.SecurityGroup{Name: name})
+-	defer s.ec2.DeleteSecurityGroup(ec2.SecurityGroup{Name: name})
 -
--func (p ProductResource) Register() {
--	ws := new(restful.WebService)
--	ws.Path("/products")
--	ws.Consumes(restful.MIME_XML)
--	ws.Produces(restful.MIME_XML)
+-	resp1, err := s.ec2.CreateSecurityGroup(ec2.SecurityGroup{Name: name, Description: descr})
+-	c.Assert(err, IsNil)
+-	c.Assert(resp1.Name, Equals, name)
 -
--	ws.Route(ws.GET("/{id}").To(p.getOne).
--		Doc("get the product by its id").
--		Param(ws.PathParameter("id", "identifier of the product").DataType("string")))
+-	perms := []ec2.IPPerm{{
+-		Protocol:  "tcp",
+-		FromPort:  200,
+-		ToPort:    1024,
+-		SourceIPs: []string{"127.0.0.1/24"},
+-	}, {
+-		Protocol:  "tcp",
+-		FromPort:  0,
+-		ToPort:    100,
+-		SourceIPs: []string{"127.0.0.1/24"},
+-	}}
 -
--	ws.Route(ws.POST("").To(p.postOne).
--		Doc("update or create a product").
--		Param(ws.BodyParameter("Product", "a Product (XML)").DataType("main.Product")))
+-	_, err = s.ec2.AuthorizeSecurityGroup(ec2.SecurityGroup{Name: name}, perms[0:1])
+-	c.Assert(err, IsNil)
 -
--	restful.Add(ws)
+-	_, err = s.ec2.AuthorizeSecurityGroup(ec2.SecurityGroup{Name: name}, perms[0:2])
+-	c.Assert(err, ErrorMatches, `.*\(InvalidPermission.Duplicate\)`)
 -}
 -
--func main() {
--	ProductResource{}.Register()
--	http.ListenAndServe(":8080", nil)
+-type filterSpec struct {
+-	name   string
+-	values []string
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-route_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-route_test.go
-deleted file mode 100644
-index 20c366b..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-route_test.go
-+++ /dev/null
-@@ -1,39 +0,0 @@
--package main
--
--import (
--	"net/http"
--	"net/http/httptest"
--	"strings"
--	"testing"
 -
--	"github.com/emicklei/go-restful"
--)
+-func (s *ServerTests) TestInstanceFiltering(c *C) {
+-	groupResp, err := s.ec2.CreateSecurityGroup(ec2.SecurityGroup{Name: sessionName("testgroup1"), Description: "testgroup one description"})
+-	c.Assert(err, IsNil)
+-	group1 := groupResp.SecurityGroup
+-	defer s.ec2.DeleteSecurityGroup(group1)
 -
--var (
--	Result string
--)
+-	groupResp, err = s.ec2.CreateSecurityGroup(ec2.SecurityGroup{Name: sessionName("testgroup2"), Description: "testgroup two description"})
+-	c.Assert(err, IsNil)
+-	group2 := groupResp.SecurityGroup
+-	defer s.ec2.DeleteSecurityGroup(group2)
 -
--func TestRouteExtractParameter(t *testing.T) {
--	// setup service
--	ws := new(restful.WebService)
--	ws.Consumes(restful.MIME_XML)
--	ws.Route(ws.GET("/test/{param}").To(DummyHandler))
--	restful.Add(ws)
+-	insts := make([]*ec2.Instance, 3)
+-	inst, err := s.ec2.RunInstances(&ec2.RunInstances{
+-		MinCount:       2,
+-		ImageId:        imageId,
+-		InstanceType:   "t1.micro",
+-		SecurityGroups: []ec2.SecurityGroup{group1},
+-	})
+-	c.Assert(err, IsNil)
+-	insts[0] = &inst.Instances[0]
+-	insts[1] = &inst.Instances[1]
+-	defer terminateInstances(c, s.ec2, insts)
 -
--	// setup request + writer
--	bodyReader := strings.NewReader("<Sample><Value>42</Value></Sample>")
--	httpRequest, _ := http.NewRequest("GET", "/test/THIS", bodyReader)
--	httpRequest.Header.Set("Content-Type", restful.MIME_XML)
--	httpWriter := httptest.NewRecorder()
+-	imageId2 := "ami-e358958a" // Natty server, i386, EBS store
+-	inst, err = s.ec2.RunInstances(&ec2.RunInstances{
+-		ImageId:        imageId2,
+-		InstanceType:   "t1.micro",
+-		SecurityGroups: []ec2.SecurityGroup{group2},
+-	})
+-	c.Assert(err, IsNil)
+-	insts[2] = &inst.Instances[0]
 -
--	// run
--	restful.DefaultContainer.ServeHTTP(httpWriter, httpRequest)
+-	ids := func(indices ...int) (instIds []string) {
+-		for _, index := range indices {
+-			instIds = append(instIds, insts[index].InstanceId)
+-		}
+-		return
+-	}
 -
--	if Result != "THIS" {
--		t.Fatalf("Result is actually: %s", Result)
+-	tests := []struct {
+-		about       string
+-		instanceIds []string     // instanceIds argument to Instances method.
+-		filters     []filterSpec // filters argument to Instances method.
+-		resultIds   []string     // set of instance ids of expected results.
+-		allowExtra  bool         // resultIds may be incomplete.
+-		err         string       // expected error.
+-	}{
+-		{
+-			about:      "check that Instances returns all instances",
+-			resultIds:  ids(0, 1, 2),
+-			allowExtra: true,
+-		}, {
+-			about:       "check that specifying two instance ids returns them",
+-			instanceIds: ids(0, 2),
+-			resultIds:   ids(0, 2),
+-		}, {
+-			about:       "check that specifying a non-existent instance id gives an error",
+-			instanceIds: append(ids(0), "i-deadbeef"),
+-			err:         `.*\(InvalidInstanceID\.NotFound\)`,
+-		}, {
+-			about: "check that a filter allowed both instances returns both of them",
+-			filters: []filterSpec{
+-				{"instance-id", ids(0, 2)},
+-			},
+-			resultIds: ids(0, 2),
+-		}, {
+-			about: "check that a filter allowing only one instance returns it",
+-			filters: []filterSpec{
+-				{"instance-id", ids(1)},
+-			},
+-			resultIds: ids(1),
+-		}, {
+-			about: "check that a filter allowing no instances returns none",
+-			filters: []filterSpec{
+-				{"instance-id", []string{"i-deadbeef12345"}},
+-			},
+-		}, {
+-			about: "check that filtering on group id works",
+-			filters: []filterSpec{
+-				{"group-id", []string{group1.Id}},
+-			},
+-			resultIds: ids(0, 1),
+-		}, {
+-			about: "check that filtering on group name works",
+-			filters: []filterSpec{
+-				{"group-name", []string{group1.Name}},
+-			},
+-			resultIds: ids(0, 1),
+-		}, {
+-			about: "check that filtering on image id works",
+-			filters: []filterSpec{
+-				{"image-id", []string{imageId}},
+-			},
+-			resultIds:  ids(0, 1),
+-			allowExtra: true,
+-		}, {
+-			about: "combination filters 1",
+-			filters: []filterSpec{
+-				{"image-id", []string{imageId, imageId2}},
+-				{"group-name", []string{group1.Name}},
+-			},
+-			resultIds: ids(0, 1),
+-		}, {
+-			about: "combination filters 2",
+-			filters: []filterSpec{
+-				{"image-id", []string{imageId2}},
+-				{"group-name", []string{group1.Name}},
+-			},
+-		},
+-	}
+-	for i, t := range tests {
+-		c.Logf("%d. %s", i, t.about)
+-		var f *ec2.Filter
+-		if t.filters != nil {
+-			f = ec2.NewFilter()
+-			for _, spec := range t.filters {
+-				f.Add(spec.name, spec.values...)
+-			}
+-		}
+-		resp, err := s.ec2.Instances(t.instanceIds, f)
+-		if t.err != "" {
+-			c.Check(err, ErrorMatches, t.err)
+-			continue
+-		}
+-		c.Assert(err, IsNil)
+-		insts := make(map[string]*ec2.Instance)
+-		for _, r := range resp.Reservations {
+-			for j := range r.Instances {
+-				inst := &r.Instances[j]
+-				c.Check(insts[inst.InstanceId], IsNil, Commentf("duplicate instance id: %q", inst.InstanceId))
+-				insts[inst.InstanceId] = inst
+-			}
+-		}
+-		if !t.allowExtra {
+-			c.Check(insts, HasLen, len(t.resultIds), Commentf("expected %d instances got %#v", len(t.resultIds), insts))
+-		}
+-		for j, id := range t.resultIds {
+-			c.Check(insts[id], NotNil, Commentf("instance id %d (%q) not found; got %#v", j, id, insts))
+-		}
 -	}
 -}
 -
--func DummyHandler(rq *restful.Request, rp *restful.Response) {
--	Result = rq.PathParameter("param")
+-func idsOnly(gs []ec2.SecurityGroup) []ec2.SecurityGroup {
+-	for i := range gs {
+-		gs[i].Name = ""
+-	}
+-	return gs
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-routefunction_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-routefunction_test.go
-deleted file mode 100644
-index 6d61c5c..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-routefunction_test.go
-+++ /dev/null
-@@ -1,29 +0,0 @@
--package main
--
--import (
--	"net/http"
--	"net/http/httptest"
--	"testing"
 -
--	"github.com/emicklei/go-restful"
--)
+-func namesOnly(gs []ec2.SecurityGroup) []ec2.SecurityGroup {
+-	for i := range gs {
+-		gs[i].Id = ""
+-	}
+-	return gs
+-}
 -
--// This example show how to test one particular RouteFunction (getIt)
--// It uses the httptest.ResponseRecorder to capture output
+-func (s *ServerTests) TestGroupFiltering(c *C) {
+-	g := make([]ec2.SecurityGroup, 4)
+-	for i := range g {
+-		resp, err := s.ec2.CreateSecurityGroup(ec2.SecurityGroup{Name: sessionName(fmt.Sprintf("testgroup%d", i)), Description: fmt.Sprintf("testdescription%d", i)})
+-		c.Assert(err, IsNil)
+-		g[i] = resp.SecurityGroup
+-		c.Logf("group %d: %v", i, g[i])
+-		defer s.ec2.DeleteSecurityGroup(g[i])
+-	}
 -
--func getIt(req *restful.Request, resp *restful.Response) {
--	resp.WriteHeader(404)
--}
+-	perms := [][]ec2.IPPerm{
+-		{{
+-			Protocol:  "tcp",
+-			FromPort:  100,
+-			ToPort:    200,
+-			SourceIPs: []string{"1.2.3.4/32"},
+-		}},
+-		{{
+-			Protocol:     "tcp",
+-			FromPort:     200,
+-			ToPort:       300,
+-			SourceGroups: []ec2.UserSecurityGroup{{Id: g[1].Id}},
+-		}},
+-		{{
+-			Protocol:     "udp",
+-			FromPort:     200,
+-			ToPort:       400,
+-			SourceGroups: []ec2.UserSecurityGroup{{Id: g[1].Id}},
+-		}},
+-	}
+-	for i, ps := range perms {
+-		_, err := s.ec2.AuthorizeSecurityGroup(g[i], ps)
+-		c.Assert(err, IsNil)
+-	}
 -
--func TestCallFunction(t *testing.T) {
--	httpReq, _ := http.NewRequest("GET", "/", nil)
--	req := restful.NewRequest(httpReq)
+-	groups := func(indices ...int) (gs []ec2.SecurityGroup) {
+-		for _, index := range indices {
+-			gs = append(gs, g[index])
+-		}
+-		return
+-	}
 -
--	recorder := new(httptest.ResponseRecorder)
--	resp := restful.NewResponse(recoder)
+-	type groupTest struct {
+-		about      string
+-		groups     []ec2.SecurityGroup // groupIds argument to SecurityGroups method.
+-		filters    []filterSpec        // filters argument to SecurityGroups method.
+-		results    []ec2.SecurityGroup // set of expected result groups.
+-		allowExtra bool                // specified results may be incomplete.
+-		err        string              // expected error.
+-	}
+-	filterCheck := func(name, val string, gs []ec2.SecurityGroup) groupTest {
+-		return groupTest{
+-			about:      "filter check " + name,
+-			filters:    []filterSpec{{name, []string{val}}},
+-			results:    gs,
+-			allowExtra: true,
+-		}
+-	}
+-	tests := []groupTest{
+-		{
+-			about:      "check that SecurityGroups returns all groups",
+-			results:    groups(0, 1, 2, 3),
+-			allowExtra: true,
+-		}, {
+-			about:   "check that specifying two group ids returns them",
+-			groups:  idsOnly(groups(0, 2)),
+-			results: groups(0, 2),
+-		}, {
+-			about:   "check that specifying names only works",
+-			groups:  namesOnly(groups(0, 2)),
+-			results: groups(0, 2),
+-		}, {
+-			about:  "check that specifying a non-existent group id gives an error",
+-			groups: append(groups(0), ec2.SecurityGroup{Id: "sg-eeeeeeeee"}),
+-			err:    `.*\(InvalidGroup\.NotFound\)`,
+-		}, {
+-			about: "check that a filter allowed two groups returns both of them",
+-			filters: []filterSpec{
+-				{"group-id", []string{g[0].Id, g[2].Id}},
+-			},
+-			results: groups(0, 2),
+-		},
+-		{
+-			about:  "check that the previous filter works when specifying a list of ids",
+-			groups: groups(1, 2),
+-			filters: []filterSpec{
+-				{"group-id", []string{g[0].Id, g[2].Id}},
+-			},
+-			results: groups(2),
+-		}, {
+-			about: "check that a filter allowing no groups returns none",
+-			filters: []filterSpec{
+-				{"group-id", []string{"sg-eeeeeeeee"}},
+-			},
+-		},
+-		filterCheck("description", "testdescription1", groups(1)),
+-		filterCheck("group-name", g[2].Name, groups(2)),
+-		filterCheck("ip-permission.cidr", "1.2.3.4/32", groups(0)),
+-		filterCheck("ip-permission.group-name", g[1].Name, groups(1, 2)),
+-		filterCheck("ip-permission.protocol", "udp", groups(2)),
+-		filterCheck("ip-permission.from-port", "200", groups(1, 2)),
+-		filterCheck("ip-permission.to-port", "200", groups(0)),
+-		// TODO owner-id
+-	}
+-	for i, t := range tests {
+-		c.Logf("%d. %s", i, t.about)
+-		var f *ec2.Filter
+-		if t.filters != nil {
+-			f = ec2.NewFilter()
+-			for _, spec := range t.filters {
+-				f.Add(spec.name, spec.values...)
+-			}
+-		}
+-		resp, err := s.ec2.SecurityGroups(t.groups, f)
+-		if t.err != "" {
+-			c.Check(err, ErrorMatches, t.err)
+-			continue
+-		}
+-		c.Assert(err, IsNil)
+-		groups := make(map[string]*ec2.SecurityGroup)
+-		for j := range resp.Groups {
+-			group := &resp.Groups[j].SecurityGroup
+-			c.Check(groups[group.Id], IsNil, Commentf("duplicate group id: %q", group.Id))
 -
--	getIt(req, resp)
--	if recorder.Code != 404 {
--		t.Logf("Missing or wrong status code:%d", recorder.Code)
+-			groups[group.Id] = group
+-		}
+-		// If extra groups may be returned, eliminate all groups that
+-		// we did not create in this session apart from the default group.
+-		if t.allowExtra {
+-			namePat := regexp.MustCompile(sessionName("testgroup[0-9]"))
+-			for id, g := range groups {
+-				if !namePat.MatchString(g.Name) {
+-					delete(groups, id)
+-				}
+-			}
+-		}
+-		c.Check(groups, HasLen, len(t.results))
+-		for j, g := range t.results {
+-			rg := groups[g.Id]
+-			c.Assert(rg, NotNil, Commentf("group %d (%v) not found; got %#v", j, g, groups))
+-			c.Check(rg.Name, Equals, g.Name, Commentf("group %d (%v)", j, g))
+-		}
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-serve-static.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-serve-static.go
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2test/filter.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2test/filter.go
 deleted file mode 100644
-index 8cb7848..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-serve-static.go
+index 1a0c046..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2test/filter.go
 +++ /dev/null
-@@ -1,47 +0,0 @@
--package main
+@@ -1,84 +0,0 @@
+-package ec2test
 -
 -import (
 -	"fmt"
--	"net/http"
--	"path"
--
--	"github.com/emicklei/go-restful"
+-	"net/url"
+-	"strings"
 -)
 -
--// This example shows how to define methods that serve static files
--// It uses the standard http.ServeFile method
+-// filter holds an ec2 filter.  A filter maps an attribute to a set of
+-// possible values for that attribute. For an item to pass through the
+-// filter, every attribute of the item mentioned in the filter must match
+-// at least one of its given values.
+-type filter map[string][]string
+-
+-// newFilter creates a new filter from the Filter fields in the url form.
 -//
--// GET http://localhost:8080/static/test.xml
--// GET http://localhost:8080/static/
+-// The filtering is specified through a map of name=>values, where the
+-// name is a well-defined key identifying the data to be matched,
+-// and the list of values holds the possible values the filtered
+-// item can take for the key to be included in the
+-// result set. For example:
 -//
--// GET http://localhost:8080/static?resource=subdir/test.xml
--
--var rootdir = "/tmp"
--
--func main() {
--	restful.DefaultContainer.Router(restful.CurlyRouter{})
+-//   Filter.1.Name=instance-type
+-//   Filter.1.Value.1=m1.small
+-//   Filter.1.Value.2=m1.large
+-//
+-func newFilter(form url.Values) filter {
+-	// TODO return an error if the fields are not well formed?
+-	names := make(map[int]string)
+-	values := make(map[int][]string)
+-	maxId := 0
+-	for name, fvalues := range form {
+-		var rest string
+-		var id int
+-		if x, _ := fmt.Sscanf(name, "Filter.%d.%s", &id, &rest); x != 2 {
+-			continue
+-		}
+-		if id > maxId {
+-			maxId = id
+-		}
+-		if rest == "Name" {
+-			names[id] = fvalues[0]
+-			continue
+-		}
+-		if !strings.HasPrefix(rest, "Value.") {
+-			continue
+-		}
+-		values[id] = append(values[id], fvalues[0])
+-	}
 -
--	ws := new(restful.WebService)
--	ws.Route(ws.GET("/static/{subpath:*}").To(staticFromPathParam))
--	ws.Route(ws.GET("/static").To(staticFromQueryParam))
--	restful.Add(ws)
+-	f := make(filter)
+-	for id, name := range names {
+-		f[name] = values[id]
+-	}
+-	return f
+-}
 -
--	println("[go-restful] serving files on http://localhost:8080/static from local /tmp")
--	http.ListenAndServe(":8080", nil)
+-func notDigit(r rune) bool {
+-	return r < '0' || r > '9'
 -}
 -
--func staticFromPathParam(req *restful.Request, resp *restful.Response) {
--	actual := path.Join(rootdir, req.PathParameter("subpath"))
--	fmt.Printf("serving %s ... (from %s)\n", actual, req.PathParameter("subpath"))
--	http.ServeFile(
--		resp.ResponseWriter,
--		req.Request,
--		actual)
+-// filterable represents an object that can be passed through a filter.
+-type filterable interface {
+-	// matchAttr returns true if given attribute of the
+-	// object matches value. It returns an error if the
+-	// attribute is not recognised or the value is malformed.
+-	matchAttr(attr, value string) (bool, error)
 -}
 -
--func staticFromQueryParam(req *restful.Request, resp *restful.Response) {
--	http.ServeFile(
--		resp.ResponseWriter,
--		req.Request,
--		path.Join(rootdir, req.QueryParameter("resource")))
+-// ok returns true if x passes through the filter.
+-func (f filter) ok(x filterable) (bool, error) {
+-next:
+-	for a, vs := range f {
+-		for _, v := range vs {
+-			if ok, err := x.matchAttr(a, v); ok {
+-				continue next
+-			} else if err != nil {
+-				return false, fmt.Errorf("bad attribute or value %q=%q for type %T: %v", a, v, x, err)
+-			}
+-		}
+-		return false, nil
+-	}
+-	return true, nil
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-user-resource.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-user-resource.go
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2test/server.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2test/server.go
 deleted file mode 100644
-index f6ec988..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-user-resource.go
+index 2f24cb2..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2test/server.go
 +++ /dev/null
-@@ -1,153 +0,0 @@
--package main
+@@ -1,993 +0,0 @@
+-// The ec2test package implements a fake EC2 provider with
+-// the capability of inducing errors on any given operation,
+-// and retrospectively determining what operations have been
+-// carried out.
+-package ec2test
 -
 -import (
--	"log"
+-	"encoding/base64"
+-	"encoding/xml"
+-	"fmt"
+-	"github.com/mitchellh/goamz/ec2"
+-	"io"
+-	"net"
 -	"net/http"
+-	"net/url"
+-	"regexp"
 -	"strconv"
--
--	"github.com/emicklei/go-restful"
--	"github.com/emicklei/go-restful/swagger"
+-	"strings"
+-	"sync"
 -)
 -
--// This example show a complete (GET,PUT,POST,DELETE) conventional example of
--// a REST Resource including documentation to be served by e.g. a Swagger UI
--// It is recommended to create a Resource struct (UserResource) that can encapsulate
--// an object that provide domain access (a DAO)
--// It has a Register method including the complete Route mapping to methods together
--// with all the appropriate documentation
--//
--// POST http://localhost:8080/users
--// <User><Id>1</Id><Name>Melissa Raspberry</Name></User>
--//
--// GET http://localhost:8080/users/1
--//
--// PUT http://localhost:8080/users/1
--// <User><Id>1</Id><Name>Melissa</Name></User>
--//
--// DELETE http://localhost:8080/users/1
--//
--
--type User struct {
--	Id, Name string
--}
--
--type UserResource struct {
--	// normally one would use DAO (data access object)
--	users map[string]User
--}
--
--func (u UserResource) Register(container *restful.Container) {
--	ws := new(restful.WebService)
--	ws.
--		Path("/users").
--		Doc("Manage Users").
--		Consumes(restful.MIME_XML, restful.MIME_JSON).
--		Produces(restful.MIME_JSON, restful.MIME_XML) // you can specify this per route as well
--
--	ws.Route(ws.GET("/{user-id}").To(u.findUser).
--		// docs
--		Doc("get a user").
--		Operation("findUser").
--		Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")).
--		Writes(User{})) // on the response
--
--	ws.Route(ws.PUT("/{user-id}").To(u.updateUser).
--		// docs
--		Doc("update a user").
--		Operation("updateUser").
--		Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")).
--		ReturnsError(409, "duplicate user-id", nil).
--		Reads(User{})) // from the request
+-var b64 = base64.StdEncoding
 -
--	ws.Route(ws.POST("").To(u.createUser).
--		// docs
--		Doc("create a user").
--		Operation("createUser").
--		Reads(User{})) // from the request
+-// Action represents a request that changes the ec2 state.
+-type Action struct {
+-	RequestId string
 -
--	ws.Route(ws.DELETE("/{user-id}").To(u.removeUser).
--		// docs
--		Doc("delete a user").
--		Operation("removeUser").
--		Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")))
+-	// Request holds the requested action as a url.Values instance
+-	Request url.Values
 -
--	container.Add(ws)
--}
+-	// If the action succeeded, Response holds the value that
+-	// was marshalled to build the XML response for the request.
+-	Response interface{}
 -
--// GET http://localhost:8080/users/1
--//
--func (u UserResource) findUser(request *restful.Request, response *restful.Response) {
--	id := request.PathParameter("user-id")
--	usr := u.users[id]
--	if len(usr.Id) == 0 {
--		response.AddHeader("Content-Type", "text/plain")
--		response.WriteErrorString(http.StatusNotFound, "404: User could not be found.")
--		return
--	}
--	response.WriteEntity(usr)
+-	// If the action failed, Err holds an error giving details of the failure.
+-	Err *ec2.Error
 -}
 -
--// POST http://localhost:8080/users
--// <User><Name>Melissa</Name></User>
--//
--func (u *UserResource) createUser(request *restful.Request, response *restful.Response) {
--	usr := new(User)
--	err := request.ReadEntity(usr)
--	if err != nil {
--		response.AddHeader("Content-Type", "text/plain")
--		response.WriteErrorString(http.StatusInternalServerError, err.Error())
--		return
--	}
--	usr.Id = strconv.Itoa(len(u.users) + 1) // simple id generation
--	u.users[usr.Id] = *usr
--	response.WriteHeader(http.StatusCreated)
--	response.WriteEntity(usr)
--}
+-// TODO possible other things:
+-// - some virtual time stamp interface, so a client
+-// can ask for all actions after a certain virtual time.
 -
--// PUT http://localhost:8080/users/1
--// <User><Id>1</Id><Name>Melissa Raspberry</Name></User>
--//
--func (u *UserResource) updateUser(request *restful.Request, response *restful.Response) {
--	usr := new(User)
--	err := request.ReadEntity(&usr)
--	if err != nil {
--		response.AddHeader("Content-Type", "text/plain")
--		response.WriteErrorString(http.StatusInternalServerError, err.Error())
--		return
--	}
--	u.users[usr.Id] = *usr
--	response.WriteEntity(usr)
--}
+-// Server implements an EC2 simulator for use in testing.
+-type Server struct {
+-	url      string
+-	listener net.Listener
+-	mu       sync.Mutex
+-	reqs     []*Action
 -
--// DELETE http://localhost:8080/users/1
--//
--func (u *UserResource) removeUser(request *restful.Request, response *restful.Response) {
--	id := request.PathParameter("user-id")
--	delete(u.users, id)
+-	instances            map[string]*Instance      // id -> instance
+-	reservations         map[string]*reservation   // id -> reservation
+-	groups               map[string]*securityGroup // id -> group
+-	maxId                counter
+-	reqId                counter
+-	reservationId        counter
+-	groupId              counter
+-	initialInstanceState ec2.InstanceState
 -}
 -
--func main() {
--	// to see what happens in the package, uncomment the following
--	//restful.TraceLogger(log.New(os.Stdout, "[restful] ", log.LstdFlags|log.Lshortfile))
--
--	wsContainer := restful.NewContainer()
--	u := UserResource{map[string]User{}}
--	u.Register(wsContainer)
--
--	// Optionally, you can install the Swagger Service which provides a nice Web UI on your REST API
--	// You need to download the Swagger HTML5 assets and change the FilePath location in the config below.
--	// Open http://localhost:8080/apidocs and enter http://localhost:8080/apidocs.json in the api input field.
--	config := swagger.Config{
--		WebServices:    wsContainer.RegisteredWebServices(), // you control what services are visible
--		WebServicesUrl: "http://localhost:8080",
--		ApiPath:        "/apidocs.json",
--
--		// Optionally, specifiy where the UI is located
--		SwaggerPath:     "/apidocs/",
--		SwaggerFilePath: "/Users/emicklei/xProjects/swagger-ui/dist"}
--	swagger.RegisterSwaggerService(config, wsContainer)
--
--	log.Printf("start listening on localhost:8080")
--	server := &http.Server{Addr: ":8080", Handler: wsContainer}
--	log.Fatal(server.ListenAndServe())
+-// reservation holds a simulated ec2 reservation.
+-type reservation struct {
+-	id        string
+-	instances map[string]*Instance
+-	groups    []*securityGroup
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-user-service.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-user-service.go
-deleted file mode 100644
-index d0d9872..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/examples/restful-user-service.go
-+++ /dev/null
-@@ -1,138 +0,0 @@
--package main
--
--import (
--	"log"
--	"net/http"
--
--	"github.com/emicklei/go-restful"
--	"github.com/emicklei/go-restful/swagger"
--)
--
--// This example is functionally the same as the example in restful-user-resource.go
--// with the only difference that is served using the restful.DefaultContainer
 -
--type User struct {
--	Id, Name string
+-// instance holds a simulated ec2 instance
+-type Instance struct {
+-	// UserData holds the data that was passed to the RunInstances request
+-	// when the instance was started.
+-	UserData    []byte
+-	id          string
+-	imageId     string
+-	reservation *reservation
+-	instType    string
+-	state       ec2.InstanceState
 -}
 -
--type UserService struct {
--	// normally one would use DAO (data access object)
--	users map[string]User
+-// permKey represents permission for a given security
+-// group or IP address (but not both) to access a given range of
+-// ports. Equality of permKeys is used in the implementation of
+-// permission sets, relying on the uniqueness of securityGroup
+-// instances.
+-type permKey struct {
+-	protocol string
+-	fromPort int
+-	toPort   int
+-	group    *securityGroup
+-	ipAddr   string
 -}
 -
--func (u UserService) Register() {
--	ws := new(restful.WebService)
--	ws.
--		Path("/users").
--		Consumes(restful.MIME_XML, restful.MIME_JSON).
--		Produces(restful.MIME_JSON, restful.MIME_XML) // you can specify this per route as well
--
--	ws.Route(ws.GET("/").To(u.findAllUsers).
--		// docs
--		Doc("get all users").
--		Operation("findAllUsers").
--		Returns(200, "OK", []User{}))
--
--	ws.Route(ws.GET("/{user-id}").To(u.findUser).
--		// docs
--		Doc("get a user").
--		Operation("findUser").
--		Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")).
--		Writes(User{})) // on the response
--
--	ws.Route(ws.PUT("/{user-id}").To(u.updateUser).
--		// docs
--		Doc("update a user").
--		Operation("updateUser").
--		Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")).
--		Reads(User{})) // from the request
--
--	ws.Route(ws.PUT("").To(u.createUser).
--		// docs
--		Doc("create a user").
--		Operation("createUser").
--		Reads(User{})) // from the request
--
--	ws.Route(ws.DELETE("/{user-id}").To(u.removeUser).
--		// docs
--		Doc("delete a user").
--		Operation("removeUser").
--		Param(ws.PathParameter("user-id", "identifier of the user").DataType("string")))
--
--	restful.Add(ws)
--}
+-// securityGroup holds a simulated ec2 security group.
+-// Instances of securityGroup should only be created through
+-// Server.createSecurityGroup to ensure that groups can be
+-// compared by pointer value.
+-type securityGroup struct {
+-	id          string
+-	name        string
+-	description string
 -
--// GET http://localhost:8080/users
--//
--func (u UserService) findAllUsers(request *restful.Request, response *restful.Response) {
--	response.WriteEntity(u.users)
+-	perms map[permKey]bool
 -}
 -
--// GET http://localhost:8080/users/1
--//
--func (u UserService) findUser(request *restful.Request, response *restful.Response) {
--	id := request.PathParameter("user-id")
--	usr := u.users[id]
--	if len(usr.Id) == 0 {
--		response.WriteErrorString(http.StatusNotFound, "User could not be found.")
--	} else {
--		response.WriteEntity(usr)
+-func (g *securityGroup) ec2SecurityGroup() ec2.SecurityGroup {
+-	return ec2.SecurityGroup{
+-		Name: g.name,
+-		Id:   g.id,
 -	}
 -}
 -
--// PUT http://localhost:8080/users/1
--// <User><Id>1</Id><Name>Melissa Raspberry</Name></User>
--//
--func (u *UserService) updateUser(request *restful.Request, response *restful.Response) {
--	usr := new(User)
--	err := request.ReadEntity(&usr)
--	if err == nil {
--		u.users[usr.Id] = *usr
--		response.WriteEntity(usr)
--	} else {
--		response.WriteError(http.StatusInternalServerError, err)
+-func (g *securityGroup) matchAttr(attr, value string) (ok bool, err error) {
+-	switch attr {
+-	case "description":
+-		return g.description == value, nil
+-	case "group-id":
+-		return g.id == value, nil
+-	case "group-name":
+-		return g.name == value, nil
+-	case "ip-permission.cidr":
+-		return g.hasPerm(func(k permKey) bool { return k.ipAddr == value }), nil
+-	case "ip-permission.group-name":
+-		return g.hasPerm(func(k permKey) bool {
+-			return k.group != nil && k.group.name == value
+-		}), nil
+-	case "ip-permission.from-port":
+-		port, err := strconv.Atoi(value)
+-		if err != nil {
+-			return false, err
+-		}
+-		return g.hasPerm(func(k permKey) bool { return k.fromPort == port }), nil
+-	case "ip-permission.to-port":
+-		port, err := strconv.Atoi(value)
+-		if err != nil {
+-			return false, err
+-		}
+-		return g.hasPerm(func(k permKey) bool { return k.toPort == port }), nil
+-	case "ip-permission.protocol":
+-		return g.hasPerm(func(k permKey) bool { return k.protocol == value }), nil
+-	case "owner-id":
+-		return value == ownerId, nil
 -	}
+-	return false, fmt.Errorf("unknown attribute %q", attr)
 -}
 -
--// PUT http://localhost:8080/users/1
--// <User><Id>1</Id><Name>Melissa</Name></User>
--//
--func (u *UserService) createUser(request *restful.Request, response *restful.Response) {
--	usr := User{Id: request.PathParameter("user-id")}
--	err := request.ReadEntity(&usr)
--	if err == nil {
--		u.users[usr.Id] = usr
--		response.WriteHeader(http.StatusCreated)
--		response.WriteEntity(usr)
--	} else {
--		response.WriteError(http.StatusInternalServerError, err)
+-func (g *securityGroup) hasPerm(test func(k permKey) bool) bool {
+-	for k := range g.perms {
+-		if test(k) {
+-			return true
+-		}
 -	}
+-	return false
 -}
 -
--// DELETE http://localhost:8080/users/1
--//
--func (u *UserService) removeUser(request *restful.Request, response *restful.Response) {
--	id := request.PathParameter("user-id")
--	delete(u.users, id)
--}
--
--func main() {
--	u := UserService{map[string]User{}}
--	u.Register()
--
--	// Optionally, you can install the Swagger Service which provides a nice Web UI on your REST API
--	// You need to download the Swagger HTML5 assets and change the FilePath location in the config below.
--	// Open http://localhost:8080/apidocs and enter http://localhost:8080/apidocs.json in the api input field.
--	config := swagger.Config{
--		WebServices:    restful.RegisteredWebServices(), // you control what services are visible
--		WebServicesUrl: "http://localhost:8080",
--		ApiPath:        "/apidocs.json",
--
--		// Optionally, specifiy where the UI is located
--		SwaggerPath:     "/apidocs/",
--		SwaggerFilePath: "/Users/emicklei/Projects/swagger-ui/dist"}
--	swagger.InstallSwaggerService(config)
--
--	log.Printf("start listening on localhost:8080")
--	log.Fatal(http.ListenAndServe(":8080", nil))
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/filter.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/filter.go
-deleted file mode 100644
-index 4b86656..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/filter.go
-+++ /dev/null
-@@ -1,26 +0,0 @@
--package restful
--
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
+-// ec2Perms returns the list of EC2 permissions granted
+-// to g. It groups permissions by port range and protocol.
+-func (g *securityGroup) ec2Perms() (perms []ec2.IPPerm) {
+-	// The grouping is held in result. We use permKey for convenience,
+-	// (ensuring that the group and ipAddr of each key is zero). For
+-	// each protocol/port range combination, we build up the permission
+-	// set in the associated value.
+-	result := make(map[permKey]*ec2.IPPerm)
+-	for k := range g.perms {
+-		groupKey := k
+-		groupKey.group = nil
+-		groupKey.ipAddr = ""
 -
--// FilterChain is a request scoped object to process one or more filters before calling the target RouteFunction.
--type FilterChain struct {
--	Filters []FilterFunction // ordered list of FilterFunction
--	Index   int              // index into filters that is currently in progress
--	Target  RouteFunction    // function to call after passing all filters
+-		ec2p := result[groupKey]
+-		if ec2p == nil {
+-			ec2p = &ec2.IPPerm{
+-				Protocol: k.protocol,
+-				FromPort: k.fromPort,
+-				ToPort:   k.toPort,
+-			}
+-			result[groupKey] = ec2p
+-		}
+-		if k.group != nil {
+-			ec2p.SourceGroups = append(ec2p.SourceGroups,
+-				ec2.UserSecurityGroup{
+-					Id:      k.group.id,
+-					Name:    k.group.name,
+-					OwnerId: ownerId,
+-				})
+-		} else {
+-			ec2p.SourceIPs = append(ec2p.SourceIPs, k.ipAddr)
+-		}
+-	}
+-	for _, ec2p := range result {
+-		perms = append(perms, *ec2p)
+-	}
+-	return
 -}
 -
--// ProcessFilter passes the request,response pair through the next of Filters.
--// Each filter can decide to proceed to the next Filter or handle the Response itself.
--func (f *FilterChain) ProcessFilter(request *Request, response *Response) {
--	if f.Index < len(f.Filters) {
--		f.Index++
--		f.Filters[f.Index-1](request, response, f)
--	} else {
--		f.Target(request, response)
--	}
+-var actions = map[string]func(*Server, http.ResponseWriter, *http.Request, string) interface{}{
+-	"RunInstances":                  (*Server).runInstances,
+-	"TerminateInstances":            (*Server).terminateInstances,
+-	"DescribeInstances":             (*Server).describeInstances,
+-	"CreateSecurityGroup":           (*Server).createSecurityGroup,
+-	"DescribeSecurityGroups":        (*Server).describeSecurityGroups,
+-	"DeleteSecurityGroup":           (*Server).deleteSecurityGroup,
+-	"AuthorizeSecurityGroupIngress": (*Server).authorizeSecurityGroupIngress,
+-	"RevokeSecurityGroupIngress":    (*Server).revokeSecurityGroupIngress,
 -}
 -
--// FilterFunction definitions must call ProcessFilter on the FilterChain to pass on the control and eventually call the RouteFunction
--type FilterFunction func(*Request, *Response, *FilterChain)
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/filter_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/filter_test.go
-deleted file mode 100644
-index fadfb57..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/filter_test.go
-+++ /dev/null
-@@ -1,141 +0,0 @@
--package restful
+-const ownerId = "9876"
 -
--import (
--	"io"
--	"net/http"
--	"net/http/httptest"
--	"testing"
--)
+-// newAction allocates a new action and adds it to the
+-// recorded list of server actions.
+-func (srv *Server) newAction() *Action {
+-	srv.mu.Lock()
+-	defer srv.mu.Unlock()
 -
--func setupServices(addGlobalFilter bool, addServiceFilter bool, addRouteFilter bool) {
--	if addGlobalFilter {
--		Filter(globalFilter)
--	}
--	Add(newTestService(addServiceFilter, addRouteFilter))
+-	a := new(Action)
+-	srv.reqs = append(srv.reqs, a)
+-	return a
 -}
 -
--func tearDown() {
--	DefaultContainer.webServices = []*WebService{}
--	DefaultContainer.isRegisteredOnRoot = true // this allows for setupServices multiple times
--	DefaultContainer.containerFilters = []FilterFunction{}
--}
+-// NewServer returns a new server.
+-func NewServer() (*Server, error) {
+-	srv := &Server{
+-		instances:            make(map[string]*Instance),
+-		groups:               make(map[string]*securityGroup),
+-		reservations:         make(map[string]*reservation),
+-		initialInstanceState: Pending,
+-	}
 -
--func newTestService(addServiceFilter bool, addRouteFilter bool) *WebService {
--	ws := new(WebService).Path("")
--	if addServiceFilter {
--		ws.Filter(serviceFilter)
+-	// Add default security group.
+-	g := &securityGroup{
+-		name:        "default",
+-		description: "default group",
+-		id:          fmt.Sprintf("sg-%d", srv.groupId.next()),
 -	}
--	rb := ws.GET("/foo").To(foo)
--	if addRouteFilter {
--		rb.Filter(routeFilter)
+-	g.perms = map[permKey]bool{
+-		permKey{
+-			protocol: "icmp",
+-			fromPort: -1,
+-			toPort:   -1,
+-			group:    g,
+-		}: true,
+-		permKey{
+-			protocol: "tcp",
+-			fromPort: 0,
+-			toPort:   65535,
+-			group:    g,
+-		}: true,
+-		permKey{
+-			protocol: "udp",
+-			fromPort: 0,
+-			toPort:   65535,
+-			group:    g,
+-		}: true,
 -	}
--	ws.Route(rb)
--	ws.Route(ws.GET("/bar").To(bar))
--	return ws
--}
+-	srv.groups[g.id] = g
 -
--func foo(req *Request, resp *Response) {
--	io.WriteString(resp.ResponseWriter, "foo")
--}
+-	l, err := net.Listen("tcp", "localhost:0")
+-	if err != nil {
+-		return nil, fmt.Errorf("cannot listen on localhost: %v", err)
+-	}
+-	srv.listener = l
 -
--func bar(req *Request, resp *Response) {
--	io.WriteString(resp.ResponseWriter, "bar")
--}
+-	srv.url = "http://" + l.Addr().String()
 -
--func fail(req *Request, resp *Response) {
--	http.Error(resp.ResponseWriter, "something failed", http.StatusInternalServerError)
+-	// we use HandlerFunc rather than *Server directly so that we
+-	// can avoid exporting HandlerFunc from *Server.
+-	go http.Serve(l, http.HandlerFunc(func(w http.ResponseWriter, req *http.Request) {
+-		srv.serveHTTP(w, req)
+-	}))
+-	return srv, nil
 -}
 -
--func globalFilter(req *Request, resp *Response, chain *FilterChain) {
--	io.WriteString(resp.ResponseWriter, "global-")
--	chain.ProcessFilter(req, resp)
+-// Quit closes down the server.
+-func (srv *Server) Quit() {
+-	srv.listener.Close()
 -}
 -
--func serviceFilter(req *Request, resp *Response, chain *FilterChain) {
--	io.WriteString(resp.ResponseWriter, "service-")
--	chain.ProcessFilter(req, resp)
+-// SetInitialInstanceState sets the state that any new instances will be started in.
+-func (srv *Server) SetInitialInstanceState(state ec2.InstanceState) {
+-	srv.mu.Lock()
+-	srv.initialInstanceState = state
+-	srv.mu.Unlock()
 -}
 -
--func routeFilter(req *Request, resp *Response, chain *FilterChain) {
--	io.WriteString(resp.ResponseWriter, "route-")
--	chain.ProcessFilter(req, resp)
+-// URL returns the URL of the server.
+-func (srv *Server) URL() string {
+-	return srv.url
 -}
 -
--func TestNoFilter(t *testing.T) {
--	tearDown()
--	setupServices(false, false, false)
--	actual := sendIt("http://example.com/foo")
--	if "foo" != actual {
--		t.Fatal("expected: foo but got:" + actual)
--	}
--}
+-// serveHTTP serves the EC2 protocol.
+-func (srv *Server) serveHTTP(w http.ResponseWriter, req *http.Request) {
+-	req.ParseForm()
 -
--func TestGlobalFilter(t *testing.T) {
--	tearDown()
--	setupServices(true, false, false)
--	actual := sendIt("http://example.com/foo")
--	if "global-foo" != actual {
--		t.Fatal("expected: global-foo but got:" + actual)
+-	a := srv.newAction()
+-	a.RequestId = fmt.Sprintf("req%d", srv.reqId.next())
+-	a.Request = req.Form
+-
+-	// Methods on Server that deal with parsing user data
+-	// may fail. To save on error handling code, we allow these
+-	// methods to call fatalf, which will panic with an *ec2.Error
+-	// which will be caught here and returned
+-	// to the client as a properly formed EC2 error.
+-	defer func() {
+-		switch err := recover().(type) {
+-		case *ec2.Error:
+-			a.Err = err
+-			err.RequestId = a.RequestId
+-			writeError(w, err)
+-		case nil:
+-		default:
+-			panic(err)
+-		}
+-	}()
+-
+-	f := actions[req.Form.Get("Action")]
+-	if f == nil {
+-		fatalf(400, "InvalidParameterValue", "Unrecognized Action")
 -	}
+-
+-	response := f(srv, w, req, a.RequestId)
+-	a.Response = response
+-
+-	w.Header().Set("Content-Type", `xml version="1.0" encoding="UTF-8"`)
+-	xmlMarshal(w, response)
 -}
 -
--func TestWebServiceFilter(t *testing.T) {
--	tearDown()
--	setupServices(true, true, false)
--	actual := sendIt("http://example.com/foo")
--	if "global-service-foo" != actual {
--		t.Fatal("expected: global-service-foo but got:" + actual)
--	}
+-// Instance returns the instance for the given instance id.
+-// It returns nil if there is no such instance.
+-func (srv *Server) Instance(id string) *Instance {
+-	srv.mu.Lock()
+-	defer srv.mu.Unlock()
+-	return srv.instances[id]
 -}
 -
--func TestRouteFilter(t *testing.T) {
--	tearDown()
--	setupServices(true, true, true)
--	actual := sendIt("http://example.com/foo")
--	if "global-service-route-foo" != actual {
--		t.Fatal("expected: global-service-route-foo but got:" + actual)
+-// writeError writes an appropriate error response.
+-// TODO how should we deal with errors when the
+-// error itself is potentially generated by backend-agnostic
+-// code?
+-func writeError(w http.ResponseWriter, err *ec2.Error) {
+-	// Error encapsulates an error returned by EC2.
+-	// TODO merge with ec2.Error when xml supports ignoring a field.
+-	type ec2error struct {
+-		Code      string // EC2 error code ("UnsupportedOperation", ...)
+-		Message   string // The human-oriented error message
+-		RequestId string
 -	}
--}
 -
--func TestRouteFilterOnly(t *testing.T) {
--	tearDown()
--	setupServices(false, false, true)
--	actual := sendIt("http://example.com/foo")
--	if "route-foo" != actual {
--		t.Fatal("expected: route-foo but got:" + actual)
+-	type Response struct {
+-		RequestId string
+-		Errors    []ec2error `xml:"Errors>Error"`
 -	}
+-
+-	w.Header().Set("Content-Type", `xml version="1.0" encoding="UTF-8"`)
+-	w.WriteHeader(err.StatusCode)
+-	xmlMarshal(w, Response{
+-		RequestId: err.RequestId,
+-		Errors: []ec2error{{
+-			Code:    err.Code,
+-			Message: err.Message,
+-		}},
+-	})
 -}
 -
--func TestBar(t *testing.T) {
--	tearDown()
--	setupServices(false, true, false)
--	actual := sendIt("http://example.com/bar")
--	if "service-bar" != actual {
--		t.Fatal("expected: service-bar but got:" + actual)
+-// xmlMarshal is the same as xml.Marshal except that
+-// it panics on error. The marshalling should not fail,
+-// but we want to know if it does.
+-func xmlMarshal(w io.Writer, x interface{}) {
+-	if err := xml.NewEncoder(w).Encode(x); err != nil {
+-		panic(fmt.Errorf("error marshalling %#v: %v", x, err))
 -	}
 -}
 -
--func TestAllFiltersBar(t *testing.T) {
--	tearDown()
--	setupServices(true, true, true)
--	actual := sendIt("http://example.com/bar")
--	if "global-service-bar" != actual {
--		t.Fatal("expected: global-service-bar but got:" + actual)
+-// formToGroups parses a set of SecurityGroup form values
+-// as found in a RunInstances request, and returns the resulting
+-// slice of security groups.
+-// It calls fatalf if a group is not found.
+-func (srv *Server) formToGroups(form url.Values) []*securityGroup {
+-	var groups []*securityGroup
+-	for name, values := range form {
+-		switch {
+-		case strings.HasPrefix(name, "SecurityGroupId."):
+-			if g := srv.groups[values[0]]; g != nil {
+-				groups = append(groups, g)
+-			} else {
+-				fatalf(400, "InvalidGroup.NotFound", "unknown group id %q", values[0])
+-			}
+-		case strings.HasPrefix(name, "SecurityGroup."):
+-			var found *securityGroup
+-			for _, g := range srv.groups {
+-				if g.name == values[0] {
+-					found = g
+-				}
+-			}
+-			if found == nil {
+-				fatalf(400, "InvalidGroup.NotFound", "unknown group name %q", values[0])
+-			}
+-			groups = append(groups, found)
+-		}
 -	}
+-	return groups
 -}
 -
--func sendIt(address string) string {
--	httpRequest, _ := http.NewRequest("GET", address, nil)
--	httpRequest.Header.Set("Accept", "*/*")
--	httpWriter := httptest.NewRecorder()
--	DefaultContainer.dispatch(httpWriter, httpRequest)
--	return httpWriter.Body.String()
--}
+-// runInstances implements the EC2 RunInstances entry point.
+-func (srv *Server) runInstances(w http.ResponseWriter, req *http.Request, reqId string) interface{} {
+-	min := atoi(req.Form.Get("MinCount"))
+-	max := atoi(req.Form.Get("MaxCount"))
+-	if min < 0 || max < 1 {
+-		fatalf(400, "InvalidParameterValue", "bad values for MinCount or MaxCount")
+-	}
+-	if min > max {
+-		fatalf(400, "InvalidParameterCombination", "MinCount is greater than MaxCount")
+-	}
+-	var userData []byte
+-	if data := req.Form.Get("UserData"); data != "" {
+-		var err error
+-		userData, err = b64.DecodeString(data)
+-		if err != nil {
+-			fatalf(400, "InvalidParameterValue", "bad UserData value: %v", err)
+-		}
+-	}
 -
--func sendItTo(address string, container *Container) string {
--	httpRequest, _ := http.NewRequest("GET", address, nil)
--	httpRequest.Header.Set("Accept", "*/*")
--	httpWriter := httptest.NewRecorder()
--	container.dispatch(httpWriter, httpRequest)
--	return httpWriter.Body.String()
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/install.sh b/Godeps/_workspace/src/github.com/emicklei/go-restful/install.sh
-deleted file mode 100644
-index b5de8a2..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/install.sh
-+++ /dev/null
-@@ -1,9 +0,0 @@
--cd examples
--	ls *.go | xargs -I {} go build {}
--	cd ..
--go fmt ...swagger && \
--go test -test.v ...swagger && \
--go install ...swagger && \
--go fmt ...restful && \
--go test -test.v ...restful && \
--go install ...restful
-\ No newline at end of file
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/jsr311.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/jsr311.go
-deleted file mode 100644
-index 3d9d7d8..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/jsr311.go
-+++ /dev/null
-@@ -1,247 +0,0 @@
--package restful
+-	// TODO attributes still to consider:
+-	//    ImageId:                  accept anything, we can verify later
+-	//    KeyName                   ?
+-	//    InstanceType              ?
+-	//    KernelId                  ?
+-	//    RamdiskId                 ?
+-	//    AvailZone                 ?
+-	//    GroupName                 tag
+-	//    Monitoring                ignore?
+-	//    SubnetId                  ?
+-	//    DisableAPITermination     bool
+-	//    ShutdownBehavior          string
+-	//    PrivateIPAddress          string
 -
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
+-	srv.mu.Lock()
+-	defer srv.mu.Unlock()
 -
--import (
--	"errors"
--	"fmt"
--	"net/http"
--	"sort"
--)
+-	// make sure that form fields are correct before creating the reservation.
+-	instType := req.Form.Get("InstanceType")
+-	imageId := req.Form.Get("ImageId")
 -
--// RouterJSR311 implements the flow for matching Requests to Routes (and consequently Resource Functions)
--// as specified by the JSR311 http://jsr311.java.net/nonav/releases/1.1/spec/spec.html.
--// RouterJSR311 implements the Router interface.
--// Concept of locators is not implemented.
--type RouterJSR311 struct{}
+-	r := srv.newReservation(srv.formToGroups(req.Form))
 -
--// SelectRoute is part of the Router interface and returns the best match
--// for the WebService and its Route for the given Request.
--func (r RouterJSR311) SelectRoute(
--	webServices []*WebService,
--	httpRequest *http.Request) (selectedService *WebService, selectedRoute *Route, err error) {
+-	var resp ec2.RunInstancesResp
+-	resp.RequestId = reqId
+-	resp.ReservationId = r.id
+-	resp.OwnerId = ownerId
 -
--	// Identify the root resource class (WebService)
--	dispatcher, finalMatch, err := r.detectDispatcher(httpRequest.URL.Path, webServices)
--	if err != nil {
--		return nil, nil, NewError(http.StatusNotFound, "")
--	}
--	// Obtain the set of candidate methods (Routes)
--	routes := r.selectRoutes(dispatcher, finalMatch)
--	if len(routes) == 0 {
--		return dispatcher, nil, NewError(http.StatusNotFound, "404: Page Not Found")
+-	for i := 0; i < max; i++ {
+-		inst := srv.newInstance(r, instType, imageId, srv.initialInstanceState)
+-		inst.UserData = userData
+-		resp.Instances = append(resp.Instances, inst.ec2instance())
 -	}
--
--	// Identify the method (Route) that will handle the request
--	route, ok := r.detectRoute(routes, httpRequest)
--	return dispatcher, route, ok
+-	return &resp
 -}
 -
--// http://jsr311.java.net/nonav/releases/1.1/spec/spec3.html#x3-360003.7.2
--func (r RouterJSR311) detectRoute(routes []Route, httpRequest *http.Request) (*Route, error) {
--	// http method
--	methodOk := []Route{}
--	for _, each := range routes {
--		if httpRequest.Method == each.Method {
--			methodOk = append(methodOk, each)
--		}
--	}
--	if len(methodOk) == 0 {
--		if trace {
--			traceLogger.Printf("no Route found (in %d routes) that matches HTTP method %s\n", len(routes), httpRequest.Method)
--		}
--		return nil, NewError(http.StatusMethodNotAllowed, "405: Method Not Allowed")
+-func (srv *Server) group(group ec2.SecurityGroup) *securityGroup {
+-	if group.Id != "" {
+-		return srv.groups[group.Id]
 -	}
--	inputMediaOk := methodOk
--	// content-type
--	contentType := httpRequest.Header.Get(HEADER_ContentType)
--	if httpRequest.ContentLength > 0 {
--		inputMediaOk = []Route{}
--		for _, each := range methodOk {
--			if each.matchesContentType(contentType) {
--				inputMediaOk = append(inputMediaOk, each)
--			}
--		}
--		if len(inputMediaOk) == 0 {
--			if trace {
--				traceLogger.Printf("no Route found (from %d) that matches HTTP Content-Type: %s\n", len(methodOk), contentType)
--			}
--			return nil, NewError(http.StatusUnsupportedMediaType, "415: Unsupported Media Type")
+-	for _, g := range srv.groups {
+-		if g.name == group.Name {
+-			return g
 -		}
 -	}
--	// accept
--	outputMediaOk := []Route{}
--	accept := httpRequest.Header.Get(HEADER_Accept)
--	if accept == "" {
--		accept = "*/*"
--	}
--	for _, each := range inputMediaOk {
--		if each.matchesAccept(accept) {
--			outputMediaOk = append(outputMediaOk, each)
+-	return nil
+-}
+-
+-// NewInstances creates n new instances in srv with the given instance type,
+-// image ID,  initial state and security groups. If any group does not already
+-// exist, it will be created. NewInstances returns the ids of the new instances.
+-func (srv *Server) NewInstances(n int, instType string, imageId string, state ec2.InstanceState, groups []ec2.SecurityGroup) []string {
+-	srv.mu.Lock()
+-	defer srv.mu.Unlock()
+-
+-	rgroups := make([]*securityGroup, len(groups))
+-	for i, group := range groups {
+-		g := srv.group(group)
+-		if g == nil {
+-			fatalf(400, "InvalidGroup.NotFound", "no such group %v", g)
 -		}
+-		rgroups[i] = g
 -	}
--	if len(outputMediaOk) == 0 {
--		if trace {
--			traceLogger.Printf("no Route found (from %d) that matches HTTP Accept: %s\n", len(inputMediaOk), accept)
--		}
--		return nil, NewError(http.StatusNotAcceptable, "406: Not Acceptable")
+-	r := srv.newReservation(rgroups)
+-
+-	ids := make([]string, n)
+-	for i := 0; i < n; i++ {
+-		inst := srv.newInstance(r, instType, imageId, state)
+-		ids[i] = inst.id
 -	}
--	return r.bestMatchByMedia(outputMediaOk, contentType, accept), nil
+-	return ids
 -}
 -
--// http://jsr311.java.net/nonav/releases/1.1/spec/spec3.html#x3-360003.7.2
--// n/m > n/* > */*
--func (r RouterJSR311) bestMatchByMedia(routes []Route, contentType string, accept string) *Route {
--	// TODO
--	return &routes[0]
+-func (srv *Server) newInstance(r *reservation, instType string, imageId string, state ec2.InstanceState) *Instance {
+-	inst := &Instance{
+-		id:          fmt.Sprintf("i-%d", srv.maxId.next()),
+-		instType:    instType,
+-		imageId:     imageId,
+-		state:       state,
+-		reservation: r,
+-	}
+-	srv.instances[inst.id] = inst
+-	r.instances[inst.id] = inst
+-	return inst
 -}
 -
--// http://jsr311.java.net/nonav/releases/1.1/spec/spec3.html#x3-360003.7.2  (step 2)
--func (r RouterJSR311) selectRoutes(dispatcher *WebService, pathRemainder string) []Route {
--	filtered := &sortableRouteCandidates{}
--	for _, each := range dispatcher.Routes() {
--		pathExpr := each.pathExpr
--		matches := pathExpr.Matcher.FindStringSubmatch(pathRemainder)
--		if matches != nil {
--			lastMatch := matches[len(matches)-1]
--			if len(lastMatch) == 0 || lastMatch == "/" { // do not include if value is neither empty nor ‘/’.
--				filtered.candidates = append(filtered.candidates,
--					routeCandidate{each, len(matches) - 1, pathExpr.LiteralCount, pathExpr.VarCount})
--			}
--		}
--	}
--	if len(filtered.candidates) == 0 {
--		if trace {
--			traceLogger.Printf("WebService on path %s has no routes that match URL path remainder:%s\n", dispatcher.rootPath, pathRemainder)
--		}
--		return []Route{}
+-func (srv *Server) newReservation(groups []*securityGroup) *reservation {
+-	r := &reservation{
+-		id:        fmt.Sprintf("r-%d", srv.reservationId.next()),
+-		instances: make(map[string]*Instance),
+-		groups:    groups,
 -	}
--	sort.Sort(sort.Reverse(filtered))
 -
--	// select other routes from candidates whoes expression matches rmatch
--	matchingRoutes := []Route{filtered.candidates[0].route}
--	for c := 1; c < len(filtered.candidates); c++ {
--		each := filtered.candidates[c]
--		if each.route.pathExpr.Matcher.MatchString(pathRemainder) {
--			matchingRoutes = append(matchingRoutes, each.route)
--		}
--	}
--	return matchingRoutes
+-	srv.reservations[r.id] = r
+-	return r
 -}
 -
--// http://jsr311.java.net/nonav/releases/1.1/spec/spec3.html#x3-360003.7.2 (step 1)
--func (r RouterJSR311) detectDispatcher(requestPath string, dispatchers []*WebService) (*WebService, string, error) {
--	filtered := &sortableDispatcherCandidates{}
--	for _, each := range dispatchers {
--		matches := each.pathExpr.Matcher.FindStringSubmatch(requestPath)
--		if matches != nil {
--			filtered.candidates = append(filtered.candidates,
--				dispatcherCandidate{each, matches[len(matches)-1], len(matches), each.pathExpr.LiteralCount, each.pathExpr.VarCount})
+-func (srv *Server) terminateInstances(w http.ResponseWriter, req *http.Request, reqId string) interface{} {
+-	srv.mu.Lock()
+-	defer srv.mu.Unlock()
+-	var resp ec2.TerminateInstancesResp
+-	resp.RequestId = reqId
+-	var insts []*Instance
+-	for attr, vals := range req.Form {
+-		if strings.HasPrefix(attr, "InstanceId.") {
+-			id := vals[0]
+-			inst := srv.instances[id]
+-			if inst == nil {
+-				fatalf(400, "InvalidInstanceID.NotFound", "no such instance id %q", id)
+-			}
+-			insts = append(insts, inst)
 -		}
 -	}
--	if len(filtered.candidates) == 0 {
--		if trace {
--			traceLogger.Printf("no WebService was found to match URL path:%s\n", requestPath)
--		}
--		return nil, "", errors.New("not found")
+-	for _, inst := range insts {
+-		resp.StateChanges = append(resp.StateChanges, inst.terminate())
 -	}
--	sort.Sort(sort.Reverse(filtered))
--	return filtered.candidates[0].dispatcher, filtered.candidates[0].finalMatch, nil
+-	return &resp
 -}
 -
--// Types and functions to support the sorting of Routes
--
--type routeCandidate struct {
--	route           Route
--	matchesCount    int // the number of capturing groups
--	literalCount    int // the number of literal characters (means those not resulting from template variable substitution)
--	nonDefaultCount int // the number of capturing groups with non-default regular expressions (i.e. not ‘([^  /]+?)’)
+-func (inst *Instance) terminate() (d ec2.InstanceStateChange) {
+-	d.PreviousState = inst.state
+-	inst.state = ShuttingDown
+-	d.CurrentState = inst.state
+-	d.InstanceId = inst.id
+-	return d
 -}
 -
--func (r routeCandidate) expressionToMatch() string {
--	return r.route.pathExpr.Source
+-func (inst *Instance) ec2instance() ec2.Instance {
+-	return ec2.Instance{
+-		InstanceId:   inst.id,
+-		InstanceType: inst.instType,
+-		ImageId:      inst.imageId,
+-		DNSName:      fmt.Sprintf("%s.example.com", inst.id),
+-		// TODO the rest
+-	}
 -}
 -
--func (r routeCandidate) String() string {
--	return fmt.Sprintf("(m=%d,l=%d,n=%d)", r.matchesCount, r.literalCount, r.nonDefaultCount)
+-func (inst *Instance) matchAttr(attr, value string) (ok bool, err error) {
+-	switch attr {
+-	case "architecture":
+-		return value == "i386", nil
+-	case "instance-id":
+-		return inst.id == value, nil
+-	case "group-id":
+-		for _, g := range inst.reservation.groups {
+-			if g.id == value {
+-				return true, nil
+-			}
+-		}
+-		return false, nil
+-	case "group-name":
+-		for _, g := range inst.reservation.groups {
+-			if g.name == value {
+-				return true, nil
+-			}
+-		}
+-		return false, nil
+-	case "image-id":
+-		return value == inst.imageId, nil
+-	case "instance-state-code":
+-		code, err := strconv.Atoi(value)
+-		if err != nil {
+-			return false, err
+-		}
+-		return code&0xff == inst.state.Code, nil
+-	case "instance-state-name":
+-		return value == inst.state.Name, nil
+-	}
+-	return false, fmt.Errorf("unknown attribute %q", attr)
 -}
 -
--type sortableRouteCandidates struct {
--	candidates []routeCandidate
--}
+-var (
+-	Pending      = ec2.InstanceState{0, "pending"}
+-	Running      = ec2.InstanceState{16, "running"}
+-	ShuttingDown = ec2.InstanceState{32, "shutting-down"}
+-	Terminated   = ec2.InstanceState{16, "terminated"}
+-	Stopped      = ec2.InstanceState{16, "stopped"}
+-)
 -
--func (rcs *sortableRouteCandidates) Len() int {
--	return len(rcs.candidates)
--}
--func (rcs *sortableRouteCandidates) Swap(i, j int) {
--	rcs.candidates[i], rcs.candidates[j] = rcs.candidates[j], rcs.candidates[i]
--}
--func (rcs *sortableRouteCandidates) Less(i, j int) bool {
--	ci := rcs.candidates[i]
--	cj := rcs.candidates[j]
--	// primary key
--	if ci.literalCount < cj.literalCount {
--		return true
--	}
--	if ci.literalCount > cj.literalCount {
--		return false
+-func (srv *Server) createSecurityGroup(w http.ResponseWriter, req *http.Request, reqId string) interface{} {
+-	name := req.Form.Get("GroupName")
+-	if name == "" {
+-		fatalf(400, "InvalidParameterValue", "empty security group name")
 -	}
--	// secundary key
--	if ci.matchesCount < cj.matchesCount {
--		return true
+-	srv.mu.Lock()
+-	defer srv.mu.Unlock()
+-	if srv.group(ec2.SecurityGroup{Name: name}) != nil {
+-		fatalf(400, "InvalidGroup.Duplicate", "group %q already exists", name)
 -	}
--	if ci.matchesCount > cj.matchesCount {
--		return false
+-	g := &securityGroup{
+-		name:        name,
+-		description: req.Form.Get("GroupDescription"),
+-		id:          fmt.Sprintf("sg-%d", srv.groupId.next()),
+-		perms:       make(map[permKey]bool),
 -	}
--	// tertiary key
--	if ci.nonDefaultCount < cj.nonDefaultCount {
--		return true
+-	srv.groups[g.id] = g
+-	// we define a local type for this because ec2.CreateSecurityGroupResp
+-	// contains SecurityGroup, but the response to this request
+-	// should not contain the security group name.
+-	type CreateSecurityGroupResponse struct {
+-		RequestId string `xml:"requestId"`
+-		Return    bool   `xml:"return"`
+-		GroupId   string `xml:"groupId"`
 -	}
--	if ci.nonDefaultCount > cj.nonDefaultCount {
--		return false
+-	r := &CreateSecurityGroupResponse{
+-		RequestId: reqId,
+-		Return:    true,
+-		GroupId:   g.id,
 -	}
--	// quaternary key ("source" is interpreted as Path)
--	return ci.route.Path < cj.route.Path
+-	return r
 -}
 -
--// Types and functions to support the sorting of Dispatchers
--
--type dispatcherCandidate struct {
--	dispatcher      *WebService
--	finalMatch      string
--	matchesCount    int // the number of capturing groups
--	literalCount    int // the number of literal characters (means those not resulting from template variable substitution)
--	nonDefaultCount int // the number of capturing groups with non-default regular expressions (i.e. not ‘([^  /]+?)’)
--}
--type sortableDispatcherCandidates struct {
--	candidates []dispatcherCandidate
+-func (srv *Server) notImplemented(w http.ResponseWriter, req *http.Request, reqId string) interface{} {
+-	fatalf(500, "InternalError", "not implemented")
+-	panic("not reached")
 -}
 -
--func (dc *sortableDispatcherCandidates) Len() int {
--	return len(dc.candidates)
--}
--func (dc *sortableDispatcherCandidates) Swap(i, j int) {
--	dc.candidates[i], dc.candidates[j] = dc.candidates[j], dc.candidates[i]
--}
--func (dc *sortableDispatcherCandidates) Less(i, j int) bool {
--	ci := dc.candidates[i]
--	cj := dc.candidates[j]
--	// primary key
--	if ci.matchesCount < cj.matchesCount {
--		return true
--	}
--	if ci.matchesCount > cj.matchesCount {
--		return false
--	}
--	// secundary key
--	if ci.literalCount < cj.literalCount {
--		return true
--	}
--	if ci.literalCount > cj.literalCount {
--		return false
+-func (srv *Server) describeInstances(w http.ResponseWriter, req *http.Request, reqId string) interface{} {
+-	srv.mu.Lock()
+-	defer srv.mu.Unlock()
+-	insts := make(map[*Instance]bool)
+-	for name, vals := range req.Form {
+-		if !strings.HasPrefix(name, "InstanceId.") {
+-			continue
+-		}
+-		inst := srv.instances[vals[0]]
+-		if inst == nil {
+-			fatalf(400, "InvalidInstanceID.NotFound", "instance %q not found", vals[0])
+-		}
+-		insts[inst] = true
 -	}
--	// tertiary key
--	return ci.nonDefaultCount < cj.nonDefaultCount
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/jsr311_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/jsr311_test.go
-deleted file mode 100644
-index b531b7f..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/jsr311_test.go
-+++ /dev/null
-@@ -1,236 +0,0 @@
--package restful
--
--import (
--	"io"
--	"sort"
--	"testing"
--)
--
--//
--// Step 1 tests
--//
--var paths = []struct {
--	// url with path (1) is handled by service with root (2) and last capturing group has value final (3)
--	path, root, final string
--}{
--	{"/", "/", "/"},
--	{"/p", "/p", ""},
--	{"/p/x", "/p/{q}", ""},
--	{"/q/x", "/q", "/x"},
--	{"/p/x/", "/p/{q}", "/"},
--	{"/p/x/y", "/p/{q}", "/y"},
--	{"/q/x/y", "/q", "/x/y"},
--	{"/z/q", "/{p}/q", ""},
--	{"/a/b/c/q", "/", "/a/b/c/q"},
--}
 -
--func TestDetectDispatcher(t *testing.T) {
--	ws1 := new(WebService).Path("/")
--	ws2 := new(WebService).Path("/p")
--	ws3 := new(WebService).Path("/q")
--	ws4 := new(WebService).Path("/p/q")
--	ws5 := new(WebService).Path("/p/{q}")
--	ws6 := new(WebService).Path("/p/{q}/")
--	ws7 := new(WebService).Path("/{p}/q")
--	var dispatchers = []*WebService{ws1, ws2, ws3, ws4, ws5, ws6, ws7}
+-	f := newFilter(req.Form)
 -
--	wc := NewContainer()
--	for _, each := range dispatchers {
--		wc.Add(each)
+-	var resp ec2.InstancesResp
+-	resp.RequestId = reqId
+-	for _, r := range srv.reservations {
+-		var instances []ec2.Instance
+-		for _, inst := range r.instances {
+-			if len(insts) > 0 && !insts[inst] {
+-				continue
+-			}
+-			ok, err := f.ok(inst)
+-			if ok {
+-				instances = append(instances, inst.ec2instance())
+-			} else if err != nil {
+-				fatalf(400, "InvalidParameterValue", "describe instances: %v", err)
+-			}
+-		}
+-		if len(instances) > 0 {
+-			var groups []ec2.SecurityGroup
+-			for _, g := range r.groups {
+-				groups = append(groups, g.ec2SecurityGroup())
+-			}
+-			resp.Reservations = append(resp.Reservations, ec2.Reservation{
+-				ReservationId:  r.id,
+-				OwnerId:        ownerId,
+-				Instances:      instances,
+-				SecurityGroups: groups,
+-			})
+-		}
 -	}
+-	return &resp
+-}
 -
--	router := RouterJSR311{}
+-func (srv *Server) describeSecurityGroups(w http.ResponseWriter, req *http.Request, reqId string) interface{} {
+-	// BUG similar bug to describeInstances, but for GroupName and GroupId
+-	srv.mu.Lock()
+-	defer srv.mu.Unlock()
 -
--	ok := true
--	for i, fixture := range paths {
--		who, final, err := router.detectDispatcher(fixture.path, dispatchers)
--		if err != nil {
--			t.Logf("error in detection:%v", err)
--			ok = false
+-	var groups []*securityGroup
+-	for name, vals := range req.Form {
+-		var g ec2.SecurityGroup
+-		switch {
+-		case strings.HasPrefix(name, "GroupName."):
+-			g.Name = vals[0]
+-		case strings.HasPrefix(name, "GroupId."):
+-			g.Id = vals[0]
+-		default:
+-			continue
 -		}
--		if who.RootPath() != fixture.root {
--			t.Logf("[line:%v] Unexpected dispatcher, expected:%v, actual:%v", i, fixture.root, who.RootPath())
--			ok = false
+-		sg := srv.group(g)
+-		if sg == nil {
+-			fatalf(400, "InvalidGroup.NotFound", "no such group %v", g)
 -		}
--		if final != fixture.final {
--			t.Logf("[line:%v] Unexpected final, expected:%v, actual:%v", i, fixture.final, final)
--			ok = false
+-		groups = append(groups, sg)
+-	}
+-	if len(groups) == 0 {
+-		for _, g := range srv.groups {
+-			groups = append(groups, g)
 -		}
 -	}
--	if !ok {
--		t.Fail()
+-
+-	f := newFilter(req.Form)
+-	var resp ec2.SecurityGroupsResp
+-	resp.RequestId = reqId
+-	for _, group := range groups {
+-		ok, err := f.ok(group)
+-		if ok {
+-			resp.Groups = append(resp.Groups, ec2.SecurityGroupInfo{
+-				OwnerId:       ownerId,
+-				SecurityGroup: group.ec2SecurityGroup(),
+-				Description:   group.description,
+-				IPPerms:       group.ec2Perms(),
+-			})
+-		} else if err != nil {
+-			fatalf(400, "InvalidParameterValue", "describe security groups: %v", err)
+-		}
 -	}
+-	return &resp
 -}
 -
--//
--// Step 2 tests
--//
+-func (srv *Server) authorizeSecurityGroupIngress(w http.ResponseWriter, req *http.Request, reqId string) interface{} {
+-	srv.mu.Lock()
+-	defer srv.mu.Unlock()
+-	g := srv.group(ec2.SecurityGroup{
+-		Name: req.Form.Get("GroupName"),
+-		Id:   req.Form.Get("GroupId"),
+-	})
+-	if g == nil {
+-		fatalf(400, "InvalidGroup.NotFound", "group not found")
+-	}
+-	perms := srv.parsePerms(req)
 -
--// go test -v -test.run TestISSUE_30 ...restful
--func TestISSUE_30(t *testing.T) {
--	ws1 := new(WebService).Path("/users")
--	ws1.Route(ws1.GET("/{id}").To(dummy))
--	ws1.Route(ws1.POST("/login").To(dummy))
--	routes := RouterJSR311{}.selectRoutes(ws1, "/login")
--	if len(routes) != 2 {
--		t.Fatal("expected 2 routes")
+-	for _, p := range perms {
+-		if g.perms[p] {
+-			fatalf(400, "InvalidPermission.Duplicate", "Permission has already been authorized on the specified group")
+-		}
 -	}
--	if routes[0].Path != "/users/login" {
--		t.Error("first is", routes[0].Path)
--		t.Logf("routes:%v", routes)
+-	for _, p := range perms {
+-		g.perms[p] = true
+-	}
+-	return &ec2.SimpleResp{
+-		XMLName:   xml.Name{"", "AuthorizeSecurityGroupIngressResponse"},
+-		RequestId: reqId,
 -	}
 -}
 -
--// go test -v -test.run TestISSUE_34 ...restful
--func TestISSUE_34(t *testing.T) {
--	ws1 := new(WebService).Path("/")
--	ws1.Route(ws1.GET("/{type}/{id}").To(dummy))
--	ws1.Route(ws1.GET("/network/{id}").To(dummy))
--	routes := RouterJSR311{}.selectRoutes(ws1, "/network/12")
--	if len(routes) != 2 {
--		t.Fatal("expected 2 routes")
--	}
--	if routes[0].Path != "/network/{id}" {
--		t.Error("first is", routes[0].Path)
--		t.Logf("routes:%v", routes)
+-func (srv *Server) revokeSecurityGroupIngress(w http.ResponseWriter, req *http.Request, reqId string) interface{} {
+-	srv.mu.Lock()
+-	defer srv.mu.Unlock()
+-	g := srv.group(ec2.SecurityGroup{
+-		Name: req.Form.Get("GroupName"),
+-		Id:   req.Form.Get("GroupId"),
+-	})
+-	if g == nil {
+-		fatalf(400, "InvalidGroup.NotFound", "group not found")
 -	}
--}
+-	perms := srv.parsePerms(req)
 -
--// go test -v -test.run TestISSUE_34_2 ...restful
--func TestISSUE_34_2(t *testing.T) {
--	ws1 := new(WebService).Path("/")
--	// change the registration order
--	ws1.Route(ws1.GET("/network/{id}").To(dummy))
--	ws1.Route(ws1.GET("/{type}/{id}").To(dummy))
--	routes := RouterJSR311{}.selectRoutes(ws1, "/network/12")
--	if len(routes) != 2 {
--		t.Fatal("expected 2 routes")
+-	// Note EC2 does not give an error if asked to revoke an authorization
+-	// that does not exist.
+-	for _, p := range perms {
+-		delete(g.perms, p)
 -	}
--	if routes[0].Path != "/network/{id}" {
--		t.Error("first is", routes[0].Path)
+-	return &ec2.SimpleResp{
+-		XMLName:   xml.Name{"", "RevokeSecurityGroupIngressResponse"},
+-		RequestId: reqId,
 -	}
 -}
 -
--// go test -v -test.run TestISSUE_137 ...restful
--func TestISSUE_137(t *testing.T) {
--	ws1 := new(WebService)
--	ws1.Route(ws1.GET("/hello").To(dummy))
--	routes := RouterJSR311{}.selectRoutes(ws1, "/")
--	t.Log(routes)
--	if len(routes) > 0 {
--		t.Error("no route expected")
--	}
--}
+-var secGroupPat = regexp.MustCompile(`^sg-[a-z0-9]+$`)
+-var ipPat = regexp.MustCompile(`^[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+/[0-9]+$`)
+-var ownerIdPat = regexp.MustCompile(`^[0-9]+$`)
 -
--func TestSelectRoutesSlash(t *testing.T) {
--	ws1 := new(WebService).Path("/")
--	ws1.Route(ws1.GET("").To(dummy))
--	ws1.Route(ws1.GET("/").To(dummy))
--	ws1.Route(ws1.GET("/u").To(dummy))
--	ws1.Route(ws1.POST("/u").To(dummy))
--	ws1.Route(ws1.POST("/u/v").To(dummy))
--	ws1.Route(ws1.POST("/u/{w}").To(dummy))
--	ws1.Route(ws1.POST("/u/{w}/z").To(dummy))
--	routes := RouterJSR311{}.selectRoutes(ws1, "/u")
--	checkRoutesContains(routes, "/u", t)
--	checkRoutesContainsNo(routes, "/u/v", t)
--	checkRoutesContainsNo(routes, "/", t)
--	checkRoutesContainsNo(routes, "/u/{w}/z", t)
--}
--func TestSelectRoutesU(t *testing.T) {
--	ws1 := new(WebService).Path("/u")
--	ws1.Route(ws1.GET("").To(dummy))
--	ws1.Route(ws1.GET("/").To(dummy))
--	ws1.Route(ws1.GET("/v").To(dummy))
--	ws1.Route(ws1.POST("/{w}").To(dummy))
--	ws1.Route(ws1.POST("/{w}/z").To(dummy))          // so full path = /u/{w}/z
--	routes := RouterJSR311{}.selectRoutes(ws1, "/v") // test against /u/v
--	checkRoutesContains(routes, "/u/{w}", t)
--}
+-// parsePerms returns a slice of permKey values extracted
+-// from the permission fields in req.
+-func (srv *Server) parsePerms(req *http.Request) []permKey {
+-	// perms maps an index found in the form to its associated
+-	// IPPerm. For instance, the form value with key
+-	// "IpPermissions.3.FromPort" will be stored in perms[3].FromPort
+-	perms := make(map[int]ec2.IPPerm)
 -
--func TestSelectRoutesUsers1(t *testing.T) {
--	ws1 := new(WebService).Path("/users")
--	ws1.Route(ws1.POST("").To(dummy))
--	ws1.Route(ws1.POST("/").To(dummy))
--	ws1.Route(ws1.PUT("/{id}").To(dummy))
--	routes := RouterJSR311{}.selectRoutes(ws1, "/1")
--	checkRoutesContains(routes, "/users/{id}", t)
--}
--func checkRoutesContains(routes []Route, path string, t *testing.T) {
--	if !containsRoutePath(routes, path, t) {
--		for _, r := range routes {
--			t.Logf("route %v %v", r.Method, r.Path)
+-	type subgroupKey struct {
+-		id1, id2 int
+-	}
+-	// Each IPPerm can have many source security groups.  The form key
+-	// for a source security group contains two indices: the index
+-	// of the IPPerm and the sub-index of the security group. The
+-	// sourceGroups map maps from a subgroupKey containing these
+-	// two indices to the associated security group. For instance,
+-	// the form value with key "IPPermissions.3.Groups.2.GroupName"
+-	// will be stored in sourceGroups[subgroupKey{3, 2}].Name.
+-	sourceGroups := make(map[subgroupKey]ec2.UserSecurityGroup)
+-
+-	// For each value in the form we store its associated information in the
+-	// above maps. The maps are necessary because the form keys may
+-	// arrive in any order, and the indices are not
+-	// necessarily sequential or even small.
+-	for name, vals := range req.Form {
+-		val := vals[0]
+-		var id1 int
+-		var rest string
+-		if x, _ := fmt.Sscanf(name, "IpPermissions.%d.%s", &id1, &rest); x != 2 {
+-			continue
+-		}
+-		ec2p := perms[id1]
+-		switch {
+-		case rest == "FromPort":
+-			ec2p.FromPort = atoi(val)
+-		case rest == "ToPort":
+-			ec2p.ToPort = atoi(val)
+-		case rest == "IpProtocol":
+-			switch val {
+-			case "tcp", "udp", "icmp":
+-				ec2p.Protocol = val
+-			default:
+-				// check it's a well formed number
+-				atoi(val)
+-				ec2p.Protocol = val
+-			}
+-		case strings.HasPrefix(rest, "Groups."):
+-			k := subgroupKey{id1: id1}
+-			if x, _ := fmt.Sscanf(rest[len("Groups."):], "%d.%s", &k.id2, &rest); x != 2 {
+-				continue
+-			}
+-			g := sourceGroups[k]
+-			switch rest {
+-			case "UserId":
+-				// BUG if the user id is blank, this does not conform to the
+-				// way that EC2 handles it - a specified but blank owner id
+-				// can cause RevokeSecurityGroupIngress to fail with
+-				// "group not found" even if the security group id has been
+-				// correctly specified.
+-				// By failing here, we ensure that we fail early in this case.
+-				if !ownerIdPat.MatchString(val) {
+-					fatalf(400, "InvalidUserID.Malformed", "Invalid user ID: %q", val)
+-				}
+-				g.OwnerId = val
+-			case "GroupName":
+-				g.Name = val
+-			case "GroupId":
+-				if !secGroupPat.MatchString(val) {
+-					fatalf(400, "InvalidGroupId.Malformed", "Invalid group ID: %q", val)
+-				}
+-				g.Id = val
+-			default:
+-				fatalf(400, "UnknownParameter", "unknown parameter %q", name)
+-			}
+-			sourceGroups[k] = g
+-		case strings.HasPrefix(rest, "IpRanges."):
+-			var id2 int
+-			if x, _ := fmt.Sscanf(rest[len("IpRanges."):], "%d.%s", &id2, &rest); x != 2 {
+-				continue
+-			}
+-			switch rest {
+-			case "CidrIp":
+-				if !ipPat.MatchString(val) {
+-					fatalf(400, "InvalidPermission.Malformed", "Invalid IP range: %q", val)
+-				}
+-				ec2p.SourceIPs = append(ec2p.SourceIPs, val)
+-			default:
+-				fatalf(400, "UnknownParameter", "unknown parameter %q", name)
+-			}
+-		default:
+-			fatalf(400, "UnknownParameter", "unknown parameter %q", name)
 -		}
--		t.Fatalf("routes should include [%v]:", path)
+-		perms[id1] = ec2p
 -	}
--}
--func checkRoutesContainsNo(routes []Route, path string, t *testing.T) {
--	if containsRoutePath(routes, path, t) {
--		for _, r := range routes {
--			t.Logf("route %v %v", r.Method, r.Path)
--		}
--		t.Fatalf("routes should not include [%v]:", path)
+-	// Associate each set of source groups with its IPPerm.
+-	for k, g := range sourceGroups {
+-		p := perms[k.id1]
+-		p.SourceGroups = append(p.SourceGroups, g)
+-		perms[k.id1] = p
 -	}
--}
--func containsRoutePath(routes []Route, path string, t *testing.T) bool {
--	for _, each := range routes {
--		if each.Path == path {
--			return true
+-
+-	// Now that we have built up the IPPerms we need, we check for
+-	// parameter errors and build up a permKey for each permission,
+-	// looking up security groups from srv as we do so.
+-	var result []permKey
+-	for _, p := range perms {
+-		if p.FromPort > p.ToPort {
+-			fatalf(400, "InvalidParameterValue", "invalid port range")
+-		}
+-		k := permKey{
+-			protocol: p.Protocol,
+-			fromPort: p.FromPort,
+-			toPort:   p.ToPort,
+-		}
+-		for _, g := range p.SourceGroups {
+-			if g.OwnerId != "" && g.OwnerId != ownerId {
+-				fatalf(400, "InvalidGroup.NotFound", "group %q not found", g.Name)
+-			}
+-			var ec2g ec2.SecurityGroup
+-			switch {
+-			case g.Id != "":
+-				ec2g.Id = g.Id
+-			case g.Name != "":
+-				ec2g.Name = g.Name
+-			}
+-			k.group = srv.group(ec2g)
+-			if k.group == nil {
+-				fatalf(400, "InvalidGroup.NotFound", "group %v not found", g)
+-			}
+-			result = append(result, k)
+-		}
+-		k.group = nil
+-		for _, ip := range p.SourceIPs {
+-			k.ipAddr = ip
+-			result = append(result, k)
 -		}
 -	}
--	return false
--}
--
--var tempregexs = []struct {
--	template, regex        string
--	literalCount, varCount int
--}{
--	{"", "^(/.*)?$", 0, 0},
--	{"/a/{b}/c/", "^/a/([^/]+?)/c(/.*)?$", 2, 1},
--	{"/{a}/{b}/{c-d-e}/", "^/([^/]+?)/([^/]+?)/([^/]+?)(/.*)?$", 0, 3},
--	{"/{p}/abcde", "^/([^/]+?)/abcde(/.*)?$", 5, 1},
+-	return result
 -}
 -
--func TestTemplateToRegularExpression(t *testing.T) {
--	ok := true
--	for i, fixture := range tempregexs {
--		actual, lCount, vCount, _ := templateToRegularExpression(fixture.template)
--		if actual != fixture.regex {
--			t.Logf("regex mismatch, expected:%v , actual:%v, line:%v\n", fixture.regex, actual, i) // 11 = where the data starts
--			ok = false
+-func (srv *Server) deleteSecurityGroup(w http.ResponseWriter, req *http.Request, reqId string) interface{} {
+-	srv.mu.Lock()
+-	defer srv.mu.Unlock()
+-	g := srv.group(ec2.SecurityGroup{
+-		Name: req.Form.Get("GroupName"),
+-		Id:   req.Form.Get("GroupId"),
+-	})
+-	if g == nil {
+-		fatalf(400, "InvalidGroup.NotFound", "group not found")
+-	}
+-	for _, r := range srv.reservations {
+-		for _, h := range r.groups {
+-			if h == g && r.hasRunningMachine() {
+-				fatalf(500, "InvalidGroup.InUse", "group is currently in use by a running instance")
+-			}
 -		}
--		if lCount != fixture.literalCount {
--			t.Logf("literal count mismatch, expected:%v , actual:%v, line:%v\n", fixture.literalCount, lCount, i)
--			ok = false
+-	}
+-	for _, sg := range srv.groups {
+-		// If a group refers to itself, it's ok to delete it.
+-		if sg == g {
+-			continue
 -		}
--		if vCount != fixture.varCount {
--			t.Logf("variable count mismatch, expected:%v , actual:%v, line:%v\n", fixture.varCount, vCount, i)
--			ok = false
+-		for k := range sg.perms {
+-			if k.group == g {
+-				fatalf(500, "InvalidGroup.InUse", "group is currently in use by group %q", sg.id)
+-			}
 -		}
 -	}
--	if !ok {
--		t.Fatal("one or more expression did not match")
+-
+-	delete(srv.groups, g.id)
+-	return &ec2.SimpleResp{
+-		XMLName:   xml.Name{"", "DeleteSecurityGroupResponse"},
+-		RequestId: reqId,
 -	}
 -}
 -
--// go test -v -test.run TestSortableRouteCandidates ...restful
--func TestSortableRouteCandidates(t *testing.T) {
--	fixture := &sortableRouteCandidates{}
--	r1 := routeCandidate{matchesCount: 0, literalCount: 0, nonDefaultCount: 0}
--	r2 := routeCandidate{matchesCount: 0, literalCount: 0, nonDefaultCount: 1}
--	r3 := routeCandidate{matchesCount: 0, literalCount: 1, nonDefaultCount: 1}
--	r4 := routeCandidate{matchesCount: 1, literalCount: 1, nonDefaultCount: 0}
--	r5 := routeCandidate{matchesCount: 1, literalCount: 0, nonDefaultCount: 0}
--	fixture.candidates = append(fixture.candidates, r5, r4, r3, r2, r1)
--	sort.Sort(sort.Reverse(fixture))
--	first := fixture.candidates[0]
--	if first.matchesCount != 1 && first.literalCount != 1 && first.nonDefaultCount != 0 {
--		t.Fatal("expected r4")
--	}
--	last := fixture.candidates[len(fixture.candidates)-1]
--	if last.matchesCount != 0 && last.literalCount != 0 && last.nonDefaultCount != 0 {
--		t.Fatal("expected r1")
+-func (r *reservation) hasRunningMachine() bool {
+-	for _, inst := range r.instances {
+-		if inst.state.Code != ShuttingDown.Code && inst.state.Code != Terminated.Code {
+-			return true
+-		}
 -	}
+-	return false
 -}
 -
--func dummy(req *Request, resp *Response) { io.WriteString(resp.ResponseWriter, "dummy") }
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/logger.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/logger.go
-deleted file mode 100644
-index 25d6a8e..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/logger.go
-+++ /dev/null
-@@ -1,16 +0,0 @@
--package restful
--
--import "log"
--
--// Copyright 2014 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
--
--var trace bool = false
--var traceLogger *log.Logger
+-type counter int
 -
--// TraceLogger enables detailed logging of Http request matching and filter invocation. Default no logger is set.
--func TraceLogger(logger *log.Logger) {
--	traceLogger = logger
--	trace = logger != nil
+-func (c *counter) next() (i int) {
+-	i = int(*c)
+-	(*c)++
+-	return
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/options_filter.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/options_filter.go
-deleted file mode 100644
-index bd5d0c2..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/options_filter.go
-+++ /dev/null
-@@ -1,24 +0,0 @@
--package restful
 -
--import "strings"
--
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
--
--// OPTIONSFilter is a filter function that inspects the Http Request for the OPTIONS method
--// and provides the response with a set of allowed methods for the request URL Path.
--// As for any filter, you can also install it for a particular WebService within a Container
--func (c Container) OPTIONSFilter(req *Request, resp *Response, chain *FilterChain) {
--	if "OPTIONS" != req.Request.Method {
--		chain.ProcessFilter(req, resp)
--		return
+-// atoi is like strconv.Atoi but is fatal if the
+-// string is not well formed.
+-func atoi(s string) int {
+-	i, err := strconv.Atoi(s)
+-	if err != nil {
+-		fatalf(400, "InvalidParameterValue", "bad number: %v", err)
 -	}
--	resp.AddHeader(HEADER_Allow, strings.Join(c.computeAllowedMethods(req), ","))
+-	return i
 -}
 -
--// OPTIONSFilter is a filter function that inspects the Http Request for the OPTIONS method
--// and provides the response with a set of allowed methods for the request URL Path.
--func OPTIONSFilter() FilterFunction {
--	return DefaultContainer.OPTIONSFilter
+-func fatalf(statusCode int, code string, f string, a ...interface{}) {
+-	panic(&ec2.Error{
+-		StatusCode: statusCode,
+-		Code:       code,
+-		Message:    fmt.Sprintf(f, a...),
+-	})
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/options_filter_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/options_filter_test.go
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/export_test.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/export_test.go
 deleted file mode 100644
-index f0fceb8..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/options_filter_test.go
+index 1c24422..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/export_test.go
 +++ /dev/null
-@@ -1,34 +0,0 @@
--package restful
+@@ -1,22 +0,0 @@
+-package ec2
 -
 -import (
--	"net/http"
--	"net/http/httptest"
--	"testing"
+-	"github.com/mitchellh/goamz/aws"
+-	"time"
 -)
 -
--// go test -v -test.run TestOptionsFilter ...restful
--func TestOptionsFilter(t *testing.T) {
--	tearDown()
--	ws := new(WebService)
--	ws.Route(ws.GET("/candy/{kind}").To(dummy))
--	ws.Route(ws.DELETE("/candy/{kind}").To(dummy))
--	ws.Route(ws.POST("/candies").To(dummy))
--	Add(ws)
--	Filter(OPTIONSFilter())
+-func Sign(auth aws.Auth, method, path string, params map[string]string, host string) {
+-	sign(auth, method, path, params, host)
+-}
 -
--	httpRequest, _ := http.NewRequest("OPTIONS", "http://here.io/candy/gum", nil)
--	httpWriter := httptest.NewRecorder()
--	DefaultContainer.dispatch(httpWriter, httpRequest)
--	actual := httpWriter.Header().Get(HEADER_Allow)
--	if "GET,DELETE" != actual {
--		t.Fatal("expected: GET,DELETE but got:" + actual)
--	}
+-func fixedTime() time.Time {
+-	return time.Date(2012, 1, 1, 0, 0, 0, 0, time.UTC)
+-}
 -
--	httpRequest, _ = http.NewRequest("OPTIONS", "http://here.io/candies", nil)
--	httpWriter = httptest.NewRecorder()
--	DefaultContainer.dispatch(httpWriter, httpRequest)
--	actual = httpWriter.Header().Get(HEADER_Allow)
--	if "POST" != actual {
--		t.Fatal("expected: POST but got:" + actual)
+-func FakeTime(fakeIt bool) {
+-	if fakeIt {
+-		timeNow = fixedTime
+-	} else {
+-		timeNow = time.Now
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/parameter.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/parameter.go
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/responses_test.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/responses_test.go
 deleted file mode 100644
-index 7f38a0a..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/parameter.go
+index 0a4dbb3..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/responses_test.go
 +++ /dev/null
-@@ -1,95 +0,0 @@
--package restful
--
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
--
--const (
--	// PathParameterKind = indicator of Request parameter type "path"
--	PathParameterKind = iota
--
--	// QueryParameterKind = indicator of Request parameter type "query"
--	QueryParameterKind
+@@ -1,854 +0,0 @@
+-package ec2_test
 -
--	// BodyParameterKind = indicator of Request parameter type "body"
--	BodyParameterKind
+-var ErrorDump = `
+-<?xml version="1.0" encoding="UTF-8"?>
+-<Response><Errors><Error><Code>UnsupportedOperation</Code>
+-<Message>AMIs with an instance-store root device are not supported for the instance type 't1.micro'.</Message>
+-</Error></Errors><RequestID>0503f4e9-bbd6-483c-b54f-c4ae9f3b30f4</RequestID></Response>
+-`
 -
--	// HeaderParameterKind = indicator of Request parameter type "header"
--	HeaderParameterKind
+-// http://goo.gl/Mcm3b
+-var RunInstancesExample = `
+-<RunInstancesResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
+-  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-  <reservationId>r-47a5402e</reservationId>
+-  <ownerId>999988887777</ownerId>
+-  <groupSet>
+-      <item>
+-          <groupId>sg-67ad940e</groupId>
+-          <groupName>default</groupName>
+-      </item>
+-  </groupSet>
+-  <instancesSet>
+-    <item>
+-      <instanceId>i-2ba64342</instanceId>
+-      <imageId>ami-60a54009</imageId>
+-      <instanceState>
+-        <code>0</code>
+-        <name>pending</name>
+-      </instanceState>
+-      <privateDnsName></privateDnsName>
+-      <dnsName></dnsName>
+-      <keyName>example-key-name</keyName>
+-      <amiLaunchIndex>0</amiLaunchIndex>
+-      <instanceType>m1.small</instanceType>
+-      <launchTime>2007-08-07T11:51:50.000Z</launchTime>
+-      <placement>
+-        <availabilityZone>us-east-1b</availabilityZone>
+-      </placement>
+-      <monitoring>
+-        <state>enabled</state>
+-      </monitoring>
+-      <virtualizationType>paravirtual</virtualizationType>
+-      <clientToken/>
+-      <tagSet/>
+-      <hypervisor>xen</hypervisor>
+-    </item>
+-    <item>
+-      <instanceId>i-2bc64242</instanceId>
+-      <imageId>ami-60a54009</imageId>
+-      <instanceState>
+-        <code>0</code>
+-        <name>pending</name>
+-      </instanceState>
+-      <privateDnsName></privateDnsName>
+-      <dnsName></dnsName>
+-      <keyName>example-key-name</keyName>
+-      <amiLaunchIndex>1</amiLaunchIndex>
+-      <instanceType>m1.small</instanceType>
+-      <launchTime>2007-08-07T11:51:50.000Z</launchTime>
+-      <placement>
+-         <availabilityZone>us-east-1b</availabilityZone>
+-      </placement>
+-      <monitoring>
+-        <state>enabled</state>
+-      </monitoring>
+-      <virtualizationType>paravirtual</virtualizationType>
+-      <clientToken/>
+-      <tagSet/>
+-      <hypervisor>xen</hypervisor>
+-    </item>
+-    <item>
+-      <instanceId>i-2be64332</instanceId>
+-      <imageId>ami-60a54009</imageId>
+-      <instanceState>
+-        <code>0</code>
+-        <name>pending</name>
+-      </instanceState>
+-      <privateDnsName></privateDnsName>
+-      <dnsName></dnsName>
+-      <keyName>example-key-name</keyName>
+-      <amiLaunchIndex>2</amiLaunchIndex>
+-      <instanceType>m1.small</instanceType>
+-      <launchTime>2007-08-07T11:51:50.000Z</launchTime>
+-      <placement>
+-         <availabilityZone>us-east-1b</availabilityZone>
+-      </placement>
+-      <monitoring>
+-        <state>enabled</state>
+-      </monitoring>
+-      <virtualizationType>paravirtual</virtualizationType>
+-      <clientToken/>
+-      <tagSet/>
+-      <hypervisor>xen</hypervisor>
+-    </item>
+-  </instancesSet>
+-</RunInstancesResponse>
+-`
 -
--	// FormParameterKind = indicator of Request parameter type "form"
--	FormParameterKind
--)
+-// http://goo.gl/GRZgCD
+-var RequestSpotInstancesExample = `
+-<RequestSpotInstancesResponse xmlns="http://ec2.amazonaws.com/doc/2014-02-01/">
+-  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-  <spotInstanceRequestSet>
+-    <item>
+-      <spotInstanceRequestId>sir-1a2b3c4d</spotInstanceRequestId>
+-      <spotPrice>0.5</spotPrice>
+-      <type>one-time</type>
+-      <state>open</state>
+-      <status>
+-        <code>pending-evaluation</code>
+-        <updateTime>2008-05-07T12:51:50.000Z</updateTime>
+-        <message>Your Spot request has been submitted for review, and is pending evaluation.</message>
+-      </status>
+-      <availabilityZoneGroup>MyAzGroup</availabilityZoneGroup>
+-      <launchSpecification>
+-        <imageId>ami-1a2b3c4d</imageId>
+-        <keyName>gsg-keypair</keyName>
+-        <groupSet>
+-          <item>
+-            <groupId>sg-1a2b3c4d</groupId>
+-            <groupName>websrv</groupName>
+-          </item>
+-        </groupSet>
+-        <instanceType>m1.small</instanceType>
+-        <blockDeviceMapping/>
+-        <monitoring>
+-          <enabled>false</enabled>
+-        </monitoring>
+-        <ebsOptimized>false</ebsOptimized>
+-      </launchSpecification>
+-      <createTime>YYYY-MM-DDTHH:MM:SS.000Z</createTime>
+-      <productDescription>Linux/UNIX</productDescription>
+-    </item>
+- </spotInstanceRequestSet>
+-</RequestSpotInstancesResponse>
+-`
 -
--// Parameter is for documententing the parameter used in a Http Request
--// ParameterData kinds are Path,Query and Body
--type Parameter struct {
--	data *ParameterData
--}
+-// http://goo.gl/KsKJJk
+-var DescribeSpotRequestsExample = `
+-<DescribeSpotInstanceRequestsResponse xmlns="http://ec2.amazonaws.com/doc/2014-02-01/">
+-  <requestId>b1719f2a-5334-4479-b2f1-26926EXAMPLE</requestId>
+-  <spotInstanceRequestSet>
+-    <item>
+-      <spotInstanceRequestId>sir-1a2b3c4d</spotInstanceRequestId>
+-      <spotPrice>0.5</spotPrice>
+-      <type>one-time</type>
+-      <state>active</state>
+-      <status>
+-        <code>fulfilled</code>
+-        <updateTime>2008-05-07T12:51:50.000Z</updateTime>
+-        <message>Your Spot request is fulfilled.</message>
+-      </status>
+-      <launchSpecification>
+-        <imageId>ami-1a2b3c4d</imageId>
+-        <keyName>gsg-keypair</keyName>
+-        <groupSet>
+-          <item>
+-            <groupId>sg-1a2b3c4d</groupId>
+-            <groupName>websrv</groupName>
+-          </item>
+-        </groupSet>
+-        <instanceType>m1.small</instanceType>
+-        <monitoring>
+-          <enabled>false</enabled>
+-        </monitoring>
+-        <ebsOptimized>false</ebsOptimized>
+-      </launchSpecification>
+-      <instanceId>i-1a2b3c4d</instanceId>
+-      <createTime>YYYY-MM-DDTHH:MM:SS.000Z</createTime>
+-      <productDescription>Linux/UNIX</productDescription>
+-      <launchedAvailabilityZone>us-east-1a</launchedAvailabilityZone>
+-    </item>
+-  </spotInstanceRequestSet>
+-</DescribeSpotInstanceRequestsResponse>
+-`
 -
--// ParameterData represents the state of a Parameter.
--// It is made public to make it accessible to e.g. the Swagger package.
--type ParameterData struct {
--	Name, Description, DataType string
--	Kind                        int
--	Required                    bool
--	AllowableValues             map[string]string
--	AllowMultiple               bool
--}
+-// http://goo.gl/DcfFgJ
+-var CancelSpotRequestsExample = `
+-<CancelSpotInstanceRequestsResponse xmlns="http://ec2.amazonaws.com/doc/2014-02-01/">
+-  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-  <spotInstanceRequestSet>
+-    <item>
+-      <spotInstanceRequestId>sir-1a2b3c4d</spotInstanceRequestId>
+-      <state>cancelled</state>
+-    </item>
+-  </spotInstanceRequestSet>
+-</CancelSpotInstanceRequestsResponse>
+-`
 -
--// Data returns the state of the Parameter
--func (p *Parameter) Data() ParameterData {
--	return *p.data
--}
+-// http://goo.gl/3BKHj
+-var TerminateInstancesExample = `
+-<TerminateInstancesResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
+-  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-  <instancesSet>
+-    <item>
+-      <instanceId>i-3ea74257</instanceId>
+-      <currentState>
+-        <code>32</code>
+-        <name>shutting-down</name>
+-      </currentState>
+-      <previousState>
+-        <code>16</code>
+-        <name>running</name>
+-      </previousState>
+-    </item>
+-  </instancesSet>
+-</TerminateInstancesResponse>
+-`
 -
--// Kind returns the parameter type indicator (see const for valid values)
--func (p *Parameter) Kind() int {
--	return p.data.Kind
--}
+-// http://goo.gl/mLbmw
+-var DescribeInstancesExample1 = `
+-<DescribeInstancesResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
+-  <requestId>98e3c9a4-848c-4d6d-8e8a-b1bdEXAMPLE</requestId>
+-  <reservationSet>
+-    <item>
+-      <reservationId>r-b27e30d9</reservationId>
+-      <ownerId>999988887777</ownerId>
+-      <groupSet>
+-        <item>
+-          <groupId>sg-67ad940e</groupId>
+-          <groupName>default</groupName>
+-        </item>
+-      </groupSet>
+-      <instancesSet>
+-        <item>
+-          <instanceId>i-c5cd56af</instanceId>
+-          <imageId>ami-1a2b3c4d</imageId>
+-          <instanceState>
+-            <code>16</code>
+-            <name>running</name>
+-          </instanceState>
+-          <privateDnsName>domU-12-31-39-10-56-34.compute-1.internal</privateDnsName>
+-          <dnsName>ec2-174-129-165-232.compute-1.amazonaws.com</dnsName>
+-          <reason/>
+-          <keyName>GSG_Keypair</keyName>
+-          <amiLaunchIndex>0</amiLaunchIndex>
+-          <productCodes/>
+-          <instanceType>m1.small</instanceType>
+-          <launchTime>2010-08-17T01:15:18.000Z</launchTime>
+-          <placement>
+-            <availabilityZone>us-east-1b</availabilityZone>
+-            <groupName/>
+-          </placement>
+-          <kernelId>aki-94c527fd</kernelId>
+-          <ramdiskId>ari-96c527ff</ramdiskId>
+-          <monitoring>
+-            <state>disabled</state>
+-          </monitoring>
+-          <privateIpAddress>10.198.85.190</privateIpAddress>
+-          <ipAddress>174.129.165.232</ipAddress>
+-          <architecture>i386</architecture>
+-          <rootDeviceType>ebs</rootDeviceType>
+-          <rootDeviceName>/dev/sda1</rootDeviceName>
+-          <blockDeviceMapping>
+-            <item>
+-              <deviceName>/dev/sda1</deviceName>
+-              <ebs>
+-                <volumeId>vol-a082c1c9</volumeId>
+-                <status>attached</status>
+-                <attachTime>2010-08-17T01:15:21.000Z</attachTime>
+-                <deleteOnTermination>false</deleteOnTermination>
+-              </ebs>
+-            </item>
+-          </blockDeviceMapping>
+-          <instanceLifecycle>spot</instanceLifecycle>
+-          <spotInstanceRequestId>sir-7a688402</spotInstanceRequestId>
+-          <virtualizationType>paravirtual</virtualizationType>
+-          <clientToken/>
+-          <tagSet/>
+-          <hypervisor>xen</hypervisor>
+-       </item>
+-      </instancesSet>
+-      <requesterId>854251627541</requesterId>
+-    </item>
+-    <item>
+-      <reservationId>r-b67e30dd</reservationId>
+-      <ownerId>999988887777</ownerId>
+-      <groupSet>
+-        <item>
+-          <groupId>sg-67ad940e</groupId>
+-          <groupName>default</groupName>
+-        </item>
+-      </groupSet>
+-      <instancesSet>
+-        <item>
+-          <instanceId>i-d9cd56b3</instanceId>
+-          <imageId>ami-1a2b3c4d</imageId>
+-          <instanceState>
+-            <code>16</code>
+-            <name>running</name>
+-          </instanceState>
+-          <privateDnsName>domU-12-31-39-10-54-E5.compute-1.internal</privateDnsName>
+-          <dnsName>ec2-184-73-58-78.compute-1.amazonaws.com</dnsName>
+-          <reason/>
+-          <keyName>GSG_Keypair</keyName>
+-          <amiLaunchIndex>0</amiLaunchIndex>
+-          <productCodes/>
+-          <instanceType>m1.large</instanceType>
+-          <launchTime>2010-08-17T01:15:19.000Z</launchTime>
+-          <placement>
+-            <availabilityZone>us-east-1b</availabilityZone>
+-            <groupName/>
+-          </placement>
+-          <kernelId>aki-94c527fd</kernelId>
+-          <ramdiskId>ari-96c527ff</ramdiskId>
+-          <monitoring>
+-            <state>disabled</state>
+-          </monitoring>
+-          <privateIpAddress>10.198.87.19</privateIpAddress>
+-          <ipAddress>184.73.58.78</ipAddress>
+-          <architecture>i386</architecture>
+-          <rootDeviceType>ebs</rootDeviceType>
+-          <rootDeviceName>/dev/sda1</rootDeviceName>
+-          <blockDeviceMapping>
+-            <item>
+-              <deviceName>/dev/sda1</deviceName>
+-              <ebs>
+-                <volumeId>vol-a282c1cb</volumeId>
+-                <status>attached</status>
+-                <attachTime>2010-08-17T01:15:23.000Z</attachTime>
+-                <deleteOnTermination>false</deleteOnTermination>
+-              </ebs>
+-            </item>
+-          </blockDeviceMapping>
+-          <instanceLifecycle>spot</instanceLifecycle>
+-          <spotInstanceRequestId>sir-55a3aa02</spotInstanceRequestId>
+-          <virtualizationType>paravirtual</virtualizationType>
+-          <clientToken/>
+-          <tagSet/>
+-          <hypervisor>xen</hypervisor>
+-       </item>
+-      </instancesSet>
+-      <requesterId>854251627541</requesterId>
+-    </item>
+-  </reservationSet>
+-</DescribeInstancesResponse>
+-`
 -
--func (p *Parameter) bePath() *Parameter {
--	p.data.Kind = PathParameterKind
--	return p
--}
--func (p *Parameter) beQuery() *Parameter {
--	p.data.Kind = QueryParameterKind
--	return p
--}
--func (p *Parameter) beBody() *Parameter {
--	p.data.Kind = BodyParameterKind
--	return p
--}
+-// http://goo.gl/mLbmw
+-var DescribeInstancesExample2 = `
+-<DescribeInstancesResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
+-  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-  <reservationSet>
+-    <item>
+-      <reservationId>r-bc7e30d7</reservationId>
+-      <ownerId>999988887777</ownerId>
+-      <groupSet>
+-        <item>
+-          <groupId>sg-67ad940e</groupId>
+-          <groupName>default</groupName>
+-        </item>
+-      </groupSet>
+-      <instancesSet>
+-        <item>
+-          <instanceId>i-c7cd56ad</instanceId>
+-          <imageId>ami-b232d0db</imageId>
+-          <instanceState>
+-            <code>16</code>
+-            <name>running</name>
+-          </instanceState>
+-          <privateDnsName>domU-12-31-39-01-76-06.compute-1.internal</privateDnsName>
+-          <dnsName>ec2-72-44-52-124.compute-1.amazonaws.com</dnsName>
+-          <keyName>GSG_Keypair</keyName>
+-          <amiLaunchIndex>0</amiLaunchIndex>
+-          <productCodes/>
+-          <instanceType>m1.small</instanceType>
+-          <launchTime>2010-08-17T01:15:16.000Z</launchTime>
+-          <placement>
+-              <availabilityZone>us-east-1b</availabilityZone>
+-          </placement>
+-          <kernelId>aki-94c527fd</kernelId>
+-          <ramdiskId>ari-96c527ff</ramdiskId>
+-          <monitoring>
+-              <state>disabled</state>
+-          </monitoring>
+-          <privateIpAddress>10.255.121.240</privateIpAddress>
+-          <ipAddress>72.44.52.124</ipAddress>
+-          <architecture>i386</architecture>
+-          <rootDeviceType>ebs</rootDeviceType>
+-          <rootDeviceName>/dev/sda1</rootDeviceName>
+-          <blockDeviceMapping>
+-              <item>
+-                 <deviceName>/dev/sda1</deviceName>
+-                 <ebs>
+-                    <volumeId>vol-a482c1cd</volumeId>
+-                    <status>attached</status>
+-                    <attachTime>2010-08-17T01:15:26.000Z</attachTime>
+-                    <deleteOnTermination>true</deleteOnTermination>
+-                </ebs>
+-             </item>
+-          </blockDeviceMapping>
+-          <virtualizationType>paravirtual</virtualizationType>
+-          <clientToken/>
+-          <tagSet>
+-              <item>
+-                    <key>webserver</key>
+-                    <value></value>
+-             </item>
+-              <item>
+-                    <key>stack</key>
+-                    <value>Production</value>
+-             </item>
+-          </tagSet>
+-          <hypervisor>xen</hypervisor>
+-        </item>
+-      </instancesSet>
+-    </item>
+-  </reservationSet>
+-</DescribeInstancesResponse>
+-`
 -
--func (p *Parameter) beHeader() *Parameter {
--	p.data.Kind = HeaderParameterKind
--	return p
--}
+-// http://goo.gl/cxU41
+-var CreateImageExample = `
+-<CreateImageResponse xmlns="http://ec2.amazonaws.com/doc/2013-02-01/">
+-   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-   <imageId>ami-4fa54026</imageId>
+-</CreateImageResponse>
+-`
 -
--func (p *Parameter) beForm() *Parameter {
--	p.data.Kind = FormParameterKind
--	return p
--}
+-// http://goo.gl/V0U25
+-var DescribeImagesExample = `
+-<DescribeImagesResponse xmlns="http://ec2.amazonaws.com/doc/2012-08-15/">
+-         <requestId>4a4a27a2-2e7c-475d-b35b-ca822EXAMPLE</requestId>
+-    <imagesSet>
+-        <item>
+-            <imageId>ami-a2469acf</imageId>
+-            <imageLocation>aws-marketplace/example-marketplace-amzn-ami.1</imageLocation>
+-            <imageState>available</imageState>
+-            <imageOwnerId>123456789999</imageOwnerId>
+-            <isPublic>true</isPublic>
+-            <productCodes>
+-                <item>
+-                    <productCode>a1b2c3d4e5f6g7h8i9j10k11</productCode>
+-                    <type>marketplace</type>
+-                </item>
+-            </productCodes>
+-            <architecture>i386</architecture>
+-            <imageType>machine</imageType>
+-            <kernelId>aki-805ea7e9</kernelId>
+-            <imageOwnerAlias>aws-marketplace</imageOwnerAlias>
+-            <name>example-marketplace-amzn-ami.1</name>
+-            <description>Amazon Linux AMI i386 EBS</description>
+-            <rootDeviceType>ebs</rootDeviceType>
+-            <rootDeviceName>/dev/sda1</rootDeviceName>
+-            <blockDeviceMapping>
+-                <item>
+-                    <deviceName>/dev/sda1</deviceName>
+-                    <ebs>
+-                        <snapshotId>snap-787e9403</snapshotId>
+-                        <volumeSize>8</volumeSize>
+-                        <deleteOnTermination>true</deleteOnTermination>
+-                    </ebs>
+-                </item>
+-            </blockDeviceMapping>
+-            <virtualizationType>paravirtual</virtualizationType>
+-            <hypervisor>xen</hypervisor>
+-        </item>
+-    </imagesSet>
+-</DescribeImagesResponse>
+-`
 -
--// Required sets the required field and return the receiver
--func (p *Parameter) Required(required bool) *Parameter {
--	p.data.Required = required
--	return p
--}
+-// http://goo.gl/bHO3z
+-var ImageAttributeExample = `
+-<DescribeImageAttributeResponse xmlns="http://ec2.amazonaws.com/doc/2013-07-15/">
+-   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-   <imageId>ami-61a54008</imageId>
+-   <launchPermission>
+-      <item>
+-         <group>all</group>
+-      </item>
+-      <item>
+-         <userId>495219933132</userId>
+-      </item>
+-   </launchPermission>
+-</DescribeImageAttributeResponse>
+-`
 -
--// AllowMultiple sets the allowMultiple field and return the receiver
--func (p *Parameter) AllowMultiple(multiple bool) *Parameter {
--	p.data.AllowMultiple = multiple
--	return p
--}
+-// http://goo.gl/ttcda
+-var CreateSnapshotExample = `
+-<CreateSnapshotResponse xmlns="http://ec2.amazonaws.com/doc/2012-10-01/">
+-  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-  <snapshotId>snap-78a54011</snapshotId>
+-  <volumeId>vol-4d826724</volumeId>
+-  <status>pending</status>
+-  <startTime>2008-05-07T12:51:50.000Z</startTime>
+-  <progress>60%</progress>
+-  <ownerId>111122223333</ownerId>
+-  <volumeSize>10</volumeSize>
+-  <description>Daily Backup</description>
+-</CreateSnapshotResponse>
+-`
 -
--// AllowableValues sets the allowableValues field and return the receiver
--func (p *Parameter) AllowableValues(values map[string]string) *Parameter {
--	p.data.AllowableValues = values
--	return p
--}
+-// http://goo.gl/vwU1y
+-var DeleteSnapshotExample = `
+-<DeleteSnapshotResponse xmlns="http://ec2.amazonaws.com/doc/2012-10-01/">
+-  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-  <return>true</return>
+-</DeleteSnapshotResponse>
+-`
 -
--// DataType sets the dataType field and return the receiver
--func (p *Parameter) DataType(typeName string) *Parameter {
--	p.data.DataType = typeName
--	return p
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/path_expression.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/path_expression.go
-deleted file mode 100644
-index 8749cb5..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/path_expression.go
-+++ /dev/null
-@@ -1,56 +0,0 @@
--package restful
+-// http://goo.gl/nkovs
+-var DescribeSnapshotsExample = `
+-<DescribeSnapshotsResponse xmlns="http://ec2.amazonaws.com/doc/2012-10-01/">
+-   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-   <snapshotSet>
+-      <item>
+-         <snapshotId>snap-1a2b3c4d</snapshotId>
+-         <volumeId>vol-8875daef</volumeId>
+-         <status>pending</status>
+-         <startTime>2010-07-29T04:12:01.000Z</startTime>
+-         <progress>30%</progress>
+-         <ownerId>111122223333</ownerId>
+-         <volumeSize>15</volumeSize>
+-         <description>Daily Backup</description>
+-         <tagSet>
+-            <item>
+-               <key>Purpose</key>
+-               <value>demo_db_14_backup</value>
+-            </item>
+-         </tagSet>
+-      </item>
+-   </snapshotSet>
+-</DescribeSnapshotsResponse>
+-`
 -
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
+-// http://goo.gl/YUjO4G
+-var ModifyImageAttributeExample = `
+-<ModifyImageAttributeResponse xmlns="http://ec2.amazonaws.com/doc/2013-06-15/">
+-  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-  <return>true</return>
+-</ModifyImageAttributeResponse>
+-`
 -
--import (
--	"bytes"
--	"regexp"
--	"strings"
--)
+-// http://goo.gl/hQwPCK
+-var CopyImageExample = `
+-<CopyImageResponse xmlns="http://ec2.amazonaws.com/doc/2013-06-15/">
+-   <requestId>60bc441d-fa2c-494d-b155-5d6a3EXAMPLE</requestId>
+-   <imageId>ami-4d3c2b1a</imageId>
+-</CopyImageResponse>
+-`
 -
--// PathExpression holds a compiled path expression (RegExp) needed to match against
--// Http request paths and to extract path parameter values.
--type pathExpression struct {
--	LiteralCount int // the number of literal characters (means those not resulting from template variable substitution)
--	VarCount     int // the number of named parameters (enclosed by {}) in the path
--	Matcher      *regexp.Regexp
--	Source       string // Path as defined by the RouteBuilder
--	tokens       []string
--}
+-var CreateKeyPairExample = `
+-<CreateKeyPairResponse xmlns="http://ec2.amazonaws.com/doc/2013-02-01/">
+-  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-  <keyName>foo</keyName>
+-  <keyFingerprint>
+-     00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00
+-  </keyFingerprint>
+-  <keyMaterial>---- BEGIN RSA PRIVATE KEY ----
+-MIICiTCCAfICCQD6m7oRw0uXOjANBgkqhkiG9w0BAQUFADCBiDELMAkGA1UEBhMC
+-VVMxCzAJBgNVBAgTAldBMRAwDgYDVQQHEwdTZWF0dGxlMQ8wDQYDVQQKEwZBbWF6
+-b24xFDASBgNVBAsTC0lBTSBDb25zb2xlMRIwEAYDVQQDEwlUZXN0Q2lsYWMxHzAd
+-BgkqhkiG9w0BCQEWEG5vb25lQGFtYXpvbi5jb20wHhcNMTEwNDI1MjA0NTIxWhcN
+-MTIwNDI0MjA0NTIxWjCBiDELMAkGA1UEBhMCVVMxCzAJBgNVBAgTAldBMRAwDgYD
+-VQQHEwdTZWF0dGxlMQ8wDQYDVQQKEwZBbWF6b24xFDASBgNVBAsTC0lBTSBDb25z
+-b2xlMRIwEAYDVQQDEwlUZXN0Q2lsYWMxHzAdBgkqhkiG9w0BCQEWEG5vb25lQGFt
+-YXpvbi5jb20wgZ8wDQYJKoZIhvcNAQEBBQADgY0AMIGJAoGBAMaK0dn+a4GmWIWJ
+-21uUSfwfEvySWtC2XADZ4nB+BLYgVIk60CpiwsZ3G93vUEIO3IyNoH/f0wYK8m9T
+-rDHudUZg3qX4waLG5M43q7Wgc/MbQITxOUSQv7c7ugFFDzQGBzZswY6786m86gpE
+-Ibb3OhjZnzcvQAaRHhdlQWIMm2nrAgMBAAEwDQYJKoZIhvcNAQEFBQADgYEAtCu4
+-nUhVVxYUntneD9+h8Mg9q6q+auNKyExzyLwaxlAoo7TJHidbtS4J5iNmZgXL0Fkb
+-FFBjvSfpJIlJ00zbhNYS5f6GuoEDmFJl0ZxBHjJnyp378OD8uTs7fLvjx79LjSTb
+-NYiytVbZPQUQ5Yaxu2jXnimvw3rrszlaEXAMPLE=
+------END RSA PRIVATE KEY-----
+-</keyMaterial>
+-</CreateKeyPairResponse>
+-`
 -
--// NewPathExpression creates a PathExpression from the input URL path.
--// Returns an error if the path is invalid.
--func newPathExpression(path string) (*pathExpression, error) {
--	expression, literalCount, varCount, tokens := templateToRegularExpression(path)
--	compiled, err := regexp.Compile(expression)
--	if err != nil {
--		return nil, err
--	}
--	return &pathExpression{literalCount, varCount, compiled, expression, tokens}, nil
--}
+-var DeleteKeyPairExample = `
+-<DeleteKeyPairResponse xmlns="http://ec2.amazonaws.com/doc/2013-02-01/">
+-  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-  <return>true</return>
+-</DeleteKeyPairResponse>
+-`
 -
--// http://jsr311.java.net/nonav/releases/1.1/spec/spec3.html#x3-370003.7.3
--func templateToRegularExpression(template string) (expression string, literalCount int, varCount int, tokens []string) {
--	var buffer bytes.Buffer
--	buffer.WriteString("^")
--	//tokens = strings.Split(template, "/")
--	tokens = tokenizePath(template)
--	for _, each := range tokens {
--		if each == "" {
--			continue
--		}
--		buffer.WriteString("/")
--		if strings.HasPrefix(each, "{") {
--			// ignore var spec
--			varCount += 1
--			buffer.WriteString("([^/]+?)")
--		} else {
--			literalCount += len(each)
--			encoded := each // TODO URI encode
--			buffer.WriteString(regexp.QuoteMeta(encoded))
--		}
--	}
--	return strings.TrimRight(buffer.String(), "/") + "(/.*)?$", literalCount, varCount, tokens
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/request.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/request.go
-deleted file mode 100644
-index 00a069f..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/request.go
-+++ /dev/null
-@@ -1,135 +0,0 @@
--package restful
+-// http://goo.gl/Eo7Yl
+-var CreateSecurityGroupExample = `
+-<CreateSecurityGroupResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
+-   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-   <return>true</return>
+-   <groupId>sg-67ad940e</groupId>
+-</CreateSecurityGroupResponse>
+-`
 -
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
+-// http://goo.gl/k12Uy
+-var DescribeSecurityGroupsExample = `
+-<DescribeSecurityGroupsResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
+-  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-  <securityGroupInfo>
+-    <item>
+-      <ownerId>999988887777</ownerId>
+-      <groupName>WebServers</groupName>
+-      <groupId>sg-67ad940e</groupId>
+-      <groupDescription>Web Servers</groupDescription>
+-      <ipPermissions>
+-        <item>
+-           <ipProtocol>tcp</ipProtocol>
+-           <fromPort>80</fromPort>
+-           <toPort>80</toPort>
+-           <groups/>
+-           <ipRanges>
+-             <item>
+-               <cidrIp>0.0.0.0/0</cidrIp>
+-             </item>
+-           </ipRanges>
+-        </item>
+-      </ipPermissions>
+-    </item>
+-    <item>
+-      <ownerId>999988887777</ownerId>
+-      <groupName>RangedPortsBySource</groupName>
+-      <groupId>sg-76abc467</groupId>
+-      <groupDescription>Group A</groupDescription>
+-      <ipPermissions>
+-        <item>
+-           <ipProtocol>tcp</ipProtocol>
+-           <fromPort>6000</fromPort>
+-           <toPort>7000</toPort>
+-           <groups/>
+-           <ipRanges/>
+-        </item>
+-      </ipPermissions>
+-    </item>
+-  </securityGroupInfo>
+-</DescribeSecurityGroupsResponse>
+-`
 -
--import (
--	"bytes"
--	"encoding/json"
--	"encoding/xml"
--	"io"
--	"io/ioutil"
--	"net/http"
--	"strings"
--)
+-// A dump which includes groups within ip permissions.
+-var DescribeSecurityGroupsDump = `
+-<?xml version="1.0" encoding="UTF-8"?>
+-<DescribeSecurityGroupsResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
+-    <requestId>87b92b57-cc6e-48b2-943f-f6f0e5c9f46c</requestId>
+-    <securityGroupInfo>
+-        <item>
+-            <ownerId>12345</ownerId>
+-            <groupName>default</groupName>
+-            <groupDescription>default group</groupDescription>
+-            <ipPermissions>
+-                <item>
+-                    <ipProtocol>icmp</ipProtocol>
+-                    <fromPort>-1</fromPort>
+-                    <toPort>-1</toPort>
+-                    <groups>
+-                        <item>
+-                            <userId>12345</userId>
+-                            <groupName>default</groupName>
+-                            <groupId>sg-67ad940e</groupId>
+-                        </item>
+-                    </groups>
+-                    <ipRanges/>
+-                </item>
+-                <item>
+-                    <ipProtocol>tcp</ipProtocol>
+-                    <fromPort>0</fromPort>
+-                    <toPort>65535</toPort>
+-                    <groups>
+-                        <item>
+-                            <userId>12345</userId>
+-                            <groupName>other</groupName>
+-                            <groupId>sg-76abc467</groupId>
+-                        </item>
+-                    </groups>
+-                    <ipRanges/>
+-                </item>
+-            </ipPermissions>
+-        </item>
+-    </securityGroupInfo>
+-</DescribeSecurityGroupsResponse>
+-`
 -
--var defaultRequestContentType string
+-// http://goo.gl/QJJDO
+-var DeleteSecurityGroupExample = `
+-<DeleteSecurityGroupResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
+-   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-   <return>true</return>
+-</DeleteSecurityGroupResponse>
+-`
 -
--var doCacheReadEntityBytes = true
+-// http://goo.gl/u2sDJ
+-var AuthorizeSecurityGroupIngressExample = `
+-<AuthorizeSecurityGroupIngressResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
+-  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-  <return>true</return>
+-</AuthorizeSecurityGroupIngressResponse>
+-`
 -
--// Request is a wrapper for a http Request that provides convenience methods
--type Request struct {
--	Request           *http.Request
--	bodyContent       *[]byte // to cache the request body for multiple reads of ReadEntity
--	pathParameters    map[string]string
--	attributes        map[string]interface{} // for storing request-scoped values
--	selectedRoutePath string                 // root path + route path that matched the request, e.g. /meetings/{id}/attendees
--}
+-// http://goo.gl/u2sDJ
+-var AuthorizeSecurityGroupEgressExample = `
+-<AuthorizeSecurityGroupEgressResponse xmlns="http://ec2.amazonaws.com/doc/2014-06-15/">
+-   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-   <return>true</return>
+-</AuthorizeSecurityGroupEgressResponse>
+-`
 -
--func NewRequest(httpRequest *http.Request) *Request {
--	return &Request{
--		Request:        httpRequest,
--		pathParameters: map[string]string{},
--		attributes:     map[string]interface{}{},
--	} // empty parameters, attributes
--}
+-// http://goo.gl/Mz7xr
+-var RevokeSecurityGroupIngressExample = `
+-<RevokeSecurityGroupIngressResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
+-  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-  <return>true</return>
+-</RevokeSecurityGroupIngressResponse>
+-`
 -
--// If ContentType is missing or */* is given then fall back to this type, otherwise
--// a "Unable to unmarshal content of type:" response is returned.
--// Valid values are restful.MIME_JSON and restful.MIME_XML
--// Example:
--// 	restful.DefaultRequestContentType(restful.MIME_JSON)
--func DefaultRequestContentType(mime string) {
--	defaultRequestContentType = mime
--}
+-// http://goo.gl/Vmkqc
+-var CreateTagsExample = `
+-<CreateTagsResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
+-   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-   <return>true</return>
+-</CreateTagsResponse>
+-`
 -
--// SetCacheReadEntity controls whether the response data ([]byte) is cached such that ReadEntity is repeatable.
--// Default is true (due to backwardcompatibility). For better performance, you should set it to false if you don't need it.
--func SetCacheReadEntity(doCache bool) {
--	doCacheReadEntityBytes = doCache
--}
+-// http://goo.gl/awKeF
+-var StartInstancesExample = `
+-<StartInstancesResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
+-  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-  <instancesSet>
+-    <item>
+-      <instanceId>i-10a64379</instanceId>
+-      <currentState>
+-          <code>0</code>
+-          <name>pending</name>
+-      </currentState>
+-      <previousState>
+-          <code>80</code>
+-          <name>stopped</name>
+-      </previousState>
+-    </item>
+-  </instancesSet>
+-</StartInstancesResponse>
+-`
 -
--// PathParameter accesses the Path parameter value by its name
--func (r *Request) PathParameter(name string) string {
--	return r.pathParameters[name]
--}
+-// http://goo.gl/436dJ
+-var StopInstancesExample = `
+-<StopInstancesResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
+-  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-  <instancesSet>
+-    <item>
+-      <instanceId>i-10a64379</instanceId>
+-      <currentState>
+-          <code>64</code>
+-          <name>stopping</name>
+-      </currentState>
+-      <previousState>
+-          <code>16</code>
+-          <name>running</name>
+-      </previousState>
+-    </item>
+-  </instancesSet>
+-</StopInstancesResponse>
+-`
 -
--// PathParameters accesses the Path parameter values
--func (r *Request) PathParameters() map[string]string {
--	return r.pathParameters
--}
+-// http://goo.gl/baoUf
+-var RebootInstancesExample = `
+-<RebootInstancesResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
+-  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-  <return>true</return>
+-</RebootInstancesResponse>
+-`
 -
--// QueryParameter returns the (first) Query parameter value by its name
--func (r *Request) QueryParameter(name string) string {
--	return r.Request.FormValue(name)
--}
+-// http://goo.gl/9rprDN
+-var AllocateAddressExample = `
+-<AllocateAddressResponse xmlns="http://ec2.amazonaws.com/doc/2013-10-15/">
+-   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-   <publicIp>198.51.100.1</publicIp>
+-   <domain>vpc</domain>
+-   <allocationId>eipalloc-5723d13e</allocationId>
+-</AllocateAddressResponse>
+-`
 -
--// BodyParameter parses the body of the request (once for typically a POST or a PUT) and returns the value of the given name or an error.
--func (r *Request) BodyParameter(name string) (string, error) {
--	err := r.Request.ParseForm()
--	if err != nil {
--		return "", err
--	}
--	return r.Request.PostFormValue(name), nil
--}
+-// http://goo.gl/3Q0oCc
+-var ReleaseAddressExample = `
+-<ReleaseAddressResponse xmlns="http://ec2.amazonaws.com/doc/2013-10-15/">
+-   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-   <return>true</return>
+-</ReleaseAddressResponse>
+-`
 -
--// HeaderParameter returns the HTTP Header value of a Header name or empty if missing
--func (r *Request) HeaderParameter(name string) string {
--	return r.Request.Header.Get(name)
--}
+-// http://goo.gl/uOSQE
+-var AssociateAddressExample = `
+-<AssociateAddressResponse xmlns="http://ec2.amazonaws.com/doc/2013-10-15/">
+-   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-   <return>true</return>
+-   <associationId>eipassoc-fc5ca095</associationId>
+-</AssociateAddressResponse>
+-`
 -
--// ReadEntity checks the Accept header and reads the content into the entityPointer
--// May be called multiple times in the request-response flow
--func (r *Request) ReadEntity(entityPointer interface{}) (err error) {
--	contentType := r.Request.Header.Get(HEADER_ContentType)
--	if doCacheReadEntityBytes {
--		return r.cachingReadEntity(contentType, entityPointer)
--	}
--	// unmarshall directly from request Body
--	return r.decodeEntity(r.Request.Body, contentType, entityPointer)
--}
+-// http://goo.gl/LrOa0
+-var DisassociateAddressExample = `
+-<DisassociateAddressResponse xmlns="http://ec2.amazonaws.com/doc/2013-10-15/">
+-   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-   <return>true</return>
+-</DisassociateAddressResponse>
+-`
 -
--func (r *Request) cachingReadEntity(contentType string, entityPointer interface{}) (err error) {
--	var buffer []byte
--	if r.bodyContent != nil {
--		buffer = *r.bodyContent
--	} else {
--		buffer, err = ioutil.ReadAll(r.Request.Body)
--		if err != nil {
--			return err
--		}
--		r.bodyContent = &buffer
--	}
--	return r.decodeEntity(bytes.NewReader(buffer), contentType, entityPointer)
--}
+-// http://goo.gl/icuXh5
+-var ModifyInstanceExample = `
+-<ModifyImageAttributeResponse xmlns="http://ec2.amazonaws.com/doc/2013-06-15/">
+-  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-  <return>true</return>
+-</ModifyImageAttributeResponse>
+-`
 -
--func (r *Request) decodeEntity(reader io.Reader, contentType string, entityPointer interface{}) (err error) {
--	if strings.Contains(contentType, MIME_XML) {
--		return xml.NewDecoder(reader).Decode(entityPointer)
--	}
--	if strings.Contains(contentType, MIME_JSON) || MIME_JSON == defaultRequestContentType {
--		decoder := json.NewDecoder(reader)
--		decoder.UseNumber()
--		return decoder.Decode(entityPointer)
--	}
--	if MIME_XML == defaultRequestContentType {
--		return xml.NewDecoder(reader).Decode(entityPointer)
--	}
--	return NewError(400, "Unable to unmarshal content of type:"+contentType)
--}
+-var CreateVpcExample = `
+-<CreateVpcResponse xmlns="http://ec2.amazonaws.com/doc/2014-06-15/">
+-   <requestId>7a62c49f-347e-4fc4-9331-6e8eEXAMPLE</requestId>
+-   <vpc>
+-      <vpcId>vpc-1a2b3c4d</vpcId>
+-      <state>pending</state>
+-      <cidrBlock>10.0.0.0/16</cidrBlock>
+-      <dhcpOptionsId>dopt-1a2b3c4d2</dhcpOptionsId>
+-      <instanceTenancy>default</instanceTenancy>
+-      <tagSet/>
+-   </vpc>
+-</CreateVpcResponse>
+-`
 -
--// SetAttribute adds or replaces the attribute with the given value.
--func (r *Request) SetAttribute(name string, value interface{}) {
--	r.attributes[name] = value
--}
+-var DescribeVpcsExample = `
+-<DescribeVpcsResponse xmlns="http://ec2.amazonaws.com/doc/2014-06-15/">
+-  <requestId>7a62c49f-347e-4fc4-9331-6e8eEXAMPLE</requestId>
+-  <vpcSet>
+-    <item>
+-      <vpcId>vpc-1a2b3c4d</vpcId>
+-      <state>available</state>
+-      <cidrBlock>10.0.0.0/23</cidrBlock>
+-      <dhcpOptionsId>dopt-7a8b9c2d</dhcpOptionsId>
+-      <instanceTenancy>default</instanceTenancy>
+-      <isDefault>false</isDefault>
+-      <tagSet/>
+-    </item>
+-  </vpcSet>
+-</DescribeVpcsResponse>
+-`
 -
--// Attribute returns the value associated to the given name. Returns nil if absent.
--func (r Request) Attribute(name string) interface{} {
--	return r.attributes[name]
--}
+-var CreateSubnetExample = `
+-<CreateSubnetResponse xmlns="http://ec2.amazonaws.com/doc/2014-06-15/">
+-  <requestId>7a62c49f-347e-4fc4-9331-6e8eEXAMPLE</requestId>
+-  <subnet>
+-    <subnetId>subnet-9d4a7b6c</subnetId>
+-    <state>pending</state>
+-    <vpcId>vpc-1a2b3c4d</vpcId>
+-    <cidrBlock>10.0.1.0/24</cidrBlock>
+-    <availableIpAddressCount>251</availableIpAddressCount>
+-    <availabilityZone>us-east-1a</availabilityZone>
+-    <tagSet/>
+-  </subnet>
+-</CreateSubnetResponse>
+-`
 -
--// SelectedRoutePath root path + route path that matched the request, e.g. /meetings/{id}/attendees
--func (r Request) SelectedRoutePath() string {
--	return r.selectedRoutePath
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/request_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/request_test.go
+-// http://goo.gl/r6ZCPm
+-var ResetImageAttributeExample = `
+-<ResetImageAttributeResponse xmlns="http://ec2.amazonaws.com/doc/2014-06-15/">
+-  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
+-  <return>true</return>
+-</ResetImageAttributeResponse>
+-`
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/sign.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/sign.go
 deleted file mode 100644
-index 6e7c55b..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/request_test.go
+index bffc3c7..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/sign.go
 +++ /dev/null
-@@ -1,204 +0,0 @@
--package restful
+@@ -1,45 +0,0 @@
+-package ec2
 -
 -import (
--	"encoding/json"
--	"net/http"
--	"net/url"
--	"strconv"
+-	"crypto/hmac"
+-	"crypto/sha256"
+-	"encoding/base64"
+-	"github.com/mitchellh/goamz/aws"
+-	"sort"
 -	"strings"
--	"testing"
 -)
 -
--func TestQueryParameter(t *testing.T) {
--	hreq := http.Request{Method: "GET"}
--	hreq.URL, _ = url.Parse("http://www.google.com/search?q=foo&q=bar")
--	rreq := Request{Request: &hreq}
--	if rreq.QueryParameter("q") != "foo" {
--		t.Errorf("q!=foo %#v", rreq)
--	}
--}
--
--type Anything map[string]interface{}
--
--type Number struct {
--	ValueFloat float64
--	ValueInt   int64
--}
+-// ----------------------------------------------------------------------------
+-// EC2 signing (http://goo.gl/fQmAN)
 -
--type Sample struct {
--	Value string
--}
+-var b64 = base64.StdEncoding
 -
--func TestReadEntityXml(t *testing.T) {
--	SetCacheReadEntity(true)
--	bodyReader := strings.NewReader("<Sample><Value>42</Value></Sample>")
--	httpRequest, _ := http.NewRequest("GET", "/test", bodyReader)
--	httpRequest.Header.Set("Content-Type", "application/xml")
--	request := &Request{Request: httpRequest}
--	sam := new(Sample)
--	request.ReadEntity(sam)
--	if sam.Value != "42" {
--		t.Fatal("read failed")
--	}
--	if request.bodyContent == nil {
--		t.Fatal("no expected cached bytes found")
+-func sign(auth aws.Auth, method, path string, params map[string]string, host string) {
+-	params["AWSAccessKeyId"] = auth.AccessKey
+-	params["SignatureVersion"] = "2"
+-	params["SignatureMethod"] = "HmacSHA256"
+-	if auth.Token != "" {
+-		params["SecurityToken"] = auth.Token
 -	}
--}
 -
--func TestReadEntityXmlNonCached(t *testing.T) {
--	SetCacheReadEntity(false)
--	bodyReader := strings.NewReader("<Sample><Value>42</Value></Sample>")
--	httpRequest, _ := http.NewRequest("GET", "/test", bodyReader)
--	httpRequest.Header.Set("Content-Type", "application/xml")
--	request := &Request{Request: httpRequest}
--	sam := new(Sample)
--	request.ReadEntity(sam)
--	if sam.Value != "42" {
--		t.Fatal("read failed")
+-	// AWS specifies that the parameters in a signed request must
+-	// be provided in the natural order of the keys. This is distinct
+-	// from the natural order of the encoded value of key=value.
+-	// Percent and equals affect the sorting order.
+-	var keys, sarray []string
+-	for k, _ := range params {
+-		keys = append(keys, k)
 -	}
--	if request.bodyContent != nil {
--		t.Fatal("unexpected cached bytes found")
+-	sort.Strings(keys)
+-	for _, k := range keys {
+-		sarray = append(sarray, aws.Encode(k)+"="+aws.Encode(params[k]))
 -	}
--}
+-	joined := strings.Join(sarray, "&")
+-	payload := method + "\n" + host + "\n" + path + "\n" + joined
+-	hash := hmac.New(sha256.New, []byte(auth.SecretKey))
+-	hash.Write([]byte(payload))
+-	signature := make([]byte, b64.EncodedLen(hash.Size()))
+-	b64.Encode(signature, hash.Sum(nil))
 -
--func TestReadEntityJson(t *testing.T) {
--	bodyReader := strings.NewReader(`{"Value" : "42"}`)
--	httpRequest, _ := http.NewRequest("GET", "/test", bodyReader)
--	httpRequest.Header.Set("Content-Type", "application/json")
--	request := &Request{Request: httpRequest}
--	sam := new(Sample)
--	request.ReadEntity(sam)
--	if sam.Value != "42" {
--		t.Fatal("read failed")
--	}
+-	params["Signature"] = string(signature)
 -}
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/sign_test.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/sign_test.go
+deleted file mode 100644
+index 86d203e..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/sign_test.go
++++ /dev/null
+@@ -1,68 +0,0 @@
+-package ec2_test
 -
--func TestReadEntityJsonCharset(t *testing.T) {
--	bodyReader := strings.NewReader(`{"Value" : "42"}`)
--	httpRequest, _ := http.NewRequest("GET", "/test", bodyReader)
--	httpRequest.Header.Set("Content-Type", "application/json; charset=UTF-8")
--	request := NewRequest(httpRequest)
--	sam := new(Sample)
--	request.ReadEntity(sam)
--	if sam.Value != "42" {
--		t.Fatal("read failed")
--	}
--}
+-import (
+-	"github.com/mitchellh/goamz/aws"
+-	"github.com/mitchellh/goamz/ec2"
+-	. "github.com/motain/gocheck"
+-)
 -
--func TestReadEntityJsonNumber(t *testing.T) {
--	SetCacheReadEntity(true)
--	bodyReader := strings.NewReader(`{"Value" : 4899710515899924123}`)
--	httpRequest, _ := http.NewRequest("GET", "/test", bodyReader)
--	httpRequest.Header.Set("Content-Type", "application/json")
--	request := &Request{Request: httpRequest}
--	any := make(Anything)
--	request.ReadEntity(&any)
--	number, ok := any["Value"].(json.Number)
--	if !ok {
--		t.Fatal("read failed")
--	}
--	vint, err := number.Int64()
--	if err != nil {
--		t.Fatal("convert failed")
--	}
--	if vint != 4899710515899924123 {
--		t.Fatal("read failed")
--	}
--	vfloat, err := number.Float64()
--	if err != nil {
--		t.Fatal("convert failed")
--	}
--	// match the default behaviour
--	vstring := strconv.FormatFloat(vfloat, 'e', 15, 64)
--	if vstring != "4.899710515899924e+18" {
--		t.Fatal("convert float64 failed")
--	}
--}
+-// EC2 ReST authentication docs: http://goo.gl/fQmAN
 -
--func TestReadEntityJsonNumberNonCached(t *testing.T) {
--	SetCacheReadEntity(false)
--	bodyReader := strings.NewReader(`{"Value" : 4899710515899924123}`)
--	httpRequest, _ := http.NewRequest("GET", "/test", bodyReader)
--	httpRequest.Header.Set("Content-Type", "application/json")
--	request := &Request{Request: httpRequest}
--	any := make(Anything)
--	request.ReadEntity(&any)
--	number, ok := any["Value"].(json.Number)
--	if !ok {
--		t.Fatal("read failed")
--	}
--	vint, err := number.Int64()
--	if err != nil {
--		t.Fatal("convert failed")
--	}
--	if vint != 4899710515899924123 {
--		t.Fatal("read failed")
--	}
--	vfloat, err := number.Float64()
--	if err != nil {
--		t.Fatal("convert failed")
--	}
--	// match the default behaviour
--	vstring := strconv.FormatFloat(vfloat, 'e', 15, 64)
--	if vstring != "4.899710515899924e+18" {
--		t.Fatal("convert float64 failed")
--	}
+-var testAuth = aws.Auth{"user", "secret", ""}
+-
+-func (s *S) TestBasicSignature(c *C) {
+-	params := map[string]string{}
+-	ec2.Sign(testAuth, "GET", "/path", params, "localhost")
+-	c.Assert(params["SignatureVersion"], Equals, "2")
+-	c.Assert(params["SignatureMethod"], Equals, "HmacSHA256")
+-	expected := "6lSe5QyXum0jMVc7cOUz32/52ZnL7N5RyKRk/09yiK4="
+-	c.Assert(params["Signature"], Equals, expected)
 -}
 -
--func TestReadEntityJsonLong(t *testing.T) {
--	bodyReader := strings.NewReader(`{"ValueFloat" : 4899710515899924123, "ValueInt": 4899710515899924123}`)
--	httpRequest, _ := http.NewRequest("GET", "/test", bodyReader)
--	httpRequest.Header.Set("Content-Type", "application/json")
--	request := &Request{Request: httpRequest}
--	number := new(Number)
--	request.ReadEntity(&number)
--	if number.ValueInt != 4899710515899924123 {
--		t.Fatal("read failed")
--	}
--	// match the default behaviour
--	vstring := strconv.FormatFloat(number.ValueFloat, 'e', 15, 64)
--	if vstring != "4.899710515899924e+18" {
--		t.Fatal("convert float64 failed")
+-func (s *S) TestParamSignature(c *C) {
+-	params := map[string]string{
+-		"param1": "value1",
+-		"param2": "value2",
+-		"param3": "value3",
 -	}
+-	ec2.Sign(testAuth, "GET", "/path", params, "localhost")
+-	expected := "XWOR4+0lmK8bD8CGDGZ4kfuSPbb2JibLJiCl/OPu1oU="
+-	c.Assert(params["Signature"], Equals, expected)
 -}
 -
--func TestBodyParameter(t *testing.T) {
--	bodyReader := strings.NewReader(`value1=42&value2=43`)
--	httpRequest, _ := http.NewRequest("POST", "/test?value1=44", bodyReader) // POST and PUT body parameters take precedence over URL query string
--	httpRequest.Header.Set("Content-Type", "application/x-www-form-urlencoded; charset=UTF-8")
--	request := NewRequest(httpRequest)
--	v1, err := request.BodyParameter("value1")
--	if err != nil {
--		t.Error(err)
--	}
--	v2, err := request.BodyParameter("value2")
--	if err != nil {
--		t.Error(err)
--	}
--	if v1 != "42" || v2 != "43" {
--		t.Fatal("read failed")
+-func (s *S) TestManyParams(c *C) {
+-	params := map[string]string{
+-		"param1":  "value10",
+-		"param2":  "value2",
+-		"param3":  "value3",
+-		"param4":  "value4",
+-		"param5":  "value5",
+-		"param6":  "value6",
+-		"param7":  "value7",
+-		"param8":  "value8",
+-		"param9":  "value9",
+-		"param10": "value1",
 -	}
+-	ec2.Sign(testAuth, "GET", "/path", params, "localhost")
+-	expected := "di0sjxIvezUgQ1SIL6i+C/H8lL+U0CQ9frLIak8jkVg="
+-	c.Assert(params["Signature"], Equals, expected)
 -}
 -
--func TestReadEntityUnkown(t *testing.T) {
--	bodyReader := strings.NewReader("?")
--	httpRequest, _ := http.NewRequest("GET", "/test", bodyReader)
--	httpRequest.Header.Set("Content-Type", "application/rubbish")
--	request := NewRequest(httpRequest)
--	sam := new(Sample)
--	err := request.ReadEntity(sam)
--	if err == nil {
--		t.Fatal("read should be in error")
--	}
+-func (s *S) TestEscaping(c *C) {
+-	params := map[string]string{"Nonce": "+ +"}
+-	ec2.Sign(testAuth, "GET", "/path", params, "localhost")
+-	c.Assert(params["Nonce"], Equals, "+ +")
+-	expected := "bqffDELReIqwjg/W0DnsnVUmfLK4wXVLO4/LuG+1VFA="
+-	c.Assert(params["Signature"], Equals, expected)
 -}
 -
--func TestSetAttribute(t *testing.T) {
--	bodyReader := strings.NewReader("?")
--	httpRequest, _ := http.NewRequest("GET", "/test", bodyReader)
--	request := NewRequest(httpRequest)
--	request.SetAttribute("go", "there")
--	there := request.Attribute("go")
--	if there != "there" {
--		t.Fatalf("missing request attribute:%v", there)
+-func (s *S) TestSignatureExample1(c *C) {
+-	params := map[string]string{
+-		"Timestamp": "2009-02-01T12:53:20+00:00",
+-		"Version":   "2007-11-07",
+-		"Action":    "ListDomains",
 -	}
+-	ec2.Sign(aws.Auth{"access", "secret", ""}, "GET", "/", params, "sdb.amazonaws.com")
+-	expected := "okj96/5ucWBSc1uR2zXVfm6mDHtgfNv657rRtt/aunQ="
+-	c.Assert(params["Signature"], Equals, expected)
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/response.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/response.go
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/LICENSE b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/LICENSE
 deleted file mode 100644
-index 0a3cbd5..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/response.go
+index f9c841a..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/LICENSE
 +++ /dev/null
-@@ -1,241 +0,0 @@
--package restful
+@@ -1,21 +0,0 @@
+-The MIT License (MIT)
 -
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
+-Copyright (c) 2013 Mitchell Hashimoto
 -
--import (
--	"encoding/json"
--	"encoding/xml"
--	"net/http"
--	"strings"
--)
+-Permission is hereby granted, free of charge, to any person obtaining a copy
+-of this software and associated documentation files (the "Software"), to deal
+-in the Software without restriction, including without limitation the rights
+-to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+-copies of the Software, and to permit persons to whom the Software is
+-furnished to do so, subject to the following conditions:
 -
--// DEPRECATED, use DefaultResponseContentType(mime)
--var DefaultResponseMimeType string
+-The above copyright notice and this permission notice shall be included in
+-all copies or substantial portions of the Software.
 -
--//PrettyPrintResponses controls the indentation feature of XML and JSON
--//serialization in the response methods WriteEntity, WriteAsJson, and
--//WriteAsXml.
--var PrettyPrintResponses = true
+-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+-IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+-FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+-AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+-LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+-OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+-THE SOFTWARE.
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/README.md b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/README.md
+deleted file mode 100644
+index 659d688..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/README.md
++++ /dev/null
+@@ -1,46 +0,0 @@
+-# mapstructure
 -
--// Response is a wrapper on the actual http ResponseWriter
--// It provides several convenience methods to prepare and write response content.
--type Response struct {
--	http.ResponseWriter
--	requestAccept string   // mime-type what the Http Request says it wants to receive
--	routeProduces []string // mime-types what the Route says it can produce
--	statusCode    int      // HTTP status code that has been written explicity (if zero then net/http has written 200)
--	contentLength int      // number of bytes written for the response body
--	prettyPrint   bool     // controls the indentation feature of XML and JSON serialization. It is initialized using var PrettyPrintResponses.
--}
+-mapstructure is a Go library for decoding generic map values to structures
+-and vice versa, while providing helpful error handling.
 -
--// Creates a new response based on a http ResponseWriter.
--func NewResponse(httpWriter http.ResponseWriter) *Response {
--	return &Response{httpWriter, "", []string{}, http.StatusOK, 0, PrettyPrintResponses} // empty content-types
--}
+-This library is most useful when decoding values from some data stream (JSON,
+-Gob, etc.) where you don't _quite_ know the structure of the underlying data
+-until you read a part of it. You can therefore read a `map[string]interface{}`
+-and use this library to decode it into the proper underlying native Go
+-structure.
 -
--// If Accept header matching fails, fall back to this type, otherwise
--// a "406: Not Acceptable" response is returned.
--// Valid values are restful.MIME_JSON and restful.MIME_XML
--// Example:
--// 	restful.DefaultResponseContentType(restful.MIME_JSON)
--func DefaultResponseContentType(mime string) {
--	DefaultResponseMimeType = mime
--}
+-## Installation
 -
--// InternalServerError writes the StatusInternalServerError header.
--// DEPRECATED, use WriteErrorString(http.StatusInternalServerError,reason)
--func (r Response) InternalServerError() Response {
--	r.WriteHeader(http.StatusInternalServerError)
--	return r
--}
+-Standard `go get`:
 -
--// PrettyPrint changes whether this response must produce pretty (line-by-line, indented) JSON or XML output.
--func (r *Response) PrettyPrint(bePretty bool) {
--	r.prettyPrint = bePretty
--}
+-```
+-$ go get github.com/mitchellh/mapstructure
+-```
 -
--// AddHeader is a shortcut for .Header().Add(header,value)
--func (r Response) AddHeader(header string, value string) Response {
--	r.Header().Add(header, value)
--	return r
--}
+-## Usage & Example
 -
--// SetRequestAccepts tells the response what Mime-type(s) the HTTP request said it wants to accept. Exposed for testing.
--func (r *Response) SetRequestAccepts(mime string) {
--	r.requestAccept = mime
--}
+-For usage and examples see the [Godoc](http://godoc.org/github.com/mitchellh/mapstructure).
 -
--// WriteEntity marshals the value using the representation denoted by the Accept Header (XML or JSON)
--// If no Accept header is specified (or */*) then return the Content-Type as specified by the first in the Route.Produces.
--// If an Accept header is specified then return the Content-Type as specified by the first in the Route.Produces that is matched with the Accept header.
--// If the value is nil then nothing is written. You may want to call WriteHeader(http.StatusNotFound) instead.
--// Current implementation ignores any q-parameters in the Accept Header.
--func (r *Response) WriteEntity(value interface{}) error {
--	if value == nil { // do not write a nil representation
--		return nil
--	}
--	for _, qualifiedMime := range strings.Split(r.requestAccept, ",") {
--		mime := strings.Trim(strings.Split(qualifiedMime, ";")[0], " ")
--		if 0 == len(mime) || mime == "*/*" {
--			for _, each := range r.routeProduces {
--				if MIME_JSON == each {
--					return r.WriteAsJson(value)
--				}
--				if MIME_XML == each {
--					return r.WriteAsXml(value)
--				}
--			}
--		} else { // mime is not blank; see if we have a match in Produces
--			for _, each := range r.routeProduces {
--				if mime == each {
--					if MIME_JSON == each {
--						return r.WriteAsJson(value)
--					}
--					if MIME_XML == each {
--						return r.WriteAsXml(value)
--					}
--				}
--			}
--		}
--	}
--	if DefaultResponseMimeType == MIME_JSON {
--		return r.WriteAsJson(value)
--	} else if DefaultResponseMimeType == MIME_XML {
--		return r.WriteAsXml(value)
--	} else {
--		if trace {
--			traceLogger.Printf("mismatch in mime-types and no defaults; (http)Accept=%v,(route)Produces=%v\n", r.requestAccept, r.routeProduces)
--		}
--		r.WriteHeader(http.StatusNotAcceptable) // for recording only
--		r.ResponseWriter.WriteHeader(http.StatusNotAcceptable)
--		if _, err := r.Write([]byte("406: Not Acceptable")); err != nil {
--			return err
--		}
--	}
--	return nil
--}
+-The `Decode` function has examples associated with it there.
 -
--// WriteAsXml is a convenience method for writing a value in xml (requires Xml tags on the value)
--func (r *Response) WriteAsXml(value interface{}) error {
--	var output []byte
--	var err error
+-## But Why?!
 -
--	if value == nil { // do not write a nil representation
--		return nil
--	}
--	if r.prettyPrint {
--		output, err = xml.MarshalIndent(value, " ", " ")
--	} else {
--		output, err = xml.Marshal(value)
--	}
+-Go offers fantastic standard libraries for decoding formats such as JSON.
+-The standard method is to have a struct pre-created, and populate that struct
+-from the bytes of the encoded format. This is great, but the problem is if
+-you have configuration or an encoding that changes slightly depending on
+-specific fields. For example, consider this JSON:
 -
--	if err != nil {
--		return r.WriteError(http.StatusInternalServerError, err)
--	}
--	r.Header().Set(HEADER_ContentType, MIME_XML)
--	if r.statusCode > 0 { // a WriteHeader was intercepted
--		r.ResponseWriter.WriteHeader(r.statusCode)
--	}
--	_, err = r.Write([]byte(xml.Header))
--	if err != nil {
--		return err
--	}
--	if _, err = r.Write(output); err != nil {
--		return err
--	}
--	return nil
+-```json
+-{
+-  "type": "person",
+-  "name": "Mitchell"
 -}
+-```
 -
--// WriteAsJson is a convenience method for writing a value in json
--func (r *Response) WriteAsJson(value interface{}) error {
--	var output []byte
--	var err error
--
--	if value == nil { // do not write a nil representation
--		return nil
--	}
--	if r.prettyPrint {
--		output, err = json.MarshalIndent(value, " ", " ")
--	} else {
--		output, err = json.Marshal(value)
--	}
+-Perhaps we can't populate a specific structure without first reading
+-the "type" field from the JSON. We could always do two passes over the
+-decoding of the JSON (reading the "type" first, and the rest later).
+-However, it is much simpler to just decode this into a `map[string]interface{}`
+-structure, read the "type" key, then use something like this library
+-to decode it into the proper structure.
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/decode_hooks.go b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/decode_hooks.go
+deleted file mode 100644
+index 087a392..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/decode_hooks.go
++++ /dev/null
+@@ -1,84 +0,0 @@
+-package mapstructure
 -
--	if err != nil {
--		return r.WriteErrorString(http.StatusInternalServerError, err.Error())
--	}
--	r.Header().Set(HEADER_ContentType, MIME_JSON)
--	if r.statusCode > 0 { // a WriteHeader was intercepted
--		r.ResponseWriter.WriteHeader(r.statusCode)
--	}
--	if _, err = r.Write(output); err != nil {
--		return err
--	}
--	return nil
--}
+-import (
+-	"reflect"
+-	"strconv"
+-	"strings"
+-)
 -
--// WriteError write the http status and the error string on the response.
--func (r *Response) WriteError(httpStatus int, err error) error {
--	return r.WriteErrorString(httpStatus, err.Error())
--}
+-// ComposeDecodeHookFunc creates a single DecodeHookFunc that
+-// automatically composes multiple DecodeHookFuncs.
+-//
+-// The composed funcs are called in order, with the result of the
+-// previous transformation.
+-func ComposeDecodeHookFunc(fs ...DecodeHookFunc) DecodeHookFunc {
+-	return func(
+-		f reflect.Kind,
+-		t reflect.Kind,
+-		data interface{}) (interface{}, error) {
+-		var err error
+-		for _, f1 := range fs {
+-			data, err = f1(f, t, data)
+-			if err != nil {
+-				return nil, err
+-			}
 -
--// WriteServiceError is a convenience method for a responding with a ServiceError and a status
--func (r *Response) WriteServiceError(httpStatus int, err ServiceError) error {
--	r.WriteHeader(httpStatus) // for recording only
--	return r.WriteEntity(err)
--}
+-			// Modify the from kind to be correct with the new data
+-			f = getKind(reflect.ValueOf(data))
+-		}
 -
--// WriteErrorString is a convenience method for an error status with the actual error
--func (r *Response) WriteErrorString(status int, errorReason string) error {
--	r.statusCode = status // for recording only
--	r.ResponseWriter.WriteHeader(status)
--	if _, err := r.Write([]byte(errorReason)); err != nil {
--		return err
+-		return data, nil
 -	}
--	return nil
 -}
 -
--// WriteHeader is overridden to remember the Status Code that has been written.
--// Note that using this method, the status value is only written when
--// - calling WriteEntity,
--// - or directly calling WriteAsXml or WriteAsJson,
--// - or if the status is one for which no response is allowed (i.e.,
--//   204 (http.StatusNoContent) or 304 (http.StatusNotModified))
--func (r *Response) WriteHeader(httpStatus int) {
--	r.statusCode = httpStatus
--	// if 204 then WriteEntity will not be called so we need to pass this code
--	if http.StatusNoContent == httpStatus ||
--		http.StatusNotModified == httpStatus {
--		r.ResponseWriter.WriteHeader(httpStatus)
--	}
--}
+-// StringToSliceHookFunc returns a DecodeHookFunc that converts
+-// string to []string by splitting on the given sep.
+-func StringToSliceHookFunc(sep string) DecodeHookFunc {
+-	return func(
+-		f reflect.Kind,
+-		t reflect.Kind,
+-		data interface{}) (interface{}, error) {
+-		if f != reflect.String || t != reflect.Slice {
+-			return data, nil
+-		}
 -
--// StatusCode returns the code that has been written using WriteHeader.
--func (r Response) StatusCode() int {
--	if 0 == r.statusCode {
--		// no status code has been written yet; assume OK
--		return http.StatusOK
--	}
--	return r.statusCode
--}
+-		raw := data.(string)
+-		if raw == "" {
+-			return []string{}, nil
+-		}
 -
--// Write writes the data to the connection as part of an HTTP reply.
--// Write is part of http.ResponseWriter interface.
--func (r *Response) Write(bytes []byte) (int, error) {
--	written, err := r.ResponseWriter.Write(bytes)
--	r.contentLength += written
--	return written, err
+-		return strings.Split(raw, sep), nil
+-	}
 -}
 -
--// ContentLength returns the number of bytes written for the response content.
--// Note that this value is only correct if all data is written through the Response using its Write* methods.
--// Data written directly using the underlying http.ResponseWriter is not accounted for.
--func (r Response) ContentLength() int {
--	return r.contentLength
--}
+-func WeaklyTypedHook(
+-	f reflect.Kind,
+-	t reflect.Kind,
+-	data interface{}) (interface{}, error) {
+-	dataVal := reflect.ValueOf(data)
+-	switch t {
+-	case reflect.String:
+-		switch f {
+-		case reflect.Bool:
+-			if dataVal.Bool() {
+-				return "1", nil
+-			} else {
+-				return "0", nil
+-			}
+-		case reflect.Float32:
+-			return strconv.FormatFloat(dataVal.Float(), 'f', -1, 64), nil
+-		case reflect.Int:
+-			return strconv.FormatInt(dataVal.Int(), 10), nil
+-		case reflect.Slice:
+-			dataType := dataVal.Type()
+-			elemKind := dataType.Elem().Kind()
+-			if elemKind == reflect.Uint8 {
+-				return string(dataVal.Interface().([]uint8)), nil
+-			}
+-		case reflect.Uint:
+-			return strconv.FormatUint(dataVal.Uint(), 10), nil
+-		}
+-	}
 -
--// CloseNotify is part of http.CloseNotifier interface
--func (r Response) CloseNotify() <-chan bool {
--	return r.ResponseWriter.(http.CloseNotifier).CloseNotify()
+-	return data, nil
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/response_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/response_test.go
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/decode_hooks_test.go b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/decode_hooks_test.go
 deleted file mode 100644
-index ee9a74f..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/response_test.go
+index b417dee..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/decode_hooks_test.go
 +++ /dev/null
-@@ -1,157 +0,0 @@
--package restful
+@@ -1,191 +0,0 @@
+-package mapstructure
 -
 -import (
 -	"errors"
--	"net/http"
--	"net/http/httptest"
+-	"reflect"
 -	"testing"
 -)
 -
--func TestWriteHeader(t *testing.T) {
--	httpWriter := httptest.NewRecorder()
--	resp := Response{httpWriter, "*/*", []string{"*/*"}, 0, 0, true}
--	resp.WriteHeader(123)
--	if resp.StatusCode() != 123 {
--		t.Errorf("Unexpected status code:%d", resp.StatusCode())
--	}
--}
--
--func TestNoWriteHeader(t *testing.T) {
--	httpWriter := httptest.NewRecorder()
--	resp := Response{httpWriter, "*/*", []string{"*/*"}, 0, 0, true}
--	if resp.StatusCode() != http.StatusOK {
--		t.Errorf("Unexpected status code:%d", resp.StatusCode())
--	}
--}
--
--type food struct {
--	Kind string
--}
--
--// go test -v -test.run TestMeasureContentLengthXml ...restful
--func TestMeasureContentLengthXml(t *testing.T) {
--	httpWriter := httptest.NewRecorder()
--	resp := Response{httpWriter, "*/*", []string{"*/*"}, 0, 0, true}
--	resp.WriteAsXml(food{"apple"})
--	if resp.ContentLength() != 76 {
--		t.Errorf("Incorrect measured length:%d", resp.ContentLength())
--	}
--}
--
--// go test -v -test.run TestMeasureContentLengthJson ...restful
--func TestMeasureContentLengthJson(t *testing.T) {
--	httpWriter := httptest.NewRecorder()
--	resp := Response{httpWriter, "*/*", []string{"*/*"}, 0, 0, true}
--	resp.WriteAsJson(food{"apple"})
--	if resp.ContentLength() != 22 {
--		t.Errorf("Incorrect measured length:%d", resp.ContentLength())
--	}
--}
--
--// go test -v -test.run TestMeasureContentLengthJsonNotPretty ...restful
--func TestMeasureContentLengthJsonNotPretty(t *testing.T) {
--	httpWriter := httptest.NewRecorder()
--	resp := Response{httpWriter, "*/*", []string{"*/*"}, 0, 0, false}
--	resp.WriteAsJson(food{"apple"})
--	if resp.ContentLength() != 16 {
--		t.Errorf("Incorrect measured length:%d", resp.ContentLength())
--	}
--}
--
--// go test -v -test.run TestMeasureContentLengthWriteErrorString ...restful
--func TestMeasureContentLengthWriteErrorString(t *testing.T) {
--	httpWriter := httptest.NewRecorder()
--	resp := Response{httpWriter, "*/*", []string{"*/*"}, 0, 0, true}
--	resp.WriteErrorString(404, "Invalid")
--	if resp.ContentLength() != len("Invalid") {
--		t.Errorf("Incorrect measured length:%d", resp.ContentLength())
--	}
--}
--
--// go test -v -test.run TestStatusCreatedAndContentTypeJson_Issue54 ...restful
--func TestStatusCreatedAndContentTypeJson_Issue54(t *testing.T) {
--	httpWriter := httptest.NewRecorder()
--	resp := Response{httpWriter, "application/json", []string{"application/json"}, 0, 0, true}
--	resp.WriteHeader(201)
--	resp.WriteAsJson(food{"Juicy"})
--	if httpWriter.HeaderMap.Get("Content-Type") != "application/json" {
--		t.Errorf("Expected content type json but got:%d", httpWriter.HeaderMap.Get("Content-Type"))
--	}
--	if httpWriter.Code != 201 {
--		t.Errorf("Expected status 201 but got:%d", httpWriter.Code)
+-func TestComposeDecodeHookFunc(t *testing.T) {
+-	f1 := func(
+-		f reflect.Kind,
+-		t reflect.Kind,
+-		data interface{}) (interface{}, error) {
+-		return data.(string) + "foo", nil
 -	}
--}
 -
--type errorOnWriteRecorder struct {
--	*httptest.ResponseRecorder
--}
+-	f2 := func(
+-		f reflect.Kind,
+-		t reflect.Kind,
+-		data interface{}) (interface{}, error) {
+-		return data.(string) + "bar", nil
+-	}
 -
--func (e errorOnWriteRecorder) Write(bytes []byte) (int, error) {
--	return 0, errors.New("fail")
--}
+-	f := ComposeDecodeHookFunc(f1, f2)
 -
--// go test -v -test.run TestLastWriteErrorCaught ...restful
--func TestLastWriteErrorCaught(t *testing.T) {
--	httpWriter := errorOnWriteRecorder{httptest.NewRecorder()}
--	resp := Response{httpWriter, "application/json", []string{"application/json"}, 0, 0, true}
--	err := resp.WriteAsJson(food{"Juicy"})
--	if err.Error() != "fail" {
--		t.Errorf("Unexpected error message:%v", err)
+-	result, err := f(reflect.String, reflect.Slice, "")
+-	if err != nil {
+-		t.Fatalf("bad: %s", err)
 -	}
--}
--
--// go test -v -test.run TestAcceptStarStar_Issue83 ...restful
--func TestAcceptStarStar_Issue83(t *testing.T) {
--	httpWriter := httptest.NewRecorder()
--	//								Accept									Produces
--	resp := Response{httpWriter, "application/bogus,*/*;q=0.8", []string{"application/json"}, 0, 0, true}
--	resp.WriteEntity(food{"Juicy"})
--	ct := httpWriter.Header().Get("Content-Type")
--	if "application/json" != ct {
--		t.Errorf("Unexpected content type:%s", ct)
+-	if result.(string) != "foobar" {
+-		t.Fatalf("bad: %#v", result)
 -	}
 -}
 -
--// go test -v -test.run TestAcceptSkipStarStar_Issue83 ...restful
--func TestAcceptSkipStarStar_Issue83(t *testing.T) {
--	httpWriter := httptest.NewRecorder()
--	//								Accept									Produces
--	resp := Response{httpWriter, " application/xml ,*/* ; q=0.8", []string{"application/json", "application/xml"}, 0, 0, true}
--	resp.WriteEntity(food{"Juicy"})
--	ct := httpWriter.Header().Get("Content-Type")
--	if "application/xml" != ct {
--		t.Errorf("Unexpected content type:%s", ct)
+-func TestComposeDecodeHookFunc_err(t *testing.T) {
+-	f1 := func(reflect.Kind, reflect.Kind, interface{}) (interface{}, error) {
+-		return nil, errors.New("foo")
 -	}
--}
 -
--// go test -v -test.run TestAcceptXmlBeforeStarStar_Issue83 ...restful
--func TestAcceptXmlBeforeStarStar_Issue83(t *testing.T) {
--	httpWriter := httptest.NewRecorder()
--	//								Accept									Produces
--	resp := Response{httpWriter, "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8", []string{"application/json"}, 0, 0, true}
--	resp.WriteEntity(food{"Juicy"})
--	ct := httpWriter.Header().Get("Content-Type")
--	if "application/json" != ct {
--		t.Errorf("Unexpected content type:%s", ct)
+-	f2 := func(reflect.Kind, reflect.Kind, interface{}) (interface{}, error) {
+-		panic("NOPE")
 -	}
--}
 -
--// go test -v -test.run TestWriteHeaderNoContent_Issue124 ...restful
--func TestWriteHeaderNoContent_Issue124(t *testing.T) {
--	httpWriter := httptest.NewRecorder()
--	resp := Response{httpWriter, "text/plain", []string{"text/plain"}, 0, 0, true}
--	resp.WriteHeader(http.StatusNoContent)
--	if httpWriter.Code != http.StatusNoContent {
--		t.Errorf("got %d want %d", httpWriter.Code, http.StatusNoContent)
--	}
--}
+-	f := ComposeDecodeHookFunc(f1, f2)
 -
--// go test -v -test.run TestStatusCreatedAndContentTypeJson_Issue163 ...restful
--func TestStatusCreatedAndContentTypeJson_Issue163(t *testing.T) {
--	httpWriter := httptest.NewRecorder()
--	resp := Response{httpWriter, "application/json", []string{"application/json"}, 0, 0, true}
--	resp.WriteHeader(http.StatusNotModified)
--	if httpWriter.Code != http.StatusNotModified {
--		t.Errorf("Got %d want %d", httpWriter.Code, http.StatusNotModified)
+-	_, err := f(reflect.String, reflect.Slice, 42)
+-	if err.Error() != "foo" {
+-		t.Fatalf("bad: %s", err)
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/route.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/route.go
-deleted file mode 100644
-index 59d6e23..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/route.go
-+++ /dev/null
-@@ -1,166 +0,0 @@
--package restful
--
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
--
--import (
--	"bytes"
--	"net/http"
--	"strings"
--)
 -
--// RouteFunction declares the signature of a function that can be bound to a Route.
--type RouteFunction func(*Request, *Response)
+-func TestComposeDecodeHookFunc_kinds(t *testing.T) {
+-	var f2From reflect.Kind
 -
--// Route binds a HTTP Method,Path,Consumes combination to a RouteFunction.
--type Route struct {
--	Method   string
--	Produces []string
--	Consumes []string
--	Path     string // webservice root path + described path
--	Function RouteFunction
--	Filters  []FilterFunction
+-	f1 := func(
+-		f reflect.Kind,
+-		t reflect.Kind,
+-		data interface{}) (interface{}, error) {
+-		return int(42), nil
+-	}
 -
--	// cached values for dispatching
--	relativePath string
--	pathParts    []string
--	pathExpr     *pathExpression // cached compilation of relativePath as RegExp
+-	f2 := func(
+-		f reflect.Kind,
+-		t reflect.Kind,
+-		data interface{}) (interface{}, error) {
+-		f2From = f
+-		return data, nil
+-	}
 -
--	// documentation
--	Doc                     string
--	Operation               string
--	ParameterDocs           []*Parameter
--	ResponseErrors          map[int]ResponseError
--	ReadSample, WriteSample interface{} // structs that model an example request or response payload
--}
+-	f := ComposeDecodeHookFunc(f1, f2)
 -
--// Initialize for Route
--func (r *Route) postBuild() {
--	r.pathParts = tokenizePath(r.Path)
+-	_, err := f(reflect.String, reflect.Slice, "")
+-	if err != nil {
+-		t.Fatalf("bad: %s", err)
+-	}
+-	if f2From != reflect.Int {
+-		t.Fatalf("bad: %#v", f2From)
+-	}
 -}
 -
--// Create Request and Response from their http versions
--func (r *Route) wrapRequestResponse(httpWriter http.ResponseWriter, httpRequest *http.Request) (*Request, *Response) {
--	params := r.extractParameters(httpRequest.URL.Path)
--	wrappedRequest := NewRequest(httpRequest)
--	wrappedRequest.pathParameters = params
--	wrappedRequest.selectedRoutePath = r.Path
--	wrappedResponse := NewResponse(httpWriter)
--	wrappedResponse.requestAccept = httpRequest.Header.Get(HEADER_Accept)
--	wrappedResponse.routeProduces = r.Produces
--	return wrappedRequest, wrappedResponse
--}
+-func TestStringToSliceHookFunc(t *testing.T) {
+-	f := StringToSliceHookFunc(",")
 -
--// dispatchWithFilters call the function after passing through its own filters
--func (r *Route) dispatchWithFilters(wrappedRequest *Request, wrappedResponse *Response) {
--	if len(r.Filters) > 0 {
--		chain := FilterChain{Filters: r.Filters, Target: r.Function}
--		chain.ProcessFilter(wrappedRequest, wrappedResponse)
--	} else {
--		// unfiltered
--		r.Function(wrappedRequest, wrappedResponse)
+-	cases := []struct {
+-		f, t   reflect.Kind
+-		data   interface{}
+-		result interface{}
+-		err    bool
+-	}{
+-		{reflect.Slice, reflect.Slice, 42, 42, false},
+-		{reflect.String, reflect.String, 42, 42, false},
+-		{
+-			reflect.String,
+-			reflect.Slice,
+-			"foo,bar,baz",
+-			[]string{"foo", "bar", "baz"},
+-			false,
+-		},
+-		{
+-			reflect.String,
+-			reflect.Slice,
+-			"",
+-			[]string{},
+-			false,
+-		},
 -	}
--}
 -
--// Return whether the mimeType matches to what this Route can produce.
--func (r Route) matchesAccept(mimeTypesWithQuality string) bool {
--	parts := strings.Split(mimeTypesWithQuality, ",")
--	for _, each := range parts {
--		var withoutQuality string
--		if strings.Contains(each, ";") {
--			withoutQuality = strings.Split(each, ";")[0]
--		} else {
--			withoutQuality = each
--		}
--		// trim before compare
--		withoutQuality = strings.Trim(withoutQuality, " ")
--		if withoutQuality == "*/*" {
--			return true
+-	for i, tc := range cases {
+-		actual, err := f(tc.f, tc.t, tc.data)
+-		if tc.err != (err != nil) {
+-			t.Fatalf("case %d: expected err %#v", i, tc.err)
 -		}
--		for _, other := range r.Produces {
--			if other == withoutQuality {
--				return true
--			}
+-		if !reflect.DeepEqual(actual, tc.result) {
+-			t.Fatalf(
+-				"case %d: expected %#v, got %#v",
+-				i, tc.result, actual)
 -		}
 -	}
--	return false
 -}
 -
--// Return whether the mimeType matches to what this Route can consume.
--func (r Route) matchesContentType(mimeTypes string) bool {
--	parts := strings.Split(mimeTypes, ",")
--	for _, each := range parts {
--		var contentType string
--		if strings.Contains(each, ";") {
--			contentType = strings.Split(each, ";")[0]
--		} else {
--			contentType = each
--		}
--		// trim before compare
--		contentType = strings.Trim(contentType, " ")
--		for _, other := range r.Consumes {
--			if other == "*/*" || other == contentType {
--				return true
--			}
--		}
+-func TestWeaklyTypedHook(t *testing.T) {
+-	var f DecodeHookFunc = WeaklyTypedHook
+-
+-	cases := []struct {
+-		f, t   reflect.Kind
+-		data   interface{}
+-		result interface{}
+-		err    bool
+-	}{
+-		// TO STRING
+-		{
+-			reflect.Bool,
+-			reflect.String,
+-			false,
+-			"0",
+-			false,
+-		},
+-
+-		{
+-			reflect.Bool,
+-			reflect.String,
+-			true,
+-			"1",
+-			false,
+-		},
+-
+-		{
+-			reflect.Float32,
+-			reflect.String,
+-			float32(7),
+-			"7",
+-			false,
+-		},
+-
+-		{
+-			reflect.Int,
+-			reflect.String,
+-			int(7),
+-			"7",
+-			false,
+-		},
+-
+-		{
+-			reflect.Slice,
+-			reflect.String,
+-			[]uint8("foo"),
+-			"foo",
+-			false,
+-		},
+-
+-		{
+-			reflect.Uint,
+-			reflect.String,
+-			uint(7),
+-			"7",
+-			false,
+-		},
 -	}
--	return false
--}
 -
--// Extract the parameters from the request url path
--func (r Route) extractParameters(urlPath string) map[string]string {
--	urlParts := tokenizePath(urlPath)
--	pathParameters := map[string]string{}
--	for i, key := range r.pathParts {
--		var value string
--		if i >= len(urlParts) {
--			value = ""
--		} else {
--			value = urlParts[i]
+-	for i, tc := range cases {
+-		actual, err := f(tc.f, tc.t, tc.data)
+-		if tc.err != (err != nil) {
+-			t.Fatalf("case %d: expected err %#v", i, tc.err)
 -		}
--		if strings.HasPrefix(key, "{") { // path-parameter
--			if colon := strings.Index(key, ":"); colon != -1 {
--				// extract by regex
--				regPart := key[colon+1 : len(key)-1]
--				keyPart := key[1:colon]
--				if regPart == "*" {
--					pathParameters[keyPart] = untokenizePath(i, urlParts)
--					break
--				} else {
--					pathParameters[keyPart] = value
--				}
--			} else {
--				// without enclosing {}
--				pathParameters[key[1:len(key)-1]] = value
--			}
+-		if !reflect.DeepEqual(actual, tc.result) {
+-			t.Fatalf(
+-				"case %d: expected %#v, got %#v",
+-				i, tc.result, actual)
 -		}
 -	}
--	return pathParameters
 -}
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/error.go b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/error.go
+deleted file mode 100644
+index 3460799..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/error.go
++++ /dev/null
+@@ -1,32 +0,0 @@
+-package mapstructure
 -
--// Untokenize back into an URL path using the slash separator
--func untokenizePath(offset int, parts []string) string {
--	var buffer bytes.Buffer
--	for p := offset; p < len(parts); p++ {
--		buffer.WriteString(parts[p])
--		// do not end
--		if p < len(parts)-1 {
--			buffer.WriteString("/")
--		}
--	}
--	return buffer.String()
+-import (
+-	"fmt"
+-	"strings"
+-)
+-
+-// Error implements the error interface and can represents multiple
+-// errors that occur in the course of a single decode.
+-type Error struct {
+-	Errors []string
 -}
 -
--// Tokenize an URL path using the slash separator ; the result does not have empty tokens
--func tokenizePath(path string) []string {
--	if "/" == path {
--		return []string{}
+-func (e *Error) Error() string {
+-	points := make([]string, len(e.Errors))
+-	for i, err := range e.Errors {
+-		points[i] = fmt.Sprintf("* %s", err)
 -	}
--	return strings.Split(strings.Trim(path, "/"), "/")
+-
+-	return fmt.Sprintf(
+-		"%d error(s) decoding:\n\n%s",
+-		len(e.Errors), strings.Join(points, "\n"))
 -}
 -
--// for debugging
--func (r Route) String() string {
--	return r.Method + " " + r.Path
+-func appendErrors(errors []string, err error) []string {
+-	switch e := err.(type) {
+-	case *Error:
+-		return append(errors, e.Errors...)
+-	default:
+-		return append(errors, e.Error())
+-	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/route_builder.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/route_builder.go
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure.go b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure.go
 deleted file mode 100644
-index 8f46619..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/route_builder.go
+index 381ba5d..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure.go
 +++ /dev/null
-@@ -1,208 +0,0 @@
--package restful
--
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
+@@ -1,704 +0,0 @@
+-// The mapstructure package exposes functionality to convert an
+-// abitrary map[string]interface{} into a native Go structure.
+-//
+-// The Go structure can be arbitrarily complex, containing slices,
+-// other structs, etc. and the decoder will properly decode nested
+-// maps and so on into the proper structures in the native Go struct.
+-// See the examples to see what the decoder is capable of.
+-package mapstructure
 -
 -import (
--	"log"
+-	"errors"
+-	"fmt"
 -	"reflect"
+-	"sort"
+-	"strconv"
 -	"strings"
 -)
 -
--// RouteBuilder is a helper to construct Routes.
--type RouteBuilder struct {
--	rootPath    string
--	currentPath string
--	produces    []string
--	consumes    []string
--	httpMethod  string        // required
--	function    RouteFunction // required
--	filters     []FilterFunction
--	// documentation
--	doc                     string
--	operation               string
--	readSample, writeSample interface{}
--	parameters              []*Parameter
--	errorMap                map[int]ResponseError
--}
--
--// Do evaluates each argument with the RouteBuilder itself.
--// This allows you to follow DRY principles without breaking the fluent programming style.
--// Example:
--// 		ws.Route(ws.DELETE("/{name}").To(t.deletePerson).Do(Returns200, Returns500))
--//
--//		func Returns500(b *RouteBuilder) {
--//			b.Returns(500, "Internal Server Error", restful.ServiceError{})
--//		}
--func (b *RouteBuilder) Do(oneArgBlocks ...func(*RouteBuilder)) *RouteBuilder {
--	for _, each := range oneArgBlocks {
--		each(b)
--	}
--	return b
--}
+-// DecodeHookFunc is the callback function that can be used for
+-// data transformations. See "DecodeHook" in the DecoderConfig
+-// struct.
+-type DecodeHookFunc func(
+-	from reflect.Kind,
+-	to reflect.Kind,
+-	data interface{}) (interface{}, error)
 -
--// To bind the route to a function.
--// If this route is matched with the incoming Http Request then call this function with the *Request,*Response pair. Required.
--func (b *RouteBuilder) To(function RouteFunction) *RouteBuilder {
--	b.function = function
--	return b
--}
+-// DecoderConfig is the configuration that is used to create a new decoder
+-// and allows customization of various aspects of decoding.
+-type DecoderConfig struct {
+-	// DecodeHook, if set, will be called before any decoding and any
+-	// type conversion (if WeaklyTypedInput is on). This lets you modify
+-	// the values before they're set down onto the resulting struct.
+-	//
+-	// If an error is returned, the entire decode will fail with that
+-	// error.
+-	DecodeHook DecodeHookFunc
 -
--// Method specifies what HTTP method to match. Required.
--func (b *RouteBuilder) Method(method string) *RouteBuilder {
--	b.httpMethod = method
--	return b
--}
+-	// If ErrorUnused is true, then it is an error for there to exist
+-	// keys in the original map that were unused in the decoding process
+-	// (extra keys).
+-	ErrorUnused bool
 -
--// Produces specifies what MIME types can be produced ; the matched one will appear in the Content-Type Http header.
--func (b *RouteBuilder) Produces(mimeTypes ...string) *RouteBuilder {
--	b.produces = mimeTypes
--	return b
--}
+-	// If WeaklyTypedInput is true, the decoder will make the following
+-	// "weak" conversions:
+-	//
+-	//   - bools to string (true = "1", false = "0")
+-	//   - numbers to string (base 10)
+-	//   - bools to int/uint (true = 1, false = 0)
+-	//   - strings to int/uint (base implied by prefix)
+-	//   - int to bool (true if value != 0)
+-	//   - string to bool (accepts: 1, t, T, TRUE, true, True, 0, f, F,
+-	//     FALSE, false, False. Anything else is an error)
+-	//   - empty array = empty map and vice versa
+-	//
+-	WeaklyTypedInput bool
 -
--// Consumes specifies what MIME types can be consumes ; the Accept Http header must matched any of these
--func (b *RouteBuilder) Consumes(mimeTypes ...string) *RouteBuilder {
--	b.consumes = mimeTypes
--	return b
--}
+-	// Metadata is the struct that will contain extra metadata about
+-	// the decoding. If this is nil, then no metadata will be tracked.
+-	Metadata *Metadata
 -
--// Path specifies the relative (w.r.t WebService root path) URL path to match. Default is "/".
--func (b *RouteBuilder) Path(subPath string) *RouteBuilder {
--	b.currentPath = subPath
--	return b
--}
+-	// Result is a pointer to the struct that will contain the decoded
+-	// value.
+-	Result interface{}
 -
--// Doc tells what this route is all about. Optional.
--func (b *RouteBuilder) Doc(documentation string) *RouteBuilder {
--	b.doc = documentation
--	return b
+-	// The tag name that mapstructure reads for field names. This
+-	// defaults to "mapstructure"
+-	TagName string
 -}
 -
--// Reads tells what resource type will be read from the request payload. Optional.
--// A parameter of type "body" is added ,required is set to true and the dataType is set to the qualified name of the sample's type.
--func (b *RouteBuilder) Reads(sample interface{}) *RouteBuilder {
--	b.readSample = sample
--	typeAsName := reflect.TypeOf(sample).String()
--	bodyParameter := &Parameter{&ParameterData{Name: "body"}}
--	bodyParameter.beBody()
--	bodyParameter.Required(true)
--	bodyParameter.DataType(typeAsName)
--	b.Param(bodyParameter)
--	return b
+-// A Decoder takes a raw interface value and turns it into structured
+-// data, keeping track of rich error information along the way in case
+-// anything goes wrong. Unlike the basic top-level Decode method, you can
+-// more finely control how the Decoder behaves using the DecoderConfig
+-// structure. The top-level Decode method is just a convenience that sets
+-// up the most basic Decoder.
+-type Decoder struct {
+-	config *DecoderConfig
 -}
 -
--// ParameterNamed returns a Parameter already known to the RouteBuilder. Returns nil if not.
--// Use this to modify or extend information for the Parameter (through its Data()).
--func (b RouteBuilder) ParameterNamed(name string) (p *Parameter) {
--	for _, each := range b.parameters {
--		if each.Data().Name == name {
--			return each
--		}
--	}
--	return p
--}
+-// Metadata contains information about decoding a structure that
+-// is tedious or difficult to get otherwise.
+-type Metadata struct {
+-	// Keys are the keys of the structure which were successfully decoded
+-	Keys []string
 -
--// Writes tells what resource type will be written as the response payload. Optional.
--func (b *RouteBuilder) Writes(sample interface{}) *RouteBuilder {
--	b.writeSample = sample
--	return b
+-	// Unused is a slice of keys that were found in the raw value but
+-	// weren't decoded since there was no matching field in the result interface
+-	Unused []string
 -}
 -
--// Param allows you to document the parameters of the Route. It adds a new Parameter (does not check for duplicates).
--func (b *RouteBuilder) Param(parameter *Parameter) *RouteBuilder {
--	if b.parameters == nil {
--		b.parameters = []*Parameter{}
+-// Decode takes a map and uses reflection to convert it into the
+-// given Go native structure. val must be a pointer to a struct.
+-func Decode(m interface{}, rawVal interface{}) error {
+-	config := &DecoderConfig{
+-		Metadata: nil,
+-		Result:   rawVal,
 -	}
--	b.parameters = append(b.parameters, parameter)
--	return b
--}
--
--// Operation allows you to document what the acutal method/function call is of the Route.
--func (b *RouteBuilder) Operation(name string) *RouteBuilder {
--	b.operation = name
--	return b
--}
 -
--// ReturnsError is deprecated, use Returns instead.
--func (b *RouteBuilder) ReturnsError(code int, message string, model interface{}) *RouteBuilder {
--	log.Println("ReturnsError is deprecated, use Returns instead.")
--	return b.Returns(code, message, model)
--}
--
--// Returns allows you to document what responses (errors or regular) can be expected.
--// The model parameter is optional ; either pass a struct instance or use nil if not applicable.
--func (b *RouteBuilder) Returns(code int, message string, model interface{}) *RouteBuilder {
--	err := ResponseError{
--		Code:    code,
--		Message: message,
--		Model:   model,
--	}
--	// lazy init because there is no NewRouteBuilder (yet)
--	if b.errorMap == nil {
--		b.errorMap = map[int]ResponseError{}
+-	decoder, err := NewDecoder(config)
+-	if err != nil {
+-		return err
 -	}
--	b.errorMap[code] = err
--	return b
--}
--
--type ResponseError struct {
--	Code    int
--	Message string
--	Model   interface{}
--}
--
--func (b *RouteBuilder) servicePath(path string) *RouteBuilder {
--	b.rootPath = path
--	return b
--}
 -
--// Filter appends a FilterFunction to the end of filters for this Route to build.
--func (b *RouteBuilder) Filter(filter FilterFunction) *RouteBuilder {
--	b.filters = append(b.filters, filter)
--	return b
+-	return decoder.Decode(m)
 -}
 -
--// If no specific Route path then set to rootPath
--// If no specific Produces then set to rootProduces
--// If no specific Consumes then set to rootConsumes
--func (b *RouteBuilder) copyDefaults(rootProduces, rootConsumes []string) {
--	if len(b.produces) == 0 {
--		b.produces = rootProduces
--	}
--	if len(b.consumes) == 0 {
--		b.consumes = rootConsumes
+-// WeakDecode is the same as Decode but is shorthand to enable
+-// WeaklyTypedInput. See DecoderConfig for more info.
+-func WeakDecode(input, output interface{}) error {
+-	config := &DecoderConfig{
+-		Metadata:         nil,
+-		Result:           output,
+-		WeaklyTypedInput: true,
 -	}
--}
 -
--// Build creates a new Route using the specification details collected by the RouteBuilder
--func (b *RouteBuilder) Build() Route {
--	pathExpr, err := newPathExpression(b.currentPath)
+-	decoder, err := NewDecoder(config)
 -	if err != nil {
--		log.Fatalf("[restful] Invalid path:%s because:%v", b.currentPath, err)
--	}
--	if b.function == nil {
--		log.Fatalf("[restful] No function specified for route:" + b.currentPath)
+-		return err
 -	}
--	route := Route{
--		Method:         b.httpMethod,
--		Path:           concatPath(b.rootPath, b.currentPath),
--		Produces:       b.produces,
--		Consumes:       b.consumes,
--		Function:       b.function,
--		Filters:        b.filters,
--		relativePath:   b.currentPath,
--		pathExpr:       pathExpr,
--		Doc:            b.doc,
--		Operation:      b.operation,
--		ParameterDocs:  b.parameters,
--		ResponseErrors: b.errorMap,
--		ReadSample:     b.readSample,
--		WriteSample:    b.writeSample}
--	route.postBuild()
--	return route
--}
 -
--func concatPath(path1, path2 string) string {
--	return strings.TrimRight(path1, "/") + "/" + strings.TrimLeft(path2, "/")
+-	return decoder.Decode(input)
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/route_builder_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/route_builder_test.go
-deleted file mode 100644
-index 42ec689..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/route_builder_test.go
-+++ /dev/null
-@@ -1,55 +0,0 @@
--package restful
--
--import (
--	"testing"
--)
--
--func TestRouteBuilder_PathParameter(t *testing.T) {
--	p := &Parameter{&ParameterData{Name: "name", Description: "desc"}}
--	p.AllowMultiple(true)
--	p.DataType("int")
--	p.Required(true)
--	values := map[string]string{"a": "b"}
--	p.AllowableValues(values)
--	p.bePath()
 -
--	b := new(RouteBuilder)
--	b.function = dummy
--	b.Param(p)
--	r := b.Build()
--	if !r.ParameterDocs[0].Data().AllowMultiple {
--		t.Error("AllowMultiple invalid")
--	}
--	if r.ParameterDocs[0].Data().DataType != "int" {
--		t.Error("dataType invalid")
--	}
--	if !r.ParameterDocs[0].Data().Required {
--		t.Error("required invalid")
--	}
--	if r.ParameterDocs[0].Data().Kind != PathParameterKind {
--		t.Error("kind invalid")
--	}
--	if r.ParameterDocs[0].Data().AllowableValues["a"] != "b" {
--		t.Error("allowableValues invalid")
--	}
--	if b.ParameterNamed("name") == nil {
--		t.Error("access to parameter failed")
+-// NewDecoder returns a new decoder for the given configuration. Once
+-// a decoder has been returned, the same configuration must not be used
+-// again.
+-func NewDecoder(config *DecoderConfig) (*Decoder, error) {
+-	val := reflect.ValueOf(config.Result)
+-	if val.Kind() != reflect.Ptr {
+-		return nil, errors.New("result must be a pointer")
 -	}
--}
 -
--func TestRouteBuilder(t *testing.T) {
--	json := "application/json"
--	b := new(RouteBuilder)
--	b.To(dummy)
--	b.Path("/routes").Method("HEAD").Consumes(json).Produces(json)
--	r := b.Build()
--	if r.Path != "/routes" {
--		t.Error("path invalid")
--	}
--	if r.Produces[0] != json {
--		t.Error("produces invalid")
--	}
--	if r.Consumes[0] != json {
--		t.Error("consumes invalid")
+-	val = val.Elem()
+-	if !val.CanAddr() {
+-		return nil, errors.New("result must be addressable (a pointer)")
 -	}
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/route_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/route_test.go
-deleted file mode 100644
-index a416576..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/route_test.go
-+++ /dev/null
-@@ -1,108 +0,0 @@
--package restful
 -
--import (
--	"testing"
--)
+-	if config.Metadata != nil {
+-		if config.Metadata.Keys == nil {
+-			config.Metadata.Keys = make([]string, 0)
+-		}
 -
--// accept should match produces
--func TestMatchesAcceptStar(t *testing.T) {
--	r := Route{Produces: []string{"application/xml"}}
--	if !r.matchesAccept("*/*") {
--		t.Errorf("accept should match star")
+-		if config.Metadata.Unused == nil {
+-			config.Metadata.Unused = make([]string, 0)
+-		}
 -	}
--}
 -
--// accept should match produces
--func TestMatchesAcceptIE(t *testing.T) {
--	r := Route{Produces: []string{"application/xml"}}
--	if !r.matchesAccept("text/html, application/xhtml+xml, */*") {
--		t.Errorf("accept should match star")
+-	if config.TagName == "" {
+-		config.TagName = "mapstructure"
 -	}
--}
 -
--// accept should match produces
--func TestMatchesAcceptXml(t *testing.T) {
--	r := Route{Produces: []string{"application/xml"}}
--	if r.matchesAccept("application/json") {
--		t.Errorf("accept should not match json")
--	}
--	if !r.matchesAccept("application/xml") {
--		t.Errorf("accept should match xml")
+-	result := &Decoder{
+-		config: config,
 -	}
+-
+-	return result, nil
 -}
 -
--// content type should match consumes
--func TestMatchesContentTypeXml(t *testing.T) {
--	r := Route{Consumes: []string{"application/xml"}}
--	if r.matchesContentType("application/json") {
--		t.Errorf("accept should not match json")
--	}
--	if !r.matchesContentType("application/xml") {
--		t.Errorf("accept should match xml")
--	}
+-// Decode decodes the given raw interface to the target pointer specified
+-// by the configuration.
+-func (d *Decoder) Decode(raw interface{}) error {
+-	return d.decode("", raw, reflect.ValueOf(d.config.Result).Elem())
 -}
 -
--// content type should match consumes
--func TestMatchesContentTypeCharsetInformation(t *testing.T) {
--	r := Route{Consumes: []string{"application/json"}}
--	if !r.matchesContentType("application/json; charset=UTF-8") {
--		t.Errorf("matchesContentType should ignore charset information")
+-// Decodes an unknown data type into a specific reflection value.
+-func (d *Decoder) decode(name string, data interface{}, val reflect.Value) error {
+-	if data == nil {
+-		// If the data is nil, then we don't set anything.
+-		return nil
 -	}
--}
 -
--func TestMatchesPath_OneParam(t *testing.T) {
--	params := doExtractParams("/from/{source}", 2, "/from/here", t)
--	if params["source"] != "here" {
--		t.Errorf("parameter mismatch here")
+-	dataVal := reflect.ValueOf(data)
+-	if !dataVal.IsValid() {
+-		// If the data value is invalid, then we just set the value
+-		// to be the zero value.
+-		val.Set(reflect.Zero(val.Type()))
+-		return nil
 -	}
--}
 -
--func TestMatchesPath_Slash(t *testing.T) {
--	params := doExtractParams("/", 0, "/", t)
--	if len(params) != 0 {
--		t.Errorf("expected empty parameters")
+-	if d.config.DecodeHook != nil {
+-		// We have a DecodeHook, so let's pre-process the data.
+-		var err error
+-		data, err = d.config.DecodeHook(getKind(dataVal), getKind(val), data)
+-		if err != nil {
+-			return err
+-		}
 -	}
--}
 -
--func TestMatchesPath_SlashNonVar(t *testing.T) {
--	params := doExtractParams("/any", 1, "/any", t)
--	if len(params) != 0 {
--		t.Errorf("expected empty parameters")
+-	var err error
+-	dataKind := getKind(val)
+-	switch dataKind {
+-	case reflect.Bool:
+-		err = d.decodeBool(name, data, val)
+-	case reflect.Interface:
+-		err = d.decodeBasic(name, data, val)
+-	case reflect.String:
+-		err = d.decodeString(name, data, val)
+-	case reflect.Int:
+-		err = d.decodeInt(name, data, val)
+-	case reflect.Uint:
+-		err = d.decodeUint(name, data, val)
+-	case reflect.Float32:
+-		err = d.decodeFloat(name, data, val)
+-	case reflect.Struct:
+-		err = d.decodeStruct(name, data, val)
+-	case reflect.Map:
+-		err = d.decodeMap(name, data, val)
+-	case reflect.Ptr:
+-		err = d.decodePtr(name, data, val)
+-	case reflect.Slice:
+-		err = d.decodeSlice(name, data, val)
+-	default:
+-		// If we reached this point then we weren't able to decode it
+-		return fmt.Errorf("%s: unsupported type: %s", name, dataKind)
 -	}
--}
 -
--func TestMatchesPath_TwoVars(t *testing.T) {
--	params := doExtractParams("/from/{source}/to/{destination}", 4, "/from/AMS/to/NY", t)
--	if params["source"] != "AMS" {
--		t.Errorf("parameter mismatch AMS")
+-	// If we reached here, then we successfully decoded SOMETHING, so
+-	// mark the key as used if we're tracking metadata.
+-	if d.config.Metadata != nil && name != "" {
+-		d.config.Metadata.Keys = append(d.config.Metadata.Keys, name)
 -	}
+-
+-	return err
 -}
 -
--func TestMatchesPath_VarOnFront(t *testing.T) {
--	params := doExtractParams("{what}/from/{source}/", 3, "who/from/SOS/", t)
--	if params["source"] != "SOS" {
--		t.Errorf("parameter mismatch SOS")
+-// This decodes a basic type (bool, int, string, etc.) and sets the
+-// value to "data" of that type.
+-func (d *Decoder) decodeBasic(name string, data interface{}, val reflect.Value) error {
+-	dataVal := reflect.ValueOf(data)
+-	dataValType := dataVal.Type()
+-	if !dataValType.AssignableTo(val.Type()) {
+-		return fmt.Errorf(
+-			"'%s' expected type '%s', got '%s'",
+-			name, val.Type(), dataValType)
 -	}
+-
+-	val.Set(dataVal)
+-	return nil
 -}
 -
--func TestExtractParameters_EmptyValue(t *testing.T) {
--	params := doExtractParams("/fixed/{var}", 2, "/fixed/", t)
--	if params["var"] != "" {
--		t.Errorf("parameter mismatch var")
+-func (d *Decoder) decodeString(name string, data interface{}, val reflect.Value) error {
+-	dataVal := reflect.ValueOf(data)
+-	dataKind := getKind(dataVal)
+-
+-	converted := true
+-	switch {
+-	case dataKind == reflect.String:
+-		val.SetString(dataVal.String())
+-	case dataKind == reflect.Bool && d.config.WeaklyTypedInput:
+-		if dataVal.Bool() {
+-			val.SetString("1")
+-		} else {
+-			val.SetString("0")
+-		}
+-	case dataKind == reflect.Int && d.config.WeaklyTypedInput:
+-		val.SetString(strconv.FormatInt(dataVal.Int(), 10))
+-	case dataKind == reflect.Uint && d.config.WeaklyTypedInput:
+-		val.SetString(strconv.FormatUint(dataVal.Uint(), 10))
+-	case dataKind == reflect.Float32 && d.config.WeaklyTypedInput:
+-		val.SetString(strconv.FormatFloat(dataVal.Float(), 'f', -1, 64))
+-	case dataKind == reflect.Slice && d.config.WeaklyTypedInput:
+-		dataType := dataVal.Type()
+-		elemKind := dataType.Elem().Kind()
+-		switch {
+-		case elemKind == reflect.Uint8:
+-			val.SetString(string(dataVal.Interface().([]uint8)))
+-		default:
+-			converted = false
+-		}
+-	default:
+-		converted = false
 -	}
--}
 -
--func TestTokenizePath(t *testing.T) {
--	if len(tokenizePath("/")) != 0 {
--		t.Errorf("not empty path tokens")
+-	if !converted {
+-		return fmt.Errorf(
+-			"'%s' expected type '%s', got unconvertible type '%s'",
+-			name, val.Type(), dataVal.Type())
 -	}
+-
+-	return nil
 -}
 -
--func doExtractParams(routePath string, size int, urlPath string, t *testing.T) map[string]string {
--	r := Route{Path: routePath}
--	r.postBuild()
--	if len(r.pathParts) != size {
--		t.Fatalf("len not %v %v, but %v", size, r.pathParts, len(r.pathParts))
+-func (d *Decoder) decodeInt(name string, data interface{}, val reflect.Value) error {
+-	dataVal := reflect.ValueOf(data)
+-	dataKind := getKind(dataVal)
+-
+-	switch {
+-	case dataKind == reflect.Int:
+-		val.SetInt(dataVal.Int())
+-	case dataKind == reflect.Uint:
+-		val.SetInt(int64(dataVal.Uint()))
+-	case dataKind == reflect.Float32:
+-		val.SetInt(int64(dataVal.Float()))
+-	case dataKind == reflect.Bool && d.config.WeaklyTypedInput:
+-		if dataVal.Bool() {
+-			val.SetInt(1)
+-		} else {
+-			val.SetInt(0)
+-		}
+-	case dataKind == reflect.String && d.config.WeaklyTypedInput:
+-		i, err := strconv.ParseInt(dataVal.String(), 0, val.Type().Bits())
+-		if err == nil {
+-			val.SetInt(i)
+-		} else {
+-			return fmt.Errorf("cannot parse '%s' as int: %s", name, err)
+-		}
+-	default:
+-		return fmt.Errorf(
+-			"'%s' expected type '%s', got unconvertible type '%s'",
+-			name, val.Type(), dataVal.Type())
 -	}
--	return r.extractParameters(urlPath)
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/router.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/router.go
-deleted file mode 100644
-index 9b32fb6..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/router.go
-+++ /dev/null
-@@ -1,18 +0,0 @@
--package restful
 -
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
+-	return nil
+-}
 -
--import "net/http"
+-func (d *Decoder) decodeUint(name string, data interface{}, val reflect.Value) error {
+-	dataVal := reflect.ValueOf(data)
+-	dataKind := getKind(dataVal)
 -
--// A RouteSelector finds the best matching Route given the input HTTP Request
--type RouteSelector interface {
+-	switch {
+-	case dataKind == reflect.Int:
+-		val.SetUint(uint64(dataVal.Int()))
+-	case dataKind == reflect.Uint:
+-		val.SetUint(dataVal.Uint())
+-	case dataKind == reflect.Float32:
+-		val.SetUint(uint64(dataVal.Float()))
+-	case dataKind == reflect.Bool && d.config.WeaklyTypedInput:
+-		if dataVal.Bool() {
+-			val.SetUint(1)
+-		} else {
+-			val.SetUint(0)
+-		}
+-	case dataKind == reflect.String && d.config.WeaklyTypedInput:
+-		i, err := strconv.ParseUint(dataVal.String(), 0, val.Type().Bits())
+-		if err == nil {
+-			val.SetUint(i)
+-		} else {
+-			return fmt.Errorf("cannot parse '%s' as uint: %s", name, err)
+-		}
+-	default:
+-		return fmt.Errorf(
+-			"'%s' expected type '%s', got unconvertible type '%s'",
+-			name, val.Type(), dataVal.Type())
+-	}
 -
--	// SelectRoute finds a Route given the input HTTP Request and a list of WebServices.
--	// It returns a selected Route and its containing WebService or an error indicating
--	// a problem.
--	SelectRoute(
--		webServices []*WebService,
--		httpRequest *http.Request) (selectedService *WebService, selected *Route, err error)
+-	return nil
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/service_error.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/service_error.go
-deleted file mode 100644
-index 62d1108..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/service_error.go
-+++ /dev/null
-@@ -1,23 +0,0 @@
--package restful
 -
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
+-func (d *Decoder) decodeBool(name string, data interface{}, val reflect.Value) error {
+-	dataVal := reflect.ValueOf(data)
+-	dataKind := getKind(dataVal)
 -
--import "fmt"
+-	switch {
+-	case dataKind == reflect.Bool:
+-		val.SetBool(dataVal.Bool())
+-	case dataKind == reflect.Int && d.config.WeaklyTypedInput:
+-		val.SetBool(dataVal.Int() != 0)
+-	case dataKind == reflect.Uint && d.config.WeaklyTypedInput:
+-		val.SetBool(dataVal.Uint() != 0)
+-	case dataKind == reflect.Float32 && d.config.WeaklyTypedInput:
+-		val.SetBool(dataVal.Float() != 0)
+-	case dataKind == reflect.String && d.config.WeaklyTypedInput:
+-		b, err := strconv.ParseBool(dataVal.String())
+-		if err == nil {
+-			val.SetBool(b)
+-		} else if dataVal.String() == "" {
+-			val.SetBool(false)
+-		} else {
+-			return fmt.Errorf("cannot parse '%s' as bool: %s", name, err)
+-		}
+-	default:
+-		return fmt.Errorf(
+-			"'%s' expected type '%s', got unconvertible type '%s'",
+-			name, val.Type(), dataVal.Type())
+-	}
 -
--// ServiceError is a transport object to pass information about a non-Http error occurred in a WebService while processing a request.
--type ServiceError struct {
--	Code    int
--	Message string
+-	return nil
 -}
 -
--// NewError returns a ServiceError using the code and reason
--func NewError(code int, message string) ServiceError {
--	return ServiceError{Code: code, Message: message}
--}
+-func (d *Decoder) decodeFloat(name string, data interface{}, val reflect.Value) error {
+-	dataVal := reflect.ValueOf(data)
+-	dataKind := getKind(dataVal)
 -
--// Error returns a text representation of the service error
--func (s ServiceError) Error() string {
--	return fmt.Sprintf("[ServiceError:%v] %v", s.Code, s.Message)
+-	switch {
+-	case dataKind == reflect.Int:
+-		val.SetFloat(float64(dataVal.Int()))
+-	case dataKind == reflect.Uint:
+-		val.SetFloat(float64(dataVal.Uint()))
+-	case dataKind == reflect.Float32:
+-		val.SetFloat(float64(dataVal.Float()))
+-	case dataKind == reflect.Bool && d.config.WeaklyTypedInput:
+-		if dataVal.Bool() {
+-			val.SetFloat(1)
+-		} else {
+-			val.SetFloat(0)
+-		}
+-	case dataKind == reflect.String && d.config.WeaklyTypedInput:
+-		f, err := strconv.ParseFloat(dataVal.String(), val.Type().Bits())
+-		if err == nil {
+-			val.SetFloat(f)
+-		} else {
+-			return fmt.Errorf("cannot parse '%s' as float: %s", name, err)
+-		}
+-	default:
+-		return fmt.Errorf(
+-			"'%s' expected type '%s', got unconvertible type '%s'",
+-			name, val.Type(), dataVal.Type())
+-	}
+-
+-	return nil
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/CHANGES.md b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/CHANGES.md
-deleted file mode 100644
-index 9980f2f..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/CHANGES.md
-+++ /dev/null
-@@ -1,27 +0,0 @@
--Change history of swagger
--=
 -
--2014-11-14
--- operation parameters are now sorted using ordering path,query,form,header,body
+-func (d *Decoder) decodeMap(name string, data interface{}, val reflect.Value) error {
+-	valType := val.Type()
+-	valKeyType := valType.Key()
+-	valElemType := valType.Elem()
 -
--2014-11-12
--- respect omitempty tag value for embedded structs
--- expose ApiVersion of WebService to Swagger ApiDeclaration
+-	// Make a new map to hold our result
+-	mapType := reflect.MapOf(valKeyType, valElemType)
+-	valMap := reflect.MakeMap(mapType)
 -
--2014-05-29
--- (api add) Ability to define custom http.Handler to serve swagger-ui static files
+-	// Check input type
+-	dataVal := reflect.Indirect(reflect.ValueOf(data))
+-	if dataVal.Kind() != reflect.Map {
+-		// Accept empty array/slice instead of an empty map in weakly typed mode
+-		if d.config.WeaklyTypedInput &&
+-			(dataVal.Kind() == reflect.Slice || dataVal.Kind() == reflect.Array) &&
+-			dataVal.Len() == 0 {
+-			val.Set(valMap)
+-			return nil
+-		} else {
+-			return fmt.Errorf("'%s' expected a map, got '%s'", name, dataVal.Kind())
+-		}
+-	}
 -
--2014-05-04
--- (fix) include model for array element type of response
+-	// Accumulate errors
+-	errors := make([]string, 0)
 -
--2014-01-03
--- (fix) do not add primitive type to the Api models
+-	for _, k := range dataVal.MapKeys() {
+-		fieldName := fmt.Sprintf("%s[%s]", name, k)
 -
--2013-11-27
--- (fix) make Swagger work for WebServices with root ("/" or "") paths
+-		// First decode the key into the proper type
+-		currentKey := reflect.Indirect(reflect.New(valKeyType))
+-		if err := d.decode(fieldName, k.Interface(), currentKey); err != nil {
+-			errors = appendErrors(errors, err)
+-			continue
+-		}
 -
--2013-10-29
--- (api add) package variable LogInfo to customize logging function
+-		// Next decode the data into the proper type
+-		v := dataVal.MapIndex(k).Interface()
+-		currentVal := reflect.Indirect(reflect.New(valElemType))
+-		if err := d.decode(fieldName, v, currentVal); err != nil {
+-			errors = appendErrors(errors, err)
+-			continue
+-		}
 -
--2013-10-15
--- upgraded to spec version 1.2 (https://github.com/wordnik/swagger-core/wiki/1.2-transition)
-\ No newline at end of file
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/README.md b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/README.md
-deleted file mode 100644
-index 2efe8f3..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/README.md
-+++ /dev/null
-@@ -1,28 +0,0 @@
--How to use Swagger UI with go-restful
--=
+-		valMap.SetMapIndex(currentKey, currentVal)
+-	}
 -
--Get the Swagger UI sources (version 1.2 only)
+-	// Set the built up map to the value
+-	val.Set(valMap)
 -
--	git clone https://github.com/wordnik/swagger-ui.git
--	
--The project contains a "dist" folder.
--Its contents has all the Swagger UI files you need.
+-	// If we had errors, return those
+-	if len(errors) > 0 {
+-		return &Error{errors}
+-	}
 -
--The `index.html` has an `url` set to `http://petstore.swagger.wordnik.com/api/api-docs`.
--You need to change that to match your WebService JSON endpoint  e.g. `http://localhost:8080/apidocs.json`
+-	return nil
+-}
 -
--Now, you can install the Swagger WebService for serving the Swagger specification in JSON.
+-func (d *Decoder) decodePtr(name string, data interface{}, val reflect.Value) error {
+-	// Create an element of the concrete (non pointer) type and decode
+-	// into that. Then set the value of the pointer to this type.
+-	valType := val.Type()
+-	valElemType := valType.Elem()
+-	realVal := reflect.New(valElemType)
+-	if err := d.decode(name, data, reflect.Indirect(realVal)); err != nil {
+-		return err
+-	}
 -
--	config := swagger.Config{
--		WebServices:    restful.RegisteredWebServices(),
--		ApiPath:        "/apidocs.json",
--		SwaggerPath:     "/apidocs/",
--		SwaggerFilePath: "/Users/emicklei/Projects/swagger-ui/dist"}
--	swagger.InstallSwaggerService(config)		
--	
--	
--Notes
----
--- Use RouteBuilder.Operation(..) to set the Nickname field of the API spec
--- The WebServices field of swagger.Config can be used to control which service you want to expose and document ; you can have multiple configs and therefore multiple endpoints.
--- Use tag "description" to annotate a struct field with a description to show in the UI
-\ No newline at end of file
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/config.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/config.go
-deleted file mode 100644
-index 4fca0fa..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/config.go
-+++ /dev/null
-@@ -1,25 +0,0 @@
--package swagger
+-	val.Set(realVal)
+-	return nil
+-}
 -
--import (
--	"net/http"
+-func (d *Decoder) decodeSlice(name string, data interface{}, val reflect.Value) error {
+-	dataVal := reflect.Indirect(reflect.ValueOf(data))
+-	dataValKind := dataVal.Kind()
+-	valType := val.Type()
+-	valElemType := valType.Elem()
+-	sliceType := reflect.SliceOf(valElemType)
 -
--	"github.com/emicklei/go-restful"
--)
+-	// Check input type
+-	if dataValKind != reflect.Array && dataValKind != reflect.Slice {
+-		// Accept empty map instead of array/slice in weakly typed mode
+-		if d.config.WeaklyTypedInput && dataVal.Kind() == reflect.Map && dataVal.Len() == 0 {
+-			val.Set(reflect.MakeSlice(sliceType, 0, 0))
+-			return nil
+-		} else {
+-			return fmt.Errorf(
+-				"'%s': source data must be an array or slice, got %s", name, dataValKind)
+-		}
+-	}
 -
--type Config struct {
--	// url where the services are available, e.g. http://localhost:8080
--	// if left empty then the basePath of Swagger is taken from the actual request
--	WebServicesUrl string
--	// path where the JSON api is avaiable , e.g. /apidocs
--	ApiPath string
--	// [optional] path where the swagger UI will be served, e.g. /swagger
--	SwaggerPath string
--	// [optional] location of folder containing Swagger HTML5 application index.html
--	SwaggerFilePath string
--	// api listing is constructed from this list of restful WebServices.
--	WebServices []*restful.WebService
--	// will serve all static content (scripts,pages,images)
--	StaticHandler http.Handler
--	// [optional] on default CORS (Cross-Origin-Resource-Sharing) is enabled.
--	DisableCORS bool
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/model_builder.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/model_builder.go
-deleted file mode 100644
-index 68524ec..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/model_builder.go
-+++ /dev/null
-@@ -1,277 +0,0 @@
--package swagger
+-	// Make a new slice to hold our result, same size as the original data.
+-	valSlice := reflect.MakeSlice(sliceType, dataVal.Len(), dataVal.Len())
 -
--import (
--	"encoding/json"
--	"reflect"
--	"strings"
--)
+-	// Accumulate any errors
+-	errors := make([]string, 0)
 -
--type modelBuilder struct {
--	Models map[string]Model
--}
+-	for i := 0; i < dataVal.Len(); i++ {
+-		currentData := dataVal.Index(i).Interface()
+-		currentField := valSlice.Index(i)
 -
--func (b modelBuilder) addModel(st reflect.Type, nameOverride string) {
--	modelName := b.keyFrom(st)
--	if nameOverride != "" {
--		modelName = nameOverride
--	}
--	// no models needed for primitive types
--	if b.isPrimitiveType(modelName) {
--		return
--	}
--	// see if we already have visited this model
--	if _, ok := b.Models[modelName]; ok {
--		return
+-		fieldName := fmt.Sprintf("%s[%d]", name, i)
+-		if err := d.decode(fieldName, currentData, currentField); err != nil {
+-			errors = appendErrors(errors, err)
+-		}
 -	}
--	sm := Model{
--		Id:         modelName,
--		Required:   []string{},
--		Properties: map[string]ModelProperty{}}
 -
--	// reference the model before further initializing (enables recursive structs)
--	b.Models[modelName] = sm
+-	// Finally, set the value to the slice we built up
+-	val.Set(valSlice)
 -
--	// check for slice or array
--	if st.Kind() == reflect.Slice || st.Kind() == reflect.Array {
--		b.addModel(st.Elem(), "")
--		return
--	}
--	// check for structure or primitive type
--	if st.Kind() != reflect.Struct {
--		return
--	}
--	for i := 0; i < st.NumField(); i++ {
--		field := st.Field(i)
--		jsonName, prop := b.buildProperty(field, &sm, modelName)
--		if descTag := field.Tag.Get("description"); descTag != "" {
--			prop.Description = descTag
--		}
--		// add if not ommitted
--		if len(jsonName) != 0 {
--			// update Required
--			if b.isPropertyRequired(field) {
--				sm.Required = append(sm.Required, jsonName)
--			}
--			sm.Properties[jsonName] = prop
--		}
+-	// If there were errors, we return those
+-	if len(errors) > 0 {
+-		return &Error{errors}
 -	}
 -
--	// update model builder with completed model
--	b.Models[modelName] = sm
+-	return nil
 -}
 -
--func (b modelBuilder) isPropertyRequired(field reflect.StructField) bool {
--	required := true
--	if jsonTag := field.Tag.Get("json"); jsonTag != "" {
--		s := strings.Split(jsonTag, ",")
--		if len(s) > 1 && s[1] == "omitempty" {
--			return false
--		}
+-func (d *Decoder) decodeStruct(name string, data interface{}, val reflect.Value) error {
+-	dataVal := reflect.Indirect(reflect.ValueOf(data))
+-	dataValKind := dataVal.Kind()
+-	if dataValKind != reflect.Map {
+-		return fmt.Errorf("'%s' expected a map, got '%s'", name, dataValKind)
 -	}
--	return required
--}
 -
--func (b modelBuilder) buildProperty(field reflect.StructField, model *Model, modelName string) (jsonName string, prop ModelProperty) {
--	jsonName = b.jsonNameOfField(field)
--	if len(jsonName) == 0 {
--		// empty name signals skip property
--		return "", prop
+-	dataValType := dataVal.Type()
+-	if kind := dataValType.Key().Kind(); kind != reflect.String && kind != reflect.Interface {
+-		return fmt.Errorf(
+-			"'%s' needs a map with string keys, has '%s' keys",
+-			name, dataValType.Key().Kind())
 -	}
--	fieldType := field.Type
--	fieldKind := fieldType.Kind()
 -
--	if jsonTag := field.Tag.Get("json"); jsonTag != "" {
--		s := strings.Split(jsonTag, ",")
--		if len(s) > 1 && s[1] == "string" {
--			fieldType = reflect.TypeOf("")
--		}
+-	dataValKeys := make(map[reflect.Value]struct{})
+-	dataValKeysUnused := make(map[interface{}]struct{})
+-	for _, dataValKey := range dataVal.MapKeys() {
+-		dataValKeys[dataValKey] = struct{}{}
+-		dataValKeysUnused[dataValKey.Interface()] = struct{}{}
 -	}
 -
--	var pType = b.jsonSchemaType(fieldType.String()) // may include pkg path
--	prop.Type = &pType
--	if b.isPrimitiveType(fieldType.String()) {
--		prop.Format = b.jsonSchemaFormat(fieldType.String())
--		return jsonName, prop
--	}
+-	errors := make([]string, 0)
 -
--	marshalerType := reflect.TypeOf((*json.Marshaler)(nil)).Elem()
--	if fieldType.Implements(marshalerType) {
--		var pType = "string"
--		prop.Type = &pType
--		return jsonName, prop
--	}
+-	// This slice will keep track of all the structs we'll be decoding.
+-	// There can be more than one struct if there are embedded structs
+-	// that are squashed.
+-	structs := make([]reflect.Value, 1, 5)
+-	structs[0] = val
 -
--	if fieldKind == reflect.Struct {
--		return b.buildStructTypeProperty(field, jsonName, model)
--	}
+-	// Compile the list of all the fields that we're going to be decoding
+-	// from all the structs.
+-	fields := make(map[*reflect.StructField]reflect.Value)
+-	for len(structs) > 0 {
+-		structVal := structs[0]
+-		structs = structs[1:]
 -
--	if fieldKind == reflect.Slice || fieldKind == reflect.Array {
--		return b.buildArrayTypeProperty(field, jsonName, modelName)
--	}
+-		structType := structVal.Type()
+-		for i := 0; i < structType.NumField(); i++ {
+-			fieldType := structType.Field(i)
 -
--	if fieldKind == reflect.Ptr {
--		return b.buildPointerTypeProperty(field, jsonName, modelName)
--	}
+-			if fieldType.Anonymous {
+-				fieldKind := fieldType.Type.Kind()
+-				if fieldKind != reflect.Struct {
+-					errors = appendErrors(errors,
+-						fmt.Errorf("%s: unsupported type: %s", fieldType.Name, fieldKind))
+-					continue
+-				}
 -
--	if fieldType.Name() == "" { // override type of anonymous structs
--		nestedTypeName := modelName + "." + jsonName
--		var pType = nestedTypeName
--		prop.Type = &pType
--		b.addModel(fieldType, nestedTypeName)
--	}
--	return jsonName, prop
--}
+-				// We have an embedded field. We "squash" the fields down
+-				// if specified in the tag.
+-				squash := false
+-				tagParts := strings.Split(fieldType.Tag.Get(d.config.TagName), ",")
+-				for _, tag := range tagParts[1:] {
+-					if tag == "squash" {
+-						squash = true
+-						break
+-					}
+-				}
 -
--func (b modelBuilder) buildStructTypeProperty(field reflect.StructField, jsonName string, model *Model) (nameJson string, prop ModelProperty) {
--	fieldType := field.Type
--	// check for anonymous
--	if len(fieldType.Name()) == 0 {
--		// anonymous
--		anonType := model.Id + "." + jsonName
--		b.addModel(fieldType, anonType)
--		prop.Type = &anonType
--		return jsonName, prop
+-				if squash {
+-					structs = append(structs, val.FieldByName(fieldType.Name))
+-					continue
+-				}
+-			}
+-
+-			// Normal struct field, store it away
+-			fields[&fieldType] = structVal.Field(i)
+-		}
 -	}
--	if field.Name == fieldType.Name() && field.Anonymous {
--		// embedded struct
--		sub := modelBuilder{map[string]Model{}}
--		sub.addModel(fieldType, "")
--		subKey := sub.keyFrom(fieldType)
--		// merge properties from sub
--		subModel := sub.Models[subKey]
--		for k, v := range subModel.Properties {
--			model.Properties[k] = v
--			// if subModel says this property is required then include it
--			required := false
--			for _, each := range subModel.Required {
--				if k == each {
--					required = true
+-
+-	for fieldType, field := range fields {
+-		fieldName := fieldType.Name
+-
+-		tagValue := fieldType.Tag.Get(d.config.TagName)
+-		tagValue = strings.SplitN(tagValue, ",", 2)[0]
+-		if tagValue != "" {
+-			fieldName = tagValue
+-		}
+-
+-		rawMapKey := reflect.ValueOf(fieldName)
+-		rawMapVal := dataVal.MapIndex(rawMapKey)
+-		if !rawMapVal.IsValid() {
+-			// Do a slower search by iterating over each key and
+-			// doing case-insensitive search.
+-			for dataValKey, _ := range dataValKeys {
+-				mK, ok := dataValKey.Interface().(string)
+-				if !ok {
+-					// Not a string key
+-					continue
+-				}
+-
+-				if strings.EqualFold(mK, fieldName) {
+-					rawMapKey = dataValKey
+-					rawMapVal = dataVal.MapIndex(dataValKey)
 -					break
 -				}
 -			}
--			if required {
--				model.Required = append(model.Required, k)
+-
+-			if !rawMapVal.IsValid() {
+-				// There was no matching key in the map for the value in
+-				// the struct. Just ignore.
+-				continue
 -			}
 -		}
--		// empty name signals skip property
--		return "", prop
--	}
--	// simple struct
--	b.addModel(fieldType, "")
--	var pType = fieldType.String()
--	prop.Type = &pType
--	return jsonName, prop
--}
 -
--func (b modelBuilder) buildArrayTypeProperty(field reflect.StructField, jsonName, modelName string) (nameJson string, prop ModelProperty) {
--	fieldType := field.Type
--	var pType = "array"
--	prop.Type = &pType
--	elemName := b.getElementTypeName(modelName, jsonName, fieldType.Elem())
--	prop.Items = []Item{Item{Ref: &elemName}}
--	// add|overwrite model for element type
--	b.addModel(fieldType.Elem(), elemName)
--	return jsonName, prop
--}
+-		// Delete the key we're using from the unused map so we stop tracking
+-		delete(dataValKeysUnused, rawMapKey.Interface())
 -
--func (b modelBuilder) buildPointerTypeProperty(field reflect.StructField, jsonName, modelName string) (nameJson string, prop ModelProperty) {
--	fieldType := field.Type
+-		if !field.IsValid() {
+-			// This should never happen
+-			panic("field is not valid")
+-		}
 -
--	// override type of pointer to list-likes
--	if fieldType.Elem().Kind() == reflect.Slice || fieldType.Elem().Kind() == reflect.Array {
--		var pType = "array"
--		prop.Type = &pType
--		elemName := b.getElementTypeName(modelName, jsonName, fieldType.Elem().Elem())
--		prop.Items = []Item{Item{Ref: &elemName}}
--		// add|overwrite model for element type
--		b.addModel(fieldType.Elem().Elem(), elemName)
--	} else {
--		// non-array, pointer type
--		var pType = fieldType.String()[1:] // no star, include pkg path
--		prop.Type = &pType
--		elemName := ""
--		if fieldType.Elem().Name() == "" {
--			elemName = modelName + "." + jsonName
--			prop.Type = &elemName
+-		// If we can't set the field, then it is unexported or something,
+-		// and we just continue onwards.
+-		if !field.CanSet() {
+-			continue
 -		}
--		b.addModel(fieldType.Elem(), elemName)
--	}
--	return jsonName, prop
--}
 -
--func (b modelBuilder) getElementTypeName(modelName, jsonName string, t reflect.Type) string {
--	if t.Name() == "" {
--		return modelName + "." + jsonName
+-		// If the name is empty string, then we're at the root, and we
+-		// don't dot-join the fields.
+-		if name != "" {
+-			fieldName = fmt.Sprintf("%s.%s", name, fieldName)
+-		}
+-
+-		if err := d.decode(fieldName, rawMapVal.Interface(), field); err != nil {
+-			errors = appendErrors(errors, err)
+-		}
 -	}
--	if b.isPrimitiveType(t.Name()) {
--		return b.jsonSchemaType(t.Name())
+-
+-	if d.config.ErrorUnused && len(dataValKeysUnused) > 0 {
+-		keys := make([]string, 0, len(dataValKeysUnused))
+-		for rawKey, _ := range dataValKeysUnused {
+-			keys = append(keys, rawKey.(string))
+-		}
+-		sort.Strings(keys)
+-
+-		err := fmt.Errorf("'%s' has invalid keys: %s", name, strings.Join(keys, ", "))
+-		errors = appendErrors(errors, err)
 -	}
--	return b.keyFrom(t)
--}
 -
--func (b modelBuilder) keyFrom(st reflect.Type) string {
--	key := st.String()
--	if len(st.Name()) == 0 { // unnamed type
--		// Swagger UI has special meaning for [
--		key = strings.Replace(key, "[]", "||", -1)
+-	if len(errors) > 0 {
+-		return &Error{errors}
 -	}
--	return key
--}
 -
--func (b modelBuilder) isPrimitiveType(modelName string) bool {
--	return strings.Contains("uint8 int int32 int64 float32 float64 bool string byte time.Time", modelName)
--}
+-	// Add the unused keys to the list of unused keys if we're tracking metadata
+-	if d.config.Metadata != nil {
+-		for rawKey, _ := range dataValKeysUnused {
+-			key := rawKey.(string)
+-			if name != "" {
+-				key = fmt.Sprintf("%s.%s", name, key)
+-			}
 -
--// jsonNameOfField returns the name of the field as it should appear in JSON format
--// An empty string indicates that this field is not part of the JSON representation
--func (b modelBuilder) jsonNameOfField(field reflect.StructField) string {
--	if jsonTag := field.Tag.Get("json"); jsonTag != "" {
--		s := strings.Split(jsonTag, ",")
--		if s[0] == "-" {
--			// empty name signals skip property
--			return ""
--		} else if s[0] != "" {
--			return s[0]
+-			d.config.Metadata.Unused = append(d.config.Metadata.Unused, key)
 -		}
 -	}
--	return field.Name
--}
 -
--func (b modelBuilder) jsonSchemaType(modelName string) string {
--	schemaMap := map[string]string{
--		"uint8":     "integer",
--		"int":       "integer",
--		"int32":     "integer",
--		"int64":     "integer",
--		"byte":      "string",
--		"float64":   "number",
--		"float32":   "number",
--		"bool":      "boolean",
--		"time.Time": "string",
--	}
--	mapped, ok := schemaMap[modelName]
--	if ok {
--		return mapped
--	} else {
--		return modelName // use as is (custom or struct)
--	}
+-	return nil
 -}
 -
--func (b modelBuilder) jsonSchemaFormat(modelName string) string {
--	schemaMap := map[string]string{
--		"int":       "int32",
--		"int32":     "int32",
--		"int64":     "int64",
--		"byte":      "byte",
--		"uint8":     "byte",
--		"float64":   "double",
--		"float32":   "float",
--		"time.Time": "date-time",
--	}
--	mapped, ok := schemaMap[modelName]
--	if ok {
--		return mapped
--	} else {
--		return "" // no format
+-func getKind(val reflect.Value) reflect.Kind {
+-	kind := val.Kind()
+-
+-	switch {
+-	case kind >= reflect.Int && kind <= reflect.Int64:
+-		return reflect.Int
+-	case kind >= reflect.Uint && kind <= reflect.Uint64:
+-		return reflect.Uint
+-	case kind >= reflect.Float32 && kind <= reflect.Float64:
+-		return reflect.Float32
+-	default:
+-		return kind
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/model_builder_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/model_builder_test.go
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_benchmark_test.go b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_benchmark_test.go
 deleted file mode 100644
-index dd966bd..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/model_builder_test.go
+index b50ac36..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_benchmark_test.go
 +++ /dev/null
-@@ -1,729 +0,0 @@
--package swagger
+@@ -1,243 +0,0 @@
+-package mapstructure
 -
 -import (
 -	"testing"
--	"time"
 -)
 -
--type YesNo bool
--
--func (y YesNo) MarshalJSON() ([]byte, error) {
--	if y {
--		return []byte("yes"), nil
--	}
--	return []byte("no"), nil
--}
--
--// clear && go test -v -test.run TestCustomMarshaller_Issue96 ...swagger
--func TestCustomMarshaller_Issue96(t *testing.T) {
--	type Vote struct {
--		What YesNo
--	}
--	testJsonFromStruct(t, Vote{}, `{
--  "swagger.Vote": {
--   "id": "swagger.Vote",
--   "required": [
--    "What"
--   ],
--   "properties": {
--    "What": {
--     "type": "string"
--    }
--   }
--  }
-- }`)
--}
--
--// clear && go test -v -test.run TestPrimitiveTypes ...swagger
--func TestPrimitiveTypes(t *testing.T) {
--	type Prims struct {
--		f float64
--		t time.Time
--	}
--	testJsonFromStruct(t, Prims{}, `{
--  "swagger.Prims": {
--   "id": "swagger.Prims",
--   "required": [
--    "f",
--    "t"
--   ],
--   "properties": {
--    "f": {
--     "type": "number",
--     "format": "double"
--    },
--    "t": {
--     "type": "string",
--     "format": "date-time"
--    }
--   }
--  }
-- }`)
--}
--
--// clear && go test -v -test.run TestS1 ...swagger
--func TestS1(t *testing.T) {
--	type S1 struct {
--		Id string
--	}
--	testJsonFromStruct(t, S1{}, `{
--  "swagger.S1": {
--   "id": "swagger.S1",
--   "required": [
--    "Id"
--   ],
--   "properties": {
--    "Id": {
--     "type": "string"
--    }
--   }
--  }
-- }`)
--}
--
--// clear && go test -v -test.run TestS2 ...swagger
--func TestS2(t *testing.T) {
--	type S2 struct {
--		Ids []string
+-func Benchmark_Decode(b *testing.B) {
+-	type Person struct {
+-		Name   string
+-		Age    int
+-		Emails []string
+-		Extra  map[string]string
 -	}
--	testJsonFromStruct(t, S2{}, `{
--  "swagger.S2": {
--   "id": "swagger.S2",
--   "required": [
--    "Ids"
--   ],
--   "properties": {
--    "Ids": {
--     "type": "array",
--     "items": [
--      {
--       "$ref": "string"
--      }
--     ]
--    }
--   }
--  }
-- }`)
--}
 -
--// clear && go test -v -test.run TestS3 ...swagger
--func TestS3(t *testing.T) {
--	type NestedS3 struct {
--		Id string
--	}
--	type S3 struct {
--		Nested NestedS3
+-	input := map[string]interface{}{
+-		"name":   "Mitchell",
+-		"age":    91,
+-		"emails": []string{"one", "two", "three"},
+-		"extra": map[string]string{
+-			"twitter": "mitchellh",
+-		},
 -	}
--	testJsonFromStruct(t, S3{}, `{
--  "swagger.NestedS3": {
--   "id": "swagger.NestedS3",
--   "required": [
--    "Id"
--   ],
--   "properties": {
--    "Id": {
--     "type": "string"
--    }
--   }
--  },
--  "swagger.S3": {
--   "id": "swagger.S3",
--   "required": [
--    "Nested"
--   ],
--   "properties": {
--    "Nested": {
--     "type": "swagger.NestedS3"
--    }
--   }
--  }
-- }`)
--}
--
--type sample struct {
--	id       string `swagger:"required"` // TODO
--	items    []item
--	rootItem item `json:"root" description:"root desc"`
--}
--
--type item struct {
--	itemName string `json:"name"`
--}
--
--// clear && go test -v -test.run TestSampleToModelAsJson ...swagger
--func TestSampleToModelAsJson(t *testing.T) {
--	testJsonFromStruct(t, sample{items: []item{}}, `{
--  "swagger.item": {
--   "id": "swagger.item",
--   "required": [
--    "name"
--   ],
--   "properties": {
--    "name": {
--     "type": "string"
--    }
--   }
--  },
--  "swagger.sample": {
--   "id": "swagger.sample",
--   "required": [
--    "id",
--    "items",
--    "root"
--   ],
--   "properties": {
--    "id": {
--     "type": "string"
--    },
--    "items": {
--     "type": "array",
--     "items": [
--      {
--       "$ref": "swagger.item"
--      }
--     ]
--    },
--    "root": {
--     "type": "swagger.item",
--     "description": "root desc"
--    }
--   }
--  }
-- }`)
--}
 -
--func TestJsonTags(t *testing.T) {
--	type X struct {
--		A string
--		B string `json:"-"`
--		C int    `json:",string"`
--		D int    `json:","`
+-	var result Person
+-	for i := 0; i < b.N; i++ {
+-		Decode(input, &result)
 -	}
--
--	expected := `{
--  "swagger.X": {
--   "id": "swagger.X",
--   "required": [
--    "A",
--    "C",
--    "D"
--   ],
--   "properties": {
--    "A": {
--     "type": "string"
--    },
--    "C": {
--     "type": "string"
--    },
--    "D": {
--     "type": "integer",
--     "format": "int32"
--    }
--   }
--  }
-- }`
--
--	testJsonFromStruct(t, X{}, expected)
 -}
 -
--func TestJsonTagOmitempty(t *testing.T) {
--	type X struct {
--		A int `json:",omitempty"`
--		B int `json:"C,omitempty"`
+-func Benchmark_DecodeBasic(b *testing.B) {
+-	input := map[string]interface{}{
+-		"vstring": "foo",
+-		"vint":    42,
+-		"Vuint":   42,
+-		"vbool":   true,
+-		"Vfloat":  42.42,
+-		"vsilent": true,
+-		"vdata":   42,
 -	}
 -
--	expected := `{
--  "swagger.X": {
--   "id": "swagger.X",
--   "properties": {
--    "A": {
--     "type": "integer",
--     "format": "int32"
--    },
--    "C": {
--     "type": "integer",
--     "format": "int32"
--    }
--   }
--  }
-- }`
--
--	testJsonFromStruct(t, X{}, expected)
--}
--
--func TestJsonTagName(t *testing.T) {
--	type X struct {
--		A string `json:"B"`
+-	var result Basic
+-	for i := 0; i < b.N; i++ {
+-		Decode(input, &result)
 -	}
--
--	expected := `{
--  "swagger.X": {
--   "id": "swagger.X",
--   "required": [
--    "B"
--   ],
--   "properties": {
--    "B": {
--     "type": "string"
--    }
--   }
--  }
-- }`
--
--	testJsonFromStruct(t, X{}, expected)
 -}
 -
--func TestAnonymousStruct(t *testing.T) {
--	type X struct {
--		A struct {
--			B int
--		}
+-func Benchmark_DecodeEmbedded(b *testing.B) {
+-	input := map[string]interface{}{
+-		"vstring": "foo",
+-		"Basic": map[string]interface{}{
+-			"vstring": "innerfoo",
+-		},
+-		"vunique": "bar",
 -	}
 -
--	expected := `{
--  "swagger.X": {
--   "id": "swagger.X",
--   "required": [
--    "A"
--   ],
--   "properties": {
--    "A": {
--     "type": "swagger.X.A"
--    }
--   }
--  },
--  "swagger.X.A": {
--   "id": "swagger.X.A",
--   "required": [
--    "B"
--   ],
--   "properties": {
--    "B": {
--     "type": "integer",
--     "format": "int32"
--    }
--   }
--  }
-- }`
--
--	testJsonFromStruct(t, X{}, expected)
--}
--
--func TestAnonymousPtrStruct(t *testing.T) {
--	type X struct {
--		A *struct {
--			B int
--		}
+-	var result Embedded
+-	for i := 0; i < b.N; i++ {
+-		Decode(input, &result)
 -	}
--
--	expected := `{
--  "swagger.X": {
--   "id": "swagger.X",
--   "required": [
--    "A"
--   ],
--   "properties": {
--    "A": {
--     "type": "swagger.X.A"
--    }
--   }
--  },
--  "swagger.X.A": {
--   "id": "swagger.X.A",
--   "required": [
--    "B"
--   ],
--   "properties": {
--    "B": {
--     "type": "integer",
--     "format": "int32"
--    }
--   }
--  }
-- }`
--
--	testJsonFromStruct(t, X{}, expected)
 -}
 -
--func TestAnonymousArrayStruct(t *testing.T) {
--	type X struct {
--		A []struct {
--			B int
--		}
--	}
--
--	expected := `{
--  "swagger.X": {
--   "id": "swagger.X",
--   "required": [
--    "A"
--   ],
--   "properties": {
--    "A": {
--     "type": "array",
--     "items": [
--      {
--       "$ref": "swagger.X.A"
--      }
--     ]
--    }
--   }
--  },
--  "swagger.X.A": {
--   "id": "swagger.X.A",
--   "required": [
--    "B"
--   ],
--   "properties": {
--    "B": {
--     "type": "integer",
--     "format": "int32"
--    }
--   }
--  }
-- }`
+-func Benchmark_DecodeTypeConversion(b *testing.B) {
+-	input := map[string]interface{}{
+-		"IntToFloat":    42,
+-		"IntToUint":     42,
+-		"IntToBool":     1,
+-		"IntToString":   42,
+-		"UintToInt":     42,
+-		"UintToFloat":   42,
+-		"UintToBool":    42,
+-		"UintToString":  42,
+-		"BoolToInt":     true,
+-		"BoolToUint":    true,
+-		"BoolToFloat":   true,
+-		"BoolToString":  true,
+-		"FloatToInt":    42.42,
+-		"FloatToUint":   42.42,
+-		"FloatToBool":   42.42,
+-		"FloatToString": 42.42,
+-		"StringToInt":   "42",
+-		"StringToUint":  "42",
+-		"StringToBool":  "1",
+-		"StringToFloat": "42.42",
+-		"SliceToMap":    []interface{}{},
+-		"MapToSlice":    map[string]interface{}{},
+-	}
 -
--	testJsonFromStruct(t, X{}, expected)
+-	var resultStrict TypeConversionResult
+-	for i := 0; i < b.N; i++ {
+-		Decode(input, &resultStrict)
+-	}
 -}
 -
--func TestAnonymousPtrArrayStruct(t *testing.T) {
--	type X struct {
--		A *[]struct {
--			B int
--		}
+-func Benchmark_DecodeMap(b *testing.B) {
+-	input := map[string]interface{}{
+-		"vfoo": "foo",
+-		"vother": map[interface{}]interface{}{
+-			"foo": "foo",
+-			"bar": "bar",
+-		},
 -	}
 -
--	expected := `{
--  "swagger.X": {
--   "id": "swagger.X",
--   "required": [
--    "A"
--   ],
--   "properties": {
--    "A": {
--     "type": "array",
--     "items": [
--      {
--       "$ref": "swagger.X.A"
--      }
--     ]
--    }
--   }
--  },
--  "swagger.X.A": {
--   "id": "swagger.X.A",
--   "required": [
--    "B"
--   ],
--   "properties": {
--    "B": {
--     "type": "integer",
--     "format": "int32"
--    }
--   }
--  }
-- }`
--
--	testJsonFromStruct(t, X{}, expected)
+-	var result Map
+-	for i := 0; i < b.N; i++ {
+-		Decode(input, &result)
+-	}
 -}
 -
--// go test -v -test.run TestEmbeddedStruct_Issue98 ...swagger
--func TestEmbeddedStruct_Issue98(t *testing.T) {
--	type Y struct {
--		A int
+-func Benchmark_DecodeMapOfStruct(b *testing.B) {
+-	input := map[string]interface{}{
+-		"value": map[string]interface{}{
+-			"foo": map[string]string{"vstring": "one"},
+-			"bar": map[string]string{"vstring": "two"},
+-		},
 -	}
--	type X struct {
--		Y
+-
+-	var result MapOfStruct
+-	for i := 0; i < b.N; i++ {
+-		Decode(input, &result)
 -	}
--	testJsonFromStruct(t, X{}, `{
--  "swagger.X": {
--   "id": "swagger.X",
--   "required": [
--    "A"
--   ],
--   "properties": {
--    "A": {
--     "type": "integer",
--     "format": "int32"
--    }
--   }
--  }
-- }`)
 -}
 -
--type Dataset struct {
--	Names []string
--}
+-func Benchmark_DecodeSlice(b *testing.B) {
+-	input := map[string]interface{}{
+-		"vfoo": "foo",
+-		"vbar": []string{"foo", "bar", "baz"},
+-	}
 -
--// clear && go test -v -test.run TestIssue85 ...swagger
--func TestIssue85(t *testing.T) {
--	anon := struct{ Datasets []Dataset }{}
--	testJsonFromStruct(t, anon, `{
--  "struct { Datasets ||swagger.Dataset }": {
--   "id": "struct { Datasets ||swagger.Dataset }",
--   "required": [
--    "Datasets"
--   ],
--   "properties": {
--    "Datasets": {
--     "type": "array",
--     "items": [
--      {
--       "$ref": "swagger.Dataset"
--      }
--     ]
--    }
--   }
--  },
--  "swagger.Dataset": {
--   "id": "swagger.Dataset",
--   "required": [
--    "Names"
--   ],
--   "properties": {
--    "Names": {
--     "type": "array",
--     "items": [
--      {
--       "$ref": "string"
--      }
--     ]
--    }
--   }
--  }
-- }`)
+-	var result Slice
+-	for i := 0; i < b.N; i++ {
+-		Decode(input, &result)
+-	}
 -}
 -
--type File struct {
--	History     []File
--	HistoryPtrs []*File
--}
+-func Benchmark_DecodeSliceOfStruct(b *testing.B) {
+-	input := map[string]interface{}{
+-		"value": []map[string]interface{}{
+-			{"vstring": "one"},
+-			{"vstring": "two"},
+-		},
+-	}
 -
--// go test -v -test.run TestRecursiveStructure ...swagger
--func TestRecursiveStructure(t *testing.T) {
--	testJsonFromStruct(t, File{}, `{
--  "swagger.File": {
--   "id": "swagger.File",
--   "required": [
--    "History",
--    "HistoryPtrs"
--   ],
--   "properties": {
--    "History": {
--     "type": "array",
--     "items": [
--      {
--       "$ref": "swagger.File"
--      }
--     ]
--    },
--    "HistoryPtrs": {
--     "type": "array",
--     "items": [
--      {
--       "$ref": "swagger.File.HistoryPtrs"
--      }
--     ]
--    }
--   }
--  },
--  "swagger.File.HistoryPtrs": {
--   "id": "swagger.File.HistoryPtrs",
--   "properties": {}
--  }
-- }`)
+-	var result SliceOfStruct
+-	for i := 0; i < b.N; i++ {
+-		Decode(input, &result)
+-	}
 -}
 -
--type A1 struct {
--	B struct {
--		Id      int
--		Comment string `json:"comment,omitempty"`
+-func Benchmark_DecodeWeaklyTypedInput(b *testing.B) {
+-	type Person struct {
+-		Name   string
+-		Age    int
+-		Emails []string
 -	}
--}
 -
--// go test -v -test.run TestEmbeddedStructA1 ...swagger
--func TestEmbeddedStructA1(t *testing.T) {
--	testJsonFromStruct(t, A1{}, `{
--  "swagger.A1": {
--   "id": "swagger.A1",
--   "required": [
--    "B"
--   ],
--   "properties": {
--    "B": {
--     "type": "swagger.A1.B"
--    }
--   }
--  },
--  "swagger.A1.B": {
--   "id": "swagger.A1.B",
--   "required": [
--    "Id"
--   ],
--   "properties": {
--    "Id": {
--     "type": "integer",
--     "format": "int32"
--    },
--    "comment": {
--     "type": "string"
--    }
--   }
--  }
-- }`)
--}
+-	// This input can come from anywhere, but typically comes from
+-	// something like decoding JSON, generated by a weakly typed language
+-	// such as PHP.
+-	input := map[string]interface{}{
+-		"name":   123,                      // number => string
+-		"age":    "42",                     // string => number
+-		"emails": map[string]interface{}{}, // empty map => empty array
+-	}
 -
--type A2 struct {
--	C
--}
--type C struct {
--	Id      int    `json:"B"`
--	Comment string `json:"comment,omitempty"`
--	Secure  bool   `json:"secure"`
--}
+-	var result Person
+-	config := &DecoderConfig{
+-		WeaklyTypedInput: true,
+-		Result:           &result,
+-	}
 -
--// go test -v -test.run TestEmbeddedStructA2 ...swagger
--func TestEmbeddedStructA2(t *testing.T) {
--	testJsonFromStruct(t, A2{}, `{
--  "swagger.A2": {
--   "id": "swagger.A2",
--   "required": [
--    "B",
--    "secure"
--   ],
--   "properties": {
--    "B": {
--     "type": "integer",
--     "format": "int32"
--    },
--    "comment": {
--     "type": "string"
--    },
--    "secure": {
--     "type": "boolean"
--    }
--   }
--  }
-- }`)
--}
+-	decoder, err := NewDecoder(config)
+-	if err != nil {
+-		panic(err)
+-	}
 -
--type A3 struct {
--	B D
+-	for i := 0; i < b.N; i++ {
+-		decoder.Decode(input)
+-	}
 -}
 -
--type D struct {
--	Id int
--}
+-func Benchmark_DecodeMetadata(b *testing.B) {
+-	type Person struct {
+-		Name string
+-		Age  int
+-	}
 -
--// clear && go test -v -test.run TestStructA3 ...swagger
--func TestStructA3(t *testing.T) {
--	testJsonFromStruct(t, A3{}, `{
--  "swagger.A3": {
--   "id": "swagger.A3",
--   "required": [
--    "B"
--   ],
--   "properties": {
--    "B": {
--     "type": "swagger.D"
--    }
--   }
--  },
--  "swagger.D": {
--   "id": "swagger.D",
--   "required": [
--    "Id"
--   ],
--   "properties": {
--    "Id": {
--     "type": "integer",
--     "format": "int32"
--    }
--   }
--  }
-- }`)
--}
+-	input := map[string]interface{}{
+-		"name":  "Mitchell",
+-		"age":   91,
+-		"email": "foo at bar.com",
+-	}
 -
--type ObjectId []byte
+-	var md Metadata
+-	var result Person
+-	config := &DecoderConfig{
+-		Metadata: &md,
+-		Result:   &result,
+-	}
 -
--type Region struct {
--	Id   ObjectId `bson:"_id" json:"id"`
--	Name string   `bson:"name" json:"name"`
--	Type string   `bson:"type" json:"type"`
+-	decoder, err := NewDecoder(config)
+-	if err != nil {
+-		panic(err)
+-	}
+-
+-	for i := 0; i < b.N; i++ {
+-		decoder.Decode(input)
+-	}
 -}
 -
--// clear && go test -v -test.run TestRegion_Issue113 ...swagger
--func TestRegion_Issue113(t *testing.T) {
--	testJsonFromStruct(t, []Region{}, `{
--  "integer": {
--   "id": "integer",
--   "properties": {}
--  },
--  "swagger.Region": {
--   "id": "swagger.Region",
--   "required": [
--    "id",
--    "name",
--    "type"
--   ],
--   "properties": {
--    "id": {
--     "type": "array",
--     "items": [
--      {
--       "$ref": "integer"
--      }
--     ]
--    },
--    "name": {
--     "type": "string"
--    },
--    "type": {
--     "type": "string"
--    }
--   }
--  },
--  "||swagger.Region": {
--   "id": "||swagger.Region",
--   "properties": {}
--  }
-- }`)
+-func Benchmark_DecodeMetadataEmbedded(b *testing.B) {
+-	input := map[string]interface{}{
+-		"vstring": "foo",
+-		"vunique": "bar",
+-	}
+-
+-	var md Metadata
+-	var result EmbeddedSquash
+-	config := &DecoderConfig{
+-		Metadata: &md,
+-		Result:   &result,
+-	}
+-
+-	decoder, err := NewDecoder(config)
+-	if err != nil {
+-		b.Fatalf("err: %s", err)
+-	}
+-
+-	for i := 0; i < b.N; i++ {
+-		decoder.Decode(input)
+-	}
 -}
 -
--// clear && go test -v -test.run TestIssue158 ...swagger
--func TestIssue158(t *testing.T) {
--	type Address struct {
--		Country string `json:"country,omitempty"`
+-func Benchmark_DecodeTagged(b *testing.B) {
+-	input := map[string]interface{}{
+-		"foo": "bar",
+-		"bar": "value",
 -	}
 -
--	type Customer struct {
--		Name    string  `json:"name"`
--		Address Address `json:"address"`
+-	var result Tagged
+-	for i := 0; i < b.N; i++ {
+-		Decode(input, &result)
 -	}
--	expected := `{
--  "swagger.Address": {
--   "id": "swagger.Address",
--   "properties": {
--    "country": {
--     "type": "string"
--    }
--   }
--  },
--  "swagger.Customer": {
--   "id": "swagger.Customer",
--   "required": [
--    "name",
--    "address"
--   ],
--   "properties": {
--    "address": {
--     "type": "swagger.Address"
--    },
--    "name": {
--     "type": "string"
--    }
--   }
--  }
-- }`
--	testJsonFromStruct(t, Customer{}, expected)
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/param_sorter.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/param_sorter.go
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_bugs_test.go b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_bugs_test.go
 deleted file mode 100644
-index 813007b..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/param_sorter.go
+index 7054f1a..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_bugs_test.go
 +++ /dev/null
-@@ -1,29 +0,0 @@
--package swagger
+@@ -1,47 +0,0 @@
+-package mapstructure
 -
--// Copyright 2014 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
+-import "testing"
 -
--type ParameterSorter []Parameter
+-// GH-1
+-func TestDecode_NilValue(t *testing.T) {
+-	input := map[string]interface{}{
+-		"vfoo":   nil,
+-		"vother": nil,
+-	}
 -
--func (s ParameterSorter) Len() int {
--	return len(s)
--}
--func (s ParameterSorter) Swap(i, j int) {
--	s[i], s[j] = s[j], s[i]
--}
+-	var result Map
+-	err := Decode(input, &result)
+-	if err != nil {
+-		t.Fatalf("should not error: %s", err)
+-	}
 -
--var typeToSortKey = map[string]string{
--	"path":   "A",
--	"query":  "B",
--	"form":   "C",
--	"header": "D",
--	"body":   "E",
+-	if result.Vfoo != "" {
+-		t.Fatalf("value should be default: %s", result.Vfoo)
+-	}
+-
+-	if result.Vother != nil {
+-		t.Fatalf("Vother should be nil: %s", result.Vother)
+-	}
 -}
 -
--func (s ParameterSorter) Less(i, j int) bool {
--	// use ordering path,query,form,header,body
--	pi := s[i]
--	pj := s[j]
--	return typeToSortKey[pi.ParamType]+pi.Name < typeToSortKey[pj.ParamType]+pj.Name
+-// GH-10
+-func TestDecode_mapInterfaceInterface(t *testing.T) {
+-	input := map[interface{}]interface{}{
+-		"vfoo":   nil,
+-		"vother": nil,
+-	}
+-
+-	var result Map
+-	err := Decode(input, &result)
+-	if err != nil {
+-		t.Fatalf("should not error: %s", err)
+-	}
+-
+-	if result.Vfoo != "" {
+-		t.Fatalf("value should be default: %s", result.Vfoo)
+-	}
+-
+-	if result.Vother != nil {
+-		t.Fatalf("Vother should be nil: %s", result.Vother)
+-	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/param_sorter_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/param_sorter_test.go
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_examples_test.go b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_examples_test.go
 deleted file mode 100644
-index ef6d9eb..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/param_sorter_test.go
+index aa393cc..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_examples_test.go
 +++ /dev/null
-@@ -1,52 +0,0 @@
--package swagger
+@@ -1,169 +0,0 @@
+-package mapstructure
 -
 -import (
--	"bytes"
--	"sort"
--	"testing"
+-	"fmt"
 -)
 -
--func TestSortParameters(t *testing.T) {
--	unsorted := []Parameter{
--		Parameter{
--			Name:      "form2",
--			ParamType: "form",
--		},
--		Parameter{
--			Name:      "header1",
--			ParamType: "header",
--		},
--		Parameter{
--			Name:      "path2",
--			ParamType: "path",
--		},
--		Parameter{
--			Name:      "body",
--			ParamType: "body",
--		},
--		Parameter{
--			Name:      "path1",
--			ParamType: "path",
--		},
--		Parameter{
--			Name:      "form1",
--			ParamType: "form",
--		},
--		Parameter{
--			Name:      "query2",
--			ParamType: "query",
--		},
--		Parameter{
--			Name:      "query1",
--			ParamType: "query",
--		},
+-func ExampleDecode() {
+-	type Person struct {
+-		Name   string
+-		Age    int
+-		Emails []string
+-		Extra  map[string]string
 -	}
--	sort.Sort(ParameterSorter(unsorted))
--	var b bytes.Buffer
--	for _, p := range unsorted {
--		b.WriteString(p.Name + ".")
+-
+-	// This input can come from anywhere, but typically comes from
+-	// something like decoding JSON where we're not quite sure of the
+-	// struct initially.
+-	input := map[string]interface{}{
+-		"name":   "Mitchell",
+-		"age":    91,
+-		"emails": []string{"one", "two", "three"},
+-		"extra": map[string]string{
+-			"twitter": "mitchellh",
+-		},
 -	}
--	if "path1.path2.query1.query2.form1.form2.header1.body." != b.String() {
--		t.Fatal("sorting has changed:" + b.String())
+-
+-	var result Person
+-	err := Decode(input, &result)
+-	if err != nil {
+-		panic(err)
 -	}
+-
+-	fmt.Printf("%#v", result)
+-	// Output:
+-	// mapstructure.Person{Name:"Mitchell", Age:91, Emails:[]string{"one", "two", "three"}, Extra:map[string]string{"twitter":"mitchellh"}}
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/swagger.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/swagger.go
-deleted file mode 100644
-index 9f2fe4b..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/swagger.go
-+++ /dev/null
-@@ -1,184 +0,0 @@
--// Package swagger implements the structures of the Swagger
--// https://github.com/wordnik/swagger-spec/blob/master/versions/1.2.md
--package swagger
 -
--const swaggerVersion = "1.2"
+-func ExampleDecode_errors() {
+-	type Person struct {
+-		Name   string
+-		Age    int
+-		Emails []string
+-		Extra  map[string]string
+-	}
 -
--// 4.3.3 Data Type Fields
--type DataTypeFields struct {
--	Type         *string  `json:"type,omitempty"` // if Ref not used
--	Ref          *string  `json:"$ref,omitempty"` // if Type not used
--	Format       string   `json:"format,omitempty"`
--	DefaultValue Special  `json:"defaultValue,omitempty"`
--	Enum         []string `json:"enum,omitempty"`
--	Minimum      string   `json:"minimum,omitempty"`
--	Maximum      string   `json:"maximum,omitempty"`
--	Items        []Item   `json:"items,omitempty"`
--	UniqueItems  *bool    `json:"uniqueItems,omitempty"`
--}
+-	// This input can come from anywhere, but typically comes from
+-	// something like decoding JSON where we're not quite sure of the
+-	// struct initially.
+-	input := map[string]interface{}{
+-		"name":   123,
+-		"age":    "bad value",
+-		"emails": []int{1, 2, 3},
+-	}
 -
--type Special string
+-	var result Person
+-	err := Decode(input, &result)
+-	if err == nil {
+-		panic("should have an error")
+-	}
 -
--// 4.3.4 Items Object
--type Item struct {
--	Type   *string `json:"type,omitempty"`
--	Ref    *string `json:"$ref,omitempty"`
--	Format string  `json:"format,omitempty"`
+-	fmt.Println(err.Error())
+-	// Output:
+-	// 5 error(s) decoding:
+-	//
+-	// * 'Name' expected type 'string', got unconvertible type 'int'
+-	// * 'Age' expected type 'int', got unconvertible type 'string'
+-	// * 'Emails[0]' expected type 'string', got unconvertible type 'int'
+-	// * 'Emails[1]' expected type 'string', got unconvertible type 'int'
+-	// * 'Emails[2]' expected type 'string', got unconvertible type 'int'
 -}
 -
--// 5.1 Resource Listing
--type ResourceListing struct {
--	SwaggerVersion string          `json:"swaggerVersion"` // e.g 1.2
--	Apis           []Resource      `json:"apis"`
--	ApiVersion     string          `json:"apiVersion"`
--	Info           Info            `json:"info"`
--	Authorizations []Authorization `json:"authorizations,omitempty"`
--}
+-func ExampleDecode_metadata() {
+-	type Person struct {
+-		Name string
+-		Age  int
+-	}
 -
--// 5.1.2 Resource Object
--type Resource struct {
--	Path        string `json:"path"` // relative or absolute, must start with /
--	Description string `json:"description"`
--}
+-	// This input can come from anywhere, but typically comes from
+-	// something like decoding JSON where we're not quite sure of the
+-	// struct initially.
+-	input := map[string]interface{}{
+-		"name":  "Mitchell",
+-		"age":   91,
+-		"email": "foo at bar.com",
+-	}
 -
--// 5.1.3 Info Object
--type Info struct {
--	Title             string `json:"title"`
--	Description       string `json:"description"`
--	TermsOfServiceUrl string `json:"termsOfServiceUrl,omitempty"`
--	Contact           string `json:"contact,omitempty"`
--	License           string `json:"license,omitempty"`
--	LicensUrl         string `json:"licensUrl,omitempty"`
--}
+-	// For metadata, we make a more advanced DecoderConfig so we can
+-	// more finely configure the decoder that is used. In this case, we
+-	// just tell the decoder we want to track metadata.
+-	var md Metadata
+-	var result Person
+-	config := &DecoderConfig{
+-		Metadata: &md,
+-		Result:   &result,
+-	}
 -
--// 5.1.5
--type Authorization struct {
--	Type       string      `json:"type"`
--	PassAs     string      `json:"passAs"`
--	Keyname    string      `json:"keyname"`
--	Scopes     []Scope     `json:"scopes"`
--	GrantTypes []GrantType `json:"grandTypes"`
--}
+-	decoder, err := NewDecoder(config)
+-	if err != nil {
+-		panic(err)
+-	}
 -
--// 5.1.6, 5.2.11
--type Scope struct {
--	// Required. The name of the scope.
--	Scope string `json:"scope"`
--	// Recommended. A short description of the scope.
--	Description string `json:"description"`
--}
+-	if err := decoder.Decode(input); err != nil {
+-		panic(err)
+-	}
 -
--// 5.1.7
--type GrantType struct {
--	Implicit          Implicit          `json:"implicit"`
--	AuthorizationCode AuthorizationCode `json:"authorization_code"`
+-	fmt.Printf("Unused keys: %#v", md.Unused)
+-	// Output:
+-	// Unused keys: []string{"email"}
 -}
 -
--// 5.1.8 Implicit Object
--type Implicit struct {
--	// Required. The login endpoint definition.
--	loginEndpoint LoginEndpoint `json:"loginEndpoint"`
--	// An optional alternative name to standard "access_token" OAuth2 parameter.
--	TokenName string `json:"tokenName"`
+-func ExampleDecode_weaklyTypedInput() {
+-	type Person struct {
+-		Name   string
+-		Age    int
+-		Emails []string
+-	}
+-
+-	// This input can come from anywhere, but typically comes from
+-	// something like decoding JSON, generated by a weakly typed language
+-	// such as PHP.
+-	input := map[string]interface{}{
+-		"name":   123,                      // number => string
+-		"age":    "42",                     // string => number
+-		"emails": map[string]interface{}{}, // empty map => empty array
+-	}
+-
+-	var result Person
+-	config := &DecoderConfig{
+-		WeaklyTypedInput: true,
+-		Result:           &result,
+-	}
+-
+-	decoder, err := NewDecoder(config)
+-	if err != nil {
+-		panic(err)
+-	}
+-
+-	err = decoder.Decode(input)
+-	if err != nil {
+-		panic(err)
+-	}
+-
+-	fmt.Printf("%#v", result)
+-	// Output: mapstructure.Person{Name:"123", Age:42, Emails:[]string{}}
 -}
 -
--// 5.1.9 Authorization Code Object
--type AuthorizationCode struct {
--	TokenRequestEndpoint TokenRequestEndpoint `json:"tokenRequestEndpoint"`
--	TokenEndpoint        TokenEndpoint        `json:"tokenEndpoint"`
+-func ExampleDecode_tags() {
+-	// Note that the mapstructure tags defined in the struct type
+-	// can indicate which fields the values are mapped to.
+-	type Person struct {
+-		Name string `mapstructure:"person_name"`
+-		Age  int    `mapstructure:"person_age"`
+-	}
+-
+-	input := map[string]interface{}{
+-		"person_name": "Mitchell",
+-		"person_age":  91,
+-	}
+-
+-	var result Person
+-	err := Decode(input, &result)
+-	if err != nil {
+-		panic(err)
+-	}
+-
+-	fmt.Printf("%#v", result)
+-	// Output:
+-	// mapstructure.Person{Name:"Mitchell", Age:91}
 -}
+diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_test.go b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_test.go
+deleted file mode 100644
+index 23029c7..0000000
+--- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_test.go
++++ /dev/null
+@@ -1,828 +0,0 @@
+-package mapstructure
 -
--// 5.1.10 Login Endpoint Object
--type LoginEndpoint struct {
--	// Required. The URL of the authorization endpoint for the implicit grant flow. The value SHOULD be in a URL format.
--	Url string `json:"url"`
+-import (
+-	"reflect"
+-	"sort"
+-	"testing"
+-)
+-
+-type Basic struct {
+-	Vstring string
+-	Vint    int
+-	Vuint   uint
+-	Vbool   bool
+-	Vfloat  float64
+-	Vextra  string
+-	vsilent bool
+-	Vdata   interface{}
 -}
 -
--// 5.1.11 Token Request Endpoint Object
--type TokenRequestEndpoint struct {
--	// Required. The URL of the authorization endpoint for the authentication code grant flow. The value SHOULD be in a URL format.
--	Url string `json:"url"`
--	// An optional alternative name to standard "client_id" OAuth2 parameter.
--	ClientIdName string `json:"clientIdName"`
--	// An optional alternative name to the standard "client_secret" OAuth2 parameter.
--	ClientSecretName string `json:"clientSecretName"`
+-type Embedded struct {
+-	Basic
+-	Vunique string
 -}
 -
--// 5.1.12 Token Endpoint Object
--type TokenEndpoint struct {
--	// Required. The URL of the token endpoint for the authentication code grant flow. The value SHOULD be in a URL format.
--	Url string `json:"url"`
--	// An optional alternative name to standard "access_token" OAuth2 parameter.
--	TokenName string `json:"tokenName"`
+-type EmbeddedPointer struct {
+-	*Basic
+-	Vunique string
 -}
 -
--// 5.2 API Declaration
--type ApiDeclaration struct {
--	SwaggerVersion string           `json:"swaggerVersion"`
--	ApiVersion     string           `json:"apiVersion"`
--	BasePath       string           `json:"basePath"`
--	ResourcePath   string           `json:"resourcePath"` // must start with /
--	Apis           []Api            `json:"apis,omitempty"`
--	Models         map[string]Model `json:"models,omitempty"`
--	Produces       []string         `json:"produces,omitempty"`
--	Consumes       []string         `json:"consumes,omitempty"`
--	Authorizations []Authorization  `json:"authorizations,omitempty"`
+-type EmbeddedSquash struct {
+-	Basic   `mapstructure:",squash"`
+-	Vunique string
 -}
 -
--// 5.2.2 API Object
--type Api struct {
--	Path        string      `json:"path"` // relative or absolute, must start with /
--	Description string      `json:"description"`
--	Operations  []Operation `json:"operations,omitempty"`
+-type Map struct {
+-	Vfoo   string
+-	Vother map[string]string
 -}
 -
--// 5.2.3 Operation Object
--type Operation struct {
--	Type             string            `json:"type"`
--	Method           string            `json:"method"`
--	Summary          string            `json:"summary,omitempty"`
--	Notes            string            `json:"notes,omitempty"`
--	Nickname         string            `json:"nickname"`
--	Authorizations   []Authorization   `json:"authorizations,omitempty"`
--	Parameters       []Parameter       `json:"parameters"`
--	ResponseMessages []ResponseMessage `json:"responseMessages,omitempty"` // optional
--	Produces         []string          `json:"produces,omitempty"`
--	Consumes         []string          `json:"consumes,omitempty"`
--	Deprecated       string            `json:"deprecated,omitempty"`
+-type MapOfStruct struct {
+-	Value map[string]Basic
 -}
 -
--// 5.2.4 Parameter Object
--type Parameter struct {
--	DataTypeFields
--	ParamType     string `json:"paramType"` // path,query,body,header,form
--	Name          string `json:"name"`
--	Description   string `json:"description"`
--	Required      bool   `json:"required"`
--	AllowMultiple bool   `json:"allowMultiple"`
+-type Nested struct {
+-	Vfoo string
+-	Vbar Basic
 -}
 -
--// 5.2.5 Response Message Object
--type ResponseMessage struct {
--	Code          int    `json:"code"`
--	Message       string `json:"message"`
--	ResponseModel string `json:"responseModel,omitempty"`
+-type NestedPointer struct {
+-	Vfoo string
+-	Vbar *Basic
 -}
 -
--// 5.2.6, 5.2.7 Models Object
--type Model struct {
--	Id            string                   `json:"id"`
--	Description   string                   `json:"description,omitempty"`
--	Required      []string                 `json:"required,omitempty"`
--	Properties    map[string]ModelProperty `json:"properties"`
--	SubTypes      []string                 `json:"subTypes,omitempty"`
--	Discriminator string                   `json:"discriminator,omitempty"`
+-type Slice struct {
+-	Vfoo string
+-	Vbar []string
 -}
 -
--// 5.2.8 Properties Object
--type ModelProperty struct {
--	DataTypeFields
--	Description string `json:"description,omitempty"`
+-type SliceOfStruct struct {
+-	Value []Basic
 -}
 -
--// 5.2.10
--type Authorizations map[string]Authorization
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/swagger_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/swagger_test.go
-deleted file mode 100644
-index 81e72f6..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/swagger_test.go
-+++ /dev/null
-@@ -1,116 +0,0 @@
--package swagger
+-type Tagged struct {
+-	Extra string `mapstructure:"bar,what,what"`
+-	Value string `mapstructure:"foo"`
+-}
 -
--import (
--	"encoding/json"
--	"fmt"
--	"testing"
+-type TypeConversionResult struct {
+-	IntToFloat         float32
+-	IntToUint          uint
+-	IntToBool          bool
+-	IntToString        string
+-	UintToInt          int
+-	UintToFloat        float32
+-	UintToBool         bool
+-	UintToString       string
+-	BoolToInt          int
+-	BoolToUint         uint
+-	BoolToFloat        float32
+-	BoolToString       string
+-	FloatToInt         int
+-	FloatToUint        uint
+-	FloatToBool        bool
+-	FloatToString      string
+-	SliceUint8ToString string
+-	StringToInt        int
+-	StringToUint       uint
+-	StringToBool       bool
+-	StringToFloat      float32
+-	SliceToMap         map[string]interface{}
+-	MapToSlice         []interface{}
+-}
 -
--	"github.com/emicklei/go-restful"
--)
+-func TestBasicTypes(t *testing.T) {
+-	t.Parallel()
 -
--// go test -v -test.run TestApi ...swagger
--func TestApi(t *testing.T) {
--	value := Api{Path: "/", Description: "Some Path", Operations: []Operation{}}
--	compareJson(t, true, value, `{"path":"/","description":"Some Path"}`)
--}
+-	input := map[string]interface{}{
+-		"vstring": "foo",
+-		"vint":    42,
+-		"Vuint":   42,
+-		"vbool":   true,
+-		"Vfloat":  42.42,
+-		"vsilent": true,
+-		"vdata":   42,
+-	}
 -
--// go test -v -test.run TestServiceToApi ...swagger
--func TestServiceToApi(t *testing.T) {
--	ws := new(restful.WebService)
--	ws.Path("/tests")
--	ws.Consumes(restful.MIME_JSON)
--	ws.Produces(restful.MIME_XML)
--	ws.Route(ws.GET("/all").To(dummy).Writes(sample{}))
--	ws.ApiVersion("1.2.3")
--	cfg := Config{
--		WebServicesUrl: "http://here.com",
--		ApiPath:        "/apipath",
--		WebServices:    []*restful.WebService{ws}}
--	sws := newSwaggerService(cfg)
--	decl := sws.composeDeclaration(ws, "/tests")
--	data, err := json.MarshalIndent(decl, " ", " ")
+-	var result Basic
+-	err := Decode(input, &result)
 -	if err != nil {
--		t.Fatal(err.Error())
+-		t.Errorf("got an err: %s", err.Error())
+-		t.FailNow()
 -	}
--	// for visual inspection only
--	fmt.Println(string(data))
--}
 -
--func dummy(i *restful.Request, o *restful.Response) {}
+-	if result.Vstring != "foo" {
+-		t.Errorf("vstring value should be 'foo': %#v", result.Vstring)
+-	}
 -
--// go test -v -test.run TestIssue78 ...swagger
--type Response struct {
--	Code  int
--	Users *[]User
--	Items *[]TestItem
--}
--type User struct {
--	Id, Name string
--}
--type TestItem struct {
--	Id, Name string
--}
+-	if result.Vint != 42 {
+-		t.Errorf("vint value should be 42: %#v", result.Vint)
+-	}
 -
--// clear && go test -v -test.run TestComposeResponseMessages ...swagger
--func TestComposeResponseMessages(t *testing.T) {
--	responseErrors := map[int]restful.ResponseError{}
--	responseErrors[400] = restful.ResponseError{Code: 400, Message: "Bad Request", Model: TestItem{}}
--	route := restful.Route{ResponseErrors: responseErrors}
--	decl := new(ApiDeclaration)
--	decl.Models = map[string]Model{}
--	msgs := composeResponseMessages(route, decl)
--	if msgs[0].ResponseModel != "swagger.TestItem" {
--		t.Errorf("got %s want swagger.TestItem", msgs[0].ResponseModel)
+-	if result.Vuint != 42 {
+-		t.Errorf("vuint value should be 42: %#v", result.Vuint)
 -	}
--}
 -
--// clear && go test -v -test.run TestComposeResponseMessageArray ...swagger
--func TestComposeResponseMessageArray(t *testing.T) {
--	responseErrors := map[int]restful.ResponseError{}
--	responseErrors[400] = restful.ResponseError{Code: 400, Message: "Bad Request", Model: []TestItem{}}
--	route := restful.Route{ResponseErrors: responseErrors}
--	decl := new(ApiDeclaration)
--	decl.Models = map[string]Model{}
--	msgs := composeResponseMessages(route, decl)
--	if msgs[0].ResponseModel != "array[swagger.TestItem]" {
--		t.Errorf("got %s want swagger.TestItem", msgs[0].ResponseModel)
+-	if result.Vbool != true {
+-		t.Errorf("vbool value should be true: %#v", result.Vbool)
 -	}
--}
 -
--func TestIssue78(t *testing.T) {
--	sws := newSwaggerService(Config{})
--	models := map[string]Model{}
--	sws.addModelFromSampleTo(&Operation{}, true, Response{Items: &[]TestItem{}}, models)
--	model, ok := models["swagger.Response"]
--	if !ok {
--		t.Fatal("missing response model")
+-	if result.Vfloat != 42.42 {
+-		t.Errorf("vfloat value should be 42.42: %#v", result.Vfloat)
 -	}
--	if "swagger.Response" != model.Id {
--		t.Fatal("wrong model id:" + model.Id)
+-
+-	if result.Vextra != "" {
+-		t.Errorf("vextra value should be empty: %#v", result.Vextra)
 -	}
--	code, ok := model.Properties["Code"]
--	if !ok {
--		t.Fatal("missing code")
+-
+-	if result.vsilent != false {
+-		t.Error("vsilent should not be set, it is unexported")
 -	}
--	if "integer" != *code.Type {
--		t.Fatal("wrong code type:" + *code.Type)
+-
+-	if result.Vdata != 42 {
+-		t.Error("vdata should be valid")
 -	}
--	items, ok := model.Properties["Items"]
--	if !ok {
--		t.Fatal("missing items")
+-}
+-
+-func TestBasic_IntWithFloat(t *testing.T) {
+-	t.Parallel()
+-
+-	input := map[string]interface{}{
+-		"vint": float64(42),
 -	}
--	if "array" != *items.Type {
--		t.Fatal("wrong items type:" + *items.Type)
+-
+-	var result Basic
+-	err := Decode(input, &result)
+-	if err != nil {
+-		t.Fatalf("got an err: %s", err)
 -	}
--	items_items := items.Items
--	if len(items_items) == 0 {
--		t.Fatal("missing items->items")
+-}
+-
+-func TestDecode_Embedded(t *testing.T) {
+-	t.Parallel()
+-
+-	input := map[string]interface{}{
+-		"vstring": "foo",
+-		"Basic": map[string]interface{}{
+-			"vstring": "innerfoo",
+-		},
+-		"vunique": "bar",
 -	}
--	ref := items_items[0].Ref
--	if ref == nil {
--		t.Fatal("missing $ref")
+-
+-	var result Embedded
+-	err := Decode(input, &result)
+-	if err != nil {
+-		t.Fatalf("got an err: %s", err.Error())
 -	}
--	if *ref != "swagger.TestItem" {
--		t.Fatal("wrong $ref:" + *ref)
+-
+-	if result.Vstring != "innerfoo" {
+-		t.Errorf("vstring value should be 'innerfoo': %#v", result.Vstring)
+-	}
+-
+-	if result.Vunique != "bar" {
+-		t.Errorf("vunique value should be 'bar': %#v", result.Vunique)
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/swagger_webservice.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/swagger_webservice.go
-deleted file mode 100644
-index 04da0a1..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/swagger_webservice.go
-+++ /dev/null
-@@ -1,353 +0,0 @@
--package swagger
 -
--import (
--	"fmt"
--	"github.com/emicklei/go-restful"
--	// "github.com/emicklei/hopwatch"
--	"log"
--	"net/http"
--	"reflect"
--	"sort"
--	"strings"
--)
+-func TestDecode_EmbeddedPointer(t *testing.T) {
+-	t.Parallel()
 -
--type SwaggerService struct {
--	config            Config
--	apiDeclarationMap map[string]ApiDeclaration
--}
+-	input := map[string]interface{}{
+-		"vstring": "foo",
+-		"Basic": map[string]interface{}{
+-			"vstring": "innerfoo",
+-		},
+-		"vunique": "bar",
+-	}
 -
--func newSwaggerService(config Config) *SwaggerService {
--	return &SwaggerService{
--		config:            config,
--		apiDeclarationMap: map[string]ApiDeclaration{}}
+-	var result EmbeddedPointer
+-	err := Decode(input, &result)
+-	if err == nil {
+-		t.Fatal("should get error")
+-	}
 -}
 -
--// LogInfo is the function that is called when this package needs to log. It defaults to log.Printf
--var LogInfo = log.Printf
+-func TestDecode_EmbeddedSquash(t *testing.T) {
+-	t.Parallel()
 -
--// InstallSwaggerService add the WebService that provides the API documentation of all services
--// conform the Swagger documentation specifcation. (https://github.com/wordnik/swagger-core/wiki).
--func InstallSwaggerService(aSwaggerConfig Config) {
--	RegisterSwaggerService(aSwaggerConfig, restful.DefaultContainer)
--}
+-	input := map[string]interface{}{
+-		"vstring": "foo",
+-		"vunique": "bar",
+-	}
 -
--// RegisterSwaggerService add the WebService that provides the API documentation of all services
--// conform the Swagger documentation specifcation. (https://github.com/wordnik/swagger-core/wiki).
--func RegisterSwaggerService(config Config, wsContainer *restful.Container) {
--	sws := newSwaggerService(config)
--	ws := new(restful.WebService)
--	ws.Path(config.ApiPath)
--	ws.Produces(restful.MIME_JSON)
--	if config.DisableCORS {
--		ws.Filter(enableCORS)
+-	var result EmbeddedSquash
+-	err := Decode(input, &result)
+-	if err != nil {
+-		t.Fatalf("got an err: %s", err.Error())
 -	}
--	ws.Route(ws.GET("/").To(sws.getListing))
--	ws.Route(ws.GET("/{a}").To(sws.getDeclarations))
--	ws.Route(ws.GET("/{a}/{b}").To(sws.getDeclarations))
--	ws.Route(ws.GET("/{a}/{b}/{c}").To(sws.getDeclarations))
--	ws.Route(ws.GET("/{a}/{b}/{c}/{d}").To(sws.getDeclarations))
--	ws.Route(ws.GET("/{a}/{b}/{c}/{d}/{e}").To(sws.getDeclarations))
--	ws.Route(ws.GET("/{a}/{b}/{c}/{d}/{e}/{f}").To(sws.getDeclarations))
--	ws.Route(ws.GET("/{a}/{b}/{c}/{d}/{e}/{f}/{g}").To(sws.getDeclarations))
--	LogInfo("[restful/swagger] listing is available at %v%v", config.WebServicesUrl, config.ApiPath)
--	wsContainer.Add(ws)
 -
--	// Build all ApiDeclarations
--	for _, each := range config.WebServices {
--		rootPath := each.RootPath()
--		// skip the api service itself
--		if rootPath != config.ApiPath {
--			if rootPath == "" || rootPath == "/" {
--				// use routes
--				for _, route := range each.Routes() {
--					entry := staticPathFromRoute(route)
--					_, exists := sws.apiDeclarationMap[entry]
--					if !exists {
--						sws.apiDeclarationMap[entry] = sws.composeDeclaration(each, entry)
--					}
--				}
--			} else { // use root path
--				sws.apiDeclarationMap[each.RootPath()] = sws.composeDeclaration(each, each.RootPath())
--			}
--		}
+-	if result.Vstring != "foo" {
+-		t.Errorf("vstring value should be 'foo': %#v", result.Vstring)
 -	}
 -
--	// Check paths for UI serving
--	if config.StaticHandler == nil && config.SwaggerFilePath != "" && config.SwaggerPath != "" {
--		swaggerPathSlash := config.SwaggerPath
--		// path must end with slash /
--		if "/" != config.SwaggerPath[len(config.SwaggerPath)-1:] {
--			LogInfo("[restful/swagger] use corrected SwaggerPath ; must end with slash (/)")
--			swaggerPathSlash += "/"
--		}
+-	if result.Vunique != "bar" {
+-		t.Errorf("vunique value should be 'bar': %#v", result.Vunique)
+-	}
+-}
 -
--		LogInfo("[restful/swagger] %v%v is mapped to folder %v", config.WebServicesUrl, swaggerPathSlash, config.SwaggerFilePath)
--		wsContainer.Handle(swaggerPathSlash, http.StripPrefix(swaggerPathSlash, http.FileServer(http.Dir(config.SwaggerFilePath))))
+-func TestDecode_DecodeHook(t *testing.T) {
+-	t.Parallel()
 -
--		//if we define a custom static handler use it
--	} else if config.StaticHandler != nil && config.SwaggerPath != "" {
--		swaggerPathSlash := config.SwaggerPath
--		// path must end with slash /
--		if "/" != config.SwaggerPath[len(config.SwaggerPath)-1:] {
--			LogInfo("[restful/swagger] use corrected SwaggerFilePath ; must end with slash (/)")
--			swaggerPathSlash += "/"
+-	input := map[string]interface{}{
+-		"vint": "WHAT",
+-	}
 -
+-	decodeHook := func(from reflect.Kind, to reflect.Kind, v interface{}) (interface{}, error) {
+-		if from == reflect.String && to != reflect.String {
+-			return 5, nil
 -		}
--		LogInfo("[restful/swagger] %v%v is mapped to custom Handler %T", config.WebServicesUrl, swaggerPathSlash, config.StaticHandler)
--		wsContainer.Handle(swaggerPathSlash, config.StaticHandler)
 -
--	} else {
--		LogInfo("[restful/swagger] Swagger(File)Path is empty ; no UI is served")
+-		return v, nil
 -	}
--}
 -
--func staticPathFromRoute(r restful.Route) string {
--	static := r.Path
--	bracket := strings.Index(static, "{")
--	if bracket <= 1 { // result cannot be empty
--		return static
+-	var result Basic
+-	config := &DecoderConfig{
+-		DecodeHook: decodeHook,
+-		Result:     &result,
 -	}
--	if bracket != -1 {
--		static = r.Path[:bracket]
+-
+-	decoder, err := NewDecoder(config)
+-	if err != nil {
+-		t.Fatalf("err: %s", err)
 -	}
--	if strings.HasSuffix(static, "/") {
--		return static[:len(static)-1]
--	} else {
--		return static
+-
+-	err = decoder.Decode(input)
+-	if err != nil {
+-		t.Fatalf("got an err: %s", err)
 -	}
--}
 -
--func enableCORS(req *restful.Request, resp *restful.Response, chain *restful.FilterChain) {
--	if origin := req.HeaderParameter(restful.HEADER_Origin); origin != "" {
--		// prevent duplicate header
--		if len(resp.Header().Get(restful.HEADER_AccessControlAllowOrigin)) == 0 {
--			resp.AddHeader(restful.HEADER_AccessControlAllowOrigin, origin)
--		}
+-	if result.Vint != 5 {
+-		t.Errorf("vint should be 5: %#v", result.Vint)
 -	}
--	chain.ProcessFilter(req, resp)
 -}
 -
--func (sws SwaggerService) getListing(req *restful.Request, resp *restful.Response) {
--	listing := ResourceListing{SwaggerVersion: swaggerVersion}
--	for k, v := range sws.apiDeclarationMap {
--		ref := Resource{Path: k}
--		if len(v.Apis) > 0 { // use description of first (could still be empty)
--			ref.Description = v.Apis[0].Description
--		}
--		listing.Apis = append(listing.Apis, ref)
+-func TestDecode_Nil(t *testing.T) {
+-	t.Parallel()
+-
+-	var input interface{} = nil
+-	result := Basic{
+-		Vstring: "foo",
+-	}
+-
+-	err := Decode(input, &result)
+-	if err != nil {
+-		t.Fatalf("err: %s", err)
+-	}
+-
+-	if result.Vstring != "foo" {
+-		t.Fatalf("bad: %#v", result.Vstring)
 -	}
--	resp.WriteAsJson(listing)
 -}
 -
--func (sws SwaggerService) getDeclarations(req *restful.Request, resp *restful.Response) {
--	decl := sws.apiDeclarationMap[composeRootPath(req)]
--	// unless WebServicesUrl is given
--	if len(sws.config.WebServicesUrl) == 0 {
--		// update base path from the actual request
--		// TODO how to detect https? assume http for now
--		(&decl).BasePath = fmt.Sprintf("http://%s", req.Request.Host)
+-func TestDecode_NonStruct(t *testing.T) {
+-	t.Parallel()
+-
+-	input := map[string]interface{}{
+-		"foo": "bar",
+-		"bar": "baz",
+-	}
+-
+-	var result map[string]string
+-	err := Decode(input, &result)
+-	if err != nil {
+-		t.Fatalf("err: %s", err)
+-	}
+-
+-	if result["foo"] != "bar" {
+-		t.Fatal("foo is not bar")
 -	}
--	resp.WriteAsJson(decl)
 -}
 -
--func (sws SwaggerService) composeDeclaration(ws *restful.WebService, pathPrefix string) ApiDeclaration {
--	decl := ApiDeclaration{
--		SwaggerVersion: swaggerVersion,
--		BasePath:       sws.config.WebServicesUrl,
--		ResourcePath:   ws.RootPath(),
--		Models:         map[string]Model{},
--		ApiVersion:     ws.Version()}
+-func TestDecode_TypeConversion(t *testing.T) {
+-	input := map[string]interface{}{
+-		"IntToFloat":         42,
+-		"IntToUint":          42,
+-		"IntToBool":          1,
+-		"IntToString":        42,
+-		"UintToInt":          42,
+-		"UintToFloat":        42,
+-		"UintToBool":         42,
+-		"UintToString":       42,
+-		"BoolToInt":          true,
+-		"BoolToUint":         true,
+-		"BoolToFloat":        true,
+-		"BoolToString":       true,
+-		"FloatToInt":         42.42,
+-		"FloatToUint":        42.42,
+-		"FloatToBool":        42.42,
+-		"FloatToString":      42.42,
+-		"SliceUint8ToString": []uint8("foo"),
+-		"StringToInt":        "42",
+-		"StringToUint":       "42",
+-		"StringToBool":       "1",
+-		"StringToFloat":      "42.42",
+-		"SliceToMap":         []interface{}{},
+-		"MapToSlice":         map[string]interface{}{},
+-	}
 -
--	// collect any path parameters
--	rootParams := []Parameter{}
--	for _, param := range ws.PathParameters() {
--		rootParams = append(rootParams, asSwaggerParameter(param.Data()))
+-	expectedResultStrict := TypeConversionResult{
+-		IntToFloat:  42.0,
+-		IntToUint:   42,
+-		UintToInt:   42,
+-		UintToFloat: 42,
+-		BoolToInt:   0,
+-		BoolToUint:  0,
+-		BoolToFloat: 0,
+-		FloatToInt:  42,
+-		FloatToUint: 42,
 -	}
--	// aggregate by path
--	pathToRoutes := map[string][]restful.Route{}
--	for _, other := range ws.Routes() {
--		if strings.HasPrefix(other.Path, pathPrefix) {
--			routes := pathToRoutes[other.Path]
--			pathToRoutes[other.Path] = append(routes, other)
--		}
+-
+-	expectedResultWeak := TypeConversionResult{
+-		IntToFloat:         42.0,
+-		IntToUint:          42,
+-		IntToBool:          true,
+-		IntToString:        "42",
+-		UintToInt:          42,
+-		UintToFloat:        42,
+-		UintToBool:         true,
+-		UintToString:       "42",
+-		BoolToInt:          1,
+-		BoolToUint:         1,
+-		BoolToFloat:        1,
+-		BoolToString:       "1",
+-		FloatToInt:         42,
+-		FloatToUint:        42,
+-		FloatToBool:        true,
+-		FloatToString:      "42.42",
+-		SliceUint8ToString: "foo",
+-		StringToInt:        42,
+-		StringToUint:       42,
+-		StringToBool:       true,
+-		StringToFloat:      42.42,
+-		SliceToMap:         map[string]interface{}{},
+-		MapToSlice:         []interface{}{},
 -	}
--	for path, routes := range pathToRoutes {
--		api := Api{Path: strings.TrimSuffix(path, "/"), Description: ws.Documentation()}
--		for _, route := range routes {
--			operation := Operation{
--				Method:           route.Method,
--				Summary:          route.Doc,
--				Type:             asDataType(route.WriteSample),
--				Parameters:       []Parameter{},
--				Nickname:         route.Operation,
--				ResponseMessages: composeResponseMessages(route, &decl)}
 -
--			operation.Consumes = route.Consumes
--			operation.Produces = route.Produces
+-	// Test strict type conversion
+-	var resultStrict TypeConversionResult
+-	err := Decode(input, &resultStrict)
+-	if err == nil {
+-		t.Errorf("should return an error")
+-	}
+-	if !reflect.DeepEqual(resultStrict, expectedResultStrict) {
+-		t.Errorf("expected %v, got: %v", expectedResultStrict, resultStrict)
+-	}
 -
--			// share root params if any
--			for _, swparam := range rootParams {
--				operation.Parameters = append(operation.Parameters, swparam)
--			}
--			// route specific params
--			for _, param := range route.ParameterDocs {
--				operation.Parameters = append(operation.Parameters, asSwaggerParameter(param.Data()))
--			}
--			// sort parameters
--			sort.Sort(ParameterSorter(operation.Parameters))
+-	// Test weak type conversion
+-	var decoder *Decoder
+-	var resultWeak TypeConversionResult
 -
--			sws.addModelsFromRouteTo(&operation, route, &decl)
--			api.Operations = append(api.Operations, operation)
--		}
--		decl.Apis = append(decl.Apis, api)
+-	config := &DecoderConfig{
+-		WeaklyTypedInput: true,
+-		Result:           &resultWeak,
 -	}
--	return decl
--}
 -
--// composeResponseMessages takes the ResponseErrors (if any) and creates ResponseMessages from them.
--func composeResponseMessages(route restful.Route, decl *ApiDeclaration) (messages []ResponseMessage) {
--	if route.ResponseErrors == nil {
--		return messages
+-	decoder, err = NewDecoder(config)
+-	if err != nil {
+-		t.Fatalf("err: %s", err)
 -	}
--	// sort by code
--	codes := sort.IntSlice{}
--	for code, _ := range route.ResponseErrors {
--		codes = append(codes, code)
+-
+-	err = decoder.Decode(input)
+-	if err != nil {
+-		t.Fatalf("got an err: %s", err)
 -	}
--	codes.Sort()
--	for _, code := range codes {
--		each := route.ResponseErrors[code]
--		message := ResponseMessage{
--			Code:    code,
--			Message: each.Message,
--		}
--		if each.Model != nil {
--			st := reflect.TypeOf(each.Model)
--			isCollection, st := detectCollectionType(st)
--			modelName := modelBuilder{}.keyFrom(st)
--			if isCollection {
--				modelName = "array[" + modelName + "]"
--			}
--			modelBuilder{decl.Models}.addModel(st, "")
--			// reference the model
--			message.ResponseModel = modelName
--		}
--		messages = append(messages, message)
+-
+-	if !reflect.DeepEqual(resultWeak, expectedResultWeak) {
+-		t.Errorf("expected \n%#v, got: \n%#v", expectedResultWeak, resultWeak)
 -	}
--	return
 -}
 -
--// addModelsFromRoute takes any read or write sample from the Route and creates a Swagger model from it.
--func (sws SwaggerService) addModelsFromRouteTo(operation *Operation, route restful.Route, decl *ApiDeclaration) {
--	if route.ReadSample != nil {
--		sws.addModelFromSampleTo(operation, false, route.ReadSample, decl.Models)
+-func TestDecoder_ErrorUnused(t *testing.T) {
+-	t.Parallel()
+-
+-	input := map[string]interface{}{
+-		"vstring": "hello",
+-		"foo":     "bar",
 -	}
--	if route.WriteSample != nil {
--		sws.addModelFromSampleTo(operation, true, route.WriteSample, decl.Models)
+-
+-	var result Basic
+-	config := &DecoderConfig{
+-		ErrorUnused: true,
+-		Result:      &result,
 -	}
--}
 -
--func detectCollectionType(st reflect.Type) (bool, reflect.Type) {
--	isCollection := false
--	if st.Kind() == reflect.Slice || st.Kind() == reflect.Array {
--		st = st.Elem()
--		isCollection = true
--	} else {
--		if st.Kind() == reflect.Ptr {
--			if st.Elem().Kind() == reflect.Slice || st.Elem().Kind() == reflect.Array {
--				st = st.Elem().Elem()
--				isCollection = true
--			}
--		}
+-	decoder, err := NewDecoder(config)
+-	if err != nil {
+-		t.Fatalf("err: %s", err)
 -	}
--	return isCollection, st
--}
 -
--// addModelFromSample creates and adds (or overwrites) a Model from a sample resource
--func (sws SwaggerService) addModelFromSampleTo(operation *Operation, isResponse bool, sample interface{}, models map[string]Model) {
--	st := reflect.TypeOf(sample)
--	isCollection, st := detectCollectionType(st)
--	modelName := modelBuilder{}.keyFrom(st)
--	if isResponse {
--		if isCollection {
--			modelName = "array[" + modelName + "]"
--		}
--		operation.Type = modelName
+-	err = decoder.Decode(input)
+-	if err == nil {
+-		t.Fatal("expected error")
 -	}
--	modelBuilder{models}.addModel(reflect.TypeOf(sample), "")
 -}
 -
--func asSwaggerParameter(param restful.ParameterData) Parameter {
--	return Parameter{
--		DataTypeFields: DataTypeFields{
--			Type:   &param.DataType,
--			Format: asFormat(param.DataType),
--		},
--		Name:        param.Name,
--		Description: param.Description,
--		ParamType:   asParamType(param.Kind),
+-func TestMap(t *testing.T) {
+-	t.Parallel()
 -
--		Required: param.Required}
--}
+-	input := map[string]interface{}{
+-		"vfoo": "foo",
+-		"vother": map[interface{}]interface{}{
+-			"foo": "foo",
+-			"bar": "bar",
+-		},
+-	}
 -
--// Between 1..7 path parameters is supported
--func composeRootPath(req *restful.Request) string {
--	path := "/" + req.PathParameter("a")
--	b := req.PathParameter("b")
--	if b == "" {
--		return path
+-	var result Map
+-	err := Decode(input, &result)
+-	if err != nil {
+-		t.Fatalf("got an error: %s", err)
 -	}
--	path = path + "/" + b
--	c := req.PathParameter("c")
--	if c == "" {
--		return path
+-
+-	if result.Vfoo != "foo" {
+-		t.Errorf("vfoo value should be 'foo': %#v", result.Vfoo)
 -	}
--	path = path + "/" + c
--	d := req.PathParameter("d")
--	if d == "" {
--		return path
+-
+-	if result.Vother == nil {
+-		t.Fatal("vother should not be nil")
 -	}
--	path = path + "/" + d
--	e := req.PathParameter("e")
--	if e == "" {
--		return path
+-
+-	if len(result.Vother) != 2 {
+-		t.Error("vother should have two items")
 -	}
--	path = path + "/" + e
--	f := req.PathParameter("f")
--	if f == "" {
--		return path
+-
+-	if result.Vother["foo"] != "foo" {
+-		t.Errorf("'foo' key should be foo, got: %#v", result.Vother["foo"])
 -	}
--	path = path + "/" + f
--	g := req.PathParameter("g")
--	if g == "" {
--		return path
+-
+-	if result.Vother["bar"] != "bar" {
+-		t.Errorf("'bar' key should be bar, got: %#v", result.Vother["bar"])
 -	}
--	return path + "/" + g
 -}
 -
--func asFormat(name string) string {
--	return "" // TODO
--}
+-func TestMapOfStruct(t *testing.T) {
+-	t.Parallel()
 -
--func asParamType(kind int) string {
--	switch {
--	case kind == restful.PathParameterKind:
--		return "path"
--	case kind == restful.QueryParameterKind:
--		return "query"
--	case kind == restful.BodyParameterKind:
--		return "body"
--	case kind == restful.HeaderParameterKind:
--		return "header"
--	case kind == restful.FormParameterKind:
--		return "form"
+-	input := map[string]interface{}{
+-		"value": map[string]interface{}{
+-			"foo": map[string]string{"vstring": "one"},
+-			"bar": map[string]string{"vstring": "two"},
+-		},
 -	}
--	return ""
--}
 -
--func asDataType(any interface{}) string {
--	if any == nil {
--		return "void"
+-	var result MapOfStruct
+-	err := Decode(input, &result)
+-	if err != nil {
+-		t.Fatalf("got an err: %s", err)
 -	}
--	return reflect.TypeOf(any).Name()
--}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/utils_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/utils_test.go
-deleted file mode 100644
-index 6127bd5..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/swagger/utils_test.go
-+++ /dev/null
-@@ -1,70 +0,0 @@
--package swagger
 -
--import (
--	"bytes"
--	"encoding/json"
--	"fmt"
--	"reflect"
--	"strings"
--	"testing"
--)
+-	if result.Value == nil {
+-		t.Fatal("value should not be nil")
+-	}
 -
--func testJsonFromStruct(t *testing.T, sample interface{}, expectedJson string) {
--	compareJson(t, false, modelsFromStruct(sample), expectedJson)
--}
+-	if len(result.Value) != 2 {
+-		t.Error("value should have two items")
+-	}
 -
--func modelsFromStruct(sample interface{}) map[string]Model {
--	models := map[string]Model{}
--	builder := modelBuilder{models}
--	builder.addModel(reflect.TypeOf(sample), "")
--	return models
+-	if result.Value["foo"].Vstring != "one" {
+-		t.Errorf("foo value should be 'one', got: %s", result.Value["foo"].Vstring)
+-	}
+-
+-	if result.Value["bar"].Vstring != "two" {
+-		t.Errorf("bar value should be 'two', got: %s", result.Value["bar"].Vstring)
+-	}
 -}
 -
--func compareJson(t *testing.T, flatCompare bool, value interface{}, expectedJsonAsString string) {
--	var output []byte
--	var err error
--	if flatCompare {
--		output, err = json.Marshal(value)
--	} else {
--		output, err = json.MarshalIndent(value, " ", " ")
+-func TestNestedType(t *testing.T) {
+-	t.Parallel()
+-
+-	input := map[string]interface{}{
+-		"vfoo": "foo",
+-		"vbar": map[string]interface{}{
+-			"vstring": "foo",
+-			"vint":    42,
+-			"vbool":   true,
+-		},
 -	}
+-
+-	var result Nested
+-	err := Decode(input, &result)
 -	if err != nil {
--		t.Error(err.Error())
--		return
+-		t.Fatalf("got an err: %s", err.Error())
 -	}
--	actual := string(output)
--	if actual != expectedJsonAsString {
--		t.Errorf("First mismatch JSON doc at line:%d", indexOfNonMatchingLine(actual, expectedJsonAsString))
--		// Use simple fmt to create a pastable output :-)
--		fmt.Println("---- expected -----")
--		fmt.Println(withLineNumbers(expectedJsonAsString))
--		fmt.Println("---- actual -----")
--		fmt.Println(withLineNumbers(actual))
--		fmt.Println("---- raw -----")
--		fmt.Println(actual)
+-
+-	if result.Vfoo != "foo" {
+-		t.Errorf("vfoo value should be 'foo': %#v", result.Vfoo)
 -	}
--}
 -
--func indexOfNonMatchingLine(actual, expected string) int {
--	a := strings.Split(actual, "\n")
--	e := strings.Split(expected, "\n")
--	size := len(a)
--	if len(e) < len(a) {
--		size = len(e)
+-	if result.Vbar.Vstring != "foo" {
+-		t.Errorf("vstring value should be 'foo': %#v", result.Vbar.Vstring)
 -	}
--	for i := 0; i < size; i++ {
--		if a[i] != e[i] {
--			return i
--		}
+-
+-	if result.Vbar.Vint != 42 {
+-		t.Errorf("vint value should be 42: %#v", result.Vbar.Vint)
 -	}
--	return -1
--}
 -
--func withLineNumbers(content string) string {
--	var buffer bytes.Buffer
--	lines := strings.Split(content, "\n")
--	for i, each := range lines {
--		buffer.WriteString(fmt.Sprintf("%d:%s\n", i, each))
+-	if result.Vbar.Vbool != true {
+-		t.Errorf("vbool value should be true: %#v", result.Vbar.Vbool)
+-	}
+-
+-	if result.Vbar.Vextra != "" {
+-		t.Errorf("vextra value should be empty: %#v", result.Vbar.Vextra)
 -	}
--	return buffer.String()
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/web_service.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/web_service.go
-deleted file mode 100644
-index f3c10e0..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/web_service.go
-+++ /dev/null
-@@ -1,190 +0,0 @@
--package restful
 -
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
+-func TestNestedTypePointer(t *testing.T) {
+-	t.Parallel()
 -
--import "log"
+-	input := map[string]interface{}{
+-		"vfoo": "foo",
+-		"vbar": &map[string]interface{}{
+-			"vstring": "foo",
+-			"vint":    42,
+-			"vbool":   true,
+-		},
+-	}
 -
--// WebService holds a collection of Route values that bind a Http Method + URL Path to a function.
--type WebService struct {
--	rootPath       string
--	pathExpr       *pathExpression // cached compilation of rootPath as RegExp
--	routes         []Route
--	produces       []string
--	consumes       []string
--	pathParameters []*Parameter
--	filters        []FilterFunction
--	documentation  string
--	apiVersion     string
--}
+-	var result NestedPointer
+-	err := Decode(input, &result)
+-	if err != nil {
+-		t.Fatalf("got an err: %s", err.Error())
+-	}
 -
--// compilePathExpression ensures that the path is compiled into a RegEx for those routers that need it.
--func (w *WebService) compilePathExpression() {
--	if len(w.rootPath) == 0 {
--		w.Path("/") // lazy initialize path
+-	if result.Vfoo != "foo" {
+-		t.Errorf("vfoo value should be 'foo': %#v", result.Vfoo)
 -	}
--	compiled, err := newPathExpression(w.rootPath)
--	if err != nil {
--		log.Fatalf("[restful] invalid path:%s because:%v", w.rootPath, err)
+-
+-	if result.Vbar.Vstring != "foo" {
+-		t.Errorf("vstring value should be 'foo': %#v", result.Vbar.Vstring)
 -	}
--	w.pathExpr = compiled
--}
 -
--// ApiVersion sets the API version for documentation purposes.
--func (w *WebService) ApiVersion(apiVersion string) *WebService {
--	w.apiVersion = apiVersion
--	return w
--}
+-	if result.Vbar.Vint != 42 {
+-		t.Errorf("vint value should be 42: %#v", result.Vbar.Vint)
+-	}
 -
--// Version returns the API version for documentation purposes.
--func (w WebService) Version() string { return w.apiVersion }
+-	if result.Vbar.Vbool != true {
+-		t.Errorf("vbool value should be true: %#v", result.Vbar.Vbool)
+-	}
 -
--// Path specifies the root URL template path of the WebService.
--// All Routes will be relative to this path.
--func (w *WebService) Path(root string) *WebService {
--	w.rootPath = root
--	w.compilePathExpression()
--	return w
+-	if result.Vbar.Vextra != "" {
+-		t.Errorf("vextra value should be empty: %#v", result.Vbar.Vextra)
+-	}
 -}
 -
--// Param adds a PathParameter to document parameters used in the root path.
--func (w *WebService) Param(parameter *Parameter) *WebService {
--	if w.pathParameters == nil {
--		w.pathParameters = []*Parameter{}
+-func TestSlice(t *testing.T) {
+-	t.Parallel()
+-
+-	inputStringSlice := map[string]interface{}{
+-		"vfoo": "foo",
+-		"vbar": []string{"foo", "bar", "baz"},
 -	}
--	w.pathParameters = append(w.pathParameters, parameter)
--	return w
--}
 -
--// PathParameter creates a new Parameter of kind Path for documentation purposes.
--// It is initialized as required with string as its DataType.
--func (w *WebService) PathParameter(name, description string) *Parameter {
--	p := &Parameter{&ParameterData{Name: name, Description: description, Required: true, DataType: "string"}}
--	p.bePath()
--	return p
--}
+-	inputStringSlicePointer := map[string]interface{}{
+-		"vfoo": "foo",
+-		"vbar": &[]string{"foo", "bar", "baz"},
+-	}
 -
--// QueryParameter creates a new Parameter of kind Query for documentation purposes.
--// It is initialized as not required with string as its DataType.
--func (w *WebService) QueryParameter(name, description string) *Parameter {
--	p := &Parameter{&ParameterData{Name: name, Description: description, Required: false, DataType: "string"}}
--	p.beQuery()
--	return p
--}
+-	outputStringSlice := &Slice{
+-		"foo",
+-		[]string{"foo", "bar", "baz"},
+-	}
 -
--// BodyParameter creates a new Parameter of kind Body for documentation purposes.
--// It is initialized as required without a DataType.
--func (w *WebService) BodyParameter(name, description string) *Parameter {
--	p := &Parameter{&ParameterData{Name: name, Description: description, Required: true}}
--	p.beBody()
--	return p
+-	testSliceInput(t, inputStringSlice, outputStringSlice)
+-	testSliceInput(t, inputStringSlicePointer, outputStringSlice)
 -}
 -
--// HeaderParameter creates a new Parameter of kind (Http) Header for documentation purposes.
--// It is initialized as not required with string as its DataType.
--func (w *WebService) HeaderParameter(name, description string) *Parameter {
--	p := &Parameter{&ParameterData{Name: name, Description: description, Required: false, DataType: "string"}}
--	p.beHeader()
--	return p
--}
+-func TestInvalidSlice(t *testing.T) {
+-	t.Parallel()
 -
--// FormParameter creates a new Parameter of kind Form (using application/x-www-form-urlencoded) for documentation purposes.
--// It is initialized as required with string as its DataType.
--func (w *WebService) FormParameter(name, description string) *Parameter {
--	p := &Parameter{&ParameterData{Name: name, Description: description, Required: false, DataType: "string"}}
--	p.beForm()
--	return p
--}
+-	input := map[string]interface{}{
+-		"vfoo": "foo",
+-		"vbar": 42,
+-	}
 -
--// Route creates a new Route using the RouteBuilder and add to the ordered list of Routes.
--func (w *WebService) Route(builder *RouteBuilder) *WebService {
--	builder.copyDefaults(w.produces, w.consumes)
--	w.routes = append(w.routes, builder.Build())
--	return w
+-	result := Slice{}
+-	err := Decode(input, &result)
+-	if err == nil {
+-		t.Errorf("expected failure")
+-	}
 -}
 -
--// Method creates a new RouteBuilder and initialize its http method
--func (w *WebService) Method(httpMethod string) *RouteBuilder {
--	return new(RouteBuilder).servicePath(w.rootPath).Method(httpMethod)
--}
+-func TestSliceOfStruct(t *testing.T) {
+-	t.Parallel()
 -
--// Produces specifies that this WebService can produce one or more MIME types.
--// Http requests must have one of these values set for the Accept header.
--func (w *WebService) Produces(contentTypes ...string) *WebService {
--	w.produces = contentTypes
--	return w
--}
+-	input := map[string]interface{}{
+-		"value": []map[string]interface{}{
+-			{"vstring": "one"},
+-			{"vstring": "two"},
+-		},
+-	}
 -
--// Consumes specifies that this WebService can consume one or more MIME types.
--// Http requests must have one of these values set for the Content-Type header.
--func (w *WebService) Consumes(accepts ...string) *WebService {
--	w.consumes = accepts
--	return w
--}
+-	var result SliceOfStruct
+-	err := Decode(input, &result)
+-	if err != nil {
+-		t.Fatalf("got unexpected error: %s", err)
+-	}
 -
--// Routes returns the Routes associated with this WebService
--func (w WebService) Routes() []Route {
--	return w.routes
--}
+-	if len(result.Value) != 2 {
+-		t.Fatalf("expected two values, got %d", len(result.Value))
+-	}
 -
--// RootPath returns the RootPath associated with this WebService. Default "/"
--func (w WebService) RootPath() string {
--	return w.rootPath
--}
+-	if result.Value[0].Vstring != "one" {
+-		t.Errorf("first value should be 'one', got: %s", result.Value[0].Vstring)
+-	}
 -
--// PathParameters return the path parameter names for (shared amoung its Routes)
--func (w WebService) PathParameters() []*Parameter {
--	return w.pathParameters
+-	if result.Value[1].Vstring != "two" {
+-		t.Errorf("second value should be 'two', got: %s", result.Value[1].Vstring)
+-	}
 -}
 -
--// Filter adds a filter function to the chain of filters applicable to all its Routes
--func (w *WebService) Filter(filter FilterFunction) *WebService {
--	w.filters = append(w.filters, filter)
--	return w
--}
+-func TestInvalidType(t *testing.T) {
+-	t.Parallel()
 -
--// Doc is used to set the documentation of this service.
--func (w *WebService) Doc(plainText string) *WebService {
--	w.documentation = plainText
--	return w
--}
+-	input := map[string]interface{}{
+-		"vstring": 42,
+-	}
 -
--// Documentation returns it.
--func (w WebService) Documentation() string {
--	return w.documentation
--}
+-	var result Basic
+-	err := Decode(input, &result)
+-	if err == nil {
+-		t.Fatal("error should exist")
+-	}
 -
--/*
--	Convenience methods
--*/
+-	derr, ok := err.(*Error)
+-	if !ok {
+-		t.Fatalf("error should be kind of Error, instead: %#v", err)
+-	}
 -
--// HEAD is a shortcut for .Method("HEAD").Path(subPath)
--func (w *WebService) HEAD(subPath string) *RouteBuilder {
--	return new(RouteBuilder).servicePath(w.rootPath).Method("HEAD").Path(subPath)
+-	if derr.Errors[0] != "'Vstring' expected type 'string', got unconvertible type 'int'" {
+-		t.Errorf("got unexpected error: %s", err)
+-	}
 -}
 -
--// GET is a shortcut for .Method("GET").Path(subPath)
--func (w *WebService) GET(subPath string) *RouteBuilder {
--	return new(RouteBuilder).servicePath(w.rootPath).Method("GET").Path(subPath)
--}
+-func TestMetadata(t *testing.T) {
+-	t.Parallel()
 -
--// POST is a shortcut for .Method("POST").Path(subPath)
--func (w *WebService) POST(subPath string) *RouteBuilder {
--	return new(RouteBuilder).servicePath(w.rootPath).Method("POST").Path(subPath)
--}
+-	input := map[string]interface{}{
+-		"vfoo": "foo",
+-		"vbar": map[string]interface{}{
+-			"vstring": "foo",
+-			"Vuint":   42,
+-			"foo":     "bar",
+-		},
+-		"bar": "nil",
+-	}
 -
--// PUT is a shortcut for .Method("PUT").Path(subPath)
--func (w *WebService) PUT(subPath string) *RouteBuilder {
--	return new(RouteBuilder).servicePath(w.rootPath).Method("PUT").Path(subPath)
--}
+-	var md Metadata
+-	var result Nested
+-	config := &DecoderConfig{
+-		Metadata: &md,
+-		Result:   &result,
+-	}
 -
--// PATCH is a shortcut for .Method("PATCH").Path(subPath)
--func (w *WebService) PATCH(subPath string) *RouteBuilder {
--	return new(RouteBuilder).servicePath(w.rootPath).Method("PATCH").Path(subPath)
--}
+-	decoder, err := NewDecoder(config)
+-	if err != nil {
+-		t.Fatalf("err: %s", err)
+-	}
 -
--// DELETE is a shortcut for .Method("DELETE").Path(subPath)
--func (w *WebService) DELETE(subPath string) *RouteBuilder {
--	return new(RouteBuilder).servicePath(w.rootPath).Method("DELETE").Path(subPath)
+-	err = decoder.Decode(input)
+-	if err != nil {
+-		t.Fatalf("err: %s", err.Error())
+-	}
+-
+-	expectedKeys := []string{"Vfoo", "Vbar.Vstring", "Vbar.Vuint", "Vbar"}
+-	if !reflect.DeepEqual(md.Keys, expectedKeys) {
+-		t.Fatalf("bad keys: %#v", md.Keys)
+-	}
+-
+-	expectedUnused := []string{"Vbar.foo", "bar"}
+-	if !reflect.DeepEqual(md.Unused, expectedUnused) {
+-		t.Fatalf("bad unused: %#v", md.Unused)
+-	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/web_service_container.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/web_service_container.go
-deleted file mode 100644
-index c9d31b0..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/web_service_container.go
-+++ /dev/null
-@@ -1,39 +0,0 @@
--package restful
 -
--// Copyright 2013 Ernest Micklei. All rights reserved.
--// Use of this source code is governed by a license
--// that can be found in the LICENSE file.
+-func TestMetadata_Embedded(t *testing.T) {
+-	t.Parallel()
 -
--import (
--	"net/http"
--)
+-	input := map[string]interface{}{
+-		"vstring": "foo",
+-		"vunique": "bar",
+-	}
 -
--// DefaultContainer is a restful.Container that uses http.DefaultServeMux
--var DefaultContainer *Container
+-	var md Metadata
+-	var result EmbeddedSquash
+-	config := &DecoderConfig{
+-		Metadata: &md,
+-		Result:   &result,
+-	}
 -
--func init() {
--	DefaultContainer = NewContainer()
--	DefaultContainer.ServeMux = http.DefaultServeMux
--}
+-	decoder, err := NewDecoder(config)
+-	if err != nil {
+-		t.Fatalf("err: %s", err)
+-	}
 -
--// If set the true then panics will not be caught to return HTTP 500.
--// In that case, Route functions are responsible for handling any error situation.
--// Default value is false = recover from panics. This has performance implications.
--// OBSOLETE ; use restful.DefaultContainer.DoNotRecover(true)
--var DoNotRecover = false
+-	err = decoder.Decode(input)
+-	if err != nil {
+-		t.Fatalf("err: %s", err.Error())
+-	}
 -
--// Add registers a new WebService add it to the DefaultContainer.
--func Add(service *WebService) {
--	DefaultContainer.Add(service)
--}
+-	expectedKeys := []string{"Vstring", "Vunique"}
 -
--// Filter appends a container FilterFunction from the DefaultContainer.
--// These are called before dispatching a http.Request to a WebService.
--func Filter(filter FilterFunction) {
--	DefaultContainer.Filter(filter)
--}
+-	sort.Strings(md.Keys)
+-	if !reflect.DeepEqual(md.Keys, expectedKeys) {
+-		t.Fatalf("bad keys: %#v", md.Keys)
+-	}
 -
--// RegisteredWebServices returns the collections of WebServices from the DefaultContainer
--func RegisteredWebServices() []*WebService {
--	return DefaultContainer.RegisteredWebServices()
+-	expectedUnused := []string{}
+-	if !reflect.DeepEqual(md.Unused, expectedUnused) {
+-		t.Fatalf("bad unused: %#v", md.Unused)
+-	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/emicklei/go-restful/web_service_test.go b/Godeps/_workspace/src/github.com/emicklei/go-restful/web_service_test.go
-deleted file mode 100644
-index e200979..0000000
---- a/Godeps/_workspace/src/github.com/emicklei/go-restful/web_service_test.go
-+++ /dev/null
-@@ -1,115 +0,0 @@
--package restful
--
--import (
--	"net/http"
--	"net/http/httptest"
--	"testing"
--)
 -
--const (
--	pathGetFriends = "/get/{userId}/friends"
--)
+-func TestNonPtrValue(t *testing.T) {
+-	t.Parallel()
 -
--func TestParameter(t *testing.T) {
--	p := &Parameter{&ParameterData{Name: "name", Description: "desc"}}
--	p.AllowMultiple(true)
--	p.DataType("int")
--	p.Required(true)
--	values := map[string]string{"a": "b"}
--	p.AllowableValues(values)
--	p.bePath()
+-	err := Decode(map[string]interface{}{}, Basic{})
+-	if err == nil {
+-		t.Fatal("error should exist")
+-	}
 -
--	ws := new(WebService)
--	ws.Param(p)
--	if ws.pathParameters[0].Data().Name != "name" {
--		t.Error("path parameter (or name) invalid")
+-	if err.Error() != "result must be a pointer" {
+-		t.Errorf("got unexpected error: %s", err)
 -	}
 -}
--func TestWebService_CanCreateParameterKinds(t *testing.T) {
--	ws := new(WebService)
--	if ws.BodyParameter("b", "b").Kind() != BodyParameterKind {
--		t.Error("body parameter expected")
+-
+-func TestTagged(t *testing.T) {
+-	t.Parallel()
+-
+-	input := map[string]interface{}{
+-		"foo": "bar",
+-		"bar": "value",
 -	}
--	if ws.PathParameter("p", "p").Kind() != PathParameterKind {
--		t.Error("path parameter expected")
+-
+-	var result Tagged
+-	err := Decode(input, &result)
+-	if err != nil {
+-		t.Fatalf("unexpected error: %s", err)
 -	}
--	if ws.QueryParameter("q", "q").Kind() != QueryParameterKind {
--		t.Error("query parameter expected")
+-
+-	if result.Value != "bar" {
+-		t.Errorf("value should be 'bar', got: %#v", result.Value)
 -	}
--}
 -
--func TestCapturePanic(t *testing.T) {
--	tearDown()
--	Add(newPanicingService())
--	httpRequest, _ := http.NewRequest("GET", "http://here.com/fire", nil)
--	httpRequest.Header.Set("Accept", "*/*")
--	httpWriter := httptest.NewRecorder()
--	DefaultContainer.dispatch(httpWriter, httpRequest)
--	if 500 != httpWriter.Code {
--		t.Error("500 expected on fire")
+-	if result.Extra != "value" {
+-		t.Errorf("extra should be 'value', got: %#v", result.Extra)
 -	}
 -}
 -
--func TestNotFound(t *testing.T) {
--	tearDown()
--	httpRequest, _ := http.NewRequest("GET", "http://here.com/missing", nil)
--	httpRequest.Header.Set("Accept", "*/*")
--	httpWriter := httptest.NewRecorder()
--	DefaultContainer.dispatch(httpWriter, httpRequest)
--	if 404 != httpWriter.Code {
--		t.Error("404 expected on missing")
+-func TestWeakDecode(t *testing.T) {
+-	t.Parallel()
+-
+-	input := map[string]interface{}{
+-		"foo": "4",
+-		"bar": "value",
 -	}
--}
 -
--func TestMethodNotAllowed(t *testing.T) {
--	tearDown()
--	Add(newGetOnlyService())
--	httpRequest, _ := http.NewRequest("POST", "http://here.com/get", nil)
--	httpRequest.Header.Set("Accept", "*/*")
--	httpWriter := httptest.NewRecorder()
--	DefaultContainer.dispatch(httpWriter, httpRequest)
--	if 405 != httpWriter.Code {
--		t.Error("405 expected method not allowed")
+-	var result struct {
+-		Foo int
+-		Bar string
 -	}
--}
 -
--func TestSelectedRoutePath_Issue100(t *testing.T) {
--	tearDown()
--	Add(newSelectedRouteTestingService())
--	httpRequest, _ := http.NewRequest("GET", "http://here.com/get/232452/friends", nil)
--	httpRequest.Header.Set("Accept", "*/*")
--	httpWriter := httptest.NewRecorder()
--	DefaultContainer.dispatch(httpWriter, httpRequest)
--	if http.StatusOK != httpWriter.Code {
--		t.Error(http.StatusOK, "expected,", httpWriter.Code, "received.")
+-	if err := WeakDecode(input, &result); err != nil {
+-		t.Fatalf("err: %s", err)
+-	}
+-	if result.Foo != 4 {
+-		t.Fatalf("bad: %#v", result)
+-	}
+-	if result.Bar != "value" {
+-		t.Fatalf("bad: %#v", result)
 -	}
 -}
 -
--func newPanicingService() *WebService {
--	ws := new(WebService).Path("")
--	ws.Route(ws.GET("/fire").To(doPanic))
--	return ws
--}
+-func testSliceInput(t *testing.T, input map[string]interface{}, expected *Slice) {
+-	var result Slice
+-	err := Decode(input, &result)
+-	if err != nil {
+-		t.Fatalf("got error: %s", err)
+-	}
 -
--func newGetOnlyService() *WebService {
--	ws := new(WebService).Path("")
--	ws.Route(ws.GET("/get").To(doPanic))
--	return ws
--}
+-	if result.Vfoo != expected.Vfoo {
+-		t.Errorf("Vfoo expected '%s', got '%s'", expected.Vfoo, result.Vfoo)
+-	}
 -
--func newSelectedRouteTestingService() *WebService {
--	ws := new(WebService).Path("")
--	ws.Route(ws.GET(pathGetFriends).To(selectedRouteChecker))
--	return ws
--}
+-	if result.Vbar == nil {
+-		t.Fatalf("Vbar a slice, got '%#v'", result.Vbar)
+-	}
 -
--func selectedRouteChecker(req *Request, resp *Response) {
--	if req.SelectedRoutePath() != pathGetFriends {
--		resp.InternalServerError()
+-	if len(result.Vbar) != len(expected.Vbar) {
+-		t.Errorf("Vbar length should be %d, got %d", len(expected.Vbar), len(result.Vbar))
 -	}
--}
 -
--func doPanic(req *Request, resp *Response) {
--	println("lightning...")
--	panic("fire")
+-	for i, v := range result.Vbar {
+-		if v != expected.Vbar[i] {
+-			t.Errorf(
+-				"Vbar[%d] should be '%#v', got '%#v'",
+-				i, expected.Vbar[i], v)
+-		}
+-	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/.travis.yml b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/.travis.yml
+diff --git a/Godeps/_workspace/src/github.com/racker/perigee/.gitignore b/Godeps/_workspace/src/github.com/racker/perigee/.gitignore
 deleted file mode 100644
-index ad1dff7..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/.travis.yml
+index 49ca32a..0000000
+--- a/Godeps/_workspace/src/github.com/racker/perigee/.gitignore
 +++ /dev/null
-@@ -1,13 +0,0 @@
--language: go
--go:
--  - 1.1.2
--  - 1.2.2
--  - 1.3.1
--  - tip
--env:
--  - GOARCH=amd64
--  - GOARCH=386
--install:
--  - go get -d ./...
--script:
--  - go test ./...
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/AUTHORS b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/AUTHORS
+@@ -1,2 +0,0 @@
+-bin/*
+-pkg/*
+diff --git a/Godeps/_workspace/src/github.com/racker/perigee/LICENSE b/Godeps/_workspace/src/github.com/racker/perigee/LICENSE
 deleted file mode 100644
-index bb79881..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/AUTHORS
+index d645695..0000000
+--- a/Godeps/_workspace/src/github.com/racker/perigee/LICENSE
 +++ /dev/null
-@@ -1,44 +0,0 @@
--# This is the official list of go-dockerclient authors for copyright purposes.
+@@ -1,202 +0,0 @@
 -
--Aldrin Leal <aldrin at leal.eng.br>
--Andreas Jaekle <andreas at jaekle.net>
--Andrews Medina <andrewsmedina at gmail.com>
--Andy Goldstein <andy.goldstein at redhat.com>
--Ben McCann <benmccann.com>
--Carlos Diaz-Padron <cpadron at mozilla.com>
--Cezar Sa Espinola <cezar.sa at corp.globo.com>
--Cheah Chu Yeow <chuyeow at gmail.com>
--cheneydeng <cheneydeng at qq.com>
--CMGS <ilskdw at gmail.com>
--Daniel, Dao Quang Minh <dqminh89 at gmail.com>
--David Huie <dahuie at gmail.com>
--Ed <edrocksit at gmail.com>
--Eric Anderson <anderson at copperegg.com>
--Fabio Rehm <fgrehm at gmail.com>
--Flavia Missi <flaviamissi at gmail.com>
--Francisco Souza <f at souza.cc>
--Jari Kolehmainen <jari.kolehmainen at digia.com>
--Jason Wilder <jwilder at litl.com>
--Jean-Baptiste Dalido <jeanbaptiste at appgratis.com>
--Jeff Mitchell <jeffrey.mitchell at gmail.com>
--Jeffrey Hulten <jhulten at gmail.com>
--Johan Euphrosine <proppy at google.com>
--Karan Misra <kidoman at gmail.com>
--Kim, Hirokuni <hirokuni.kim at kvh.co.jp>
--Lucas Clemente <lucas at clemente.io>
--Omeid Matten <public at omeid.me>
--Paul Morie <pmorie at gmail.com>
--Peter Jihoon Kim <raingrove at gmail.com>
--Philippe Lafoucrière <philippe.lafoucriere at tech-angels.com>
--Rafe Colton <r.colton at modcloth.com>
--Robert Williamson <williamson.robert at gmail.com>
--Salvador Gironès <salvadorgirones at gmail.com>
--Simon Eskildsen <sirup at sirupsen.com>
--Simon Menke <simon.menke at gmail.com>
--Skolos <skolos at gopherlab.com>
--Soulou <leo at unbekandt.eu>
--Sridhar Ratnakumar <sridharr at activestate.com>
--Summer Mousa <smousa at zenoss.com>
--Tarsis Azevedo <tarsis at corp.globo.com>
--Tim Schindler <tim at catalyst-zero.com>
--Wiliam Souza <wiliamsouza83 at gmail.com>
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/DOCKER-LICENSE b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/DOCKER-LICENSE
-deleted file mode 100644
-index f4130a5..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/DOCKER-LICENSE
-+++ /dev/null
-@@ -1,6 +0,0 @@
 -                                 Apache License
 -                           Version 2.0, January 2004
 -                        http://www.apache.org/licenses/
 -
--You can find the Docker license int the following link:
--https://raw2.github.com/dotcloud/docker/master/LICENSE
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/LICENSE b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/LICENSE
-deleted file mode 100644
-index 7a6d8bb..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/LICENSE
-+++ /dev/null
-@@ -1,22 +0,0 @@
--Copyright (c) 2014, go-dockerclient authors
--All rights reserved.
+-   TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
 -
--Redistribution and use in source and binary forms, with or without
--modification, are permitted provided that the following conditions are met:
+-   1. Definitions.
 -
--  * Redistributions of source code must retain the above copyright notice,
--this list of conditions and the following disclaimer.
--  * Redistributions in binary form must reproduce the above copyright notice,
--this list of conditions and the following disclaimer in the documentation
--and/or other materials provided with the distribution.
+-      "License" shall mean the terms and conditions for use, reproduction,
+-      and distribution as defined by Sections 1 through 9 of this document.
 -
--THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
--ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
--WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
--DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
--FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
--DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
--SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
--CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
--OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
--OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/README.markdown b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/README.markdown
+-      "Licensor" shall mean the copyright owner or entity authorized by
+-      the copyright owner that is granting the License.
+-
+-      "Legal Entity" shall mean the union of the acting entity and all
+-      other entities that control, are controlled by, or are under common
+-      control with that entity. For the purposes of this definition,
+-      "control" means (i) the power, direct or indirect, to cause the
+-      direction or management of such entity, whether by contract or
+-      otherwise, or (ii) ownership of fifty percent (50%) or more of the
+-      outstanding shares, or (iii) beneficial ownership of such entity.
+-
+-      "You" (or "Your") shall mean an individual or Legal Entity
+-      exercising permissions granted by this License.
+-
+-      "Source" form shall mean the preferred form for making modifications,
+-      including but not limited to software source code, documentation
+-      source, and configuration files.
+-
+-      "Object" form shall mean any form resulting from mechanical
+-      transformation or translation of a Source form, including but
+-      not limited to compiled object code, generated documentation,
+-      and conversions to other media types.
+-
+-      "Work" shall mean the work of authorship, whether in Source or
+-      Object form, made available under the License, as indicated by a
+-      copyright notice that is included in or attached to the work
+-      (an example is provided in the Appendix below).
+-
+-      "Derivative Works" shall mean any work, whether in Source or Object
+-      form, that is based on (or derived from) the Work and for which the
+-      editorial revisions, annotations, elaborations, or other modifications
+-      represent, as a whole, an original work of authorship. For the purposes
+-      of this License, Derivative Works shall not include works that remain
+-      separable from, or merely link (or bind by name) to the interfaces of,
+-      the Work and Derivative Works thereof.
+-
+-      "Contribution" shall mean any work of authorship, including
+-      the original version of the Work and any modifications or additions
+-      to that Work or Derivative Works thereof, that is intentionally
+-      submitted to Licensor for inclusion in the Work by the copyright owner
+-      or by an individual or Legal Entity authorized to submit on behalf of
+-      the copyright owner. For the purposes of this definition, "submitted"
+-      means any form of electronic, verbal, or written communication sent
+-      to the Licensor or its representatives, including but not limited to
+-      communication on electronic mailing lists, source code control systems,
+-      and issue tracking systems that are managed by, or on behalf of, the
+-      Licensor for the purpose of discussing and improving the Work, but
+-      excluding communication that is conspicuously marked or otherwise
+-      designated in writing by the copyright owner as "Not a Contribution."
+-
+-      "Contributor" shall mean Licensor and any individual or Legal Entity
+-      on behalf of whom a Contribution has been received by Licensor and
+-      subsequently incorporated within the Work.
+-
+-   2. Grant of Copyright License. Subject to the terms and conditions of
+-      this License, each Contributor hereby grants to You a perpetual,
+-      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+-      copyright license to reproduce, prepare Derivative Works of,
+-      publicly display, publicly perform, sublicense, and distribute the
+-      Work and such Derivative Works in Source or Object form.
+-
+-   3. Grant of Patent License. Subject to the terms and conditions of
+-      this License, each Contributor hereby grants to You a perpetual,
+-      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+-      (except as stated in this section) patent license to make, have made,
+-      use, offer to sell, sell, import, and otherwise transfer the Work,
+-      where such license applies only to those patent claims licensable
+-      by such Contributor that are necessarily infringed by their
+-      Contribution(s) alone or by combination of their Contribution(s)
+-      with the Work to which such Contribution(s) was submitted. If You
+-      institute patent litigation against any entity (including a
+-      cross-claim or counterclaim in a lawsuit) alleging that the Work
+-      or a Contribution incorporated within the Work constitutes direct
+-      or contributory patent infringement, then any patent licenses
+-      granted to You under this License for that Work shall terminate
+-      as of the date such litigation is filed.
+-
+-   4. Redistribution. You may reproduce and distribute copies of the
+-      Work or Derivative Works thereof in any medium, with or without
+-      modifications, and in Source or Object form, provided that You
+-      meet the following conditions:
+-
+-      (a) You must give any other recipients of the Work or
+-          Derivative Works a copy of this License; and
+-
+-      (b) You must cause any modified files to carry prominent notices
+-          stating that You changed the files; and
+-
+-      (c) You must retain, in the Source form of any Derivative Works
+-          that You distribute, all copyright, patent, trademark, and
+-          attribution notices from the Source form of the Work,
+-          excluding those notices that do not pertain to any part of
+-          the Derivative Works; and
+-
+-      (d) If the Work includes a "NOTICE" text file as part of its
+-          distribution, then any Derivative Works that You distribute must
+-          include a readable copy of the attribution notices contained
+-          within such NOTICE file, excluding those notices that do not
+-          pertain to any part of the Derivative Works, in at least one
+-          of the following places: within a NOTICE text file distributed
+-          as part of the Derivative Works; within the Source form or
+-          documentation, if provided along with the Derivative Works; or,
+-          within a display generated by the Derivative Works, if and
+-          wherever such third-party notices normally appear. The contents
+-          of the NOTICE file are for informational purposes only and
+-          do not modify the License. You may add Your own attribution
+-          notices within Derivative Works that You distribute, alongside
+-          or as an addendum to the NOTICE text from the Work, provided
+-          that such additional attribution notices cannot be construed
+-          as modifying the License.
+-
+-      You may add Your own copyright statement to Your modifications and
+-      may provide additional or different license terms and conditions
+-      for use, reproduction, or distribution of Your modifications, or
+-      for any such Derivative Works as a whole, provided Your use,
+-      reproduction, and distribution of the Work otherwise complies with
+-      the conditions stated in this License.
+-
+-   5. Submission of Contributions. Unless You explicitly state otherwise,
+-      any Contribution intentionally submitted for inclusion in the Work
+-      by You to the Licensor shall be under the terms and conditions of
+-      this License, without any additional terms or conditions.
+-      Notwithstanding the above, nothing herein shall supersede or modify
+-      the terms of any separate license agreement you may have executed
+-      with Licensor regarding such Contributions.
+-
+-   6. Trademarks. This License does not grant permission to use the trade
+-      names, trademarks, service marks, or product names of the Licensor,
+-      except as required for reasonable and customary use in describing the
+-      origin of the Work and reproducing the content of the NOTICE file.
+-
+-   7. Disclaimer of Warranty. Unless required by applicable law or
+-      agreed to in writing, Licensor provides the Work (and each
+-      Contributor provides its Contributions) on an "AS IS" BASIS,
+-      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+-      implied, including, without limitation, any warranties or conditions
+-      of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+-      PARTICULAR PURPOSE. You are solely responsible for determining the
+-      appropriateness of using or redistributing the Work and assume any
+-      risks associated with Your exercise of permissions under this License.
+-
+-   8. Limitation of Liability. In no event and under no legal theory,
+-      whether in tort (including negligence), contract, or otherwise,
+-      unless required by applicable law (such as deliberate and grossly
+-      negligent acts) or agreed to in writing, shall any Contributor be
+-      liable to You for damages, including any direct, indirect, special,
+-      incidental, or consequential damages of any character arising as a
+-      result of this License or out of the use or inability to use the
+-      Work (including but not limited to damages for loss of goodwill,
+-      work stoppage, computer failure or malfunction, or any and all
+-      other commercial damages or losses), even if such Contributor
+-      has been advised of the possibility of such damages.
+-
+-   9. Accepting Warranty or Additional Liability. While redistributing
+-      the Work or Derivative Works thereof, You may choose to offer,
+-      and charge a fee for, acceptance of support, warranty, indemnity,
+-      or other liability obligations and/or rights consistent with this
+-      License. However, in accepting such obligations, You may act only
+-      on Your own behalf and on Your sole responsibility, not on behalf
+-      of any other Contributor, and only if You agree to indemnify,
+-      defend, and hold each Contributor harmless for any liability
+-      incurred by, or claims asserted against, such Contributor by reason
+-      of your accepting any such warranty or additional liability.
+-
+-   END OF TERMS AND CONDITIONS
+-
+-   APPENDIX: How to apply the Apache License to your work.
+-
+-      To apply the Apache License to your work, attach the following
+-      boilerplate notice, with the fields enclosed by brackets "[]"
+-      replaced with your own identifying information. (Don't include
+-      the brackets!)  The text should be enclosed in the appropriate
+-      comment syntax for the file format. We also recommend that a
+-      file or class name and description of purpose be included on the
+-      same "printed page" as the copyright notice for easier
+-      identification within third-party archives.
+-
+-   Copyright [yyyy] [name of copyright owner]
+-
+-   Licensed under the Apache License, Version 2.0 (the "License");
+-   you may not use this file except in compliance with the License.
+-   You may obtain a copy of the License at
+-
+-       http://www.apache.org/licenses/LICENSE-2.0
+-
+-   Unless required by applicable law or agreed to in writing, software
+-   distributed under the License is distributed on an "AS IS" BASIS,
+-   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-   See the License for the specific language governing permissions and
+-   limitations under the License.
+diff --git a/Godeps/_workspace/src/github.com/racker/perigee/README.md b/Godeps/_workspace/src/github.com/racker/perigee/README.md
 deleted file mode 100644
-index 66cedca..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/README.markdown
+index 81cbf4a..0000000
+--- a/Godeps/_workspace/src/github.com/racker/perigee/README.md
 +++ /dev/null
-@@ -1,42 +0,0 @@
--#go-dockerclient
+@@ -1,120 +0,0 @@
+-# perigee
 -
--[![Build Status](https://drone.io/github.com/fsouza/go-dockerclient/status.png)](https://drone.io/github.com/fsouza/go-dockerclient/latest)
--[![Build Status](https://travis-ci.org/fsouza/go-dockerclient.png)](https://travis-ci.org/fsouza/go-dockerclient)
+-Perigee provides a REST client that, while it should be generic enough to use with most any RESTful API, is nonetheless optimized to the needs of the OpenStack APIs.
+-Perigee grew out of the need to refactor out common API access code from the [gorax](http://github.com/racker/gorax) project.
 -
--[![GoDoc](http://godoc.org/github.com/fsouza/go-dockerclient?status.png)](http://godoc.org/github.com/fsouza/go-dockerclient)
+-Several things influenced the name of the project.
+-Numerous elements of the OpenStack ecosystem are named after astronomical artifacts.
+-Additionally, perigee occurs when two orbiting bodies are closest to each other.
+-Perigee seemed appropriate for something aiming to bring OpenStack and other RESTful services closer to the end-user.
 -
--This package presents a client for the Docker remote API.
+-**This library is still in the very early stages of development. Unless you want to contribute, it probably isn't what you want**
 -
--For more details, check the [remote API documentation](http://docs.docker.io/en/latest/reference/api/docker_remote_api/).
+-## Installation and Testing
 -
--## Example
+-To install:
 -
--```go
--package main
+-```bash
+-go get github.com/racker/perigee
+-```
 -
--import (
--        "fmt"
--        "github.com/fsouza/go-dockerclient"
--)
+-To run unit tests:
 -
--func main() {
--        endpoint := "unix:///var/run/docker.sock"
--        client, _ := docker.NewClient(endpoint)
--        imgs, _ := client.ListImages(true)
--        for _, img := range imgs {
--                fmt.Println("ID: ", img.ID)
--                fmt.Println("RepoTags: ", img.RepoTags)
--                fmt.Println("Created: ", img.Created)
--                fmt.Println("Size: ", img.Size)
--                fmt.Println("VirtualSize: ", img.VirtualSize)
--                fmt.Println("ParentId: ", img.ParentId)
--        }
--}
+-```bash
+-go test github.com/racker/perigee
 -```
 -
--## Developing
+-## Contributing
 -
--You can run the tests with:
+-The following guidelines are preliminary, as this project is just starting out.
+-However, this should serve as a working first-draft.
 -
--    go get -d ./...
--    go test ./...
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/change.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/change.go
-deleted file mode 100644
-index cafffad..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/change.go
-+++ /dev/null
-@@ -1,36 +0,0 @@
--// Copyright 2014 go-dockerclient authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the LICENSE file.
+-### Branching
 -
--package docker
+-The master branch must always be a valid build.
+-The `go get` command will not work otherwise.
+-Therefore, development must occur on a different branch.
 -
--import "fmt"
+-When creating a feature branch, do so off the master branch:
 -
--type ChangeType int
+-```bash
+-git checkout master
+-git pull
+-git checkout -b featureBranch
+-git checkout -b featureBranch-wip   # optional
+-```
 -
--const (
--	ChangeModify ChangeType = iota
--	ChangeAdd
--	ChangeDelete
--)
+-Perform all your editing and testing in the WIP-branch.
+-Feel free to make as many commits as you see fit.
+-You may even open "WIP" pull requests from your feature branch to seek feedback.
+-WIP pull requests will **never** be merged, however.
 -
--// Change represents a change in a container.
--//
--// See http://goo.gl/QkW9sH for more details.
--type Change struct {
--	Path string
--	Kind ChangeType
--}
+-To get code merged, you'll need to "squash" your changes into one or more clean commits in the feature branch.
+-These steps should be followed:
 -
--func (change *Change) String() string {
--	var kind string
--	switch change.Kind {
--	case ChangeModify:
--		kind = "C"
--	case ChangeAdd:
--		kind = "A"
--	case ChangeDelete:
--		kind = "D"
--	}
--	return fmt.Sprintf("%s %s", kind, change.Path)
--}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/change_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/change_test.go
-deleted file mode 100644
-index 7c2ec30..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/change_test.go
-+++ /dev/null
-@@ -1,26 +0,0 @@
--// Copyright 2014 go-dockerclient authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the LICENSE file.
+-```bash
+-git checkout featureBranch
+-git merge --squash featureBranch-wip
+-git commit -a
+-git push origin featureBranch
+-```
 -
--package docker
+-You may now open a nice, clean, self-contained pull request from featureBranch to master.
 -
--import (
--	"testing"
--)
+-The `git commit -a` command above will open a text editor so that
+-you may provide a comprehensive description of the changes.
 -
--func TestChangeString(t *testing.T) {
--	var tests = []struct {
--		change   Change
--		expected string
--	}{
--		{Change{"/etc/passwd", ChangeModify}, "C /etc/passwd"},
--		{Change{"/etc/passwd", ChangeAdd}, "A /etc/passwd"},
--		{Change{"/etc/passwd", ChangeDelete}, "D /etc/passwd"},
--		{Change{"/etc/passwd", 33}, " /etc/passwd"},
--	}
--	for _, tt := range tests {
--		if got := tt.change.String(); got != tt.expected {
--			t.Errorf("Change.String(): want %q. Got %q.", tt.expected, got)
--		}
--	}
--}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/client.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/client.go
-deleted file mode 100644
-index e68a9ef..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/client.go
-+++ /dev/null
-@@ -1,546 +0,0 @@
--// Copyright 2014 go-dockerclient authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the LICENSE file.
+-In general, when submitting a pull request against master,
+-be sure to answer the following questions:
 -
--// Package docker provides a client for the Docker remote API.
--//
--// See http://goo.gl/G3plxW for more details on the remote API.
--package docker
+-- What is the problem?
+-- Why is it a problem?
+-- What is your solution?
+-- How does your solution work?  (Recommended for non-trivial changes.)
+-- Why should we use your solution over someone elses?  (Recommended especially if multiple solutions being discussed.)
 -
--import (
--	"bytes"
--	"encoding/json"
--	"errors"
--	"fmt"
--	"io"
--	"io/ioutil"
--	"net"
--	"net/http"
--	"net/http/httputil"
--	"net/url"
--	"reflect"
--	"strconv"
--	"strings"
--)
+-Remember that monster-sized pull requests are a bear to code-review,
+-so having helpful commit logs are an absolute must to review changes as quickly as possible.
 -
--const userAgent = "go-dockerclient"
+-Finally, (s)he who breaks master is ultimately responsible for fixing master.
 -
--var (
--	// ErrInvalidEndpoint is returned when the endpoint is not a valid HTTP URL.
--	ErrInvalidEndpoint = errors.New("invalid endpoint")
+-### Source Representation
 -
--	// ErrConnectionRefused is returned when the client cannot connect to the given endpoint.
--	ErrConnectionRefused = errors.New("cannot connect to Docker endpoint")
+-The Go community firmly believes in a consistent representation for all Go source code.
+-We do too.
+-Make sure all source code is passed through "go fmt" *before* you create your pull request.
 -
--	apiVersion_1_12, _ = NewApiVersion("1.12")
--)
+-Please note, however, that we fully acknowledge and recognize that we no longer rely upon punch-cards for representing source files.
+-Therefore, no 80-column limit exists.
+-However, if a line exceeds 132 columns, you may want to consider splitting the line.
 -
--// ApiVersion is an internal representation of a version of the Remote API.
--type ApiVersion []int
+-### Unit and Integration Tests
 -
--// NewApiVersion returns an instance of ApiVersion for the given string.
--//
--// The given string must be in the form <major>.<minor>.<patch>, where <major>,
--// <minor> and <patch> are integer numbers.
--func NewApiVersion(input string) (ApiVersion, error) {
--	if !strings.Contains(input, ".") {
--		return nil, fmt.Errorf("Unable to parse version %q", input)
--	}
--	arr := strings.Split(input, ".")
--	ret := make(ApiVersion, len(arr))
--	var err error
--	for i, val := range arr {
--		ret[i], err = strconv.Atoi(val)
--		if err != nil {
--			return nil, fmt.Errorf("Unable to parse version %q: %q is not an integer", input, val)
--		}
--	}
--	return ret, nil
--}
+-Pull requests that include non-trivial code changes without accompanying unit tests will be flatly rejected.
+-While we have no way of enforcing this practice,
+-you can ensure your code is thoroughly tested by always [writing tests first by intention.](http://en.wikipedia.org/wiki/Test-driven_development)
 -
--func (version ApiVersion) String() string {
--	var str string
--	for i, val := range version {
--		str += strconv.Itoa(val)
--		if i < len(version)-1 {
--			str += "."
--		}
--	}
--	return str
--}
+-When creating a pull request, if even one test fails, the PR will be rejected.
+-Make sure all unit tests pass.
+-Make sure all integration tests pass.
 -
--func (version ApiVersion) LessThan(other ApiVersion) bool {
--	return version.compare(other) < 0
--}
+-### Documentation
 -
--func (version ApiVersion) LessThanOrEqualTo(other ApiVersion) bool {
--	return version.compare(other) <= 0
--}
+-Private functions and methods which are obvious to anyone unfamiliar with gorax needn't be accompanied by documentation.
+-However, this is a code-smell; if submitting a PR, expect to justify your decision.
 -
--func (version ApiVersion) GreaterThan(other ApiVersion) bool {
--	return version.compare(other) > 0
--}
+-Public functions, regardless of how obvious, **must** have accompanying godoc-style documentation.
+-This is not to suggest you should provide a tome for each function, however.
+-Sometimes a link to more information is more appropriate, provided the link is stable, reliable, and pertinent.
 -
--func (version ApiVersion) GreaterThanOrEqualTo(other ApiVersion) bool {
--	return version.compare(other) >= 0
--}
+-Changing documentation often results in bizarre diffs in pull requests, due to text often spanning multiple lines.
+-To work around this, put [one logical thought or sentence on a single line.](http://rhodesmill.org/brandon/2012/one-sentence-per-line/)
+-While this looks weird in a plain-text editor,
+-remember that both godoc and HTML viewers will reflow text.
+-The source code and its comments should be easy to edit with minimal diff pollution.
+-Let software dedicated to presenting the documentation to human readers deal with its presentation.
 -
--func (version ApiVersion) compare(other ApiVersion) int {
--	for i, v := range version {
--		if i <= len(other)-1 {
--			otherVersion := other[i]
+-## Examples
 -
--			if v < otherVersion {
--				return -1
--			} else if v > otherVersion {
--				return 1
--			}
--		}
--	}
--	if len(version) > len(other) {
--		return 1
--	}
--	if len(version) < len(other) {
--		return -1
--	}
--	return 0
--}
+-t.b.d.
 -
--// Client is the basic type of this package. It provides methods for
--// interaction with the API.
--type Client struct {
--	SkipServerVersionCheck bool
--	HTTPClient             *http.Client
+diff --git a/Godeps/_workspace/src/github.com/racker/perigee/api.go b/Godeps/_workspace/src/github.com/racker/perigee/api.go
+deleted file mode 100644
+index 0fcbadb..0000000
+--- a/Godeps/_workspace/src/github.com/racker/perigee/api.go
++++ /dev/null
+@@ -1,269 +0,0 @@
+-// vim: ts=8 sw=8 noet ai
 -
--	endpoint            string
--	endpointURL         *url.URL
--	eventMonitor        *eventMonitoringState
--	requestedApiVersion ApiVersion
--	serverApiVersion    ApiVersion
--	expectedApiVersion  ApiVersion
--}
+-package perigee
 -
--// NewClient returns a Client instance ready for communication with the given
--// server endpoint. It will use the latest remote API version available in the
--// server.
--func NewClient(endpoint string) (*Client, error) {
--	client, err := NewVersionedClient(endpoint, "")
--	if err != nil {
--		return nil, err
--	}
--	client.SkipServerVersionCheck = true
--	return client, nil
--}
+-import (
+-	"encoding/json"
+-	"fmt"
+-	"io"
+-	"io/ioutil"
+-	"log"
+-	"net/http"
+-	"strings"
+-)
 -
--// NewVersionedClient returns a Client instance ready for communication with
--// the given server endpoint, using a specific remote API version.
--func NewVersionedClient(endpoint string, apiVersionString string) (*Client, error) {
--	u, err := parseEndpoint(endpoint)
--	if err != nil {
--		return nil, err
--	}
--	var requestedApiVersion ApiVersion
--	if strings.Contains(apiVersionString, ".") {
--		requestedApiVersion, err = NewApiVersion(apiVersionString)
--		if err != nil {
--			return nil, err
--		}
--	}
--	return &Client{
--		HTTPClient:          http.DefaultClient,
--		endpoint:            endpoint,
--		endpointURL:         u,
--		eventMonitor:        new(eventMonitoringState),
--		requestedApiVersion: requestedApiVersion,
--	}, nil
+-// The UnexpectedResponseCodeError structure represents a mismatch in understanding between server and client in terms of response codes.
+-// Most often, this is due to an actual error condition (e.g., getting a 404 for a resource when you expect a 200).
+-// However, it needn't always be the case (e.g., getting a 204 (No Content) response back when a 200 is expected).
+-type UnexpectedResponseCodeError struct {
+-	Url      string
+-	Expected []int
+-	Actual   int
+-	Body     []byte
 -}
 -
--func (c *Client) checkApiVersion() error {
--	serverApiVersionString, err := c.getServerApiVersionString()
--	if err != nil {
--		return err
--	}
--	c.serverApiVersion, err = NewApiVersion(serverApiVersionString)
--	if err != nil {
--		return err
--	}
--	if c.requestedApiVersion == nil {
--		c.expectedApiVersion = c.serverApiVersion
--	} else {
--		c.expectedApiVersion = c.requestedApiVersion
--	}
--	return nil
+-func (err *UnexpectedResponseCodeError) Error() string {
+-	return fmt.Sprintf("Expected HTTP response code %d when accessing URL(%s); got %d instead with the following body:\n%s", err.Expected, err.Url, err.Actual, string(err.Body))
 -}
 -
--// Ping pings the docker server
--//
--// See http://goo.gl/stJENm for more details.
--func (c *Client) Ping() error {
--	path := "/_ping"
--	body, status, err := c.do("GET", path, nil)
--	if err != nil {
--		return err
--	}
--	if status != http.StatusOK {
--		return newError(status, body)
--	}
--	return nil
--}
+-// Request issues an HTTP request, marshaling parameters, and unmarshaling results, as configured in the provided Options parameter.
+-// The Response structure returned, if any, will include accumulated results recovered from the HTTP server.
+-// See the Response structure for more details.
+-func Request(method string, url string, opts Options) (*Response, error) {
+-	var body io.Reader
+-	var response Response
 -
--func (c *Client) getServerApiVersionString() (version string, err error) {
--	body, status, err := c.do("GET", "/version", nil)
--	if err != nil {
--		return "", err
--	}
--	if status != http.StatusOK {
--		return "", fmt.Errorf("Received unexpected status %d while trying to retrieve the server version", status)
--	}
--	var versionResponse map[string]string
--	err = json.Unmarshal(body, &versionResponse)
--	if err != nil {
--		return "", err
+-	client := opts.CustomClient
+-	if client == nil {
+-		client = new(http.Client)
 -	}
--	version = versionResponse["ApiVersion"]
--	return version, nil
--}
 -
--func (c *Client) do(method, path string, data interface{}) ([]byte, int, error) {
--	var params io.Reader
--	if data != nil {
--		buf, err := json.Marshal(data)
--		if err != nil {
--			return nil, -1, err
--		}
--		params = bytes.NewBuffer(buf)
--	}
--	if path != "/version" && !c.SkipServerVersionCheck && c.expectedApiVersion == nil {
--		err := c.checkApiVersion()
--		if err != nil {
--			return nil, -1, err
--		}
--	}
--	req, err := http.NewRequest(method, c.getURL(path), params)
--	if err != nil {
--		return nil, -1, err
--	}
--	req.Header.Set("User-Agent", userAgent)
--	if data != nil {
--		req.Header.Set("Content-Type", "application/json")
--	} else if method == "POST" {
--		req.Header.Set("Content-Type", "plain/text")
--	}
--	var resp *http.Response
--	protocol := c.endpointURL.Scheme
--	address := c.endpointURL.Path
--	if protocol == "unix" {
--		dial, err := net.Dial(protocol, address)
--		if err != nil {
--			return nil, -1, err
--		}
--		defer dial.Close()
--		clientconn := httputil.NewClientConn(dial, nil)
--		resp, err = clientconn.Do(req)
--		if err != nil {
--			return nil, -1, err
--		}
--		defer clientconn.Close()
--	} else {
--		resp, err = c.HTTPClient.Do(req)
--	}
--	if err != nil {
--		if strings.Contains(err.Error(), "connection refused") {
--			return nil, -1, ErrConnectionRefused
--		}
--		return nil, -1, err
--	}
--	defer resp.Body.Close()
--	body, err := ioutil.ReadAll(resp.Body)
--	if err != nil {
--		return nil, -1, err
--	}
--	if resp.StatusCode < 200 || resp.StatusCode >= 400 {
--		return nil, resp.StatusCode, newError(resp.StatusCode, body)
--	}
--	return body, resp.StatusCode, nil
--}
+-	contentType := opts.ContentType
 -
--func (c *Client) stream(method, path string, setRawTerminal, rawJSONStream bool, headers map[string]string, in io.Reader, stdout, stderr io.Writer) error {
--	if (method == "POST" || method == "PUT") && in == nil {
--		in = bytes.NewReader(nil)
--	}
--	if path != "/version" && !c.SkipServerVersionCheck && c.expectedApiVersion == nil {
--		err := c.checkApiVersion()
--		if err != nil {
--			return err
--		}
--	}
--	req, err := http.NewRequest(method, c.getURL(path), in)
--	if err != nil {
--		return err
--	}
--	req.Header.Set("User-Agent", userAgent)
--	if method == "POST" {
--		req.Header.Set("Content-Type", "plain/text")
--	}
--	for key, val := range headers {
--		req.Header.Set(key, val)
--	}
--	var resp *http.Response
--	protocol := c.endpointURL.Scheme
--	address := c.endpointURL.Path
--	if stdout == nil {
--		stdout = ioutil.Discard
--	}
--	if stderr == nil {
--		stderr = ioutil.Discard
--	}
--	if protocol == "unix" {
--		dial, err := net.Dial(protocol, address)
--		if err != nil {
--			return err
--		}
--		clientconn := httputil.NewClientConn(dial, nil)
--		resp, err = clientconn.Do(req)
--		defer clientconn.Close()
--	} else {
--		resp, err = c.HTTPClient.Do(req)
--	}
--	if err != nil {
--		if strings.Contains(err.Error(), "connection refused") {
--			return ErrConnectionRefused
--		}
--		return err
--	}
--	defer resp.Body.Close()
--	if resp.StatusCode < 200 || resp.StatusCode >= 400 {
--		body, err := ioutil.ReadAll(resp.Body)
--		if err != nil {
--			return err
--		}
--		return newError(resp.StatusCode, body)
--	}
--	if resp.Header.Get("Content-Type") == "application/json" {
--		// if we want to get raw json stream, just copy it back to output
--		// without decoding it
--		if rawJSONStream {
--			_, err = io.Copy(stdout, resp.Body)
--			return err
+-	body = nil
+-	if opts.ReqBody != nil {
+-		if contentType == "" {
+-			contentType = "application/json"
 -		}
--		dec := json.NewDecoder(resp.Body)
--		for {
--			var m jsonMessage
--			if err := dec.Decode(&m); err == io.EOF {
--				break
--			} else if err != nil {
--				return err
--			}
--			if m.Stream != "" {
--				fmt.Fprint(stdout, m.Stream)
--			} else if m.Progress != "" {
--				fmt.Fprintf(stdout, "%s %s\r", m.Status, m.Progress)
--			} else if m.Error != "" {
--				return errors.New(m.Error)
+-
+-		if contentType == "application/json" {
+-			bodyText, err := json.Marshal(opts.ReqBody)
+-			if err != nil {
+-				return nil, err
 -			}
--			if m.Status != "" {
--				fmt.Fprintln(stdout, m.Status)
+-			body = strings.NewReader(string(bodyText))
+-			if opts.DumpReqJson {
+-				log.Printf("Making request:\n%#v\n", string(bodyText))
 -			}
--		}
--	} else {
--		if setRawTerminal {
--			_, err = io.Copy(stdout, resp.Body)
 -		} else {
--			_, err = stdCopy(stdout, stderr, resp.Body)
+-			// assume opts.ReqBody implements the correct interface
+-			body = opts.ReqBody.(io.Reader)
 -		}
--		return err
 -	}
--	return nil
--}
 -
--func (c *Client) hijack(method, path string, success chan struct{}, setRawTerminal bool, in io.Reader, stderr, stdout io.Writer, data interface{}) error {
--	if path != "/version" && !c.SkipServerVersionCheck && c.expectedApiVersion == nil {
--		err := c.checkApiVersion()
--		if err != nil {
--			return err
+-	req, err := http.NewRequest(method, url, body)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	if contentType != "" {
+-		req.Header.Add("Content-Type", contentType)
+-	}
+-
+-	if opts.ContentLength > 0 {
+-		req.ContentLength = opts.ContentLength
+-		req.Header.Add("Content-Length", string(opts.ContentLength))
+-	}
+-
+-	if opts.MoreHeaders != nil {
+-		for k, v := range opts.MoreHeaders {
+-			req.Header.Add(k, v)
 -		}
 -	}
 -
--	var params io.Reader
--	if data != nil {
--		buf, err := json.Marshal(data)
--		if err != nil {
--			return err
+-	if accept := req.Header.Get("Accept"); accept == "" {
+-		accept = opts.Accept
+-		if accept == "" {
+-			accept = "application/json"
 -		}
--		params = bytes.NewBuffer(buf)
+-		req.Header.Add("Accept", accept)
 -	}
 -
--	if stdout == nil {
--		stdout = ioutil.Discard
+-	if opts.SetHeaders != nil {
+-		err = opts.SetHeaders(req)
+-		if err != nil {
+-			return &response, err
+-		}
 -	}
--	if stderr == nil {
--		stderr = ioutil.Discard
+-
+-	httpResponse, err := client.Do(req)
+-	if httpResponse != nil {
+-		response.HttpResponse = *httpResponse
+-		response.StatusCode = httpResponse.StatusCode
 -	}
--	req, err := http.NewRequest(method, c.getURL(path), params)
+-
 -	if err != nil {
--		return err
--	}
--	req.Header.Set("Content-Type", "plain/text")
--	protocol := c.endpointURL.Scheme
--	address := c.endpointURL.Path
--	if protocol != "unix" {
--		protocol = "tcp"
--		address = c.endpointURL.Host
+-		return &response, err
 -	}
--	dial, err := net.Dial(protocol, address)
--	if err != nil {
--		return err
+-	// This if-statement is legacy code, preserved for backward compatibility.
+-	if opts.StatusCode != nil {
+-		*opts.StatusCode = httpResponse.StatusCode
 -	}
--	defer dial.Close()
--	clientconn := httputil.NewClientConn(dial, nil)
--	clientconn.Do(req)
--	if success != nil {
--		success <- struct{}{}
--		<-success
+-
+-	acceptableResponseCodes := opts.OkCodes
+-	if len(acceptableResponseCodes) != 0 {
+-		if not_in(httpResponse.StatusCode, acceptableResponseCodes) {
+-			b, _ := ioutil.ReadAll(httpResponse.Body)
+-			httpResponse.Body.Close()
+-			return &response, &UnexpectedResponseCodeError{
+-				Url:      url,
+-				Expected: acceptableResponseCodes,
+-				Actual:   httpResponse.StatusCode,
+-				Body:     b,
+-			}
+-		}
 -	}
--	rwc, br := clientconn.Hijack()
--	errs := make(chan error, 2)
--	exit := make(chan bool)
--	go func() {
--		defer close(exit)
--		var err error
--		if setRawTerminal {
--			_, err = io.Copy(stdout, br)
--		} else {
--			_, err = stdCopy(stdout, stderr, br)
+-	if opts.Results != nil {
+-		defer httpResponse.Body.Close()
+-		jsonResult, err := ioutil.ReadAll(httpResponse.Body)
+-		response.JsonResult = jsonResult
+-		if err != nil {
+-			return &response, err
 -		}
--		errs <- err
--	}()
--	go func() {
--		var err error
--		if in != nil {
--			_, err = io.Copy(rwc, in)
+-
+-		err = json.Unmarshal(jsonResult, opts.Results)
+-		// This if-statement is legacy code, preserved for backward compatibility.
+-		if opts.ResponseJson != nil {
+-			*opts.ResponseJson = jsonResult
 -		}
--		rwc.(interface {
--			CloseWrite() error
--		}).CloseWrite()
--		errs <- err
--	}()
--	<-exit
--	return <-errs
+-	}
+-	return &response, err
 -}
 -
--func (c *Client) getURL(path string) string {
--	urlStr := strings.TrimRight(c.endpointURL.String(), "/")
--	if c.endpointURL.Scheme == "unix" {
--		urlStr = ""
+-// not_in returns false if, and only if, the provided needle is _not_
+-// in the given set of integers.
+-func not_in(needle int, haystack []int) bool {
+-	for _, straw := range haystack {
+-		if needle == straw {
+-			return false
+-		}
 -	}
+-	return true
+-}
 -
--	if c.requestedApiVersion != nil {
--		return fmt.Sprintf("%s/v%s%s", urlStr, c.requestedApiVersion, path)
--	} else {
--		return fmt.Sprintf("%s%s", urlStr, path)
+-// Post makes a POST request against a server using the provided HTTP client.
+-// The url must be a fully-formed URL string.
+-// DEPRECATED.  Use Request() instead.
+-func Post(url string, opts Options) error {
+-	r, err := Request("POST", url, opts)
+-	if opts.Response != nil {
+-		*opts.Response = r
 -	}
+-	return err
 -}
 -
--type jsonMessage struct {
--	Status   string `json:"status,omitempty"`
--	Progress string `json:"progress,omitempty"`
--	Error    string `json:"error,omitempty"`
--	Stream   string `json:"stream,omitempty"`
+-// Get makes a GET request against a server using the provided HTTP client.
+-// The url must be a fully-formed URL string.
+-// DEPRECATED.  Use Request() instead.
+-func Get(url string, opts Options) error {
+-	r, err := Request("GET", url, opts)
+-	if opts.Response != nil {
+-		*opts.Response = r
+-	}
+-	return err
 -}
 -
--func queryString(opts interface{}) string {
--	if opts == nil {
--		return ""
--	}
--	value := reflect.ValueOf(opts)
--	if value.Kind() == reflect.Ptr {
--		value = value.Elem()
--	}
--	if value.Kind() != reflect.Struct {
--		return ""
--	}
--	items := url.Values(map[string][]string{})
--	for i := 0; i < value.NumField(); i++ {
--		field := value.Type().Field(i)
--		if field.PkgPath != "" {
--			continue
--		}
--		key := field.Tag.Get("qs")
--		if key == "" {
--			key = strings.ToLower(field.Name)
--		} else if key == "-" {
--			continue
--		}
--		v := value.Field(i)
--		switch v.Kind() {
--		case reflect.Bool:
--			if v.Bool() {
--				items.Add(key, "1")
--			}
--		case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
--			if v.Int() > 0 {
--				items.Add(key, strconv.FormatInt(v.Int(), 10))
--			}
--		case reflect.Float32, reflect.Float64:
--			if v.Float() > 0 {
--				items.Add(key, strconv.FormatFloat(v.Float(), 'f', -1, 64))
--			}
--		case reflect.String:
--			if v.String() != "" {
--				items.Add(key, v.String())
--			}
--		case reflect.Ptr:
--			if !v.IsNil() {
--				if b, err := json.Marshal(v.Interface()); err == nil {
--					items.Add(key, string(b))
--				}
--			}
--		}
+-// Delete makes a DELETE request against a server using the provided HTTP client.
+-// The url must be a fully-formed URL string.
+-// DEPRECATED.  Use Request() instead.
+-func Delete(url string, opts Options) error {
+-	r, err := Request("DELETE", url, opts)
+-	if opts.Response != nil {
+-		*opts.Response = r
 -	}
--	return items.Encode()
+-	return err
 -}
 -
--// Error represents failures in the API. It represents a failure from the API.
--type Error struct {
--	Status  int
--	Message string
+-// Put makes a PUT request against a server using the provided HTTP client.
+-// The url must be a fully-formed URL string.
+-// DEPRECATED.  Use Request() instead.
+-func Put(url string, opts Options) error {
+-	r, err := Request("PUT", url, opts)
+-	if opts.Response != nil {
+-		*opts.Response = r
+-	}
+-	return err
 -}
 -
--func newError(status int, body []byte) *Error {
--	return &Error{Status: status, Message: string(body)}
+-// Options describes a set of optional parameters to the various request calls.
+-//
+-// The custom client can be used for a variety of purposes beyond selecting encrypted versus unencrypted channels.
+-// Transports can be defined to provide augmented logging, header manipulation, et. al.
+-//
+-// If the ReqBody field is provided, it will be embedded as a JSON object.
+-// Otherwise, provide nil.
+-//
+-// If JSON output is to be expected from the response,
+-// provide either a pointer to the container structure in Results,
+-// or a pointer to a nil-initialized pointer variable.
+-// The latter method will cause the unmarshaller to allocate the container type for you.
+-// If no response is expected, provide a nil Results value.
+-//
+-// The MoreHeaders map, if non-nil or empty, provides a set of headers to add to those
+-// already present in the request.  At present, only Accepted and Content-Type are set
+-// by default.
+-//
+-// OkCodes provides a set of acceptable, positive responses.
+-//
+-// If provided, StatusCode specifies a pointer to an integer, which will receive the
+-// returned HTTP status code, successful or not.  DEPRECATED; use the Response.StatusCode field instead for new software.
+-//
+-// ResponseJson, if specified, provides a means for returning the raw JSON.  This is
+-// most useful for diagnostics.  DEPRECATED; use the Response.JsonResult field instead for new software.
+-//
+-// DumpReqJson, if set to true, will cause the request to appear to stdout for debugging purposes.
+-// This attribute may be removed at any time in the future; DO NOT use this attribute in production software.
+-//
+-// Response, if set, provides a way to communicate the complete set of HTTP response, raw JSON, status code, and
+-// other useful attributes back to the caller.  Note that the Request() method returns a Response structure as part
+-// of its public interface; you don't need to set the Response field here to use this structure.  The Response field
+-// exists primarily for legacy or deprecated functions.
+-//
+-// SetHeaders allows the caller to provide code to set any custom headers programmatically.  Typically, this
+-// facility can invoke, e.g., SetBasicAuth() on the request to easily set up authentication.
+-// Any error generated will terminate the request and will propegate back to the caller.
+-type Options struct {
+-	CustomClient  *http.Client
+-	ReqBody       interface{}
+-	Results       interface{}
+-	MoreHeaders   map[string]string
+-	OkCodes       []int
+-	StatusCode    *int    `DEPRECATED`
+-	DumpReqJson   bool    `UNSUPPORTED`
+-	ResponseJson  *[]byte `DEPRECATED`
+-	Response      **Response
+-	ContentType   string `json:"Content-Type,omitempty"`
+-	ContentLength int64  `json:"Content-Length,omitempty"`
+-	Accept        string `json:"Accept,omitempty"`
+-	SetHeaders    func(r *http.Request) error
 -}
 -
--func (e *Error) Error() string {
--	return fmt.Sprintf("API error (%d): %s", e.Status, e.Message)
--}
+-// Response contains return values from the various request calls.
+-//
+-// HttpResponse will return the http response from the request call.
+-// Note: HttpResponse.Body is always closed and will not be available from this return value.
+-//
+-// StatusCode specifies the returned HTTP status code, successful or not.
+-//
+-// If Results is specified in the Options:
+-// - JsonResult will contain the raw return from the request call
+-//   This is most useful for diagnostics.
+-// - Result will contain the unmarshalled json either in the Result passed in
+-//   or the unmarshaller will allocate the container type for you.
 -
--func parseEndpoint(endpoint string) (*url.URL, error) {
--	u, err := url.Parse(endpoint)
--	if err != nil {
--		return nil, ErrInvalidEndpoint
--	}
--	if u.Scheme == "tcp" {
--		u.Scheme = "http"
--	}
--	if u.Scheme != "http" && u.Scheme != "https" && u.Scheme != "unix" {
--		return nil, ErrInvalidEndpoint
--	}
--	if u.Scheme != "unix" {
--		_, port, err := net.SplitHostPort(u.Host)
--		if err != nil {
--			if e, ok := err.(*net.AddrError); ok {
--				if e.Err == "missing port in address" {
--					return u, nil
--				}
--			}
--			return nil, ErrInvalidEndpoint
--		}
--		number, err := strconv.ParseInt(port, 10, 64)
--		if err == nil && number > 0 && number < 65536 {
--			return u, nil
--		}
--	} else {
--		return u, nil // we don't need port when using a unix socket
--	}
--	return nil, ErrInvalidEndpoint
+-type Response struct {
+-	HttpResponse http.Response
+-	JsonResult   []byte
+-	Results      interface{}
+-	StatusCode   int
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/client_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/client_test.go
+diff --git a/Godeps/_workspace/src/github.com/racker/perigee/api_test.go b/Godeps/_workspace/src/github.com/racker/perigee/api_test.go
 deleted file mode 100644
-index 9def171..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/client_test.go
+index da943b2..0000000
+--- a/Godeps/_workspace/src/github.com/racker/perigee/api_test.go
 +++ /dev/null
-@@ -1,290 +0,0 @@
--// Copyright 2014 go-dockerclient 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 docker
+@@ -1,226 +0,0 @@
+-package perigee
 -
 -import (
+-	"bytes"
 -	"fmt"
--	"io/ioutil"
 -	"net/http"
--	"net/url"
--	"reflect"
--	"strconv"
+-	"net/http/httptest"
 -	"strings"
 -	"testing"
 -)
 -
--func TestNewAPIClient(t *testing.T) {
--	endpoint := "http://localhost:4243"
--	client, err := NewClient(endpoint)
+-func TestNormal(t *testing.T) {
+-	handler := http.HandlerFunc(
+-		func(w http.ResponseWriter, r *http.Request) {
+-			w.Write([]byte("testing"))
+-		})
+-	ts := httptest.NewServer(handler)
+-	defer ts.Close()
+-
+-	response, err := Request("GET", ts.URL, Options{})
 -	if err != nil {
--		t.Fatal(err)
+-		t.Fatalf("should not have error: %s", err)
 -	}
--	if client.endpoint != endpoint {
--		t.Errorf("Expected endpoint %s. Got %s.", endpoint, client.endpoint)
+-	if response.StatusCode != 200 {
+-		t.Fatalf("response code %d is not 200", response.StatusCode)
 -	}
--	if client.HTTPClient != http.DefaultClient {
--		t.Errorf("Expected http.Client %#v. Got %#v.", http.DefaultClient, client.HTTPClient)
+-}
+-
+-func TestOKCodes(t *testing.T) {
+-	expectCode := 201
+-	handler := http.HandlerFunc(
+-		func(w http.ResponseWriter, r *http.Request) {
+-			w.WriteHeader(expectCode)
+-			w.Write([]byte("testing"))
+-		})
+-	ts := httptest.NewServer(handler)
+-	defer ts.Close()
+-
+-	options := Options{
+-		OkCodes: []int{expectCode},
 -	}
--	// test unix socket endpoints
--	endpoint = "unix:///var/run/docker.sock"
--	client, err = NewClient(endpoint)
+-	results, err := Request("GET", ts.URL, options)
 -	if err != nil {
--		t.Fatal(err)
--	}
--	if client.endpoint != endpoint {
--		t.Errorf("Expected endpoint %s. Got %s.", endpoint, client.endpoint)
--	}
--	if !client.SkipServerVersionCheck {
--		t.Error("Expected SkipServerVersionCheck to be true, got false")
+-		t.Fatalf("should not have error: %s", err)
 -	}
--	if client.requestedApiVersion != nil {
--		t.Errorf("Expected requestedApiVersion to be nil, got %#v.", client.requestedApiVersion)
+-	if results.StatusCode != expectCode {
+-		t.Fatalf("response code %d is not %d", results.StatusCode, expectCode)
 -	}
 -}
 -
--func TestNewVersionedClient(t *testing.T) {
--	endpoint := "http://localhost:4243"
--	client, err := NewVersionedClient(endpoint, "1.12")
+-func TestLocation(t *testing.T) {
+-	newLocation := "http://www.example.com"
+-	handler := http.HandlerFunc(
+-		func(w http.ResponseWriter, r *http.Request) {
+-			w.Header().Set("Location", newLocation)
+-			w.Write([]byte("testing"))
+-		})
+-	ts := httptest.NewServer(handler)
+-	defer ts.Close()
+-
+-	response, err := Request("GET", ts.URL, Options{})
 -	if err != nil {
--		t.Fatal(err)
--	}
--	if client.endpoint != endpoint {
--		t.Errorf("Expected endpoint %s. Got %s.", endpoint, client.endpoint)
--	}
--	if client.HTTPClient != http.DefaultClient {
--		t.Errorf("Expected http.Client %#v. Got %#v.", http.DefaultClient, client.HTTPClient)
+-		t.Fatalf("should not have error: %s", err)
 -	}
--	if reqVersion := client.requestedApiVersion.String(); reqVersion != "1.12" {
--		t.Errorf("Wrong requestApiVersion. Want %q. Got %q.", "1.12", reqVersion)
+-
+-	location, err := response.HttpResponse.Location()
+-	if err != nil {
+-		t.Fatalf("should not have error: %s", err)
 -	}
--	if client.SkipServerVersionCheck {
--		t.Error("Expected SkipServerVersionCheck to be false, got true")
+-
+-	if location.String() != newLocation {
+-		t.Fatalf("location returned \"%s\" is not \"%s\"", location.String(), newLocation)
 -	}
 -}
 -
--func TestNewClientInvalidEndpoint(t *testing.T) {
--	cases := []string{
--		"htp://localhost:3243", "http://localhost:a", "localhost:8080",
--		"", "localhost", "http://localhost:8080:8383", "http://localhost:65536",
--		"https://localhost:-20",
+-func TestHeaders(t *testing.T) {
+-	newLocation := "http://www.example.com"
+-	handler := http.HandlerFunc(
+-		func(w http.ResponseWriter, r *http.Request) {
+-			w.Header().Set("Location", newLocation)
+-			w.Write([]byte("testing"))
+-		})
+-	ts := httptest.NewServer(handler)
+-	defer ts.Close()
+-
+-	response, err := Request("GET", ts.URL, Options{})
+-	if err != nil {
+-		t.Fatalf("should not have error: %s", err)
 -	}
--	for _, c := range cases {
--		client, err := NewClient(c)
--		if client != nil {
--			t.Errorf("Want <nil> client for invalid endpoint, got %#v.", client)
--		}
--		if !reflect.DeepEqual(err, ErrInvalidEndpoint) {
--			t.Errorf("NewClient(%q): Got invalid error for invalid endpoint. Want %#v. Got %#v.", c, ErrInvalidEndpoint, err)
--		}
+-
+-	location := response.HttpResponse.Header.Get("Location")
+-	if location == "" {
+-		t.Fatalf("Location should not empty")
+-	}
+-
+-	if location != newLocation {
+-		t.Fatalf("location returned \"%s\" is not \"%s\"", location, newLocation)
 -	}
 -}
 -
--func TestGetURL(t *testing.T) {
--	var tests = []struct {
--		endpoint string
--		path     string
--		expected string
--	}{
--		{"http://localhost:4243/", "/", "http://localhost:4243/"},
--		{"http://localhost:4243", "/", "http://localhost:4243/"},
--		{"http://localhost:4243", "/containers/ps", "http://localhost:4243/containers/ps"},
--		{"tcp://localhost:4243", "/containers/ps", "http://localhost:4243/containers/ps"},
--		{"http://localhost:4243/////", "/", "http://localhost:4243/"},
--		{"unix:///var/run/docker.socket", "/containers", "/containers"},
+-func TestCustomHeaders(t *testing.T) {
+-	var contentType, accept, contentLength string
+-
+-	handler := http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+-		m := map[string][]string(r.Header)
+-		contentType = m["Content-Type"][0]
+-		accept = m["Accept"][0]
+-		contentLength = m["Content-Length"][0]
+-	})
+-	ts := httptest.NewServer(handler)
+-	defer ts.Close()
+-
+-	_, err := Request("GET", ts.URL, Options{
+-		ContentLength: 5,
+-		ContentType:   "x-application/vb",
+-		Accept:        "x-application/c",
+-		ReqBody:       strings.NewReader("Hello"),
+-	})
+-	if err != nil {
+-		t.Fatalf(err.Error())
 -	}
--	for _, tt := range tests {
--		client, _ := NewClient(tt.endpoint)
--		client.endpoint = tt.endpoint
--		client.SkipServerVersionCheck = true
--		got := client.getURL(tt.path)
--		if got != tt.expected {
--			t.Errorf("getURL(%q): Got %s. Want %s.", tt.path, got, tt.expected)
--		}
+-
+-	if contentType != "x-application/vb" {
+-		t.Fatalf("I expected x-application/vb; got ", contentType)
 -	}
--}
 -
--func TestError(t *testing.T) {
--	err := newError(400, []byte("bad parameter"))
--	expected := Error{Status: 400, Message: "bad parameter"}
--	if !reflect.DeepEqual(expected, *err) {
--		t.Errorf("Wrong error type. Want %#v. Got %#v.", expected, *err)
+-	if contentLength != "5" {
+-		t.Fatalf("I expected 5 byte content length; got ", contentLength)
 -	}
--	message := "API error (400): bad parameter"
--	if err.Error() != message {
--		t.Errorf("Wrong error message. Want %q. Got %q.", message, err.Error())
+-
+-	if accept != "x-application/c" {
+-		t.Fatalf("I expected x-application/c; got ", accept)
 -	}
 -}
 -
--func TestQueryString(t *testing.T) {
--	v := float32(2.4)
--	f32QueryString := fmt.Sprintf("w=%s&x=10&y=10.35", strconv.FormatFloat(float64(v), 'f', -1, 64))
--	jsonPerson := url.QueryEscape(`{"Name":"gopher","age":4}`)
--	var tests = []struct {
--		input interface{}
--		want  string
--	}{
--		{&ListContainersOptions{All: true}, "all=1"},
--		{ListContainersOptions{All: true}, "all=1"},
--		{ListContainersOptions{Before: "something"}, "before=something"},
--		{ListContainersOptions{Before: "something", Since: "other"}, "before=something&since=other"},
--		{dumb{X: 10, Y: 10.35000}, "x=10&y=10.35"},
--		{dumb{W: v, X: 10, Y: 10.35000}, f32QueryString},
--		{dumb{X: 10, Y: 10.35000, Z: 10}, "x=10&y=10.35&zee=10"},
--		{dumb{v: 4, X: 10, Y: 10.35000}, "x=10&y=10.35"},
--		{dumb{T: 10, Y: 10.35000}, "y=10.35"},
--		{dumb{Person: &person{Name: "gopher", Age: 4}}, "p=" + jsonPerson},
--		{nil, ""},
--		{10, ""},
--		{"not_a_struct", ""},
+-func TestJson(t *testing.T) {
+-	newLocation := "http://www.example.com"
+-	jsonBytes := []byte(`{"foo": {"bar": "baz"}}`)
+-	handler := http.HandlerFunc(
+-		func(w http.ResponseWriter, r *http.Request) {
+-			w.Header().Set("Location", newLocation)
+-			w.Write(jsonBytes)
+-		})
+-	ts := httptest.NewServer(handler)
+-	defer ts.Close()
+-
+-	type Data struct {
+-		Foo struct {
+-			Bar string `json:"bar"`
+-		} `json:"foo"`
 -	}
--	for _, tt := range tests {
--		got := queryString(tt.input)
--		if got != tt.want {
--			t.Errorf("queryString(%v). Want %q. Got %q.", tt.input, tt.want, got)
--		}
+-	var data Data
+-
+-	response, err := Request("GET", ts.URL, Options{Results: &data})
+-	if err != nil {
+-		t.Fatalf("should not have error: %s", err)
 -	}
--}
 -
--func TestNewApiVersionFailures(t *testing.T) {
--	var tests = []struct {
--		input         string
--		expectedError string
--	}{
--		{"1-0", `Unable to parse version "1-0"`},
--		{"1.0-beta", `Unable to parse version "1.0-beta": "0-beta" is not an integer`},
+-	if bytes.Compare(jsonBytes, response.JsonResult) != 0 {
+-		t.Fatalf("json returned \"%s\" is not \"%s\"", response.JsonResult, jsonBytes)
 -	}
--	for _, tt := range tests {
--		v, err := NewApiVersion(tt.input)
--		if v != nil {
--			t.Errorf("Expected <nil> version, got %v.", v)
--		}
--		if err.Error() != tt.expectedError {
--			t.Errorf("NewApiVersion(%q): wrong error. Want %q. Got %q", tt.input, tt.expectedError, err.Error())
--		}
+-
+-	if data.Foo.Bar != "baz" {
+-		t.Fatalf("Results returned %v", data)
 -	}
 -}
 -
--func TestApiVersions(t *testing.T) {
--	var tests = []struct {
--		a                              string
--		b                              string
--		expectedALessThanB             bool
--		expectedALessThanOrEqualToB    bool
--		expectedAGreaterThanB          bool
--		expectedAGreaterThanOrEqualToB bool
--	}{
--		{"1.11", "1.11", false, true, false, true},
--		{"1.10", "1.11", true, true, false, false},
--		{"1.11", "1.10", false, false, true, true},
+-func TestSetHeaders(t *testing.T) {
+-	var wasCalled bool
+-	handler := http.HandlerFunc(
+-		func(w http.ResponseWriter, r *http.Request) {
+-			w.Write([]byte("Hi"))
+-		})
+-	ts := httptest.NewServer(handler)
+-	defer ts.Close()
 -
--		{"1.9", "1.11", true, true, false, false},
--		{"1.11", "1.9", false, false, true, true},
+-	_, err := Request("GET", ts.URL, Options{
+-		SetHeaders: func(r *http.Request) error {
+-			wasCalled = true
+-			return nil
+-		},
+-	})
 -
--		{"1.1.1", "1.1", false, false, true, true},
--		{"1.1", "1.1.1", true, true, false, false},
+-	if err != nil {
+-		t.Fatal(err)
+-	}
 -
--		{"2.1", "1.1.1", false, false, true, true},
--		{"2.1", "1.3.1", false, false, true, true},
--		{"1.1.1", "2.1", true, true, false, false},
--		{"1.3.1", "2.1", true, true, false, false},
+-	if !wasCalled {
+-		t.Fatal("I expected header setter callback to be called, but it wasn't")
 -	}
 -
--	for _, tt := range tests {
--		a, _ := NewApiVersion(tt.a)
--		b, _ := NewApiVersion(tt.b)
+-	myError := fmt.Errorf("boo")
 -
--		if tt.expectedALessThanB && !a.LessThan(b) {
--			t.Errorf("Expected %#v < %#v", a, b)
--		}
--		if tt.expectedALessThanOrEqualToB && !a.LessThanOrEqualTo(b) {
--			t.Errorf("Expected %#v <= %#v", a, b)
--		}
--		if tt.expectedAGreaterThanB && !a.GreaterThan(b) {
--			t.Errorf("Expected %#v > %#v", a, b)
--		}
--		if tt.expectedAGreaterThanOrEqualToB && !a.GreaterThanOrEqualTo(b) {
--			t.Errorf("Expected %#v >= %#v", a, b)
--		}
+-	_, err = Request("GET", ts.URL, Options{
+-		SetHeaders: func(r *http.Request) error {
+-			return myError
+-		},
+-	})
+-
+-	if err != myError {
+-		t.Fatal("I expected errors to propegate back to the caller.")
 -	}
 -}
 -
--func TestPing(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	err := client.Ping()
+-func TestBodilessMethodsAreSentWithoutContentHeaders(t *testing.T) {
+-	var h map[string][]string
+-
+-	handler := http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+-		h = r.Header
+-	})
+-	ts := httptest.NewServer(handler)
+-	defer ts.Close()
+-
+-	_, err := Request("GET", ts.URL, Options{})
 -	if err != nil {
--		t.Fatal(err)
+-		t.Fatalf(err.Error())
 -	}
--}
 -
--func TestPingFailing(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusInternalServerError}
--	client := newTestClient(fakeRT)
--	err := client.Ping()
--	if err == nil {
--		t.Fatal("Expected non nil error, got nil")
--	}
--	expectedErrMsg := "API error (500): "
--	if err.Error() != expectedErrMsg {
--		t.Fatalf("Expected error to be %q, got: %q", expectedErrMsg, err.Error())
+-	if len(h["Content-Type"]) != 0 {
+-		t.Fatalf("I expected nothing for Content-Type but got ", h["Content-Type"])
 -	}
--}
 -
--func TestPingFailingWrongStatus(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusAccepted}
--	client := newTestClient(fakeRT)
--	err := client.Ping()
--	if err == nil {
--		t.Fatal("Expected non nil error, got nil")
--	}
--	expectedErrMsg := "API error (202): "
--	if err.Error() != expectedErrMsg {
--		t.Fatalf("Expected error to be %q, got: %q", expectedErrMsg, err.Error())
+-	if len(h["Content-Length"]) != 0 {
+-		t.Fatalf("I expected nothing for Content-Length but got ", h["Content-Length"])
 -	}
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/.travis.yml b/Godeps/_workspace/src/github.com/rackspace/gophercloud/.travis.yml
+deleted file mode 100644
+index cf4f8ca..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/.travis.yml
++++ /dev/null
+@@ -1,14 +0,0 @@
+-language: go
+-install:
+-  - go get -v -tags 'fixtures acceptance' ./...
+-go:
+-  - 1.1
+-  - 1.2
+-  - tip
+-script: script/cibuild
+-after_success:
+-  - go get code.google.com/p/go.tools/cmd/cover
+-  - go get github.com/axw/gocov/gocov
+-  - go get github.com/mattn/goveralls
+-  - export PATH=$PATH:$HOME/gopath/bin/
+-  - goveralls 2k7PTU3xa474Hymwgdj6XjqenNfGTNkO8
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/CONTRIBUTING.md b/Godeps/_workspace/src/github.com/rackspace/gophercloud/CONTRIBUTING.md
+deleted file mode 100644
+index 4f596a1..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/CONTRIBUTING.md
++++ /dev/null
+@@ -1,275 +0,0 @@
+-# Contributing to gophercloud
 -
--type FakeRoundTripper struct {
--	message  string
--	status   int
--	header   map[string]string
--	requests []*http.Request
--}
+-- [Getting started](#getting-started)
+-- [Tests](#tests)
+-- [Style guide](#basic-style-guide)
+-- [5 ways to get involved](#5-ways-to-get-involved)
 -
--func (rt *FakeRoundTripper) RoundTrip(r *http.Request) (*http.Response, error) {
--	body := strings.NewReader(rt.message)
--	rt.requests = append(rt.requests, r)
--	res := &http.Response{
--		StatusCode: rt.status,
--		Body:       ioutil.NopCloser(body),
--		Header:     make(http.Header),
--	}
--	for k, v := range rt.header {
--		res.Header.Set(k, v)
--	}
--	return res, nil
--}
+-## Setting up your git workspace
 -
--func (rt *FakeRoundTripper) Reset() {
--	rt.requests = nil
+-As a contributor you will need to setup your workspace in a slightly different
+-way than just downloading it. Here are the basic installation instructions:
+-
+-1. Configure your `$GOPATH` and run `go get` as described in the main
+-[README](/#how-to-install).
+-
+-2. Move into the directory that houses your local repository:
+-
+-   ```bash
+-   cd ${GOPATH}/src/github.com/rackspace/gophercloud
+-   ```
+-
+-3. Fork the `rackspace/gophercloud` repository and update your remote refs. You
+-will need to rename the `origin` remote branch to `upstream`, and add your
+-fork as `origin` instead:
+-
+-   ```bash
+-   git remote rename origin upstream
+-   git remote add origin git at github.com/<my_username>/gophercloud
+-   ```
+-
+-4. Checkout the latest development branch ([click here](/branches) to see all
+-the branches):
+-
+-   ```bash
+-   git checkout release/v1.0.1
+-   ```
+-
+-5. If you're working on something (discussed more in detail below), you will
+-need to checkout a new feature branch:
+-
+-   ```bash
+-   git checkout -b my-new-feature
+-   ```
+-
+-Another thing to bear in mind is that you will need to add a few extra
+-environment variables for acceptance tests - this is documented in our
+-[acceptance tests readme](/acceptance).
+-
+-## Tests
+-
+-When working on a new or existing feature, testing will be the backbone of your
+-work since it helps uncover and prevent regressions in the codebase. There are
+-two types of test we use in gophercloud: unit tests and acceptance tests, which
+-are both described below.
+-
+-### Unit tests
+-
+-Unit tests are the fine-grained tests that establish and ensure the behaviour
+-of individual units of functionality. We usually test on an
+-operation-by-operation basis (an operation typically being an API action) with
+-the use of mocking to set up explicit expectations. Each operation will set up
+-its HTTP response expectation, and then test how the system responds when fed
+-this controlled, pre-determined input.
+-
+-To make life easier, we've introduced a bunch of test helpers to simplify the
+-process of testing expectations with assertions:
+-
+-```go
+-import (
+-  "testing"
+-
+-  "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestSomething(t *testing.T) {
+-  result, err := Operation()
+-
+-  testhelper.AssertEquals(t, "foo", result.Bar)
+-  testhelper.AssertNoErr(t, err)
 -}
 -
--type person struct {
--	Name string
--	Age  int `json:"age"`
+-func TestSomethingElse(t *testing.T) {
+-  testhelper.CheckEquals(t, "expected", "actual")
 -}
+-```
 -
--type dumb struct {
--	T      int `qs:"-"`
--	v      int
--	W      float32
--	X      int
--	Y      float64
--	Z      int     `qs:"zee"`
--	Person *person `qs:"p"`
+-`AssertEquals` and `AssertNoErr` will throw a fatal error if a value does not
+-match an expected value or if an error has been declared, respectively. You can
+-also use `CheckEquals` and `CheckNoErr` for the same purpose; the only difference
+-being that `t.Errorf` is raised rather than `t.Fatalf`.
+-
+-Here is a truncated example of mocked HTTP responses:
+-
+-```go
+-import (
+-	"testing"
+-
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
+-
+-func TestGet(t *testing.T) {
+-	// Setup the HTTP request multiplexer and server
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/networks/d32019d3-bc6e-4319-9c1d-6722fc136a22", func(w http.ResponseWriter, r *http.Request) {
+-		// Test we're using the correct HTTP method
+-		th.TestMethod(t, r, "GET")
+-
+-		// Test we're setting the auth token
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		// Set the appropriate headers for our mocked response
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		// Set the HTTP body
+-		fmt.Fprintf(w, `
+-{
+-    "network": {
+-        "status": "ACTIVE",
+-        "name": "private-network",
+-        "admin_state_up": true,
+-        "tenant_id": "4fd44f30292945e481c7b8a0c8908869",
+-        "shared": true,
+-        "id": "d32019d3-bc6e-4319-9c1d-6722fc136a22"
+-    }
 -}
+-			`)
+-	})
 -
--type fakeEndpointURL struct {
--	Scheme string
+-	// Call our API operation
+-	network, err := Get(fake.ServiceClient(), "d32019d3-bc6e-4319-9c1d-6722fc136a22").Extract()
+-
+-	// Assert no errors and equality
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, n.Status, "ACTIVE")
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/container.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/container.go
+-```
+-
+-### Acceptance tests
+-
+-As we've already mentioned, unit tests have a very narrow and confined focus -
+-they test small units of behaviour. Acceptance tests on the other hand have a
+-far larger scope: they are fully functional tests that test the entire API of a
+-service in one fell swoop. They don't care about unit isolation or mocking
+-expectations, they instead do a full run-through and consequently test how the
+-entire system _integrates_ together. When an API satisfies expectations, it
+-proves by default that the requirements for a contract have been met.
+-
+-Please be aware that acceptance tests will hit a live API - and may incur
+-service charges from your provider. Although most tests handle their own
+-teardown procedures, it is always worth manually checking that resources are
+-deleted after the test suite finishes.
+-
+-### Running tests
+-
+-To run all tests:
+-
+-```bash
+-go test ./...
+-```
+-
+-To run all tests with verbose output:
+-
+-```bash
+-go test -v ./...
+-```
+-
+-To run tests that match certain [build tags]():
+-
+-```bash
+-go test -tags "foo bar" ./...
+-```
+-
+-To run tests for a particular sub-package:
+-
+-```bash
+-cd ./path/to/package && go test .
+-```
+-
+-## Basic style guide
+-
+-We follow the standard formatting recommendations and language idioms set out
+-in the [Effective Go](https://golang.org/doc/effective_go.html) guide. It's
+-definitely worth reading - but the relevant sections are
+-[formatting](https://golang.org/doc/effective_go.html#formatting)
+-and [names](https://golang.org/doc/effective_go.html#names).
+-
+-## 5 ways to get involved
+-
+-There are five main ways you can get involved in our open-source project, and
+-each is described briefly below. Once you've made up your mind and decided on
+-your fix, you will need to follow the same basic steps that all submissions are
+-required to adhere to:
+-
+-1. [fork](https://help.github.com/articles/fork-a-repo/) the `rackspace/gophercloud` repository
+-2. checkout a [new branch](https://github.com/Kunena/Kunena-Forum/wiki/Create-a-new-branch-with-git-and-manage-branches)
+-3. submit your branch as a [pull request](https://help.github.com/articles/creating-a-pull-request/)
+-
+-### 1. Providing feedback
+-
+-On of the easiest ways to get readily involved in our project is to let us know
+-about your experiences using our SDK. Feedback like this is incredibly useful
+-to us, because it allows us to refine and change features based on what our
+-users want and expect of us. There are a bunch of ways to get in contact! You
+-can [ping us](mailto:sdk-support at rackspace.com) via e-mail, talk to us on irc
+-(#rackspace-dev on freenode), [tweet us](https://twitter.com/rackspace), or
+-submit an issue on our [bug tracker](/issues). Things you might like to tell us
+-are:
+-
+-* how easy was it to start using our SDK?
+-* did it meet your expectations? If not, why not?
+-* did our documentation help or hinder you?
+-* what could we improve in general?
+-
+-### 2. Fixing bugs
+-
+-If you want to start fixing open bugs, we'd really appreciate that! Bug fixing
+-is central to any project. The best way to get started is by heading to our
+-[bug tracker](https://github.com/rackspace/gophercloud/issues) and finding open
+-bugs that you think nobody is working on. It might be useful to comment on the
+-thread to see the current state of the issue and if anybody has made any
+-breakthroughs on it so far.
+-
+-### 3. Improving documentation
+-
+-We have three forms of documentation:
+-
+-* short README documents that briefly introduce a topic
+-* reference documentation on [godoc.org](http://godoc.org) that is automatically
+-generated from source code comments
+-* user documentation on our [homepage](http://gophercloud.io) that includes
+-getting started guides, installation guides and code samples
+-
+-If you feel that a certain section could be improved - whether it's to clarify
+-ambiguity, correct a technical mistake, or to fix a grammatical error - please
+-feel entitled to do so! We welcome doc pull requests with the same childlike
+-enthusiasm as any other contribution!
+-
+-### 4. Optimizing existing features
+-
+-If you would like to improve or optimize an existing feature, please be aware
+-that we adhere to [semantic versioning](http://semver.org) - which means that
+-we cannot introduce breaking changes to the API without a major version change
+-(v1.x -> v2.x). Making that leap is a big step, so we encourage contributors to
+-refactor rather than rewrite. Running tests will prevent regression and avoid
+-the possibility of breaking somebody's current implementation.
+-
+-Another tip is to keep the focus of your work as small as possible - try not to
+-introduce a change that affects lots and lots of files because it introduces
+-added risk and increases the cognitive load on the reviewers checking your
+-work. Change-sets which are easily understood and will not negatively impact
+-users are more likely to be integrated quickly.
+-
+-Lastly, if you're seeking to optimize a particular operation, you should try to
+-demonstrate a negative performance impact - perhaps using go's inbuilt
+-[benchmark capabilities](http://dave.cheney.net/2013/06/30/how-to-write-benchmarks-in-go).
+-
+-### 5. Working on a new feature
+-
+-If you've found something we've left out, definitely feel free to start work on
+-introducing that feature. It's always useful to open an issue or submit a pull
+-request early on to indicate your intent to a core contributor - this enables
+-quick/early feedback and can help steer you in the right direction by avoiding
+-known issues. It might also help you avoid losing time implementing something
+-that might not ever work. One tip is to prefix your Pull Request issue title
+-with [wip] - then people know it's a work in progress.
+-
+-You must ensure that all of your work is well tested - both in terms of unit
+-and acceptance tests. Untested code will not be merged because it introduces
+-too much of a risk to end-users.
+-
+-Happy hacking!
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/CONTRIBUTORS.md b/Godeps/_workspace/src/github.com/rackspace/gophercloud/CONTRIBUTORS.md
 deleted file mode 100644
-index c649b5a..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/container.go
+index eb97094..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/CONTRIBUTORS.md
 +++ /dev/null
-@@ -1,731 +0,0 @@
--// Copyright 2014 go-dockerclient authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the LICENSE file.
+@@ -1,12 +0,0 @@
+-Contributors
+-============
+-
+-| Name | Email |
+-| ---- | ----- |
+-| Samuel A. Falvo II | <sam.falvo at rackspace.com>
+-| Glen Campbell | <glen.campbell at rackspace.com>
+-| Jesse Noller | <jesse.noller at rackspace.com>
+-| Jon Perritt | <jon.perritt at rackspace.com>
+-| Ash Wilson | <ash.wilson at rackspace.com>
+-| Jamie Hannaford | <jamie.hannaford at rackspace.com>
+-| Don Schenck | don.schenck at rackspace.com>
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/LICENSE b/Godeps/_workspace/src/github.com/rackspace/gophercloud/LICENSE
+deleted file mode 100644
+index fbbbc9e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/LICENSE
++++ /dev/null
+@@ -1,191 +0,0 @@
+-Copyright 2012-2013 Rackspace, Inc.
+-
+-Licensed under the Apache License, Version 2.0 (the "License"); you may not use
+-this file except in compliance with the License.  You may obtain a copy of the
+-License at
+-
+-  http://www.apache.org/licenses/LICENSE-2.0
+-
+-Unless required by applicable law or agreed to in writing, software distributed
+-under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
+-CONDITIONS OF ANY KIND, either express or implied.  See the License for the
+-specific language governing permissions and limitations under the License.                                
+-
+-------
+- 
+-				Apache License
+-                           Version 2.0, January 2004
+-                        http://www.apache.org/licenses/
+-
+-   TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+-
+-   1. Definitions.
+-
+-      "License" shall mean the terms and conditions for use, reproduction,
+-      and distribution as defined by Sections 1 through 9 of this document.
+-
+-      "Licensor" shall mean the copyright owner or entity authorized by
+-      the copyright owner that is granting the License.
+-
+-      "Legal Entity" shall mean the union of the acting entity and all
+-      other entities that control, are controlled by, or are under common
+-      control with that entity. For the purposes of this definition,
+-      "control" means (i) the power, direct or indirect, to cause the
+-      direction or management of such entity, whether by contract or
+-      otherwise, or (ii) ownership of fifty percent (50%) or more of the
+-      outstanding shares, or (iii) beneficial ownership of such entity.
+-
+-      "You" (or "Your") shall mean an individual or Legal Entity
+-      exercising permissions granted by this License.
+-
+-      "Source" form shall mean the preferred form for making modifications,
+-      including but not limited to software source code, documentation
+-      source, and configuration files.
+-
+-      "Object" form shall mean any form resulting from mechanical
+-      transformation or translation of a Source form, including but
+-      not limited to compiled object code, generated documentation,
+-      and conversions to other media types.
+-
+-      "Work" shall mean the work of authorship, whether in Source or
+-      Object form, made available under the License, as indicated by a
+-      copyright notice that is included in or attached to the work
+-      (an example is provided in the Appendix below).
+-
+-      "Derivative Works" shall mean any work, whether in Source or Object
+-      form, that is based on (or derived from) the Work and for which the
+-      editorial revisions, annotations, elaborations, or other modifications
+-      represent, as a whole, an original work of authorship. For the purposes
+-      of this License, Derivative Works shall not include works that remain
+-      separable from, or merely link (or bind by name) to the interfaces of,
+-      the Work and Derivative Works thereof.
+-
+-      "Contribution" shall mean any work of authorship, including
+-      the original version of the Work and any modifications or additions
+-      to that Work or Derivative Works thereof, that is intentionally
+-      submitted to Licensor for inclusion in the Work by the copyright owner
+-      or by an individual or Legal Entity authorized to submit on behalf of
+-      the copyright owner. For the purposes of this definition, "submitted"
+-      means any form of electronic, verbal, or written communication sent
+-      to the Licensor or its representatives, including but not limited to
+-      communication on electronic mailing lists, source code control systems,
+-      and issue tracking systems that are managed by, or on behalf of, the
+-      Licensor for the purpose of discussing and improving the Work, but
+-      excluding communication that is conspicuously marked or otherwise
+-      designated in writing by the copyright owner as "Not a Contribution."
+-
+-      "Contributor" shall mean Licensor and any individual or Legal Entity
+-      on behalf of whom a Contribution has been received by Licensor and
+-      subsequently incorporated within the Work.
+-
+-   2. Grant of Copyright License. Subject to the terms and conditions of
+-      this License, each Contributor hereby grants to You a perpetual,
+-      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+-      copyright license to reproduce, prepare Derivative Works of,
+-      publicly display, publicly perform, sublicense, and distribute the
+-      Work and such Derivative Works in Source or Object form.
+-
+-   3. Grant of Patent License. Subject to the terms and conditions of
+-      this License, each Contributor hereby grants to You a perpetual,
+-      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+-      (except as stated in this section) patent license to make, have made,
+-      use, offer to sell, sell, import, and otherwise transfer the Work,
+-      where such license applies only to those patent claims licensable
+-      by such Contributor that are necessarily infringed by their
+-      Contribution(s) alone or by combination of their Contribution(s)
+-      with the Work to which such Contribution(s) was submitted. If You
+-      institute patent litigation against any entity (including a
+-      cross-claim or counterclaim in a lawsuit) alleging that the Work
+-      or a Contribution incorporated within the Work constitutes direct
+-      or contributory patent infringement, then any patent licenses
+-      granted to You under this License for that Work shall terminate
+-      as of the date such litigation is filed.
+-
+-   4. Redistribution. You may reproduce and distribute copies of the
+-      Work or Derivative Works thereof in any medium, with or without
+-      modifications, and in Source or Object form, provided that You
+-      meet the following conditions:
+-
+-      (a) You must give any other recipients of the Work or
+-          Derivative Works a copy of this License; and
+-
+-      (b) You must cause any modified files to carry prominent notices
+-          stating that You changed the files; and
+-
+-      (c) You must retain, in the Source form of any Derivative Works
+-          that You distribute, all copyright, patent, trademark, and
+-          attribution notices from the Source form of the Work,
+-          excluding those notices that do not pertain to any part of
+-          the Derivative Works; and
+-
+-      (d) If the Work includes a "NOTICE" text file as part of its
+-          distribution, then any Derivative Works that You distribute must
+-          include a readable copy of the attribution notices contained
+-          within such NOTICE file, excluding those notices that do not
+-          pertain to any part of the Derivative Works, in at least one
+-          of the following places: within a NOTICE text file distributed
+-          as part of the Derivative Works; within the Source form or
+-          documentation, if provided along with the Derivative Works; or,
+-          within a display generated by the Derivative Works, if and
+-          wherever such third-party notices normally appear. The contents
+-          of the NOTICE file are for informational purposes only and
+-          do not modify the License. You may add Your own attribution
+-          notices within Derivative Works that You distribute, alongside
+-          or as an addendum to the NOTICE text from the Work, provided
+-          that such additional attribution notices cannot be construed
+-          as modifying the License.
+-
+-      You may add Your own copyright statement to Your modifications and
+-      may provide additional or different license terms and conditions
+-      for use, reproduction, or distribution of Your modifications, or
+-      for any such Derivative Works as a whole, provided Your use,
+-      reproduction, and distribution of the Work otherwise complies with
+-      the conditions stated in this License.
+-
+-   5. Submission of Contributions. Unless You explicitly state otherwise,
+-      any Contribution intentionally submitted for inclusion in the Work
+-      by You to the Licensor shall be under the terms and conditions of
+-      this License, without any additional terms or conditions.
+-      Notwithstanding the above, nothing herein shall supersede or modify
+-      the terms of any separate license agreement you may have executed
+-      with Licensor regarding such Contributions.
+-
+-   6. Trademarks. This License does not grant permission to use the trade
+-      names, trademarks, service marks, or product names of the Licensor,
+-      except as required for reasonable and customary use in describing the
+-      origin of the Work and reproducing the content of the NOTICE file.
+-
+-   7. Disclaimer of Warranty. Unless required by applicable law or
+-      agreed to in writing, Licensor provides the Work (and each
+-      Contributor provides its Contributions) on an "AS IS" BASIS,
+-      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+-      implied, including, without limitation, any warranties or conditions
+-      of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+-      PARTICULAR PURPOSE. You are solely responsible for determining the
+-      appropriateness of using or redistributing the Work and assume any
+-      risks associated with Your exercise of permissions under this License.
+-
+-   8. Limitation of Liability. In no event and under no legal theory,
+-      whether in tort (including negligence), contract, or otherwise,
+-      unless required by applicable law (such as deliberate and grossly
+-      negligent acts) or agreed to in writing, shall any Contributor be
+-      liable to You for damages, including any direct, indirect, special,
+-      incidental, or consequential damages of any character arising as a
+-      result of this License or out of the use or inability to use the
+-      Work (including but not limited to damages for loss of goodwill,
+-      work stoppage, computer failure or malfunction, or any and all
+-      other commercial damages or losses), even if such Contributor
+-      has been advised of the possibility of such damages.
+-
+-   9. Accepting Warranty or Additional Liability. While redistributing
+-      the Work or Derivative Works thereof, You may choose to offer,
+-      and charge a fee for, acceptance of support, warranty, indemnity,
+-      or other liability obligations and/or rights consistent with this
+-      License. However, in accepting such obligations, You may act only
+-      on Your own behalf and on Your sole responsibility, not on behalf
+-      of any other Contributor, and only if You agree to indemnify,
+-      defend, and hold each Contributor harmless for any liability
+-      incurred by, or claims asserted against, such Contributor by reason
+-      of your accepting any such warranty or additional liability.
+-
+-   END OF TERMS AND CONDITIONS
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/README.md b/Godeps/_workspace/src/github.com/rackspace/gophercloud/README.md
+deleted file mode 100644
+index 9f7552b..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/README.md
++++ /dev/null
+@@ -1,161 +0,0 @@
+-# Gophercloud: the OpenStack SDK for Go
+-[![Build Status](https://travis-ci.org/rackspace/gophercloud.svg?branch=master)](https://travis-ci.org/rackspace/gophercloud)
+-
+-Gophercloud is a flexible SDK that allows you to consume and work with OpenStack
+-clouds in a simple and idiomatic way using golang. Many services are supported,
+-including Compute, Block Storage, Object Storage, Networking, and Identity.
+-Each service API is backed with getting started guides, code samples, reference
+-documentation, unit tests and acceptance tests.
+-
+-## Useful links
+-
+-* [Gophercloud homepage](http://gophercloud.io)
+-* [Reference documentation](http://godoc.org/github.com/rackspace/gophercloud)
+-* [Getting started guides](http://gophercloud.io/docs)
+-* [Effective Go](https://golang.org/doc/effective_go.html)
+-
+-## How to install
+-
+-Before installing, you need to ensure that your [GOPATH environment variable](https://golang.org/doc/code.html#GOPATH)
+-is pointing to an appropriate directory where you want to install Gophercloud:
+-
+-```bash
+-mkdir $HOME/go
+-export GOPATH=$HOME/go
+-```
+-
+-To protect yourself against changes in your dependencies, we highly recommend choosing a
+-[dependency management solution](https://code.google.com/p/go-wiki/wiki/PackageManagementTools) for
+-your projects, such as [godep](https://github.com/tools/godep). Once this is set up, you can install
+-Gophercloud as a dependency like so:
+-
+-```bash
+-go get github.com/rackspace/gophercloud
+-
+-# Edit your code to import relevant packages from "github.com/rackspace/gophercloud"
+-
+-godep save ./...
+-```
 -
--package docker
+-This will install all the source files you need into a `Godeps/_workspace` directory, which is
+-referenceable from your own source files when you use the `godep go` command.
+-
+-## Getting started
+-
+-### Credentials
+-
+-Because you'll be hitting an API, you will need to retrieve your OpenStack
+-credentials and either store them as environment variables or in your local Go
+-files. The first method is recommended because it decouples credential
+-information from source code, allowing you to push the latter to your version
+-control system without any security risk.
+-
+-You will need to retrieve the following:
+-
+-* username
+-* password
+-* tenant name or tenant ID
+-* a valid Keystone identity URL
+-
+-For users that have the OpenStack dashboard installed, there's a shortcut. If
+-you visit the `project/access_and_security` path in Horizon and click on the
+-"Download OpenStack RC File" button at the top right hand corner, you will
+-download a bash file that exports all of your access details to environment
+-variables. To execute the file, run `source admin-openrc.sh` and you will be
+-prompted for your password.
 -
+-### Authentication
+-
+-Once you have access to your credentials, you can begin plugging them into
+-Gophercloud. The next step is authentication, and this is handled by a base
+-"Provider" struct. To get one, you can either pass in your credentials
+-explicitly, or tell Gophercloud to use environment variables:
+-
+-```go
 -import (
--	"bytes"
--	"encoding/json"
--	"fmt"
--	"io"
--	"net/http"
--	"net/url"
--	"strconv"
--	"strings"
--	"time"
+-  "github.com/rackspace/gophercloud"
+-  "github.com/rackspace/gophercloud/openstack"
+-  "github.com/rackspace/gophercloud/openstack/utils"
 -)
 -
--// ListContainersOptions specify parameters to the ListContainers function.
--//
--// See http://goo.gl/XqtcyU for more details.
--type ListContainersOptions struct {
--	All    bool
--	Size   bool
--	Limit  int
--	Since  string
--	Before string
+-// Option 1: Pass in the values yourself
+-opts := gophercloud.AuthOptions{
+-  IdentityEndpoint: "https://my-openstack.com:5000/v2.0",
+-  Username: "{username}",
+-  Password: "{password}",
+-  TenantID: "{tenant_id}",
 -}
 -
--type APIPort struct {
--	PrivatePort int64  `json:"PrivatePort,omitempty" yaml:"PrivatePort,omitempty"`
--	PublicPort  int64  `json:"PublicPort,omitempty" yaml:"PublicPort,omitempty"`
--	Type        string `json:"Type,omitempty" yaml:"Type,omitempty"`
--	IP          string `json:"IP,omitempty" yaml:"IP,omitempty"`
--}
+-// Option 2: Use a utility function to retrieve all your environment variables
+-opts, err := openstack.AuthOptionsFromEnv()
+-```
 -
--// APIContainers represents a container.
--//
--// See http://goo.gl/QeFH7U for more details.
--type APIContainers struct {
--	ID         string    `json:"Id" yaml:"Id"`
--	Image      string    `json:"Image,omitempty" yaml:"Image,omitempty"`
--	Command    string    `json:"Command,omitempty" yaml:"Command,omitempty"`
--	Created    int64     `json:"Created,omitempty" yaml:"Created,omitempty"`
--	Status     string    `json:"Status,omitempty" yaml:"Status,omitempty"`
--	Ports      []APIPort `json:"Ports,omitempty" yaml:"Ports,omitempty"`
--	SizeRw     int64     `json:"SizeRw,omitempty" yaml:"SizeRw,omitempty"`
--	SizeRootFs int64     `json:"SizeRootFs,omitempty" yaml:"SizeRootFs,omitempty"`
--	Names      []string  `json:"Names,omitempty" yaml:"Names,omitempty"`
--}
+-Once you have the `opts` variable, you can pass it in and get back a
+-`ProviderClient` struct:
 -
--// ListContainers returns a slice of containers matching the given criteria.
--//
--// See http://goo.gl/XqtcyU for more details.
--func (c *Client) ListContainers(opts ListContainersOptions) ([]APIContainers, error) {
--	path := "/containers/json?" + queryString(opts)
--	body, _, err := c.do("GET", path, nil)
--	if err != nil {
--		return nil, err
--	}
--	var containers []APIContainers
--	err = json.Unmarshal(body, &containers)
--	if err != nil {
--		return nil, err
--	}
--	return containers, nil
--}
+-```go
+-provider, err := openstack.AuthenticatedClient(opts)
+-```
 -
--// Port represents the port number and the protocol, in the form
--// <number>/<protocol>. For example: 80/tcp.
--type Port string
+-The `ProviderClient` is the top-level client that all of your OpenStack services
+-derive from. The provider contains all of the authentication details that allow
+-your Go code to access the API - such as the base URL and token ID.
 -
--// Port returns the number of the port.
--func (p Port) Port() string {
--	return strings.Split(string(p), "/")[0]
--}
+-### Provision a server
 -
--// Proto returns the name of the protocol.
--func (p Port) Proto() string {
--	parts := strings.Split(string(p), "/")
--	if len(parts) == 1 {
--		return "tcp"
--	}
--	return parts[1]
--}
+-Once we have a base Provider, we inject it as a dependency into each OpenStack
+-service. In order to work with the Compute API, we need a Compute service
+-client; which can be created like so:
 -
--// State represents the state of a container.
--type State struct {
--	Running    bool      `json:"Running,omitempty" yaml:"Running,omitempty"`
--	Paused     bool      `json:"Paused,omitempty" yaml:"Paused,omitempty"`
--	Pid        int       `json:"Pid,omitempty" yaml:"Pid,omitempty"`
--	ExitCode   int       `json:"ExitCode,omitempty" yaml:"ExitCode,omitempty"`
--	StartedAt  time.Time `json:"StartedAt,omitempty" yaml:"StartedAt,omitempty"`
--	FinishedAt time.Time `json:"FinishedAt,omitempty" yaml:"FinishedAt,omitempty"`
--}
+-```go
+-client, err := openstack.NewComputeV2(provider, gophercloud.EndpointOpts{
+-  Region: os.Getenv("OS_REGION_NAME"),
+-})
+-```
 -
--// String returns the string representation of a state.
--func (s *State) String() string {
--	if s.Running {
--		if s.Paused {
--			return "paused"
--		}
--		return fmt.Sprintf("Up %s", time.Now().UTC().Sub(s.StartedAt))
--	}
--	return fmt.Sprintf("Exit %d", s.ExitCode)
--}
+-We then use this `client` for any Compute API operation we want. In our case,
+-we want to provision a new server - so we invoke the `Create` method and pass
+-in the flavor ID (hardware specification) and image ID (operating system) we're
+-interested in:
 -
--type PortBinding struct {
--	HostIp   string `json:"HostIP,omitempty" yaml:"HostIP,omitempty"`
--	HostPort string `json:"HostPort,omitempty" yaml:"HostPort,omitempty"`
--}
+-```go
+-import "github.com/rackspace/gophercloud/openstack/compute/v2/servers"
 -
--type PortMapping map[string]string
+-server, err := servers.Create(client, servers.CreateOpts{
+-  Name:      "My new server!",
+-  FlavorRef: "flavor_id",
+-  ImageRef:  "image_id",
+-}).Extract()
+-```
 -
--type NetworkSettings struct {
--	IPAddress   string                 `json:"IPAddress,omitempty" yaml:"IPAddress,omitempty"`
--	IPPrefixLen int                    `json:"IPPrefixLen,omitempty" yaml:"IPPrefixLen,omitempty"`
--	Gateway     string                 `json:"Gateway,omitempty" yaml:"Gateway,omitempty"`
--	Bridge      string                 `json:"Bridge,omitempty" yaml:"Bridge,omitempty"`
--	PortMapping map[string]PortMapping `json:"PortMapping,omitempty" yaml:"PortMapping,omitempty"`
--	Ports       map[Port][]PortBinding `json:"Ports,omitempty" yaml:"Ports,omitempty"`
--}
+-If you are unsure about what images and flavors are, you can read our [Compute
+-Getting Started guide](http://gophercloud.io/docs/compute). The above code
+-sample creates a new server with the parameters, and embodies the new resource
+-in the `server` variable (a
+-[`servers.Server`](http://godoc.org/github.com/rackspace/gophercloud) struct).
 -
--func (settings *NetworkSettings) PortMappingAPI() []APIPort {
--	var mapping []APIPort
--	for port, bindings := range settings.Ports {
--		p, _ := parsePort(port.Port())
--		if len(bindings) == 0 {
--			mapping = append(mapping, APIPort{
--				PublicPort: int64(p),
--				Type:       port.Proto(),
--			})
--			continue
--		}
--		for _, binding := range bindings {
--			p, _ := parsePort(port.Port())
--			h, _ := parsePort(binding.HostPort)
--			mapping = append(mapping, APIPort{
--				PrivatePort: int64(p),
--				PublicPort:  int64(h),
--				Type:        port.Proto(),
--				IP:          binding.HostIp,
--			})
--		}
--	}
--	return mapping
--}
+-### Next steps
 -
--func parsePort(rawPort string) (int, error) {
--	port, err := strconv.ParseUint(rawPort, 10, 16)
--	if err != nil {
--		return 0, err
--	}
--	return int(port), nil
--}
+-Cool! You've handled authentication, got your `ProviderClient` and provisioned
+-a new server. You're now ready to use more OpenStack services.
 -
--type Config struct {
--	Hostname        string              `json:"Hostname,omitempty" yaml:"Hostname,omitempty"`
--	Domainname      string              `json:"Domainname,omitempty" yaml:"Domainname,omitempty"`
--	User            string              `json:"User,omitempty" yaml:"User,omitempty"`
--	Memory          int64               `json:"Memory,omitempty" yaml:"Memory,omitempty"`
--	MemorySwap      int64               `json:"MemorySwap,omitempty" yaml:"MemorySwap,omitempty"`
--	CpuShares       int64               `json:"CpuShares,omitempty" yaml:"CpuShares,omitempty"`
--	CpuSet          string              `json:"CpuSet,omitempty" yaml:"CpuSet,omitempty"`
--	AttachStdin     bool                `json:"AttachStdin,omitempty" yaml:"AttachStdin,omitempty"`
--	AttachStdout    bool                `json:"AttachStdout,omitempty" yaml:"AttachStdout,omitempty"`
--	AttachStderr    bool                `json:"AttachStderr,omitempty" yaml:"AttachStderr,omitempty"`
--	PortSpecs       []string            `json:"PortSpecs,omitempty" yaml:"PortSpecs,omitempty"`
--	ExposedPorts    map[Port]struct{}   `json:"ExposedPorts,omitempty" yaml:"ExposedPorts,omitempty"`
--	Tty             bool                `json:"Tty,omitempty" yaml:"Tty,omitempty"`
--	OpenStdin       bool                `json:"OpenStdin,omitempty" yaml:"OpenStdin,omitempty"`
--	StdinOnce       bool                `json:"StdinOnce,omitempty" yaml:"StdinOnce,omitempty"`
--	Env             []string            `json:"Env,omitempty" yaml:"Env,omitempty"`
--	Cmd             []string            `json:"Cmd,omitempty" yaml:"Cmd,omitempty"`
--	Dns             []string            `json:"Dns,omitempty" yaml:"Dns,omitempty"` // For Docker API v1.9 and below only
--	Image           string              `json:"Image,omitempty" yaml:"Image,omitempty"`
--	Volumes         map[string]struct{} `json:"Volumes,omitempty" yaml:"Volumes,omitempty"`
--	VolumesFrom     string              `json:"VolumesFrom,omitempty" yaml:"VolumesFrom,omitempty"`
--	WorkingDir      string              `json:"WorkingDir,omitempty" yaml:"WorkingDir,omitempty"`
--	Entrypoint      []string            `json:"Entrypoint,omitempty" yaml:"Entrypoint,omitempty"`
--	NetworkDisabled bool                `json:"NetworkDisabled,omitempty" yaml:"NetworkDisabled,omitempty"`
--}
+-* [Getting started with Compute](http://gophercloud.io/docs/compute)
+-* [Getting started with Object Storage](http://gophercloud.io/docs/object-storage)
+-* [Getting started with Networking](http://gophercloud.io/docs/networking)
+-* [Getting started with Block Storage](http://gophercloud.io/docs/block-storage)
+-* [Getting started with Identity](http://gophercloud.io/docs/identity)
 -
--type Container struct {
--	ID string `json:"Id" yaml:"Id"`
+-## Contributing
 -
--	Created time.Time `json:"Created,omitempty" yaml:"Created,omitempty"`
+-Engaging the community and lowering barriers for contributors is something we
+-care a lot about. For this reason, we've taken the time to write a [contributing
+-guide](./CONTRIBUTING.md) for folks interested in getting involved in our project.
+-If you're not sure how you can get involved, feel free to submit an issue or
+-[e-mail us](mailto:sdk-support at rackspace.com) privately. You don't need to be a
+-Go expert - all members of the community are welcome!
+-
+-## Help and feedback
+-
+-If you're struggling with something or have spotted a potential bug, feel free
+-to submit an issue to our [bug tracker](/issues) or e-mail us directly at
+-[sdk-support at rackspace.com](mailto:sdk-support at rackspace.com).
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/UPGRADING.md b/Godeps/_workspace/src/github.com/rackspace/gophercloud/UPGRADING.md
+deleted file mode 100644
+index da3758b..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/UPGRADING.md
++++ /dev/null
+@@ -1,338 +0,0 @@
+-# Upgrading to v1.0.0
+-
+-With the arrival of this new major version increment, the unfortunate news is
+-that breaking changes have been introduced to existing services. The API
+-has been completely rewritten from the ground up to make the library more
+-extensible, maintainable and easy-to-use.
+-
+-Below we've compiled upgrade instructions for the various services that
+-existed before. If you have a specific issue that is not addressed below,
+-please [submit an issue](/issues/new) or
+-[e-mail our support team](mailto:sdk-support at rackspace.com).
+-
+-* [Authentication](#authentication)
+-* [Servers](#servers)
+-  * [List servers](#list-servers)
+-  * [Get server details](#get-server-details)
+-  * [Create server](#create-server)
+-  * [Resize server](#resize-server)
+-  * [Reboot server](#reboot-server)
+-  * [Update server](#update-server)
+-  * [Rebuild server](#rebuild-server)
+-  * [Change admin password](#change-admin-password)
+-  * [Delete server](#delete-server)
+-  * [Rescue server](#rescue-server)
+-* [Images and flavors](#images-and-flavors)
+-  * [List images](#list-images)
+-  * [List flavors](#list-flavors)
+-  * [Create/delete image](#createdelete-image)
+-* [Other](#other)
+-  * [List keypairs](#list-keypairs)
+-  * [Create/delete keypair](#createdelete-keypair)
+-  * [List IP addresses](#list-ip-addresses)
+-
+-# Authentication
+-
+-One of the major differences that this release introduces is the level of
+-sub-packaging to differentiate between services and providers. You now have
+-the option of authenticating with OpenStack and other providers (like Rackspace).
+-
+-To authenticate with a vanilla OpenStack installation, you can either specify
+-your credentials like this:
 -
--	Path string   `json:"Path,omitempty" yaml:"Path,omitempty"`
--	Args []string `json:"Args,omitempty" yaml:"Args,omitempty"`
+-```go
+-import (
+-  "github.com/rackspace/gophercloud"
+-  "github.com/rackspace/gophercloud/openstack"
+-)
 -
--	Config *Config `json:"Config,omitempty" yaml:"Config,omitempty"`
--	State  State   `json:"State,omitempty" yaml:"State,omitempty"`
--	Image  string  `json:"Image,omitempty" yaml:"Image,omitempty"`
+-opts := gophercloud.AuthOptions{
+-  IdentityEndpoint: "https://my-openstack.com:5000/v2.0",
+-  Username: "{username}",
+-  Password: "{password}",
+-  TenantID: "{tenant_id}",
+-}
+-```
 -
--	NetworkSettings *NetworkSettings `json:"NetworkSettings,omitempty" yaml:"NetworkSettings,omitempty"`
+-Or have them pulled in through environment variables, like this:
 -
--	SysInitPath    string `json:"SysInitPath,omitempty" yaml:"SysInitPath,omitempty"`
--	ResolvConfPath string `json:"ResolvConfPath,omitempty" yaml:"ResolvConfPath,omitempty"`
--	HostnamePath   string `json:"HostnamePath,omitempty" yaml:"HostnamePath,omitempty"`
--	HostsPath      string `json:"HostsPath,omitempty" yaml:"HostsPath,omitempty"`
--	Name           string `json:"Name,omitempty" yaml:"Name,omitempty"`
--	Driver         string `json:"Driver,omitempty" yaml:"Driver,omitempty"`
+-```go
+-opts, err := openstack.AuthOptionsFromEnv()
+-```
 -
--	Volumes    map[string]string `json:"Volumes,omitempty" yaml:"Volumes,omitempty"`
--	VolumesRW  map[string]bool   `json:"VolumesRW,omitempty" yaml:"VolumesRW,omitempty"`
--	HostConfig *HostConfig       `json:"HostConfig,omitempty" yaml:"HostConfig,omitempty"`
--}
+-Once you have your `AuthOptions` struct, you pass it in to get back a `Provider`,
+-like so:
 -
--// InspectContainer returns information about a container by its ID.
--//
--// See http://goo.gl/CxVuJ5 for more details.
--func (c *Client) InspectContainer(id string) (*Container, error) {
--	path := "/containers/" + id + "/json"
--	body, status, err := c.do("GET", path, nil)
--	if status == http.StatusNotFound {
--		return nil, &NoSuchContainer{ID: id}
--	}
--	if err != nil {
--		return nil, err
--	}
--	var container Container
--	err = json.Unmarshal(body, &container)
--	if err != nil {
--		return nil, err
--	}
--	return &container, nil
--}
+-```go
+-provider, err := openstack.AuthenticatedClient(opts)
+-```
 -
--// ContainerChanges returns changes in the filesystem of the given container.
--//
--// See http://goo.gl/QkW9sH for more details.
--func (c *Client) ContainerChanges(id string) ([]Change, error) {
--	path := "/containers/" + id + "/changes"
--	body, status, err := c.do("GET", path, nil)
--	if status == http.StatusNotFound {
--		return nil, &NoSuchContainer{ID: id}
--	}
--	if err != nil {
--		return nil, err
--	}
--	var changes []Change
--	err = json.Unmarshal(body, &changes)
--	if err != nil {
--		return nil, err
--	}
--	return changes, nil
--}
+-This provider is the top-level structure that all services are created from.
 -
--// CreateContainerOptions specify parameters to the CreateContainer function.
--//
--// See http://goo.gl/mErxNp for more details.
--type CreateContainerOptions struct {
--	Name   string
--	Config *Config `qs:"-"`
--}
+-# Servers
 -
--// CreateContainer creates a new container, returning the container instance,
--// or an error in case of failure.
--//
--// See http://goo.gl/mErxNp for more details.
--func (c *Client) CreateContainer(opts CreateContainerOptions) (*Container, error) {
--	path := "/containers/create?" + queryString(opts)
--	body, status, err := c.do("POST", path, opts.Config)
--	if status == http.StatusNotFound {
--		return nil, ErrNoSuchImage
--	}
--	if err != nil {
--		return nil, err
--	}
--	var container Container
--	err = json.Unmarshal(body, &container)
--	if err != nil {
--		return nil, err
--	}
+-Before you can interact with the Compute API, you need to retrieve a
+-`gophercloud.ServiceClient`. To do this:
 -
--	container.Name = opts.Name
+-```go
+-// Define your region, etc.
+-opts := gophercloud.EndpointOpts{Region: "RegionOne"}
 -
--	return &container, nil
--}
+-client, err := openstack.NewComputeV2(provider, opts)
+-```
 -
--type KeyValuePair struct {
--	Key   string `json:"Key,omitempty" yaml:"Key,omitempty"`
--	Value string `json:"Value,omitempty" yaml:"Value,omitempty"`
--}
+-## List servers
 -
--// RestartPolicy represents the policy for automatically restarting a container.
--//
--// Possible values are:
--//
--//   - always: the docker daemon will always restart the container
--//   - on-failure: the docker daemon will restart the container on failures, at
--//                 most MaximumRetryCount times
--//   - no: the docker daemon will not restart the container automatically
--type RestartPolicy struct {
--	Name              string `json:"Name,omitempty" yaml:"Name,omitempty"`
--	MaximumRetryCount int    `json:"MaximumRetryCount,omitempty" yaml:"MaximumRetryCount,omitempty"`
--}
+-All operations that involve API collections (servers, flavors, images) now use
+-the `pagination.Pager` interface. This interface represents paginated entities
+-that can be iterated over.
 -
--// AlwaysRestart returns a restart policy that tells the Docker daemon to
--// always restart the container.
--func AlwaysRestart() RestartPolicy {
--	return RestartPolicy{Name: "always"}
--}
+-Once you have a Pager, you can then pass a callback function into its `EachPage`
+-method, and this will allow you to traverse over the collection and execute
+-arbitrary functionality. So, an example with list servers:
 -
--// RestartOnFailure returns a restart policy that tells the Docker daemon to
--// restart the container on failures, trying at most maxRetry times.
--func RestartOnFailure(maxRetry int) RestartPolicy {
--	return RestartPolicy{Name: "on-failure", MaximumRetryCount: maxRetry}
--}
+-```go
+-import (
+-  "fmt"
+-  "github.com/rackspace/gophercloud/pagination"
+-  "github.com/rackspace/gophercloud/openstack/compute/v2/servers"
+-)
 -
--// NeverRestart returns a restart policy that tells the Docker daemon to never
--// restart the container on failures.
--func NeverRestart() RestartPolicy {
--	return RestartPolicy{Name: "no"}
--}
+-// We have the option of filtering the server list. If we want the full
+-// collection, leave it as an empty struct or nil
+-opts := servers.ListOpts{Name: "server_1"}
 -
--type HostConfig struct {
--	Binds           []string               `json:"Binds,omitempty" yaml:"Binds,omitempty"`
--	CapAdd          []string               `json:"CapAdd,omitempty" yaml:"CapAdd,omitempty"`
--	CapDrop         []string               `json:"CapDrop,omitempty" yaml:"CapDrop,omitempty"`
--	ContainerIDFile string                 `json:"ContainerIDFile,omitempty" yaml:"ContainerIDFile,omitempty"`
--	LxcConf         []KeyValuePair         `json:"LxcConf,omitempty" yaml:"LxcConf,omitempty"`
--	Privileged      bool                   `json:"Privileged,omitempty" yaml:"Privileged,omitempty"`
--	PortBindings    map[Port][]PortBinding `json:"PortBindings,omitempty" yaml:"PortBindings,omitempty"`
--	Links           []string               `json:"Links,omitempty" yaml:"Links,omitempty"`
--	PublishAllPorts bool                   `json:"PublishAllPorts,omitempty" yaml:"PublishAllPorts,omitempty"`
--	Dns             []string               `json:"Dns,omitempty" yaml:"Dns,omitempty"` // For Docker API v1.10 and above only
--	DnsSearch       []string               `json:"DnsSearch,omitempty" yaml:"DnsSearch,omitempty"`
--	VolumesFrom     []string               `json:"VolumesFrom,omitempty" yaml:"VolumesFrom,omitempty"`
--	NetworkMode     string                 `json:"NetworkMode,omitempty" yaml:"NetworkMode,omitempty"`
--	RestartPolicy   RestartPolicy          `json:"RestartPolicy,omitempty" yaml:"RestartPolicy,omitempty"`
--}
+-// Retrieve a pager (i.e. a paginated collection)
+-pager := servers.List(client, opts)
 -
--// StartContainer starts a container, returning an error in case of failure.
--//
--// See http://goo.gl/iM5GYs for more details.
--func (c *Client) StartContainer(id string, hostConfig *HostConfig) error {
--	if hostConfig == nil {
--		hostConfig = &HostConfig{}
--	}
--	path := "/containers/" + id + "/start"
--	_, status, err := c.do("POST", path, hostConfig)
--	if status == http.StatusNotFound {
--		return &NoSuchContainer{ID: id}
--	}
--	if status == http.StatusNotModified {
--		return &ContainerAlreadyRunning{ID: id}
--	}
--	if err != nil {
--		return err
--	}
--	return nil
--}
+-// Define an anonymous function to be executed on each page's iteration
+-err := pager.EachPage(func(page pagination.Page) (bool, error) {
+-  serverList, err := servers.ExtractServers(page)
 -
--// StopContainer stops a container, killing it after the given timeout (in
--// seconds).
--//
--// See http://goo.gl/EbcpXt for more details.
--func (c *Client) StopContainer(id string, timeout uint) error {
--	path := fmt.Sprintf("/containers/%s/stop?t=%d", id, timeout)
--	_, status, err := c.do("POST", path, nil)
--	if status == http.StatusNotFound {
--		return &NoSuchContainer{ID: id}
--	}
--	if status == http.StatusNotModified {
--		return &ContainerNotRunning{ID: id}
--	}
--	if err != nil {
--		return err
--	}
--	return nil
--}
+-  // `s' will be a servers.Server struct
+-  for _, s := range serverList {
+-    fmt.Printf("We have a server. ID=%s, Name=%s", s.ID, s.Name)
+-  }
+-})
+-```
 -
--// RestartContainer stops a container, killing it after the given timeout (in
--// seconds), during the stop process.
--//
--// See http://goo.gl/VOzR2n for more details.
--func (c *Client) RestartContainer(id string, timeout uint) error {
--	path := fmt.Sprintf("/containers/%s/restart?t=%d", id, timeout)
--	_, status, err := c.do("POST", path, nil)
--	if status == http.StatusNotFound {
--		return &NoSuchContainer{ID: id}
--	}
--	if err != nil {
--		return err
--	}
--	return nil
--}
+-## Get server details
 -
--// PauseContainer pauses the given container.
--//
--// See http://goo.gl/AM5t42 for more details.
--func (c *Client) PauseContainer(id string) error {
--	path := fmt.Sprintf("/containers/%s/pause", id)
--	_, status, err := c.do("POST", path, nil)
--	if status == http.StatusNotFound {
--		return &NoSuchContainer{ID: id}
--	}
--	if err != nil {
--		return err
--	}
--	return nil
--}
+-```go
+-import "github.com/rackspace/gophercloud/openstack/compute/v2/servers"
 -
--// UnpauseContainer pauses the given container.
--//
--// See http://goo.gl/eBrNSL for more details.
--func (c *Client) UnpauseContainer(id string) error {
--	path := fmt.Sprintf("/containers/%s/unpause", id)
--	_, status, err := c.do("POST", path, nil)
--	if status == http.StatusNotFound {
--		return &NoSuchContainer{ID: id}
--	}
--	if err != nil {
--		return err
--	}
--	return nil
--}
+-// Get the HTTP result
+-response := servers.Get(client, "server_id")
 -
--// TopResult represents the list of processes running in a container, as
--// returned by /containers/<id>/top.
--//
--// See http://goo.gl/qu4gse for more details.
--type TopResult struct {
--	Titles    []string
--	Processes [][]string
--}
+-// Extract a Server struct from the response
+-server, err := response.Extract()
+-```
 -
--// TopContainer returns processes running inside a container
--//
--// See http://goo.gl/qu4gse for more details.
--func (c *Client) TopContainer(id string, psArgs string) (TopResult, error) {
--	var args string
--	var result TopResult
--	if psArgs != "" {
--		args = fmt.Sprintf("?ps_args=%s", psArgs)
--	}
--	path := fmt.Sprintf("/containers/%s/top%s", id, args)
--	body, status, err := c.do("GET", path, nil)
--	if status == http.StatusNotFound {
--		return result, &NoSuchContainer{ID: id}
--	}
--	if err != nil {
--		return result, err
--	}
--	err = json.Unmarshal(body, &result)
--	if err != nil {
--		return result, err
--	}
--	return result, nil
--}
+-## Create server
 -
--// KillContainerOptions represents the set of options that can be used in a
--// call to KillContainer.
--//
--// See http://goo.gl/TFkECx for more details.
--type KillContainerOptions struct {
--	// The ID of the container.
--	ID string `qs:"-"`
+-```go
+-import "github.com/rackspace/gophercloud/openstack/compute/v2/servers"
 -
--	// The signal to send to the container. When omitted, Docker server
--	// will assume SIGKILL.
--	Signal Signal
+-// Define our options
+-opts := servers.CreateOpts{
+-  Name: "new_server",
+-  FlavorRef: "flavorID",
+-  ImageRef: "imageID",
 -}
 -
--// KillContainer kills a container, returning an error in case of failure.
--//
--// See http://goo.gl/TFkECx for more details.
--func (c *Client) KillContainer(opts KillContainerOptions) error {
--	path := "/containers/" + opts.ID + "/kill" + "?" + queryString(opts)
--	_, status, err := c.do("POST", path, nil)
--	if status == http.StatusNotFound {
--		return &NoSuchContainer{ID: opts.ID}
--	}
--	if err != nil {
--		return err
--	}
--	return nil
--}
+-// Get our response
+-response := servers.Create(client, opts)
 -
--// RemoveContainerOptions encapsulates options to remove a container.
--//
--// See http://goo.gl/ZB83ji for more details.
--type RemoveContainerOptions struct {
--	// The ID of the container.
--	ID string `qs:"-"`
+-// Extract
+-server, err := response.Extract()
+-```
 -
--	// A flag that indicates whether Docker should remove the volumes
--	// associated to the container.
--	RemoveVolumes bool `qs:"v"`
+-## Change admin password
 -
--	// A flag that indicates whether Docker should remove the container
--	// even if it is currently running.
--	Force bool
--}
+-```go
+-import "github.com/rackspace/gophercloud/openstack/compute/v2/servers"
 -
--// RemoveContainer removes a container, returning an error in case of failure.
--//
--// See http://goo.gl/ZB83ji for more details.
--func (c *Client) RemoveContainer(opts RemoveContainerOptions) error {
--	path := "/containers/" + opts.ID + "?" + queryString(opts)
--	_, status, err := c.do("DELETE", path, nil)
--	if status == http.StatusNotFound {
--		return &NoSuchContainer{ID: opts.ID}
--	}
--	if err != nil {
--		return err
--	}
--	return nil
--}
+-result := servers.ChangeAdminPassword(client, "server_id", "newPassword_&123")
+-```
 -
--// CopyFromContainerOptions is the set of options that can be used when copying
--// files or folders from a container.
--//
--// See http://goo.gl/rINMlw for more details.
--type CopyFromContainerOptions struct {
--	OutputStream io.Writer `json:"-"`
--	Container    string    `json:"-"`
--	Resource     string
--}
+-## Resize server
 -
--// CopyFromContainer copy files or folders from a container, using a given
--// resource.
--//
--// See http://goo.gl/rINMlw for more details.
--func (c *Client) CopyFromContainer(opts CopyFromContainerOptions) error {
--	if opts.Container == "" {
--		return &NoSuchContainer{ID: opts.Container}
--	}
--	url := fmt.Sprintf("/containers/%s/copy", opts.Container)
--	body, status, err := c.do("POST", url, opts)
--	if status == http.StatusNotFound {
--		return &NoSuchContainer{ID: opts.Container}
--	}
--	if err != nil {
--		return err
--	}
--	io.Copy(opts.OutputStream, bytes.NewBuffer(body))
--	return nil
--}
+-```go
+-import "github.com/rackspace/gophercloud/openstack/compute/v2/servers"
 -
--// WaitContainer blocks until the given container stops, return the exit code
--// of the container status.
--//
--// See http://goo.gl/J88DHU for more details.
--func (c *Client) WaitContainer(id string) (int, error) {
--	body, status, err := c.do("POST", "/containers/"+id+"/wait", nil)
--	if status == http.StatusNotFound {
--		return 0, &NoSuchContainer{ID: id}
--	}
--	if err != nil {
--		return 0, err
--	}
--	var r struct{ StatusCode int }
--	err = json.Unmarshal(body, &r)
--	if err != nil {
--		return 0, err
--	}
--	return r.StatusCode, nil
--}
+-result := servers.Resize(client, "server_id", "new_flavor_id")
+-```
 -
--// CommitContainerOptions aggregates parameters to the CommitContainer method.
--//
--// See http://goo.gl/Jn8pe8 for more details.
--type CommitContainerOptions struct {
--	Container  string
--	Repository string `qs:"repo"`
--	Tag        string
--	Message    string `qs:"m"`
--	Author     string
--	Run        *Config `qs:"-"`
--}
+-## Reboot server
 -
--// CommitContainer creates a new image from a container's changes.
--//
--// See http://goo.gl/Jn8pe8 for more details.
--func (c *Client) CommitContainer(opts CommitContainerOptions) (*Image, error) {
--	path := "/commit?" + queryString(opts)
--	body, status, err := c.do("POST", path, opts.Run)
--	if status == http.StatusNotFound {
--		return nil, &NoSuchContainer{ID: opts.Container}
--	}
--	if err != nil {
--		return nil, err
--	}
--	var image Image
--	err = json.Unmarshal(body, &image)
--	if err != nil {
--		return nil, err
--	}
--	return &image, nil
--}
+-```go
+-import "github.com/rackspace/gophercloud/openstack/compute/v2/servers"
 -
--// AttachToContainerOptions is the set of options that can be used when
--// attaching to a container.
--//
--// See http://goo.gl/RRAhws for more details.
--type AttachToContainerOptions struct {
--	Container    string    `qs:"-"`
--	InputStream  io.Reader `qs:"-"`
--	OutputStream io.Writer `qs:"-"`
--	ErrorStream  io.Writer `qs:"-"`
+-// You have a choice of two reboot methods: servers.SoftReboot or servers.HardReboot
+-result := servers.Reboot(client, "server_id", servers.SoftReboot)
+-```
 -
--	// Get container logs, sending it to OutputStream.
--	Logs bool
+-## Update server
 -
--	// Stream the response?
--	Stream bool
+-```go
+-import "github.com/rackspace/gophercloud/openstack/compute/v2/servers"
 -
--	// Attach to stdin, and use InputStream.
--	Stdin bool
+-opts := servers.UpdateOpts{Name: "new_name"}
 -
--	// Attach to stdout, and use OutputStream.
--	Stdout bool
+-server, err := servers.Update(client, "server_id", opts).Extract()
+-```
 -
--	// Attach to stderr, and use ErrorStream.
--	Stderr bool
+-## Rebuild server
 -
--	// If set, after a successful connect, a sentinel will be sent and then the
--	// client will block on receive before continuing.
--	//
--	// It must be an unbuffered channel. Using a buffered channel can lead
--	// to unexpected behavior.
--	Success chan struct{}
+-```go
+-import "github.com/rackspace/gophercloud/openstack/compute/v2/servers"
 -
--	// Use raw terminal? Usually true when the container contains a TTY.
--	RawTerminal bool `qs:"-"`
+-// You have the option of specifying additional options
+-opts := RebuildOpts{
+-  Name:      "new_name",
+-  AdminPass: "admin_password",
+-  ImageID:   "image_id",
+-  Metadata:  map[string]string{"owner": "me"},
 -}
 -
--// AttachToContainer attaches to a container, using the given options.
--//
--// See http://goo.gl/RRAhws for more details.
--func (c *Client) AttachToContainer(opts AttachToContainerOptions) error {
--	if opts.Container == "" {
--		return &NoSuchContainer{ID: opts.Container}
--	}
--	path := "/containers/" + opts.Container + "/attach?" + queryString(opts)
--	return c.hijack("POST", path, opts.Success, opts.RawTerminal, opts.InputStream, opts.ErrorStream, opts.OutputStream, nil)
--}
+-result := servers.Rebuild(client, "server_id", opts)
 -
--// LogsOptions represents the set of options used when getting logs from a
--// container.
--//
--// See http://goo.gl/rLhKSU for more details.
--type LogsOptions struct {
--	Container    string    `qs:"-"`
--	OutputStream io.Writer `qs:"-"`
--	ErrorStream  io.Writer `qs:"-"`
--	Follow       bool
--	Stdout       bool
--	Stderr       bool
--	Timestamps   bool
--	Tail         string
+-// You can extract a servers.Server struct from the HTTP response
+-server, err := result.Extract()
+-```
 -
--	// Use raw terminal? Usually true when the container contains a TTY.
--	RawTerminal bool `qs:"-"`
--}
+-## Delete server
 -
--// Logs gets stdout and stderr logs from the specified container.
--//
--// See http://goo.gl/rLhKSU for more details.
--func (c *Client) Logs(opts LogsOptions) error {
--	if opts.Container == "" {
--		return &NoSuchContainer{ID: opts.Container}
--	}
--	if opts.Tail == "" {
--		opts.Tail = "all"
--	}
--	path := "/containers/" + opts.Container + "/logs?" + queryString(opts)
--	return c.stream("GET", path, opts.RawTerminal, false, nil, nil, opts.OutputStream, opts.ErrorStream)
--}
+-```go
+-import "github.com/rackspace/gophercloud/openstack/compute/v2/servers"
 -
--// ResizeContainerTTY resizes the terminal to the given height and width.
--func (c *Client) ResizeContainerTTY(id string, height, width int) error {
--	params := make(url.Values)
--	params.Set("h", strconv.Itoa(height))
--	params.Set("w", strconv.Itoa(width))
--	_, _, err := c.do("POST", "/containers/"+id+"/resize?"+params.Encode(), nil)
--	return err
--}
+-response := servers.Delete(client, "server_id")
+-```
 -
--// ExportContainerOptions is the set of parameters to the ExportContainer
--// method.
--//
--// See http://goo.gl/hnzE62 for more details.
--type ExportContainerOptions struct {
--	ID           string
--	OutputStream io.Writer
--}
+-## Rescue server
 -
--// ExportContainer export the contents of container id as tar archive
--// and prints the exported contents to stdout.
--//
--// See http://goo.gl/hnzE62 for more details.
--func (c *Client) ExportContainer(opts ExportContainerOptions) error {
--	if opts.ID == "" {
--		return &NoSuchContainer{ID: opts.ID}
--	}
--	url := fmt.Sprintf("/containers/%s/export", opts.ID)
--	return c.stream("GET", url, true, false, nil, nil, opts.OutputStream, nil)
--}
+-The server rescue extension for Compute is not currently supported.
 -
--// NoSuchContainer is the error returned when a given container does not exist.
--type NoSuchContainer struct {
--	ID string
--}
+-# Images and flavors
 -
--func (err *NoSuchContainer) Error() string {
--	return "No such container: " + err.ID
--}
+-## List images
 -
--// ContainerAlreadyRunning is the error returned when a given container is
--// already running.
--type ContainerAlreadyRunning struct {
--	ID string
--}
+-As with listing servers (see above), you first retrieve a Pager, and then pass
+-in a callback over each page:
 -
--func (err *ContainerAlreadyRunning) Error() string {
--	return "Container already running: " + err.ID
--}
+-```go
+-import (
+-  "github.com/rackspace/gophercloud/pagination"
+-  "github.com/rackspace/gophercloud/openstack/compute/v2/images"
+-)
 -
--// ContainerNotRunning is the error returned when a given container is not
--// running.
--type ContainerNotRunning struct {
--	ID string
--}
+-// We have the option of filtering the image list. If we want the full
+-// collection, leave it as an empty struct
+-opts := images.ListOpts{ChangesSince: "2014-01-01T01:02:03Z", Name: "Ubuntu 12.04"}
 -
--func (err *ContainerNotRunning) Error() string {
--	return "Container not running: " + err.ID
--}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/container_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/container_test.go
-deleted file mode 100644
-index d80270b..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/container_test.go
-+++ /dev/null
-@@ -1,1495 +0,0 @@
--// Copyright 2014 go-dockerclient authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the LICENSE file.
+-// Retrieve a pager (i.e. a paginated collection)
+-pager := images.List(client, opts)
 -
--package docker
+-// Define an anonymous function to be executed on each page's iteration
+-err := pager.EachPage(func(page pagination.Page) (bool, error) {
+-  imageList, err := images.ExtractImages(page)
+-
+-  for _, i := range imageList {
+-    // "i" will be a images.Image
+-  }
+-})
+-```
 -
+-## List flavors
+-
+-```go
 -import (
--	"bytes"
--	"encoding/json"
--	"io/ioutil"
--	"net"
--	"net/http"
--	"net/http/httptest"
--	"net/url"
--	"os"
--	"reflect"
--	"regexp"
--	"runtime"
--	"strconv"
--	"strings"
--	"testing"
--	"time"
+-  "github.com/rackspace/gophercloud/pagination"
+-  "github.com/rackspace/gophercloud/openstack/compute/v2/flavors"
 -)
 -
--func TestStateString(t *testing.T) {
--	started := time.Now().Add(-3 * time.Hour)
--	var tests = []struct {
--		input    State
--		expected string
--	}{
--		{State{Running: true, Paused: true}, "^paused$"},
--		{State{Running: true, StartedAt: started}, "^Up 3h.*$"},
--		{State{Running: false, ExitCode: 7}, "^Exit 7$"},
--	}
--	for _, tt := range tests {
--		re := regexp.MustCompile(tt.expected)
--		if got := tt.input.String(); !re.MatchString(got) {
--			t.Errorf("State.String(): wrong result. Want %q. Got %q.", tt.expected, got)
--		}
--	}
--}
+-// We have the option of filtering the flavor list. If we want the full
+-// collection, leave it as an empty struct
+-opts := flavors.ListOpts{ChangesSince: "2014-01-01T01:02:03Z", MinRAM: 4}
 -
--func TestListContainers(t *testing.T) {
--	jsonContainers := `[
--     {
--             "Id": "8dfafdbc3a40",
--             "Image": "base:latest",
--             "Command": "echo 1",
--             "Created": 1367854155,
--             "Ports":[{"PrivatePort": 2222, "PublicPort": 3333, "Type": "tcp"}],
--             "Status": "Exit 0"
--     },
--     {
--             "Id": "9cd87474be90",
--             "Image": "base:latest",
--             "Command": "echo 222222",
--             "Created": 1367854155,
--             "Ports":[{"PrivatePort": 2222, "PublicPort": 3333, "Type": "tcp"}],
--             "Status": "Exit 0"
--     },
--     {
--             "Id": "3176a2479c92",
--             "Image": "base:latest",
--             "Command": "echo 3333333333333333",
--             "Created": 1367854154,
--             "Ports":[{"PrivatePort": 2221, "PublicPort": 3331, "Type": "tcp"}],
--             "Status": "Exit 0"
--     },
--     {
--             "Id": "4cb07b47f9fb",
--             "Image": "base:latest",
--             "Command": "echo 444444444444444444444444444444444",
--             "Ports":[{"PrivatePort": 2223, "PublicPort": 3332, "Type": "tcp"}],
--             "Created": 1367854152,
--             "Status": "Exit 0"
--     }
--]`
--	var expected []APIContainers
--	err := json.Unmarshal([]byte(jsonContainers), &expected)
--	if err != nil {
--		t.Fatal(err)
--	}
--	client := newTestClient(&FakeRoundTripper{message: jsonContainers, status: http.StatusOK})
--	containers, err := client.ListContainers(ListContainersOptions{})
--	if err != nil {
--		t.Fatal(err)
--	}
--	if !reflect.DeepEqual(containers, expected) {
--		t.Errorf("ListContainers: Expected %#v. Got %#v.", expected, containers)
--	}
--}
+-// Retrieve a pager (i.e. a paginated collection)
+-pager := flavors.List(client, opts)
 -
--func TestListContainersParams(t *testing.T) {
--	var tests = []struct {
--		input  ListContainersOptions
--		params map[string][]string
--	}{
--		{ListContainersOptions{}, map[string][]string{}},
--		{ListContainersOptions{All: true}, map[string][]string{"all": {"1"}}},
--		{ListContainersOptions{All: true, Limit: 10}, map[string][]string{"all": {"1"}, "limit": {"10"}}},
--		{
--			ListContainersOptions{All: true, Limit: 10, Since: "adf9983", Before: "abdeef"},
--			map[string][]string{"all": {"1"}, "limit": {"10"}, "since": {"adf9983"}, "before": {"abdeef"}},
--		},
--	}
--	fakeRT := &FakeRoundTripper{message: "[]", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	u, _ := url.Parse(client.getURL("/containers/json"))
--	for _, tt := range tests {
--		client.ListContainers(tt.input)
--		got := map[string][]string(fakeRT.requests[0].URL.Query())
--		if !reflect.DeepEqual(got, tt.params) {
--			t.Errorf("Expected %#v, got %#v.", tt.params, got)
--		}
--		if path := fakeRT.requests[0].URL.Path; path != u.Path {
--			t.Errorf("Wrong path on request. Want %q. Got %q.", u.Path, path)
--		}
--		if meth := fakeRT.requests[0].Method; meth != "GET" {
--			t.Errorf("Wrong HTTP method. Want GET. Got %s.", meth)
--		}
--		fakeRT.Reset()
--	}
--}
+-// Define an anonymous function to be executed on each page's iteration
+-err := pager.EachPage(func(page pagination.Page) (bool, error) {
+-  flavorList, err := networks.ExtractFlavors(page)
 -
--func TestListContainersFailure(t *testing.T) {
--	var tests = []struct {
--		status  int
--		message string
--	}{
--		{400, "bad parameter"},
--		{500, "internal server error"},
--	}
--	for _, tt := range tests {
--		client := newTestClient(&FakeRoundTripper{message: tt.message, status: tt.status})
--		expected := Error{Status: tt.status, Message: tt.message}
--		containers, err := client.ListContainers(ListContainersOptions{})
--		if !reflect.DeepEqual(expected, *err.(*Error)) {
--			t.Errorf("Wrong error in ListContainers. Want %#v. Got %#v.", expected, err)
--		}
--		if len(containers) > 0 {
--			t.Errorf("ListContainers failure. Expected empty list. Got %#v.", containers)
--		}
--	}
--}
+-  for _, f := range flavorList {
+-    // "f" will be a flavors.Flavor
+-  }
+-})
+-```
 -
--func TestInspectContainer(t *testing.T) {
--	jsonContainer := `{
--             "Id": "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2",
--             "Created": "2013-05-07T14:51:42.087658+02:00",
--             "Path": "date",
--             "Args": [],
--             "Config": {
--                     "Hostname": "4fa6e0f0c678",
--                     "User": "",
--                     "Memory": 17179869184,
--                     "MemorySwap": 34359738368,
--                     "AttachStdin": false,
--                     "AttachStdout": true,
--                     "AttachStderr": true,
--                     "PortSpecs": null,
--                     "Tty": false,
--                     "OpenStdin": false,
--                     "StdinOnce": false,
--                     "Env": null,
--                     "Cmd": [
--                             "date"
--                     ],
--                     "Image": "base",
--                     "Volumes": {},
--                     "VolumesFrom": ""
--             },
--             "State": {
--                     "Running": false,
--                     "Pid": 0,
--                     "ExitCode": 0,
--                     "StartedAt": "2013-05-07T14:51:42.087658+02:00",
--                     "Ghost": false
--             },
--             "Image": "b750fe79269d2ec9a3c593ef05b4332b1d1a02a62b4accb2c21d589ff2f5f2dc",
--             "NetworkSettings": {
--                     "IpAddress": "",
--                     "IpPrefixLen": 0,
--                     "Gateway": "",
--                     "Bridge": "",
--                     "PortMapping": null
--             },
--             "SysInitPath": "/home/kitty/go/src/github.com/dotcloud/docker/bin/docker",
--             "ResolvConfPath": "/etc/resolv.conf",
--             "Volumes": {},
--             "HostConfig": {
--               "Binds": null,
--               "ContainerIDFile": "",
--               "LxcConf": [],
--               "Privileged": false,
--               "PortBindings": {
--                 "80/tcp": [
--                   {
--                     "HostIp": "0.0.0.0",
--                     "HostPort": "49153"
--                   }
--                 ]
--               },
--               "Links": null,
--               "PublishAllPorts": false
--             }
--}`
--	var expected Container
--	err := json.Unmarshal([]byte(jsonContainer), &expected)
--	if err != nil {
--		t.Fatal(err)
--	}
--	fakeRT := &FakeRoundTripper{message: jsonContainer, status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	id := "4fa6e0f0c678"
--	container, err := client.InspectContainer(id)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if !reflect.DeepEqual(*container, expected) {
--		t.Errorf("InspectContainer(%q): Expected %#v. Got %#v.", id, expected, container)
--	}
--	expectedURL, _ := url.Parse(client.getURL("/containers/4fa6e0f0c678/json"))
--	if gotPath := fakeRT.requests[0].URL.Path; gotPath != expectedURL.Path {
--		t.Errorf("InspectContainer(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
--	}
--}
+-## Create/delete image
 -
--func TestInspectContainerNegativeSwap(t *testing.T) {
--	jsonContainer := `{
--             "Id": "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2",
--             "Created": "2013-05-07T14:51:42.087658+02:00",
--             "Path": "date",
--             "Args": [],
--             "Config": {
--                     "Hostname": "4fa6e0f0c678",
--                     "User": "",
--                     "Memory": 17179869184,
--                     "MemorySwap": -1,
--                     "AttachStdin": false,
--                     "AttachStdout": true,
--                     "AttachStderr": true,
--                     "PortSpecs": null,
--                     "Tty": false,
--                     "OpenStdin": false,
--                     "StdinOnce": false,
--                     "Env": null,
--                     "Cmd": [
--                             "date"
--                     ],
--                     "Image": "base",
--                     "Volumes": {},
--                     "VolumesFrom": ""
--             },
--             "State": {
--                     "Running": false,
--                     "Pid": 0,
--                     "ExitCode": 0,
--                     "StartedAt": "2013-05-07T14:51:42.087658+02:00",
--                     "Ghost": false
--             },
--             "Image": "b750fe79269d2ec9a3c593ef05b4332b1d1a02a62b4accb2c21d589ff2f5f2dc",
--             "NetworkSettings": {
--                     "IpAddress": "",
--                     "IpPrefixLen": 0,
--                     "Gateway": "",
--                     "Bridge": "",
--                     "PortMapping": null
--             },
--             "SysInitPath": "/home/kitty/go/src/github.com/dotcloud/docker/bin/docker",
--             "ResolvConfPath": "/etc/resolv.conf",
--             "Volumes": {},
--             "HostConfig": {
--               "Binds": null,
--               "ContainerIDFile": "",
--               "LxcConf": [],
--               "Privileged": false,
--               "PortBindings": {
--                 "80/tcp": [
--                   {
--                     "HostIp": "0.0.0.0",
--                     "HostPort": "49153"
--                   }
--                 ]
--               },
--               "Links": null,
--               "PublishAllPorts": false
--             }
--}`
--	var expected Container
--	err := json.Unmarshal([]byte(jsonContainer), &expected)
--	if err != nil {
--		t.Fatal(err)
--	}
--	fakeRT := &FakeRoundTripper{message: jsonContainer, status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	id := "4fa6e0f0c678"
--	container, err := client.InspectContainer(id)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if !reflect.DeepEqual(*container, expected) {
--		t.Errorf("InspectContainer(%q): Expected %#v. Got %#v.", id, expected, container)
--	}
--	expectedURL, _ := url.Parse(client.getURL("/containers/4fa6e0f0c678/json"))
--	if gotPath := fakeRT.requests[0].URL.Path; gotPath != expectedURL.Path {
--		t.Errorf("InspectContainer(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
--	}
--}
+-Image management has been shifted to Glance, but unfortunately this service is
+-not supported as of yet. You can, however, list Compute images like so:
 -
--func TestInspectContainerFailure(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "server error", status: 500})
--	expected := Error{Status: 500, Message: "server error"}
--	container, err := client.InspectContainer("abe033")
--	if container != nil {
--		t.Errorf("InspectContainer: Expected <nil> container, got %#v", container)
--	}
--	if !reflect.DeepEqual(expected, *err.(*Error)) {
--		t.Errorf("InspectContainer: Wrong error information. Want %#v. Got %#v.", expected, err)
--	}
--}
+-```go
+-import "github.com/rackspace/gophercloud/openstack/compute/v2/images"
+-
+-// Retrieve a pager (i.e. a paginated collection)
+-pager := images.List(client, opts)
+-
+-// Define an anonymous function to be executed on each page's iteration
+-err := pager.EachPage(func(page pagination.Page) (bool, error) {
+-  imageList, err := images.ExtractImages(page)
+-
+-  for _, i := range imageList {
+-    // "i" will be a images.Image
+-  }
+-})
+-```
+-
+-# Other
+-
+-## List keypairs
+-
+-```go
+-import "github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs"
+-
+-// Retrieve a pager (i.e. a paginated collection)
+-pager := keypairs.List(client, opts)
+-
+-// Define an anonymous function to be executed on each page's iteration
+-err := pager.EachPage(func(page pagination.Page) (bool, error) {
+-  keyList, err := keypairs.ExtractKeyPairs(page)
+-
+-  for _, k := range keyList {
+-    // "k" will be a keypairs.KeyPair
+-  }
+-})
+-```
 -
--func TestInspectContainerNotFound(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "no such container", status: 404})
--	container, err := client.InspectContainer("abe033")
--	if container != nil {
--		t.Errorf("InspectContainer: Expected <nil> container, got %#v", container)
--	}
--	expected := &NoSuchContainer{ID: "abe033"}
--	if !reflect.DeepEqual(err, expected) {
--		t.Errorf("InspectContainer: Wrong error information. Want %#v. Got %#v.", expected, err)
--	}
--}
+-## Create/delete keypairs
 -
--func TestContainerChanges(t *testing.T) {
--	jsonChanges := `[
--     {
--             "Path":"/dev",
--             "Kind":0
--     },
--     {
--             "Path":"/dev/kmsg",
--             "Kind":1
--     },
--     {
--             "Path":"/test",
--             "Kind":1
--     }
--]`
--	var expected []Change
--	err := json.Unmarshal([]byte(jsonChanges), &expected)
--	if err != nil {
--		t.Fatal(err)
--	}
--	fakeRT := &FakeRoundTripper{message: jsonChanges, status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	id := "4fa6e0f0c678"
--	changes, err := client.ContainerChanges(id)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if !reflect.DeepEqual(changes, expected) {
--		t.Errorf("ContainerChanges(%q): Expected %#v. Got %#v.", id, expected, changes)
--	}
--	expectedURL, _ := url.Parse(client.getURL("/containers/4fa6e0f0c678/changes"))
--	if gotPath := fakeRT.requests[0].URL.Path; gotPath != expectedURL.Path {
--		t.Errorf("ContainerChanges(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
--	}
+-To create a new keypair, you need to specify its name and, optionally, a
+-pregenerated OpenSSH-formatted public key.
+-
+-```go
+-import "github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs"
+-
+-opts := keypairs.CreateOpts{
+-  Name: "new_key",
+-  PublicKey: "...",
 -}
 -
--func TestContainerChangesFailure(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "server error", status: 500})
--	expected := Error{Status: 500, Message: "server error"}
--	changes, err := client.ContainerChanges("abe033")
--	if changes != nil {
--		t.Errorf("ContainerChanges: Expected <nil> changes, got %#v", changes)
--	}
--	if !reflect.DeepEqual(expected, *err.(*Error)) {
--		t.Errorf("ContainerChanges: Wrong error information. Want %#v. Got %#v.", expected, err)
--	}
+-response := keypairs.Create(client, opts)
+-
+-key, err := response.Extract()
+-```
+-
+-To delete an existing keypair:
+-
+-```go
+-response := keypairs.Delete(client, "keypair_id")
+-```
+-
+-## List IP addresses
+-
+-This operation is not currently supported.
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/README.md b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/README.md
+deleted file mode 100644
+index 3199837..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/README.md
++++ /dev/null
+@@ -1,57 +0,0 @@
+-# Gophercloud Acceptance tests
+-
+-The purpose of these acceptance tests is to validate that SDK features meet
+-the requirements of a contract - to consumers, other parts of the library, and
+-to a remote API.
+-
+-> **Note:** Because every test will be run against a real API endpoint, you
+-> may incur bandwidth and service charges for all the resource usage. These
+-> tests *should* remove their remote products automatically. However, there may
+-> be certain cases where this does not happen; always double-check to make sure
+-> you have no stragglers left behind.
+-
+-### Step 1. Set environment variables
+-
+-A lot of tests rely on environment variables for configuration - so you will need
+-to set them before running the suite. If you're testing against pure OpenStack APIs,
+-you can download a file that contains all of these variables for you: just visit
+-the `project/access_and_security` page in your control panel and click the "Download
+-OpenStack RC File" button at the top right. For all other providers, you will need
+-to set them manually.
+-
+-#### Authentication
+-
+-|Name|Description|
+-|---|---|
+-|`OS_USERNAME`|Your API username|
+-|`OS_PASSWORD`|Your API password|
+-|`OS_AUTH_URL`|The identity URL you need to authenticate|
+-|`OS_TENANT_NAME`|Your API tenant name|
+-|`OS_TENANT_ID`|Your API tenant ID|
+-|`RS_USERNAME`|Your Rackspace username|
+-|`RS_API_KEY`|Your Rackspace API key|
+-
+-#### General
+-
+-|Name|Description|
+-|---|---|
+-|`OS_REGION_NAME`|The region you want your resources to reside in|
+-|`RS_REGION`|Rackspace region you want your resource to reside in|
+-
+-#### Compute
+-
+-|Name|Description|
+-|---|---|
+-|`OS_IMAGE_ID`|The ID of the image your want your server to be based on|
+-|`OS_FLAVOR_ID`|The ID of the flavor you want your server to be based on|
+-|`OS_FLAVOR_ID_RESIZE`|The ID of the flavor you want your server to be resized to|
+-|`RS_IMAGE_ID`|The ID of the image you want servers to be created with|
+-|`RS_FLAVOR_ID`|The ID of the flavor you want your server to be created with|
+-
+-### 2. Run the test suite
+-
+-From the root directory, run:
+-
+-```
+-./script/acceptancetest
+-```
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/blockstorage/v1/snapshots_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/blockstorage/v1/snapshots_test.go
+deleted file mode 100644
+index 9132ee5..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/blockstorage/v1/snapshots_test.go
++++ /dev/null
+@@ -1,70 +0,0 @@
+-// +build acceptance
+-
+-package v1
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots"
+-	"github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestSnapshots(t *testing.T) {
+-
+-	client, err := newClient()
+-	th.AssertNoErr(t, err)
+-	
+-	v, err := volumes.Create(client, &volumes.CreateOpts{
+-		Name: "gophercloud-test-volume",
+-		Size: 1,
+-	}).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	err = volumes.WaitForStatus(client, v.ID, "available", 120)
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Created volume: %v\n", v)
+-
+-	ss, err := snapshots.Create(client, &snapshots.CreateOpts{
+-		Name:     "gophercloud-test-snapshot",
+-		VolumeID: v.ID,
+-	}).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	err = snapshots.WaitForStatus(client, ss.ID, "available", 120)
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Created snapshot: %+v\n", ss)
+-
+-	err = snapshots.Delete(client, ss.ID).ExtractErr()
+-	th.AssertNoErr(t, err)
+-
+-	err = gophercloud.WaitFor(120, func() (bool, error) {
+-		_, err := snapshots.Get(client, ss.ID).Extract()
+-		if err != nil {
+-			return true, nil
+-		}
+-
+-		return false, nil
+-	})
+-	th.AssertNoErr(t, err)
+-
+-	t.Log("Deleted snapshot\n")
+-
+-	err = volumes.Delete(client, v.ID).ExtractErr()
+-	th.AssertNoErr(t, err)
+-
+-	err = gophercloud.WaitFor(120, func() (bool, error) {
+-		_, err := volumes.Get(client, v.ID).Extract()
+-		if err != nil {
+-			return true, nil
+-		}
+-
+-		return false, nil
+-	})
+-	th.AssertNoErr(t, err)
+-
+-	t.Log("Deleted volume\n")
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/blockstorage/v1/volumes_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/blockstorage/v1/volumes_test.go
+deleted file mode 100644
+index 99da39a..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/blockstorage/v1/volumes_test.go
++++ /dev/null
+@@ -1,63 +0,0 @@
+-// +build acceptance blockstorage
 -
--func TestContainerChangesNotFound(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "no such container", status: 404})
--	changes, err := client.ContainerChanges("abe033")
--	if changes != nil {
--		t.Errorf("ContainerChanges: Expected <nil> changes, got %#v", changes)
--	}
--	expected := &NoSuchContainer{ID: "abe033"}
--	if !reflect.DeepEqual(err, expected) {
--		t.Errorf("ContainerChanges: Wrong error information. Want %#v. Got %#v.", expected, err)
--	}
+-package v1
+-
+-import (
+-	"os"
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/openstack"
+-	"github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func newClient() (*gophercloud.ServiceClient, error) {
+-	ao, err := openstack.AuthOptionsFromEnv()
+-	th.AssertNoErr(t, err)
+-
+-	client, err := openstack.AuthenticatedClient(ao)
+-	th.AssertNoErr(t, err)
+-
+-	return openstack.NewBlockStorageV1(client, gophercloud.EndpointOpts{
+-		Region: os.Getenv("OS_REGION_NAME"),
+-	})
 -}
 -
--func TestCreateContainer(t *testing.T) {
--	jsonContainer := `{
--             "Id": "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2",
--	     "Warnings": []
--}`
--	var expected Container
--	err := json.Unmarshal([]byte(jsonContainer), &expected)
--	if err != nil {
--		t.Fatal(err)
--	}
--	fakeRT := &FakeRoundTripper{message: jsonContainer, status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	config := Config{AttachStdout: true, AttachStdin: true}
--	opts := CreateContainerOptions{Name: "TestCreateContainer", Config: &config}
--	container, err := client.CreateContainer(opts)
--	if err != nil {
--		t.Fatal(err)
--	}
--	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
--	if container.ID != id {
--		t.Errorf("CreateContainer: wrong ID. Want %q. Got %q.", id, container.ID)
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "POST" {
--		t.Errorf("CreateContainer: wrong HTTP method. Want %q. Got %q.", "POST", req.Method)
--	}
--	expectedURL, _ := url.Parse(client.getURL("/containers/create"))
--	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
--		t.Errorf("CreateContainer: Wrong path in request. Want %q. Got %q.", expectedURL.Path, gotPath)
--	}
--	var gotBody Config
--	err = json.NewDecoder(req.Body).Decode(&gotBody)
--	if err != nil {
--		t.Fatal(err)
+-func TestVolumes(t *testing.T) {
+-	client, err := newClient()
+-	th.AssertNoErr(t, err)
+-
+-	cv, err := volumes.Create(client, &volumes.CreateOpts{
+-		Size: 1,
+-		Name: "gophercloud-test-volume",
+-	}).Extract()
+-	th.AssertNoErr(t, err)
+-	defer func() {
+-		err = volumes.WaitForStatus(client, cv.ID, "available", 60)
+-		th.AssertNoErr(t, err)
+-		err = volumes.Delete(client, cv.ID).ExtractErr()
+-		th.AssertNoErr(t, err)
+-	}()
+-
+-	_, err = volumes.Update(client, cv.ID, &volumes.UpdateOpts{
+-		Name: "gophercloud-updated-volume",
+-	}).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	v, err := volumes.Get(client, cv.ID).Extract()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Got volume: %+v\n", v)
+-
+-	if v.Name != "gophercloud-updated-volume" {
+-		t.Errorf("Unable to update volume: Expected name: gophercloud-updated-volume\nActual name: %s", v.Name)
 -	}
+-
+-	err = volumes.List(client, &volumes.ListOpts{Name: "gophercloud-updated-volume"}).EachPage(func(page pagination.Page) (bool, error) {
+-		vols, err := volumes.ExtractVolumes(page)
+-		th.CheckEquals(t, 1, len(vols))
+-		return true, err
+-	})
+-	th.AssertNoErr(t, err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/blockstorage/v1/volumetypes_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/blockstorage/v1/volumetypes_test.go
+deleted file mode 100644
+index 5adcd81..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/blockstorage/v1/volumetypes_test.go
++++ /dev/null
+@@ -1,49 +0,0 @@
+-// +build acceptance
 -
--func TestCreateContainerImageNotFound(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "No such image", status: http.StatusNotFound})
--	config := Config{AttachStdout: true, AttachStdin: true}
--	container, err := client.CreateContainer(CreateContainerOptions{Config: &config})
--	if container != nil {
--		t.Errorf("CreateContainer: expected <nil> container, got %#v.", container)
--	}
--	if !reflect.DeepEqual(err, ErrNoSuchImage) {
--		t.Errorf("CreateContainer: Wrong error type. Want %#v. Got %#v.", ErrNoSuchImage, err)
--	}
+-package v1
+-
+-import (
+-	"testing"
+-	"time"
+-
+-	"github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestVolumeTypes(t *testing.T) {
+-	client, err := newClient()
+-	th.AssertNoErr(t, err)
+-
+-	vt, err := volumetypes.Create(client, &volumetypes.CreateOpts{
+-		ExtraSpecs: map[string]interface{}{
+-			"capabilities": "gpu",
+-			"priority":     3,
+-		},
+-		Name: "gophercloud-test-volumeType",
+-	}).Extract()
+-	th.AssertNoErr(t, err)
+-	defer func() {
+-		time.Sleep(10000 * time.Millisecond)
+-		err = volumetypes.Delete(client, vt.ID).ExtractErr()
+-		if err != nil {
+-			t.Error(err)
+-			return
+-		}
+-	}()
+-	t.Logf("Created volume type: %+v\n", vt)
+-
+-	vt, err = volumetypes.Get(client, vt.ID).Extract()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Got volume type: %+v\n", vt)
+-
+-	err = volumetypes.List(client).EachPage(func(page pagination.Page) (bool, error) {
+-		volTypes, err := volumetypes.ExtractVolumeTypes(page)
+-		if len(volTypes) != 1 {
+-			t.Errorf("Expected 1 volume type, got %d", len(volTypes))
+-		}
+-		t.Logf("Listing volume types: %+v\n", volTypes)
+-		return true, err
+-	})
+-	th.AssertNoErr(t, err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/client_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/client_test.go
+deleted file mode 100644
+index 6e88819..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/client_test.go
++++ /dev/null
+@@ -1,40 +0,0 @@
+-// +build acceptance
 -
--func TestStartContainer(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
--	err := client.StartContainer(id, &HostConfig{})
+-package openstack
+-
+-import (
+-	"os"
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/openstack"
+-)
+-
+-func TestAuthenticatedClient(t *testing.T) {
+-	// Obtain credentials from the environment.
+-	ao, err := openstack.AuthOptionsFromEnv()
 -	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "POST" {
--		t.Errorf("StartContainer(%q): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
--	}
--	expectedURL, _ := url.Parse(client.getURL("/containers/" + id + "/start"))
--	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
--		t.Errorf("StartContainer(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
--	}
--	expectedContentType := "application/json"
--	if contentType := req.Header.Get("Content-Type"); contentType != expectedContentType {
--		t.Errorf("StartContainer(%q): Wrong content-type in request. Want %q. Got %q.", id, expectedContentType, contentType)
+-		t.Fatalf("Unable to acquire credentials: %v", err)
 -	}
--}
 -
--func TestStartContainerNilHostConfig(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
--	err := client.StartContainer(id, nil)
+-	client, err := openstack.AuthenticatedClient(ao)
 -	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "POST" {
--		t.Errorf("StartContainer(%q): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
--	}
--	expectedURL, _ := url.Parse(client.getURL("/containers/" + id + "/start"))
--	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
--		t.Errorf("StartContainer(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
--	}
--	expectedContentType := "application/json"
--	if contentType := req.Header.Get("Content-Type"); contentType != expectedContentType {
--		t.Errorf("StartContainer(%q): Wrong content-type in request. Want %q. Got %q.", id, expectedContentType, contentType)
+-		t.Fatalf("Unable to authenticate: %v", err)
 -	}
--}
 -
--func TestStartContainerNotFound(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
--	err := client.StartContainer("a2344", &HostConfig{})
--	expected := &NoSuchContainer{ID: "a2344"}
--	if !reflect.DeepEqual(err, expected) {
--		t.Errorf("StartContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
+-	if client.TokenID == "" {
+-		t.Errorf("No token ID assigned to the client")
 -	}
--}
 -
--func TestStartContainerAlreadyRunning(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "container already running", status: http.StatusNotModified})
--	err := client.StartContainer("a2334", &HostConfig{})
--	expected := &ContainerAlreadyRunning{ID: "a2334"}
--	if !reflect.DeepEqual(err, expected) {
--		t.Errorf("StartContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
--	}
--}
+-	t.Logf("Client successfully acquired a token: %v", client.TokenID)
 -
--func TestStopContainer(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusNoContent}
--	client := newTestClient(fakeRT)
--	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
--	err := client.StopContainer(id, 10)
+-	// Find the storage service in the service catalog.
+-	storage, err := openstack.NewObjectStorageV1(client, gophercloud.EndpointOpts{
+-		Region: os.Getenv("OS_REGION_NAME"),
+-	})
 -	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "POST" {
--		t.Errorf("StopContainer(%q, 10): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
--	}
--	expectedURL, _ := url.Parse(client.getURL("/containers/" + id + "/stop"))
--	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
--		t.Errorf("StopContainer(%q, 10): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
+-		t.Errorf("Unable to locate a storage service: %v", err)
+-	} else {
+-		t.Logf("Located a storage service at endpoint: [%s]", storage.Endpoint)
 -	}
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/bootfromvolume_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/bootfromvolume_test.go
+deleted file mode 100644
+index d08abe6..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/bootfromvolume_test.go
++++ /dev/null
+@@ -1,50 +0,0 @@
+-// +build acceptance
 -
--func TestStopContainerNotFound(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
--	err := client.StopContainer("a2334", 10)
--	expected := &NoSuchContainer{ID: "a2334"}
--	if !reflect.DeepEqual(err, expected) {
--		t.Errorf("StopContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
--	}
--}
+-package v2
 -
--func TestStopContainerNotRunning(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "container not running", status: http.StatusNotModified})
--	err := client.StopContainer("a2334", 10)
--	expected := &ContainerNotRunning{ID: "a2334"}
--	if !reflect.DeepEqual(err, expected) {
--		t.Errorf("StopContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
--	}
--}
+-import (
+-	"testing"
 -
--func TestRestartContainer(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusNoContent}
--	client := newTestClient(fakeRT)
--	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
--	err := client.RestartContainer(id, 10)
--	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "POST" {
--		t.Errorf("RestartContainer(%q, 10): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
--	}
--	expectedURL, _ := url.Parse(client.getURL("/containers/" + id + "/restart"))
--	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
--		t.Errorf("RestartContainer(%q, 10): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
--	}
--}
+-	"github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume"
+-	"github.com/rackspace/gophercloud/openstack/compute/v2/servers"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/smashwilson/gophercloud/acceptance/tools"
+-)
 -
--func TestRestartContainerNotFound(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
--	err := client.RestartContainer("a2334", 10)
--	expected := &NoSuchContainer{ID: "a2334"}
--	if !reflect.DeepEqual(err, expected) {
--		t.Errorf("RestartContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
+-func TestBootFromVolume(t *testing.T) {
+-	client, err := newClient()
+-	th.AssertNoErr(t, err)
+-
+-	if testing.Short() {
+-		t.Skip("Skipping test that requires server creation in short mode.")
 -	}
--}
 -
--func TestPauseContainer(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusNoContent}
--	client := newTestClient(fakeRT)
--	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
--	err := client.PauseContainer(id)
+-	choices, err := ComputeChoicesFromEnv()
 -	if err != nil {
 -		t.Fatal(err)
 -	}
--	req := fakeRT.requests[0]
--	if req.Method != "POST" {
--		t.Errorf("PauseContainer(%q): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
--	}
--	expectedURL, _ := url.Parse(client.getURL("/containers/" + id + "/pause"))
--	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
--		t.Errorf("PauseContainer(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
--	}
--}
 -
--func TestPauseContainerNotFound(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
--	err := client.PauseContainer("a2334")
--	expected := &NoSuchContainer{ID: "a2334"}
--	if !reflect.DeepEqual(err, expected) {
--		t.Errorf("PauseContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
--	}
--}
+-	name := tools.RandomString("Gophercloud-", 8)
+-	t.Logf("Creating server [%s].", name)
 -
--func TestUnpauseContainer(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusNoContent}
--	client := newTestClient(fakeRT)
--	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
--	err := client.UnpauseContainer(id)
--	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "POST" {
--		t.Errorf("PauseContainer(%q): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
--	}
--	expectedURL, _ := url.Parse(client.getURL("/containers/" + id + "/unpause"))
--	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
--		t.Errorf("PauseContainer(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
+-	bd := []bootfromvolume.BlockDevice{
+-		bootfromvolume.BlockDevice{
+-			UUID:       choices.ImageID,
+-			SourceType: bootfromvolume.Image,
+-			VolumeSize: 10,
+-		},
 -	}
--}
 -
--func TestUnpauseContainerNotFound(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
--	err := client.UnpauseContainer("a2334")
--	expected := &NoSuchContainer{ID: "a2334"}
--	if !reflect.DeepEqual(err, expected) {
--		t.Errorf("PauseContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
+-	serverCreateOpts := servers.CreateOpts{
+-		Name:      name,
+-		FlavorRef: "3",
 -	}
+-	server, err := bootfromvolume.Create(client, bootfromvolume.CreateOptsExt{
+-		serverCreateOpts,
+-		bd,
+-	}).Extract()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Created server: %+v\n", server)
+-	//defer deleteServer(t, client, server)
+-	t.Logf("Deleting server [%s]...", name)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/compute_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/compute_test.go
+deleted file mode 100644
+index 46eb9ff..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/compute_test.go
++++ /dev/null
+@@ -1,97 +0,0 @@
+-// +build acceptance
 -
--func TestKillContainer(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusNoContent}
--	client := newTestClient(fakeRT)
--	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
--	err := client.KillContainer(KillContainerOptions{ID: id})
+-package v2
+-
+-import (
+-	"fmt"
+-	"os"
+-	"strings"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/acceptance/tools"
+-	"github.com/rackspace/gophercloud/openstack"
+-	"github.com/rackspace/gophercloud/openstack/compute/v2/servers"
+-)
+-
+-func newClient() (*gophercloud.ServiceClient, error) {
+-	ao, err := openstack.AuthOptionsFromEnv()
 -	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "POST" {
--		t.Errorf("KillContainer(%q): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
--	}
--	expectedURL, _ := url.Parse(client.getURL("/containers/" + id + "/kill"))
--	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
--		t.Errorf("KillContainer(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
+-		return nil, err
 -	}
--}
 -
--func TestKillContainerSignal(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusNoContent}
--	client := newTestClient(fakeRT)
--	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
--	err := client.KillContainer(KillContainerOptions{ID: id, Signal: SIGTERM})
+-	client, err := openstack.AuthenticatedClient(ao)
 -	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "POST" {
--		t.Errorf("KillContainer(%q): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
--	}
--	if signal := req.URL.Query().Get("signal"); signal != "15" {
--		t.Errorf("KillContainer(%q): Wrong query string in request. Want %q. Got %q.", id, "15", signal)
+-		return nil, err
 -	}
--}
 -
--func TestKillContainerNotFound(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
--	err := client.KillContainer(KillContainerOptions{ID: "a2334"})
--	expected := &NoSuchContainer{ID: "a2334"}
--	if !reflect.DeepEqual(err, expected) {
--		t.Errorf("KillContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
--	}
+-	return openstack.NewComputeV2(client, gophercloud.EndpointOpts{
+-		Region: os.Getenv("OS_REGION_NAME"),
+-	})
 -}
 -
--func TestRemoveContainer(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
--	opts := RemoveContainerOptions{ID: id}
--	err := client.RemoveContainer(opts)
--	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "DELETE" {
--		t.Errorf("RemoveContainer(%q): wrong HTTP method. Want %q. Got %q.", id, "DELETE", req.Method)
--	}
--	expectedURL, _ := url.Parse(client.getURL("/containers/" + id))
--	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
--		t.Errorf("RemoveContainer(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
--	}
--}
+-func waitForStatus(client *gophercloud.ServiceClient, server *servers.Server, status string) error {
+-	return tools.WaitFor(func() (bool, error) {
+-		latest, err := servers.Get(client, server.ID).Extract()
+-		if err != nil {
+-			return false, err
+-		}
 -
--func TestRemoveContainerRemoveVolumes(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
--	opts := RemoveContainerOptions{ID: id, RemoveVolumes: true}
--	err := client.RemoveContainer(opts)
--	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	params := map[string][]string(req.URL.Query())
--	expected := map[string][]string{"v": {"1"}}
--	if !reflect.DeepEqual(params, expected) {
--		t.Errorf("RemoveContainer(%q): wrong parameters. Want %#v. Got %#v.", id, expected, params)
--	}
+-		if latest.Status == status {
+-			// Success!
+-			return true, nil
+-		}
+-
+-		return false, nil
+-	})
 -}
 -
--func TestRemoveContainerNotFound(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
--	err := client.RemoveContainer(RemoveContainerOptions{ID: "a2334"})
--	expected := &NoSuchContainer{ID: "a2334"}
--	if !reflect.DeepEqual(err, expected) {
--		t.Errorf("RemoveContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
--	}
+-// ComputeChoices contains image and flavor selections for use by the acceptance tests.
+-type ComputeChoices struct {
+-	// ImageID contains the ID of a valid image.
+-	ImageID string
+-
+-	// FlavorID contains the ID of a valid flavor.
+-	FlavorID string
+-
+-	// FlavorIDResize contains the ID of a different flavor available on the same OpenStack installation, that is distinct
+-	// from FlavorID.
+-	FlavorIDResize string
 -}
 -
--func TestResizeContainerTTY(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
--	err := client.ResizeContainerTTY(id, 40, 80)
--	if err != nil {
--		t.Fatal(err)
+-// ComputeChoicesFromEnv populates a ComputeChoices struct from environment variables.
+-// If any required state is missing, an `error` will be returned that enumerates the missing properties.
+-func ComputeChoicesFromEnv() (*ComputeChoices, error) {
+-	imageID := os.Getenv("OS_IMAGE_ID")
+-	flavorID := os.Getenv("OS_FLAVOR_ID")
+-	flavorIDResize := os.Getenv("OS_FLAVOR_ID_RESIZE")
+-
+-	missing := make([]string, 0, 3)
+-	if imageID == "" {
+-		missing = append(missing, "OS_IMAGE_ID")
 -	}
--	req := fakeRT.requests[0]
--	if req.Method != "POST" {
--		t.Errorf("ResizeContainerTTY(%q): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
+-	if flavorID == "" {
+-		missing = append(missing, "OS_FLAVOR_ID")
 -	}
--	expectedURL, _ := url.Parse(client.getURL("/containers/" + id + "/resize"))
--	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
--		t.Errorf("ResizeContainerTTY(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
+-	if flavorIDResize == "" {
+-		missing = append(missing, "OS_FLAVOR_ID_RESIZE")
 -	}
--	got := map[string][]string(req.URL.Query())
--	expectedParams := map[string][]string{
--		"w": {"80"},
--		"h": {"40"},
+-
+-	notDistinct := ""
+-	if flavorID == flavorIDResize {
+-		notDistinct = "OS_FLAVOR_ID and OS_FLAVOR_ID_RESIZE must be distinct."
 -	}
--	if !reflect.DeepEqual(got, expectedParams) {
--		t.Errorf("Expected %#v, got %#v.", expectedParams, got)
+-
+-	if len(missing) > 0 || notDistinct != "" {
+-		text := "You're missing some important setup:\n"
+-		if len(missing) > 0 {
+-			text += " * These environment variables must be provided: " + strings.Join(missing, ", ") + "\n"
+-		}
+-		if notDistinct != "" {
+-			text += " * " + notDistinct + "\n"
+-		}
+-
+-		return nil, fmt.Errorf(text)
 -	}
+-
+-	return &ComputeChoices{ImageID: imageID, FlavorID: flavorID, FlavorIDResize: flavorIDResize}, nil
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/extension_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/extension_test.go
+deleted file mode 100644
+index 1356ffa..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/extension_test.go
++++ /dev/null
+@@ -1,47 +0,0 @@
+-// +build acceptance compute extensionss
 -
--func TestWaitContainer(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: `{"StatusCode": 56}`, status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	id := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
--	status, err := client.WaitContainer(id)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if status != 56 {
--		t.Errorf("WaitContainer(%q): wrong return. Want 56. Got %d.", id, status)
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "POST" {
--		t.Errorf("WaitContainer(%q): wrong HTTP method. Want %q. Got %q.", id, "POST", req.Method)
--	}
--	expectedURL, _ := url.Parse(client.getURL("/containers/" + id + "/wait"))
--	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
--		t.Errorf("WaitContainer(%q): Wrong path in request. Want %q. Got %q.", id, expectedURL.Path, gotPath)
--	}
+-package v2
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/openstack/compute/v2/extensions"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestListExtensions(t *testing.T) {
+-	client, err := newClient()
+-	th.AssertNoErr(t, err)
+-
+-	err = extensions.List(client).EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page ---")
+-
+-		exts, err := extensions.ExtractExtensions(page)
+-		th.AssertNoErr(t, err)
+-
+-		for i, ext := range exts {
+-			t.Logf("[%02d]    name=[%s]\n", i, ext.Name)
+-			t.Logf("       alias=[%s]\n", ext.Alias)
+-			t.Logf(" description=[%s]\n", ext.Description)
+-		}
+-
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
 -}
 -
--func TestWaitContainerNotFound(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
--	_, err := client.WaitContainer("a2334")
--	expected := &NoSuchContainer{ID: "a2334"}
--	if !reflect.DeepEqual(err, expected) {
--		t.Errorf("WaitContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
--	}
+-func TestGetExtension(t *testing.T) {
+-	client, err := newClient()
+-	th.AssertNoErr(t, err)
+-
+-	ext, err := extensions.Get(client, "os-admin-actions").Extract()
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Extension details:")
+-	t.Logf("        name=[%s]\n", ext.Name)
+-	t.Logf("   namespace=[%s]\n", ext.Namespace)
+-	t.Logf("       alias=[%s]\n", ext.Alias)
+-	t.Logf(" description=[%s]\n", ext.Description)
+-	t.Logf("     updated=[%s]\n", ext.Updated)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/flavors_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/flavors_test.go
+deleted file mode 100644
+index 9f51b12..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/flavors_test.go
++++ /dev/null
+@@ -1,57 +0,0 @@
+-// +build acceptance compute flavors
 -
--func TestCommitContainer(t *testing.T) {
--	response := `{"Id":"596069db4bf5"}`
--	client := newTestClient(&FakeRoundTripper{message: response, status: http.StatusOK})
--	id := "596069db4bf5"
--	image, err := client.CommitContainer(CommitContainerOptions{})
+-package v2
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/openstack/compute/v2/flavors"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
+-
+-func TestListFlavors(t *testing.T) {
+-	client, err := newClient()
 -	if err != nil {
--		t.Fatal(err)
--	}
--	if image.ID != id {
--		t.Errorf("CommitContainer: Wrong image id. Want %q. Got %q.", id, image.ID)
+-		t.Fatalf("Unable to create a compute client: %v", err)
 -	}
--}
 -
--func TestCommitContainerParams(t *testing.T) {
--	cfg := Config{Memory: 67108864}
--	json, _ := json.Marshal(&cfg)
--	var tests = []struct {
--		input  CommitContainerOptions
--		params map[string][]string
--		body   []byte
--	}{
--		{CommitContainerOptions{}, map[string][]string{}, nil},
--		{CommitContainerOptions{Container: "44c004db4b17"}, map[string][]string{"container": {"44c004db4b17"}}, nil},
--		{
--			CommitContainerOptions{Container: "44c004db4b17", Repository: "tsuru/python", Message: "something"},
--			map[string][]string{"container": {"44c004db4b17"}, "repo": {"tsuru/python"}, "m": {"something"}},
--			nil,
--		},
--		{
--			CommitContainerOptions{Container: "44c004db4b17", Run: &cfg},
--			map[string][]string{"container": {"44c004db4b17"}},
--			json,
--		},
--	}
--	fakeRT := &FakeRoundTripper{message: "[]", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	u, _ := url.Parse(client.getURL("/commit"))
--	for _, tt := range tests {
--		client.CommitContainer(tt.input)
--		got := map[string][]string(fakeRT.requests[0].URL.Query())
--		if !reflect.DeepEqual(got, tt.params) {
--			t.Errorf("Expected %#v, got %#v.", tt.params, got)
--		}
--		if path := fakeRT.requests[0].URL.Path; path != u.Path {
--			t.Errorf("Wrong path on request. Want %q. Got %q.", u.Path, path)
--		}
--		if meth := fakeRT.requests[0].Method; meth != "POST" {
--			t.Errorf("Wrong HTTP method. Want POST. Got %s.", meth)
+-	t.Logf("ID\tRegion\tName\tStatus\tCreated")
+-
+-	pager := flavors.ListDetail(client, nil)
+-	count, pages := 0, 0
+-	pager.EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("---")
+-		pages++
+-		flavors, err := flavors.ExtractFlavors(page)
+-		if err != nil {
+-			return false, err
 -		}
--		if tt.body != nil {
--			if requestBody, err := ioutil.ReadAll(fakeRT.requests[0].Body); err == nil {
--				if bytes.Compare(requestBody, tt.body) != 0 {
--					t.Errorf("Expected body %#v, got %#v", tt.body, requestBody)
--				}
--			} else {
--				t.Errorf("Error reading request body: %#v", err)
--			}
+-
+-		for _, f := range flavors {
+-			t.Logf("%s\t%s\t%d\t%d\t%d", f.ID, f.Name, f.RAM, f.Disk, f.VCPUs)
 -		}
--		fakeRT.Reset()
--	}
--}
 -
--func TestCommitContainerFailure(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusInternalServerError})
--	_, err := client.CommitContainer(CommitContainerOptions{})
--	if err == nil {
--		t.Error("Expected non-nil error, got <nil>.")
--	}
--}
+-		return true, nil
+-	})
 -
--func TestCommitContainerNotFound(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
--	_, err := client.CommitContainer(CommitContainerOptions{})
--	expected := &NoSuchContainer{ID: ""}
--	if !reflect.DeepEqual(err, expected) {
--		t.Errorf("CommitContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
--	}
+-	t.Logf("--------\n%d flavors listed on %d pages.", count, pages)
 -}
 -
--func TestAttachToContainerLogs(t *testing.T) {
--	var req http.Request
--	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
--		w.Write([]byte{1, 0, 0, 0, 0, 0, 0, 19})
--		w.Write([]byte("something happened!"))
--		req = *r
--	}))
--	defer server.Close()
--	client, _ := NewClient(server.URL)
--	client.SkipServerVersionCheck = true
--	var buf bytes.Buffer
--	opts := AttachToContainerOptions{
--		Container:    "a123456",
--		OutputStream: &buf,
--		Stdout:       true,
--		Stderr:       true,
--		Logs:         true,
--	}
--	err := client.AttachToContainer(opts)
+-func TestGetFlavor(t *testing.T) {
+-	client, err := newClient()
 -	if err != nil {
--		t.Fatal(err)
--	}
--	expected := "something happened!"
--	if buf.String() != expected {
--		t.Errorf("AttachToContainer for logs: wrong output. Want %q. Got %q.", expected, buf.String())
--	}
--	if req.Method != "POST" {
--		t.Errorf("AttachToContainer: wrong HTTP method. Want POST. Got %s.", req.Method)
+-		t.Fatalf("Unable to create a compute client: %v", err)
 -	}
--	u, _ := url.Parse(client.getURL("/containers/a123456/attach"))
--	if req.URL.Path != u.Path {
--		t.Errorf("AttachToContainer for logs: wrong HTTP path. Want %q. Got %q.", u.Path, req.URL.Path)
--	}
--	expectedQs := map[string][]string{
--		"logs":   {"1"},
--		"stdout": {"1"},
--		"stderr": {"1"},
--	}
--	got := map[string][]string(req.URL.Query())
--	if !reflect.DeepEqual(got, expectedQs) {
--		t.Errorf("AttachToContainer: wrong query string. Want %#v. Got %#v.", expectedQs, got)
--	}
--}
 -
--func TestAttachToContainer(t *testing.T) {
--	var reader = strings.NewReader("send value")
--	var req http.Request
--	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
--		w.Write([]byte{1, 0, 0, 0, 0, 0, 0, 5})
--		w.Write([]byte("hello"))
--		req = *r
--	}))
--	defer server.Close()
--	client, _ := NewClient(server.URL)
--	client.SkipServerVersionCheck = true
--	var stdout, stderr bytes.Buffer
--	opts := AttachToContainerOptions{
--		Container:    "a123456",
--		OutputStream: &stdout,
--		ErrorStream:  &stderr,
--		InputStream:  reader,
--		Stdin:        true,
--		Stdout:       true,
--		Stderr:       true,
--		Stream:       true,
--		RawTerminal:  true,
--	}
--	err := client.AttachToContainer(opts)
+-	choices, err := ComputeChoicesFromEnv()
 -	if err != nil {
 -		t.Fatal(err)
 -	}
--	expected := map[string][]string{
--		"stdin":  {"1"},
--		"stdout": {"1"},
--		"stderr": {"1"},
--		"stream": {"1"},
--	}
--	got := map[string][]string(req.URL.Query())
--	if !reflect.DeepEqual(got, expected) {
--		t.Errorf("AttachToContainer: wrong query string. Want %#v. Got %#v.", expected, got)
--	}
--}
--
--func TestAttachToContainerSentinel(t *testing.T) {
--	var reader = strings.NewReader("send value")
--	var req http.Request
--	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
--		w.Write([]byte{1, 0, 0, 0, 0, 0, 0, 5})
--		w.Write([]byte("hello"))
--		req = *r
--	}))
--	defer server.Close()
--	client, _ := NewClient(server.URL)
--	client.SkipServerVersionCheck = true
--	var stdout, stderr bytes.Buffer
--	success := make(chan struct{})
--	opts := AttachToContainerOptions{
--		Container:    "a123456",
--		OutputStream: &stdout,
--		ErrorStream:  &stderr,
--		InputStream:  reader,
--		Stdin:        true,
--		Stdout:       true,
--		Stderr:       true,
--		Stream:       true,
--		RawTerminal:  true,
--		Success:      success,
--	}
--	go client.AttachToContainer(opts)
--	success <- <-success
--}
 -
--func TestAttachToContainerNilStdout(t *testing.T) {
--	var reader = strings.NewReader("send value")
--	var req http.Request
--	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
--		w.Write([]byte{1, 0, 0, 0, 0, 0, 0, 5})
--		w.Write([]byte("hello"))
--		req = *r
--	}))
--	defer server.Close()
--	client, _ := NewClient(server.URL)
--	client.SkipServerVersionCheck = true
--	var stderr bytes.Buffer
--	opts := AttachToContainerOptions{
--		Container:    "a123456",
--		OutputStream: nil,
--		ErrorStream:  &stderr,
--		InputStream:  reader,
--		Stdin:        true,
--		Stdout:       true,
--		Stderr:       true,
--		Stream:       true,
--		RawTerminal:  true,
--	}
--	err := client.AttachToContainer(opts)
+-	flavor, err := flavors.Get(client, choices.FlavorID).Extract()
 -	if err != nil {
--		t.Fatal(err)
+-		t.Fatalf("Unable to get flavor information: %v", err)
 -	}
+-
+-	t.Logf("Flavor: %#v", flavor)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/images_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/images_test.go
+deleted file mode 100644
+index ceab22f..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/images_test.go
++++ /dev/null
+@@ -1,37 +0,0 @@
+-// +build acceptance compute images
 -
--func TestAttachToContainerNilStderr(t *testing.T) {
--	var reader = strings.NewReader("send value")
--	var req http.Request
--	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
--		w.Write([]byte{1, 0, 0, 0, 0, 0, 0, 5})
--		w.Write([]byte("hello"))
--		req = *r
--	}))
--	defer server.Close()
--	client, _ := NewClient(server.URL)
--	client.SkipServerVersionCheck = true
--	var stdout bytes.Buffer
--	opts := AttachToContainerOptions{
--		Container:    "a123456",
--		OutputStream: &stdout,
--		InputStream:  reader,
--		Stdin:        true,
--		Stdout:       true,
--		Stderr:       true,
--		Stream:       true,
--		RawTerminal:  true,
--	}
--	err := client.AttachToContainer(opts)
+-package v2
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/openstack/compute/v2/images"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
+-
+-func TestListImages(t *testing.T) {
+-	client, err := newClient()
 -	if err != nil {
--		t.Fatal(err)
+-		t.Fatalf("Unable to create a compute: client: %v", err)
 -	}
+-
+-	t.Logf("ID\tRegion\tName\tStatus\tCreated")
+-
+-	pager := images.ListDetail(client, nil)
+-	count, pages := 0, 0
+-	pager.EachPage(func(page pagination.Page) (bool, error) {
+-		pages++
+-		images, err := images.ExtractImages(page)
+-		if err != nil {
+-			return false, err
+-		}
+-
+-		for _, i := range images {
+-			t.Logf("%s\t%s\t%s\t%s", i.ID, i.Name, i.Status, i.Created)
+-		}
+-
+-		return true, nil
+-	})
+-
+-	t.Logf("--------\n%d images listed on %d pages.", count, pages)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/pkg.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/pkg.go
+deleted file mode 100644
+index bb158c3..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/pkg.go
++++ /dev/null
+@@ -1,3 +0,0 @@
+-// The v2 package contains acceptance tests for the Openstack Compute V2 service.
 -
--func TestAttachToContainerRawTerminalFalse(t *testing.T) {
--	input := strings.NewReader("send value")
--	var req http.Request
--	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
--		prefix := []byte{1, 0, 0, 0, 0, 0, 0, 5}
--		w.Write(prefix)
--		w.Write([]byte("hello"))
--		req = *r
--	}))
--	defer server.Close()
--	client, _ := NewClient(server.URL)
--	client.SkipServerVersionCheck = true
--	var stdout, stderr bytes.Buffer
--	opts := AttachToContainerOptions{
--		Container:    "a123456",
--		OutputStream: &stdout,
--		ErrorStream:  &stderr,
--		InputStream:  input,
--		Stdin:        true,
--		Stdout:       true,
--		Stderr:       true,
--		Stream:       true,
--		RawTerminal:  false,
--	}
--	err := client.AttachToContainer(opts)
+-package v2
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/servers_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/servers_test.go
+deleted file mode 100644
+index e223c18..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/compute/v2/servers_test.go
++++ /dev/null
+@@ -1,393 +0,0 @@
+-// +build acceptance compute servers
+-
+-package v2
+-
+-import (
+-	"os"
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/acceptance/tools"
+-	"github.com/rackspace/gophercloud/openstack"
+-	"github.com/rackspace/gophercloud/openstack/compute/v2/servers"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/networks"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
+-
+-func TestListServers(t *testing.T) {
+-	client, err := newClient()
 -	if err != nil {
--		t.Fatal(err)
--	}
--	expected := map[string][]string{
--		"stdin":  {"1"},
--		"stdout": {"1"},
--		"stderr": {"1"},
--		"stream": {"1"},
--	}
--	got := map[string][]string(req.URL.Query())
--	if !reflect.DeepEqual(got, expected) {
--		t.Errorf("AttachToContainer: wrong query string. Want %#v. Got %#v.", expected, got)
--	}
--	t.Log(stderr.String())
--	t.Log(stdout.String())
--	if stdout.String() != "hello" {
--		t.Errorf("AttachToContainer: wrong content written to stdout. Want %q. Got %q.", "hello", stderr.String())
+-		t.Fatalf("Unable to create a compute client: %v", err)
 -	}
--}
 -
--func TestAttachToContainerWithoutContainer(t *testing.T) {
--	var client Client
--	err := client.AttachToContainer(AttachToContainerOptions{})
--	expected := &NoSuchContainer{ID: ""}
--	if !reflect.DeepEqual(err, expected) {
--		t.Errorf("AttachToContainer: wrong error. Want %#v. Got %#v.", expected, err)
--	}
+-	t.Logf("ID\tRegion\tName\tStatus\tIPv4\tIPv6")
+-
+-	pager := servers.List(client, servers.ListOpts{})
+-	count, pages := 0, 0
+-	pager.EachPage(func(page pagination.Page) (bool, error) {
+-		pages++
+-		t.Logf("---")
+-
+-		servers, err := servers.ExtractServers(page)
+-		if err != nil {
+-			return false, err
+-		}
+-
+-		for _, s := range servers {
+-			t.Logf("%s\t%s\t%s\t%s\t%s\t\n", s.ID, s.Name, s.Status, s.AccessIPv4, s.AccessIPv6)
+-			count++
+-		}
+-
+-		return true, nil
+-	})
+-
+-	t.Logf("--------\n%d servers listed on %d pages.\n", count, pages)
 -}
 -
--func TestLogs(t *testing.T) {
--	var req http.Request
--	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
--		prefix := []byte{1, 0, 0, 0, 0, 0, 0, 19}
--		w.Write(prefix)
--		w.Write([]byte("something happened!"))
--		req = *r
--	}))
--	defer server.Close()
--	client, _ := NewClient(server.URL)
--	client.SkipServerVersionCheck = true
--	var buf bytes.Buffer
--	opts := LogsOptions{
--		Container:    "a123456",
--		OutputStream: &buf,
--		Follow:       true,
--		Stdout:       true,
--		Stderr:       true,
--		Timestamps:   true,
--	}
--	err := client.Logs(opts)
+-func networkingClient() (*gophercloud.ServiceClient, error) {
+-	opts, err := openstack.AuthOptionsFromEnv()
 -	if err != nil {
--		t.Fatal(err)
--	}
--	expected := "something happened!"
--	if buf.String() != expected {
--		t.Errorf("Logs: wrong output. Want %q. Got %q.", expected, buf.String())
--	}
--	if req.Method != "GET" {
--		t.Errorf("Logs: wrong HTTP method. Want GET. Got %s.", req.Method)
--	}
--	u, _ := url.Parse(client.getURL("/containers/a123456/logs"))
--	if req.URL.Path != u.Path {
--		t.Errorf("AttachToContainer for logs: wrong HTTP path. Want %q. Got %q.", u.Path, req.URL.Path)
--	}
--	expectedQs := map[string][]string{
--		"follow":     {"1"},
--		"stdout":     {"1"},
--		"stderr":     {"1"},
--		"timestamps": {"1"},
--		"tail":       {"all"},
--	}
--	got := map[string][]string(req.URL.Query())
--	if !reflect.DeepEqual(got, expectedQs) {
--		t.Errorf("Logs: wrong query string. Want %#v. Got %#v.", expectedQs, got)
+-		return nil, err
 -	}
--}
 -
--func TestLogsNilStdoutDoesntFail(t *testing.T) {
--	var req http.Request
--	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
--		prefix := []byte{1, 0, 0, 0, 0, 0, 0, 19}
--		w.Write(prefix)
--		w.Write([]byte("something happened!"))
--		req = *r
--	}))
--	defer server.Close()
--	client, _ := NewClient(server.URL)
--	client.SkipServerVersionCheck = true
--	opts := LogsOptions{
--		Container:  "a123456",
--		Follow:     true,
--		Stdout:     true,
--		Stderr:     true,
--		Timestamps: true,
--	}
--	err := client.Logs(opts)
+-	provider, err := openstack.AuthenticatedClient(opts)
 -	if err != nil {
--		t.Fatal(err)
+-		return nil, err
 -	}
+-
+-	return openstack.NewNetworkV2(provider, gophercloud.EndpointOpts{
+-		Name:   "neutron",
+-		Region: os.Getenv("OS_REGION_NAME"),
+-	})
 -}
 -
--func TestLogsNilStderrDoesntFail(t *testing.T) {
--	var req http.Request
--	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
--		prefix := []byte{2, 0, 0, 0, 0, 0, 0, 19}
--		w.Write(prefix)
--		w.Write([]byte("something happened!"))
--		req = *r
--	}))
--	defer server.Close()
--	client, _ := NewClient(server.URL)
--	client.SkipServerVersionCheck = true
--	opts := LogsOptions{
--		Container:  "a123456",
--		Follow:     true,
--		Stdout:     true,
--		Stderr:     true,
--		Timestamps: true,
+-func createServer(t *testing.T, client *gophercloud.ServiceClient, choices *ComputeChoices) (*servers.Server, error) {
+-	if testing.Short() {
+-		t.Skip("Skipping test that requires server creation in short mode.")
 -	}
--	err := client.Logs(opts)
+-
+-	var network networks.Network
+-
+-	networkingClient, err := networkingClient()
 -	if err != nil {
--		t.Fatal(err)
+-		t.Fatalf("Unable to create a networking client: %v", err)
 -	}
--}
 -
--func TestLogsSpecifyingTail(t *testing.T) {
--	var req http.Request
--	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
--		prefix := []byte{1, 0, 0, 0, 0, 0, 0, 19}
--		w.Write(prefix)
--		w.Write([]byte("something happened!"))
--		req = *r
--	}))
--	defer server.Close()
--	client, _ := NewClient(server.URL)
--	client.SkipServerVersionCheck = true
--	var buf bytes.Buffer
--	opts := LogsOptions{
--		Container:    "a123456",
--		OutputStream: &buf,
--		Follow:       true,
--		Stdout:       true,
--		Stderr:       true,
--		Timestamps:   true,
--		Tail:         "100",
+-	pager := networks.List(networkingClient, networks.ListOpts{Name: "public", Limit: 1})
+-	pager.EachPage(func(page pagination.Page) (bool, error) {
+-		networks, err := networks.ExtractNetworks(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract networks: %v", err)
+-			return false, err
+-		}
+-
+-		if len(networks) == 0 {
+-			t.Fatalf("No networks to attach to server")
+-			return false, err
+-		}
+-
+-		network = networks[0]
+-
+-		return false, nil
+-	})
+-
+-	name := tools.RandomString("ACPTTEST", 16)
+-	t.Logf("Attempting to create server: %s\n", name)
+-
+-	server, err := servers.Create(client, servers.CreateOpts{
+-		Name:      name,
+-		FlavorRef: choices.FlavorID,
+-		ImageRef:  choices.ImageID,
+-		Networks: []servers.Network{
+-			servers.Network{UUID: network.ID},
+-		},
+-	}).Extract()
+-	if err != nil {
+-		t.Fatalf("Unable to create server: %v", err)
 -	}
--	err := client.Logs(opts)
+-
+-	return server, err
+-}
+-
+-func TestCreateDestroyServer(t *testing.T) {
+-	choices, err := ComputeChoicesFromEnv()
 -	if err != nil {
 -		t.Fatal(err)
 -	}
--	expected := "something happened!"
--	if buf.String() != expected {
--		t.Errorf("Logs: wrong output. Want %q. Got %q.", expected, buf.String())
--	}
--	if req.Method != "GET" {
--		t.Errorf("Logs: wrong HTTP method. Want GET. Got %s.", req.Method)
--	}
--	u, _ := url.Parse(client.getURL("/containers/a123456/logs"))
--	if req.URL.Path != u.Path {
--		t.Errorf("AttachToContainer for logs: wrong HTTP path. Want %q. Got %q.", u.Path, req.URL.Path)
+-
+-	client, err := newClient()
+-	if err != nil {
+-		t.Fatalf("Unable to create a compute client: %v", err)
 -	}
--	expectedQs := map[string][]string{
--		"follow":     {"1"},
--		"stdout":     {"1"},
--		"stderr":     {"1"},
--		"timestamps": {"1"},
--		"tail":       {"100"},
+-
+-	server, err := createServer(t, client, choices)
+-	if err != nil {
+-		t.Fatalf("Unable to create server: %v", err)
 -	}
--	got := map[string][]string(req.URL.Query())
--	if !reflect.DeepEqual(got, expectedQs) {
--		t.Errorf("Logs: wrong query string. Want %#v. Got %#v.", expectedQs, got)
+-	defer func() {
+-		servers.Delete(client, server.ID)
+-		t.Logf("Server deleted.")
+-	}()
+-
+-	if err = waitForStatus(client, server, "ACTIVE"); err != nil {
+-		t.Fatalf("Unable to wait for server: %v", err)
 -	}
 -}
 -
--func TestLogsRawTerminal(t *testing.T) {
--	var req http.Request
--	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
--		w.Write([]byte("something happened!"))
--		req = *r
--	}))
--	defer server.Close()
--	client, _ := NewClient(server.URL)
--	client.SkipServerVersionCheck = true
--	var buf bytes.Buffer
--	opts := LogsOptions{
--		Container:    "a123456",
--		OutputStream: &buf,
--		Follow:       true,
--		RawTerminal:  true,
--		Stdout:       true,
--		Stderr:       true,
--		Timestamps:   true,
--		Tail:         "100",
+-func TestUpdateServer(t *testing.T) {
+-	client, err := newClient()
+-	if err != nil {
+-		t.Fatalf("Unable to create a compute client: %v", err)
 -	}
--	err := client.Logs(opts)
+-
+-	choices, err := ComputeChoicesFromEnv()
 -	if err != nil {
 -		t.Fatal(err)
 -	}
--	expected := "something happened!"
--	if buf.String() != expected {
--		t.Errorf("Logs: wrong output. Want %q. Got %q.", expected, buf.String())
+-
+-	server, err := createServer(t, client, choices)
+-	if err != nil {
+-		t.Fatal(err)
 -	}
--}
+-	defer servers.Delete(client, server.ID)
 -
--func TestLogsNoContainer(t *testing.T) {
--	var client Client
--	err := client.Logs(LogsOptions{})
--	expected := &NoSuchContainer{ID: ""}
--	if !reflect.DeepEqual(err, expected) {
--		t.Errorf("AttachToContainer: wrong error. Want %#v. Got %#v.", expected, err)
+-	if err = waitForStatus(client, server, "ACTIVE"); err != nil {
+-		t.Fatal(err)
 -	}
--}
 -
--func TestNoSuchContainerError(t *testing.T) {
--	var err error = &NoSuchContainer{ID: "i345"}
--	expected := "No such container: i345"
--	if got := err.Error(); got != expected {
--		t.Errorf("NoSuchContainer: wrong message. Want %q. Got %q.", expected, got)
+-	alternateName := tools.RandomString("ACPTTEST", 16)
+-	for alternateName == server.Name {
+-		alternateName = tools.RandomString("ACPTTEST", 16)
 -	}
--}
 -
--func TestExportContainer(t *testing.T) {
--	content := "exported container tar content"
--	out := stdoutMock{bytes.NewBufferString(content)}
--	client := newTestClient(&FakeRoundTripper{status: http.StatusOK})
--	opts := ExportContainerOptions{ID: "4fa6e0f0c678", OutputStream: out}
--	err := client.ExportContainer(opts)
+-	t.Logf("Attempting to rename the server to %s.", alternateName)
+-
+-	updated, err := servers.Update(client, server.ID, servers.UpdateOpts{Name: alternateName}).Extract()
 -	if err != nil {
--		t.Errorf("ExportContainer: caugh error %#v while exporting container, expected nil", err.Error())
+-		t.Fatalf("Unable to rename server: %v", err)
 -	}
--	if out.String() != content {
--		t.Errorf("ExportContainer: wrong stdout. Want %#v. Got %#v.", content, out.String())
+-
+-	if updated.ID != server.ID {
+-		t.Errorf("Updated server ID [%s] didn't match original server ID [%s]!", updated.ID, server.ID)
 -	}
+-
+-	err = tools.WaitFor(func() (bool, error) {
+-		latest, err := servers.Get(client, updated.ID).Extract()
+-		if err != nil {
+-			return false, err
+-		}
+-
+-		return latest.Name == alternateName, nil
+-	})
 -}
 -
--func TestExportContainerViaUnixSocket(t *testing.T) {
--	if runtime.GOOS != "darwin" {
--		t.Skip("skipping test on %q", runtime.GOOS)
+-func TestActionChangeAdminPassword(t *testing.T) {
+-	t.Parallel()
+-
+-	client, err := newClient()
+-	if err != nil {
+-		t.Fatalf("Unable to create a compute client: %v", err)
 -	}
--	content := "exported container tar content"
--	var buf []byte
--	out := bytes.NewBuffer(buf)
--	tempSocket := tempfile("export_socket")
--	defer os.Remove(tempSocket)
--	endpoint := "unix://" + tempSocket
--	u, _ := parseEndpoint(endpoint)
--	client := Client{
--		HTTPClient:             http.DefaultClient,
--		endpoint:               endpoint,
--		endpointURL:            u,
--		SkipServerVersionCheck: true,
+-
+-	choices, err := ComputeChoicesFromEnv()
+-	if err != nil {
+-		t.Fatal(err)
 -	}
--	listening := make(chan string)
--	done := make(chan int)
--	go runStreamConnServer(t, "unix", tempSocket, listening, done)
--	<-listening // wait for server to start
--	opts := ExportContainerOptions{ID: "4fa6e0f0c678", OutputStream: out}
--	err := client.ExportContainer(opts)
--	<-done // make sure server stopped
+-
+-	server, err := createServer(t, client, choices)
 -	if err != nil {
--		t.Errorf("ExportContainer: caugh error %#v while exporting container, expected nil", err.Error())
+-		t.Fatal(err)
 -	}
--	if out.String() != content {
--		t.Errorf("ExportContainer: wrong stdout. Want %#v. Got %#v.", content, out.String())
+-	defer servers.Delete(client, server.ID)
+-
+-	if err = waitForStatus(client, server, "ACTIVE"); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	randomPassword := tools.MakeNewPassword(server.AdminPass)
+-	res := servers.ChangeAdminPassword(client, server.ID, randomPassword)
+-	if res.Err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	if err = waitForStatus(client, server, "PASSWORD"); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	if err = waitForStatus(client, server, "ACTIVE"); err != nil {
+-		t.Fatal(err)
 -	}
 -}
 -
--func runStreamConnServer(t *testing.T, network, laddr string, listening chan<- string, done chan<- int) {
--	defer close(done)
--	l, err := net.Listen(network, laddr)
+-func TestActionReboot(t *testing.T) {
+-	t.Parallel()
+-
+-	client, err := newClient()
 -	if err != nil {
--		t.Errorf("Listen(%q, %q) failed: %v", network, laddr, err)
--		listening <- "<nil>"
--		return
+-		t.Fatalf("Unable to create a compute client: %v", err)
 -	}
--	defer l.Close()
--	listening <- l.Addr().String()
--	c, err := l.Accept()
+-
+-	choices, err := ComputeChoicesFromEnv()
 -	if err != nil {
--		t.Logf("Accept failed: %v", err)
--		return
+-		t.Fatal(err)
 -	}
--	c.Write([]byte("HTTP/1.1 200 OK\n\nexported container tar content"))
--	c.Close()
--}
 -
--func tempfile(filename string) string {
--	return os.TempDir() + "/" + filename + "." + strconv.Itoa(os.Getpid())
--}
+-	server, err := createServer(t, client, choices)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	defer servers.Delete(client, server.ID)
 -
--func TestExportContainerNoId(t *testing.T) {
--	client := Client{}
--	out := stdoutMock{bytes.NewBufferString("")}
--	err := client.ExportContainer(ExportContainerOptions{OutputStream: out})
--	e, ok := err.(*NoSuchContainer)
--	if !ok {
--		t.Errorf("ExportContainer: wrong error. Want NoSuchContainer. Got %#v.", e)
+-	if err = waitForStatus(client, server, "ACTIVE"); err != nil {
+-		t.Fatal(err)
 -	}
--	if e.ID != "" {
--		t.Errorf("ExportContainer: wrong ID. Want %q. Got %q", "", e.ID)
+-
+-	res := servers.Reboot(client, server.ID, "aldhjflaskhjf")
+-	if res.Err == nil {
+-		t.Fatal("Expected the SDK to provide an ArgumentError here")
 -	}
--}
 -
--func TestCopyFromContainer(t *testing.T) {
--	content := "File content"
--	out := stdoutMock{bytes.NewBufferString(content)}
--	client := newTestClient(&FakeRoundTripper{status: http.StatusOK})
--	opts := CopyFromContainerOptions{
--		Container:    "a123456",
--		OutputStream: out,
+-	t.Logf("Attempting reboot of server %s", server.ID)
+-	res = servers.Reboot(client, server.ID, servers.OSReboot)
+-	if res.Err != nil {
+-		t.Fatalf("Unable to reboot server: %v", err)
 -	}
--	err := client.CopyFromContainer(opts)
--	if err != nil {
--		t.Errorf("CopyFromContainer: caugh error %#v while copying from container, expected nil", err.Error())
+-
+-	if err = waitForStatus(client, server, "REBOOT"); err != nil {
+-		t.Fatal(err)
 -	}
--	if out.String() != content {
--		t.Errorf("CopyFromContainer: wrong stdout. Want %#v. Got %#v.", content, out.String())
+-
+-	if err = waitForStatus(client, server, "ACTIVE"); err != nil {
+-		t.Fatal(err)
 -	}
 -}
 -
--func TestCopyFromContainerEmptyContainer(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{status: http.StatusOK})
--	err := client.CopyFromContainer(CopyFromContainerOptions{})
--	_, ok := err.(*NoSuchContainer)
--	if !ok {
--		t.Errorf("CopyFromContainer: invalid error returned. Want NoSuchContainer, got %#v.", err)
+-func TestActionRebuild(t *testing.T) {
+-	t.Parallel()
+-
+-	client, err := newClient()
+-	if err != nil {
+-		t.Fatalf("Unable to create a compute client: %v", err)
 -	}
--}
 -
--func TestPassingNameOptToCreateContainerReturnsItInContainer(t *testing.T) {
--	jsonContainer := `{
--             "Id": "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2",
--	     "Warnings": []
--}`
--	fakeRT := &FakeRoundTripper{message: jsonContainer, status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	config := Config{AttachStdout: true, AttachStdin: true}
--	opts := CreateContainerOptions{Name: "TestCreateContainer", Config: &config}
--	container, err := client.CreateContainer(opts)
+-	choices, err := ComputeChoicesFromEnv()
 -	if err != nil {
 -		t.Fatal(err)
 -	}
--	if container.Name != "TestCreateContainer" {
--		t.Errorf("Container name expected to be TestCreateContainer, was %s", container.Name)
+-
+-	server, err := createServer(t, client, choices)
+-	if err != nil {
+-		t.Fatal(err)
 -	}
--}
+-	defer servers.Delete(client, server.ID)
 -
--func TestAlwaysRestart(t *testing.T) {
--	policy := AlwaysRestart()
--	if policy.Name != "always" {
--		t.Errorf("AlwaysRestart(): wrong policy name. Want %q. Got %q", "always", policy.Name)
+-	if err = waitForStatus(client, server, "ACTIVE"); err != nil {
+-		t.Fatal(err)
 -	}
--	if policy.MaximumRetryCount != 0 {
--		t.Errorf("AlwaysRestart(): wrong MaximumRetryCount. Want 0. Got %d", policy.MaximumRetryCount)
+-
+-	t.Logf("Attempting to rebuild server %s", server.ID)
+-
+-	rebuildOpts := servers.RebuildOpts{
+-		Name:      tools.RandomString("ACPTTEST", 16),
+-		AdminPass: tools.MakeNewPassword(server.AdminPass),
+-		ImageID:   choices.ImageID,
 -	}
--}
 -
--func TestRestartOnFailure(t *testing.T) {
--	const retry = 5
--	policy := RestartOnFailure(retry)
--	if policy.Name != "on-failure" {
--		t.Errorf("RestartOnFailure(%d): wrong policy name. Want %q. Got %q", retry, "on-failure", policy.Name)
+-	rebuilt, err := servers.Rebuild(client, server.ID, rebuildOpts).Extract()
+-	if err != nil {
+-		t.Fatal(err)
 -	}
--	if policy.MaximumRetryCount != retry {
--		t.Errorf("RestartOnFailure(%d): wrong MaximumRetryCount. Want %d. Got %d", retry, retry, policy.MaximumRetryCount)
+-
+-	if rebuilt.ID != server.ID {
+-		t.Errorf("Expected rebuilt server ID of [%s]; got [%s]", server.ID, rebuilt.ID)
+-	}
+-
+-	if err = waitForStatus(client, rebuilt, "REBUILD"); err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	if err = waitForStatus(client, rebuilt, "ACTIVE"); err != nil {
+-		t.Fatal(err)
 -	}
 -}
 -
--func TestNeverRestart(t *testing.T) {
--	policy := NeverRestart()
--	if policy.Name != "no" {
--		t.Errorf("NeverRestart(): wrong policy name. Want %q. Got %q", "always", policy.Name)
+-func resizeServer(t *testing.T, client *gophercloud.ServiceClient, server *servers.Server, choices *ComputeChoices) {
+-	if err := waitForStatus(client, server, "ACTIVE"); err != nil {
+-		t.Fatal(err)
 -	}
--	if policy.MaximumRetryCount != 0 {
--		t.Errorf("NeverRestart(): wrong MaximumRetryCount. Want 0. Got %d", policy.MaximumRetryCount)
+-
+-	t.Logf("Attempting to resize server [%s]", server.ID)
+-
+-	opts := &servers.ResizeOpts{
+-		FlavorRef: choices.FlavorIDResize,
+-	}
+-	if res := servers.Resize(client, server.ID, opts); res.Err != nil {
+-		t.Fatal(res.Err)
+-	}
+-
+-	if err := waitForStatus(client, server, "VERIFY_RESIZE"); err != nil {
+-		t.Fatal(err)
 -	}
 -}
 -
--func TestTopContainer(t *testing.T) {
--	jsonTop := `{
--  "Processes": [
--    [
--      "ubuntu",
--      "3087",
--      "815",
--      "0",
--      "01:44",
--      "?",
--      "00:00:00",
--      "cmd1"
--    ],
--    [
--      "root",
--      "3158",
--      "3087",
--      "0",
--      "01:44",
--      "?",
--      "00:00:01",
--      "cmd2"
--    ]
--  ],
--  "Titles": [
--    "UID",
--    "PID",
--    "PPID",
--    "C",
--    "STIME",
--    "TTY",
--    "TIME",
--    "CMD"
--  ]
--}`
--	var expected TopResult
--	err := json.Unmarshal([]byte(jsonTop), &expected)
+-func TestActionResizeConfirm(t *testing.T) {
+-	t.Parallel()
+-
+-	choices, err := ComputeChoicesFromEnv()
 -	if err != nil {
 -		t.Fatal(err)
 -	}
--	id := "4fa6e0f0"
--	fakeRT := &FakeRoundTripper{message: jsonTop, status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	processes, err := client.TopContainer(id, "")
+-
+-	client, err := newClient()
 -	if err != nil {
--		t.Fatal(err)
+-		t.Fatalf("Unable to create a compute client: %v", err)
 -	}
--	if !reflect.DeepEqual(processes, expected) {
--		t.Errorf("TopContainer: Expected %#v. Got %#v.", expected, processes)
+-
+-	server, err := createServer(t, client, choices)
+-	if err != nil {
+-		t.Fatal(err)
 -	}
--	if len(processes.Processes) != 2 || len(processes.Processes[0]) != 8 ||
--		processes.Processes[0][7] != "cmd1" {
--		t.Errorf("TopContainer: Process list to include cmd1. Got %#v.", expected, processes)
+-	defer servers.Delete(client, server.ID)
+-	resizeServer(t, client, server, choices)
+-
+-	t.Logf("Attempting to confirm resize for server %s", server.ID)
+-
+-	if res := servers.ConfirmResize(client, server.ID); res.Err != nil {
+-		t.Fatal(err)
 -	}
--	expectedURI := "/containers/" + id + "/top"
--	if !strings.HasSuffix(fakeRT.requests[0].URL.String(), expectedURI) {
--		t.Errorf("TopContainer: Expected URI to have %q. Got %q.", expectedURI, fakeRT.requests[0].URL.String())
+-
+-	if err = waitForStatus(client, server, "ACTIVE"); err != nil {
+-		t.Fatal(err)
 -	}
 -}
 -
--func TestTopContainerNotFound(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "no such container", status: http.StatusNotFound})
--	_, err := client.TopContainer("abef348", "")
--	expected := &NoSuchContainer{ID: "abef348"}
--	if !reflect.DeepEqual(err, expected) {
--		t.Errorf("StopContainer: Wrong error returned. Want %#v. Got %#v.", expected, err)
+-func TestActionResizeRevert(t *testing.T) {
+-	t.Parallel()
+-
+-	choices, err := ComputeChoicesFromEnv()
+-	if err != nil {
+-		t.Fatal(err)
 -	}
--}
 -
--func TestTopContainerWithPsArgs(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "no such container", status: http.StatusNotFound}
--	client := newTestClient(fakeRT)
--	client.TopContainer("abef348", "aux")
--	expectedURI := "/containers/abef348/top?ps_args=aux"
--	if !strings.HasSuffix(fakeRT.requests[0].URL.String(), expectedURI) {
--		t.Errorf("TopContainer: Expected URI to have %q. Got %q.", expectedURI, fakeRT.requests[0].URL.String())
+-	client, err := newClient()
+-	if err != nil {
+-		t.Fatalf("Unable to create a compute client: %v", err)
+-	}
+-
+-	server, err := createServer(t, client, choices)
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	defer servers.Delete(client, server.ID)
+-	resizeServer(t, client, server, choices)
+-
+-	t.Logf("Attempting to revert resize for server %s", server.ID)
+-
+-	if res := servers.RevertResize(client, server.ID); res.Err != nil {
+-		t.Fatal(err)
+-	}
+-
+-	if err = waitForStatus(client, server, "ACTIVE"); err != nil {
+-		t.Fatal(err)
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/env.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/env.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/extension_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/extension_test.go
 deleted file mode 100644
-index c54b0b0..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/env.go
+index 2b4e062..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/extension_test.go
 +++ /dev/null
-@@ -1,168 +0,0 @@
--// Copyright 2014 Docker authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the DOCKER-LICENSE file.
+@@ -1,46 +0,0 @@
+-// +build acceptance
 -
--package docker
+-package v2
 -
 -import (
--	"encoding/json"
--	"fmt"
--	"io"
--	"strconv"
--	"strings"
+-	"testing"
+-
+-	extensions2 "github.com/rackspace/gophercloud/openstack/identity/v2/extensions"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--// Env represents a list of key-pair represented in the form KEY=VALUE.
--type Env []string
+-func TestEnumerateExtensions(t *testing.T) {
+-	service := authenticatedClient(t)
 -
--// Get returns the string value of the given key.
--func (env *Env) Get(key string) (value string) {
--	return env.Map()[key]
+-	t.Logf("Extensions available on this identity endpoint:")
+-	count := 0
+-	err := extensions2.List(service).EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page %02d ---", count)
+-
+-		extensions, err := extensions2.ExtractExtensions(page)
+-		th.AssertNoErr(t, err)
+-
+-		for i, ext := range extensions {
+-			t.Logf("[%02d] name=[%s] namespace=[%s]", i, ext.Name, ext.Namespace)
+-			t.Logf("     alias=[%s] updated=[%s]", ext.Alias, ext.Updated)
+-			t.Logf("     description=[%s]", ext.Description)
+-		}
+-
+-		count++
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
 -}
 -
--// Exists checks whether the given key is defined in the internal Env
--// representation.
--func (env *Env) Exists(key string) bool {
--	_, exists := env.Map()[key]
--	return exists
+-func TestGetExtension(t *testing.T) {
+-	service := authenticatedClient(t)
+-
+-	ext, err := extensions2.Get(service, "OS-KSCRUD").Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.CheckEquals(t, "OpenStack Keystone User CRUD", ext.Name)
+-	th.CheckEquals(t, "http://docs.openstack.org/identity/api/ext/OS-KSCRUD/v1.0", ext.Namespace)
+-	th.CheckEquals(t, "OS-KSCRUD", ext.Alias)
+-	th.CheckEquals(t, "OpenStack extensions to Keystone v2.0 API enabling User Operations.", ext.Description)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/identity_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/identity_test.go
+deleted file mode 100644
+index feae233..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/identity_test.go
++++ /dev/null
+@@ -1,47 +0,0 @@
+-// +build acceptance
 -
--// GetBool returns a boolean representation of the given key. The key is false
--// whenever its value if 0, no, false, none or an empty string. Any other value
--// will be interpreted as true.
--func (env *Env) GetBool(key string) (value bool) {
--	s := strings.ToLower(strings.Trim(env.Get(key), " \t"))
--	if s == "" || s == "0" || s == "no" || s == "false" || s == "none" {
--		return false
+-package v2
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/openstack"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func v2AuthOptions(t *testing.T) gophercloud.AuthOptions {
+-	// Obtain credentials from the environment.
+-	ao, err := openstack.AuthOptionsFromEnv()
+-	th.AssertNoErr(t, err)
+-
+-	// Trim out unused fields. Prefer authentication by API key to password.
+-	ao.UserID, ao.DomainID, ao.DomainName = "", "", ""
+-	if ao.APIKey != "" {
+-		ao.Password = ""
 -	}
--	return true
+-
+-	return ao
 -}
 -
--// SetBool defines a boolean value to the given key.
--func (env *Env) SetBool(key string, value bool) {
--	if value {
--		env.Set(key, "1")
--	} else {
--		env.Set(key, "0")
+-func createClient(t *testing.T, auth bool) *gophercloud.ServiceClient {
+-	ao := v2AuthOptions(t)
+-
+-	provider, err := openstack.NewClient(ao.IdentityEndpoint)
+-	th.AssertNoErr(t, err)
+-
+-	if auth {
+-		err = openstack.AuthenticateV2(provider, ao)
+-		th.AssertNoErr(t, err)
 -	}
--}
 -
--// GetInt returns the value of the provided key, converted to int.
--//
--// It the value cannot be represented as an integer, it returns -1.
--func (env *Env) GetInt(key string) int {
--	return int(env.GetInt64(key))
+-	return openstack.NewIdentityV2(provider)
 -}
 -
--// SetInt defines an integer value to the given key.
--func (env *Env) SetInt(key string, value int) {
--	env.Set(key, strconv.Itoa(value))
+-func unauthenticatedClient(t *testing.T) *gophercloud.ServiceClient {
+-	return createClient(t, false)
 -}
 -
--// GetInt64 returns the value of the provided key, converted to int64.
--//
--// It the value cannot be represented as an integer, it returns -1.
--func (env *Env) GetInt64(key string) int64 {
--	s := strings.Trim(env.Get(key), " \t")
--	val, err := strconv.ParseInt(s, 10, 64)
--	if err != nil {
--		return -1
--	}
--	return val
+-func authenticatedClient(t *testing.T) *gophercloud.ServiceClient {
+-	return createClient(t, true)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/pkg.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/pkg.go
+deleted file mode 100644
+index 5ec3cc8..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/pkg.go
++++ /dev/null
+@@ -1 +0,0 @@
+-package v2
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/tenant_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/tenant_test.go
+deleted file mode 100644
+index 2054598..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/tenant_test.go
++++ /dev/null
+@@ -1,32 +0,0 @@
+-// +build acceptance
 -
--// SetInt64 defines an integer (64-bit wide) value to the given key.
--func (env *Env) SetInt64(key string, value int64) {
--	env.Set(key, strconv.FormatInt(value, 10))
+-package v2
+-
+-import (
+-	"testing"
+-
+-	tenants2 "github.com/rackspace/gophercloud/openstack/identity/v2/tenants"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestEnumerateTenants(t *testing.T) {
+-	service := authenticatedClient(t)
+-
+-	t.Logf("Tenants to which your current token grants access:")
+-	count := 0
+-	err := tenants2.List(service, nil).EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page %02d ---", count)
+-
+-		tenants, err := tenants2.ExtractTenants(page)
+-		th.AssertNoErr(t, err)
+-		for i, tenant := range tenants {
+-			t.Logf("[%02d] name=[%s] id=[%s] description=[%s] enabled=[%v]",
+-				i, tenant.Name, tenant.ID, tenant.Description, tenant.Enabled)
+-		}
+-
+-		count++
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/token_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/token_test.go
+deleted file mode 100644
+index 0632a48..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v2/token_test.go
++++ /dev/null
+@@ -1,38 +0,0 @@
+-// +build acceptance
 -
--// GetJSON unmarshals the value of the provided key in the provided iface.
--//
--// iface is a value that can be provided to the json.Unmarshal function.
--func (env *Env) GetJSON(key string, iface interface{}) error {
--	sval := env.Get(key)
--	if sval == "" {
--		return nil
+-package v2
+-
+-import (
+-	"testing"
+-
+-	tokens2 "github.com/rackspace/gophercloud/openstack/identity/v2/tokens"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestAuthenticate(t *testing.T) {
+-	ao := v2AuthOptions(t)
+-	service := unauthenticatedClient(t)
+-
+-	// Authenticated!
+-	result := tokens2.Create(service, tokens2.WrapOptions(ao))
+-
+-	// Extract and print the token.
+-	token, err := result.ExtractToken()
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Acquired token: [%s]", token.ID)
+-	t.Logf("The token will expire at: [%s]", token.ExpiresAt.String())
+-	t.Logf("The token is valid for tenant: [%#v]", token.Tenant)
+-
+-	// Extract and print the service catalog.
+-	catalog, err := result.ExtractServiceCatalog()
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Acquired service catalog listing [%d] services", len(catalog.Entries))
+-	for i, entry := range catalog.Entries {
+-		t.Logf("[%02d]: name=[%s], type=[%s]", i, entry.Name, entry.Type)
+-		for _, endpoint := range entry.Endpoints {
+-			t.Logf("      - region=[%s] publicURL=[%s]", endpoint.Region, endpoint.PublicURL)
+-		}
 -	}
--	return json.Unmarshal([]byte(sval), iface)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/endpoint_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/endpoint_test.go
+deleted file mode 100644
+index ea893c2..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/endpoint_test.go
++++ /dev/null
+@@ -1,111 +0,0 @@
+-// +build acceptance
 -
--// SetJSON marshals the given value to JSON format and stores it using the
--// provided key.
--func (env *Env) SetJSON(key string, value interface{}) error {
--	sval, err := json.Marshal(value)
+-package v3
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	endpoints3 "github.com/rackspace/gophercloud/openstack/identity/v3/endpoints"
+-	services3 "github.com/rackspace/gophercloud/openstack/identity/v3/services"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
+-
+-func TestListEndpoints(t *testing.T) {
+-	// Create a service client.
+-	serviceClient := createAuthenticatedClient(t)
+-	if serviceClient == nil {
+-		return
+-	}
+-
+-	// Use the service to list all available endpoints.
+-	pager := endpoints3.List(serviceClient, endpoints3.ListOpts{})
+-	err := pager.EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page ---")
+-
+-		endpoints, err := endpoints3.ExtractEndpoints(page)
+-		if err != nil {
+-			t.Fatalf("Error extracting endpoings: %v", err)
+-		}
+-
+-		for _, endpoint := range endpoints {
+-			t.Logf("Endpoint: %8s %10s %9s %s",
+-				endpoint.ID,
+-				endpoint.Availability,
+-				endpoint.Name,
+-				endpoint.URL)
+-		}
+-
+-		return true, nil
+-	})
 -	if err != nil {
--		return err
+-		t.Errorf("Unexpected error while iterating endpoint pages: %v", err)
 -	}
--	env.Set(key, string(sval))
--	return nil
 -}
 -
--// GetList returns a list of strings matching the provided key. It handles the
--// list as a JSON representation of a list of strings.
--//
--// If the given key matches to a single string, it will return a list
--// containing only the value that matches the key.
--func (env *Env) GetList(key string) []string {
--	sval := env.Get(key)
--	if sval == "" {
--		return nil
--	}
--	var l []string
--	if err := json.Unmarshal([]byte(sval), &l); err != nil {
--		l = append(l, sval)
+-func TestNavigateCatalog(t *testing.T) {
+-	// Create a service client.
+-	client := createAuthenticatedClient(t)
+-	if client == nil {
+-		return
 -	}
--	return l
--}
 -
--// SetList stores the given list in the provided key, after serializing it to
--// JSON format.
--func (env *Env) SetList(key string, value []string) error {
--	return env.SetJSON(key, value)
--}
+-	var compute *services3.Service
+-	var endpoint *endpoints3.Endpoint
 -
--// Set defines the value of a key to the given string.
--func (env *Env) Set(key, value string) {
--	*env = append(*env, key+"="+value)
--}
+-	// Discover the service we're interested in.
+-	servicePager := services3.List(client, services3.ListOpts{ServiceType: "compute"})
+-	err := servicePager.EachPage(func(page pagination.Page) (bool, error) {
+-		part, err := services3.ExtractServices(page)
+-		if err != nil {
+-			return false, err
+-		}
+-		if compute != nil {
+-			t.Fatalf("Expected one service, got more than one page")
+-			return false, nil
+-		}
+-		if len(part) != 1 {
+-			t.Fatalf("Expected one service, got %d", len(part))
+-			return false, nil
+-		}
 -
--// Decode decodes `src` as a json dictionary, and adds each decoded key-value
--// pair to the environment.
--//
--// If `src` cannot be decoded as a json dictionary, an error is returned.
--func (env *Env) Decode(src io.Reader) error {
--	m := make(map[string]interface{})
--	if err := json.NewDecoder(src).Decode(&m); err != nil {
--		return err
+-		compute = &part[0]
+-		return true, nil
+-	})
+-	if err != nil {
+-		t.Fatalf("Unexpected error iterating pages: %v", err)
 -	}
--	for k, v := range m {
--		env.SetAuto(k, v)
+-
+-	if compute == nil {
+-		t.Fatalf("No compute service found.")
 -	}
--	return nil
--}
 -
--// SetAuto will try to define the Set* method to call based on the given value.
--func (env *Env) SetAuto(key string, value interface{}) {
--	if fval, ok := value.(float64); ok {
--		env.SetInt64(key, int64(fval))
--	} else if sval, ok := value.(string); ok {
--		env.Set(key, sval)
--	} else if val, err := json.Marshal(value); err == nil {
--		env.Set(key, string(val))
--	} else {
--		env.Set(key, fmt.Sprintf("%v", value))
+-	// Enumerate the endpoints available for this service.
+-	computePager := endpoints3.List(client, endpoints3.ListOpts{
+-		Availability: gophercloud.AvailabilityPublic,
+-		ServiceID:    compute.ID,
+-	})
+-	err = computePager.EachPage(func(page pagination.Page) (bool, error) {
+-		part, err := endpoints3.ExtractEndpoints(page)
+-		if err != nil {
+-			return false, err
+-		}
+-		if endpoint != nil {
+-			t.Fatalf("Expected one endpoint, got more than one page")
+-			return false, nil
+-		}
+-		if len(part) != 1 {
+-			t.Fatalf("Expected one endpoint, got %d", len(part))
+-			return false, nil
+-		}
+-
+-		endpoint = &part[0]
+-		return true, nil
+-	})
+-
+-	if endpoint == nil {
+-		t.Fatalf("No endpoint found.")
 -	}
+-
+-	t.Logf("Success. The compute endpoint is at %s.", endpoint.URL)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/identity_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/identity_test.go
+deleted file mode 100644
+index ce64345..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/identity_test.go
++++ /dev/null
+@@ -1,39 +0,0 @@
+-// +build acceptance
 -
--// Map returns the map representation of the env.
--func (env *Env) Map() map[string]string {
--	if len(*env) == 0 {
+-package v3
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/openstack"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func createAuthenticatedClient(t *testing.T) *gophercloud.ServiceClient {
+-	// Obtain credentials from the environment.
+-	ao, err := openstack.AuthOptionsFromEnv()
+-	th.AssertNoErr(t, err)
+-
+-	// Trim out unused fields.
+-	ao.Username, ao.TenantID, ao.TenantName = "", "", ""
+-
+-	if ao.UserID == "" {
+-		t.Logf("Skipping identity v3 tests because no OS_USERID is present.")
 -		return nil
 -	}
--	m := make(map[string]string)
--	for _, kv := range *env {
--		parts := strings.SplitN(kv, "=", 2)
--		m[parts[0]] = parts[1]
+-
+-	// Create a client and manually authenticate against v3.
+-	providerClient, err := openstack.NewClient(ao.IdentityEndpoint)
+-	if err != nil {
+-		t.Fatalf("Unable to instantiate client: %v", err)
 -	}
--	return m
+-
+-	err = openstack.AuthenticateV3(providerClient, ao)
+-	if err != nil {
+-		t.Fatalf("Unable to authenticate against identity v3: %v", err)
+-	}
+-
+-	// Create a service client.
+-	return openstack.NewIdentityV3(providerClient)
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/env_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/env_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/pkg.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/pkg.go
 deleted file mode 100644
-index 6d03d7b..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/env_test.go
+index eac3ae9..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/pkg.go
 +++ /dev/null
-@@ -1,349 +0,0 @@
--// Copyright 2014 go-dockerclient authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the DOCKER-LICENSE file.
+@@ -1 +0,0 @@
+-package v3
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/service_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/service_test.go
+deleted file mode 100644
+index 082bd11..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/service_test.go
++++ /dev/null
+@@ -1,36 +0,0 @@
+-// +build acceptance
 -
--package docker
+-package v3
 -
 -import (
--	"bytes"
--	"errors"
--	"reflect"
--	"sort"
 -	"testing"
+-
+-	services3 "github.com/rackspace/gophercloud/openstack/identity/v3/services"
+-	"github.com/rackspace/gophercloud/pagination"
 -)
 -
--func TestGet(t *testing.T) {
--	var tests = []struct {
--		input    []string
--		query    string
--		expected string
--	}{
--		{[]string{"PATH=/usr/bin:/bin", "PYTHONPATH=/usr/local"}, "PATH", "/usr/bin:/bin"},
--		{[]string{"PATH=/usr/bin:/bin", "PYTHONPATH=/usr/local"}, "PYTHONPATH", "/usr/local"},
--		{[]string{"PATH=/usr/bin:/bin", "PYTHONPATH=/usr/local"}, "PYTHONPATHI", ""},
--		{[]string{"WAT="}, "WAT", ""},
+-func TestListServices(t *testing.T) {
+-	// Create a service client.
+-	serviceClient := createAuthenticatedClient(t)
+-	if serviceClient == nil {
+-		return
 -	}
--	for _, tt := range tests {
--		env := Env(tt.input)
--		got := env.Get(tt.query)
--		if got != tt.expected {
--			t.Errorf("Env.Get(%q): wrong result. Want %q. Got %q", tt.query, tt.expected, got)
+-
+-	// Use the client to list all available services.
+-	pager := services3.List(serviceClient, services3.ListOpts{})
+-	err := pager.EachPage(func(page pagination.Page) (bool, error) {
+-		parts, err := services3.ExtractServices(page)
+-		if err != nil {
+-			return false, err
 -		}
--	}
--}
 -
--func TestExists(t *testing.T) {
--	var tests = []struct {
--		input    []string
--		query    string
--		expected bool
--	}{
--		{[]string{"WAT=", "PYTHONPATH=/usr/local"}, "WAT", true},
--		{[]string{"PATH=/usr/bin:/bin", "PYTHONPATH=/usr/local"}, "PYTHONPATH", true},
--		{[]string{"PATH=/usr/bin:/bin", "PYTHONPATH=/usr/local"}, "PYTHONPATHI", false},
--	}
--	for _, tt := range tests {
--		env := Env(tt.input)
--		got := env.Exists(tt.query)
--		if got != tt.expected {
--			t.Errorf("Env.Exists(%q): wrong result. Want %v. Got %v", tt.query, tt.expected, got)
+-		t.Logf("--- Page ---")
+-		for _, service := range parts {
+-			t.Logf("Service: %32s %15s %10s %s", service.ID, service.Type, service.Name, *service.Description)
 -		}
+-		return true, nil
+-	})
+-	if err != nil {
+-		t.Errorf("Unexpected error traversing pages: %v", err)
 -	}
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/token_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/token_test.go
+deleted file mode 100644
+index 4342ade..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/identity/v3/token_test.go
++++ /dev/null
+@@ -1,42 +0,0 @@
+-// +build acceptance
 -
--func TestGetBool(t *testing.T) {
--	var tests = []struct {
--		input    string
--		expected bool
--	}{
--		{"EMTPY_VAR", false}, {"ZERO_VAR", false}, {"NO_VAR", false},
--		{"FALSE_VAR", false}, {"NONE_VAR", false}, {"TRUE_VAR", true},
--		{"WAT", true}, {"PATH", true}, {"ONE_VAR", true}, {"NO_VAR_TAB", false},
+-package v3
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/openstack"
+-	tokens3 "github.com/rackspace/gophercloud/openstack/identity/v3/tokens"
+-)
+-
+-func TestGetToken(t *testing.T) {
+-	// Obtain credentials from the environment.
+-	ao, err := openstack.AuthOptionsFromEnv()
+-	if err != nil {
+-		t.Fatalf("Unable to acquire credentials: %v", err)
 -	}
--	env := Env([]string{
--		"EMPTY_VAR=", "ZERO_VAR=0", "NO_VAR=no", "FALSE_VAR=false",
--		"NONE_VAR=none", "TRUE_VAR=true", "WAT=wat", "PATH=/usr/bin:/bin",
--		"ONE_VAR=1", "NO_VAR_TAB=0 \t\t\t",
--	})
--	for _, tt := range tests {
--		got := env.GetBool(tt.input)
--		if got != tt.expected {
--			t.Errorf("Env.GetBool(%q): wrong result. Want %v. Got %v.", tt.input, tt.expected, got)
--		}
+-
+-	// Trim out unused fields. Skip if we don't have a UserID.
+-	ao.Username, ao.TenantID, ao.TenantName = "", "", ""
+-	if ao.UserID == "" {
+-		t.Logf("Skipping identity v3 tests because no OS_USERID is present.")
+-		return
 -	}
--}
 -
--func TestSetBool(t *testing.T) {
--	var tests = []struct {
--		input    bool
--		expected string
--	}{
--		{true, "1"}, {false, "0"},
+-	// Create an unauthenticated client.
+-	provider, err := openstack.NewClient(ao.IdentityEndpoint)
+-	if err != nil {
+-		t.Fatalf("Unable to instantiate client: %v", err)
 -	}
--	for _, tt := range tests {
--		var env Env
--		env.SetBool("SOME", tt.input)
--		if got := env.Get("SOME"); got != tt.expected {
--			t.Errorf("Env.SetBool(%v): wrong result. Want %q. Got %q", tt.input, tt.expected, got)
--		}
+-
+-	// Create a service client.
+-	service := openstack.NewIdentityV3(provider)
+-
+-	// Use the service to create a token.
+-	token, err := tokens3.Create(service, ao, nil).Extract()
+-	if err != nil {
+-		t.Fatalf("Unable to get token: %v", err)
 -	}
+-
+-	t.Logf("Acquired token: %s", token.ID)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/apiversion_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/apiversion_test.go
+deleted file mode 100644
+index 99e1d01..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/apiversion_test.go
++++ /dev/null
+@@ -1,51 +0,0 @@
+-// +build acceptance networking
 -
--func TestGetInt(t *testing.T) {
--	var tests = []struct {
--		input    string
--		expected int
--	}{
--		{"NEGATIVE_INTEGER", -10}, {"NON_INTEGER", -1}, {"ONE", 1}, {"TWO", 2},
--	}
--	env := Env([]string{"NEGATIVE_INTEGER=-10", "NON_INTEGER=wat", "ONE=1", "TWO=2"})
--	for _, tt := range tests {
--		got := env.GetInt(tt.input)
--		if got != tt.expected {
--			t.Errorf("Env.GetInt(%q): wrong result. Want %d. Got %d", tt.input, tt.expected, got)
+-package v2
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/apiversions"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestListAPIVersions(t *testing.T) {
+-	Setup(t)
+-	defer Teardown()
+-
+-	pager := apiversions.ListVersions(Client)
+-	err := pager.EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page ---")
+-
+-		versions, err := apiversions.ExtractAPIVersions(page)
+-		th.AssertNoErr(t, err)
+-
+-		for _, v := range versions {
+-			t.Logf("API Version: ID [%s] Status [%s]", v.ID, v.Status)
 -		}
--	}
+-
+-		return true, nil
+-	})
+-	th.CheckNoErr(t, err)
 -}
 -
--func TestSetInt(t *testing.T) {
--	var tests = []struct {
--		input    int
--		expected string
--	}{
--		{10, "10"}, {13, "13"}, {7, "7"}, {33, "33"},
--		{0, "0"}, {-34, "-34"},
--	}
--	for _, tt := range tests {
--		var env Env
--		env.SetInt("SOME", tt.input)
--		if got := env.Get("SOME"); got != tt.expected {
--			t.Errorf("Env.SetBool(%d): wrong result. Want %q. Got %q", tt.input, tt.expected, got)
+-func TestListAPIResources(t *testing.T) {
+-	Setup(t)
+-	defer Teardown()
+-
+-	pager := apiversions.ListVersionResources(Client, "v2.0")
+-	err := pager.EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page ---")
+-
+-		vrs, err := apiversions.ExtractVersionResources(page)
+-		th.AssertNoErr(t, err)
+-
+-		for _, vr := range vrs {
+-			t.Logf("Network: Name [%s] Collection [%s]", vr.Name, vr.Collection)
 -		}
--	}
+-
+-		return true, nil
+-	})
+-	th.CheckNoErr(t, err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/common.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/common.go
+deleted file mode 100644
+index 1efac2c..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/common.go
++++ /dev/null
+@@ -1,39 +0,0 @@
+-package v2
 -
--func TestGetInt64(t *testing.T) {
--	var tests = []struct {
--		input    string
--		expected int64
--	}{
--		{"NEGATIVE_INTEGER", -10}, {"NON_INTEGER", -1}, {"ONE", 1}, {"TWO", 2},
+-import (
+-	"os"
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/openstack"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-var Client *gophercloud.ServiceClient
+-
+-func NewClient() (*gophercloud.ServiceClient, error) {
+-	opts, err := openstack.AuthOptionsFromEnv()
+-	if err != nil {
+-		return nil, err
 -	}
--	env := Env([]string{"NEGATIVE_INTEGER=-10", "NON_INTEGER=wat", "ONE=1", "TWO=2"})
--	for _, tt := range tests {
--		got := env.GetInt64(tt.input)
--		if got != tt.expected {
--			t.Errorf("Env.GetInt64(%q): wrong result. Want %d. Got %d", tt.input, tt.expected, got)
--		}
+-
+-	provider, err := openstack.AuthenticatedClient(opts)
+-	if err != nil {
+-		return nil, err
 -	}
+-
+-	return openstack.NewNetworkV2(provider, gophercloud.EndpointOpts{
+-		Name:   "neutron",
+-		Region: os.Getenv("OS_REGION_NAME"),
+-	})
 -}
 -
--func TestSetInt64(t *testing.T) {
--	var tests = []struct {
--		input    int64
--		expected string
--	}{
--		{10, "10"}, {13, "13"}, {7, "7"}, {33, "33"},
--		{0, "0"}, {-34, "-34"},
--	}
--	for _, tt := range tests {
--		var env Env
--		env.SetInt64("SOME", tt.input)
--		if got := env.Get("SOME"); got != tt.expected {
--			t.Errorf("Env.SetBool(%d): wrong result. Want %q. Got %q", tt.input, tt.expected, got)
+-func Setup(t *testing.T) {
+-	client, err := NewClient()
+-	th.AssertNoErr(t, err)
+-	Client = client
+-}
+-
+-func Teardown() {
+-	Client = nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extension_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extension_test.go
+deleted file mode 100644
+index edcbba4..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extension_test.go
++++ /dev/null
+@@ -1,45 +0,0 @@
+-// +build acceptance networking
+-
+-package v2
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/extensions"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestListExts(t *testing.T) {
+-	Setup(t)
+-	defer Teardown()
+-
+-	pager := extensions.List(Client)
+-	err := pager.EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page ---")
+-
+-		exts, err := extensions.ExtractExtensions(page)
+-		th.AssertNoErr(t, err)
+-
+-		for _, ext := range exts {
+-			t.Logf("Extension: Name [%s] Description [%s]", ext.Name, ext.Description)
 -		}
--	}
+-
+-		return true, nil
+-	})
+-	th.CheckNoErr(t, err)
 -}
 -
--func TestGetJSON(t *testing.T) {
--	var p struct {
--		Name string `json:"name"`
--		Age  int    `json:"age"`
--	}
--	var env Env
--	env.Set("person", `{"name":"Gopher","age":5}`)
--	err := env.GetJSON("person", &p)
--	if err != nil {
--		t.Error(err)
--	}
--	if p.Name != "Gopher" {
--		t.Errorf("Env.GetJSON(%q): wrong name. Want %q. Got %q", "person", "Gopher", p.Name)
--	}
--	if p.Age != 5 {
--		t.Errorf("Env.GetJSON(%q): wrong age. Want %d. Got %d", "person", 5, p.Age)
--	}
+-func TestGetExt(t *testing.T) {
+-	Setup(t)
+-	defer Teardown()
+-
+-	ext, err := extensions.Get(Client, "service-type").Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, ext.Updated, "2013-01-20T00:00:00-00:00")
+-	th.AssertEquals(t, ext.Name, "Neutron Service Type Management")
+-	th.AssertEquals(t, ext.Namespace, "http://docs.openstack.org/ext/neutron/service-type/api/v1.0")
+-	th.AssertEquals(t, ext.Alias, "service-type")
+-	th.AssertEquals(t, ext.Description, "API for retrieving service providers for Neutron advanced services")
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/layer3_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/layer3_test.go
+deleted file mode 100644
+index 63e0be3..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/layer3_test.go
++++ /dev/null
+@@ -1,300 +0,0 @@
+-// +build acceptance networking layer3ext
 -
--func TestGetJSONAbsent(t *testing.T) {
--	var l []string
--	var env Env
--	err := env.GetJSON("person", &l)
--	if err != nil {
--		t.Error(err)
--	}
--	if l != nil {
--		t.Errorf("Env.GetJSON(): get unexpected list %v", l)
--	}
+-package extensions
+-
+-import (
+-	"testing"
+-
+-	base "github.com/rackspace/gophercloud/acceptance/openstack/networking/v2"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/extensions/external"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/floatingips"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/routers"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/networks"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/ports"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/subnets"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-const (
+-	cidr1 = "10.0.0.1/24"
+-	cidr2 = "20.0.0.1/24"
+-)
+-
+-func TestAll(t *testing.T) {
+-	base.Setup(t)
+-	defer base.Teardown()
+-
+-	testRouter(t)
+-	testFloatingIP(t)
 -}
 -
--func TestGetJSONFailure(t *testing.T) {
--	var p []string
--	var env Env
--	env.Set("list-person", `{"name":"Gopher","age":5}`)
--	err := env.GetJSON("list-person", &p)
--	if err == nil {
--		t.Errorf("Env.GetJSON(%q): got unexpected <nil> error.", "list-person")
--	}
+-func testRouter(t *testing.T) {
+-	// Setup: Create network
+-	networkID := createNetwork(t)
+-
+-	// Create router
+-	routerID := createRouter(t, networkID)
+-
+-	// Lists routers
+-	listRouters(t)
+-
+-	// Update router
+-	updateRouter(t, routerID)
+-
+-	// Get router
+-	getRouter(t, routerID)
+-
+-	// Create new subnet. Note: this subnet will be deleted when networkID is deleted
+-	subnetID := createSubnet(t, networkID, cidr2)
+-
+-	// Add interface
+-	addInterface(t, routerID, subnetID)
+-
+-	// Remove interface
+-	removeInterface(t, routerID, subnetID)
+-
+-	// Delete router
+-	deleteRouter(t, routerID)
+-
+-	// Cleanup
+-	deleteNetwork(t, networkID)
 -}
 -
--func TestSetJSON(t *testing.T) {
--	var p1 = struct {
--		Name string `json:"name"`
--		Age  int    `json:"age"`
--	}{Name: "Gopher", Age: 5}
--	var env Env
--	err := env.SetJSON("person", p1)
--	if err != nil {
--		t.Error(err)
--	}
--	var p2 struct {
--		Name string `json:"name"`
--		Age  int    `json:"age"`
--	}
--	err = env.GetJSON("person", &p2)
--	if err != nil {
--		t.Error(err)
--	}
--	if !reflect.DeepEqual(p1, p2) {
--		t.Errorf("Env.SetJSON(%q): wrong result. Want %v. Got %v", "person", p1, p2)
--	}
+-func testFloatingIP(t *testing.T) {
+-	// Setup external network
+-	extNetworkID := createNetwork(t)
+-
+-	// Setup internal network, subnet and port
+-	intNetworkID, subnetID, portID := createInternalTopology(t)
+-
+-	// Now the important part: we need to allow the external network to talk to
+-	// the internal subnet. For this we need a router that has an interface to
+-	// the internal subnet.
+-	routerID := bridgeIntSubnetWithExtNetwork(t, extNetworkID, subnetID)
+-
+-	// Create floating IP
+-	ipID := createFloatingIP(t, extNetworkID, portID)
+-
+-	// Get floating IP
+-	getFloatingIP(t, ipID)
+-
+-	// Update floating IP
+-	updateFloatingIP(t, ipID, portID)
+-
+-	// Delete floating IP
+-	deleteFloatingIP(t, ipID)
+-
+-	// Remove the internal subnet interface
+-	removeInterface(t, routerID, subnetID)
+-
+-	// Delete router and external network
+-	deleteRouter(t, routerID)
+-	deleteNetwork(t, extNetworkID)
+-
+-	// Delete internal port and network
+-	deletePort(t, portID)
+-	deleteNetwork(t, intNetworkID)
 -}
 -
--func TestSetJSONFailure(t *testing.T) {
--	var env Env
--	err := env.SetJSON("person", unmarshable{})
--	if err == nil {
--		t.Error("Env.SetJSON(): got unexpected <nil> error")
+-func createNetwork(t *testing.T) string {
+-	t.Logf("Creating a network")
+-
+-	asu := true
+-	opts := external.CreateOpts{
+-		Parent:   networks.CreateOpts{Name: "sample_network", AdminStateUp: &asu},
+-		External: true,
 -	}
--	if env.Exists("person") {
--		t.Errorf("Env.SetJSON(): should not define the key %q, but did", "person")
+-	n, err := networks.Create(base.Client, opts).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	if n.ID == "" {
+-		t.Fatalf("No ID returned when creating a network")
 -	}
+-
+-	createSubnet(t, n.ID, cidr1)
+-
+-	t.Logf("Network created: ID [%s]", n.ID)
+-
+-	return n.ID
 -}
 -
--func TestGetList(t *testing.T) {
--	var tests = []struct {
--		input    string
--		expected []string
--	}{
--		{"WAT=wat", []string{"wat"}},
--		{`WAT=["wat","wet","wit","wot","wut"]`, []string{"wat", "wet", "wit", "wot", "wut"}},
--		{"WAT=", nil},
+-func deleteNetwork(t *testing.T, networkID string) {
+-	t.Logf("Deleting network %s", networkID)
+-	networks.Delete(base.Client, networkID)
+-}
+-
+-func deletePort(t *testing.T, portID string) {
+-	t.Logf("Deleting port %s", portID)
+-	ports.Delete(base.Client, portID)
+-}
+-
+-func createInternalTopology(t *testing.T) (string, string, string) {
+-	t.Logf("Creating an internal network (for port)")
+-	opts := networks.CreateOpts{Name: "internal_network"}
+-	n, err := networks.Create(base.Client, opts).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	// A subnet is also needed
+-	subnetID := createSubnet(t, n.ID, cidr2)
+-
+-	t.Logf("Creating an internal port on network %s", n.ID)
+-	p, err := ports.Create(base.Client, ports.CreateOpts{
+-		NetworkID: n.ID,
+-		Name:      "fixed_internal_port",
+-	}).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	return n.ID, subnetID, p.ID
+-}
+-
+-func bridgeIntSubnetWithExtNetwork(t *testing.T, networkID, subnetID string) string {
+-	// Create router with external gateway info
+-	routerID := createRouter(t, networkID)
+-
+-	// Add interface for internal subnet
+-	addInterface(t, routerID, subnetID)
+-
+-	return routerID
+-}
+-
+-func createSubnet(t *testing.T, networkID, cidr string) string {
+-	t.Logf("Creating a subnet for network %s", networkID)
+-
+-	iFalse := false
+-	s, err := subnets.Create(base.Client, subnets.CreateOpts{
+-		NetworkID:  networkID,
+-		CIDR:       cidr,
+-		IPVersion:  subnets.IPv4,
+-		Name:       "my_subnet",
+-		EnableDHCP: &iFalse,
+-	}).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Subnet created: ID [%s]", s.ID)
+-
+-	return s.ID
+-}
+-
+-func createRouter(t *testing.T, networkID string) string {
+-	t.Logf("Creating a router for network %s", networkID)
+-
+-	asu := false
+-	gwi := routers.GatewayInfo{NetworkID: networkID}
+-	r, err := routers.Create(base.Client, routers.CreateOpts{
+-		Name:         "foo_router",
+-		AdminStateUp: &asu,
+-		GatewayInfo:  &gwi,
+-	}).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	if r.ID == "" {
+-		t.Fatalf("No ID returned when creating a router")
 -	}
--	for _, tt := range tests {
--		env := Env([]string{tt.input})
--		got := env.GetList("WAT")
--		if !reflect.DeepEqual(got, tt.expected) {
--			t.Errorf("Env.GetList(%q): wrong result. Want %v. Got %v", "WAT", tt.expected, got)
+-
+-	t.Logf("Router created: ID [%s]", r.ID)
+-
+-	return r.ID
+-}
+-
+-func listRouters(t *testing.T) {
+-	pager := routers.List(base.Client, routers.ListOpts{})
+-
+-	err := pager.EachPage(func(page pagination.Page) (bool, error) {
+-		routerList, err := routers.ExtractRouters(page)
+-		th.AssertNoErr(t, err)
+-
+-		for _, r := range routerList {
+-			t.Logf("Listing router: ID [%s] Name [%s] Status [%s] GatewayInfo [%#v]",
+-				r.ID, r.Name, r.Status, r.GatewayInfo)
 -		}
+-
+-		return true, nil
+-	})
+-
+-	th.AssertNoErr(t, err)
+-}
+-
+-func updateRouter(t *testing.T, routerID string) {
+-	_, err := routers.Update(base.Client, routerID, routers.UpdateOpts{
+-		Name: "another_name",
+-	}).Extract()
+-
+-	th.AssertNoErr(t, err)
+-}
+-
+-func getRouter(t *testing.T, routerID string) {
+-	r, err := routers.Get(base.Client, routerID).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Getting router: ID [%s] Name [%s] Status [%s]", r.ID, r.Name, r.Status)
+-}
+-
+-func addInterface(t *testing.T, routerID, subnetID string) {
+-	ir, err := routers.AddInterface(base.Client, routerID, routers.InterfaceOpts{SubnetID: subnetID}).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Interface added to router %s: SubnetID [%s] PortID [%s]", routerID, ir.SubnetID, ir.PortID)
+-}
+-
+-func removeInterface(t *testing.T, routerID, subnetID string) {
+-	ir, err := routers.RemoveInterface(base.Client, routerID, routers.InterfaceOpts{SubnetID: subnetID}).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Interface %s removed from %s", ir.ID, routerID)
+-}
+-
+-func deleteRouter(t *testing.T, routerID string) {
+-	t.Logf("Deleting router %s", routerID)
+-
+-	res := routers.Delete(base.Client, routerID)
+-
+-	th.AssertNoErr(t, res.Err)
+-}
+-
+-func createFloatingIP(t *testing.T, networkID, portID string) string {
+-	t.Logf("Creating floating IP on network [%s] with port [%s]", networkID, portID)
+-
+-	opts := floatingips.CreateOpts{
+-		FloatingNetworkID: networkID,
+-		PortID:            portID,
 -	}
+-
+-	ip, err := floatingips.Create(base.Client, opts).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Floating IP created: ID [%s] Status [%s] Fixed (internal) IP: [%s] Floating (external) IP: [%s]",
+-		ip.ID, ip.Status, ip.FixedIP, ip.FloatingIP)
+-
+-	return ip.ID
+-}
+-
+-func getFloatingIP(t *testing.T, ipID string) {
+-	ip, err := floatingips.Get(base.Client, ipID).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Getting floating IP: ID [%s] Status [%s]", ip.ID, ip.Status)
+-}
+-
+-func updateFloatingIP(t *testing.T, ipID, portID string) {
+-	t.Logf("Disassociate all ports from IP %s", ipID)
+-	_, err := floatingips.Update(base.Client, ipID, floatingips.UpdateOpts{PortID: ""}).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Re-associate the port %s", portID)
+-	_, err = floatingips.Update(base.Client, ipID, floatingips.UpdateOpts{PortID: portID}).Extract()
+-	th.AssertNoErr(t, err)
+-}
+-
+-func deleteFloatingIP(t *testing.T, ipID string) {
+-	t.Logf("Deleting IP %s", ipID)
+-	res := floatingips.Delete(base.Client, ipID)
+-	th.AssertNoErr(t, res.Err)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/common.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/common.go
+deleted file mode 100644
+index 27dfe5f..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/common.go
++++ /dev/null
+@@ -1,78 +0,0 @@
+-package lbaas
+-
+-import (
+-	"testing"
+-
+-	base "github.com/rackspace/gophercloud/acceptance/openstack/networking/v2"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/monitors"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/pools"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/networks"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/subnets"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func SetupTopology(t *testing.T) (string, string) {
+-	// create network
+-	n, err := networks.Create(base.Client, networks.CreateOpts{Name: "tmp_network"}).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Created network %s", n.ID)
+-
+-	// create subnet
+-	s, err := subnets.Create(base.Client, subnets.CreateOpts{
+-		NetworkID: n.ID,
+-		CIDR:      "192.168.199.0/24",
+-		IPVersion: subnets.IPv4,
+-		Name:      "tmp_subnet",
+-	}).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Created subnet %s", s.ID)
+-
+-	return n.ID, s.ID
+-}
+-
+-func DeleteTopology(t *testing.T, networkID string) {
+-	res := networks.Delete(base.Client, networkID)
+-	th.AssertNoErr(t, res.Err)
+-	t.Logf("Deleted network %s", networkID)
+-}
+-
+-func CreatePool(t *testing.T, subnetID string) string {
+-	p, err := pools.Create(base.Client, pools.CreateOpts{
+-		LBMethod: pools.LBMethodRoundRobin,
+-		Protocol: "HTTP",
+-		Name:     "tmp_pool",
+-		SubnetID: subnetID,
+-	}).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Created pool %s", p.ID)
+-
+-	return p.ID
+-}
+-
+-func DeletePool(t *testing.T, poolID string) {
+-	res := pools.Delete(base.Client, poolID)
+-	th.AssertNoErr(t, res.Err)
+-	t.Logf("Deleted pool %s", poolID)
+-}
+-
+-func CreateMonitor(t *testing.T) string {
+-	m, err := monitors.Create(base.Client, monitors.CreateOpts{
+-		Delay:         10,
+-		Timeout:       10,
+-		MaxRetries:    3,
+-		Type:          monitors.TypeHTTP,
+-		ExpectedCodes: "200",
+-		URLPath:       "/login",
+-		HTTPMethod:    "GET",
+-	}).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Created monitor ID [%s]", m.ID)
+-
+-	return m.ID
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/member_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/member_test.go
+deleted file mode 100644
+index 9b60582..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/member_test.go
++++ /dev/null
+@@ -1,95 +0,0 @@
+-// +build acceptance networking lbaas lbaasmember
+-
+-package lbaas
+-
+-import (
+-	"testing"
+-
+-	base "github.com/rackspace/gophercloud/acceptance/openstack/networking/v2"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/members"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--func TestSetList(t *testing.T) {
--	list := []string{"a", "b", "c"}
--	var env Env
--	env.SetList("SOME", list)
--	if got := env.GetList("SOME"); !reflect.DeepEqual(got, list) {
--		t.Errorf("Env.SetList(%v): wrong result. Got %v", list, got)
--	}
+-func TestMembers(t *testing.T) {
+-	base.Setup(t)
+-	defer base.Teardown()
+-
+-	// setup
+-	networkID, subnetID := SetupTopology(t)
+-	poolID := CreatePool(t, subnetID)
+-
+-	// create member
+-	memberID := createMember(t, poolID)
+-
+-	// list members
+-	listMembers(t)
+-
+-	// update member
+-	updateMember(t, memberID)
+-
+-	// get member
+-	getMember(t, memberID)
+-
+-	// delete member
+-	deleteMember(t, memberID)
+-
+-	// teardown
+-	DeletePool(t, poolID)
+-	DeleteTopology(t, networkID)
 -}
 -
--func TestSet(t *testing.T) {
--	var env Env
--	env.Set("PATH", "/home/bin:/bin")
--	env.Set("SOMETHING", "/usr/bin")
--	env.Set("PATH", "/bin")
--	if expected, got := "/usr/bin", env.Get("SOMETHING"); got != expected {
--		t.Errorf("Env.Set(%q): wrong result. Want %q. Got %q", expected, expected, got)
--	}
--	if expected, got := "/bin", env.Get("PATH"); got != expected {
--		t.Errorf("Env.Set(%q): wrong result. Want %q. Got %q", expected, expected, got)
--	}
+-func createMember(t *testing.T, poolID string) string {
+-	m, err := members.Create(base.Client, members.CreateOpts{
+-		Address:      "192.168.199.1",
+-		ProtocolPort: 8080,
+-		PoolID:       poolID,
+-	}).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Created member: ID [%s] Status [%s] Weight [%d] Address [%s] Port [%d]",
+-		m.ID, m.Status, m.Weight, m.Address, m.ProtocolPort)
+-
+-	return m.ID
 -}
 -
--func TestDecode(t *testing.T) {
--	var tests = []struct {
--		input       string
--		expectedOut []string
--		expectedErr string
--	}{
--		{
--			`{"PATH":"/usr/bin:/bin","containers":54,"wat":["123","345"]}`,
--			[]string{"PATH=/usr/bin:/bin", "containers=54", `wat=["123","345"]`},
--			"",
--		},
--		{"}}", nil, "invalid character '}' looking for beginning of value"},
--		{`{}`, nil, ""},
--	}
--	for _, tt := range tests {
--		var env Env
--		err := env.Decode(bytes.NewBufferString(tt.input))
--		if tt.expectedErr == "" {
--			if err != nil {
--				t.Error(err)
--			}
--		} else if tt.expectedErr != err.Error() {
--			t.Errorf("Env.Decode(): invalid error. Want %q. Got %q.", tt.expectedErr, err)
--		}
--		got := []string(env)
--		sort.Strings(got)
--		sort.Strings(tt.expectedOut)
--		if !reflect.DeepEqual(got, tt.expectedOut) {
--			t.Errorf("Env.Decode(): wrong result. Want %v. Got %v.", tt.expectedOut, got)
+-func listMembers(t *testing.T) {
+-	err := members.List(base.Client, members.ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		memberList, err := members.ExtractMembers(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract members: %v", err)
+-			return false, err
 -		}
--	}
--}
 -
--func TestSetAuto(t *testing.T) {
--	buf := bytes.NewBufferString("oi")
--	var tests = []struct {
--		input    interface{}
--		expected string
--	}{
--		{10, "10"},
--		{10.3, "10"},
--		{"oi", "oi"},
--		{buf, "{}"},
--		{unmarshable{}, "{}"},
--	}
--	for _, tt := range tests {
--		var env Env
--		env.SetAuto("SOME", tt.input)
--		if got := env.Get("SOME"); got != tt.expected {
--			t.Errorf("Env.SetAuto(%v): wrong result. Want %q. Got %q", tt.input, tt.expected, got)
+-		for _, m := range memberList {
+-			t.Logf("Listing member: ID [%s] Status [%s]", m.ID, m.Status)
 -		}
--	}
+-
+-		return true, nil
+-	})
+-
+-	th.AssertNoErr(t, err)
 -}
 -
--func TestMap(t *testing.T) {
--	var tests = []struct {
--		input    []string
--		expected map[string]string
--	}{
--		{[]string{"PATH=/usr/bin:/bin", "PYTHONPATH=/usr/local"}, map[string]string{"PATH": "/usr/bin:/bin", "PYTHONPATH": "/usr/local"}},
--		{nil, nil},
--	}
--	for _, tt := range tests {
--		env := Env(tt.input)
--		got := env.Map()
--		if !reflect.DeepEqual(got, tt.expected) {
--			t.Errorf("Env.Map(): wrong result. Want %v. Got %v", tt.expected, got)
--		}
--	}
+-func updateMember(t *testing.T, memberID string) {
+-	m, err := members.Update(base.Client, memberID, members.UpdateOpts{AdminStateUp: true}).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Updated member ID [%s]", m.ID)
 -}
 -
--type unmarshable struct {
+-func getMember(t *testing.T, memberID string) {
+-	m, err := members.Get(base.Client, memberID).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Getting member ID [%s]", m.ID)
 -}
 -
--func (unmarshable) MarshalJSON() ([]byte, error) {
--	return nil, errors.New("cannot marshal")
+-func deleteMember(t *testing.T, memberID string) {
+-	res := members.Delete(base.Client, memberID)
+-	th.AssertNoErr(t, res.Err)
+-	t.Logf("Deleted member %s", memberID)
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/event.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/event.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/monitor_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/monitor_test.go
 deleted file mode 100644
-index 262d4ee..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/event.go
+index 9056fff..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/monitor_test.go
 +++ /dev/null
-@@ -1,278 +0,0 @@
--// Copyright 2014 go-dockerclient authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the LICENSE file.
+@@ -1,77 +0,0 @@
+-// +build acceptance networking lbaas lbaasmonitor
 -
--package docker
+-package lbaas
 -
 -import (
--	"encoding/json"
--	"errors"
--	"fmt"
--	"io"
--	"math"
--	"net"
--	"net/http"
--	"net/http/httputil"
--	"sync"
--	"sync/atomic"
--	"time"
+-	"testing"
+-
+-	base "github.com/rackspace/gophercloud/acceptance/openstack/networking/v2"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/monitors"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--// APIEvents represents an event returned by the API.
--type APIEvents struct {
--	Status string `json:"Status,omitempty" yaml:"Status,omitempty"`
--	ID     string `json:"ID,omitempty" yaml:"ID,omitempty"`
--	From   string `json:"From,omitempty" yaml:"From,omitempty"`
--	Time   int64  `json:"Time,omitempty" yaml:"Time,omitempty"`
--}
+-func TestMonitors(t *testing.T) {
+-	base.Setup(t)
+-	defer base.Teardown()
 -
--type eventMonitoringState struct {
--	sync.RWMutex
--	sync.WaitGroup
--	enabled   bool
--	lastSeen  *int64
--	C         chan *APIEvents
--	errC      chan error
--	listeners []chan<- *APIEvents
--}
+-	// create monitor
+-	monitorID := CreateMonitor(t)
 -
--const (
--	maxMonitorConnRetries = 5
--	retryInitialWaitTime  = 10.
--)
+-	// list monitors
+-	listMonitors(t)
 -
--var (
--	// ErrNoListeners is the error returned when no listeners are available
--	// to receive an event.
--	ErrNoListeners = errors.New("no listeners present to receive event")
+-	// update monitor
+-	updateMonitor(t, monitorID)
 -
--	// ErrListenerAlreadyExists is the error returned when the listerner already
--	// exists.
--	ErrListenerAlreadyExists = errors.New("listener already exists for docker events")
--)
+-	// get monitor
+-	getMonitor(t, monitorID)
 -
--// AddEventListener adds a new listener to container events in the Docker API.
--//
--// The parameter is a channel through which events will be sent.
--func (c *Client) AddEventListener(listener chan<- *APIEvents) error {
--	var err error
--	if !c.eventMonitor.isEnabled() {
--		err = c.eventMonitor.enableEventMonitoring(c)
--		if err != nil {
--			return err
--		}
--	}
--	err = c.eventMonitor.addListener(listener)
--	if err != nil {
--		return err
--	}
--	return nil
+-	// delete monitor
+-	deleteMonitor(t, monitorID)
 -}
 -
--// RemoveEventListener removes a listener from the monitor.
--func (c *Client) RemoveEventListener(listener chan *APIEvents) error {
--	err := c.eventMonitor.removeListener(listener)
--	if err != nil {
--		return err
--	}
--	if len(c.eventMonitor.listeners) == 0 {
--		err = c.eventMonitor.disableEventMonitoring()
+-func listMonitors(t *testing.T) {
+-	err := monitors.List(base.Client, monitors.ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		monitorList, err := monitors.ExtractMonitors(page)
 -		if err != nil {
--			return err
+-			t.Errorf("Failed to extract monitors: %v", err)
+-			return false, err
 -		}
--	}
--	return nil
+-
+-		for _, m := range monitorList {
+-			t.Logf("Listing monitor: ID [%s] Type [%s] Delay [%ds] Timeout [%d] Retries [%d] Status [%s]",
+-				m.ID, m.Type, m.Delay, m.Timeout, m.MaxRetries, m.Status)
+-		}
+-
+-		return true, nil
+-	})
+-
+-	th.AssertNoErr(t, err)
 -}
 -
--func (eventState *eventMonitoringState) addListener(listener chan<- *APIEvents) error {
--	eventState.Lock()
--	defer eventState.Unlock()
--	if listenerExists(listener, &eventState.listeners) {
--		return ErrListenerAlreadyExists
--	}
--	eventState.Add(1)
--	eventState.listeners = append(eventState.listeners, listener)
--	return nil
+-func updateMonitor(t *testing.T, monitorID string) {
+-	opts := monitors.UpdateOpts{Delay: 10, Timeout: 10, MaxRetries: 3}
+-	m, err := monitors.Update(base.Client, monitorID, opts).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Updated monitor ID [%s]", m.ID)
 -}
 -
--func (eventState *eventMonitoringState) removeListener(listener chan<- *APIEvents) error {
--	eventState.Lock()
--	defer eventState.Unlock()
--	if listenerExists(listener, &eventState.listeners) {
--		var newListeners []chan<- *APIEvents
--		for _, l := range eventState.listeners {
--			if l != listener {
--				newListeners = append(newListeners, l)
--			}
--		}
--		eventState.listeners = newListeners
--		eventState.Add(-1)
--	}
--	return nil
+-func getMonitor(t *testing.T, monitorID string) {
+-	m, err := monitors.Get(base.Client, monitorID).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Getting monitor ID [%s]: URL path [%s] HTTP Method [%s] Accepted codes [%s]",
+-		m.ID, m.URLPath, m.HTTPMethod, m.ExpectedCodes)
 -}
 -
--func listenerExists(a chan<- *APIEvents, list *[]chan<- *APIEvents) bool {
--	for _, b := range *list {
--		if b == a {
--			return true
+-func deleteMonitor(t *testing.T, monitorID string) {
+-	res := monitors.Delete(base.Client, monitorID)
+-
+-	th.AssertNoErr(t, res.Err)
+-
+-	t.Logf("Deleted monitor %s", monitorID)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/pkg.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/pkg.go
+deleted file mode 100644
+index f5a7df7..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/pkg.go
++++ /dev/null
+@@ -1 +0,0 @@
+-package lbaas
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/pool_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/pool_test.go
+deleted file mode 100644
+index 8194064..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/pool_test.go
++++ /dev/null
+@@ -1,98 +0,0 @@
+-// +build acceptance networking lbaas lbaaspool
+-
+-package lbaas
+-
+-import (
+-	"testing"
+-
+-	base "github.com/rackspace/gophercloud/acceptance/openstack/networking/v2"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/pools"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestPools(t *testing.T) {
+-	base.Setup(t)
+-	defer base.Teardown()
+-
+-	// setup
+-	networkID, subnetID := SetupTopology(t)
+-
+-	// create pool
+-	poolID := CreatePool(t, subnetID)
+-
+-	// list pools
+-	listPools(t)
+-
+-	// update pool
+-	updatePool(t, poolID)
+-
+-	// get pool
+-	getPool(t, poolID)
+-
+-	// create monitor
+-	monitorID := CreateMonitor(t)
+-
+-	// associate health monitor
+-	associateMonitor(t, poolID, monitorID)
+-
+-	// disassociate health monitor
+-	disassociateMonitor(t, poolID, monitorID)
+-
+-	// delete pool
+-	DeletePool(t, poolID)
+-
+-	// teardown
+-	DeleteTopology(t, networkID)
+-}
+-
+-func listPools(t *testing.T) {
+-	err := pools.List(base.Client, pools.ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		poolList, err := pools.ExtractPools(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract pools: %v", err)
+-			return false, err
 -		}
--	}
--	return false
+-
+-		for _, p := range poolList {
+-			t.Logf("Listing pool: ID [%s] Name [%s] Status [%s] LB algorithm [%s]", p.ID, p.Name, p.Status, p.LBMethod)
+-		}
+-
+-		return true, nil
+-	})
+-
+-	th.AssertNoErr(t, err)
 -}
 -
--func (eventState *eventMonitoringState) enableEventMonitoring(c *Client) error {
--	eventState.Lock()
--	defer eventState.Unlock()
--	if !eventState.enabled {
--		eventState.enabled = true
--		var lastSeenDefault = int64(0)
--		eventState.lastSeen = &lastSeenDefault
--		eventState.C = make(chan *APIEvents, 100)
--		eventState.errC = make(chan error, 1)
--		go eventState.monitorEvents(c)
--	}
--	return nil
+-func updatePool(t *testing.T, poolID string) {
+-	opts := pools.UpdateOpts{Name: "SuperPool", LBMethod: pools.LBMethodLeastConnections}
+-	p, err := pools.Update(base.Client, poolID, opts).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Updated pool ID [%s]", p.ID)
 -}
 -
--func (eventState *eventMonitoringState) disableEventMonitoring() error {
--	eventState.Wait()
--	eventState.Lock()
--	defer eventState.Unlock()
--	if eventState.enabled {
--		eventState.enabled = false
--		close(eventState.C)
--		close(eventState.errC)
--	}
--	return nil
+-func getPool(t *testing.T, poolID string) {
+-	p, err := pools.Get(base.Client, poolID).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Getting pool ID [%s]", p.ID)
 -}
 -
--func (eventState *eventMonitoringState) monitorEvents(c *Client) {
--	var err error
--	for eventState.noListeners() {
--		time.Sleep(10 * time.Millisecond)
--	}
--	if err = eventState.connectWithRetry(c); err != nil {
--		eventState.terminate(err)
--	}
--	for eventState.isEnabled() {
--		timeout := time.After(100 * time.Millisecond)
--		select {
--		case ev, ok := <-eventState.C:
--			if !ok {
--				return
--			}
--			go eventState.sendEvent(ev)
--			go eventState.updateLastSeen(ev)
--		case err = <-eventState.errC:
--			if err == ErrNoListeners {
--				eventState.terminate(nil)
--				return
--			} else if err != nil {
--				defer func() { go eventState.monitorEvents(c) }()
--				return
--			}
--		case <-timeout:
--			continue
--		}
--	}
+-func associateMonitor(t *testing.T, poolID, monitorID string) {
+-	res := pools.AssociateMonitor(base.Client, poolID, monitorID)
+-
+-	th.AssertNoErr(t, res.Err)
+-
+-	t.Logf("Associated pool %s with monitor %s", poolID, monitorID)
 -}
 -
--func (eventState *eventMonitoringState) connectWithRetry(c *Client) error {
--	var retries int
--	var err error
--	for err = c.eventHijack(atomic.LoadInt64(eventState.lastSeen), eventState.C, eventState.errC); err != nil && retries < maxMonitorConnRetries; retries++ {
--		waitTime := int64(retryInitialWaitTime * math.Pow(2, float64(retries)))
--		time.Sleep(time.Duration(waitTime) * time.Millisecond)
--		err = c.eventHijack(atomic.LoadInt64(eventState.lastSeen), eventState.C, eventState.errC)
--	}
--	return err
+-func disassociateMonitor(t *testing.T, poolID, monitorID string) {
+-	res := pools.DisassociateMonitor(base.Client, poolID, monitorID)
+-
+-	th.AssertNoErr(t, res.Err)
+-
+-	t.Logf("Disassociated pool %s with monitor %s", poolID, monitorID)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/vip_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/vip_test.go
+deleted file mode 100644
+index c8dff2d..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/lbaas/vip_test.go
++++ /dev/null
+@@ -1,101 +0,0 @@
+-// +build acceptance networking lbaas lbaasvip
 -
--func (eventState *eventMonitoringState) noListeners() bool {
--	eventState.RLock()
--	defer eventState.RUnlock()
--	return len(eventState.listeners) == 0
+-package lbaas
+-
+-import (
+-	"testing"
+-
+-	base "github.com/rackspace/gophercloud/acceptance/openstack/networking/v2"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/vips"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestVIPs(t *testing.T) {
+-	base.Setup(t)
+-	defer base.Teardown()
+-
+-	// setup
+-	networkID, subnetID := SetupTopology(t)
+-	poolID := CreatePool(t, subnetID)
+-
+-	// create VIP
+-	VIPID := createVIP(t, subnetID, poolID)
+-
+-	// list VIPs
+-	listVIPs(t)
+-
+-	// update VIP
+-	updateVIP(t, VIPID)
+-
+-	// get VIP
+-	getVIP(t, VIPID)
+-
+-	// delete VIP
+-	deleteVIP(t, VIPID)
+-
+-	// teardown
+-	DeletePool(t, poolID)
+-	DeleteTopology(t, networkID)
 -}
 -
--func (eventState *eventMonitoringState) isEnabled() bool {
--	eventState.RLock()
--	defer eventState.RUnlock()
--	return eventState.enabled
+-func createVIP(t *testing.T, subnetID, poolID string) string {
+-	p, err := vips.Create(base.Client, vips.CreateOpts{
+-		Protocol:     "HTTP",
+-		Name:         "New_VIP",
+-		AdminStateUp: vips.Up,
+-		SubnetID:     subnetID,
+-		PoolID:       poolID,
+-		ProtocolPort: 80,
+-	}).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Created pool %s", p.ID)
+-
+-	return p.ID
 -}
 -
--func (eventState *eventMonitoringState) sendEvent(event *APIEvents) {
--	eventState.RLock()
--	defer eventState.RUnlock()
--	eventState.Add(1)
--	defer eventState.Done()
--	if eventState.isEnabled() {
--		if eventState.noListeners() {
--			eventState.errC <- ErrNoListeners
--			return
+-func listVIPs(t *testing.T) {
+-	err := vips.List(base.Client, vips.ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		vipList, err := vips.ExtractVIPs(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract VIPs: %v", err)
+-			return false, err
 -		}
 -
--		for _, listener := range eventState.listeners {
--			listener <- event
+-		for _, vip := range vipList {
+-			t.Logf("Listing VIP: ID [%s] Name [%s] Address [%s] Port [%s] Connection Limit [%d]",
+-				vip.ID, vip.Name, vip.Address, vip.ProtocolPort, vip.ConnLimit)
 -		}
--	}
+-
+-		return true, nil
+-	})
+-
+-	th.AssertNoErr(t, err)
 -}
 -
--func (eventState *eventMonitoringState) updateLastSeen(e *APIEvents) {
--	eventState.Lock()
--	defer eventState.Unlock()
--	if atomic.LoadInt64(eventState.lastSeen) < e.Time {
--		atomic.StoreInt64(eventState.lastSeen, e.Time)
--	}
+-func updateVIP(t *testing.T, VIPID string) {
+-	i1000 := 1000
+-	_, err := vips.Update(base.Client, VIPID, vips.UpdateOpts{ConnLimit: &i1000}).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Updated VIP ID [%s]", VIPID)
 -}
 -
--func (eventState *eventMonitoringState) terminate(err error) {
--	eventState.disableEventMonitoring()
+-func getVIP(t *testing.T, VIPID string) {
+-	vip, err := vips.Get(base.Client, VIPID).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Getting VIP ID [%s]: Status [%s]", vip.ID, vip.Status)
 -}
 -
--func (c *Client) eventHijack(startTime int64, eventChan chan *APIEvents, errChan chan error) error {
--	uri := "/events"
--	if startTime != 0 {
--		uri += fmt.Sprintf("?since=%d", startTime)
--	}
--	protocol := c.endpointURL.Scheme
--	address := c.endpointURL.Path
--	if protocol != "unix" {
--		protocol = "tcp"
--		address = c.endpointURL.Host
--	}
--	dial, err := net.Dial(protocol, address)
--	if err != nil {
--		return err
--	}
--	conn := httputil.NewClientConn(dial, nil)
--	req, err := http.NewRequest("GET", uri, nil)
--	if err != nil {
--		return err
--	}
--	res, err := conn.Do(req)
--	if err != nil {
--		return err
--	}
--	go func(res *http.Response, conn *httputil.ClientConn) {
--		defer conn.Close()
--		defer res.Body.Close()
--		decoder := json.NewDecoder(res.Body)
--		for {
--			var event APIEvents
--			if err = decoder.Decode(&event); err != nil {
--				if err == io.EOF || err == io.ErrUnexpectedEOF {
--					break
--				}
--				errChan <- err
--			}
--			if event.Time == 0 {
--				continue
--			}
--			if !c.eventMonitor.isEnabled() {
--				return
--			}
--			c.eventMonitor.C <- &event
--		}
--	}(res, conn)
--	return nil
+-func deleteVIP(t *testing.T, VIPID string) {
+-	res := vips.Delete(base.Client, VIPID)
+-
+-	th.AssertNoErr(t, res.Err)
+-
+-	t.Logf("Deleted VIP %s", VIPID)
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/event_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/event_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/pkg.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/pkg.go
 deleted file mode 100644
-index cb54f4a..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/event_test.go
+index aeec0fa..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/pkg.go
 +++ /dev/null
-@@ -1,93 +0,0 @@
--// Copyright 2014 go-dockerclient authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the LICENSE file.
+@@ -1 +0,0 @@
+-package extensions
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/provider_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/provider_test.go
+deleted file mode 100644
+index f10c9d9..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/provider_test.go
++++ /dev/null
+@@ -1,68 +0,0 @@
+-// +build acceptance networking
 -
--package docker
+-package extensions
 -
 -import (
--	"bufio"
--	"fmt"
--	"net/http"
--	"net/http/httptest"
--	"strings"
+-	"strconv"
 -	"testing"
--	"time"
+-
+-	base "github.com/rackspace/gophercloud/acceptance/openstack/networking/v2"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/networks"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--func TestEventListeners(t *testing.T) {
--	response := `{"status":"create","id":"dfdf82bd3881","from":"base:latest","time":1374067924}
--{"status":"start","id":"dfdf82bd3881","from":"base:latest","time":1374067924}
--{"status":"stop","id":"dfdf82bd3881","from":"base:latest","time":1374067966}
--{"status":"destroy","id":"dfdf82bd3881","from":"base:latest","time":1374067970}
--`
+-func TestNetworkCRUDOperations(t *testing.T) {
+-	base.Setup(t)
+-	defer base.Teardown()
 -
--	var req http.Request
--	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
--		rsc := bufio.NewScanner(strings.NewReader(response))
--		for rsc.Scan() {
--			w.Write([]byte(rsc.Text()))
--			w.(http.Flusher).Flush()
--			time.Sleep(10 * time.Millisecond)
--		}
--		req = *r
--	}))
--	defer server.Close()
+-	// Create a network
+-	n, err := networks.Create(base.Client, networks.CreateOpts{Name: "sample_network", AdminStateUp: networks.Up}).Extract()
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, n.Name, "sample_network")
+-	th.AssertEquals(t, n.AdminStateUp, true)
+-	networkID := n.ID
 -
--	client, err := NewClient(server.URL)
--	if err != nil {
--		t.Errorf("Failed to create client: %s", err)
--	}
--	client.SkipServerVersionCheck = true
+-	// List networks
+-	pager := networks.List(base.Client, networks.ListOpts{Limit: 2})
+-	err = pager.EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page ---")
 -
--	listener := make(chan *APIEvents, 10)
--	defer func() { time.Sleep(10 * time.Millisecond); client.RemoveEventListener(listener) }()
+-		networkList, err := networks.ExtractNetworks(page)
+-		th.AssertNoErr(t, err)
 -
--	err = client.AddEventListener(listener)
--	if err != nil {
--		t.Errorf("Failed to add event listener: %s", err)
--	}
+-		for _, n := range networkList {
+-			t.Logf("Network: ID [%s] Name [%s] Status [%s] Is shared? [%s]",
+-				n.ID, n.Name, n.Status, strconv.FormatBool(n.Shared))
+-		}
 -
--	timeout := time.After(1 * time.Second)
--	var count int
+-		return true, nil
+-	})
+-	th.CheckNoErr(t, err)
 -
--	for {
--		select {
--		case msg := <-listener:
--			t.Logf("Recieved: %s", *msg)
--			count++
--			err = checkEvent(count, msg)
--			if err != nil {
--				t.Fatalf("Check event failed: %s", err)
--			}
--			if count == 4 {
--				return
--			}
--		case <-timeout:
--			t.Fatal("TestAddEventListener timed out waiting on events")
--		}
+-	// Get a network
+-	if networkID == "" {
+-		t.Fatalf("In order to retrieve a network, the NetworkID must be set")
 -	}
+-	n, err = networks.Get(base.Client, networkID).Extract()
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, n.Status, "ACTIVE")
+-	th.AssertDeepEquals(t, n.Subnets, []string{})
+-	th.AssertEquals(t, n.Name, "sample_network")
+-	th.AssertEquals(t, n.AdminStateUp, true)
+-	th.AssertEquals(t, n.Shared, false)
+-	th.AssertEquals(t, n.ID, networkID)
+-
+-	// Update network
+-	n, err = networks.Update(base.Client, networkID, networks.UpdateOpts{Name: "new_network_name"}).Extract()
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, n.Name, "new_network_name")
+-
+-	// Delete network
+-	res := networks.Delete(base.Client, networkID)
+-	th.AssertNoErr(t, res.Err)
 -}
 -
--func checkEvent(index int, event *APIEvents) error {
--	if event.ID != "dfdf82bd3881" {
--		return fmt.Errorf("event ID did not match. Expected dfdf82bd3881 got %s", event.ID)
--	}
--	if event.From != "base:latest" {
--		return fmt.Errorf("event from did not match. Expected base:latest got %s", event.From)
--	}
--	var status string
--	switch index {
--	case 1:
--		status = "create"
--	case 2:
--		status = "start"
--	case 3:
--		status = "stop"
--	case 4:
--		status = "destroy"
--	}
--	if event.Status != status {
--		return fmt.Errorf("event status did not match. Expected %s got %s", status, event.Status)
--	}
--	return nil
+-func TestCreateMultipleNetworks(t *testing.T) {
+-	//networks.CreateMany()
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/example_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/example_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/security_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/security_test.go
 deleted file mode 100644
-index 8c2c719..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/example_test.go
+index 7d75292..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/extensions/security_test.go
 +++ /dev/null
-@@ -1,168 +0,0 @@
--// Copyright 2014 go-dockerclient authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the LICENSE file.
+@@ -1,171 +0,0 @@
+-// +build acceptance networking security
 -
--package docker_test
+-package extensions
 -
 -import (
--	"archive/tar"
--	"bytes"
--	"fmt"
--	"io"
--	"log"
--	"time"
+-	"testing"
 -
--	"github.com/fsouza/go-dockerclient"
+-	base "github.com/rackspace/gophercloud/acceptance/openstack/networking/v2"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/groups"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/networks"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/ports"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--func ExampleClient_AttachToContainer() {
--	client, err := docker.NewClient("http://localhost:4243")
--	if err != nil {
--		log.Fatal(err)
--	}
--	client.SkipServerVersionCheck = true
--	// Reading logs from container a84849 and sending them to buf.
--	var buf bytes.Buffer
--	err = client.AttachToContainer(docker.AttachToContainerOptions{
--		Container:    "a84849",
--		OutputStream: &buf,
--		Logs:         true,
--		Stdout:       true,
--		Stderr:       true,
--	})
--	if err != nil {
--		log.Fatal(err)
--	}
--	log.Println(buf.String())
--	buf.Reset()
--	err = client.AttachToContainer(docker.AttachToContainerOptions{
--		Container:    "a84849",
--		OutputStream: &buf,
--		Stdout:       true,
--		Stream:       true,
--	})
--	if err != nil {
--		log.Fatal(err)
--	}
--	log.Println(buf.String())
--}
+-func TestSecurityGroups(t *testing.T) {
+-	base.Setup(t)
+-	defer base.Teardown()
 -
--func ExampleClient_CopyFromContainer() {
--	client, err := docker.NewClient("http://localhost:4243")
--	if err != nil {
--		log.Fatal(err)
--	}
--	cid := "a84849"
--	var buf bytes.Buffer
--	filename := "/tmp/output.txt"
--	err = client.CopyFromContainer(docker.CopyFromContainerOptions{
--		Container:    cid,
--		Resource:     filename,
--		OutputStream: &buf,
--	})
--	if err != nil {
--		log.Fatalf("Error while copying from %s: %s\n", cid, err)
--	}
--	content := new(bytes.Buffer)
--	r := bytes.NewReader(buf.Bytes())
--	tr := tar.NewReader(r)
--	tr.Next()
--	if err != nil && err != io.EOF {
--		log.Fatal(err)
--	}
--	if _, err := io.Copy(content, tr); err != nil {
--		log.Fatal(err)
--	}
--	log.Println(buf.String())
+-	// create security group
+-	groupID := createSecGroup(t)
+-
+-	// delete security group
+-	defer deleteSecGroup(t, groupID)
+-
+-	// list security group
+-	listSecGroups(t)
+-
+-	// get security group
+-	getSecGroup(t, groupID)
+-
+-	// create port with security group
+-	networkID, portID := createPort(t, groupID)
+-
+-	// teardown
+-	defer deleteNetwork(t, networkID)
+-
+-	// delete port
+-	defer deletePort(t, portID)
 -}
 -
--func ExampleClient_BuildImage() {
--	client, err := docker.NewClient("http://localhost:4243")
--	if err != nil {
--		log.Fatal(err)
--	}
+-func TestSecurityGroupRules(t *testing.T) {
+-	base.Setup(t)
+-	defer base.Teardown()
 -
--	t := time.Now()
--	inputbuf, outputbuf := bytes.NewBuffer(nil), bytes.NewBuffer(nil)
--	tr := tar.NewWriter(inputbuf)
--	tr.WriteHeader(&tar.Header{Name: "Dockerfile", Size: 10, ModTime: t, AccessTime: t, ChangeTime: t})
--	tr.Write([]byte("FROM base\n"))
--	tr.Close()
--	opts := docker.BuildImageOptions{
--		Name:         "test",
--		InputStream:  inputbuf,
--		OutputStream: outputbuf,
--	}
--	if err := client.BuildImage(opts); err != nil {
--		log.Fatal(err)
--	}
+-	// create security group
+-	groupID := createSecGroup(t)
+-
+-	defer deleteSecGroup(t, groupID)
+-
+-	// create security group rule
+-	ruleID := createSecRule(t, groupID)
+-
+-	// delete security group rule
+-	defer deleteSecRule(t, ruleID)
+-
+-	// list security group rule
+-	listSecRules(t)
+-
+-	// get security group rule
+-	getSecRule(t, ruleID)
 -}
 -
--func ExampleClient_ListenEvents() {
--	client, err := docker.NewClient("http://localhost:4243")
--	if err != nil {
--		log.Fatal(err)
--	}
+-func createSecGroup(t *testing.T) string {
+-	sg, err := groups.Create(base.Client, groups.CreateOpts{
+-		Name:        "new-webservers",
+-		Description: "security group for webservers",
+-	}).Extract()
 -
--	listener := make(chan *docker.APIEvents)
--	err = client.AddEventListener(listener)
--	if err != nil {
--		log.Fatal(err)
--	}
+-	th.AssertNoErr(t, err)
 -
--	defer func() {
+-	t.Logf("Created security group %s", sg.ID)
 -
--		err = client.RemoveEventListener(listener)
+-	return sg.ID
+-}
+-
+-func listSecGroups(t *testing.T) {
+-	err := groups.List(base.Client, groups.ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		list, err := groups.ExtractGroups(page)
 -		if err != nil {
--			log.Fatal(err)
+-			t.Errorf("Failed to extract secgroups: %v", err)
+-			return false, err
 -		}
 -
--	}()
+-		for _, sg := range list {
+-			t.Logf("Listing security group: ID [%s] Name [%s]", sg.ID, sg.Name)
+-		}
 -
--	timeout := time.After(1 * time.Second)
+-		return true, nil
+-	})
 -
--	for {
--		select {
--		case msg := <-listener:
--			log.Println(msg)
--		case <-timeout:
--			break
--		}
--	}
+-	th.AssertNoErr(t, err)
+-}
 -
+-func getSecGroup(t *testing.T, id string) {
+-	sg, err := groups.Get(base.Client, id).Extract()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Getting security group: ID [%s] Name [%s] Description [%s]", sg.ID, sg.Name, sg.Description)
 -}
 -
--func ExampleEnv_Map() {
--	e := docker.Env([]string{"A=1", "B=2", "C=3"})
--	envs := e.Map()
--	for k, v := range envs {
--		fmt.Printf("%s=%q\n", k, v)
+-func createPort(t *testing.T, groupID string) (string, string) {
+-	n, err := networks.Create(base.Client, networks.CreateOpts{Name: "tmp_network"}).Extract()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Created network %s", n.ID)
+-
+-	opts := ports.CreateOpts{
+-		NetworkID:      n.ID,
+-		Name:           "my_port",
+-		SecurityGroups: []string{groupID},
 -	}
+-	p, err := ports.Create(base.Client, opts).Extract()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Created port %s with security group %s", p.ID, groupID)
+-
+-	return n.ID, p.ID
 -}
 -
--func ExampleEnv_SetJSON() {
--	type Person struct {
--		Name string
--		Age  int
--	}
--	p := Person{Name: "Gopher", Age: 4}
--	var e docker.Env
--	err := e.SetJSON("person", p)
--	if err != nil {
--		log.Fatal(err)
--	}
+-func deleteSecGroup(t *testing.T, groupID string) {
+-	res := groups.Delete(base.Client, groupID)
+-	th.AssertNoErr(t, res.Err)
+-	t.Logf("Deleted security group %s", groupID)
 -}
 -
--func ExampleEnv_GetJSON() {
--	type Person struct {
--		Name string
--		Age  int
--	}
--	p := Person{Name: "Gopher", Age: 4}
--	var e docker.Env
--	e.Set("person", `{"name":"Gopher","age":4}`)
--	err := e.GetJSON("person", &p)
--	if err != nil {
--		log.Fatal(err)
--	}
+-func createSecRule(t *testing.T, groupID string) string {
+-	r, err := rules.Create(base.Client, rules.CreateOpts{
+-		Direction:    "ingress",
+-		PortRangeMin: 80,
+-		EtherType:    "IPv4",
+-		PortRangeMax: 80,
+-		Protocol:     "tcp",
+-		SecGroupID:   groupID,
+-	}).Extract()
+-
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Created security group rule %s", r.ID)
+-
+-	return r.ID
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/exec.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/exec.go
+-
+-func listSecRules(t *testing.T) {
+-	err := rules.List(base.Client, rules.ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		list, err := rules.ExtractRules(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract sec rules: %v", err)
+-			return false, err
+-		}
+-
+-		for _, r := range list {
+-			t.Logf("Listing security rule: ID [%s]", r.ID)
+-		}
+-
+-		return true, nil
+-	})
+-
+-	th.AssertNoErr(t, err)
+-}
+-
+-func getSecRule(t *testing.T, id string) {
+-	r, err := rules.Get(base.Client, id).Extract()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Getting security rule: ID [%s] Direction [%s] EtherType [%s] Protocol [%s]",
+-		r.ID, r.Direction, r.EtherType, r.Protocol)
+-}
+-
+-func deleteSecRule(t *testing.T, id string) {
+-	res := rules.Delete(base.Client, id)
+-	th.AssertNoErr(t, res.Err)
+-	t.Logf("Deleted security rule %s", id)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/network_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/network_test.go
 deleted file mode 100644
-index 62a0a80..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/exec.go
+index be8a3a1..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/network_test.go
 +++ /dev/null
-@@ -1,126 +0,0 @@
--// Copyright 2014 go-dockerclient authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the LICENSE file.
--
--// Docs can currently be found at https://github.com/docker/docker/blob/master/docs/sources/reference/api/docker_remote_api_v1.15.md#exec-create
+@@ -1,68 +0,0 @@
+-// +build acceptance networking
 -
--package docker
+-package v2
 -
 -import (
--	"encoding/json"
--	"fmt"
--	"io"
--	"net/http"
--	"net/url"
 -	"strconv"
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/networks"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--// CreateExecOptions specify parameters to the CreateExecContainer function.
--//
--// See http://goo.gl/8izrzI for more details
--type CreateExecOptions struct {
--	AttachStdin  bool     `json:"AttachStdin,omitempty" yaml:"AttachStdin,omitempty"`
--	AttachStdout bool     `json:"AttachStdout,omitempty" yaml:"AttachStdout,omitempty"`
--	AttachStderr bool     `json:"AttachStderr,omitempty" yaml:"AttachStderr,omitempty"`
--	Tty          bool     `json:"Tty,omitempty" yaml:"Tty,omitempty"`
--	Cmd          []string `json:"Cmd,omitempty" yaml:"Cmd,omitempty"`
--	Container    string   `json:"Container,omitempty" yaml:"Container,omitempty"`
--}
+-func TestNetworkCRUDOperations(t *testing.T) {
+-	Setup(t)
+-	defer Teardown()
 -
--// StartExecOptions specify parameters to the StartExecContainer function.
--//
--// See http://goo.gl/JW8Lxl for more details
--type StartExecOptions struct {
--	Detach bool `json:"Detach,omitempty" yaml:"Detach,omitempty"`
+-	// Create a network
+-	n, err := networks.Create(Client, networks.CreateOpts{Name: "sample_network", AdminStateUp: networks.Up}).Extract()
+-	th.AssertNoErr(t, err)
+-	defer networks.Delete(Client, n.ID)
+-	th.AssertEquals(t, n.Name, "sample_network")
+-	th.AssertEquals(t, n.AdminStateUp, true)
+-	networkID := n.ID
 -
--	Tty bool `json:"Tty,omitempty" yaml:"Tty,omitempty"`
+-	// List networks
+-	pager := networks.List(Client, networks.ListOpts{Limit: 2})
+-	err = pager.EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page ---")
 -
--	InputStream  io.Reader `qs:"-"`
--	OutputStream io.Writer `qs:"-"`
--	ErrorStream  io.Writer `qs:"-"`
+-		networkList, err := networks.ExtractNetworks(page)
+-		th.AssertNoErr(t, err)
 -
--	// Use raw terminal? Usually true when the container contains a TTY.
--	RawTerminal bool `qs:"-"`
+-		for _, n := range networkList {
+-			t.Logf("Network: ID [%s] Name [%s] Status [%s] Is shared? [%s]",
+-				n.ID, n.Name, n.Status, strconv.FormatBool(n.Shared))
+-		}
 -
--	// If set, after a successful connect, a sentinel will be sent and then the
--	// client will block on receive before continuing.
--	//
--	// It must be an unbuffered channel. Using a buffered channel can lead
--	// to unexpected behavior.
--	Success chan struct{} `json:"-"`
+-		return true, nil
+-	})
+-	th.CheckNoErr(t, err)
+-
+-	// Get a network
+-	if networkID == "" {
+-		t.Fatalf("In order to retrieve a network, the NetworkID must be set")
+-	}
+-	n, err = networks.Get(Client, networkID).Extract()
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, n.Status, "ACTIVE")
+-	th.AssertDeepEquals(t, n.Subnets, []string{})
+-	th.AssertEquals(t, n.Name, "sample_network")
+-	th.AssertEquals(t, n.AdminStateUp, true)
+-	th.AssertEquals(t, n.Shared, false)
+-	th.AssertEquals(t, n.ID, networkID)
+-
+-	// Update network
+-	n, err = networks.Update(Client, networkID, networks.UpdateOpts{Name: "new_network_name"}).Extract()
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, n.Name, "new_network_name")
+-
+-	// Delete network
+-	res := networks.Delete(Client, networkID)
+-	th.AssertNoErr(t, res.Err)
 -}
 -
--type Exec struct {
--	Id string `json:"Id,omitempty" yaml:"Id,omitempty"`
+-func TestCreateMultipleNetworks(t *testing.T) {
+-	//networks.CreateMany()
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/pkg.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/pkg.go
+deleted file mode 100644
+index 5ec3cc8..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/pkg.go
++++ /dev/null
+@@ -1 +0,0 @@
+-package v2
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/port_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/port_test.go
+deleted file mode 100644
+index 7f22dbd..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/port_test.go
++++ /dev/null
+@@ -1,117 +0,0 @@
+-// +build acceptance networking
 -
--// CreateExec sets up an exec instance in a running container `id`, returning the exec
--// instance, or an error in case of failure.
--//
--// See http://goo.gl/8izrzI for more details
--func (c *Client) CreateExec(opts CreateExecOptions) (*Exec, error) {
--	path := fmt.Sprintf("/containers/%s/exec", opts.Container)
--	body, status, err := c.do("POST", path, opts)
--	if status == http.StatusNotFound {
--		return nil, &NoSuchContainer{ID: opts.Container}
--	}
--	if err != nil {
--		return nil, err
--	}
--	var exec Exec
--	err = json.Unmarshal(body, &exec)
--	if err != nil {
--		return nil, err
+-package v2
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/networks"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/ports"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/subnets"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestPortCRUD(t *testing.T) {
+-	Setup(t)
+-	defer Teardown()
+-
+-	// Setup network
+-	t.Log("Setting up network")
+-	networkID, err := createNetwork()
+-	th.AssertNoErr(t, err)
+-	defer networks.Delete(Client, networkID)
+-
+-	// Setup subnet
+-	t.Logf("Setting up subnet on network %s", networkID)
+-	subnetID, err := createSubnet(networkID)
+-	th.AssertNoErr(t, err)
+-	defer subnets.Delete(Client, subnetID)
+-
+-	// Create port
+-	t.Logf("Create port based on subnet %s", subnetID)
+-	portID := createPort(t, networkID, subnetID)
+-
+-	// List ports
+-	t.Logf("Listing all ports")
+-	listPorts(t)
+-
+-	// Get port
+-	if portID == "" {
+-		t.Fatalf("In order to retrieve a port, the portID must be set")
 -	}
+-	p, err := ports.Get(Client, portID).Extract()
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, p.ID, portID)
 -
--	return &exec, nil
+-	// Update port
+-	p, err = ports.Update(Client, portID, ports.UpdateOpts{Name: "new_port_name"}).Extract()
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, p.Name, "new_port_name")
+-
+-	// Delete port
+-	res := ports.Delete(Client, portID)
+-	th.AssertNoErr(t, res.Err)
 -}
 -
--// Starts a previously set up exec instance id. If opts.Detach is true, it returns
--// after starting the exec command. Otherwise, it sets up an interactive session
--// with the exec command.
--//
--// See http://goo.gl/JW8Lxl for more details
--func (c *Client) StartExec(id string, opts StartExecOptions) error {
--	if id == "" {
--		return &NoSuchExec{ID: id}
+-func createPort(t *testing.T, networkID, subnetID string) string {
+-	enable := false
+-	opts := ports.CreateOpts{
+-		NetworkID:    networkID,
+-		Name:         "my_port",
+-		AdminStateUp: &enable,
+-		FixedIPs:     []ports.IP{ports.IP{SubnetID: subnetID}},
 -	}
+-	p, err := ports.Create(Client, opts).Extract()
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, p.NetworkID, networkID)
+-	th.AssertEquals(t, p.Name, "my_port")
+-	th.AssertEquals(t, p.AdminStateUp, false)
 -
--	path := fmt.Sprintf("/exec/%s/start", id)
+-	return p.ID
+-}
 -
--	if opts.Detach {
--		_, status, err := c.do("POST", path, opts)
--		if status == http.StatusNotFound {
--			return &NoSuchExec{ID: id}
--		}
--		if err != nil {
--			return err
+-func listPorts(t *testing.T) {
+-	count := 0
+-	pager := ports.List(Client, ports.ListOpts{})
+-	err := pager.EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		t.Logf("--- Page ---")
+-
+-		portList, err := ports.ExtractPorts(page)
+-		th.AssertNoErr(t, err)
+-
+-		for _, p := range portList {
+-			t.Logf("Port: ID [%s] Name [%s] Status [%d] MAC addr [%s] Fixed IPs [%#v] Security groups [%#v]",
+-				p.ID, p.Name, p.Status, p.MACAddress, p.FixedIPs, p.SecurityGroups)
 -		}
--		return nil
--	}
 -
--	return c.hijack("POST", path, opts.Success, opts.RawTerminal, opts.InputStream, opts.ErrorStream, opts.OutputStream, opts)
--}
+-		return true, nil
+-	})
 -
--// Resizes the tty session used by the exec command id. This API is valid only
--// if Tty was specified as part of creating and starting the exec command.
--//
--// See http://goo.gl/YDSx1f for more details
--func (c *Client) ResizeExecTTY(id string, height, width int) error {
--	params := make(url.Values)
--	params.Set("h", strconv.Itoa(height))
--	params.Set("w", strconv.Itoa(width))
+-	th.CheckNoErr(t, err)
 -
--	path := fmt.Sprintf("/exec/%s/resize?%s", id, params.Encode())
--	_, _, err := c.do("POST", path, nil)
--	return err
+-	if count == 0 {
+-		t.Logf("No pages were iterated over when listing ports")
+-	}
 -}
 -
--// NoSuchExec is the error returned when a given exec instance does not exist.
--type NoSuchExec struct {
--	ID string
+-func createNetwork() (string, error) {
+-	res, err := networks.Create(Client, networks.CreateOpts{Name: "tmp_network", AdminStateUp: networks.Up}).Extract()
+-	return res.ID, err
 -}
 -
--func (err *NoSuchExec) Error() string {
--	return "No such exec instance: " + err.ID
+-func createSubnet(networkID string) (string, error) {
+-	s, err := subnets.Create(Client, subnets.CreateOpts{
+-		NetworkID:  networkID,
+-		CIDR:       "192.168.199.0/24",
+-		IPVersion:  subnets.IPv4,
+-		Name:       "my_subnet",
+-		EnableDHCP: subnets.Down,
+-	}).Extract()
+-	return s.ID, err
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/exec_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/exec_test.go
+-
+-func TestPortBatchCreate(t *testing.T) {
+-	// todo
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/subnet_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/subnet_test.go
 deleted file mode 100644
-index 70fa64b..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/exec_test.go
+index 097a303..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/networking/v2/subnet_test.go
 +++ /dev/null
-@@ -1,128 +0,0 @@
--// Copyright 2014 go-dockerclient authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the LICENSE file.
+@@ -1,86 +0,0 @@
+-// +build acceptance networking
 -
--package docker
+-package v2
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/networks"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/subnets"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestList(t *testing.T) {
+-	Setup(t)
+-	defer Teardown()
+-
+-	pager := subnets.List(Client, subnets.ListOpts{Limit: 2})
+-	err := pager.EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page ---")
+-
+-		subnetList, err := subnets.ExtractSubnets(page)
+-		th.AssertNoErr(t, err)
+-
+-		for _, s := range subnetList {
+-			t.Logf("Subnet: ID [%s] Name [%s] IP Version [%d] CIDR [%s] GatewayIP [%s]",
+-				s.ID, s.Name, s.IPVersion, s.CIDR, s.GatewayIP)
+-		}
+-
+-		return true, nil
+-	})
+-	th.CheckNoErr(t, err)
+-}
+-
+-func TestCRUD(t *testing.T) {
+-	Setup(t)
+-	defer Teardown()
+-
+-	// Setup network
+-	t.Log("Setting up network")
+-	n, err := networks.Create(Client, networks.CreateOpts{Name: "tmp_network", AdminStateUp: networks.Up}).Extract()
+-	th.AssertNoErr(t, err)
+-	networkID := n.ID
+-	defer networks.Delete(Client, networkID)
+-
+-	// Create subnet
+-	t.Log("Create subnet")
+-	enable := false
+-	opts := subnets.CreateOpts{
+-		NetworkID:  networkID,
+-		CIDR:       "192.168.199.0/24",
+-		IPVersion:  subnets.IPv4,
+-		Name:       "my_subnet",
+-		EnableDHCP: &enable,
+-	}
+-	s, err := subnets.Create(Client, opts).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, s.NetworkID, networkID)
+-	th.AssertEquals(t, s.CIDR, "192.168.199.0/24")
+-	th.AssertEquals(t, s.IPVersion, 4)
+-	th.AssertEquals(t, s.Name, "my_subnet")
+-	th.AssertEquals(t, s.EnableDHCP, false)
+-	subnetID := s.ID
+-
+-	// Get subnet
+-	t.Log("Getting subnet")
+-	s, err = subnets.Get(Client, subnetID).Extract()
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, s.ID, subnetID)
+-
+-	// Update subnet
+-	t.Log("Update subnet")
+-	s, err = subnets.Update(Client, subnetID, subnets.UpdateOpts{Name: "new_subnet_name"}).Extract()
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, s.Name, "new_subnet_name")
+-
+-	// Delete subnet
+-	t.Log("Delete subnet")
+-	res := subnets.Delete(Client, subnetID)
+-	th.AssertNoErr(t, res.Err)
+-}
+-
+-func TestBatchCreate(t *testing.T) {
+-	// todo
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/objectstorage/v1/accounts_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/objectstorage/v1/accounts_test.go
+deleted file mode 100644
+index f7c01a7..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/objectstorage/v1/accounts_test.go
++++ /dev/null
+@@ -1,44 +0,0 @@
+-// +build acceptance
+-
+-package v1
 -
 -import (
--	"bytes"
--	"encoding/json"
--	"net/http"
--	"net/http/httptest"
--	"net/url"
 -	"strings"
 -	"testing"
+-
+-	"github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts"
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--func TestExecCreate(t *testing.T) {
--	jsonContainer := `{"Id": "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"}`
--	var expected struct{ Id string }
--	err := json.Unmarshal([]byte(jsonContainer), &expected)
--	if err != nil {
--		t.Fatal(err)
--	}
--	fakeRT := &FakeRoundTripper{message: jsonContainer, status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	config := CreateExecOptions{
--		Container:    "test",
--		AttachStdin:  true,
--		AttachStdout: true,
--		AttachStderr: false,
--		Tty:          false,
--		Cmd:          []string{"touch", "/tmp/file"},
--	}
--	execObj, err := client.CreateExec(config)
--	if err != nil {
--		t.Fatal(err)
--	}
--	expectedId := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
--	if execObj.Id != expectedId {
--		t.Errorf("ExecCreate: wrong ID. Want %q. Got %q.", expectedId, execObj.Id)
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "POST" {
--		t.Errorf("ExecCreate: wrong HTTP method. Want %q. Got %q.", "POST", req.Method)
--	}
--	expectedURL, _ := url.Parse(client.getURL("/containers/test/exec"))
--	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
--		t.Errorf("ExecCreate: Wrong path in request. Want %q. Got %q.", expectedURL.Path, gotPath)
--	}
--	var gotBody struct{ Id string }
--	err = json.NewDecoder(req.Body).Decode(&gotBody)
--	if err != nil {
--		t.Fatal(err)
--	}
--}
+-func TestAccounts(t *testing.T) {
+-	// Create a provider client for making the HTTP requests.
+-	// See common.go in this directory for more information.
+-	client := newClient(t)
 -
--func TestExecStartDetached(t *testing.T) {
--	execId := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
--	fakeRT := &FakeRoundTripper{status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	config := StartExecOptions{
--		Detach: true,
--	}
--	err := client.StartExec(execId, config)
--	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "POST" {
--		t.Errorf("ExecStart: wrong HTTP method. Want %q. Got %q.", "POST", req.Method)
--	}
--	expectedURL, _ := url.Parse(client.getURL("/exec/" + execId + "/start"))
--	if gotPath := req.URL.Path; gotPath != expectedURL.Path {
--		t.Errorf("ExecCreate: Wrong path in request. Want %q. Got %q.", expectedURL.Path, gotPath)
--	}
--	t.Log(req.Body)
--	var gotBody struct{ Detach bool }
--	err = json.NewDecoder(req.Body).Decode(&gotBody)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if !gotBody.Detach {
--		t.Fatal("Expected Detach in StartExecOptions to be true")
--	}
--}
+-	// Update an account's metadata.
+-	updateres := accounts.Update(client, accounts.UpdateOpts{Metadata: metadata})
+-	th.AssertNoErr(t, updateres.Err)
 -
--func TestExecStartAndAttach(t *testing.T) {
--	var reader = strings.NewReader("send value")
--	var req http.Request
--	server := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
--		w.Write([]byte{1, 0, 0, 0, 0, 0, 0, 5})
--		w.Write([]byte("hello"))
--		req = *r
--	}))
--	defer server.Close()
--	client, _ := NewClient(server.URL)
--	client.SkipServerVersionCheck = true
--	var stdout, stderr bytes.Buffer
--	success := make(chan struct{})
--	execId := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
--	opts := StartExecOptions{
--		OutputStream: &stdout,
--		ErrorStream:  &stderr,
--		InputStream:  reader,
--		RawTerminal:  true,
--		Success:      success,
--	}
--	go client.StartExec(execId, opts)
--	<-success
--}
+-	// Defer the deletion of the metadata set above.
+-	defer func() {
+-		tempMap := make(map[string]string)
+-		for k := range metadata {
+-			tempMap[k] = ""
+-		}
+-		updateres = accounts.Update(client, accounts.UpdateOpts{Metadata: tempMap})
+-		th.AssertNoErr(t, updateres.Err)
+-	}()
 -
--func TestExecResize(t *testing.T) {
--	execId := "4fa6e0f0c6786287e131c3852c58a2e01cc697a68231826813597e4994f1d6e2"
--	fakeRT := &FakeRoundTripper{status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	err := client.ResizeExecTTY(execId, 10, 20)
--	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "POST" {
--		t.Errorf("ExecStart: wrong HTTP method. Want %q. Got %q.", "POST", req.Method)
--	}
--	expectedURL, _ := url.Parse(client.getURL("/exec/" + execId + "/resize?h=10&w=20"))
--	if gotPath := req.URL.RequestURI(); gotPath != expectedURL.RequestURI() {
--		t.Errorf("ExecCreate: Wrong path in request. Want %q. Got %q.", expectedURL.Path, gotPath)
+-	// Retrieve account metadata.
+-	getres := accounts.Get(client, nil)
+-	th.AssertNoErr(t, getres.Err)
+-	// Extract the custom metadata from the 'Get' response.
+-	am, err := getres.ExtractMetadata()
+-	th.AssertNoErr(t, err)
+-	for k := range metadata {
+-		if am[k] != metadata[strings.Title(k)] {
+-			t.Errorf("Expected custom metadata with key: %s", k)
+-			return
+-		}
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/image.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/image.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/objectstorage/v1/common.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/objectstorage/v1/common.go
 deleted file mode 100644
-index e1fbb23..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/image.go
+index 1eac681..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/objectstorage/v1/common.go
 +++ /dev/null
-@@ -1,417 +0,0 @@
--// Copyright 2014 go-dockerclient authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the LICENSE file.
+@@ -1,28 +0,0 @@
+-// +build acceptance
 -
--package docker
+-package v1
 -
 -import (
--	"bytes"
--	"encoding/base64"
--	"encoding/json"
--	"errors"
--	"fmt"
--	"io"
--	"io/ioutil"
--	"net/http"
--	"net/url"
 -	"os"
--	"time"
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/openstack"
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--// APIImages represent an image returned in the ListImages call.
--type APIImages struct {
--	ID          string   `json:"Id" yaml:"Id"`
--	RepoTags    []string `json:"RepoTags,omitempty" yaml:"RepoTags,omitempty"`
--	Created     int64    `json:"Created,omitempty" yaml:"Created,omitempty"`
--	Size        int64    `json:"Size,omitempty" yaml:"Size,omitempty"`
--	VirtualSize int64    `json:"VirtualSize,omitempty" yaml:"VirtualSize,omitempty"`
--	ParentId    string   `json:"ParentId,omitempty" yaml:"ParentId,omitempty"`
--}
+-var metadata = map[string]string{"gopher": "cloud"}
 -
--type Image struct {
--	ID              string    `json:"Id" yaml:"Id"`
--	Parent          string    `json:"Parent,omitempty" yaml:"Parent,omitempty"`
--	Comment         string    `json:"Comment,omitempty" yaml:"Comment,omitempty"`
--	Created         time.Time `json:"Created,omitempty" yaml:"Created,omitempty"`
--	Container       string    `json:"Container,omitempty" yaml:"Container,omitempty"`
--	ContainerConfig Config    `json:"ContainerConfig,omitempty" yaml:"ContainerConfig,omitempty"`
--	DockerVersion   string    `json:"DockerVersion,omitempty" yaml:"DockerVersion,omitempty"`
--	Author          string    `json:"Author,omitempty" yaml:"Author,omitempty"`
--	Config          *Config   `json:"Config,omitempty" yaml:"Config,omitempty"`
--	Architecture    string    `json:"Architecture,omitempty" yaml:"Architecture,omitempty"`
--	Size            int64     `json:"Size,omitempty" yaml:"Size,omitempty"`
+-func newClient(t *testing.T) *gophercloud.ServiceClient {
+-	ao, err := openstack.AuthOptionsFromEnv()
+-	th.AssertNoErr(t, err)
+-
+-	client, err := openstack.AuthenticatedClient(ao)
+-	th.AssertNoErr(t, err)
+-
+-	c, err := openstack.NewObjectStorageV1(client, gophercloud.EndpointOpts{
+-		Region: os.Getenv("OS_REGION_NAME"),
+-	})
+-	th.AssertNoErr(t, err)
+-	return c
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/objectstorage/v1/containers_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/objectstorage/v1/containers_test.go
+deleted file mode 100644
+index d6832f1..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/objectstorage/v1/containers_test.go
++++ /dev/null
+@@ -1,89 +0,0 @@
+-// +build acceptance
+-
+-package v1
+-
+-import (
+-	"strings"
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/acceptance/tools"
+-	"github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-// numContainers is the number of containers to create for testing.
+-var numContainers = 2
+-
+-func TestContainers(t *testing.T) {
+-	// Create a new client to execute the HTTP requests. See common.go for newClient body.
+-	client := newClient(t)
+-
+-	// Create a slice of random container names.
+-	cNames := make([]string, numContainers)
+-	for i := 0; i < numContainers; i++ {
+-		cNames[i] = tools.RandomString("gophercloud-test-container-", 8)
+-	}
+-
+-	// Create numContainers containers.
+-	for i := 0; i < len(cNames); i++ {
+-		res := containers.Create(client, cNames[i], nil)
+-		th.AssertNoErr(t, res.Err)
+-	}
+-	// Delete the numContainers containers after function completion.
+-	defer func() {
+-		for i := 0; i < len(cNames); i++ {
+-			res := containers.Delete(client, cNames[i])
+-			th.AssertNoErr(t, res.Err)
+-		}
+-	}()
+-
+-	// List the numContainer names that were just created. To just list those,
+-	// the 'prefix' parameter is used.
+-	err := containers.List(client, &containers.ListOpts{Full: true, Prefix: "gophercloud-test-container-"}).EachPage(func(page pagination.Page) (bool, error) {
+-		containerList, err := containers.ExtractInfo(page)
+-		th.AssertNoErr(t, err)
+-
+-		for _, n := range containerList {
+-			t.Logf("Container: Name [%s] Count [%d] Bytes [%d]",
+-				n.Name, n.Count, n.Bytes)
+-		}
+-
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
 -
--// ImageHistory represent a layer in an image's history returned by the
--// ImageHistory call.
--type ImageHistory struct {
--	ID        string   `json:"Id" yaml:"Id"`
--	Tags      []string `json:"Tags,omitempty" yaml:"Tags,omitempty"`
--	Created   int64    `json:"Created,omitempty" yaml:"Created,omitempty"`
--	CreatedBy string   `json:"CreatedBy,omitempty" yaml:"CreatedBy,omitempty"`
--	Size      int64    `json:"Size,omitempty" yaml:"Size,omitempty"`
--}
+-	// List the info for the numContainer containers that were created.
+-	err = containers.List(client, &containers.ListOpts{Full: false, Prefix: "gophercloud-test-container-"}).EachPage(func(page pagination.Page) (bool, error) {
+-		containerList, err := containers.ExtractNames(page)
+-		th.AssertNoErr(t, err)
+-		for _, n := range containerList {
+-			t.Logf("Container: Name [%s]", n)
+-		}
 -
--type ImagePre012 struct {
--	ID              string    `json:"id"`
--	Parent          string    `json:"parent,omitempty"`
--	Comment         string    `json:"comment,omitempty"`
--	Created         time.Time `json:"created"`
--	Container       string    `json:"container,omitempty"`
--	ContainerConfig Config    `json:"container_config,omitempty"`
--	DockerVersion   string    `json:"docker_version,omitempty"`
--	Author          string    `json:"author,omitempty"`
--	Config          *Config   `json:"config,omitempty"`
--	Architecture    string    `json:"architecture,omitempty"`
--	Size            int64     `json:"size,omitempty"`
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-
+-	// Update one of the numContainer container metadata.
+-	updateres := containers.Update(client, cNames[0], &containers.UpdateOpts{Metadata: metadata})
+-	th.AssertNoErr(t, updateres.Err)
+-	// After the tests are done, delete the metadata that was set.
+-	defer func() {
+-		tempMap := make(map[string]string)
+-		for k := range metadata {
+-			tempMap[k] = ""
+-		}
+-		res := containers.Update(client, cNames[0], &containers.UpdateOpts{Metadata: tempMap})
+-		th.AssertNoErr(t, res.Err)
+-	}()
+-
+-	// Retrieve a container's metadata.
+-	cm, err := containers.Get(client, cNames[0]).ExtractMetadata()
+-	th.AssertNoErr(t, err)
+-	for k := range metadata {
+-		if cm[k] != metadata[strings.Title(k)] {
+-			t.Errorf("Expected custom metadata with key: %s", k)
+-		}
+-	}
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/objectstorage/v1/objects_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/objectstorage/v1/objects_test.go
+deleted file mode 100644
+index a8de338..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/objectstorage/v1/objects_test.go
++++ /dev/null
+@@ -1,119 +0,0 @@
+-// +build acceptance
 -
--var (
--	// ErrNoSuchImage is the error returned when the image does not exist.
--	ErrNoSuchImage = errors.New("no such image")
+-package v1
 -
--	// ErrMissingRepo is the error returned when the remote repository is
--	// missing.
--	ErrMissingRepo = errors.New("missing remote repository e.g. 'github.com/user/repo'")
+-import (
+-	"bytes"
+-	"strings"
+-	"testing"
 -
--	// ErrMissingOutputStream is the error returned when no output stream
--	// is provided to some calls, like BuildImage.
--	ErrMissingOutputStream = errors.New("missing output stream")
+-	"github.com/rackspace/gophercloud/acceptance/tools"
+-	"github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers"
+-	"github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--// ListImages returns the list of available images in the server.
--//
--// See http://goo.gl/VmcR6v for more details.
--func (c *Client) ListImages(all bool) ([]APIImages, error) {
--	path := "/images/json?all="
--	if all {
--		path += "1"
--	} else {
--		path += "0"
+-// numObjects is the number of objects to create for testing.
+-var numObjects = 2
+-
+-func TestObjects(t *testing.T) {
+-	// Create a provider client for executing the HTTP request.
+-	// See common.go for more information.
+-	client := newClient(t)
+-
+-	// Make a slice of length numObjects to hold the random object names.
+-	oNames := make([]string, numObjects)
+-	for i := 0; i < len(oNames); i++ {
+-		oNames[i] = tools.RandomString("test-object-", 8)
 -	}
--	body, _, err := c.do("GET", path, nil)
--	if err != nil {
--		return nil, err
+-
+-	// Create a container to hold the test objects.
+-	cName := tools.RandomString("test-container-", 8)
+-	header, err := containers.Create(client, cName, nil).ExtractHeader()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Create object headers: %+v\n", header)
+-
+-	// Defer deletion of the container until after testing.
+-	defer func() {
+-		res := containers.Delete(client, cName)
+-		th.AssertNoErr(t, res.Err)
+-	}()
+-
+-	// Create a slice of buffers to hold the test object content.
+-	oContents := make([]*bytes.Buffer, numObjects)
+-	for i := 0; i < numObjects; i++ {
+-		oContents[i] = bytes.NewBuffer([]byte(tools.RandomString("", 10)))
+-		res := objects.Create(client, cName, oNames[i], oContents[i], nil)
+-		th.AssertNoErr(t, res.Err)
 -	}
--	var images []APIImages
--	err = json.Unmarshal(body, &images)
--	if err != nil {
--		return nil, err
+-	// Delete the objects after testing.
+-	defer func() {
+-		for i := 0; i < numObjects; i++ {
+-			res := objects.Delete(client, cName, oNames[i], nil)
+-			th.AssertNoErr(t, res.Err)
+-		}
+-	}()
+-
+-	ons := make([]string, 0, len(oNames))
+-	err = objects.List(client, cName, &objects.ListOpts{Full: false, Prefix: "test-object-"}).EachPage(func(page pagination.Page) (bool, error) {
+-		names, err := objects.ExtractNames(page)
+-		th.AssertNoErr(t, err)
+-		ons = append(ons, names...)
+-
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, len(ons), len(oNames))
+-
+-	ois := make([]objects.Object, 0, len(oNames))
+-	err = objects.List(client, cName, &objects.ListOpts{Full: true, Prefix: "test-object-"}).EachPage(func(page pagination.Page) (bool, error) {
+-		info, err := objects.ExtractInfo(page)
+-		th.AssertNoErr(t, err)
+-
+-		ois = append(ois, info...)
+-
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, len(ois), len(oNames))
+-
+-	// Copy the contents of one object to another.
+-	copyres := objects.Copy(client, cName, oNames[0], &objects.CopyOpts{Destination: cName + "/" + oNames[1]})
+-	th.AssertNoErr(t, copyres.Err)
+-
+-	// Download one of the objects that was created above.
+-	o1Content, err := objects.Download(client, cName, oNames[0], nil).ExtractContent()
+-	th.AssertNoErr(t, err)
+-
+-	// Download the another object that was create above.
+-	o2Content, err := objects.Download(client, cName, oNames[1], nil).ExtractContent()
+-	th.AssertNoErr(t, err)
+-
+-	// Compare the two object's contents to test that the copy worked.
+-	th.AssertEquals(t, string(o2Content), string(o1Content))
+-
+-	// Update an object's metadata.
+-	updateres := objects.Update(client, cName, oNames[0], &objects.UpdateOpts{Metadata: metadata})
+-	th.AssertNoErr(t, updateres.Err)
+-
+-	// Delete the object's metadata after testing.
+-	defer func() {
+-		tempMap := make(map[string]string)
+-		for k := range metadata {
+-			tempMap[k] = ""
+-		}
+-		res := objects.Update(client, cName, oNames[0], &objects.UpdateOpts{Metadata: tempMap})
+-		th.AssertNoErr(t, res.Err)
+-	}()
+-
+-	// Retrieve an object's metadata.
+-	om, err := objects.Get(client, cName, oNames[0], nil).ExtractMetadata()
+-	th.AssertNoErr(t, err)
+-	for k := range metadata {
+-		if om[k] != metadata[strings.Title(k)] {
+-			t.Errorf("Expected custom metadata with key: %s", k)
+-			return
+-		}
 -	}
--	return images, nil
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/pkg.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/pkg.go
+deleted file mode 100644
+index 3a8ecdb..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/openstack/pkg.go
++++ /dev/null
+@@ -1,4 +0,0 @@
+-// +build acceptance
 -
--// ImageHistory returns the history of the image by its name or ID.
--//
--// See http://goo.gl/2oJmNs for more details.
--func (c *Client) ImageHistory(name string) ([]ImageHistory, error) {
--	body, status, err := c.do("GET", "/images/"+name+"/history", nil)
--	if status == http.StatusNotFound {
--		return nil, ErrNoSuchImage
--	}
+-package openstack
+-
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/blockstorage/v1/common.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/blockstorage/v1/common.go
+deleted file mode 100644
+index e9fdd99..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/blockstorage/v1/common.go
++++ /dev/null
+@@ -1,38 +0,0 @@
+-// +build acceptance
+-
+-package v1
+-
+-import (
+-	"os"
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/acceptance/tools"
+-	"github.com/rackspace/gophercloud/rackspace"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func newClient() (*gophercloud.ServiceClient, error) {
+-	opts, err := rackspace.AuthOptionsFromEnv()
 -	if err != nil {
 -		return nil, err
 -	}
--	var history []ImageHistory
--	err = json.Unmarshal(body, &history)
+-	opts = tools.OnlyRS(opts)
+-	region := os.Getenv("RS_REGION")
+-
+-	provider, err := rackspace.AuthenticatedClient(opts)
 -	if err != nil {
 -		return nil, err
 -	}
--	return history, nil
+-
+-	return rackspace.NewBlockStorageV1(provider, gophercloud.EndpointOpts{
+-		Region: region,
+-	})
 -}
 -
--// RemoveImage removes an image by its name or ID.
--//
--// See http://goo.gl/znj0wM for more details.
--func (c *Client) RemoveImage(name string) error {
--	_, status, err := c.do("DELETE", "/images/"+name, nil)
--	if status == http.StatusNotFound {
--		return ErrNoSuchImage
--	}
--	return err
+-func setup(t *testing.T) *gophercloud.ServiceClient {
+-	client, err := newClient()
+-	th.AssertNoErr(t, err)
+-
+-	return client
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/blockstorage/v1/snapshot_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/blockstorage/v1/snapshot_test.go
+deleted file mode 100644
+index 25b2cfe..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/blockstorage/v1/snapshot_test.go
++++ /dev/null
+@@ -1,82 +0,0 @@
+-// +build acceptance blockstorage snapshots
 -
--// InspectImage returns an image by its name or ID.
--//
--// See http://goo.gl/Q112NY for more details.
--func (c *Client) InspectImage(name string) (*Image, error) {
--	body, status, err := c.do("GET", "/images/"+name+"/json", nil)
--	if status == http.StatusNotFound {
--		return nil, ErrNoSuchImage
--	}
--	if err != nil {
--		return nil, err
--	}
+-package v1
 -
--	var image Image
+-import (
+-	"testing"
+-	"time"
 -
--	// if the caller elected to skip checking the server's version, assume it's the latest
--	if c.SkipServerVersionCheck || c.expectedApiVersion.GreaterThanOrEqualTo(apiVersion_1_12) {
--		err = json.Unmarshal(body, &image)
--		if err != nil {
--			return nil, err
--		}
--	} else {
--		var imagePre012 ImagePre012
--		err = json.Unmarshal(body, &imagePre012)
--		if err != nil {
--			return nil, err
--		}
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-	"github.com/rackspace/gophercloud/rackspace/blockstorage/v1/snapshots"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--		image.ID = imagePre012.ID
--		image.Parent = imagePre012.Parent
--		image.Comment = imagePre012.Comment
--		image.Created = imagePre012.Created
--		image.Container = imagePre012.Container
--		image.ContainerConfig = imagePre012.ContainerConfig
--		image.DockerVersion = imagePre012.DockerVersion
--		image.Author = imagePre012.Author
--		image.Config = imagePre012.Config
--		image.Architecture = imagePre012.Architecture
--		image.Size = imagePre012.Size
--	}
+-func TestSnapshots(t *testing.T) {
+-	client := setup(t)
+-	volID := testVolumeCreate(t, client)
 -
--	return &image, nil
--}
+-	t.Log("Creating snapshots")
+-	s := testSnapshotCreate(t, client, volID)
+-	id := s.ID
 -
--// PushImageOptions represents options to use in the PushImage method.
--//
--// See http://goo.gl/pN8A3P for more details.
--type PushImageOptions struct {
--	// Name of the image
--	Name string
+-	t.Log("Listing snapshots")
+-	testSnapshotList(t, client)
 -
--	// Tag of the image
--	Tag string
+-	t.Logf("Getting snapshot %s", id)
+-	testSnapshotGet(t, client, id)
 -
--	// Registry server to push the image
--	Registry string
+-	t.Logf("Updating snapshot %s", id)
+-	testSnapshotUpdate(t, client, id)
 -
--	OutputStream  io.Writer `qs:"-"`
--	RawJSONStream bool      `qs:"-"`
--}
+-	t.Logf("Deleting snapshot %s", id)
+-	testSnapshotDelete(t, client, id)
+-	s.WaitUntilDeleted(client, -1)
 -
--// AuthConfiguration represents authentication options to use in the PushImage
--// method. It represents the authentication in the Docker index server.
--type AuthConfiguration struct {
--	Username string `json:"username,omitempty"`
--	Password string `json:"password,omitempty"`
--	Email    string `json:"email,omitempty"`
+-	t.Logf("Deleting volume %s", volID)
+-	testVolumeDelete(t, client, volID)
 -}
 -
--// PushImage pushes an image to a remote registry, logging progress to w.
--//
--// An empty instance of AuthConfiguration may be used for unauthenticated
--// pushes.
--//
--// See http://goo.gl/pN8A3P for more details.
--func (c *Client) PushImage(opts PushImageOptions, auth AuthConfiguration) error {
--	if opts.Name == "" {
--		return ErrNoSuchImage
--	}
--	name := opts.Name
--	opts.Name = ""
--	path := "/images/" + name + "/push?" + queryString(&opts)
--	var headers = make(map[string]string)
--	var buf bytes.Buffer
--	json.NewEncoder(&buf).Encode(auth)
--
--	headers["X-Registry-Auth"] = base64.URLEncoding.EncodeToString(buf.Bytes())
+-func testSnapshotCreate(t *testing.T, client *gophercloud.ServiceClient, volID string) *snapshots.Snapshot {
+-	opts := snapshots.CreateOpts{VolumeID: volID, Name: "snapshot-001"}
+-	s, err := snapshots.Create(client, opts).Extract()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Created snapshot %s", s.ID)
 -
--	return c.stream("POST", path, true, opts.RawJSONStream, headers, nil, opts.OutputStream, nil)
--}
+-	t.Logf("Waiting for new snapshot to become available...")
+-	start := time.Now().Second()
+-	s.WaitUntilComplete(client, -1)
+-	t.Logf("Snapshot completed after %ds", time.Now().Second()-start)
 -
--// PullImageOptions present the set of options available for pulling an image
--// from a registry.
--//
--// See http://goo.gl/ACyYNS for more details.
--type PullImageOptions struct {
--	Repository    string `qs:"fromImage"`
--	Registry      string
--	Tag           string
--	OutputStream  io.Writer `qs:"-"`
--	RawJSONStream bool      `qs:"-"`
+-	return s
 -}
 -
--// PullImage pulls an image from a remote registry, logging progress to w.
--//
--// See http://goo.gl/ACyYNS for more details.
--func (c *Client) PullImage(opts PullImageOptions, auth AuthConfiguration) error {
--	if opts.Repository == "" {
--		return ErrNoSuchImage
--	}
+-func testSnapshotList(t *testing.T, client *gophercloud.ServiceClient) {
+-	snapshots.List(client).EachPage(func(page pagination.Page) (bool, error) {
+-		sList, err := snapshots.ExtractSnapshots(page)
+-		th.AssertNoErr(t, err)
 -
--	var headers = make(map[string]string)
--	var buf bytes.Buffer
--	json.NewEncoder(&buf).Encode(auth)
--	headers["X-Registry-Auth"] = base64.URLEncoding.EncodeToString(buf.Bytes())
+-		for _, s := range sList {
+-			t.Logf("Snapshot: ID [%s] Name [%s] Volume ID [%s] Progress [%s] Created [%s]",
+-				s.ID, s.Name, s.VolumeID, s.Progress, s.CreatedAt)
+-		}
 -
--	return c.createImage(queryString(&opts), headers, nil, opts.OutputStream, opts.RawJSONStream)
+-		return true, nil
+-	})
 -}
 -
--func (c *Client) createImage(qs string, headers map[string]string, in io.Reader, w io.Writer, rawJSONStream bool) error {
--	path := "/images/create?" + qs
--	return c.stream("POST", path, true, rawJSONStream, headers, in, w, nil)
+-func testSnapshotGet(t *testing.T, client *gophercloud.ServiceClient, id string) {
+-	_, err := snapshots.Get(client, id).Extract()
+-	th.AssertNoErr(t, err)
 -}
 -
--// LoadImageOptions represents the options for LoadImage Docker API Call
--//
--// See http://goo.gl/Y8NNCq for more details.
--type LoadImageOptions struct {
--	InputStream io.Reader
+-func testSnapshotUpdate(t *testing.T, client *gophercloud.ServiceClient, id string) {
+-	_, err := snapshots.Update(client, id, snapshots.UpdateOpts{Name: "new_name"}).Extract()
+-	th.AssertNoErr(t, err)
 -}
 -
--// LoadImage imports a tarball docker image
--//
--// See http://goo.gl/Y8NNCq for more details.
--func (c *Client) LoadImage(opts LoadImageOptions) error {
--	return c.stream("POST", "/images/load", true, false, nil, opts.InputStream, nil, nil)
+-func testSnapshotDelete(t *testing.T, client *gophercloud.ServiceClient, id string) {
+-	res := snapshots.Delete(client, id)
+-	th.AssertNoErr(t, res.Err)
+-	t.Logf("Deleted snapshot %s", id)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/blockstorage/v1/volume_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/blockstorage/v1/volume_test.go
+deleted file mode 100644
+index f86f9ad..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/blockstorage/v1/volume_test.go
++++ /dev/null
+@@ -1,71 +0,0 @@
+-// +build acceptance blockstorage volumes
 -
--// ExportImageOptions represent the options for ExportImage Docker API call
--//
--// See http://goo.gl/mi6kvk for more details.
--type ExportImageOptions struct {
--	Name         string
--	OutputStream io.Writer
--}
+-package v1
 -
--// ExportImage exports an image (as a tar file) into the stream
--//
--// See http://goo.gl/mi6kvk for more details.
--func (c *Client) ExportImage(opts ExportImageOptions) error {
--	return c.stream("GET", fmt.Sprintf("/images/%s/get", opts.Name), true, false, nil, nil, opts.OutputStream, nil)
--}
+-import (
+-	"testing"
 -
--// ImportImageOptions present the set of informations available for importing
--// an image from a source file or the stdin.
--//
--// See http://goo.gl/PhBKnS for more details.
--type ImportImageOptions struct {
--	Repository string `qs:"repo"`
--	Source     string `qs:"fromSrc"`
--	Tag        string `qs:"tag"`
+-	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes"
+-	"github.com/rackspace/gophercloud/pagination"
+-	"github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumes"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--	InputStream  io.Reader `qs:"-"`
--	OutputStream io.Writer `qs:"-"`
--}
+-func TestVolumes(t *testing.T) {
+-	client := setup(t)
 -
--// ImportImage imports an image from a url, a file or stdin
--//
--// See http://goo.gl/PhBKnS for more details.
--func (c *Client) ImportImage(opts ImportImageOptions) error {
--	if opts.Repository == "" {
--		return ErrNoSuchImage
--	}
--	if opts.Source != "-" {
--		opts.InputStream = nil
--	}
--	if opts.Source != "-" && !isURL(opts.Source) {
--		f, err := os.Open(opts.Source)
--		if err != nil {
--			return err
--		}
--		b, err := ioutil.ReadAll(f)
--		opts.InputStream = bytes.NewBuffer(b)
--		opts.Source = "-"
--	}
--	return c.createImage(queryString(&opts), nil, opts.InputStream, opts.OutputStream, false)
--}
+-	t.Logf("Listing volumes")
+-	testVolumeList(t, client)
 -
--// BuildImageOptions present the set of informations available for building an
--// image from a tarfile with a Dockerfile in it.
--//
--// For more details about the Docker building process, see
--// http://goo.gl/tlPXPu.
--type BuildImageOptions struct {
--	Name                string    `qs:"t"`
--	NoCache             bool      `qs:"nocache"`
--	SuppressOutput      bool      `qs:"q"`
--	RmTmpContainer      bool      `qs:"rm"`
--	ForceRmTmpContainer bool      `qs:"forcerm"`
--	InputStream         io.Reader `qs:"-"`
--	OutputStream        io.Writer `qs:"-"`
--	RawJSONStream       bool      `qs:"-"`
--	Remote              string    `qs:"remote"`
--}
+-	t.Logf("Creating volume")
+-	volumeID := testVolumeCreate(t, client)
 -
--// BuildImage builds an image from a tarball's url or a Dockerfile in the input
--// stream.
--//
--// See http://goo.gl/wRsW76 for more details.
--func (c *Client) BuildImage(opts BuildImageOptions) error {
--	if opts.OutputStream == nil {
--		return ErrMissingOutputStream
--	}
--	var headers map[string]string
--	if opts.Remote != "" && opts.Name == "" {
--		opts.Name = opts.Remote
--	}
--	if opts.InputStream != nil {
--		headers = map[string]string{"Content-Type": "application/tar"}
--	} else if opts.Remote == "" {
--		return ErrMissingRepo
--	}
--	return c.stream("POST", fmt.Sprintf("/build?%s",
--		queryString(&opts)), true, opts.RawJSONStream, headers, opts.InputStream, opts.OutputStream, nil)
--}
+-	t.Logf("Getting volume %s", volumeID)
+-	testVolumeGet(t, client, volumeID)
 -
--// TagImageOptions present the set of options to tag an image.
--//
--// See http://goo.gl/5g6qFy for more details.
--type TagImageOptions struct {
--	Repo  string
--	Tag   string
--	Force bool
+-	t.Logf("Updating volume %s", volumeID)
+-	testVolumeUpdate(t, client, volumeID)
+-
+-	t.Logf("Deleting volume %s", volumeID)
+-	testVolumeDelete(t, client, volumeID)
 -}
 -
--// TagImage adds a tag to the image identified by the given name.
--//
--// See http://goo.gl/5g6qFy for more details.
--func (c *Client) TagImage(name string, opts TagImageOptions) error {
--	if name == "" {
--		return ErrNoSuchImage
--	}
--	_, status, err := c.do("POST", fmt.Sprintf("/images/"+name+"/tag?%s",
--		queryString(&opts)), nil)
--	if status == http.StatusNotFound {
--		return ErrNoSuchImage
--	}
+-func testVolumeList(t *testing.T, client *gophercloud.ServiceClient) {
+-	volumes.List(client).EachPage(func(page pagination.Page) (bool, error) {
+-		vList, err := volumes.ExtractVolumes(page)
+-		th.AssertNoErr(t, err)
 -
--	return err
+-		for _, v := range vList {
+-			t.Logf("Volume: ID [%s] Name [%s] Type [%s] Created [%s]", v.ID, v.Name,
+-				v.VolumeType, v.CreatedAt)
+-		}
+-
+-		return true, nil
+-	})
 -}
 -
--func isURL(u string) bool {
--	p, err := url.Parse(u)
--	if err != nil {
--		return false
--	}
--	return p.Scheme == "http" || p.Scheme == "https"
+-func testVolumeCreate(t *testing.T, client *gophercloud.ServiceClient) string {
+-	vol, err := volumes.Create(client, os.CreateOpts{Size: 75}).Extract()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Created volume: ID [%s] Size [%s]", vol.ID, vol.Size)
+-	return vol.ID
 -}
 -
--// APIImageSearch reflect the result of a search on the dockerHub
--//
--// See http://goo.gl/xI5lLZ for more details.
--type APIImageSearch struct {
--	Description string `json:"description,omitempty" yaml:"description,omitempty"`
--	IsOfficial  bool   `json:"is_official,omitempty" yaml:"is_official,omitempty"`
--	IsAutomated bool   `json:"is_automated,omitempty" yaml:"is_automated,omitempty"`
--	Name        string `json:"name,omitempty" yaml:"name,omitempty"`
--	StarCount   int    `json:"star_count,omitempty" yaml:"star_count,omitempty"`
+-func testVolumeGet(t *testing.T, client *gophercloud.ServiceClient, id string) {
+-	vol, err := volumes.Get(client, id).Extract()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Created volume: ID [%s] Size [%s]", vol.ID, vol.Size)
 -}
 -
--// SearchImages search the docker hub with a specific given term.
--//
--// See http://goo.gl/xI5lLZ for more details.
--func (c *Client) SearchImages(term string) ([]APIImageSearch, error) {
--	body, _, err := c.do("GET", "/images/search?term="+term, nil)
--	if err != nil {
--		return nil, err
--	}
--	var searchResult []APIImageSearch
--	err = json.Unmarshal(body, &searchResult)
--	if err != nil {
--		return nil, err
--	}
--	return searchResult, nil
+-func testVolumeUpdate(t *testing.T, client *gophercloud.ServiceClient, id string) {
+-	vol, err := volumes.Update(client, id, volumes.UpdateOpts{Name: "new_name"}).Extract()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Created volume: ID [%s] Name [%s]", vol.ID, vol.Name)
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/image_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/image_test.go
+-
+-func testVolumeDelete(t *testing.T, client *gophercloud.ServiceClient, id string) {
+-	res := volumes.Delete(client, id)
+-	th.AssertNoErr(t, res.Err)
+-	t.Logf("Deleted volume %s", id)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/blockstorage/v1/volume_type_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/blockstorage/v1/volume_type_test.go
 deleted file mode 100644
-index 5a7b2de..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/image_test.go
+index 716f2b9..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/blockstorage/v1/volume_type_test.go
 +++ /dev/null
-@@ -1,861 +0,0 @@
--// Copyright 2014 go-dockerclient authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the LICENSE file.
+@@ -1,46 +0,0 @@
+-// +build acceptance blockstorage volumetypes
 -
--package docker
+-package v1
 -
 -import (
--	"bytes"
--	"encoding/base64"
--	"encoding/json"
--	"io/ioutil"
--	"net/http"
--	"net/url"
--	"os"
--	"reflect"
--	"strings"
 -	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-	"github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumetypes"
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--func newTestClient(rt *FakeRoundTripper) Client {
--	endpoint := "http://localhost:4243"
--	u, _ := parseEndpoint("http://localhost:4243")
--	client := Client{
--		HTTPClient:             &http.Client{Transport: rt},
--		endpoint:               endpoint,
--		endpointURL:            u,
--		SkipServerVersionCheck: true,
--	}
--	return client
--}
+-func TestAll(t *testing.T) {
+-	client := setup(t)
 -
--type stdoutMock struct {
--	*bytes.Buffer
--}
+-	t.Logf("Listing volume types")
+-	id := testList(t, client)
 -
--func (m stdoutMock) Close() error {
--	return nil
+-	t.Logf("Getting volume type %s", id)
+-	testGet(t, client, id)
 -}
 -
--type stdinMock struct {
--	*bytes.Buffer
--}
+-func testList(t *testing.T, client *gophercloud.ServiceClient) string {
+-	var lastID string
 -
--func (m stdinMock) Close() error {
--	return nil
--}
+-	volumetypes.List(client).EachPage(func(page pagination.Page) (bool, error) {
+-		typeList, err := volumetypes.ExtractVolumeTypes(page)
+-		th.AssertNoErr(t, err)
 -
--func TestListImages(t *testing.T) {
--	body := `[
--     {
--             "Repository":"base",
--             "Tag":"ubuntu-12.10",
--             "Id":"b750fe79269d",
--             "Created":1364102658
--     },
--     {
--             "Repository":"base",
--             "Tag":"ubuntu-quantal",
--             "Id":"b750fe79269d",
--             "Created":1364102658
--     },
--     {
--             "RepoTag": [
--             "ubuntu:12.04",
--             "ubuntu:precise",
--             "ubuntu:latest"
--             ],
--             "Id": "8dbd9e392a964c",
--             "Created": 1365714795,
--             "Size": 131506275,
--             "VirtualSize": 131506275
--      },
--      {
--             "RepoTag": [
--             "ubuntu:12.10",
--             "ubuntu:quantal"
--             ],
--             "ParentId": "27cf784147099545",
--             "Id": "b750fe79269d2e",
--             "Created": 1364102658,
--             "Size": 24653,
--             "VirtualSize": 180116135
--      }
--]`
--	var expected []APIImages
--	err := json.Unmarshal([]byte(body), &expected)
--	if err != nil {
--		t.Fatal(err)
--	}
--	client := newTestClient(&FakeRoundTripper{message: body, status: http.StatusOK})
--	images, err := client.ListImages(false)
--	if err != nil {
--		t.Error(err)
--	}
--	if !reflect.DeepEqual(images, expected) {
--		t.Errorf("ListImages: Wrong return value. Want %#v. Got %#v.", expected, images)
--	}
--}
+-		for _, vt := range typeList {
+-			t.Logf("Volume type: ID [%s] Name [%s]", vt.ID, vt.Name)
+-			lastID = vt.ID
+-		}
 -
--func TestListImagesParameters(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "null", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	_, err := client.ListImages(false)
--	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "GET" {
--		t.Errorf("ListImages(false: Wrong HTTP method. Want GET. Got %s.", req.Method)
--	}
--	if all := req.URL.Query().Get("all"); all != "0" {
--		t.Errorf("ListImages(false): Wrong parameter. Want all=0. Got all=%s", all)
--	}
--	fakeRT.Reset()
--	_, err = client.ListImages(true)
--	if err != nil {
--		t.Fatal(err)
--	}
--	req = fakeRT.requests[0]
--	if all := req.URL.Query().Get("all"); all != "1" {
--		t.Errorf("ListImages(true): Wrong parameter. Want all=1. Got all=%s", all)
--	}
--}
+-		return true, nil
+-	})
 -
--func TestImageHistory(t *testing.T) {
--	body := `[
--	{
--		"Id": "25daec02219d2d852f7526137213a9b199926b4b24e732eab5b8bc6c49bd470e",
--		"Tags": [
--			"debian:7.6",
--			"debian:latest",
--			"debian:7",
--			"debian:wheezy"
--		],
--		"Created": 1409856216,
--		"CreatedBy": "/bin/sh -c #(nop) CMD [/bin/bash]"
--	},
--	{
--		"Id": "41026a5347fb5be6ed16115bf22df8569697139f246186de9ae8d4f67c335dce",
--		"Created": 1409856213,
--		"CreatedBy": "/bin/sh -c #(nop) ADD file:1ee9e97209d00e3416a4543b23574cc7259684741a46bbcbc755909b8a053a38 in /",
--		"Size": 85178663
--	},
--	{
--		"Id": "511136ea3c5a64f264b78b5433614aec563103b4d4702f3ba7d4d2698e22c158",
--		"Tags": [
--			"scratch:latest"
--		],
--		"Created": 1371157430
--	}
--]`
--	var expected []ImageHistory
--	err := json.Unmarshal([]byte(body), &expected)
--	if err != nil {
--		t.Fatal(err)
--	}
--	client := newTestClient(&FakeRoundTripper{message: body, status: http.StatusOK})
--	history, err := client.ImageHistory("debian:latest")
--	if err != nil {
--		t.Error(err)
--	}
--	if !reflect.DeepEqual(history, expected) {
--		t.Errorf("ImageHistory: Wrong return value. Want %#v. Got %#v.", expected, history)
--	}
+-	return lastID
 -}
 -
--func TestRemoveImage(t *testing.T) {
--	name := "test"
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusNoContent}
--	client := newTestClient(fakeRT)
--	err := client.RemoveImage(name)
--	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	expectedMethod := "DELETE"
--	if req.Method != expectedMethod {
--		t.Errorf("RemoveImage(%q): Wrong HTTP method. Want %s. Got %s.", name, expectedMethod, req.Method)
--	}
--	u, _ := url.Parse(client.getURL("/images/" + name))
--	if req.URL.Path != u.Path {
--		t.Errorf("RemoveImage(%q): Wrong request path. Want %q. Got %q.", name, u.Path, req.URL.Path)
--	}
+-func testGet(t *testing.T, client *gophercloud.ServiceClient, id string) {
+-	vt, err := volumetypes.Get(client, id).Extract()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Volume: ID [%s] Name [%s]", vt.ID, vt.Name)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/client_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/client_test.go
+deleted file mode 100644
+index 61214c0..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/client_test.go
++++ /dev/null
+@@ -1,28 +0,0 @@
+-// +build acceptance
 -
--func TestRemoveImageNotFound(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "no such image", status: http.StatusNotFound})
--	err := client.RemoveImage("test:")
--	if err != ErrNoSuchImage {
--		t.Errorf("RemoveImage: wrong error. Want %#v. Got %#v.", ErrNoSuchImage, err)
--	}
--}
+-package rackspace
 -
--func TestInspectImage(t *testing.T) {
--	body := `{
--     "id":"b750fe79269d2ec9a3c593ef05b4332b1d1a02a62b4accb2c21d589ff2f5f2dc",
--     "parent":"27cf784147099545",
--     "created":"2013-03-23T22:24:18.818426-07:00",
--     "container":"3d67245a8d72ecf13f33dffac9f79dcdf70f75acb84d308770391510e0c23ad0",
--     "container_config":{"Memory":0}
--}`
--	var expected Image
--	json.Unmarshal([]byte(body), &expected)
--	fakeRT := &FakeRoundTripper{message: body, status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	image, err := client.InspectImage(expected.ID)
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/acceptance/tools"
+-	"github.com/rackspace/gophercloud/rackspace"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestAuthenticatedClient(t *testing.T) {
+-	// Obtain credentials from the environment.
+-	ao, err := rackspace.AuthOptionsFromEnv()
+-	th.AssertNoErr(t, err)
+-
+-	client, err := rackspace.AuthenticatedClient(tools.OnlyRS(ao))
 -	if err != nil {
--		t.Fatal(err)
--	}
--	if !reflect.DeepEqual(*image, expected) {
--		t.Errorf("InspectImage(%q): Wrong image returned. Want %#v. Got %#v.", expected.ID, expected, *image)
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "GET" {
--		t.Errorf("InspectImage(%q): Wrong HTTP method. Want GET. Got %s.", expected.ID, req.Method)
--	}
--	u, _ := url.Parse(client.getURL("/images/" + expected.ID + "/json"))
--	if req.URL.Path != u.Path {
--		t.Errorf("InspectImage(%q): Wrong request URL. Want %q. Got %q.", expected.ID, u.Path, req.URL.Path)
+-		t.Fatalf("Unable to authenticate: %v", err)
 -	}
--}
 -
--func TestInspectImageNotFound(t *testing.T) {
--	client := newTestClient(&FakeRoundTripper{message: "no such image", status: http.StatusNotFound})
--	name := "test"
--	image, err := client.InspectImage(name)
--	if image != nil {
--		t.Errorf("InspectImage(%q): expected <nil> image, got %#v.", name, image)
--	}
--	if err != ErrNoSuchImage {
--		t.Errorf("InspectImage(%q): wrong error. Want %#v. Got %#v.", name, ErrNoSuchImage, err)
+-	if client.TokenID == "" {
+-		t.Errorf("No token ID assigned to the client")
 -	}
+-
+-	t.Logf("Client successfully acquired a token: %v", client.TokenID)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/bootfromvolume_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/bootfromvolume_test.go
+deleted file mode 100644
+index 010bf42..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/bootfromvolume_test.go
++++ /dev/null
+@@ -1,46 +0,0 @@
+-// +build acceptance
 -
--func TestPushImage(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "Pushing 1/100", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	var buf bytes.Buffer
--	err := client.PushImage(PushImageOptions{Name: "test", OutputStream: &buf}, AuthConfiguration{})
--	if err != nil {
--		t.Fatal(err)
--	}
--	expected := "Pushing 1/100"
--	if buf.String() != expected {
--		t.Errorf("PushImage: Wrong output. Want %q. Got %q.", expected, buf.String())
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "POST" {
--		t.Errorf("PushImage: Wrong HTTP method. Want POST. Got %s.", req.Method)
--	}
--	u, _ := url.Parse(client.getURL("/images/test/push"))
--	if req.URL.Path != u.Path {
--		t.Errorf("PushImage: Wrong request path. Want %q. Got %q.", u.Path, req.URL.Path)
--	}
--	if query := req.URL.Query().Encode(); query != "" {
--		t.Errorf("PushImage: Wrong query string. Want no parameters, got %q.", query)
--	}
+-package v2
 -
--	auth, err := base64.URLEncoding.DecodeString(req.Header.Get("X-Registry-Auth"))
--	if err != nil {
--		t.Errorf("PushImage: caught error decoding auth. %#v", err.Error())
--	}
--	if strings.TrimSpace(string(auth)) != "{}" {
--		t.Errorf("PushImage: wrong body. Want %q. Got %q.",
--			base64.URLEncoding.EncodeToString([]byte("{}")), req.Header.Get("X-Registry-Auth"))
+-import (
+-	"testing"
+-
+-	osBFV "github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume"
+-	"github.com/rackspace/gophercloud/rackspace/compute/v2/bootfromvolume"
+-	"github.com/rackspace/gophercloud/rackspace/compute/v2/servers"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/smashwilson/gophercloud/acceptance/tools"
+-)
+-
+-func TestBootFromVolume(t *testing.T) {
+-	client, err := newClient()
+-	th.AssertNoErr(t, err)
+-
+-	if testing.Short() {
+-		t.Skip("Skipping test that requires server creation in short mode.")
 -	}
--}
 -
--func TestPushImageWithRawJSON(t *testing.T) {
--	body := `
--	{"status":"Pushing..."}
--	{"status":"Pushing", "progress":"1/? (n/a)", "progressDetail":{"current":1}}}
--	{"status":"Image successfully pushed"}
--	`
--	fakeRT := &FakeRoundTripper{
--		message: body,
--		status:  http.StatusOK,
--		header: map[string]string{
--			"Content-Type": "application/json",
+-	options, err := optionsFromEnv()
+-	th.AssertNoErr(t, err)
+-
+-	name := tools.RandomString("Gophercloud-", 8)
+-	t.Logf("Creating server [%s].", name)
+-
+-	bd := []osBFV.BlockDevice{
+-		osBFV.BlockDevice{
+-			UUID:       options.imageID,
+-			SourceType: osBFV.Image,
+-			VolumeSize: 10,
 -		},
 -	}
--	client := newTestClient(fakeRT)
--	var buf bytes.Buffer
 -
--	err := client.PushImage(PushImageOptions{
--		Name:          "test",
--		OutputStream:  &buf,
--		RawJSONStream: true,
--	}, AuthConfiguration{})
--	if err != nil {
--		t.Fatal(err)
--	}
--	if buf.String() != body {
--		t.Errorf("PushImage: Wrong raw output. Want %q. Got %q.", body, buf.String())
--	}
+-	server, err := bootfromvolume.Create(client, servers.CreateOpts{
+-		Name:        name,
+-		FlavorRef:   "performance1-1",
+-		BlockDevice: bd,
+-	}).Extract()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Created server: %+v\n", server)
+-	//defer deleteServer(t, client, server)
+-	t.Logf("Deleting server [%s]...", name)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/compute_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/compute_test.go
+deleted file mode 100644
+index 3ca6dc9..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/compute_test.go
++++ /dev/null
+@@ -1,60 +0,0 @@
+-// +build acceptance
 -
--func TestPushImageWithAuthentication(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "Pushing 1/100", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	var buf bytes.Buffer
--	inputAuth := AuthConfiguration{
--		Username: "gopher",
--		Password: "gopher123",
--		Email:    "gopher at tsuru.io",
--	}
--	err := client.PushImage(PushImageOptions{Name: "test", OutputStream: &buf}, inputAuth)
--	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	var gotAuth AuthConfiguration
+-package v2
 -
--	auth, err := base64.URLEncoding.DecodeString(req.Header.Get("X-Registry-Auth"))
+-import (
+-	"errors"
+-	"os"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/acceptance/tools"
+-	"github.com/rackspace/gophercloud/rackspace"
+-)
+-
+-func newClient() (*gophercloud.ServiceClient, error) {
+-	// Obtain credentials from the environment.
+-	options, err := rackspace.AuthOptionsFromEnv()
 -	if err != nil {
--		t.Errorf("PushImage: caught error decoding auth. %#v", err.Error())
+-		return nil, err
 -	}
+-	options = tools.OnlyRS(options)
+-	region := os.Getenv("RS_REGION")
 -
--	err = json.Unmarshal(auth, &gotAuth)
--	if err != nil {
--		t.Fatal(err)
+-	if options.Username == "" {
+-		return nil, errors.New("Please provide a Rackspace username as RS_USERNAME.")
 -	}
--	if !reflect.DeepEqual(gotAuth, inputAuth) {
--		t.Errorf("PushImage: wrong auth configuration. Want %#v. Got %#v.", inputAuth, gotAuth)
+-	if options.APIKey == "" {
+-		return nil, errors.New("Please provide a Rackspace API key as RS_API_KEY.")
 -	}
--}
--
--func TestPushImageCustomRegistry(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "Pushing 1/100", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	var authConfig AuthConfiguration
--	var buf bytes.Buffer
--	opts := PushImageOptions{
--		Name: "test", Registry: "docker.tsuru.io",
--		OutputStream: &buf,
+-	if region == "" {
+-		return nil, errors.New("Please provide a Rackspace region as RS_REGION.")
 -	}
--	err := client.PushImage(opts, authConfig)
+-
+-	client, err := rackspace.AuthenticatedClient(options)
 -	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	expectedQuery := "registry=docker.tsuru.io"
--	if query := req.URL.Query().Encode(); query != expectedQuery {
--		t.Errorf("PushImage: Wrong query string. Want %q. Got %q.", expectedQuery, query)
+-		return nil, err
 -	}
+-
+-	return rackspace.NewComputeV2(client, gophercloud.EndpointOpts{
+-		Region: region,
+-	})
 -}
 -
--func TestPushImageNoName(t *testing.T) {
--	client := Client{}
--	err := client.PushImage(PushImageOptions{}, AuthConfiguration{})
--	if err != ErrNoSuchImage {
--		t.Errorf("PushImage: got wrong error. Want %#v. Got %#v.", ErrNoSuchImage, err)
--	}
+-type serverOpts struct {
+-	imageID  string
+-	flavorID string
 -}
 -
--func TestPullImage(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "Pulling 1/100", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	var buf bytes.Buffer
--	err := client.PullImage(PullImageOptions{Repository: "base", OutputStream: &buf},
--		AuthConfiguration{})
--	if err != nil {
--		t.Fatal(err)
--	}
--	expected := "Pulling 1/100"
--	if buf.String() != expected {
--		t.Errorf("PullImage: Wrong output. Want %q. Got %q.", expected, buf.String())
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "POST" {
--		t.Errorf("PullImage: Wrong HTTP method. Want POST. Got %s.", req.Method)
+-func optionsFromEnv() (*serverOpts, error) {
+-	options := &serverOpts{
+-		imageID:  os.Getenv("RS_IMAGE_ID"),
+-		flavorID: os.Getenv("RS_FLAVOR_ID"),
 -	}
--	u, _ := url.Parse(client.getURL("/images/create"))
--	if req.URL.Path != u.Path {
--		t.Errorf("PullImage: Wrong request path. Want %q. Got %q.", u.Path, req.URL.Path)
+-	if options.imageID == "" {
+-		return nil, errors.New("Please provide a valid Rackspace image ID as RS_IMAGE_ID")
 -	}
--	expectedQuery := "fromImage=base"
--	if query := req.URL.Query().Encode(); query != expectedQuery {
--		t.Errorf("PullImage: Wrong query strin. Want %q. Got %q.", expectedQuery, query)
+-	if options.flavorID == "" {
+-		return nil, errors.New("Please provide a valid Rackspace flavor ID as RS_FLAVOR_ID")
 -	}
+-	return options, nil
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/flavors_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/flavors_test.go
+deleted file mode 100644
+index 4618ecc..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/flavors_test.go
++++ /dev/null
+@@ -1,61 +0,0 @@
+-// +build acceptance
 -
--func TestPullImageWithRawJSON(t *testing.T) {
--	body := `
--	{"status":"Pulling..."}
--	{"status":"Pulling", "progress":"1 B/ 100 B", "progressDetail":{"current":1, "total":100}}
--	`
--	fakeRT := &FakeRoundTripper{
--		message: body,
--		status:  http.StatusOK,
--		header: map[string]string{
--			"Content-Type": "application/json",
--		},
--	}
--	client := newTestClient(fakeRT)
--	var buf bytes.Buffer
--	err := client.PullImage(PullImageOptions{
--		Repository:    "base",
--		OutputStream:  &buf,
--		RawJSONStream: true,
--	}, AuthConfiguration{})
--	if err != nil {
--		t.Fatal(err)
--	}
--	if buf.String() != body {
--		t.Errorf("PullImage: Wrong raw output. Want %q. Got %q", body, buf.String())
+-package v2
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/pagination"
+-	"github.com/rackspace/gophercloud/rackspace/compute/v2/flavors"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestListFlavors(t *testing.T) {
+-	client, err := newClient()
+-	th.AssertNoErr(t, err)
+-
+-	count := 0
+-	err = flavors.ListDetail(client, nil).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		t.Logf("-- Page %0d --", count)
+-
+-		fs, err := flavors.ExtractFlavors(page)
+-		th.AssertNoErr(t, err)
+-
+-		for i, flavor := range fs {
+-			t.Logf("[%02d]      id=[%s]", i, flavor.ID)
+-			t.Logf("        name=[%s]", flavor.Name)
+-			t.Logf("        disk=[%d]", flavor.Disk)
+-			t.Logf("         RAM=[%d]", flavor.RAM)
+-			t.Logf(" rxtx_factor=[%f]", flavor.RxTxFactor)
+-			t.Logf("        swap=[%d]", flavor.Swap)
+-			t.Logf("       VCPUs=[%d]", flavor.VCPUs)
+-		}
+-
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	if count == 0 {
+-		t.Errorf("No flavors listed!")
 -	}
 -}
 -
--func TestPullImageWithoutOutputStream(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "Pulling 1/100", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	opts := PullImageOptions{
--		Repository: "base",
--		Registry:   "docker.tsuru.io",
--	}
--	err := client.PullImage(opts, AuthConfiguration{})
--	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	expected := map[string][]string{"fromImage": {"base"}, "registry": {"docker.tsuru.io"}}
--	got := map[string][]string(req.URL.Query())
--	if !reflect.DeepEqual(got, expected) {
--		t.Errorf("PullImage: wrong query string. Want %#v. Got %#v.", expected, got)
--	}
+-func TestGetFlavor(t *testing.T) {
+-	client, err := newClient()
+-	th.AssertNoErr(t, err)
+-
+-	options, err := optionsFromEnv()
+-	th.AssertNoErr(t, err)
+-
+-	flavor, err := flavors.Get(client, options.flavorID).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Requested flavor:")
+-	t.Logf("          id=[%s]", flavor.ID)
+-	t.Logf("        name=[%s]", flavor.Name)
+-	t.Logf("        disk=[%d]", flavor.Disk)
+-	t.Logf("         RAM=[%d]", flavor.RAM)
+-	t.Logf(" rxtx_factor=[%f]", flavor.RxTxFactor)
+-	t.Logf("        swap=[%d]", flavor.Swap)
+-	t.Logf("       VCPUs=[%d]", flavor.VCPUs)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/images_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/images_test.go
+deleted file mode 100644
+index 5e36c2e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/images_test.go
++++ /dev/null
+@@ -1,63 +0,0 @@
+-// +build acceptance
 -
--func TestPullImageCustomRegistry(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "Pulling 1/100", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	var buf bytes.Buffer
--	opts := PullImageOptions{
--		Repository:   "base",
--		Registry:     "docker.tsuru.io",
--		OutputStream: &buf,
--	}
--	err := client.PullImage(opts, AuthConfiguration{})
--	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	expected := map[string][]string{"fromImage": {"base"}, "registry": {"docker.tsuru.io"}}
--	got := map[string][]string(req.URL.Query())
--	if !reflect.DeepEqual(got, expected) {
--		t.Errorf("PullImage: wrong query string. Want %#v. Got %#v.", expected, got)
+-package v2
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/pagination"
+-	"github.com/rackspace/gophercloud/rackspace/compute/v2/images"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestListImages(t *testing.T) {
+-	client, err := newClient()
+-	th.AssertNoErr(t, err)
+-
+-	count := 0
+-	err = images.ListDetail(client, nil).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		t.Logf("-- Page %02d --", count)
+-
+-		is, err := images.ExtractImages(page)
+-		th.AssertNoErr(t, err)
+-
+-		for i, image := range is {
+-			t.Logf("[%02d]   id=[%s]", i, image.ID)
+-			t.Logf("     name=[%s]", image.Name)
+-			t.Logf("  created=[%s]", image.Created)
+-			t.Logf("  updated=[%s]", image.Updated)
+-			t.Logf(" min disk=[%d]", image.MinDisk)
+-			t.Logf("  min RAM=[%d]", image.MinRAM)
+-			t.Logf(" progress=[%d]", image.Progress)
+-			t.Logf("   status=[%s]", image.Status)
+-		}
+-
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	if count < 1 {
+-		t.Errorf("Expected at least one page of images.")
 -	}
 -}
 -
--func TestPullImageTag(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "Pulling 1/100", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	var buf bytes.Buffer
--	opts := PullImageOptions{
--		Repository:   "base",
--		Registry:     "docker.tsuru.io",
--		Tag:          "latest",
--		OutputStream: &buf,
--	}
--	err := client.PullImage(opts, AuthConfiguration{})
--	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	expected := map[string][]string{"fromImage": {"base"}, "registry": {"docker.tsuru.io"}, "tag": {"latest"}}
--	got := map[string][]string(req.URL.Query())
--	if !reflect.DeepEqual(got, expected) {
--		t.Errorf("PullImage: wrong query string. Want %#v. Got %#v.", expected, got)
--	}
+-func TestGetImage(t *testing.T) {
+-	client, err := newClient()
+-	th.AssertNoErr(t, err)
+-
+-	options, err := optionsFromEnv()
+-	th.AssertNoErr(t, err)
+-
+-	image, err := images.Get(client, options.imageID).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Requested image:")
+-	t.Logf("       id=[%s]", image.ID)
+-	t.Logf("     name=[%s]", image.Name)
+-	t.Logf("  created=[%s]", image.Created)
+-	t.Logf("  updated=[%s]", image.Updated)
+-	t.Logf(" min disk=[%d]", image.MinDisk)
+-	t.Logf("  min RAM=[%d]", image.MinRAM)
+-	t.Logf(" progress=[%d]", image.Progress)
+-	t.Logf("   status=[%s]", image.Status)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/keypairs_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/keypairs_test.go
+deleted file mode 100644
+index 9bd6eb4..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/keypairs_test.go
++++ /dev/null
+@@ -1,87 +0,0 @@
+-// +build acceptance rackspace
 -
--func TestPullImageNoRepository(t *testing.T) {
--	var opts PullImageOptions
--	client := Client{}
--	err := client.PullImage(opts, AuthConfiguration{})
--	if err != ErrNoSuchImage {
--		t.Errorf("PullImage: got wrong error. Want %#v. Got %#v.", ErrNoSuchImage, err)
--	}
+-package v2
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/acceptance/tools"
+-	os "github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs"
+-	"github.com/rackspace/gophercloud/pagination"
+-	"github.com/rackspace/gophercloud/rackspace/compute/v2/keypairs"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func deleteKeyPair(t *testing.T, client *gophercloud.ServiceClient, name string) {
+-	err := keypairs.Delete(client, name).ExtractErr()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Successfully deleted key [%s].", name)
 -}
 -
--func TestImportImageFromUrl(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	var buf bytes.Buffer
--	opts := ImportImageOptions{
--		Source:       "http://mycompany.com/file.tar",
--		Repository:   "testimage",
--		Tag:          "tag",
--		OutputStream: &buf,
--	}
--	err := client.ImportImage(opts)
--	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	expected := map[string][]string{"fromSrc": {opts.Source}, "repo": {opts.Repository}, "tag": {opts.Tag}}
--	got := map[string][]string(req.URL.Query())
--	if !reflect.DeepEqual(got, expected) {
--		t.Errorf("ImportImage: wrong query string. Want %#v. Got %#v.", expected, got)
--	}
+-func TestCreateKeyPair(t *testing.T) {
+-	client, err := newClient()
+-	th.AssertNoErr(t, err)
+-
+-	name := tools.RandomString("createdkey-", 8)
+-	k, err := keypairs.Create(client, os.CreateOpts{Name: name}).Extract()
+-	th.AssertNoErr(t, err)
+-	defer deleteKeyPair(t, client, name)
+-
+-	t.Logf("Created a new keypair:")
+-	t.Logf("        name=[%s]", k.Name)
+-	t.Logf(" fingerprint=[%s]", k.Fingerprint)
+-	t.Logf("   publickey=[%s]", tools.Elide(k.PublicKey))
+-	t.Logf("  privatekey=[%s]", tools.Elide(k.PrivateKey))
+-	t.Logf("      userid=[%s]", k.UserID)
 -}
 -
--func TestImportImageFromInput(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	in := bytes.NewBufferString("tar content")
--	var buf bytes.Buffer
--	opts := ImportImageOptions{
--		Source: "-", Repository: "testimage",
--		InputStream: in, OutputStream: &buf,
--		Tag: "tag",
--	}
--	err := client.ImportImage(opts)
--	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	expected := map[string][]string{"fromSrc": {opts.Source}, "repo": {opts.Repository}, "tag": {opts.Tag}}
--	got := map[string][]string(req.URL.Query())
--	if !reflect.DeepEqual(got, expected) {
--		t.Errorf("ImportImage: wrong query string. Want %#v. Got %#v.", expected, got)
--	}
--	body, err := ioutil.ReadAll(req.Body)
--	if err != nil {
--		t.Errorf("ImportImage: caugth error while reading body %#v", err.Error())
--	}
--	e := "tar content"
--	if string(body) != e {
--		t.Errorf("ImportImage: wrong body. Want %#v. Got %#v.", e, string(body))
--	}
+-func TestImportKeyPair(t *testing.T) {
+-	client, err := newClient()
+-	th.AssertNoErr(t, err)
+-
+-	name := tools.RandomString("importedkey-", 8)
+-	pubkey := "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDlIQ3r+zd97kb9Hzmujd3V6pbO53eb3Go4q2E8iqVGWQfZTrFdL9KACJnqJIm9HmncfRkUTxE37hqeGCCv8uD+ZPmPiZG2E60OX1mGDjbbzAyReRwYWXgXHopggZTLak5k4mwZYaxwaufbVBDRn847e01lZnaXaszEToLM37NLw+uz29sl3TwYy2R0RGHPwPc160aWmdLjSyd1Nd4c9pvvOP/EoEuBjIC6NJJwg2Rvg9sjjx9jYj0QUgc8CqKLN25oMZ69kNJzlFylKRUoeeVr89txlR59yehJWk6Uw6lYFTdJmcmQOFVAJ12RMmS1hLWCM8UzAgtw+EDa0eqBxBDl smash at winter"
+-
+-	k, err := keypairs.Create(client, os.CreateOpts{
+-		Name:      name,
+-		PublicKey: pubkey,
+-	}).Extract()
+-	th.AssertNoErr(t, err)
+-	defer deleteKeyPair(t, client, name)
+-
+-	th.CheckEquals(t, pubkey, k.PublicKey)
+-	th.CheckEquals(t, "", k.PrivateKey)
+-
+-	t.Logf("Imported an existing keypair:")
+-	t.Logf("        name=[%s]", k.Name)
+-	t.Logf(" fingerprint=[%s]", k.Fingerprint)
+-	t.Logf("   publickey=[%s]", tools.Elide(k.PublicKey))
+-	t.Logf("  privatekey=[%s]", tools.Elide(k.PrivateKey))
+-	t.Logf("      userid=[%s]", k.UserID)
 -}
 -
--func TestImportImageDoesNotPassesInputIfSourceIsNotDash(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	var buf bytes.Buffer
--	in := bytes.NewBufferString("foo")
--	opts := ImportImageOptions{
--		Source: "http://test.com/container.tar", Repository: "testimage",
--		InputStream: in, OutputStream: &buf,
--	}
--	err := client.ImportImage(opts)
--	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	expected := map[string][]string{"fromSrc": {opts.Source}, "repo": {opts.Repository}}
--	got := map[string][]string(req.URL.Query())
--	if !reflect.DeepEqual(got, expected) {
--		t.Errorf("ImportImage: wrong query string. Want %#v. Got %#v.", expected, got)
--	}
--	body, err := ioutil.ReadAll(req.Body)
--	if err != nil {
--		t.Errorf("ImportImage: caugth error while reading body %#v", err.Error())
--	}
--	if string(body) != "" {
--		t.Errorf("ImportImage: wrong body. Want nothing. Got %#v.", string(body))
--	}
+-func TestListKeyPairs(t *testing.T) {
+-	client, err := newClient()
+-	th.AssertNoErr(t, err)
+-
+-	count := 0
+-	err = keypairs.List(client).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		t.Logf("--- %02d ---", count)
+-
+-		ks, err := keypairs.ExtractKeyPairs(page)
+-		th.AssertNoErr(t, err)
+-
+-		for i, keypair := range ks {
+-			t.Logf("[%02d]    name=[%s]", i, keypair.Name)
+-			t.Logf(" fingerprint=[%s]", keypair.Fingerprint)
+-			t.Logf("   publickey=[%s]", tools.Elide(keypair.PublicKey))
+-			t.Logf("  privatekey=[%s]", tools.Elide(keypair.PrivateKey))
+-			t.Logf("      userid=[%s]", keypair.UserID)
+-		}
+-
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/networks_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/networks_test.go
+deleted file mode 100644
+index e8fc4d3..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/networks_test.go
++++ /dev/null
+@@ -1,53 +0,0 @@
+-// +build acceptance rackspace
 -
--func TestImportImageShouldPassTarContentToBodyWhenSourceIsFilePath(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	var buf bytes.Buffer
--	tarPath := "testing/data/container.tar"
--	opts := ImportImageOptions{
--		Source: tarPath, Repository: "testimage",
--		OutputStream: &buf,
--	}
--	err := client.ImportImage(opts)
--	if err != nil {
--		t.Fatal(err)
--	}
--	tar, err := os.Open(tarPath)
--	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	tarContent, err := ioutil.ReadAll(tar)
--	body, err := ioutil.ReadAll(req.Body)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if !reflect.DeepEqual(tarContent, body) {
--		t.Errorf("ImportImage: wrong body. Want %#v content. Got %#v.", tarPath, body)
+-package v2
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/pagination"
+-	"github.com/rackspace/gophercloud/rackspace/compute/v2/networks"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestNetworks(t *testing.T) {
+-	client, err := newClient()
+-	th.AssertNoErr(t, err)
+-
+-	// Create a network
+-	n, err := networks.Create(client, networks.CreateOpts{Label: "sample_network", CIDR: "172.20.0.0/24"}).Extract()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Created network: %+v\n", n)
+-	defer networks.Delete(client, n.ID)
+-	th.AssertEquals(t, n.Label, "sample_network")
+-	th.AssertEquals(t, n.CIDR, "172.20.0.0/24")
+-	networkID := n.ID
+-
+-	// List networks
+-	pager := networks.List(client)
+-	err = pager.EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page ---")
+-
+-		networkList, err := networks.ExtractNetworks(page)
+-		th.AssertNoErr(t, err)
+-
+-		for _, n := range networkList {
+-			t.Logf("Network: ID [%s] Label [%s] CIDR [%s]",
+-				n.ID, n.Label, n.CIDR)
+-		}
+-
+-		return true, nil
+-	})
+-	th.CheckNoErr(t, err)
+-
+-	// Get a network
+-	if networkID == "" {
+-		t.Fatalf("In order to retrieve a network, the NetworkID must be set")
 -	}
+-	n, err = networks.Get(client, networkID).Extract()
+-	t.Logf("Retrieved Network: %+v\n", n)
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, n.CIDR, "172.20.0.0/24")
+-	th.AssertEquals(t, n.Label, "sample_network")
+-	th.AssertEquals(t, n.ID, networkID)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/pkg.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/pkg.go
+deleted file mode 100644
+index 5ec3cc8..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/pkg.go
++++ /dev/null
+@@ -1 +0,0 @@
+-package v2
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/servers_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/servers_test.go
+deleted file mode 100644
+index 511f0a9..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/servers_test.go
++++ /dev/null
+@@ -1,199 +0,0 @@
+-// +build acceptance
+-
+-package v2
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/acceptance/tools"
+-	"github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig"
+-	oskey "github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs"
+-	os "github.com/rackspace/gophercloud/openstack/compute/v2/servers"
+-	"github.com/rackspace/gophercloud/pagination"
+-	"github.com/rackspace/gophercloud/rackspace/compute/v2/keypairs"
+-	"github.com/rackspace/gophercloud/rackspace/compute/v2/servers"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func createServerKeyPair(t *testing.T, client *gophercloud.ServiceClient) *oskey.KeyPair {
+-	name := tools.RandomString("importedkey-", 8)
+-	pubkey := "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDlIQ3r+zd97kb9Hzmujd3V6pbO53eb3Go4q2E8iqVGWQfZTrFdL9KACJnqJIm9HmncfRkUTxE37hqeGCCv8uD+ZPmPiZG2E60OX1mGDjbbzAyReRwYWXgXHopggZTLak5k4mwZYaxwaufbVBDRn847e01lZnaXaszEToLM37NLw+uz29sl3TwYy2R0RGHPwPc160aWmdLjSyd1Nd4c9pvvOP/EoEuBjIC6NJJwg2Rvg9sjjx9jYj0QUgc8CqKLN25oMZ69kNJzlFylKRUoeeVr89txlR59yehJWk6Uw6lYFTdJmcmQOFVAJ12RMmS1hLWCM8UzAgtw+EDa0eqBxBDl smash at winter"
+-
+-	k, err := keypairs.Create(client, oskey.CreateOpts{
+-		Name:      name,
+-		PublicKey: pubkey,
+-	}).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	return k
 -}
 -
--func TestImportImageShouldChangeSourceToDashWhenItsAFilePath(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	var buf bytes.Buffer
--	tarPath := "testing/data/container.tar"
--	opts := ImportImageOptions{
--		Source: tarPath, Repository: "testimage",
--		OutputStream: &buf,
+-func createServer(t *testing.T, client *gophercloud.ServiceClient, keyName string) *os.Server {
+-	if testing.Short() {
+-		t.Skip("Skipping test that requires server creation in short mode.")
 -	}
--	err := client.ImportImage(opts)
--	if err != nil {
--		t.Fatal(err)
+-
+-	options, err := optionsFromEnv()
+-	th.AssertNoErr(t, err)
+-
+-	name := tools.RandomString("Gophercloud-", 8)
+-
+-	opts := &servers.CreateOpts{
+-		Name:       name,
+-		ImageRef:   options.imageID,
+-		FlavorRef:  options.flavorID,
+-		DiskConfig: diskconfig.Manual,
 -	}
--	req := fakeRT.requests[0]
--	expected := map[string][]string{"fromSrc": {"-"}, "repo": {opts.Repository}}
--	got := map[string][]string(req.URL.Query())
--	if !reflect.DeepEqual(got, expected) {
--		t.Errorf("ImportImage: wrong query string. Want %#v. Got %#v.", expected, got)
+-
+-	if keyName != "" {
+-		opts.KeyPair = keyName
 -	}
+-
+-	t.Logf("Creating server [%s].", name)
+-	s, err := servers.Create(client, opts).Extract()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Creating server.")
+-
+-	err = servers.WaitForStatus(client, s.ID, "ACTIVE", 300)
+-	th.AssertNoErr(t, err)
+-	t.Logf("Server created successfully.")
+-
+-	return s
 -}
 -
--func TestBuildImageParameters(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	var buf bytes.Buffer
--	opts := BuildImageOptions{
--		Name:                "testImage",
--		NoCache:             true,
--		SuppressOutput:      true,
--		RmTmpContainer:      true,
--		ForceRmTmpContainer: true,
--		InputStream:         &buf,
--		OutputStream:        &buf,
--	}
--	err := client.BuildImage(opts)
--	if err != nil && strings.Index(err.Error(), "build image fail") == -1 {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	expected := map[string][]string{"t": {opts.Name}, "nocache": {"1"}, "q": {"1"}, "rm": {"1"}, "forcerm": {"1"}}
--	got := map[string][]string(req.URL.Query())
--	if !reflect.DeepEqual(got, expected) {
--		t.Errorf("BuildImage: wrong query string. Want %#v. Got %#v.", expected, got)
--	}
+-func logServer(t *testing.T, server *os.Server, index int) {
+-	if index == -1 {
+-		t.Logf("             id=[%s]", server.ID)
+-	} else {
+-		t.Logf("[%02d]             id=[%s]", index, server.ID)
+-	}
+-	t.Logf("           name=[%s]", server.Name)
+-	t.Logf("      tenant ID=[%s]", server.TenantID)
+-	t.Logf("        user ID=[%s]", server.UserID)
+-	t.Logf("        updated=[%s]", server.Updated)
+-	t.Logf("        created=[%s]", server.Created)
+-	t.Logf("        host ID=[%s]", server.HostID)
+-	t.Logf("    access IPv4=[%s]", server.AccessIPv4)
+-	t.Logf("    access IPv6=[%s]", server.AccessIPv6)
+-	t.Logf("          image=[%v]", server.Image)
+-	t.Logf("         flavor=[%v]", server.Flavor)
+-	t.Logf("      addresses=[%v]", server.Addresses)
+-	t.Logf("       metadata=[%v]", server.Metadata)
+-	t.Logf("          links=[%v]", server.Links)
+-	t.Logf("        keyname=[%s]", server.KeyName)
+-	t.Logf(" admin password=[%s]", server.AdminPass)
+-	t.Logf("         status=[%s]", server.Status)
+-	t.Logf("       progress=[%d]", server.Progress)
+-}
+-
+-func getServer(t *testing.T, client *gophercloud.ServiceClient, server *os.Server) {
+-	t.Logf("> servers.Get")
+-
+-	details, err := servers.Get(client, server.ID).Extract()
+-	th.AssertNoErr(t, err)
+-	logServer(t, details, -1)
+-}
+-
+-func listServers(t *testing.T, client *gophercloud.ServiceClient) {
+-	t.Logf("> servers.List")
+-
+-	count := 0
+-	err := servers.List(client, nil).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		t.Logf("--- Page %02d ---", count)
+-
+-		s, err := servers.ExtractServers(page)
+-		th.AssertNoErr(t, err)
+-		for index, server := range s {
+-			logServer(t, &server, index)
+-		}
+-
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
 -}
 -
--func TestBuildImageParametersForRemoteBuild(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	var buf bytes.Buffer
--	opts := BuildImageOptions{
--		Name:           "testImage",
--		Remote:         "testing/data/container.tar",
--		SuppressOutput: true,
--		OutputStream:   &buf,
--	}
--	err := client.BuildImage(opts)
--	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	expected := map[string][]string{"t": {opts.Name}, "remote": {opts.Remote}, "q": {"1"}}
--	got := map[string][]string(req.URL.Query())
--	if !reflect.DeepEqual(got, expected) {
--		t.Errorf("BuildImage: wrong query string. Want %#v. Got %#v.", expected, got)
--	}
+-func changeAdminPassword(t *testing.T, client *gophercloud.ServiceClient, server *os.Server) {
+-	t.Logf("> servers.ChangeAdminPassword")
+-
+-	original := server.AdminPass
+-
+-	t.Logf("Changing server password.")
+-	err := servers.ChangeAdminPassword(client, server.ID, tools.MakeNewPassword(original)).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	err = servers.WaitForStatus(client, server.ID, "ACTIVE", 300)
+-	th.AssertNoErr(t, err)
+-	t.Logf("Password changed successfully.")
 -}
 -
--func TestBuildImageMissingRepoAndNilInput(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	var buf bytes.Buffer
--	opts := BuildImageOptions{
--		Name:           "testImage",
--		SuppressOutput: true,
--		OutputStream:   &buf,
--	}
--	err := client.BuildImage(opts)
--	if err != ErrMissingRepo {
--		t.Errorf("BuildImage: wrong error returned. Want %#v. Got %#v.", ErrMissingRepo, err)
--	}
+-func rebootServer(t *testing.T, client *gophercloud.ServiceClient, server *os.Server) {
+-	t.Logf("> servers.Reboot")
+-
+-	err := servers.Reboot(client, server.ID, os.HardReboot).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	err = servers.WaitForStatus(client, server.ID, "ACTIVE", 300)
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Server successfully rebooted.")
 -}
 -
--func TestBuildImageMissingOutputStream(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	opts := BuildImageOptions{Name: "testImage"}
--	err := client.BuildImage(opts)
--	if err != ErrMissingOutputStream {
--		t.Errorf("BuildImage: wrong error returned. Want %#v. Got %#v.", ErrMissingOutputStream, err)
+-func rebuildServer(t *testing.T, client *gophercloud.ServiceClient, server *os.Server) {
+-	t.Logf("> servers.Rebuild")
+-
+-	options, err := optionsFromEnv()
+-	th.AssertNoErr(t, err)
+-
+-	opts := servers.RebuildOpts{
+-		Name:       tools.RandomString("RenamedGopher", 16),
+-		AdminPass:  tools.MakeNewPassword(server.AdminPass),
+-		ImageID:    options.imageID,
+-		DiskConfig: diskconfig.Manual,
 -	}
+-	after, err := servers.Rebuild(client, server.ID, opts).Extract()
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, after.ID, server.ID)
+-
+-	err = servers.WaitForStatus(client, after.ID, "ACTIVE", 300)
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Server successfully rebuilt.")
+-	logServer(t, after, -1)
 -}
 -
--func TestBuildImageWithRawJSON(t *testing.T) {
--	body := `
--	{"stream":"Step 0 : FROM ubuntu:latest\n"}
--	{"stream":" ---\u003e 4300eb9d3c8d\n"}
--	{"stream":"Step 1 : MAINTAINER docker <eng at docker.com>\n"}
--	{"stream":" ---\u003e Using cache\n"}
--	{"stream":" ---\u003e 3a3ed758c370\n"}
--	{"stream":"Step 2 : CMD /usr/bin/top\n"}
--	{"stream":" ---\u003e Running in 36b1479cc2e4\n"}
--	{"stream":" ---\u003e 4b6188aebe39\n"}
--	{"stream":"Removing intermediate container 36b1479cc2e4\n"}
--	{"stream":"Successfully built 4b6188aebe39\n"}
--    `
--	fakeRT := &FakeRoundTripper{
--		message: body,
--		status:  http.StatusOK,
--		header: map[string]string{
--			"Content-Type": "application/json",
--		},
--	}
--	client := newTestClient(fakeRT)
--	var buf bytes.Buffer
--	opts := BuildImageOptions{
--		Name:           "testImage",
--		RmTmpContainer: true,
--		InputStream:    &buf,
--		OutputStream:   &buf,
--		RawJSONStream:  true,
--	}
--	err := client.BuildImage(opts)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if buf.String() != body {
--		t.Errorf("BuildImage: Wrong raw output. Want %q. Got %q.", body, buf.String())
--	}
+-func deleteServer(t *testing.T, client *gophercloud.ServiceClient, server *os.Server) {
+-	t.Logf("> servers.Delete")
+-
+-	res := servers.Delete(client, server.ID)
+-	th.AssertNoErr(t, res.Err)
+-
+-	t.Logf("Server deleted successfully.")
 -}
 -
--func TestBuildImageRemoteWithoutName(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	var buf bytes.Buffer
--	opts := BuildImageOptions{
--		Remote:         "testing/data/container.tar",
--		SuppressOutput: true,
--		OutputStream:   &buf,
--	}
--	err := client.BuildImage(opts)
--	if err != nil {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	expected := map[string][]string{"t": {opts.Remote}, "remote": {opts.Remote}, "q": {"1"}}
--	got := map[string][]string(req.URL.Query())
--	if !reflect.DeepEqual(got, expected) {
--		t.Errorf("BuildImage: wrong query string. Want %#v. Got %#v.", expected, got)
--	}
+-func deleteServerKeyPair(t *testing.T, client *gophercloud.ServiceClient, k *oskey.KeyPair) {
+-	t.Logf("> keypairs.Delete")
+-
+-	err := keypairs.Delete(client, k.Name).ExtractErr()
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Keypair deleted successfully.")
 -}
 -
--func TestTagImageParameters(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	opts := TagImageOptions{Repo: "testImage"}
--	err := client.TagImage("base", opts)
--	if err != nil && strings.Index(err.Error(), "tag image fail") == -1 {
--		t.Fatal(err)
--	}
--	req := fakeRT.requests[0]
--	expected := "http://localhost:4243/images/base/tag?repo=testImage"
--	got := req.URL.String()
--	if !reflect.DeepEqual(got, expected) {
--		t.Errorf("TagImage: wrong query string. Want %#v. Got %#v.", expected, got)
--	}
+-func TestServerOperations(t *testing.T) {
+-	client, err := newClient()
+-	th.AssertNoErr(t, err)
+-
+-	kp := createServerKeyPair(t, client)
+-	defer deleteServerKeyPair(t, client, kp)
+-
+-	server := createServer(t, client, kp.Name)
+-	defer deleteServer(t, client, server)
+-
+-	getServer(t, client, server)
+-	listServers(t, client)
+-	changeAdminPassword(t, client, server)
+-	rebootServer(t, client, server)
+-	rebuildServer(t, client, server)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/virtualinterfaces_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/virtualinterfaces_test.go
+deleted file mode 100644
+index 39475e1..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/compute/v2/virtualinterfaces_test.go
++++ /dev/null
+@@ -1,53 +0,0 @@
+-// +build acceptance rackspace
 -
--func TestTagImageMissingRepo(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	opts := TagImageOptions{Repo: "testImage"}
--	err := client.TagImage("", opts)
--	if err != ErrNoSuchImage {
--		t.Errorf("TestTag: wrong error returned. Want %#v. Got %#v.",
--			ErrNoSuchImage, err)
--	}
+-package v2
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/pagination"
+-	"github.com/rackspace/gophercloud/rackspace/compute/v2/networks"
+-	"github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestVirtualInterfaces(t *testing.T) {
+-	client, err := newClient()
+-	th.AssertNoErr(t, err)
+-
+-	// Create a server
+-	server := createServer(t, client, "")
+-	t.Logf("Created Server: %v\n", server)
+-	defer deleteServer(t, client, server)
+-	serverID := server.ID
+-
+-	// Create a network
+-	n, err := networks.Create(client, networks.CreateOpts{Label: "sample_network", CIDR: "172.20.0.0/24"}).Extract()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Created Network: %v\n", n)
+-	defer networks.Delete(client, n.ID)
+-	networkID := n.ID
+-
+-	// Create a virtual interface
+-	vi, err := virtualinterfaces.Create(client, serverID, networkID).Extract()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Created virtual interface: %+v\n", vi)
+-	defer virtualinterfaces.Delete(client, serverID, vi.ID)
+-
+-	// List virtual interfaces
+-	pager := virtualinterfaces.List(client, serverID)
+-	err = pager.EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page ---")
+-
+-		virtualinterfacesList, err := virtualinterfaces.ExtractVirtualInterfaces(page)
+-		th.AssertNoErr(t, err)
+-
+-		for _, vi := range virtualinterfacesList {
+-			t.Logf("Virtual Interface: ID [%s] MAC Address [%s] IP Addresses [%v]",
+-				vi.ID, vi.MACAddress, vi.IPAddresses)
+-		}
+-
+-		return true, nil
+-	})
+-	th.CheckNoErr(t, err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/identity/v2/extension_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/identity/v2/extension_test.go
+deleted file mode 100644
+index a50e015..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/identity/v2/extension_test.go
++++ /dev/null
+@@ -1,54 +0,0 @@
+-// +build acceptance
 -
--func TestIsUrl(t *testing.T) {
--	url := "http://foo.bar/"
--	result := isURL(url)
--	if !result {
--		t.Errorf("isURL: wrong match. Expected %#v to be a url. Got %#v.", url, result)
--	}
--	url = "/foo/bar.tar"
--	result = isURL(url)
--	if result {
--		t.Errorf("isURL: wrong match. Expected %#v to not be a url. Got %#v", url, result)
+-package v2
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/pagination"
+-	extensions2 "github.com/rackspace/gophercloud/rackspace/identity/v2/extensions"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestExtensions(t *testing.T) {
+-	service := authenticatedClient(t)
+-
+-	t.Logf("Extensions available on this identity endpoint:")
+-	count := 0
+-	var chosen string
+-	err := extensions2.List(service).EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page %02d ---", count)
+-
+-		extensions, err := extensions2.ExtractExtensions(page)
+-		th.AssertNoErr(t, err)
+-
+-		for i, ext := range extensions {
+-			if chosen == "" {
+-				chosen = ext.Alias
+-			}
+-
+-			t.Logf("[%02d] name=[%s] namespace=[%s]", i, ext.Name, ext.Namespace)
+-			t.Logf("     alias=[%s] updated=[%s]", ext.Alias, ext.Updated)
+-			t.Logf("     description=[%s]", ext.Description)
+-		}
+-
+-		count++
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-
+-	if chosen == "" {
+-		t.Logf("No extensions found.")
+-		return
 -	}
+-
+-	ext, err := extensions2.Get(service, chosen).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Detail for extension [%s]:", chosen)
+-	t.Logf("        name=[%s]", ext.Name)
+-	t.Logf("   namespace=[%s]", ext.Namespace)
+-	t.Logf("       alias=[%s]", ext.Alias)
+-	t.Logf("     updated=[%s]", ext.Updated)
+-	t.Logf(" description=[%s]", ext.Description)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/identity/v2/identity_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/identity/v2/identity_test.go
+deleted file mode 100644
+index 1182982..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/identity/v2/identity_test.go
++++ /dev/null
+@@ -1,50 +0,0 @@
+-// +build acceptance
 -
--func TestLoadImage(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	tar, err := os.Open("testing/data/container.tar")
--	if err != nil {
--		t.Fatal(err)
--	} else {
--		defer tar.Close()
--	}
--	opts := LoadImageOptions{InputStream: tar}
--	err = client.LoadImage(opts)
--	if nil != err {
--		t.Error(err)
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "POST" {
--		t.Errorf("LoadImage: wrong method. Expected %q. Got %q.", "POST", req.Method)
+-package v2
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/acceptance/tools"
+-	"github.com/rackspace/gophercloud/rackspace"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func rackspaceAuthOptions(t *testing.T) gophercloud.AuthOptions {
+-	// Obtain credentials from the environment.
+-	options, err := rackspace.AuthOptionsFromEnv()
+-	th.AssertNoErr(t, err)
+-	options = tools.OnlyRS(options)
+-
+-	if options.Username == "" {
+-		t.Fatal("Please provide a Rackspace username as RS_USERNAME.")
 -	}
--	if req.URL.Path != "/images/load" {
--		t.Errorf("LoadImage: wrong URL. Expected %q. Got %q.", "/images/load", req.URL.Path)
+-	if options.APIKey == "" {
+-		t.Fatal("Please provide a Rackspace API key as RS_API_KEY.")
 -	}
+-
+-	return options
 -}
 -
--func TestExportImage(t *testing.T) {
--	var buf bytes.Buffer
--	fakeRT := &FakeRoundTripper{message: "", status: http.StatusOK}
--	client := newTestClient(fakeRT)
--	opts := ExportImageOptions{Name: "testimage", OutputStream: &buf}
--	err := client.ExportImage(opts)
--	if nil != err {
--		t.Error(err)
--	}
--	req := fakeRT.requests[0]
--	if req.Method != "GET" {
--		t.Errorf("ExportImage: wrong method. Expected %q. Got %q.", "GET", req.Method)
--	}
--	expectedPath := "/images/testimage/get"
--	if req.URL.Path != expectedPath {
--		t.Errorf("ExportIMage: wrong path. Expected %q. Got %q.", expectedPath, req.URL.Path)
+-func createClient(t *testing.T, auth bool) *gophercloud.ServiceClient {
+-	ao := rackspaceAuthOptions(t)
+-
+-	provider, err := rackspace.NewClient(ao.IdentityEndpoint)
+-	th.AssertNoErr(t, err)
+-
+-	if auth {
+-		err = rackspace.Authenticate(provider, ao)
+-		th.AssertNoErr(t, err)
 -	}
+-
+-	return rackspace.NewIdentityV2(provider)
 -}
 -
--func TestSearchImages(t *testing.T) {
--	body := `[
--	{
--		"description":"A container with Cassandra 2.0.3",
--		"is_official":true,
--		"is_automated":true,
--		"name":"poklet/cassandra",
--		"star_count":17
--	},
--	{
--		"description":"A container with Cassandra 2.0.3",
--		"is_official":true,
--		"is_automated":false,
--		"name":"poklet/cassandra",
--		"star_count":17
--	}
--	,
--	{
--		"description":"A container with Cassandra 2.0.3",
--		"is_official":false,
--		"is_automated":true,
--		"name":"poklet/cassandra",
--		"star_count":17
--	}
--]`
--	var expected []APIImageSearch
--	err := json.Unmarshal([]byte(body), &expected)
--	if err != nil {
--		t.Fatal(err)
--	}
--	client := newTestClient(&FakeRoundTripper{message: body, status: http.StatusOK})
--	result, err := client.SearchImages("cassandra")
--	if err != nil {
--		t.Error(err)
--	}
--	if !reflect.DeepEqual(result, expected) {
--		t.Errorf("SearchImages: Wrong return value. Want %#v. Got %#v.", expected, result)
--	}
+-func unauthenticatedClient(t *testing.T) *gophercloud.ServiceClient {
+-	return createClient(t, false)
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/misc.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/misc.go
+-
+-func authenticatedClient(t *testing.T) *gophercloud.ServiceClient {
+-	return createClient(t, true)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/identity/v2/tenant_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/identity/v2/tenant_test.go
 deleted file mode 100644
-index 2678ab5..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/misc.go
+index 6081a49..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/identity/v2/tenant_test.go
 +++ /dev/null
-@@ -1,59 +0,0 @@
--// Copyright 2014 go-dockerclient authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the LICENSE file.
+@@ -1,37 +0,0 @@
+-// +build acceptance
 -
--package docker
+-package v2
 -
 -import (
--	"bytes"
--	"strings"
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/pagination"
+-	rstenants "github.com/rackspace/gophercloud/rackspace/identity/v2/tenants"
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--// Version returns version information about the docker server.
--//
--// See http://goo.gl/BOZrF5 for more details.
--func (c *Client) Version() (*Env, error) {
--	body, _, err := c.do("GET", "/version", nil)
--	if err != nil {
--		return nil, err
--	}
--	var env Env
--	if err := env.Decode(bytes.NewReader(body)); err != nil {
--		return nil, err
+-func TestTenants(t *testing.T) {
+-	service := authenticatedClient(t)
+-
+-	t.Logf("Tenants available to the currently issued token:")
+-	count := 0
+-	err := rstenants.List(service, nil).EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page %02d ---", count)
+-
+-		tenants, err := rstenants.ExtractTenants(page)
+-		th.AssertNoErr(t, err)
+-
+-		for i, tenant := range tenants {
+-			t.Logf("[%02d]      id=[%s]", i, tenant.ID)
+-			t.Logf("        name=[%s] enabled=[%v]", i, tenant.Name, tenant.Enabled)
+-			t.Logf(" description=[%s]", tenant.Description)
+-		}
+-
+-		count++
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	if count == 0 {
+-		t.Errorf("No tenants listed for your current token.")
 -	}
--	return &env, nil
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/accounts_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/accounts_test.go
+deleted file mode 100644
+index 145e4e0..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/accounts_test.go
++++ /dev/null
+@@ -1,33 +0,0 @@
+-// +build acceptance rackspace
 -
--// Info returns system-wide information about the Docker server.
--//
--// See http://goo.gl/wmqZsW for more details.
--func (c *Client) Info() (*Env, error) {
--	body, _, err := c.do("GET", "/info", nil)
--	if err != nil {
--		return nil, err
--	}
--	var info Env
--	err = info.Decode(bytes.NewReader(body))
--	if err != nil {
--		return nil, err
--	}
--	return &info, nil
+-package v1
+-
+-import (
+-	"testing"
+-
+-	raxAccounts "github.com/rackspace/gophercloud/rackspace/objectstorage/v1/accounts"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestAccounts(t *testing.T) {
+-	c, err := createClient(t, false)
+-	th.AssertNoErr(t, err)
+-
+-	updateres := raxAccounts.Update(c, raxAccounts.UpdateOpts{Metadata: map[string]string{"white": "mountains"}})
+-	th.AssertNoErr(t, updateres.Err)
+-	t.Logf("Headers from Update Account request: %+v\n", updateres.Header)
+-	defer func() {
+-		updateres = raxAccounts.Update(c, raxAccounts.UpdateOpts{Metadata: map[string]string{"white": ""}})
+-		th.AssertNoErr(t, updateres.Err)
+-		metadata, err := raxAccounts.Get(c).ExtractMetadata()
+-		th.AssertNoErr(t, err)
+-		t.Logf("Metadata from Get Account request (after update reverted): %+v\n", metadata)
+-		th.CheckEquals(t, metadata["White"], "")
+-	}()
+-
+-	metadata, err := raxAccounts.Get(c).ExtractMetadata()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Metadata from Get Account request (after update): %+v\n", metadata)
+-
+-	th.CheckEquals(t, metadata["White"], "mountains")
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/bulk_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/bulk_test.go
+deleted file mode 100644
+index 79013a5..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/bulk_test.go
++++ /dev/null
+@@ -1,23 +0,0 @@
+-// +build acceptance rackspace objectstorage v1
 -
--// ParseRepositoryTag gets the name of the repository and returns it splitted
--// in two parts: the repository and the tag.
--//
--// Some examples:
--//
--//     localhost.localdomain:5000/samalba/hipache:latest -> localhost.localdomain:5000/samalba/hipache, latest
--//     localhost.localdomain:5000/samalba/hipache -> localhost.localdomain:5000/samalba/hipache, ""
--func ParseRepositoryTag(repoTag string) (repository string, tag string) {
--	n := strings.LastIndex(repoTag, ":")
--	if n < 0 {
--		return repoTag, ""
--	}
--	if tag := repoTag[n+1:]; !strings.Contains(tag, "/") {
--		return repoTag[:n], tag
+-package v1
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestBulk(t *testing.T) {
+-	c, err := createClient(t, false)
+-	th.AssertNoErr(t, err)
+-
+-	var options bulk.DeleteOpts
+-	options = append(options, "container/object1")
+-	res := bulk.Delete(c, options)
+-	th.AssertNoErr(t, res.Err)
+-	body, err := res.ExtractBody()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Response body from Bulk Delete Request: %+v\n", body)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/cdncontainers_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/cdncontainers_test.go
+deleted file mode 100644
+index e1bf38b..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/cdncontainers_test.go
++++ /dev/null
+@@ -1,61 +0,0 @@
+-// +build acceptance rackspace objectstorage v1
+-
+-package v1
+-
+-import (
+-	"testing"
+-
+-	osContainers "github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers"
+-	"github.com/rackspace/gophercloud/pagination"
+-	raxCDNContainers "github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers"
+-	raxContainers "github.com/rackspace/gophercloud/rackspace/objectstorage/v1/containers"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestCDNContainers(t *testing.T) {
+-	raxClient, err := createClient(t, false)
+-	th.AssertNoErr(t, err)
+-
+-	createres := raxContainers.Create(raxClient, "gophercloud-test", nil)
+-	th.AssertNoErr(t, createres.Err)
+-	t.Logf("Headers from Create Container request: %+v\n", createres.Header)
+-	defer func() {
+-		res := raxContainers.Delete(raxClient, "gophercloud-test")
+-		th.AssertNoErr(t, res.Err)
+-	}()
+-
+-	raxCDNClient, err := createClient(t, true)
+-	th.AssertNoErr(t, err)
+-
+-	r := raxCDNContainers.Enable(raxCDNClient, "gophercloud-test", raxCDNContainers.EnableOpts{CDNEnabled: true, TTL: 900})
+-	th.AssertNoErr(t, r.Err)
+-	t.Logf("Headers from Enable CDN Container request: %+v\n", r.Header)
+-
+-	t.Logf("Container Names available to the currently issued token:")
+-	count := 0
+-	err = raxCDNContainers.List(raxCDNClient, &osContainers.ListOpts{Full: false}).EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page %02d ---", count)
+-
+-		names, err := raxCDNContainers.ExtractNames(page)
+-		th.AssertNoErr(t, err)
+-
+-		for i, name := range names {
+-			t.Logf("[%02d] %s", i, name)
+-		}
+-
+-		count++
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	if count == 0 {
+-		t.Errorf("No CDN containers listed for your current token.")
 -	}
--	return repoTag, ""
+-
+-	updateres := raxCDNContainers.Update(raxCDNClient, "gophercloud-test", raxCDNContainers.UpdateOpts{CDNEnabled: false})
+-	th.AssertNoErr(t, updateres.Err)
+-	t.Logf("Headers from Update CDN Container request: %+v\n", updateres.Header)
+-
+-	metadata, err := raxCDNContainers.Get(raxCDNClient, "gophercloud-test").ExtractMetadata()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Headers from Get CDN Container request (after update): %+v\n", metadata)
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/misc_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/misc_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/cdnobjects_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/cdnobjects_test.go
 deleted file mode 100644
-index ceaf076..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/misc_test.go
+index 6e477ae..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/cdnobjects_test.go
 +++ /dev/null
-@@ -1,159 +0,0 @@
--// Copyright 2014 go-dockerclient authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the LICENSE file.
+@@ -1,46 +0,0 @@
+-// +build acceptance rackspace objectstorage v1
 -
--package docker
+-package v1
 -
 -import (
--	"net/http"
--	"net/url"
--	"reflect"
--	"sort"
+-	"bytes"
 -	"testing"
+-
+-	raxCDNContainers "github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers"
+-	raxCDNObjects "github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdnobjects"
+-	raxContainers "github.com/rackspace/gophercloud/rackspace/objectstorage/v1/containers"
+-	raxObjects "github.com/rackspace/gophercloud/rackspace/objectstorage/v1/objects"
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--type DockerVersion struct {
--	Version   string
--	GitCommit string
--	GoVersion string
+-func TestCDNObjects(t *testing.T) {
+-	raxClient, err := createClient(t, false)
+-	th.AssertNoErr(t, err)
+-
+-	createContResult := raxContainers.Create(raxClient, "gophercloud-test", nil)
+-	th.AssertNoErr(t, createContResult.Err)
+-	t.Logf("Headers from Create Container request: %+v\n", createContResult.Header)
+-	defer func() {
+-		deleteResult := raxContainers.Delete(raxClient, "gophercloud-test")
+-		th.AssertNoErr(t, deleteResult.Err)
+-	}()
+-
+-	header, err := raxObjects.Create(raxClient, "gophercloud-test", "test-object", bytes.NewBufferString("gophercloud cdn test"), nil).ExtractHeader()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Headers from Create Object request: %+v\n", header)
+-	defer func() {
+-		deleteResult := raxObjects.Delete(raxClient, "gophercloud-test", "test-object", nil)
+-		th.AssertNoErr(t, deleteResult.Err)
+-	}()
+-
+-	raxCDNClient, err := createClient(t, true)
+-	th.AssertNoErr(t, err)
+-
+-	enableResult := raxCDNContainers.Enable(raxCDNClient, "gophercloud-test", raxCDNContainers.EnableOpts{CDNEnabled: true, TTL: 900})
+-	th.AssertNoErr(t, enableResult.Err)
+-	t.Logf("Headers from Enable CDN Container request: %+v\n", enableResult.Header)
+-
+-	deleteResult := raxCDNObjects.Delete(raxCDNClient, "gophercloud-test", "test-object", nil)
+-	th.AssertNoErr(t, deleteResult.Err)
+-	t.Logf("Headers from Delete CDN Object request: %+v\n", deleteResult.Err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/common.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/common.go
+deleted file mode 100644
+index 1ae0727..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/common.go
++++ /dev/null
+@@ -1,54 +0,0 @@
+-// +build acceptance rackspace objectstorage v1
 -
--func TestVersion(t *testing.T) {
--	body := `{
--     "Version":"0.2.2",
--     "GitCommit":"5a2a5cc+CHANGES",
--     "GoVersion":"go1.0.3"
--}`
--	fakeRT := FakeRoundTripper{message: body, status: http.StatusOK}
--	client := newTestClient(&fakeRT)
--	expected := DockerVersion{
--		Version:   "0.2.2",
--		GitCommit: "5a2a5cc+CHANGES",
--		GoVersion: "go1.0.3",
+-package v1
+-
+-import (
+-	"os"
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/acceptance/tools"
+-	"github.com/rackspace/gophercloud/rackspace"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func rackspaceAuthOptions(t *testing.T) gophercloud.AuthOptions {
+-	// Obtain credentials from the environment.
+-	options, err := rackspace.AuthOptionsFromEnv()
+-	th.AssertNoErr(t, err)
+-	options = tools.OnlyRS(options)
+-
+-	if options.Username == "" {
+-		t.Fatal("Please provide a Rackspace username as RS_USERNAME.")
 -	}
--	version, err := client.Version()
--	if err != nil {
--		t.Fatal(err)
+-	if options.APIKey == "" {
+-		t.Fatal("Please provide a Rackspace API key as RS_API_KEY.")
 -	}
 -
--	if result := version.Get("Version"); result != expected.Version {
--		t.Errorf("Version(): Wrong result. Want %#v. Got %#v.", expected.Version, version.Get("Version"))
--	}
--	if result := version.Get("GitCommit"); result != expected.GitCommit {
--		t.Errorf("GitCommit(): Wrong result. Want %#v. Got %#v.", expected.GitCommit, version.Get("GitCommit"))
+-	return options
+-}
+-
+-func createClient(t *testing.T, cdn bool) (*gophercloud.ServiceClient, error) {
+-	region := os.Getenv("RS_REGION")
+-	if region == "" {
+-		t.Fatal("Please provide a Rackspace region as RS_REGION")
 -	}
--	if result := version.Get("GoVersion"); result != expected.GoVersion {
--		t.Errorf("GoVersion(): Wrong result. Want %#v. Got %#v.", expected.GoVersion, version.Get("GoVersion"))
+-
+-	ao := rackspaceAuthOptions(t)
+-
+-	provider, err := rackspace.NewClient(ao.IdentityEndpoint)
+-	th.AssertNoErr(t, err)
+-
+-	err = rackspace.Authenticate(provider, ao)
+-	th.AssertNoErr(t, err)
+-
+-	if cdn {
+-		return rackspace.NewObjectCDNV1(provider, gophercloud.EndpointOpts{
+-			Region: region,
+-		})
 -	}
--	req := fakeRT.requests[0]
--	if req.Method != "GET" {
--		t.Errorf("Version(): wrong request method. Want GET. Got %s.", req.Method)
+-
+-	return rackspace.NewObjectStorageV1(provider, gophercloud.EndpointOpts{
+-		Region: region,
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/containers_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/containers_test.go
+deleted file mode 100644
+index a7339cf..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/containers_test.go
++++ /dev/null
+@@ -1,85 +0,0 @@
+-// +build acceptance rackspace objectstorage v1
+-
+-package v1
+-
+-import (
+-	"testing"
+-
+-	osContainers "github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers"
+-	"github.com/rackspace/gophercloud/pagination"
+-	raxContainers "github.com/rackspace/gophercloud/rackspace/objectstorage/v1/containers"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestContainers(t *testing.T) {
+-	c, err := createClient(t, false)
+-	th.AssertNoErr(t, err)
+-
+-	t.Logf("Containers Info available to the currently issued token:")
+-	count := 0
+-	err = raxContainers.List(c, &osContainers.ListOpts{Full: true}).EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page %02d ---", count)
+-
+-		containers, err := raxContainers.ExtractInfo(page)
+-		th.AssertNoErr(t, err)
+-
+-		for i, container := range containers {
+-			t.Logf("[%02d]      name=[%s]", i, container.Name)
+-			t.Logf("            count=[%d]", container.Count)
+-			t.Logf("            bytes=[%d]", container.Bytes)
+-		}
+-
+-		count++
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	if count == 0 {
+-		t.Errorf("No containers listed for your current token.")
 -	}
--	u, _ := url.Parse(client.getURL("/version"))
--	if req.URL.Path != u.Path {
--		t.Errorf("Version(): wrong request path. Want %q. Got %q.", u.Path, req.URL.Path)
+-
+-	t.Logf("Container Names available to the currently issued token:")
+-	count = 0
+-	err = raxContainers.List(c, &osContainers.ListOpts{Full: false}).EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page %02d ---", count)
+-
+-		names, err := raxContainers.ExtractNames(page)
+-		th.AssertNoErr(t, err)
+-
+-		for i, name := range names {
+-			t.Logf("[%02d] %s", i, name)
+-		}
+-
+-		count++
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	if count == 0 {
+-		t.Errorf("No containers listed for your current token.")
 -	}
+-
+-	createres := raxContainers.Create(c, "gophercloud-test", nil)
+-	th.AssertNoErr(t, createres.Err)
+-	defer func() {
+-		res := raxContainers.Delete(c, "gophercloud-test")
+-		th.AssertNoErr(t, res.Err)
+-	}()
+-
+-	updateres := raxContainers.Update(c, "gophercloud-test", raxContainers.UpdateOpts{Metadata: map[string]string{"white": "mountains"}})
+-	th.AssertNoErr(t, updateres.Err)
+-	t.Logf("Headers from Update Account request: %+v\n", updateres.Header)
+-	defer func() {
+-		res := raxContainers.Update(c, "gophercloud-test", raxContainers.UpdateOpts{Metadata: map[string]string{"white": ""}})
+-		th.AssertNoErr(t, res.Err)
+-		metadata, err := raxContainers.Get(c, "gophercloud-test").ExtractMetadata()
+-		th.AssertNoErr(t, err)
+-		t.Logf("Metadata from Get Account request (after update reverted): %+v\n", metadata)
+-		th.CheckEquals(t, metadata["White"], "")
+-	}()
+-
+-	getres := raxContainers.Get(c, "gophercloud-test")
+-	t.Logf("Headers from Get Account request (after update): %+v\n", getres.Header)
+-	metadata, err := getres.ExtractMetadata()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Metadata from Get Account request (after update): %+v\n", metadata)
+-	th.CheckEquals(t, metadata["White"], "mountains")
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/objects_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/objects_test.go
+deleted file mode 100644
+index 462f284..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/objectstorage/v1/objects_test.go
++++ /dev/null
+@@ -1,112 +0,0 @@
+-// +build acceptance rackspace objectstorage v1
 -
--func TestVersionError(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "internal error", status: http.StatusInternalServerError}
--	client := newTestClient(fakeRT)
--	version, err := client.Version()
--	if version != nil {
--		t.Errorf("Version(): expected <nil> value, got %#v.", version)
+-package v1
+-
+-import (
+-	"bytes"
+-	"testing"
+-
+-	osObjects "github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects"
+-	"github.com/rackspace/gophercloud/pagination"
+-	raxContainers "github.com/rackspace/gophercloud/rackspace/objectstorage/v1/containers"
+-	raxObjects "github.com/rackspace/gophercloud/rackspace/objectstorage/v1/objects"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestObjects(t *testing.T) {
+-	c, err := createClient(t, false)
+-	th.AssertNoErr(t, err)
+-
+-	res := raxContainers.Create(c, "gophercloud-test", nil)
+-	th.AssertNoErr(t, res.Err)
+-
+-	defer func() {
+-		res := raxContainers.Delete(c, "gophercloud-test")
+-		th.AssertNoErr(t, res.Err)
+-	}()
+-
+-	content := bytes.NewBufferString("Lewis Carroll")
+-	options := &osObjects.CreateOpts{ContentType: "text/plain"}
+-	createres := raxObjects.Create(c, "gophercloud-test", "o1", content, options)
+-	th.AssertNoErr(t, createres.Err)
+-	defer func() {
+-		res := raxObjects.Delete(c, "gophercloud-test", "o1", nil)
+-		th.AssertNoErr(t, res.Err)
+-	}()
+-
+-	t.Logf("Objects Info available to the currently issued token:")
+-	count := 0
+-	err = raxObjects.List(c, "gophercloud-test", &osObjects.ListOpts{Full: true}).EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page %02d ---", count)
+-
+-		objects, err := raxObjects.ExtractInfo(page)
+-		th.AssertNoErr(t, err)
+-
+-		for i, object := range objects {
+-			t.Logf("[%02d]      name=[%s]", i, object.Name)
+-			t.Logf("            content-type=[%s]", object.ContentType)
+-			t.Logf("            bytes=[%d]", object.Bytes)
+-			t.Logf("            last-modified=[%s]", object.LastModified)
+-			t.Logf("            hash=[%s]", object.Hash)
+-		}
+-
+-		count++
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	if count == 0 {
+-		t.Errorf("No objects listed for your current token.")
 -	}
--	if err == nil {
--		t.Error("Version(): unexpected <nil> error")
+-	t.Logf("Container Names available to the currently issued token:")
+-	count = 0
+-	err = raxObjects.List(c, "gophercloud-test", &osObjects.ListOpts{Full: false}).EachPage(func(page pagination.Page) (bool, error) {
+-		t.Logf("--- Page %02d ---", count)
+-
+-		names, err := raxObjects.ExtractNames(page)
+-		th.AssertNoErr(t, err)
+-
+-		for i, name := range names {
+-			t.Logf("[%02d] %s", i, name)
+-		}
+-
+-		count++
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	if count == 0 {
+-		t.Errorf("No objects listed for your current token.")
 -	}
+-
+-	copyres := raxObjects.Copy(c, "gophercloud-test", "o1", &raxObjects.CopyOpts{Destination: "gophercloud-test/o2"})
+-	th.AssertNoErr(t, copyres.Err)
+-	defer func() {
+-		res := raxObjects.Delete(c, "gophercloud-test", "o2", nil)
+-		th.AssertNoErr(t, res.Err)
+-	}()
+-
+-	o1Content, err := raxObjects.Download(c, "gophercloud-test", "o1", nil).ExtractContent()
+-	th.AssertNoErr(t, err)
+-	o2Content, err := raxObjects.Download(c, "gophercloud-test", "o2", nil).ExtractContent()
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, string(o2Content), string(o1Content))
+-
+-	updateres := raxObjects.Update(c, "gophercloud-test", "o2", osObjects.UpdateOpts{Metadata: map[string]string{"white": "mountains"}})
+-	th.AssertNoErr(t, updateres.Err)
+-	t.Logf("Headers from Update Account request: %+v\n", updateres.Header)
+-	defer func() {
+-		res := raxObjects.Update(c, "gophercloud-test", "o2", osObjects.UpdateOpts{Metadata: map[string]string{"white": ""}})
+-		th.AssertNoErr(t, res.Err)
+-		metadata, err := raxObjects.Get(c, "gophercloud-test", "o2", nil).ExtractMetadata()
+-		th.AssertNoErr(t, err)
+-		t.Logf("Metadata from Get Account request (after update reverted): %+v\n", metadata)
+-		th.CheckEquals(t, metadata["White"], "")
+-	}()
+-
+-	getres := raxObjects.Get(c, "gophercloud-test", "o2", nil)
+-	th.AssertNoErr(t, getres.Err)
+-	t.Logf("Headers from Get Account request (after update): %+v\n", getres.Header)
+-	metadata, err := getres.ExtractMetadata()
+-	th.AssertNoErr(t, err)
+-	t.Logf("Metadata from Get Account request (after update): %+v\n", metadata)
+-	th.CheckEquals(t, metadata["White"], "mountains")
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/pkg.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/pkg.go
+deleted file mode 100644
+index 5d17b32..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/rackspace/pkg.go
++++ /dev/null
+@@ -1 +0,0 @@
+-package rackspace
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/tools/pkg.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/tools/pkg.go
+deleted file mode 100644
+index f7eca12..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/tools/pkg.go
++++ /dev/null
+@@ -1 +0,0 @@
+-package tools
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/tools/tools.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/tools/tools.go
+deleted file mode 100644
+index 61b1d7a..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/tools/tools.go
++++ /dev/null
+@@ -1,82 +0,0 @@
+-// +build acceptance
 -
--func TestInfo(t *testing.T) {
--	body := `{
--     "Containers":11,
--     "Images":16,
--     "Debug":0,
--     "NFd":11,
--     "NGoroutines":21,
--     "MemoryLimit":1,
--     "SwapLimit":0
--}`
--	fakeRT := FakeRoundTripper{message: body, status: http.StatusOK}
--	client := newTestClient(&fakeRT)
--	expected := Env{}
--	expected.SetInt("Containers", 11)
--	expected.SetInt("Images", 16)
--	expected.SetBool("Debug", false)
--	expected.SetInt("NFd", 11)
--	expected.SetInt("NGoroutines", 21)
--	expected.SetBool("MemoryLimit", true)
--	expected.SetBool("SwapLimit", false)
--	info, err := client.Info()
--	if err != nil {
--		t.Fatal(err)
+-package tools
+-
+-import (
+-	"crypto/rand"
+-	"errors"
+-	"os"
+-	"time"
+-
+-	"github.com/rackspace/gophercloud"
+-)
+-
+-// ErrTimeout is returned if WaitFor takes longer than 300 second to happen.
+-var ErrTimeout = errors.New("Timed out")
+-
+-// OnlyRS overrides the default Gophercloud behavior of using OS_-prefixed environment variables
+-// if RS_ variables aren't present. Otherwise, they'll stomp over each other here in the acceptance
+-// tests, where you need to have both defined.
+-func OnlyRS(original gophercloud.AuthOptions) gophercloud.AuthOptions {
+-	if os.Getenv("RS_AUTH_URL") == "" {
+-		original.IdentityEndpoint = ""
 -	}
--	infoSlice := []string(*info)
--	expectedSlice := []string(expected)
--	sort.Strings(infoSlice)
--	sort.Strings(expectedSlice)
--	if !reflect.DeepEqual(expectedSlice, infoSlice) {
--		t.Errorf("Info(): Wrong result.\nWant %#v.\nGot %#v.", expected, *info)
+-	if os.Getenv("RS_USERNAME") == "" {
+-		original.Username = ""
 -	}
--	req := fakeRT.requests[0]
--	if req.Method != "GET" {
--		t.Errorf("Info(): Wrong HTTP method. Want GET. Got %s.", req.Method)
+-	if os.Getenv("RS_PASSWORD") == "" {
+-		original.Password = ""
 -	}
--	u, _ := url.Parse(client.getURL("/info"))
--	if req.URL.Path != u.Path {
--		t.Errorf("Info(): Wrong request path. Want %q. Got %q.", u.Path, req.URL.Path)
+-	if os.Getenv("RS_API_KEY") == "" {
+-		original.APIKey = ""
 -	}
+-	return original
 -}
 -
--func TestInfoError(t *testing.T) {
--	fakeRT := &FakeRoundTripper{message: "internal error", status: http.StatusInternalServerError}
--	client := newTestClient(fakeRT)
--	version, err := client.Info()
--	if version != nil {
--		t.Errorf("Info(): expected <nil> value, got %#v.", version)
+-// WaitFor polls a predicate function once per second to wait for a certain state to arrive.
+-func WaitFor(predicate func() (bool, error)) error {
+-	for i := 0; i < 300; i++ {
+-		time.Sleep(1 * time.Second)
+-
+-		satisfied, err := predicate()
+-		if err != nil {
+-			return err
+-		}
+-		if satisfied {
+-			return nil
+-		}
 -	}
--	if err == nil {
--		t.Error("Info(): unexpected <nil> error")
+-	return ErrTimeout
+-}
+-
+-// MakeNewPassword generates a new string that's guaranteed to be different than the given one.
+-func MakeNewPassword(oldPass string) string {
+-	randomPassword := RandomString("", 16)
+-	for randomPassword == oldPass {
+-		randomPassword = RandomString("", 16)
 -	}
+-	return randomPassword
 -}
 -
--func TestParseRepositoryTag(t *testing.T) {
--	var tests = []struct {
--		input        string
--		expectedRepo string
--		expectedTag  string
--	}{
--		{
--			"localhost.localdomain:5000/samalba/hipache:latest",
--			"localhost.localdomain:5000/samalba/hipache",
--			"latest",
--		},
--		{
--			"localhost.localdomain:5000/samalba/hipache",
--			"localhost.localdomain:5000/samalba/hipache",
--			"",
--		},
--		{
--			"tsuru/python",
--			"tsuru/python",
--			"",
--		},
--		{
--			"tsuru/python:2.7",
--			"tsuru/python",
--			"2.7",
--		},
+-// 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))]
 -	}
--	for _, tt := range tests {
--		repo, tag := ParseRepositoryTag(tt.input)
--		if repo != tt.expectedRepo {
--			t.Errorf("ParseRepositoryTag(%q): wrong repository. Want %q. Got %q", tt.input, tt.expectedRepo, repo)
--		}
--		if tag != tt.expectedTag {
--			t.Errorf("ParseRepositoryTag(%q): wrong tag. Want %q. Got %q", tt.input, tt.expectedTag, tag)
--		}
+-	return prefix + string(bytes)
+-}
+-
+-// Elide returns the first bit of its input string with a suffix of "..." if it's longer than
+-// a comfortable 40 characters.
+-func Elide(value string) string {
+-	if len(value) > 40 {
+-		return value[0:37] + "..."
 -	}
+-	return value
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/signal.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/signal.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/auth_options.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/auth_options.go
 deleted file mode 100644
-index 16aa003..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/signal.go
+index bc0ef65..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/auth_options.go
 +++ /dev/null
-@@ -1,49 +0,0 @@
--// Copyright 2014 go-dockerclient authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the LICENSE file.
+@@ -1,38 +0,0 @@
+-package gophercloud
 -
--package docker
+-// AuthOptions allows anyone calling Authenticate to supply the required access
+-// credentials. Its fields are the union of those recognized by each identity
+-// implementation and provider.
+-type AuthOptions struct {
+-	// IdentityEndpoint specifies the HTTP endpoint that is required to work with
+-	// the Identity API of the appropriate version. Required by the identity
+-	// services, but often populated by a provider Client.
+-	IdentityEndpoint string
+-
+-	// Username is required if using Identity V2 API. Consult with your provider's
+-	// control panel to discover your account's username. In Identity V3, either
+-	// UserID or a combination of Username and DomainID or DomainName.
+-	Username, UserID string
+-
+-	// Exactly one of Password or ApiKey is required for the Identity V2 and V3
+-	// APIs. Consult with your provider's control panel to discover your account's
+-	// preferred method of authentication.
+-	Password, APIKey string
+-
+-	// At most one of DomainID and DomainName must be provided if using Username
+-	// with Identity V3. Otherwise, either are optional.
+-	DomainID, DomainName string
+-
+-	// The TenantID and TenantName fields are optional for the Identity V2 API.
+-	// Some providers allow you to specify a TenantName instead of the TenantId.
+-	// Some require both.  Your provider's authentication policies will determine
+-	// how these fields influence authentication.
+-	TenantID, TenantName string
+-
+-	// AllowReauth should be set to true if you grant permission for Gophercloud to
+-	// cache your credentials in memory, and to allow Gophercloud to attempt to
+-	// re-authenticate automatically if/when your token expires.  If you set it to
+-	// false, it will not cache these settings, but re-authentication will not be
+-	// possible.  This setting defaults to false.
+-	AllowReauth bool
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/auth_results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/auth_results.go
+deleted file mode 100644
+index 1a1faa5..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/auth_results.go
++++ /dev/null
+@@ -1,15 +0,0 @@
+-package gophercloud
 -
--// Signal represents a signal that can be send to the container on
--// KillContainer call.
--type Signal int
+-import "time"
 -
--// These values represent all signals available on Linux, where containers will
--// be running.
--const (
--	SIGABRT   = Signal(0x6)
--	SIGALRM   = Signal(0xe)
--	SIGBUS    = Signal(0x7)
--	SIGCHLD   = Signal(0x11)
--	SIGCLD    = Signal(0x11)
--	SIGCONT   = Signal(0x12)
--	SIGFPE    = Signal(0x8)
--	SIGHUP    = Signal(0x1)
--	SIGILL    = Signal(0x4)
--	SIGINT    = Signal(0x2)
--	SIGIO     = Signal(0x1d)
--	SIGIOT    = Signal(0x6)
--	SIGKILL   = Signal(0x9)
--	SIGPIPE   = Signal(0xd)
--	SIGPOLL   = Signal(0x1d)
--	SIGPROF   = Signal(0x1b)
--	SIGPWR    = Signal(0x1e)
--	SIGQUIT   = Signal(0x3)
--	SIGSEGV   = Signal(0xb)
--	SIGSTKFLT = Signal(0x10)
--	SIGSTOP   = Signal(0x13)
--	SIGSYS    = Signal(0x1f)
--	SIGTERM   = Signal(0xf)
--	SIGTRAP   = Signal(0x5)
--	SIGTSTP   = Signal(0x14)
--	SIGTTIN   = Signal(0x15)
--	SIGTTOU   = Signal(0x16)
--	SIGUNUSED = Signal(0x1f)
--	SIGURG    = Signal(0x17)
--	SIGUSR1   = Signal(0xa)
--	SIGUSR2   = Signal(0xc)
--	SIGVTALRM = Signal(0x1a)
--	SIGWINCH  = Signal(0x1c)
--	SIGXCPU   = Signal(0x18)
--	SIGXFSZ   = Signal(0x19)
--)
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/stdcopy.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/stdcopy.go
+-// AuthResults encapsulates the raw results from an authentication request. As OpenStack allows
+-// extensions to influence the structure returned in ways that Gophercloud cannot predict at
+-// compile-time, you should use type-safe accessors to work with the data represented by this type,
+-// such as ServiceCatalog and TokenID.
+-type AuthResults interface {
+-	// TokenID returns the token's ID value from the authentication response.
+-	TokenID() (string, error)
+-
+-	// ExpiresAt retrieves the token's expiration time.
+-	ExpiresAt() (time.Time, error)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/endpoint_search.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/endpoint_search.go
 deleted file mode 100644
-index 3782f3d..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/stdcopy.go
+index b6f6b48..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/endpoint_search.go
 +++ /dev/null
-@@ -1,91 +0,0 @@
--// Copyright 2014 Docker authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the DOCKER-LICENSE file.
+@@ -1,65 +0,0 @@
+-package gophercloud
 -
--package docker
+-import "errors"
 -
--import (
--	"encoding/binary"
--	"errors"
--	"io"
+-var (
+-	// ErrServiceNotFound is returned when no service matches the EndpointOpts.
+-	ErrServiceNotFound = errors.New("No suitable service could be found in the service catalog.")
+-
+-	// ErrEndpointNotFound is returned when no available endpoints match the provided EndpointOpts.
+-	ErrEndpointNotFound = errors.New("No suitable endpoint could be found in the service catalog.")
 -)
 -
+-// Availability indicates whether a specific service endpoint is accessible.
+-// Identity v2 lists these as different kinds of URLs ("adminURL",
+-// "internalURL", and "publicURL"), while v3 lists them as "Interfaces".
+-type Availability string
+-
 -const (
--	stdWriterPrefixLen = 8
--	stdWriterFdIndex   = 0
--	stdWriterSizeIndex = 4
+-	// AvailabilityAdmin makes an endpoint only available to administrators.
+-	AvailabilityAdmin Availability = "admin"
+-
+-	// AvailabilityPublic makes an endpoint available to everyone.
+-	AvailabilityPublic Availability = "public"
+-
+-	// AvailabilityInternal makes an endpoint only available within the cluster.
+-	AvailabilityInternal Availability = "internal"
 -)
 -
--var errInvalidStdHeader = errors.New("Unrecognized input header")
+-// EndpointOpts contains options for finding an endpoint for an Openstack client.
+-type EndpointOpts struct {
+-	// Type is the service type for the client (e.g., "compute", "object-store").
+-	// Required.
+-	Type string
 -
--func stdCopy(dstout, dsterr io.Writer, src io.Reader) (written int64, err error) {
--	var (
--		buf       = make([]byte, 32*1024+stdWriterPrefixLen+1)
--		bufLen    = len(buf)
--		nr, nw    int
--		er, ew    error
--		out       io.Writer
--		frameSize int
--	)
--	for {
--		for nr < stdWriterPrefixLen {
--			var nr2 int
--			nr2, er = src.Read(buf[nr:])
--			if er == io.EOF {
--				if nr < stdWriterPrefixLen && nr2 < stdWriterPrefixLen {
--					return written, nil
--				}
--				nr += nr2
--				break
--			} else if er != nil {
--				return 0, er
--			}
--			nr += nr2
--		}
--		switch buf[stdWriterFdIndex] {
--		case 0:
--			fallthrough
--		case 1:
--			out = dstout
--		case 2:
--			out = dsterr
--		default:
--			return 0, errInvalidStdHeader
--		}
--		frameSize = int(binary.BigEndian.Uint32(buf[stdWriterSizeIndex : stdWriterSizeIndex+4]))
--		if frameSize+stdWriterPrefixLen > bufLen {
--			buf = append(buf, make([]byte, frameSize+stdWriterPrefixLen-len(buf)+1)...)
--			bufLen = len(buf)
--		}
--		for nr < frameSize+stdWriterPrefixLen {
--			var nr2 int
--			nr2, er = src.Read(buf[nr:])
--			if er == io.EOF {
--				if nr == 0 {
--					return written, nil
--				}
--				nr += nr2
--				break
--			} else if er != nil {
--				return 0, er
--			}
--			nr += nr2
--		}
--		bound := frameSize + stdWriterPrefixLen
--		if bound > nr {
--			bound = nr
--		}
--		nw, ew = out.Write(buf[stdWriterPrefixLen:bound])
--		if nw > 0 {
--			written += int64(nw)
--		}
--		if ew != nil {
--			return 0, ew
--		}
--		if nw != frameSize {
--			return written, io.ErrShortWrite
--		}
--		copy(buf, buf[frameSize+stdWriterPrefixLen:])
--		nr -= frameSize + stdWriterPrefixLen
+-	// Name is the service name for the client (e.g., "nova") as it appears in
+-	// the service catalog. Services can have the same Type but a different Name,
+-	// which is why both Type and Name are sometimes needed. Optional.
+-	Name string
+-
+-	// Region is the geographic region in which the service resides. Required only
+-	// for services that span multiple regions.
+-	Region string
+-
+-	// Availability is the visibility of the endpoint to be returned. Valid types
+-	// are: AvailabilityPublic, AvailabilityInternal, or AvailabilityAdmin.
+-	// Availability is not required, and defaults to AvailabilityPublic.
+-	// Not all providers or services offer all Availability options.
+-	Availability Availability
+-}
+-
+-// EndpointLocator is a function that describes how to locate a single endpoint
+-// from a service catalog for a specific ProviderClient. It should be set
+-// during ProviderClient authentication and used to discover related ServiceClients.
+-type EndpointLocator func(EndpointOpts) (string, error)
+-
+-// ApplyDefaults sets EndpointOpts fields if not already set. Currently,
+-// EndpointOpts.Availability defaults to the public endpoint.
+-func (eo *EndpointOpts) ApplyDefaults(t string) {
+-	if eo.Type == "" {
+-		eo.Type = t
+-	}
+-	if eo.Availability == "" {
+-		eo.Availability = AvailabilityPublic
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/stdcopy_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/stdcopy_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/endpoint_search_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/endpoint_search_test.go
 deleted file mode 100644
-index 75b8922..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/stdcopy_test.go
+index 3457453..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/endpoint_search_test.go
 +++ /dev/null
-@@ -1,255 +0,0 @@
--// Copyright 2014 go-dockerclient authors. All rights reserved.
--// Use of this source code is governed by a BSD-style
--// license that can be found in the DOCKER-LICENSE file.
--
--package docker
+@@ -1,19 +0,0 @@
+-package gophercloud
 -
 -import (
--	"bytes"
--	"encoding/binary"
--	"errors"
--	"io"
--	"strings"
 -	"testing"
--	"testing/iotest"
+-
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--type errorWriter struct {
--}
+-func TestApplyDefaultsToEndpointOpts(t *testing.T) {
+-	eo := EndpointOpts{Availability: AvailabilityPublic}
+-	eo.ApplyDefaults("compute")
+-	expected := EndpointOpts{Availability: AvailabilityPublic, Type: "compute"}
+-	th.CheckDeepEquals(t, expected, eo)
 -
--func (errorWriter) Write([]byte) (int, error) {
--	return 0, errors.New("something went wrong")
+-	eo = EndpointOpts{Type: "compute"}
+-	eo.ApplyDefaults("object-store")
+-	expected = EndpointOpts{Availability: AvailabilityPublic, Type: "compute"}
+-	th.CheckDeepEquals(t, expected, eo)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/auth_env.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/auth_env.go
+deleted file mode 100644
+index a4402b6..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/auth_env.go
++++ /dev/null
+@@ -1,58 +0,0 @@
+-package openstack
 -
--func TestStdCopy(t *testing.T) {
--	var input, stdout, stderr bytes.Buffer
--	input.Write([]byte{2, 0, 0, 0, 0, 0, 0, 19})
--	input.Write([]byte("something happened!"))
--	input.Write([]byte{1, 0, 0, 0, 0, 0, 0, 12})
--	input.Write([]byte("just kidding"))
--	input.Write([]byte{0, 0, 0, 0, 0, 0, 0, 6})
--	input.Write([]byte("\nyeah!"))
--	n, err := stdCopy(&stdout, &stderr, &input)
--	if err != nil {
--		t.Fatal(err)
+-import (
+-	"fmt"
+-	"os"
+-
+-	"github.com/rackspace/gophercloud"
+-)
+-
+-var nilOptions = gophercloud.AuthOptions{}
+-
+-// ErrNoAuthUrl, ErrNoUsername, and ErrNoPassword errors indicate of the required OS_AUTH_URL, OS_USERNAME, or OS_PASSWORD
+-// environment variables, respectively, remain undefined.  See the AuthOptions() function for more details.
+-var (
+-	ErrNoAuthURL  = fmt.Errorf("Environment variable OS_AUTH_URL needs to be set.")
+-	ErrNoUsername = fmt.Errorf("Environment variable OS_USERNAME needs to be set.")
+-	ErrNoPassword = fmt.Errorf("Environment variable OS_PASSWORD needs to be set.")
+-)
+-
+-// AuthOptions fills out an identity.AuthOptions structure with the settings found on the various OpenStack
+-// OS_* environment variables.  The following variables provide sources of truth: OS_AUTH_URL, OS_USERNAME,
+-// OS_PASSWORD, OS_TENANT_ID, and OS_TENANT_NAME.  Of these, OS_USERNAME, OS_PASSWORD, and OS_AUTH_URL must
+-// have settings, or an error will result.  OS_TENANT_ID and OS_TENANT_NAME are optional.
+-func AuthOptionsFromEnv() (gophercloud.AuthOptions, error) {
+-	authURL := os.Getenv("OS_AUTH_URL")
+-	username := os.Getenv("OS_USERNAME")
+-	userID := os.Getenv("OS_USERID")
+-	password := os.Getenv("OS_PASSWORD")
+-	tenantID := os.Getenv("OS_TENANT_ID")
+-	tenantName := os.Getenv("OS_TENANT_NAME")
+-	domainID := os.Getenv("OS_DOMAIN_ID")
+-	domainName := os.Getenv("OS_DOMAIN_NAME")
+-
+-	if authURL == "" {
+-		return nilOptions, ErrNoAuthURL
 -	}
--	if expected := int64(19 + 12 + 6); n != expected {
--		t.Errorf("Wrong number of bytes. Want %d. Got %d.", expected, n)
+-
+-	if username == "" && userID == "" {
+-		return nilOptions, ErrNoUsername
 -	}
--	if got := stderr.String(); got != "something happened!" {
--		t.Errorf("stdCopy: wrong stderr. Want %q. Got %q.", "something happened!", got)
+-
+-	if password == "" {
+-		return nilOptions, ErrNoPassword
 -	}
--	if got := stdout.String(); got != "just kidding\nyeah!" {
--		t.Errorf("stdCopy: wrong stdout. Want %q. Got %q.", "just kidding\nyeah!", got)
+-
+-	ao := gophercloud.AuthOptions{
+-		IdentityEndpoint: authURL,
+-		UserID:           userID,
+-		Username:         username,
+-		Password:         password,
+-		TenantID:         tenantID,
+-		TenantName:       tenantName,
+-		DomainID:         domainID,
+-		DomainName:       domainName,
+-	}
+-
+-	return ao, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/doc.go
+deleted file mode 100644
+index e3af39f..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/doc.go
++++ /dev/null
+@@ -1,3 +0,0 @@
+-// Package apiversions provides information and interaction with the different
+-// API versions for the OpenStack Block Storage service, code-named Cinder.
+-package apiversions
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/requests.go
+deleted file mode 100644
+index 016bf37..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/requests.go
++++ /dev/null
+@@ -1,28 +0,0 @@
+-package apiversions
+-
+-import (
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-
+-	"github.com/racker/perigee"
+-)
+-
+-// List lists all the Cinder API versions available to end-users.
+-func List(c *gophercloud.ServiceClient) pagination.Pager {
+-	return pagination.NewPager(c, listURL(c), func(r pagination.PageResult) pagination.Page {
+-		return APIVersionPage{pagination.SinglePageBase(r)}
+-	})
+-}
+-
+-// Get will retrieve the volume type with the provided ID. To extract the volume
+-// type from the result, call the Extract method on the GetResult.
+-func Get(client *gophercloud.ServiceClient, v string) GetResult {
+-	var res GetResult
+-	_, err := perigee.Request("GET", getURL(client, v), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{200},
+-		Results:     &res.Body,
+-	})
+-	res.Err = err
+-	return res
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/requests_test.go
+deleted file mode 100644
+index 56b5e4f..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/requests_test.go
++++ /dev/null
+@@ -1,145 +0,0 @@
+-package apiversions
+-
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
+-
+-func TestListVersions(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `{
+-			"versions": [
+-				{
+-					"status": "CURRENT",
+-					"updated": "2012-01-04T11:33:21Z",
+-					"id": "v1.0",
+-					"links": [
+-						{
+-							"href": "http://23.253.228.211:8776/v1/",
+-							"rel": "self"
+-						}
+-					]
+-			    },
+-				{
+-					"status": "CURRENT",
+-					"updated": "2012-11-21T11:33:21Z",
+-					"id": "v2.0",
+-					"links": [
+-						{
+-							"href": "http://23.253.228.211:8776/v2/",
+-							"rel": "self"
+-						}
+-					]
+-				}
+-			]
+-		}`)
+-	})
+-
+-	count := 0
+-
+-	List(client.ServiceClient()).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractAPIVersions(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract API versions: %v", err)
+-			return false, err
+-		}
+-
+-		expected := []APIVersion{
+-			APIVersion{
+-				ID:      "v1.0",
+-				Status:  "CURRENT",
+-				Updated: "2012-01-04T11:33:21Z",
+-			},
+-			APIVersion{
+-				ID:      "v2.0",
+-				Status:  "CURRENT",
+-				Updated: "2012-11-21T11:33:21Z",
+-			},
+-		}
+-
+-		th.AssertDeepEquals(t, expected, actual)
+-
+-		return true, nil
+-	})
+-
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
 -	}
 -}
 -
--func TestStdCopyStress(t *testing.T) {
--	var input, stdout, stderr bytes.Buffer
--	value := strings.Repeat("something ", 4096)
--	writer := newStdWriter(&input, Stdout)
--	writer.Write([]byte(value))
--	n, err := stdCopy(&stdout, &stderr, &input)
+-func TestAPIInfo(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v1/", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `{
+-			"version": {
+-				"status": "CURRENT",
+-				"updated": "2012-01-04T11:33:21Z",
+-				"media-types": [
+-					{
+-						"base": "application/xml",
+-						"type": "application/vnd.openstack.volume+xml;version=1"
+-					},
+-					{
+-						"base": "application/json",
+-						"type": "application/vnd.openstack.volume+json;version=1"
+-					}
+-				],
+-				"id": "v1.0",
+-				"links": [
+-					{
+-						"href": "http://23.253.228.211:8776/v1/",
+-						"rel": "self"
+-					},
+-					{
+-						"href": "http://jorgew.github.com/block-storage-api/content/os-block-storage-1.0.pdf",
+-						"type": "application/pdf",
+-						"rel": "describedby"
+-					},
+-					{
+-						"href": "http://docs.rackspacecloud.com/servers/api/v1.1/application.wadl",
+-						"type": "application/vnd.sun.wadl+xml",
+-						"rel": "describedby"
+-					}
+-				]
+-			}
+-		}`)
+-	})
+-
+-	actual, err := Get(client.ServiceClient(), "v1").Extract()
 -	if err != nil {
--		t.Fatal(err)
--	}
--	if n != 40960 {
--		t.Errorf("Wrong number of bytes. Want 40960. Got %d.", n)
--	}
--	if got := stderr.String(); got != "" {
--		t.Errorf("stdCopy: wrong stderr. Want empty string. Got %q", got)
+-		t.Errorf("Failed to extract version: %v", err)
 -	}
--	if got := stdout.String(); got != value {
--		t.Errorf("stdCopy: wrong stdout. Want %q. Got %q", value, got)
+-
+-	expected := APIVersion{
+-		ID:      "v1.0",
+-		Status:  "CURRENT",
+-		Updated: "2012-01-04T11:33:21Z",
 -	}
+-
+-	th.AssertEquals(t, actual.ID, expected.ID)
+-	th.AssertEquals(t, actual.Status, expected.Status)
+-	th.AssertEquals(t, actual.Updated, expected.Updated)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/results.go
+deleted file mode 100644
+index 7b0df11..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/results.go
++++ /dev/null
+@@ -1,58 +0,0 @@
+-package apiversions
 -
--func TestStdCopyInvalidStdHeader(t *testing.T) {
--	var input, stdout, stderr bytes.Buffer
--	input.Write([]byte{3, 0, 0, 0, 0, 0, 0, 19})
--	n, err := stdCopy(&stdout, &stderr, &input)
--	if n != 0 {
--		t.Errorf("stdCopy: wrong number of bytes. Want 0. Got %d", n)
--	}
--	if err != errInvalidStdHeader {
--		t.Errorf("stdCopy: wrong error. Want ErrInvalidStdHeader. Got %#v", err)
--	}
+-import (
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-
+-	"github.com/mitchellh/mapstructure"
+-)
+-
+-// APIVersion represents an API version for Cinder.
+-type APIVersion struct {
+-	ID      string `json:"id" mapstructure:"id"`           // unique identifier
+-	Status  string `json:"status" mapstructure:"status"`   // current status
+-	Updated string `json:"updated" mapstructure:"updated"` // date last updated
 -}
 -
--func TestStdCopyBigFrame(t *testing.T) {
--	var input, stdout, stderr bytes.Buffer
--	input.Write([]byte{2, 0, 0, 0, 0, 0, 0, 18})
--	input.Write([]byte("something happened!"))
--	n, err := stdCopy(&stdout, &stderr, &input)
+-// APIVersionPage is the page returned by a pager when traversing over a
+-// collection of API versions.
+-type APIVersionPage struct {
+-	pagination.SinglePageBase
+-}
+-
+-// IsEmpty checks whether an APIVersionPage struct is empty.
+-func (r APIVersionPage) IsEmpty() (bool, error) {
+-	is, err := ExtractAPIVersions(r)
 -	if err != nil {
--		t.Fatal(err)
--	}
--	if expected := int64(18); n != expected {
--		t.Errorf("Wrong number of bytes. Want %d. Got %d.", expected, n)
--	}
--	if got := stderr.String(); got != "something happened" {
--		t.Errorf("stdCopy: wrong stderr. Want %q. Got %q.", "something happened", got)
--	}
--	if got := stdout.String(); got != "" {
--		t.Errorf("stdCopy: wrong stdout. Want %q. Got %q.", "", got)
+-		return true, err
 -	}
+-	return len(is) == 0, nil
 -}
 -
--func TestStdCopySmallFrame(t *testing.T) {
--	var input, stdout, stderr bytes.Buffer
--	input.Write([]byte{2, 0, 0, 0, 0, 0, 0, 20})
--	input.Write([]byte("something happened!"))
--	n, err := stdCopy(&stdout, &stderr, &input)
--	if err != io.ErrShortWrite {
--		t.Errorf("stdCopy: wrong error. Want ShortWrite. Got %#v", err)
--	}
--	if expected := int64(19); n != expected {
--		t.Errorf("Wrong number of bytes. Want %d. Got %d.", expected, n)
--	}
--	if got := stderr.String(); got != "something happened!" {
--		t.Errorf("stdCopy: wrong stderr. Want %q. Got %q.", "something happened", got)
--	}
--	if got := stdout.String(); got != "" {
--		t.Errorf("stdCopy: wrong stdout. Want %q. Got %q.", "", got)
+-// ExtractAPIVersions takes a collection page, extracts all of the elements,
+-// and returns them a slice of APIVersion structs. It is effectively a cast.
+-func ExtractAPIVersions(page pagination.Page) ([]APIVersion, error) {
+-	var resp struct {
+-		Versions []APIVersion `mapstructure:"versions"`
 -	}
+-
+-	err := mapstructure.Decode(page.(APIVersionPage).Body, &resp)
+-
+-	return resp.Versions, err
 -}
 -
--func TestStdCopyEmpty(t *testing.T) {
--	var input, stdout, stderr bytes.Buffer
--	n, err := stdCopy(&stdout, &stderr, &input)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if n != 0 {
--		t.Errorf("stdCopy: wrong number of bytes. Want 0. Got %d.", n)
--	}
+-// GetResult represents the result of a get operation.
+-type GetResult struct {
+-	gophercloud.Result
 -}
 -
--func TestStdCopyCorruptedHeader(t *testing.T) {
--	var input, stdout, stderr bytes.Buffer
--	input.Write([]byte{2, 0, 0, 0, 0})
--	n, err := stdCopy(&stdout, &stderr, &input)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if n != 0 {
--		t.Errorf("stdCopy: wrong number of bytes. Want 0. Got %d.", n)
+-// Extract is a function that accepts a result and extracts an API version resource.
+-func (r GetResult) Extract() (*APIVersion, error) {
+-	var resp struct {
+-		Version *APIVersion `mapstructure:"version"`
 -	}
+-
+-	err := mapstructure.Decode(r.Body, &resp)
+-
+-	return resp.Version, err
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/urls.go
+deleted file mode 100644
+index 56f8260..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/urls.go
++++ /dev/null
+@@ -1,15 +0,0 @@
+-package apiversions
 -
--func TestStdCopyTruncateWriter(t *testing.T) {
--	var input, stdout, stderr bytes.Buffer
--	input.Write([]byte{2, 0, 0, 0, 0, 0, 0, 19})
--	input.Write([]byte("something happened!"))
--	n, err := stdCopy(&stdout, iotest.TruncateWriter(&stderr, 7), &input)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if expected := int64(19); n != expected {
--		t.Errorf("Wrong number of bytes. Want %d. Got %d.", expected, n)
--	}
--	if got := stderr.String(); got != "somethi" {
--		t.Errorf("stdCopy: wrong stderr. Want %q. Got %q.", "somethi", got)
--	}
--	if got := stdout.String(); got != "" {
--		t.Errorf("stdCopy: wrong stdout. Want %q. Got %q.", "", got)
--	}
+-import (
+-	"strings"
+-
+-	"github.com/rackspace/gophercloud"
+-)
+-
+-func getURL(c *gophercloud.ServiceClient, version string) string {
+-	return c.ServiceURL(strings.TrimRight(version, "/") + "/")
 -}
 -
--func TestStdCopyHeaderOnly(t *testing.T) {
--	var input, stdout, stderr bytes.Buffer
--	input.Write([]byte{2, 0, 0, 0, 0, 0, 0, 19})
--	n, err := stdCopy(&stdout, iotest.TruncateWriter(&stderr, 7), &input)
--	if err != io.ErrShortWrite {
--		t.Errorf("stdCopy: wrong error. Want ShortWrite. Got %#v", err)
--	}
--	if n != 0 {
--		t.Errorf("Wrong number of bytes. Want 0. Got %d.", n)
--	}
--	if got := stderr.String(); got != "" {
--		t.Errorf("stdCopy: wrong stderr. Want %q. Got %q.", "", got)
--	}
--	if got := stdout.String(); got != "" {
--		t.Errorf("stdCopy: wrong stdout. Want %q. Got %q.", "", got)
--	}
+-func listURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL("")
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/urls_test.go
+deleted file mode 100644
+index 37e9142..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/apiversions/urls_test.go
++++ /dev/null
+@@ -1,26 +0,0 @@
+-package apiversions
 -
--func TestStdCopyDataErrReader(t *testing.T) {
--	var input, stdout, stderr bytes.Buffer
--	input.Write([]byte{2, 0, 0, 0, 0, 0, 0, 19})
--	input.Write([]byte("something happened!"))
--	n, err := stdCopy(&stdout, &stderr, iotest.DataErrReader(&input))
--	if err != nil {
--		t.Fatal(err)
--	}
--	if expected := int64(19); n != expected {
--		t.Errorf("Wrong number of bytes. Want %d. Got %d.", expected, n)
--	}
--	if got := stderr.String(); got != "something happened!" {
--		t.Errorf("stdCopy: wrong stderr. Want %q. Got %q.", "something happened!", got)
--	}
--	if got := stdout.String(); got != "" {
--		t.Errorf("stdCopy: wrong stdout. Want %q. Got %q.", "", got)
--	}
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-const endpoint = "http://localhost:57909/"
+-
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint}
 -}
 -
--func TestStdCopyTimeoutReader(t *testing.T) {
--	var input, stdout, stderr bytes.Buffer
--	input.Write([]byte{2, 0, 0, 0, 0, 0, 0, 19})
--	input.Write([]byte("something happened!"))
--	_, err := stdCopy(&stdout, &stderr, iotest.TimeoutReader(&input))
--	if err != iotest.ErrTimeout {
--		t.Errorf("stdCopy: wrong error. Want ErrTimeout. Got %#v.", err)
--	}
+-func TestGetURL(t *testing.T) {
+-	actual := getURL(endpointClient(), "v1")
+-	expected := endpoint + "v1/"
+-	th.AssertEquals(t, expected, actual)
 -}
 -
--func TestStdCopyWriteError(t *testing.T) {
--	var input bytes.Buffer
--	input.Write([]byte{2, 0, 0, 0, 0, 0, 0, 19})
--	input.Write([]byte("something happened!"))
--	var stdout, stderr errorWriter
--	n, err := stdCopy(stdout, stderr, &input)
--	if err.Error() != "something went wrong" {
--		t.Errorf("stdCopy: wrong error. Want %q. Got %q", "something went wrong", err)
--	}
--	if n != 0 {
--		t.Errorf("stdCopy: wrong number of bytes. Want 0. Got %d.", n)
--	}
+-func TestListURL(t *testing.T) {
+-	actual := listURL(endpointClient())
+-	expected := endpoint
+-	th.AssertEquals(t, expected, actual)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/doc.go
+deleted file mode 100644
+index 198f830..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/doc.go
++++ /dev/null
+@@ -1,5 +0,0 @@
+-// Package snapshots provides information and interaction with snapshots in the
+-// OpenStack Block Storage service. A snapshot is a point in time copy of the
+-// data contained in an external storage volume, and can be controlled
+-// programmatically.
+-package snapshots
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/fixtures.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/fixtures.go
+deleted file mode 100644
+index d1461fb..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/fixtures.go
++++ /dev/null
+@@ -1,114 +0,0 @@
+-package snapshots
 -
--type StdType [8]byte
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--var (
--	Stdin  = StdType{0: 0}
--	Stdout = StdType{0: 1}
--	Stderr = StdType{0: 2}
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
 -)
 -
--type StdWriter struct {
--	io.Writer
--	prefix  StdType
--	sizeBuf []byte
+-func MockListResponse(t *testing.T) {
+-	th.Mux.HandleFunc("/snapshots", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-    {
+-      "snapshots": [
+-        {
+-          "id": "289da7f8-6440-407c-9fb4-7db01ec49164",
+-          "display_name": "snapshot-001"
+-        },
+-        {
+-          "id": "96c3bda7-c82a-4f50-be73-ca7621794835",
+-          "display_name": "snapshot-002"
+-        }
+-      ]
+-    }
+-    `)
+-	})
 -}
 -
--func (w *StdWriter) Write(buf []byte) (n int, err error) {
--	if w == nil || w.Writer == nil {
--		return 0, errors.New("Writer not instanciated")
--	}
--	binary.BigEndian.PutUint32(w.prefix[4:], uint32(len(buf)))
--	buf = append(w.prefix[:], buf...)
+-func MockGetResponse(t *testing.T) {
+-	th.Mux.HandleFunc("/snapshots/d32019d3-bc6e-4319-9c1d-6722fc136a22", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--	n, err = w.Writer.Write(buf)
--	return n - 8, err
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-		fmt.Fprintf(w, `
+-{
+-    "snapshot": {
+-        "display_name": "snapshot-001",
+-        "id": "d32019d3-bc6e-4319-9c1d-6722fc136a22"
+-    }
+-}
+-      `)
+-	})
 -}
 -
--func newStdWriter(w io.Writer, t StdType) *StdWriter {
--	if len(t) != 8 {
--		return nil
--	}
+-func MockCreateResponse(t *testing.T) {
+-	th.Mux.HandleFunc("/snapshots", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "snapshot": {
+-        "volume_id": "1234",
+-        "display_name": "snapshot-001"
+-    }
+-}
+-      `)
 -
--	return &StdWriter{
--		Writer:  w,
--		prefix:  t,
--		sizeBuf: make([]byte, 4),
--	}
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "snapshot": {
+-        "volume_id": "1234",
+-        "display_name": "snapshot-001",
+-        "id": "d32019d3-bc6e-4319-9c1d-6722fc136a22"
+-    }
+-}
+-    `)
+-	})
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/Dockerfile b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/Dockerfile
-deleted file mode 100644
-index 0948dcf..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/Dockerfile
-+++ /dev/null
-@@ -1,15 +0,0 @@
--# this file describes how to build tsuru python image
--# to run it:
--# 1- install docker
--# 2- run: $ docker build -t tsuru/python https://raw.github.com/tsuru/basebuilder/master/python/Dockerfile
 -
--from	base:ubuntu-quantal
--run	apt-get install wget -y --force-yes
--run	wget http://github.com/tsuru/basebuilder/tarball/master -O basebuilder.tar.gz --no-check-certificate
--run	mkdir /var/lib/tsuru
--run	tar -xvf basebuilder.tar.gz -C /var/lib/tsuru --strip 1
--run	cp /var/lib/tsuru/python/deploy /var/lib/tsuru
--run	cp /var/lib/tsuru/base/restart /var/lib/tsuru
--run	cp /var/lib/tsuru/base/start /var/lib/tsuru
--run	/var/lib/tsuru/base/install
--run	/var/lib/tsuru/base/setup
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/container.tar b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/container.tar
-deleted file mode 100644
-index e4b066e3b6df8cb78ac445a34234f3780d164cf4..0000000000000000000000000000000000000000
-GIT binary patch
-literal 0
-HcmV?d00001
-
-literal 2048
-zcmeH_Q3``F42FH)DgF~kTC`qZ7s*`9%A^%r$Bu89Fp<6NMew1akmheFe?H>)Y5N#5
-z`(UT)m>?q4G^iwZ#(XmAwH8Ujv`|_rQd)Ig3sQ!(szArs+5bAH%#&Di1HU}iJx_zp
-z+3uU9k~Zgl)J<3?S%)LS_Hgc7e)t4AX&%Rz>>WAcX2Ec>82D}md=O1Y)p%bo=N_rJ
-OD+CIGLZA@%gTMmt=q{T8
-
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/dockerfile.tar b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/data/dockerfile.tar
-deleted file mode 100644
-index 32c9ce64704835cd096b85ac44c35b5087b5ccdd..0000000000000000000000000000000000000000
-GIT binary patch
-literal 0
-HcmV?d00001
-
-literal 2560
-zcmeHGy>8<$49;3V1%d0TNOs}`$a>xT46-c8LTt+?QB8ACf0XPiQll-<p+kUZFvXvb
-z{76$zR-LqKOs7{rc7zbS?G{!f_q$z^qL_3tiM%LE$cs&}-<R8RFF at p*a#OBA{1~IF
-z#KEI<M2)`Q_$$ZaN?}d2uwARM6CtMNqP&sw3$QgF;sQXey>h0~9$I?_v`_`p)qp;@
-z0OJK)JAmosQD=m*-~y?5ASGvD1{zS;L7n!AYz2z}2Y8%Kb25fgK0fDb5l4UE+{yF$
-zXs`{{TG^hbn!J);Cl1>2UV0=k!T8hL+GbhfZ2u5L51|SJ2KFb&fyiW3|3Qw(jvC+i
-zouk4oz*u9Q((Iyric9uLhPZsmgZ8ANMrS_2p5cn+n!M}dU&=mMrdq8|OlgOvF-oFN
-zh5A!%9Pk(EcxS4q(c~Z~u-BL7!+gIN2&&-GnGy1YRpY|{e@?X?J9}9;KY_$PxYO}H
-o;5QJT#=q||{Y*ZuNn-Gk-)jtGb|Y`+PV+v2`vmS2xaA4_1I+dVl>h($
-
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/server.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/server.go
+-func MockUpdateMetadataResponse(t *testing.T) {
+-	th.Mux.HandleFunc("/snapshots/123/metadata", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestJSONRequest(t, r, `
+-    {
+-      "metadata": {
+-        "key": "v1"
+-      }
+-    }
+-    `)
+-
+-		fmt.Fprintf(w, `
+-      {
+-        "metadata": {
+-          "key": "v1"
+-        }
+-      }
+-    `)
+-	})
+-}
+-
+-func MockDeleteResponse(t *testing.T) {
+-	th.Mux.HandleFunc("/snapshots/d32019d3-bc6e-4319-9c1d-6722fc136a22", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/requests.go
 deleted file mode 100644
-index e2ca1d9..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/server.go
+index 443f696..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/requests.go
 +++ /dev/null
-@@ -1,692 +0,0 @@
--// Copyright 2014 go-dockerclient 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 testing provides a fake implementation of the Docker API, useful for
--// testing purpose.
--package testing
+@@ -1,188 +0,0 @@
+-package snapshots
 -
 -import (
--	"archive/tar"
--	"crypto/rand"
--	"encoding/json"
--	"errors"
 -	"fmt"
--	mathrand "math/rand"
--	"net"
--	"net/http"
--	"regexp"
--	"strconv"
--	"strings"
--	"sync"
--	"time"
 -
--	"github.com/fsouza/go-dockerclient"
--	"github.com/gorilla/mux"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-
+-	"github.com/racker/perigee"
 -)
 -
--// DockerServer represents a programmable, concurrent (not much), HTTP server
--// implementing a fake version of the Docker remote API.
--//
--// It can used in standalone mode, listening for connections or as an arbitrary
--// HTTP handler.
--//
--// For more details on the remote API, check http://goo.gl/G3plxW.
--type DockerServer struct {
--	containers     []*docker.Container
--	cMut           sync.RWMutex
--	images         []docker.Image
--	iMut           sync.RWMutex
--	imgIDs         map[string]string
--	listener       net.Listener
--	mux            *mux.Router
--	hook           func(*http.Request)
--	failures       map[string]string
--	customHandlers map[string]http.Handler
--	handlerMutex   sync.RWMutex
--	cChan          chan<- *docker.Container
+-// CreateOptsBuilder allows extensions to add additional parameters to the
+-// Create request.
+-type CreateOptsBuilder interface {
+-	ToSnapshotCreateMap() (map[string]interface{}, error)
 -}
 -
--// NewServer returns a new instance of the fake server, in standalone mode. Use
--// the method URL to get the URL of the server.
--//
--// It receives the bind address (use 127.0.0.1:0 for getting an available port
--// on the host), a channel of containers and a hook function, that will be
--// called on every request.
--//
--// The fake server will send containers in the channel whenever the container
--// changes its state, via the HTTP API (i.e.: create, start and stop). This
--// channel may be nil, which means that the server won't notify on state
--// changes.
--func NewServer(bind string, containerChan chan<- *docker.Container, hook func(*http.Request)) (*DockerServer, error) {
--	listener, err := net.Listen("tcp", bind)
--	if err != nil {
--		return nil, err
+-// CreateOpts contains options for creating a Snapshot. This object is passed to
+-// the snapshots.Create function. For more information about these parameters,
+-// see the Snapshot object.
+-type CreateOpts struct {
+-	// OPTIONAL
+-	Description string
+-	// OPTIONAL
+-	Force bool
+-	// OPTIONAL
+-	Metadata map[string]interface{}
+-	// OPTIONAL
+-	Name string
+-	// REQUIRED
+-	VolumeID string
+-}
+-
+-// ToSnapshotCreateMap assembles a request body based on the contents of a
+-// CreateOpts.
+-func (opts CreateOpts) ToSnapshotCreateMap() (map[string]interface{}, error) {
+-	s := make(map[string]interface{})
+-
+-	if opts.VolumeID == "" {
+-		return nil, fmt.Errorf("Required CreateOpts field 'VolumeID' not set.")
 -	}
--	server := DockerServer{
--		listener:       listener,
--		imgIDs:         make(map[string]string),
--		hook:           hook,
--		failures:       make(map[string]string),
--		customHandlers: make(map[string]http.Handler),
--		cChan:          containerChan,
+-	s["volume_id"] = opts.VolumeID
+-
+-	if opts.Description != "" {
+-		s["display_description"] = opts.Description
 -	}
--	server.buildMuxer()
--	go http.Serve(listener, &server)
--	return &server, nil
+-	if opts.Force == true {
+-		s["force"] = opts.Force
+-	}
+-	if opts.Metadata != nil {
+-		s["metadata"] = opts.Metadata
+-	}
+-	if opts.Name != "" {
+-		s["display_name"] = opts.Name
+-	}
+-
+-	return map[string]interface{}{"snapshot": s}, nil
 -}
 -
--func (s *DockerServer) notify(container *docker.Container) {
--	if s.cChan != nil {
--		s.cChan <- container
+-// Create will create a new Snapshot based on the values in CreateOpts. To
+-// extract the Snapshot object from the response, call the Extract method on the
+-// CreateResult.
+-func Create(client *gophercloud.ServiceClient, opts CreateOptsBuilder) CreateResult {
+-	var res CreateResult
+-
+-	reqBody, err := opts.ToSnapshotCreateMap()
+-	if err != nil {
+-		res.Err = err
+-		return res
 -	}
+-
+-	_, res.Err = perigee.Request("POST", createURL(client), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{200, 201},
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-	})
+-	return res
 -}
 -
--func (s *DockerServer) buildMuxer() {
--	s.mux = mux.NewRouter()
--	s.mux.Path("/commit").Methods("POST").HandlerFunc(s.handlerWrapper(s.commitContainer))
--	s.mux.Path("/containers/json").Methods("GET").HandlerFunc(s.handlerWrapper(s.listContainers))
--	s.mux.Path("/containers/create").Methods("POST").HandlerFunc(s.handlerWrapper(s.createContainer))
--	s.mux.Path("/containers/{id:.*}/json").Methods("GET").HandlerFunc(s.handlerWrapper(s.inspectContainer))
--	s.mux.Path("/containers/{id:.*}/top").Methods("GET").HandlerFunc(s.handlerWrapper(s.topContainer))
--	s.mux.Path("/containers/{id:.*}/start").Methods("POST").HandlerFunc(s.handlerWrapper(s.startContainer))
--	s.mux.Path("/containers/{id:.*}/stop").Methods("POST").HandlerFunc(s.handlerWrapper(s.stopContainer))
--	s.mux.Path("/containers/{id:.*}/pause").Methods("POST").HandlerFunc(s.handlerWrapper(s.pauseContainer))
--	s.mux.Path("/containers/{id:.*}/unpause").Methods("POST").HandlerFunc(s.handlerWrapper(s.unpauseContainer))
--	s.mux.Path("/containers/{id:.*}/wait").Methods("POST").HandlerFunc(s.handlerWrapper(s.waitContainer))
--	s.mux.Path("/containers/{id:.*}/attach").Methods("POST").HandlerFunc(s.handlerWrapper(s.attachContainer))
--	s.mux.Path("/containers/{id:.*}").Methods("DELETE").HandlerFunc(s.handlerWrapper(s.removeContainer))
--	s.mux.Path("/images/create").Methods("POST").HandlerFunc(s.handlerWrapper(s.pullImage))
--	s.mux.Path("/build").Methods("POST").HandlerFunc(s.handlerWrapper(s.buildImage))
--	s.mux.Path("/images/json").Methods("GET").HandlerFunc(s.handlerWrapper(s.listImages))
--	s.mux.Path("/images/{id:.*}").Methods("DELETE").HandlerFunc(s.handlerWrapper(s.removeImage))
--	s.mux.Path("/images/{name:.*}/json").Methods("GET").HandlerFunc(s.handlerWrapper(s.inspectImage))
--	s.mux.Path("/images/{name:.*}/push").Methods("POST").HandlerFunc(s.handlerWrapper(s.pushImage))
--	s.mux.Path("/events").Methods("GET").HandlerFunc(s.listEvents)
--	s.mux.Path("/_ping").Methods("GET").HandlerFunc(s.handlerWrapper(s.pingDocker))
--	s.mux.Path("/images/load").Methods("POST").HandlerFunc(s.handlerWrapper(s.loadImage))
--	s.mux.Path("/images/{id:.*}/get").Methods("GET").HandlerFunc(s.handlerWrapper(s.getImage))
+-// Delete will delete the existing Snapshot with the provided ID.
+-func Delete(client *gophercloud.ServiceClient, id string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", deleteURL(client, id), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{202, 204},
+-	})
+-	return res
 -}
 -
--// PrepareFailure adds a new expected failure based on a URL regexp it receives
--// an id for the failure.
--func (s *DockerServer) PrepareFailure(id string, urlRegexp string) {
--	s.failures[id] = urlRegexp
+-// Get retrieves the Snapshot with the provided ID. To extract the Snapshot
+-// object from the response, call the Extract method on the GetResult.
+-func Get(client *gophercloud.ServiceClient, id string) GetResult {
+-	var res GetResult
+-	_, res.Err = perigee.Request("GET", getURL(client, id), perigee.Options{
+-		Results:     &res.Body,
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{200},
+-	})
+-	return res
 -}
 -
--// ResetFailure removes an expected failure identified by the given id.
--func (s *DockerServer) ResetFailure(id string) {
--	delete(s.failures, id)
+-// ListOptsBuilder allows extensions to add additional parameters to the List
+-// request.
+-type ListOptsBuilder interface {
+-	ToSnapshotListQuery() (string, error)
 -}
 -
--// CustomHandler registers a custom handler for a specific path.
--//
--// For example:
--//
--//     server.CustomHandler("/containers/json", http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
--//         http.Error(w, "Something wrong is not right", http.StatusInternalServerError)
--//     }))
--func (s *DockerServer) CustomHandler(path string, handler http.Handler) {
--	s.handlerMutex.Lock()
--	s.customHandlers[path] = handler
--	s.handlerMutex.Unlock()
+-// ListOpts hold options for listing Snapshots. It is passed to the
+-// snapshots.List function.
+-type ListOpts struct {
+-	Name     string `q:"display_name"`
+-	Status   string `q:"status"`
+-	VolumeID string `q:"volume_id"`
 -}
 -
--// MutateContainer changes the state of a container, returning an error if the
--// given id does not match to any container "running" in the server.
--func (s *DockerServer) MutateContainer(id string, state docker.State) error {
--	for _, container := range s.containers {
--		if container.ID == id {
--			container.State = state
--			return nil
--		}
+-// ToSnapshotListQuery formats a ListOpts into a query string.
+-func (opts ListOpts) ToSnapshotListQuery() (string, error) {
+-	q, err := gophercloud.BuildQueryString(opts)
+-	if err != nil {
+-		return "", err
 -	}
--	return errors.New("container not found")
+-	return q.String(), nil
 -}
 -
--// Stop stops the server.
--func (s *DockerServer) Stop() {
--	if s.listener != nil {
--		s.listener.Close()
+-// List returns Snapshots optionally limited by the conditions provided in
+-// ListOpts.
+-func List(client *gophercloud.ServiceClient, opts ListOptsBuilder) pagination.Pager {
+-	url := listURL(client)
+-	if opts != nil {
+-		query, err := opts.ToSnapshotListQuery()
+-		if err != nil {
+-			return pagination.Pager{Err: err}
+-		}
+-		url += query
 -	}
--}
 -
--// URL returns the HTTP URL of the server.
--func (s *DockerServer) URL() string {
--	if s.listener == nil {
--		return ""
+-	createPage := func(r pagination.PageResult) pagination.Page {
+-		return ListResult{pagination.SinglePageBase(r)}
 -	}
--	return "http://" + s.listener.Addr().String() + "/"
+-	return pagination.NewPager(client, url, createPage)
 -}
 -
--// ServeHTTP handles HTTP requests sent to the server.
--func (s *DockerServer) ServeHTTP(w http.ResponseWriter, r *http.Request) {
--	s.handlerMutex.RLock()
--	defer s.handlerMutex.RUnlock()
--	if handler, ok := s.customHandlers[r.URL.Path]; ok {
--		handler.ServeHTTP(w, r)
--		return
--	}
--	s.mux.ServeHTTP(w, r)
--	if s.hook != nil {
--		s.hook(r)
--	}
+-// UpdateMetadataOptsBuilder allows extensions to add additional parameters to
+-// the Update request.
+-type UpdateMetadataOptsBuilder interface {
+-	ToSnapshotUpdateMetadataMap() (map[string]interface{}, error)
 -}
 -
--// Returns default http.Handler mux, it allows customHandlers to call the
--// default behavior if wanted.
--func (s *DockerServer) DefaultHandler() http.Handler {
--	return s.mux
+-// UpdateMetadataOpts contain options for updating an existing Snapshot. This
+-// object is passed to the snapshots.Update function. For more information
+-// about the parameters, see the Snapshot object.
+-type UpdateMetadataOpts struct {
+-	Metadata map[string]interface{}
 -}
 -
--func (s *DockerServer) handlerWrapper(f func(http.ResponseWriter, *http.Request)) func(http.ResponseWriter, *http.Request) {
--	return func(w http.ResponseWriter, r *http.Request) {
--		for errorID, urlRegexp := range s.failures {
--			matched, err := regexp.MatchString(urlRegexp, r.URL.Path)
--			if err != nil {
--				http.Error(w, err.Error(), http.StatusBadRequest)
--				return
--			}
--			if !matched {
--				continue
--			}
--			http.Error(w, errorID, http.StatusBadRequest)
--			return
--		}
--		f(w, r)
+-// ToSnapshotUpdateMetadataMap assembles a request body based on the contents of
+-// an UpdateMetadataOpts.
+-func (opts UpdateMetadataOpts) ToSnapshotUpdateMetadataMap() (map[string]interface{}, error) {
+-	v := make(map[string]interface{})
+-
+-	if opts.Metadata != nil {
+-		v["metadata"] = opts.Metadata
 -	}
+-
+-	return v, nil
 -}
 -
--func (s *DockerServer) listContainers(w http.ResponseWriter, r *http.Request) {
--	all := r.URL.Query().Get("all")
--	s.cMut.RLock()
--	result := make([]docker.APIContainers, len(s.containers))
--	for i, container := range s.containers {
--		if all == "1" || container.State.Running {
--			result[i] = docker.APIContainers{
--				ID:      container.ID,
--				Image:   container.Image,
--				Command: fmt.Sprintf("%s %s", container.Path, strings.Join(container.Args, " ")),
--				Created: container.Created.Unix(),
--				Status:  container.State.String(),
--				Ports:   container.NetworkSettings.PortMappingAPI(),
--			}
--		}
+-// UpdateMetadata will update the Snapshot with provided information. To
+-// extract the updated Snapshot from the response, call the ExtractMetadata
+-// method on the UpdateMetadataResult.
+-func UpdateMetadata(client *gophercloud.ServiceClient, id string, opts UpdateMetadataOptsBuilder) UpdateMetadataResult {
+-	var res UpdateMetadataResult
+-
+-	reqBody, err := opts.ToSnapshotUpdateMetadataMap()
+-	if err != nil {
+-		res.Err = err
+-		return res
 -	}
--	s.cMut.RUnlock()
--	w.Header().Set("Content-Type", "application/json")
--	w.WriteHeader(http.StatusOK)
--	json.NewEncoder(w).Encode(result)
+-
+-	_, res.Err = perigee.Request("PUT", updateMetadataURL(client, id), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{200},
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-	})
+-	return res
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/requests_test.go
+deleted file mode 100644
+index d0f9e88..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/requests_test.go
++++ /dev/null
+@@ -1,104 +0,0 @@
+-package snapshots
 -
--func (s *DockerServer) listImages(w http.ResponseWriter, r *http.Request) {
--	s.cMut.RLock()
--	result := make([]docker.APIImages, len(s.images))
--	for i, image := range s.images {
--		result[i] = docker.APIImages{
--			ID:      image.ID,
--			Created: image.Created.Unix(),
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
+-
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	MockListResponse(t)
+-
+-	count := 0
+-
+-	List(client.ServiceClient(), &ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractSnapshots(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract snapshots: %v", err)
+-			return false, err
 -		}
--		for tag, id := range s.imgIDs {
--			if id == image.ID {
--				result[i].RepoTags = append(result[i].RepoTags, tag)
--			}
+-
+-		expected := []Snapshot{
+-			Snapshot{
+-				ID:   "289da7f8-6440-407c-9fb4-7db01ec49164",
+-				Name: "snapshot-001",
+-			},
+-			Snapshot{
+-				ID:   "96c3bda7-c82a-4f50-be73-ca7621794835",
+-				Name: "snapshot-002",
+-			},
 -		}
+-
+-		th.CheckDeepEquals(t, expected, actual)
+-
+-		return true, nil
+-	})
+-
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
 -	}
--	s.cMut.RUnlock()
--	w.Header().Set("Content-Type", "application/json")
--	w.WriteHeader(http.StatusOK)
--	json.NewEncoder(w).Encode(result)
 -}
 -
--func (s *DockerServer) findImage(id string) (string, error) {
--	s.iMut.RLock()
--	defer s.iMut.RUnlock()
--	image, ok := s.imgIDs[id]
--	if ok {
--		return image, nil
--	}
--	image, _, err := s.findImageByID(id)
--	return image, err
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	MockGetResponse(t)
+-
+-	v, err := Get(client.ServiceClient(), "d32019d3-bc6e-4319-9c1d-6722fc136a22").Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, v.Name, "snapshot-001")
+-	th.AssertEquals(t, v.ID, "d32019d3-bc6e-4319-9c1d-6722fc136a22")
 -}
 -
--func (s *DockerServer) findImageByID(id string) (string, int, error) {
--	s.iMut.RLock()
--	defer s.iMut.RUnlock()
--	for i, image := range s.images {
--		if image.ID == id {
--			return image.ID, i, nil
--		}
--	}
--	return "", -1, errors.New("No such image")
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	MockCreateResponse(t)
+-
+-	options := CreateOpts{VolumeID: "1234", Name: "snapshot-001"}
+-	n, err := Create(client.ServiceClient(), options).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, n.VolumeID, "1234")
+-	th.AssertEquals(t, n.Name, "snapshot-001")
+-	th.AssertEquals(t, n.ID, "d32019d3-bc6e-4319-9c1d-6722fc136a22")
 -}
 -
--func (s *DockerServer) createContainer(w http.ResponseWriter, r *http.Request) {
--	var config docker.Config
--	defer r.Body.Close()
--	err := json.NewDecoder(r.Body).Decode(&config)
--	if err != nil {
--		http.Error(w, err.Error(), http.StatusBadRequest)
--		return
--	}
--	image, err := s.findImage(config.Image)
--	if err != nil {
--		http.Error(w, err.Error(), http.StatusNotFound)
--		return
--	}
--	w.WriteHeader(http.StatusCreated)
--	ports := map[docker.Port][]docker.PortBinding{}
--	for port := range config.ExposedPorts {
--		ports[port] = []docker.PortBinding{{
--			HostIp:   "0.0.0.0",
--			HostPort: strconv.Itoa(mathrand.Int() % 65536),
--		}}
--	}
+-func TestUpdateMetadata(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	//the container may not have cmd when using a Dockerfile
--	var path string
--	var args []string
--	if len(config.Cmd) == 1 {
--		path = config.Cmd[0]
--	} else if len(config.Cmd) > 1 {
--		path = config.Cmd[0]
--		args = config.Cmd[1:]
--	}
+-	MockUpdateMetadataResponse(t)
 -
--	container := docker.Container{
--		ID:      s.generateID(),
--		Created: time.Now(),
--		Path:    path,
--		Args:    args,
--		Config:  &config,
--		State: docker.State{
--			Running:   false,
--			Pid:       mathrand.Int() % 50000,
--			ExitCode:  0,
--			StartedAt: time.Now(),
--		},
--		Image: image,
--		NetworkSettings: &docker.NetworkSettings{
--			IPAddress:   fmt.Sprintf("172.16.42.%d", mathrand.Int()%250+2),
--			IPPrefixLen: 24,
--			Gateway:     "172.16.42.1",
--			Bridge:      "docker0",
--			Ports:       ports,
+-	expected := map[string]interface{}{"key": "v1"}
+-
+-	options := &UpdateMetadataOpts{
+-		Metadata: map[string]interface{}{
+-			"key": "v1",
 -		},
 -	}
--	s.cMut.Lock()
--	s.containers = append(s.containers, &container)
--	s.cMut.Unlock()
--	s.notify(&container)
--	var c = struct{ ID string }{ID: container.ID}
--	json.NewEncoder(w).Encode(c)
+-
+-	actual, err := UpdateMetadata(client.ServiceClient(), "123", options).ExtractMetadata()
+-
+-	th.AssertNoErr(t, err)
+-	th.AssertDeepEquals(t, actual, expected)
 -}
 -
--func (s *DockerServer) generateID() string {
--	var buf [16]byte
--	rand.Read(buf[:])
--	return fmt.Sprintf("%x", buf)
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	MockDeleteResponse(t)
+-
+-	res := Delete(client.ServiceClient(), "d32019d3-bc6e-4319-9c1d-6722fc136a22")
+-	th.AssertNoErr(t, res.Err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/results.go
+deleted file mode 100644
+index e595798..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/results.go
++++ /dev/null
+@@ -1,123 +0,0 @@
+-package snapshots
 -
--func (s *DockerServer) inspectContainer(w http.ResponseWriter, r *http.Request) {
--	id := mux.Vars(r)["id"]
--	container, _, err := s.findContainer(id)
--	if err != nil {
--		http.Error(w, err.Error(), http.StatusNotFound)
--		return
--	}
--	w.Header().Set("Content-Type", "application/json")
--	w.WriteHeader(http.StatusOK)
--	json.NewEncoder(w).Encode(container)
+-import (
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-
+-	"github.com/mitchellh/mapstructure"
+-)
+-
+-// Snapshot contains all the information associated with an OpenStack Snapshot.
+-type Snapshot struct {
+-	// Currect status of the Snapshot.
+-	Status string `mapstructure:"status"`
+-
+-	// Display name.
+-	Name string `mapstructure:"display_name"`
+-
+-	// Instances onto which the Snapshot is attached.
+-	Attachments []string `mapstructure:"attachments"`
+-
+-	// Logical group.
+-	AvailabilityZone string `mapstructure:"availability_zone"`
+-
+-	// Is the Snapshot bootable?
+-	Bootable string `mapstructure:"bootable"`
+-
+-	// Date created.
+-	CreatedAt string `mapstructure:"created_at"`
+-
+-	// Display description.
+-	Description string `mapstructure:"display_discription"`
+-
+-	// See VolumeType object for more information.
+-	VolumeType string `mapstructure:"volume_type"`
+-
+-	// ID of the Snapshot from which this Snapshot was created.
+-	SnapshotID string `mapstructure:"snapshot_id"`
+-
+-	// ID of the Volume from which this Snapshot was created.
+-	VolumeID string `mapstructure:"volume_id"`
+-
+-	// User-defined key-value pairs.
+-	Metadata map[string]string `mapstructure:"metadata"`
+-
+-	// Unique identifier.
+-	ID string `mapstructure:"id"`
+-
+-	// Size of the Snapshot, in GB.
+-	Size int `mapstructure:"size"`
 -}
 -
--func (s *DockerServer) topContainer(w http.ResponseWriter, r *http.Request) {
--	id := mux.Vars(r)["id"]
--	container, _, err := s.findContainer(id)
--	if err != nil {
--		http.Error(w, err.Error(), http.StatusNotFound)
--		return
--	}
--	if !container.State.Running {
--		w.WriteHeader(http.StatusInternalServerError)
--		fmt.Fprintf(w, "Container %s is not running", id)
--		return
--	}
--	w.Header().Set("Content-Type", "application/json")
--	w.WriteHeader(http.StatusOK)
--	result := docker.TopResult{
--		Titles: []string{"UID", "PID", "PPID", "C", "STIME", "TTY", "TIME", "CMD"},
--		Processes: [][]string{
--			{"root", "7535", "7516", "0", "03:20", "?", "00:00:00", container.Path + " " + strings.Join(container.Args, " ")},
--		},
--	}
--	json.NewEncoder(w).Encode(result)
+-// CreateResult contains the response body and error from a Create request.
+-type CreateResult struct {
+-	commonResult
 -}
 -
--func (s *DockerServer) startContainer(w http.ResponseWriter, r *http.Request) {
--	id := mux.Vars(r)["id"]
--	container, _, err := s.findContainer(id)
--	if err != nil {
--		http.Error(w, err.Error(), http.StatusNotFound)
--		return
--	}
--	s.cMut.Lock()
--	defer s.cMut.Unlock()
--	if container.State.Running {
--		http.Error(w, "Container already running", http.StatusBadRequest)
--		return
--	}
--	container.State.Running = true
--	s.notify(container)
+-// GetResult contains the response body and error from a Get request.
+-type GetResult struct {
+-	commonResult
 -}
 -
--func (s *DockerServer) stopContainer(w http.ResponseWriter, r *http.Request) {
--	id := mux.Vars(r)["id"]
--	container, _, err := s.findContainer(id)
--	if err != nil {
--		http.Error(w, err.Error(), http.StatusNotFound)
--		return
--	}
--	s.cMut.Lock()
--	defer s.cMut.Unlock()
--	if !container.State.Running {
--		http.Error(w, "Container not running", http.StatusBadRequest)
--		return
--	}
--	w.WriteHeader(http.StatusNoContent)
--	container.State.Running = false
--	s.notify(container)
+-// DeleteResult contains the response body and error from a Delete request.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
 -}
 -
--func (s *DockerServer) pauseContainer(w http.ResponseWriter, r *http.Request) {
--	id := mux.Vars(r)["id"]
--	container, _, err := s.findContainer(id)
--	if err != nil {
--		http.Error(w, err.Error(), http.StatusNotFound)
--		return
--	}
--	s.cMut.Lock()
--	defer s.cMut.Unlock()
--	if container.State.Paused {
--		http.Error(w, "Container already paused", http.StatusBadRequest)
--		return
--	}
--	w.WriteHeader(http.StatusNoContent)
--	container.State.Paused = true
+-// ListResult is a pagination.Pager that is returned from a call to the List function.
+-type ListResult struct {
+-	pagination.SinglePageBase
 -}
 -
--func (s *DockerServer) unpauseContainer(w http.ResponseWriter, r *http.Request) {
--	id := mux.Vars(r)["id"]
--	container, _, err := s.findContainer(id)
+-// IsEmpty returns true if a ListResult contains no Snapshots.
+-func (r ListResult) IsEmpty() (bool, error) {
+-	volumes, err := ExtractSnapshots(r)
 -	if err != nil {
--		http.Error(w, err.Error(), http.StatusNotFound)
--		return
--	}
--	s.cMut.Lock()
--	defer s.cMut.Unlock()
--	if !container.State.Paused {
--		http.Error(w, "Container not paused", http.StatusBadRequest)
--		return
+-		return true, err
 -	}
--	w.WriteHeader(http.StatusNoContent)
--	container.State.Paused = false
+-	return len(volumes) == 0, nil
 -}
 -
--func (s *DockerServer) attachContainer(w http.ResponseWriter, r *http.Request) {
--	id := mux.Vars(r)["id"]
--	container, _, err := s.findContainer(id)
--	if err != nil {
--		http.Error(w, err.Error(), http.StatusNotFound)
--		return
--	}
--	outStream := newStdWriter(w, stdout)
--	fmt.Fprintf(outStream, "HTTP/1.1 200 OK\r\nContent-Type: application/vnd.docker.raw-stream\r\n\r\n")
--	if container.State.Running {
--		fmt.Fprintf(outStream, "Container %q is running\n", container.ID)
--	} else {
--		fmt.Fprintf(outStream, "Container %q is not running\n", container.ID)
+-// ExtractSnapshots extracts and returns Snapshots. It is used while iterating over a snapshots.List call.
+-func ExtractSnapshots(page pagination.Page) ([]Snapshot, error) {
+-	var response struct {
+-		Snapshots []Snapshot `json:"snapshots"`
 -	}
--	fmt.Fprintln(outStream, "What happened?")
--	fmt.Fprintln(outStream, "Something happened")
+-
+-	err := mapstructure.Decode(page.(ListResult).Body, &response)
+-	return response.Snapshots, err
 -}
 -
--func (s *DockerServer) waitContainer(w http.ResponseWriter, r *http.Request) {
--	id := mux.Vars(r)["id"]
--	container, _, err := s.findContainer(id)
--	if err != nil {
--		http.Error(w, err.Error(), http.StatusNotFound)
--		return
--	}
--	for {
--		time.Sleep(1e6)
--		s.cMut.RLock()
--		if !container.State.Running {
--			s.cMut.RUnlock()
--			break
--		}
--		s.cMut.RUnlock()
--	}
--	result := map[string]int{"StatusCode": container.State.ExitCode}
--	json.NewEncoder(w).Encode(result)
+-// UpdateMetadataResult contains the response body and error from an UpdateMetadata request.
+-type UpdateMetadataResult struct {
+-	commonResult
 -}
 -
--func (s *DockerServer) removeContainer(w http.ResponseWriter, r *http.Request) {
--	id := mux.Vars(r)["id"]
--	_, index, err := s.findContainer(id)
--	if err != nil {
--		http.Error(w, err.Error(), http.StatusNotFound)
--		return
--	}
--	if s.containers[index].State.Running {
--		msg := "Error: API error (406): Impossible to remove a running container, please stop it first"
--		http.Error(w, msg, http.StatusInternalServerError)
--		return
+-// ExtractMetadata returns the metadata from a response from snapshots.UpdateMetadata.
+-func (r UpdateMetadataResult) ExtractMetadata() (map[string]interface{}, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
 -	}
--	w.WriteHeader(http.StatusNoContent)
--	s.cMut.Lock()
--	defer s.cMut.Unlock()
--	s.containers[index] = s.containers[len(s.containers)-1]
--	s.containers = s.containers[:len(s.containers)-1]
+-
+-	m := r.Body.(map[string]interface{})["metadata"]
+-	return m.(map[string]interface{}), nil
 -}
 -
--func (s *DockerServer) commitContainer(w http.ResponseWriter, r *http.Request) {
--	id := r.URL.Query().Get("container")
--	container, _, err := s.findContainer(id)
--	if err != nil {
--		http.Error(w, err.Error(), http.StatusNotFound)
--		return
--	}
--	var config *docker.Config
--	runConfig := r.URL.Query().Get("run")
--	if runConfig != "" {
--		config = new(docker.Config)
--		err = json.Unmarshal([]byte(runConfig), config)
--		if err != nil {
--			http.Error(w, err.Error(), http.StatusBadRequest)
--			return
--		}
--	}
--	w.WriteHeader(http.StatusOK)
--	image := docker.Image{
--		ID:        "img-" + container.ID,
--		Parent:    container.Image,
--		Container: container.ID,
--		Comment:   r.URL.Query().Get("m"),
--		Author:    r.URL.Query().Get("author"),
--		Config:    config,
+-type commonResult struct {
+-	gophercloud.Result
+-}
+-
+-// Extract will get the Snapshot object out of the commonResult object.
+-func (r commonResult) Extract() (*Snapshot, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
 -	}
--	repository := r.URL.Query().Get("repo")
--	s.iMut.Lock()
--	s.images = append(s.images, image)
--	if repository != "" {
--		s.imgIDs[repository] = image.ID
+-
+-	var res struct {
+-		Snapshot *Snapshot `json:"snapshot"`
 -	}
--	s.iMut.Unlock()
--	fmt.Fprintf(w, `{"ID":%q}`, image.ID)
+-
+-	err := mapstructure.Decode(r.Body, &res)
+-
+-	return res.Snapshot, err
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/urls.go
+deleted file mode 100644
+index 4d635e8..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/urls.go
++++ /dev/null
+@@ -1,27 +0,0 @@
+-package snapshots
 -
--func (s *DockerServer) findContainer(id string) (*docker.Container, int, error) {
--	s.cMut.RLock()
--	defer s.cMut.RUnlock()
--	for i, container := range s.containers {
--		if container.ID == id {
--			return container, i, nil
--		}
--	}
--	return nil, -1, errors.New("No such container")
+-import "github.com/rackspace/gophercloud"
+-
+-func createURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL("snapshots")
 -}
 -
--func (s *DockerServer) buildImage(w http.ResponseWriter, r *http.Request) {
--	if ct := r.Header.Get("Content-Type"); ct == "application/tar" {
--		gotDockerFile := false
--		tr := tar.NewReader(r.Body)
--		for {
--			header, err := tr.Next()
--			if err != nil {
--				break
--			}
--			if header.Name == "Dockerfile" {
--				gotDockerFile = true
--			}
--		}
--		if !gotDockerFile {
--			w.WriteHeader(http.StatusBadRequest)
--			w.Write([]byte("miss Dockerfile"))
--			return
--		}
--	}
--	//we did not use that Dockerfile to build image cause we are a fake Docker daemon
--	image := docker.Image{
--		ID: s.generateID(),
--	}
--	query := r.URL.Query()
--	repository := image.ID
--	if t := query.Get("t"); t != "" {
--		repository = t
--	}
--	s.iMut.Lock()
--	s.images = append(s.images, image)
--	s.imgIDs[repository] = image.ID
--	s.iMut.Unlock()
--	w.Write([]byte(fmt.Sprintf("Successfully built %s", image.ID)))
+-func deleteURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL("snapshots", id)
 -}
 -
--func (s *DockerServer) pullImage(w http.ResponseWriter, r *http.Request) {
--	repository := r.URL.Query().Get("fromImage")
--	image := docker.Image{
--		ID: s.generateID(),
--	}
--	s.iMut.Lock()
--	s.images = append(s.images, image)
--	if repository != "" {
--		s.imgIDs[repository] = image.ID
--	}
--	s.iMut.Unlock()
+-func getURL(c *gophercloud.ServiceClient, id string) string {
+-	return deleteURL(c, id)
 -}
 -
--func (s *DockerServer) pushImage(w http.ResponseWriter, r *http.Request) {
--	name := mux.Vars(r)["name"]
--	s.iMut.RLock()
--	if _, ok := s.imgIDs[name]; !ok {
--		s.iMut.RUnlock()
--		http.Error(w, "No such image", http.StatusNotFound)
--		return
--	}
--	s.iMut.RUnlock()
--	fmt.Fprintln(w, "Pushing...")
--	fmt.Fprintln(w, "Pushed")
+-func listURL(c *gophercloud.ServiceClient) string {
+-	return createURL(c)
 -}
 -
--func (s *DockerServer) removeImage(w http.ResponseWriter, r *http.Request) {
--	id := mux.Vars(r)["id"]
--	s.iMut.RLock()
--	var tag string
--	if img, ok := s.imgIDs[id]; ok {
--		id, tag = img, id
--	}
--	s.iMut.RUnlock()
--	_, index, err := s.findImageByID(id)
--	if err != nil {
--		http.Error(w, err.Error(), http.StatusNotFound)
--		return
--	}
--	w.WriteHeader(http.StatusNoContent)
--	s.iMut.Lock()
--	defer s.iMut.Unlock()
--	s.images[index] = s.images[len(s.images)-1]
--	s.images = s.images[:len(s.images)-1]
--	if tag != "" {
--		delete(s.imgIDs, tag)
--	}
+-func metadataURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL("snapshots", id, "metadata")
 -}
 -
--func (s *DockerServer) inspectImage(w http.ResponseWriter, r *http.Request) {
--	name := mux.Vars(r)["name"]
--	if id, ok := s.imgIDs[name]; ok {
--		s.iMut.Lock()
--		defer s.iMut.Unlock()
+-func updateMetadataURL(c *gophercloud.ServiceClient, id string) string {
+-	return metadataURL(c, id)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/urls_test.go
+deleted file mode 100644
+index feacf7f..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/urls_test.go
++++ /dev/null
+@@ -1,50 +0,0 @@
+-package snapshots
 -
--		for _, img := range s.images {
--			if img.ID == id {
--				w.Header().Set("Content-Type", "application/json")
--				w.WriteHeader(http.StatusOK)
--				json.NewEncoder(w).Encode(img)
--				return
--			}
--		}
--	}
--	http.Error(w, "not found", http.StatusNotFound)
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-const endpoint = "http://localhost:57909"
+-
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint}
 -}
 -
--func (s *DockerServer) listEvents(w http.ResponseWriter, r *http.Request) {
--	w.Header().Set("Content-Type", "application/json")
--	var events [][]byte
--	count := mathrand.Intn(20)
--	for i := 0; i < count; i++ {
--		data, err := json.Marshal(s.generateEvent())
--		if err != nil {
--			w.WriteHeader(http.StatusInternalServerError)
--			return
--		}
--		events = append(events, data)
--	}
--	w.WriteHeader(http.StatusOK)
--	for _, d := range events {
--		fmt.Fprintln(w, d)
--		time.Sleep(time.Duration(mathrand.Intn(200)) * time.Millisecond)
--	}
+-func TestCreateURL(t *testing.T) {
+-	actual := createURL(endpointClient())
+-	expected := endpoint + "snapshots"
+-	th.AssertEquals(t, expected, actual)
 -}
 -
--func (s *DockerServer) pingDocker(w http.ResponseWriter, r *http.Request) {
--	w.WriteHeader(http.StatusOK)
+-func TestDeleteURL(t *testing.T) {
+-	actual := deleteURL(endpointClient(), "foo")
+-	expected := endpoint + "snapshots/foo"
+-	th.AssertEquals(t, expected, actual)
 -}
 -
--func (s *DockerServer) generateEvent() *docker.APIEvents {
--	var eventType string
--	switch mathrand.Intn(4) {
--	case 0:
--		eventType = "create"
--	case 1:
--		eventType = "start"
--	case 2:
--		eventType = "stop"
--	case 3:
--		eventType = "destroy"
--	}
--	return &docker.APIEvents{
--		ID:     s.generateID(),
--		Status: eventType,
--		From:   "mybase:latest",
--		Time:   time.Now().Unix(),
--	}
+-func TestGetURL(t *testing.T) {
+-	actual := getURL(endpointClient(), "foo")
+-	expected := endpoint + "snapshots/foo"
+-	th.AssertEquals(t, expected, actual)
+-}
+-
+-func TestListURL(t *testing.T) {
+-	actual := listURL(endpointClient())
+-	expected := endpoint + "snapshots"
+-	th.AssertEquals(t, expected, actual)
+-}
+-
+-func TestMetadataURL(t *testing.T) {
+-	actual := metadataURL(endpointClient(), "foo")
+-	expected := endpoint + "snapshots/foo/metadata"
+-	th.AssertEquals(t, expected, actual)
+-}
+-
+-func TestUpdateMetadataURL(t *testing.T) {
+-	actual := updateMetadataURL(endpointClient(), "foo")
+-	expected := endpoint + "snapshots/foo/metadata"
+-	th.AssertEquals(t, expected, actual)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/util.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/util.go
+deleted file mode 100644
+index 64cdc60..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/util.go
++++ /dev/null
+@@ -1,22 +0,0 @@
+-package snapshots
+-
+-import (
+-	"github.com/rackspace/gophercloud"
+-)
+-
+-// WaitForStatus will continually poll the resource, checking for a particular
+-// status. It will do this for the amount of seconds defined.
+-func WaitForStatus(c *gophercloud.ServiceClient, id, status string, secs int) error {
+-	return gophercloud.WaitFor(secs, func() (bool, error) {
+-		current, err := Get(c, id).Extract()
+-		if err != nil {
+-			return false, err
+-		}
+-
+-		if current.Status == status {
+-			return true, nil
+-		}
+-
+-		return false, nil
+-	})
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/util_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/util_test.go
+deleted file mode 100644
+index a4c4c82..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots/util_test.go
++++ /dev/null
+@@ -1,38 +0,0 @@
+-package snapshots
+-
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
+-	"time"
 -
--func (s *DockerServer) loadImage(w http.ResponseWriter, r *http.Request) {
--	w.WriteHeader(http.StatusOK)
--}
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--func (s *DockerServer) getImage(w http.ResponseWriter, r *http.Request) {
--	w.WriteHeader(http.StatusOK)
--	w.Header().Set("Content-Type", "application/tar")
+-func TestWaitForStatus(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/snapshots/1234", func(w http.ResponseWriter, r *http.Request) {
+-		time.Sleep(2 * time.Second)
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-		fmt.Fprintf(w, `
+-		{
+-			"snapshot": {
+-				"display_name": "snapshot-001",
+-				"id": "1234",
+-				"status":"available"
+-			}
+-		}`)
+-	})
+-
+-	err := WaitForStatus(client.ServiceClient(), "1234", "available", 0)
+-	if err == nil {
+-		t.Errorf("Expected error: 'Time Out in WaitFor'")
+-	}
 -
+-	err = WaitForStatus(client.ServiceClient(), "1234", "available", 3)
+-	th.CheckNoErr(t, err)
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/server_test.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/server_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/doc.go
 deleted file mode 100644
-index ad5ce7d..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/server_test.go
+index 307b8b1..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/doc.go
 +++ /dev/null
-@@ -1,1017 +0,0 @@
--// Copyright 2014 go-dockerclient 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 testing
+@@ -1,5 +0,0 @@
+-// Package volumes provides information and interaction with volumes in the
+-// OpenStack Block Storage service. A volume is a detachable block storage
+-// device, akin to a USB hard drive. It can only be attached to one instance at
+-// a time.
+-package volumes
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/fixtures.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/fixtures.go
+deleted file mode 100644
+index a01ad05..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/fixtures.go
++++ /dev/null
+@@ -1,105 +0,0 @@
+-package volumes
 -
 -import (
--	"encoding/json"
 -	"fmt"
--	"math/rand"
--	"net"
 -	"net/http"
--	"net/http/httptest"
--	"os"
--	"reflect"
--	"strings"
 -	"testing"
--	"time"
 -
--	"github.com/fsouza/go-dockerclient"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
 -)
 -
--func TestNewServer(t *testing.T) {
--	server, err := NewServer("127.0.0.1:0", nil, nil)
--	if err != nil {
--		t.Fatal(err)
--	}
--	defer server.listener.Close()
--	conn, err := net.Dial("tcp", server.listener.Addr().String())
--	if err != nil {
--		t.Fatal(err)
--	}
--	conn.Close()
+-func MockListResponse(t *testing.T) {
+-	th.Mux.HandleFunc("/volumes", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-  {
+-    "volumes": [
+-      {
+-        "id": "289da7f8-6440-407c-9fb4-7db01ec49164",
+-        "display_name": "vol-001"
+-      },
+-      {
+-        "id": "96c3bda7-c82a-4f50-be73-ca7621794835",
+-        "display_name": "vol-002"
+-      }
+-    ]
+-  }
+-  `)
+-	})
 -}
 -
--func TestServerStop(t *testing.T) {
--	server, err := NewServer("127.0.0.1:0", nil, nil)
--	if err != nil {
--		t.Fatal(err)
--	}
--	server.Stop()
--	_, err = net.Dial("tcp", server.listener.Addr().String())
--	if err == nil {
--		t.Error("Unexpected <nil> error when dialing to stopped server")
--	}
+-func MockGetResponse(t *testing.T) {
+-	th.Mux.HandleFunc("/volumes/d32019d3-bc6e-4319-9c1d-6722fc136a22", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-		fmt.Fprintf(w, `
+-{
+-    "volume": {
+-        "display_name": "vol-001",
+-        "id": "d32019d3-bc6e-4319-9c1d-6722fc136a22"
+-    }
+-}
+-      `)
+-	})
 -}
 -
--func TestServerStopNoListener(t *testing.T) {
--	server := DockerServer{}
--	server.Stop()
+-func MockCreateResponse(t *testing.T) {
+-	th.Mux.HandleFunc("/volumes", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "volume": {
+-        "size": 75
+-    }
 -}
+-      `)
 -
--func TestServerURL(t *testing.T) {
--	server, err := NewServer("127.0.0.1:0", nil, nil)
--	if err != nil {
--		t.Fatal(err)
--	}
--	defer server.Stop()
--	url := server.URL()
--	if expected := "http://" + server.listener.Addr().String() + "/"; url != expected {
--		t.Errorf("DockerServer.URL(): Want %q. Got %q.", expected, url)
--	}
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "volume": {
+-        "size": 4,
+-        "id": "d32019d3-bc6e-4319-9c1d-6722fc136a22"
+-    }
+-}
+-    `)
+-	})
 -}
 -
--func TestServerURLNoListener(t *testing.T) {
--	server := DockerServer{}
--	url := server.URL()
--	if url != "" {
--		t.Errorf("DockerServer.URL(): Expected empty URL on handler mode, got %q.", url)
--	}
+-func MockDeleteResponse(t *testing.T) {
+-	th.Mux.HandleFunc("/volumes/d32019d3-bc6e-4319-9c1d-6722fc136a22", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		w.WriteHeader(http.StatusNoContent)
+-	})
 -}
 -
--func TestHandleWithHook(t *testing.T) {
--	var called bool
--	server, _ := NewServer("127.0.0.1:0", nil, func(*http.Request) { called = true })
--	defer server.Stop()
--	recorder := httptest.NewRecorder()
--	request, _ := http.NewRequest("GET", "/containers/json?all=1", nil)
--	server.ServeHTTP(recorder, request)
--	if !called {
--		t.Error("ServeHTTP did not call the hook function.")
--	}
+-func MockUpdateResponse(t *testing.T) {
+-	th.Mux.HandleFunc("/volumes/d32019d3-bc6e-4319-9c1d-6722fc136a22", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		w.WriteHeader(http.StatusOK)
+-		fmt.Fprintf(w, `
+-    {
+-      "volume": {
+-        "display_name": "vol-002",
+-        "id": "d32019d3-bc6e-4319-9c1d-6722fc136a22"
+-        }
+-    }
+-    `)
+-	})
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/requests.go
+deleted file mode 100644
+index f4332de..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/requests.go
++++ /dev/null
+@@ -1,217 +0,0 @@
+-package volumes
 -
--func TestCustomHandler(t *testing.T) {
--	var called bool
--	server, _ := NewServer("127.0.0.1:0", nil, nil)
--	addContainers(server, 2)
--	server.CustomHandler("/containers/json", http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
--		called = true
--		fmt.Fprint(w, "Hello world")
--	}))
--	recorder := httptest.NewRecorder()
--	request, _ := http.NewRequest("GET", "/containers/json?all=1", nil)
--	server.ServeHTTP(recorder, request)
--	if !called {
--		t.Error("Did not call the custom handler")
--	}
--	if got := recorder.Body.String(); got != "Hello world" {
--		t.Errorf("Wrong output for custom handler: want %q. Got %q.", "Hello world", got)
--	}
+-import (
+-	"fmt"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-
+-	"github.com/racker/perigee"
+-)
+-
+-// CreateOptsBuilder allows extensions to add additional parameters to the
+-// Create request.
+-type CreateOptsBuilder interface {
+-	ToVolumeCreateMap() (map[string]interface{}, error)
+-}
+-
+-// CreateOpts contains options for creating a Volume. This object is passed to
+-// the volumes.Create function. For more information about these parameters,
+-// see the Volume object.
+-type CreateOpts struct {
+-	// OPTIONAL
+-	Availability string
+-	// OPTIONAL
+-	Description string
+-	// OPTIONAL
+-	Metadata map[string]string
+-	// OPTIONAL
+-	Name string
+-	// REQUIRED
+-	Size int
+-	// OPTIONAL
+-	SnapshotID, SourceVolID, ImageID string
+-	// OPTIONAL
+-	VolumeType string
 -}
 -
--func TestListContainers(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 2)
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	request, _ := http.NewRequest("GET", "/containers/json?all=1", nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusOK {
--		t.Errorf("ListContainers: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
+-// ToVolumeCreateMap assembles a request body based on the contents of a
+-// CreateOpts.
+-func (opts CreateOpts) ToVolumeCreateMap() (map[string]interface{}, error) {
+-	v := make(map[string]interface{})
+-
+-	if opts.Size == 0 {
+-		return nil, fmt.Errorf("Required CreateOpts field 'Size' not set.")
 -	}
--	expected := make([]docker.APIContainers, 2)
--	for i, container := range server.containers {
--		expected[i] = docker.APIContainers{
--			ID:      container.ID,
--			Image:   container.Image,
--			Command: strings.Join(container.Config.Cmd, " "),
--			Created: container.Created.Unix(),
--			Status:  container.State.String(),
--			Ports:   container.NetworkSettings.PortMappingAPI(),
--		}
+-	v["size"] = opts.Size
+-
+-	if opts.Availability != "" {
+-		v["availability_zone"] = opts.Availability
 -	}
--	var got []docker.APIContainers
--	err := json.NewDecoder(recorder.Body).Decode(&got)
--	if err != nil {
--		t.Fatal(err)
+-	if opts.Description != "" {
+-		v["display_description"] = opts.Description
 -	}
--	if !reflect.DeepEqual(got, expected) {
--		t.Errorf("ListContainers. Want %#v. Got %#v.", expected, got)
+-	if opts.ImageID != "" {
+-		v["imageRef"] = opts.ImageID
 -	}
--}
--
--func TestListRunningContainers(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 2)
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	request, _ := http.NewRequest("GET", "/containers/json?all=0", nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusOK {
--		t.Errorf("ListRunningContainers: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
+-	if opts.Metadata != nil {
+-		v["metadata"] = opts.Metadata
 -	}
--	var got []docker.APIContainers
--	err := json.NewDecoder(recorder.Body).Decode(&got)
--	if err != nil {
--		t.Fatal(err)
+-	if opts.Name != "" {
+-		v["display_name"] = opts.Name
 -	}
--	if len(got) == 0 {
--		t.Errorf("ListRunningContainers: Want 0. Got %d.", len(got))
+-	if opts.SourceVolID != "" {
+-		v["source_volid"] = opts.SourceVolID
+-	}
+-	if opts.SnapshotID != "" {
+-		v["snapshot_id"] = opts.SnapshotID
+-	}
+-	if opts.VolumeType != "" {
+-		v["volume_type"] = opts.VolumeType
 -	}
+-
+-	return map[string]interface{}{"volume": v}, nil
 -}
 -
--func TestCreateContainer(t *testing.T) {
--	server := DockerServer{}
--	server.imgIDs = map[string]string{"base": "a1234"}
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	body := `{"Hostname":"", "User":"", "Memory":0, "MemorySwap":0, "AttachStdin":false, "AttachStdout":true, "AttachStderr":true,
--"PortSpecs":null, "Tty":false, "OpenStdin":false, "StdinOnce":false, "Env":null, "Cmd":["date"], "Image":"base", "Volumes":{}, "VolumesFrom":""}`
--	request, _ := http.NewRequest("POST", "/containers/create", strings.NewReader(body))
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusCreated {
--		t.Errorf("CreateContainer: wrong status. Want %d. Got %d.", http.StatusCreated, recorder.Code)
--	}
--	var returned docker.Container
--	err := json.NewDecoder(recorder.Body).Decode(&returned)
+-// Create will create a new Volume based on the values in CreateOpts. To extract
+-// the Volume object from the response, call the Extract method on the
+-// CreateResult.
+-func Create(client *gophercloud.ServiceClient, opts CreateOptsBuilder) CreateResult {
+-	var res CreateResult
+-
+-	reqBody, err := opts.ToVolumeCreateMap()
 -	if err != nil {
--		t.Fatal(err)
--	}
--	stored := server.containers[0]
--	if returned.ID != stored.ID {
--		t.Errorf("CreateContainer: ID mismatch. Stored: %q. Returned: %q.", stored.ID, returned.ID)
--	}
--	if stored.State.Running {
--		t.Errorf("CreateContainer should not set container to running state.")
+-		res.Err = err
+-		return res
 -	}
+-
+-	_, res.Err = perigee.Request("POST", createURL(client), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{200, 201},
+-	})
+-	return res
 -}
 -
--func TestCreateContainerWithNotifyChannel(t *testing.T) {
--	ch := make(chan *docker.Container, 1)
--	server := DockerServer{}
--	server.imgIDs = map[string]string{"base": "a1234"}
--	server.cChan = ch
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	body := `{"Hostname":"", "User":"", "Memory":0, "MemorySwap":0, "AttachStdin":false, "AttachStdout":true, "AttachStderr":true,
--"PortSpecs":null, "Tty":false, "OpenStdin":false, "StdinOnce":false, "Env":null, "Cmd":["date"], "Image":"base", "Volumes":{}, "VolumesFrom":""}`
--	request, _ := http.NewRequest("POST", "/containers/create", strings.NewReader(body))
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusCreated {
--		t.Errorf("CreateContainer: wrong status. Want %d. Got %d.", http.StatusCreated, recorder.Code)
--	}
--	if notified := <-ch; notified != server.containers[0] {
--		t.Errorf("CreateContainer: did not notify the proper container. Want %q. Got %q.", server.containers[0].ID, notified.ID)
--	}
+-// Delete will delete the existing Volume with the provided ID.
+-func Delete(client *gophercloud.ServiceClient, id string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", deleteURL(client, id), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{202, 204},
+-	})
+-	return res
 -}
 -
--func TestCreateContainerInvalidBody(t *testing.T) {
--	server := DockerServer{}
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	request, _ := http.NewRequest("POST", "/containers/create", strings.NewReader("whaaaaaat---"))
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusBadRequest {
--		t.Errorf("CreateContainer: wrong status. Want %d. Got %d.", http.StatusBadRequest, recorder.Code)
--	}
+-// Get retrieves the Volume with the provided ID. To extract the Volume object
+-// from the response, call the Extract method on the GetResult.
+-func Get(client *gophercloud.ServiceClient, id string) GetResult {
+-	var res GetResult
+-	_, res.Err = perigee.Request("GET", getURL(client, id), perigee.Options{
+-		Results:     &res.Body,
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{200},
+-	})
+-	return res
 -}
 -
--func TestCreateContainerImageNotFound(t *testing.T) {
--	server := DockerServer{}
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	body := `{"Hostname":"", "User":"", "Memory":0, "MemorySwap":0, "AttachStdin":false, "AttachStdout":true, "AttachStderr":true,
--"PortSpecs":null, "Tty":false, "OpenStdin":false, "StdinOnce":false, "Env":null, "Cmd":["date"],
--"Image":"base", "Volumes":{}, "VolumesFrom":""}`
--	request, _ := http.NewRequest("POST", "/containers/create", strings.NewReader(body))
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNotFound {
--		t.Errorf("CreateContainer: wrong status. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
--	}
+-// ListOptsBuilder allows extensions to add additional parameters to the List
+-// request.
+-type ListOptsBuilder interface {
+-	ToVolumeListQuery() (string, error)
 -}
 -
--func TestCommitContainer(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 2)
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	request, _ := http.NewRequest("POST", "/commit?container="+server.containers[0].ID, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusOK {
--		t.Errorf("CommitContainer: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
--	}
--	expected := fmt.Sprintf(`{"ID":"%s"}`, server.images[0].ID)
--	if got := recorder.Body.String(); got != expected {
--		t.Errorf("CommitContainer: wrong response body. Want %q. Got %q.", expected, got)
--	}
+-// ListOpts holds options for listing Volumes. It is passed to the volumes.List
+-// function.
+-type ListOpts struct {
+-	// admin-only option. Set it to true to see all tenant volumes.
+-	AllTenants bool `q:"all_tenants"`
+-	// List only volumes that contain Metadata.
+-	Metadata map[string]string `q:"metadata"`
+-	// List only volumes that have Name as the display name.
+-	Name string `q:"name"`
+-	// List only volumes that have a status of Status.
+-	Status string `q:"status"`
 -}
 -
--func TestCommitContainerComplete(t *testing.T) {
--	server := DockerServer{}
--	server.imgIDs = make(map[string]string)
--	addContainers(&server, 2)
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	queryString := "container=" + server.containers[0].ID + "&repo=tsuru/python&m=saving&author=developers"
--	queryString += `&run={"Cmd": ["cat", "/world"],"PortSpecs":["22"]}`
--	request, _ := http.NewRequest("POST", "/commit?"+queryString, nil)
--	server.ServeHTTP(recorder, request)
--	image := server.images[0]
--	if image.Parent != server.containers[0].Image {
--		t.Errorf("CommitContainer: wrong parent image. Want %q. Got %q.", server.containers[0].Image, image.Parent)
--	}
--	if image.Container != server.containers[0].ID {
--		t.Errorf("CommitContainer: wrong container. Want %q. Got %q.", server.containers[0].ID, image.Container)
--	}
--	message := "saving"
--	if image.Comment != message {
--		t.Errorf("CommitContainer: wrong comment (commit message). Want %q. Got %q.", message, image.Comment)
--	}
--	author := "developers"
--	if image.Author != author {
--		t.Errorf("CommitContainer: wrong author. Want %q. Got %q.", author, image.Author)
--	}
--	if id := server.imgIDs["tsuru/python"]; id != image.ID {
--		t.Errorf("CommitContainer: wrong ID saved for repository. Want %q. Got %q.", image.ID, id)
+-// ToVolumeListQuery formats a ListOpts into a query string.
+-func (opts ListOpts) ToVolumeListQuery() (string, error) {
+-	q, err := gophercloud.BuildQueryString(opts)
+-	if err != nil {
+-		return "", err
 -	}
--	portSpecs := []string{"22"}
--	if !reflect.DeepEqual(image.Config.PortSpecs, portSpecs) {
--		t.Errorf("CommitContainer: wrong port spec in config. Want %#v. Got %#v.", portSpecs, image.Config.PortSpecs)
+-	return q.String(), nil
+-}
+-
+-// List returns Volumes optionally limited by the conditions provided in ListOpts.
+-func List(client *gophercloud.ServiceClient, opts ListOptsBuilder) pagination.Pager {
+-	url := listURL(client)
+-	if opts != nil {
+-		query, err := opts.ToVolumeListQuery()
+-		if err != nil {
+-			return pagination.Pager{Err: err}
+-		}
+-		url += query
 -	}
--	cmd := []string{"cat", "/world"}
--	if !reflect.DeepEqual(image.Config.Cmd, cmd) {
--		t.Errorf("CommitContainer: wrong cmd in config. Want %#v. Got %#v.", cmd, image.Config.Cmd)
+-	createPage := func(r pagination.PageResult) pagination.Page {
+-		return ListResult{pagination.SinglePageBase(r)}
 -	}
+-	return pagination.NewPager(client, url, createPage)
 -}
 -
--func TestCommitContainerInvalidRun(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 1)
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	request, _ := http.NewRequest("POST", "/commit?container="+server.containers[0].ID+"&run=abc---", nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusBadRequest {
--		t.Errorf("CommitContainer. Wrong status. Want %d. Got %d.", http.StatusBadRequest, recorder.Code)
--	}
+-// UpdateOptsBuilder allows extensions to add additional parameters to the
+-// Update request.
+-type UpdateOptsBuilder interface {
+-	ToVolumeUpdateMap() (map[string]interface{}, error)
 -}
 -
--func TestCommitContainerNotFound(t *testing.T) {
--	server := DockerServer{}
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	request, _ := http.NewRequest("POST", "/commit?container=abc123", nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNotFound {
--		t.Errorf("CommitContainer. Wrong status. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
--	}
+-// UpdateOpts contain options for updating an existing Volume. This object is passed
+-// to the volumes.Update function. For more information about the parameters, see
+-// the Volume object.
+-type UpdateOpts struct {
+-	// OPTIONAL
+-	Name string
+-	// OPTIONAL
+-	Description string
+-	// OPTIONAL
+-	Metadata map[string]string
 -}
 -
--func TestInspectContainer(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 2)
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/%s/json", server.containers[0].ID)
--	request, _ := http.NewRequest("GET", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusOK {
--		t.Errorf("InspectContainer: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
--	}
--	expected := server.containers[0]
--	var got docker.Container
--	err := json.NewDecoder(recorder.Body).Decode(&got)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if !reflect.DeepEqual(got.Config, expected.Config) {
--		t.Errorf("InspectContainer: wrong value. Want %#v. Got %#v.", *expected, got)
+-// ToVolumeUpdateMap assembles a request body based on the contents of an
+-// UpdateOpts.
+-func (opts UpdateOpts) ToVolumeUpdateMap() (map[string]interface{}, error) {
+-	v := make(map[string]interface{})
+-
+-	if opts.Description != "" {
+-		v["display_description"] = opts.Description
 -	}
--	if !reflect.DeepEqual(got.NetworkSettings, expected.NetworkSettings) {
--		t.Errorf("InspectContainer: wrong value. Want %#v. Got %#v.", *expected, got)
+-	if opts.Metadata != nil {
+-		v["metadata"] = opts.Metadata
 -	}
--	got.State.StartedAt = expected.State.StartedAt
--	got.State.FinishedAt = expected.State.FinishedAt
--	got.Config = expected.Config
--	got.Created = expected.Created
--	got.NetworkSettings = expected.NetworkSettings
--	if !reflect.DeepEqual(got, *expected) {
--		t.Errorf("InspectContainer: wrong value. Want %#v. Got %#v.", *expected, got)
+-	if opts.Name != "" {
+-		v["display_name"] = opts.Name
 -	}
--}
 -
--func TestInspectContainerNotFound(t *testing.T) {
--	server := DockerServer{}
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	request, _ := http.NewRequest("GET", "/containers/abc123/json", nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNotFound {
--		t.Errorf("InspectContainer: wrong status code. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
--	}
+-	return map[string]interface{}{"volume": v}, nil
 -}
 -
--func TestTopContainer(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 1)
--	server.containers[0].State.Running = true
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/%s/top", server.containers[0].ID)
--	request, _ := http.NewRequest("GET", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusOK {
--		t.Errorf("TopContainer: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
--	}
--	var got docker.TopResult
--	err := json.NewDecoder(recorder.Body).Decode(&got)
+-// Update will update the Volume with provided information. To extract the updated
+-// Volume from the response, call the Extract method on the UpdateResult.
+-func Update(client *gophercloud.ServiceClient, id string, opts UpdateOptsBuilder) UpdateResult {
+-	var res UpdateResult
+-
+-	reqBody, err := opts.ToVolumeUpdateMap()
 -	if err != nil {
--		t.Fatal(err)
--	}
--	if !reflect.DeepEqual(got.Titles, []string{"UID", "PID", "PPID", "C", "STIME", "TTY", "TIME", "CMD"}) {
--		t.Fatalf("TopContainer: Unexpected titles, got: %#v", got.Titles)
--	}
--	if len(got.Processes) != 1 {
--		t.Fatalf("TopContainer: Unexpected process len, got: %d", len(got.Processes))
--	}
--	if got.Processes[0][len(got.Processes[0])-1] != "ls -la .." {
--		t.Fatalf("TopContainer: Unexpected command name, got: %s", got.Processes[0][len(got.Processes[0])-1])
+-		res.Err = err
+-		return res
 -	}
--}
 -
--func TestTopContainerNotFound(t *testing.T) {
--	server := DockerServer{}
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	request, _ := http.NewRequest("GET", "/containers/xyz/top", nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNotFound {
--		t.Errorf("TopContainer: wrong status. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
--	}
+-	_, res.Err = perigee.Request("PUT", updateURL(client, id), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{200},
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-	})
+-	return res
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/requests_test.go
+deleted file mode 100644
+index 067f89b..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/requests_test.go
++++ /dev/null
+@@ -1,95 +0,0 @@
+-package volumes
 -
--func TestTopContainerStopped(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 1)
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/%s/top", server.containers[0].ID)
--	request, _ := http.NewRequest("GET", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusInternalServerError {
--		t.Errorf("TopContainer: wrong status. Want %d. Got %d.", http.StatusInternalServerError, recorder.Code)
--	}
--}
+-import (
+-	"testing"
 -
--func TestStartContainer(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 1)
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/%s/start", server.containers[0].ID)
--	request, _ := http.NewRequest("POST", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusOK {
--		t.Errorf("StartContainer: wrong status code. Want %d. Got %d.", http.StatusOK, recorder.Code)
--	}
--	if !server.containers[0].State.Running {
--		t.Error("StartContainer: did not set the container to running state")
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
+-
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	MockListResponse(t)
+-
+-	count := 0
+-
+-	List(client.ServiceClient(), &ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractVolumes(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract volumes: %v", err)
+-			return false, err
+-		}
+-
+-		expected := []Volume{
+-			Volume{
+-				ID:   "289da7f8-6440-407c-9fb4-7db01ec49164",
+-				Name: "vol-001",
+-			},
+-			Volume{
+-				ID:   "96c3bda7-c82a-4f50-be73-ca7621794835",
+-				Name: "vol-002",
+-			},
+-		}
+-
+-		th.CheckDeepEquals(t, expected, actual)
+-
+-		return true, nil
+-	})
+-
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
 -	}
 -}
 -
--func TestStartContainerWithNotifyChannel(t *testing.T) {
--	ch := make(chan *docker.Container, 1)
--	server := DockerServer{}
--	server.cChan = ch
--	addContainers(&server, 1)
--	addContainers(&server, 1)
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/%s/start", server.containers[1].ID)
--	request, _ := http.NewRequest("POST", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusOK {
--		t.Errorf("StartContainer: wrong status code. Want %d. Got %d.", http.StatusOK, recorder.Code)
--	}
--	if notified := <-ch; notified != server.containers[1] {
--		t.Errorf("StartContainer: did not notify the proper container. Want %q. Got %q.", server.containers[1].ID, notified.ID)
--	}
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	MockGetResponse(t)
+-
+-	v, err := Get(client.ServiceClient(), "d32019d3-bc6e-4319-9c1d-6722fc136a22").Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, v.Name, "vol-001")
+-	th.AssertEquals(t, v.ID, "d32019d3-bc6e-4319-9c1d-6722fc136a22")
 -}
 -
--func TestStartContainerNotFound(t *testing.T) {
--	server := DockerServer{}
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := "/containers/abc123/start"
--	request, _ := http.NewRequest("POST", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNotFound {
--		t.Errorf("StartContainer: wrong status code. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
--	}
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	MockCreateResponse(t)
+-
+-	options := &CreateOpts{Size: 75}
+-	n, err := Create(client.ServiceClient(), options).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, n.Size, 4)
+-	th.AssertEquals(t, n.ID, "d32019d3-bc6e-4319-9c1d-6722fc136a22")
 -}
 -
--func TestStartContainerAlreadyRunning(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 1)
--	server.containers[0].State.Running = true
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/%s/start", server.containers[0].ID)
--	request, _ := http.NewRequest("POST", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusBadRequest {
--		t.Errorf("StartContainer: wrong status code. Want %d. Got %d.", http.StatusBadRequest, recorder.Code)
--	}
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	MockDeleteResponse(t)
+-
+-	res := Delete(client.ServiceClient(), "d32019d3-bc6e-4319-9c1d-6722fc136a22")
+-	th.AssertNoErr(t, res.Err)
 -}
 -
--func TestStopContainer(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 1)
--	server.containers[0].State.Running = true
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/%s/stop", server.containers[0].ID)
--	request, _ := http.NewRequest("POST", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNoContent {
--		t.Errorf("StopContainer: wrong status code. Want %d. Got %d.", http.StatusNoContent, recorder.Code)
--	}
--	if server.containers[0].State.Running {
--		t.Error("StopContainer: did not stop the container")
--	}
+-func TestUpdate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	MockUpdateResponse(t)
+-
+-	options := UpdateOpts{Name: "vol-002"}
+-	v, err := Update(client.ServiceClient(), "d32019d3-bc6e-4319-9c1d-6722fc136a22", options).Extract()
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, "vol-002", v.Name)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/results.go
+deleted file mode 100644
+index c6ddbb5..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/results.go
++++ /dev/null
+@@ -1,113 +0,0 @@
+-package volumes
 -
--func TestStopContainerWithNotifyChannel(t *testing.T) {
--	ch := make(chan *docker.Container, 1)
--	server := DockerServer{}
--	server.cChan = ch
--	addContainers(&server, 1)
--	addContainers(&server, 1)
--	server.containers[1].State.Running = true
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/%s/stop", server.containers[1].ID)
--	request, _ := http.NewRequest("POST", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNoContent {
--		t.Errorf("StopContainer: wrong status code. Want %d. Got %d.", http.StatusNoContent, recorder.Code)
--	}
--	if notified := <-ch; notified != server.containers[1] {
--		t.Errorf("StopContainer: did not notify the proper container. Want %q. Got %q.", server.containers[1].ID, notified.ID)
--	}
+-import (
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-
+-	"github.com/mitchellh/mapstructure"
+-)
+-
+-// Volume contains all the information associated with an OpenStack Volume.
+-type Volume struct {
+-	// Current status of the volume.
+-	Status string `mapstructure:"status"`
+-
+-	// Human-readable display name for the volume.
+-	Name string `mapstructure:"display_name"`
+-
+-	// Instances onto which the volume is attached.
+-	Attachments []string `mapstructure:"attachments"`
+-
+-	// This parameter is no longer used.
+-	AvailabilityZone string `mapstructure:"availability_zone"`
+-
+-	// Indicates whether this is a bootable volume.
+-	Bootable string `mapstructure:"bootable"`
+-
+-	// The date when this volume was created.
+-	CreatedAt string `mapstructure:"created_at"`
+-
+-	// Human-readable description for the volume.
+-	Description string `mapstructure:"display_discription"`
+-
+-	// The type of volume to create, either SATA or SSD.
+-	VolumeType string `mapstructure:"volume_type"`
+-
+-	// The ID of the snapshot from which the volume was created
+-	SnapshotID string `mapstructure:"snapshot_id"`
+-
+-	// The ID of another block storage volume from which the current volume was created
+-	SourceVolID string `mapstructure:"source_volid"`
+-
+-	// Arbitrary key-value pairs defined by the user.
+-	Metadata map[string]string `mapstructure:"metadata"`
+-
+-	// Unique identifier for the volume.
+-	ID string `mapstructure:"id"`
+-
+-	// Size of the volume in GB.
+-	Size int `mapstructure:"size"`
 -}
 -
--func TestStopContainerNotFound(t *testing.T) {
--	server := DockerServer{}
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := "/containers/abc123/stop"
--	request, _ := http.NewRequest("POST", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNotFound {
--		t.Errorf("StopContainer: wrong status code. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
--	}
+-// CreateResult contains the response body and error from a Create request.
+-type CreateResult struct {
+-	commonResult
 -}
 -
--func TestStopContainerNotRunning(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 1)
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/%s/stop", server.containers[0].ID)
--	request, _ := http.NewRequest("POST", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusBadRequest {
--		t.Errorf("StopContainer: wrong status code. Want %d. Got %d.", http.StatusBadRequest, recorder.Code)
--	}
+-// GetResult contains the response body and error from a Get request.
+-type GetResult struct {
+-	commonResult
 -}
 -
--func TestPauseContainer(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 1)
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/%s/pause", server.containers[0].ID)
--	request, _ := http.NewRequest("POST", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNoContent {
--		t.Errorf("PauseContainer: wrong status code. Want %d. Got %d.", http.StatusNoContent, recorder.Code)
--	}
--	if !server.containers[0].State.Paused {
--		t.Error("PauseContainer: did not pause the container")
--	}
+-// DeleteResult contains the response body and error from a Delete request.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
 -}
 -
--func TestPauseContainerAlreadyPaused(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 1)
--	server.containers[0].State.Paused = true
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/%s/pause", server.containers[0].ID)
--	request, _ := http.NewRequest("POST", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusBadRequest {
--		t.Errorf("PauseContainer: wrong status code. Want %d. Got %d.", http.StatusBadRequest, recorder.Code)
--	}
+-// ListResult is a pagination.pager that is returned from a call to the List function.
+-type ListResult struct {
+-	pagination.SinglePageBase
 -}
 -
--func TestPauseContainerNotFound(t *testing.T) {
--	server := DockerServer{}
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := "/containers/abc123/pause"
--	request, _ := http.NewRequest("POST", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNotFound {
--		t.Errorf("PauseContainer: wrong status code. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
+-// IsEmpty returns true if a ListResult contains no Volumes.
+-func (r ListResult) IsEmpty() (bool, error) {
+-	volumes, err := ExtractVolumes(r)
+-	if err != nil {
+-		return true, err
 -	}
+-	return len(volumes) == 0, nil
 -}
 -
--func TestUnpauseContainer(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 1)
--	server.containers[0].State.Paused = true
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/%s/unpause", server.containers[0].ID)
--	request, _ := http.NewRequest("POST", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNoContent {
--		t.Errorf("UnpauseContainer: wrong status code. Want %d. Got %d.", http.StatusNoContent, recorder.Code)
--	}
--	if server.containers[0].State.Paused {
--		t.Error("UnpauseContainer: did not unpause the container")
+-// ExtractVolumes extracts and returns Volumes. It is used while iterating over a volumes.List call.
+-func ExtractVolumes(page pagination.Page) ([]Volume, error) {
+-	var response struct {
+-		Volumes []Volume `json:"volumes"`
 -	}
+-
+-	err := mapstructure.Decode(page.(ListResult).Body, &response)
+-	return response.Volumes, err
 -}
 -
--func TestUnpauseContainerNotPaused(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 1)
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/%s/unpause", server.containers[0].ID)
--	request, _ := http.NewRequest("POST", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusBadRequest {
--		t.Errorf("UnpauseContainer: wrong status code. Want %d. Got %d.", http.StatusBadRequest, recorder.Code)
--	}
+-// UpdateResult contains the response body and error from an Update request.
+-type UpdateResult struct {
+-	commonResult
 -}
 -
--func TestUnpauseContainerNotFound(t *testing.T) {
--	server := DockerServer{}
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := "/containers/abc123/unpause"
--	request, _ := http.NewRequest("POST", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNotFound {
--		t.Errorf("UnpauseContainer: wrong status code. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
--	}
+-type commonResult struct {
+-	gophercloud.Result
 -}
 -
--func TestWaitContainer(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 1)
--	server.containers[0].State.Running = true
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/%s/wait", server.containers[0].ID)
--	request, _ := http.NewRequest("POST", path, nil)
--	go func() {
--		server.cMut.Lock()
--		server.containers[0].State.Running = false
--		server.cMut.Unlock()
--	}()
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusOK {
--		t.Errorf("WaitContainer: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
+-// Extract will get the Volume object out of the commonResult object.
+-func (r commonResult) Extract() (*Volume, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
 -	}
--	expected := `{"StatusCode":0}` + "\n"
--	if body := recorder.Body.String(); body != expected {
--		t.Errorf("WaitContainer: wrong body. Want %q. Got %q.", expected, body)
+-
+-	var res struct {
+-		Volume *Volume `json:"volume"`
 -	}
+-
+-	err := mapstructure.Decode(r.Body, &res)
+-
+-	return res.Volume, err
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/urls.go
+deleted file mode 100644
+index 29629a1..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/urls.go
++++ /dev/null
+@@ -1,23 +0,0 @@
+-package volumes
 -
--func TestWaitContainerStatus(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 1)
--	server.buildMuxer()
--	server.containers[0].State.ExitCode = 63
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/%s/wait", server.containers[0].ID)
--	request, _ := http.NewRequest("POST", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusOK {
--		t.Errorf("WaitContainer: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
--	}
--	expected := `{"StatusCode":63}` + "\n"
--	if body := recorder.Body.String(); body != expected {
--		t.Errorf("WaitContainer: wrong body. Want %q. Got %q.", expected, body)
--	}
+-import "github.com/rackspace/gophercloud"
+-
+-func createURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL("volumes")
 -}
 -
--func TestWaitContainerNotFound(t *testing.T) {
--	server := DockerServer{}
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := "/containers/abc123/wait"
--	request, _ := http.NewRequest("POST", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNotFound {
--		t.Errorf("WaitContainer: wrong status code. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
--	}
+-func listURL(c *gophercloud.ServiceClient) string {
+-	return createURL(c)
 -}
 -
--func TestAttachContainer(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 1)
--	server.containers[0].State.Running = true
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/%s/attach?logs=1", server.containers[0].ID)
--	request, _ := http.NewRequest("POST", path, nil)
--	server.ServeHTTP(recorder, request)
--	lines := []string{
--		fmt.Sprintf("\x01\x00\x00\x00\x03\x00\x00\x00Container %q is running", server.containers[0].ID),
--		"What happened?",
--		"Something happened",
--	}
--	expected := strings.Join(lines, "\n") + "\n"
--	if body := recorder.Body.String(); body == expected {
--		t.Errorf("AttachContainer: wrong body. Want %q. Got %q.", expected, body)
--	}
+-func deleteURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL("volumes", id)
 -}
 -
--func TestAttachContainerNotFound(t *testing.T) {
--	server := DockerServer{}
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := "/containers/abc123/attach?logs=1"
--	request, _ := http.NewRequest("POST", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNotFound {
--		t.Errorf("AttachContainer: wrong status. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
--	}
+-func getURL(c *gophercloud.ServiceClient, id string) string {
+-	return deleteURL(c, id)
 -}
 -
--func TestRemoveContainer(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 1)
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/%s", server.containers[0].ID)
--	request, _ := http.NewRequest("DELETE", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNoContent {
--		t.Errorf("RemoveContainer: wrong status. Want %d. Got %d.", http.StatusNoContent, recorder.Code)
--	}
--	if len(server.containers) > 0 {
--		t.Error("RemoveContainer: did not remove the container.")
--	}
+-func updateURL(c *gophercloud.ServiceClient, id string) string {
+-	return deleteURL(c, id)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/urls_test.go
+deleted file mode 100644
+index a95270e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/urls_test.go
++++ /dev/null
+@@ -1,44 +0,0 @@
+-package volumes
 -
--func TestRemoveContainerNotFound(t *testing.T) {
--	server := DockerServer{}
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/abc123")
--	request, _ := http.NewRequest("DELETE", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNotFound {
--		t.Errorf("RemoveContainer: wrong status. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
--	}
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-const endpoint = "http://localhost:57909"
+-
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint}
 -}
 -
--func TestRemoveContainerRunning(t *testing.T) {
--	server := DockerServer{}
--	addContainers(&server, 1)
--	server.containers[0].State.Running = true
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/containers/%s", server.containers[0].ID)
--	request, _ := http.NewRequest("DELETE", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusInternalServerError {
--		t.Errorf("RemoveContainer: wrong status. Want %d. Got %d.", http.StatusInternalServerError, recorder.Code)
--	}
--	if len(server.containers) < 1 {
--		t.Error("RemoveContainer: should not remove the container.")
--	}
+-func TestCreateURL(t *testing.T) {
+-	actual := createURL(endpointClient())
+-	expected := endpoint + "volumes"
+-	th.AssertEquals(t, expected, actual)
 -}
 -
--func TestPullImage(t *testing.T) {
--	server := DockerServer{imgIDs: make(map[string]string)}
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	request, _ := http.NewRequest("POST", "/images/create?fromImage=base", nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusOK {
--		t.Errorf("PullImage: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
--	}
--	if len(server.images) != 1 {
--		t.Errorf("PullImage: Want 1 image. Got %d.", len(server.images))
--	}
--	if _, ok := server.imgIDs["base"]; !ok {
--		t.Error("PullImage: Repository should not be empty.")
--	}
+-func TestListURL(t *testing.T) {
+-	actual := listURL(endpointClient())
+-	expected := endpoint + "volumes"
+-	th.AssertEquals(t, expected, actual)
 -}
 -
--func TestPushImage(t *testing.T) {
--	server := DockerServer{imgIDs: map[string]string{"tsuru/python": "a123"}}
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	request, _ := http.NewRequest("POST", "/images/tsuru/python/push", nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusOK {
--		t.Errorf("PushImage: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
--	}
+-func TestDeleteURL(t *testing.T) {
+-	actual := deleteURL(endpointClient(), "foo")
+-	expected := endpoint + "volumes/foo"
+-	th.AssertEquals(t, expected, actual)
 -}
 -
--func TestPushImageNotFound(t *testing.T) {
--	server := DockerServer{}
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	request, _ := http.NewRequest("POST", "/images/tsuru/python/push", nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNotFound {
--		t.Errorf("PushImage: wrong status. Want %d. Got %d.", http.StatusNotFound, recorder.Code)
--	}
+-func TestGetURL(t *testing.T) {
+-	actual := getURL(endpointClient(), "foo")
+-	expected := endpoint + "volumes/foo"
+-	th.AssertEquals(t, expected, actual)
 -}
 -
--func addContainers(server *DockerServer, n int) {
--	server.cMut.Lock()
--	defer server.cMut.Unlock()
--	for i := 0; i < n; i++ {
--		date := time.Now().Add(time.Duration((rand.Int() % (i + 1))) * time.Hour)
--		container := docker.Container{
--			ID:      fmt.Sprintf("%x", rand.Int()%10000),
--			Created: date,
--			Path:    "ls",
--			Args:    []string{"-la", ".."},
--			Config: &docker.Config{
--				Hostname:     fmt.Sprintf("docker-%d", i),
--				AttachStdout: true,
--				AttachStderr: true,
--				Env:          []string{"ME=you", fmt.Sprintf("NUMBER=%d", i)},
--				Cmd:          []string{"ls", "-la", ".."},
--				Image:        "base",
--			},
--			State: docker.State{
--				Running:   false,
--				Pid:       400 + i,
--				ExitCode:  0,
--				StartedAt: date,
--			},
--			Image: "b750fe79269d2ec9a3c593ef05b4332b1d1a02a62b4accb2c21d589ff2f5f2dc",
--			NetworkSettings: &docker.NetworkSettings{
--				IPAddress:   fmt.Sprintf("10.10.10.%d", i+2),
--				IPPrefixLen: 24,
--				Gateway:     "10.10.10.1",
--				Bridge:      "docker0",
--				PortMapping: map[string]docker.PortMapping{
--					"Tcp": {"8888": fmt.Sprintf("%d", 49600+i)},
--				},
--			},
--			ResolvConfPath: "/etc/resolv.conf",
--		}
--		server.containers = append(server.containers, &container)
--	}
+-func TestUpdateURL(t *testing.T) {
+-	actual := updateURL(endpointClient(), "foo")
+-	expected := endpoint + "volumes/foo"
+-	th.AssertEquals(t, expected, actual)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/util.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/util.go
+deleted file mode 100644
+index 1dda695..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/util.go
++++ /dev/null
+@@ -1,22 +0,0 @@
+-package volumes
 -
--func addImages(server *DockerServer, n int, repo bool) {
--	server.iMut.Lock()
--	defer server.iMut.Unlock()
--	if server.imgIDs == nil {
--		server.imgIDs = make(map[string]string)
--	}
--	for i := 0; i < n; i++ {
--		date := time.Now().Add(time.Duration((rand.Int() % (i + 1))) * time.Hour)
--		image := docker.Image{
--			ID:      fmt.Sprintf("%x", rand.Int()%10000),
--			Created: date,
--		}
--		server.images = append(server.images, image)
--		if repo {
--			repo := "docker/python-" + image.ID
--			server.imgIDs[repo] = image.ID
+-import (
+-	"github.com/rackspace/gophercloud"
+-)
+-
+-// WaitForStatus will continually poll the resource, checking for a particular
+-// status. It will do this for the amount of seconds defined.
+-func WaitForStatus(c *gophercloud.ServiceClient, id, status string, secs int) error {
+-	return gophercloud.WaitFor(secs, func() (bool, error) {
+-		current, err := Get(c, id).Extract()
+-		if err != nil {
+-			return false, err
 -		}
--	}
--}
 -
--func TestListImages(t *testing.T) {
--	server := DockerServer{}
--	addImages(&server, 2, true)
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	request, _ := http.NewRequest("GET", "/images/json?all=1", nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusOK {
--		t.Errorf("ListImages: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
--	}
--	expected := make([]docker.APIImages, 2)
--	for i, image := range server.images {
--		expected[i] = docker.APIImages{
--			ID:       image.ID,
--			Created:  image.Created.Unix(),
--			RepoTags: []string{"docker/python-" + image.ID},
+-		if current.Status == status {
+-			return true, nil
 -		}
--	}
--	var got []docker.APIImages
--	err := json.NewDecoder(recorder.Body).Decode(&got)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if !reflect.DeepEqual(got, expected) {
--		t.Errorf("ListImages. Want %#v. Got %#v.", expected, got)
--	}
--}
 -
--func TestRemoveImage(t *testing.T) {
--	server := DockerServer{}
--	addImages(&server, 1, false)
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	path := fmt.Sprintf("/images/%s", server.images[0].ID)
--	request, _ := http.NewRequest("DELETE", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNoContent {
--		t.Errorf("RemoveImage: wrong status. Want %d. Got %d.", http.StatusNoContent, recorder.Code)
--	}
--	if len(server.images) > 0 {
--		t.Error("RemoveImage: did not remove the image.")
--	}
+-		return false, nil
+-	})
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/util_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/util_test.go
+deleted file mode 100644
+index 24ef3b6..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes/util_test.go
++++ /dev/null
+@@ -1,38 +0,0 @@
+-package volumes
 -
--func TestRemoveImageByName(t *testing.T) {
--	server := DockerServer{}
--	addImages(&server, 1, true)
--	server.buildMuxer()
--	recorder := httptest.NewRecorder()
--	imgName := "docker/python-" + server.images[0].ID
--	path := "/images/" + imgName
--	request, _ := http.NewRequest("DELETE", path, nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusNoContent {
--		t.Errorf("RemoveImage: wrong status. Want %d. Got %d.", http.StatusNoContent, recorder.Code)
--	}
--	if len(server.images) > 0 {
--		t.Error("RemoveImage: did not remove the image.")
--	}
--	_, ok := server.imgIDs[imgName]
--	if ok {
--		t.Error("RemoveImage: did not remove image tag name.")
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
+-	"time"
+-
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
+-
+-func TestWaitForStatus(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/volumes/1234", func(w http.ResponseWriter, r *http.Request) {
+-		time.Sleep(3 * time.Second)
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-		fmt.Fprintf(w, `
+-		{
+-			"volume": {
+-				"display_name": "vol-001",
+-				"id": "1234",
+-				"status":"available"
+-			}
+-		}`)
+-	})
+-
+-	err := WaitForStatus(client.ServiceClient(), "1234", "available", 0)
+-	if err == nil {
+-		t.Errorf("Expected error: 'Time Out in WaitFor'")
 -	}
+-
+-	err = WaitForStatus(client.ServiceClient(), "1234", "available", 6)
+-	th.CheckNoErr(t, err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/doc.go
+deleted file mode 100644
+index 793084f..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/doc.go
++++ /dev/null
+@@ -1,9 +0,0 @@
+-// Package volumetypes provides information and interaction with volume types
+-// in the OpenStack Block Storage service. A volume type indicates the type of
+-// a block storage volume, such as SATA, SCSCI, SSD, etc. These can be
+-// customized or defined by the OpenStack admin.
+-//
+-// You can also define extra_specs associated with your volume types. For
+-// instance, you could have a VolumeType=SATA, with extra_specs (RPM=10000,
+-// RAID-Level=5) . Extra_specs are defined and customized by the admin.
+-package volumetypes
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/fixtures.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/fixtures.go
+deleted file mode 100644
+index e3326ea..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/fixtures.go
++++ /dev/null
+@@ -1,60 +0,0 @@
+-package volumetypes
 -
--func TestPrepareFailure(t *testing.T) {
--	server := DockerServer{failures: make(map[string]string)}
--	server.buildMuxer()
--	errorID := "my_error"
--	server.PrepareFailure(errorID, "containers/json")
--	recorder := httptest.NewRecorder()
--	request, _ := http.NewRequest("GET", "/containers/json?all=1", nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusBadRequest {
--		t.Errorf("PrepareFailure: wrong status. Want %d. Got %d.", http.StatusBadRequest, recorder.Code)
--	}
--	if recorder.Body.String() != errorID+"\n" {
--		t.Errorf("PrepareFailure: wrong message. Want %s. Got %s.", errorID, recorder.Body.String())
--	}
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
+-
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
+-
+-func MockListResponse(t *testing.T) {
+-	th.Mux.HandleFunc("/types", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-    {
+-      "volume_types": [
+-        {
+-          "id": "289da7f8-6440-407c-9fb4-7db01ec49164",
+-          "name": "vol-type-001",
+-          "extra_specs": {
+-            "capabilities": "gpu"
+-            }
+-        },
+-        {
+-          "id": "96c3bda7-c82a-4f50-be73-ca7621794835",
+-          "name": "vol-type-002",
+-          "extra_specs": {}
+-        }
+-      ]
+-    }
+-    `)
+-	})
 -}
 -
--func TestRemoveFailure(t *testing.T) {
--	server := DockerServer{failures: make(map[string]string)}
--	server.buildMuxer()
--	errorID := "my_error"
--	server.PrepareFailure(errorID, "containers/json")
--	recorder := httptest.NewRecorder()
--	request, _ := http.NewRequest("GET", "/containers/json?all=1", nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusBadRequest {
--		t.Errorf("PrepareFailure: wrong status. Want %d. Got %d.", http.StatusBadRequest, recorder.Code)
--	}
--	server.ResetFailure(errorID)
--	recorder = httptest.NewRecorder()
--	request, _ = http.NewRequest("GET", "/containers/json?all=1", nil)
--	server.ServeHTTP(recorder, request)
--	if recorder.Code != http.StatusOK {
--		t.Errorf("RemoveFailure: wrong status. Want %d. Got %d.", http.StatusOK, recorder.Code)
--	}
+-func MockGetResponse(t *testing.T) {
+-	th.Mux.HandleFunc("/types/d32019d3-bc6e-4319-9c1d-6722fc136a22", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-		fmt.Fprintf(w, `
+-{
+-    "volume_type": {
+-        "name": "vol-type-001",
+-        "id": "d32019d3-bc6e-4319-9c1d-6722fc136a22",
+-    "extra_specs": {
+-      "serverNumber": "2"
+-    }
+-    }
+-}
+-      `)
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/requests.go
+deleted file mode 100644
+index 87e20f6..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/requests.go
++++ /dev/null
+@@ -1,87 +0,0 @@
+-package volumetypes
+-
+-import (
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
+-
+-// CreateOptsBuilder allows extensions to add additional parameters to the
+-// Create request.
+-type CreateOptsBuilder interface {
+-	ToVolumeTypeCreateMap() (map[string]interface{}, error)
 -}
 -
--func TestMutateContainer(t *testing.T) {
--	server := DockerServer{failures: make(map[string]string)}
--	server.buildMuxer()
--	server.containers = append(server.containers, &docker.Container{ID: "id123"})
--	state := docker.State{Running: false, ExitCode: 1}
--	err := server.MutateContainer("id123", state)
--	if err != nil {
--		t.Fatal(err)
--	}
--	if !reflect.DeepEqual(server.containers[0].State, state) {
--		t.Errorf("Wrong state after mutation.\nWant %#v.\nGot %#v.",
--			state, server.containers[0].State)
--	}
+-// CreateOpts are options for creating a volume type.
+-type CreateOpts struct {
+-	// OPTIONAL. See VolumeType.
+-	ExtraSpecs map[string]interface{}
+-	// OPTIONAL. See VolumeType.
+-	Name string
 -}
 -
--func TestMutateContainerNotFound(t *testing.T) {
--	server := DockerServer{failures: make(map[string]string)}
--	server.buildMuxer()
--	state := docker.State{Running: false, ExitCode: 1}
--	err := server.MutateContainer("id123", state)
--	if err == nil {
--		t.Error("Unexpected <nil> error")
+-// ToVolumeTypeCreateMap casts a CreateOpts struct to a map.
+-func (opts CreateOpts) ToVolumeTypeCreateMap() (map[string]interface{}, error) {
+-	vt := make(map[string]interface{})
+-
+-	if opts.ExtraSpecs != nil {
+-		vt["extra_specs"] = opts.ExtraSpecs
 -	}
--	if err.Error() != "container not found" {
--		t.Errorf("wrong error message. Want %q. Got %q.", "container not found", err)
+-	if opts.Name != "" {
+-		vt["name"] = opts.Name
 -	}
+-
+-	return map[string]interface{}{"volume_type": vt}, nil
 -}
 -
--func TestBuildImageWithContentTypeTar(t *testing.T) {
--	server := DockerServer{imgIDs: make(map[string]string)}
--	imageName := "teste"
--	recorder := httptest.NewRecorder()
--	tarFile, err := os.Open("data/dockerfile.tar")
+-// Create will create a new volume. To extract the created volume type object,
+-// call the Extract method on the CreateResult.
+-func Create(client *gophercloud.ServiceClient, opts CreateOptsBuilder) CreateResult {
+-	var res CreateResult
+-
+-	reqBody, err := opts.ToVolumeTypeCreateMap()
 -	if err != nil {
--		t.Fatal(err)
--	}
--	defer tarFile.Close()
--	request, _ := http.NewRequest("POST", "/build?t=teste", tarFile)
--	request.Header.Add("Content-Type", "application/tar")
--	server.buildImage(recorder, request)
--	if recorder.Body.String() == "miss Dockerfile" {
--		t.Errorf("BuildImage: miss Dockerfile")
--		return
--	}
--	if _, ok := server.imgIDs[imageName]; ok == false {
--		t.Errorf("BuildImage: image %s not builded", imageName)
+-		res.Err = err
+-		return res
 -	}
+-
+-	_, res.Err = perigee.Request("POST", createURL(client), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{200, 201},
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-	})
+-	return res
 -}
 -
--func TestBuildImageWithRemoteDockerfile(t *testing.T) {
--	server := DockerServer{imgIDs: make(map[string]string)}
--	imageName := "teste"
--	recorder := httptest.NewRecorder()
--	request, _ := http.NewRequest("POST", "/build?t=teste&remote=http://localhost/Dockerfile", nil)
--	server.buildImage(recorder, request)
--	if _, ok := server.imgIDs[imageName]; ok == false {
--		t.Errorf("BuildImage: image %s not builded", imageName)
--	}
+-// Delete will delete the volume type with the provided ID.
+-func Delete(client *gophercloud.ServiceClient, id string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", deleteURL(client, id), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{202},
+-	})
+-	return res
 -}
 -
--func TestPing(t *testing.T) {
--	server := DockerServer{}
--	recorder := httptest.NewRecorder()
--	request, _ := http.NewRequest("GET", "/_ping", nil)
--	server.pingDocker(recorder, request)
--	if recorder.Body.String() != "" {
--		t.Errorf("Ping: Unexpected body: %s", recorder.Body.String())
--	}
--	if recorder.Code != http.StatusOK {
--		t.Errorf("Ping: Expected code %d, got: %d", http.StatusOK, recorder.Code)
--	}
+-// Get will retrieve the volume type with the provided ID. To extract the volume
+-// type from the result, call the Extract method on the GetResult.
+-func Get(client *gophercloud.ServiceClient, id string) GetResult {
+-	var res GetResult
+-	_, err := perigee.Request("GET", getURL(client, id), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{200},
+-		Results:     &res.Body,
+-	})
+-	res.Err = err
+-	return res
 -}
 -
--func TestDefaultHandler(t *testing.T) {
--	server, err := NewServer("127.0.0.1:0", nil, nil)
--	if err != nil {
--		t.Fatal(err)
--	}
--	defer server.listener.Close()
--	if server.mux != server.DefaultHandler() {
--		t.Fatalf("DefaultHandler: Expected to return server.mux, got: %#v", server.DefaultHandler())
+-// List returns all volume types.
+-func List(client *gophercloud.ServiceClient) pagination.Pager {
+-	createPage := func(r pagination.PageResult) pagination.Page {
+-		return ListResult{pagination.SinglePageBase(r)}
 -	}
+-
+-	return pagination.NewPager(client, listURL(client), createPage)
 -}
-diff --git a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/writer.go b/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/writer.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/requests_test.go
 deleted file mode 100644
-index 42752b0..0000000
---- a/Godeps/_workspace/src/github.com/fsouza/go-dockerclient/testing/writer.go
+index 8d40bfe..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/requests_test.go
 +++ /dev/null
-@@ -1,43 +0,0 @@
--// Copyright 2014 go-dockerclient 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 testing
+@@ -1,118 +0,0 @@
+-package volumetypes
 -
 -import (
--	"encoding/binary"
--	"errors"
--	"io"
+-	"fmt"
+-	"net/http"
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
 -)
 -
--type stdType [8]byte
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--var (
--	stdin  stdType = stdType{0: 0}
--	stdout stdType = stdType{0: 1}
--	stderr stdType = stdType{0: 2}
+-	MockListResponse(t)
+-
+-	count := 0
+-
+-	List(client.ServiceClient()).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractVolumeTypes(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract volume types: %v", err)
+-			return false, err
+-		}
+-
+-		expected := []VolumeType{
+-			VolumeType{
+-				ID:   "289da7f8-6440-407c-9fb4-7db01ec49164",
+-				Name: "vol-type-001",
+-				ExtraSpecs: map[string]interface{}{
+-					"capabilities": "gpu",
+-				},
+-			},
+-			VolumeType{
+-				ID:         "96c3bda7-c82a-4f50-be73-ca7621794835",
+-				Name:       "vol-type-002",
+-				ExtraSpecs: map[string]interface{}{},
+-			},
+-		}
+-
+-		th.CheckDeepEquals(t, expected, actual)
+-
+-		return true, nil
+-	})
+-
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
+-	}
+-}
+-
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	MockGetResponse(t)
+-
+-	vt, err := Get(client.ServiceClient(), "d32019d3-bc6e-4319-9c1d-6722fc136a22").Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertDeepEquals(t, vt.ExtraSpecs, map[string]interface{}{"serverNumber": "2"})
+-	th.AssertEquals(t, vt.Name, "vol-type-001")
+-	th.AssertEquals(t, vt.ID, "d32019d3-bc6e-4319-9c1d-6722fc136a22")
+-}
+-
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/types", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "volume_type": {
+-        "name": "vol-type-001"
+-    }
+-}
+-			`)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "volume_type": {
+-        "name": "vol-type-001",
+-        "id": "d32019d3-bc6e-4319-9c1d-6722fc136a22"
+-    }
+-}
+-		`)
+-	})
+-
+-	options := &CreateOpts{Name: "vol-type-001"}
+-	n, err := Create(client.ServiceClient(), options).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, n.Name, "vol-type-001")
+-	th.AssertEquals(t, n.ID, "d32019d3-bc6e-4319-9c1d-6722fc136a22")
+-}
+-
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/types/d32019d3-bc6e-4319-9c1d-6722fc136a22", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-		w.WriteHeader(http.StatusAccepted)
+-	})
+-
+-	err := Delete(client.ServiceClient(), "d32019d3-bc6e-4319-9c1d-6722fc136a22").ExtractErr()
+-	th.AssertNoErr(t, err)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/results.go
+deleted file mode 100644
+index c049a04..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/results.go
++++ /dev/null
+@@ -1,72 +0,0 @@
+-package volumetypes
+-
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
 -)
 -
--type stdWriter struct {
--	io.Writer
--	prefix  stdType
--	sizeBuf []byte
+-// VolumeType contains all information associated with an OpenStack Volume Type.
+-type VolumeType struct {
+-	ExtraSpecs map[string]interface{} `json:"extra_specs" mapstructure:"extra_specs"` // user-defined metadata
+-	ID         string                 `json:"id" mapstructure:"id"`                   // unique identifier
+-	Name       string                 `json:"name" mapstructure:"name"`               // display name
 -}
 -
--func (w *stdWriter) Write(buf []byte) (n int, err error) {
--	if w == nil || w.Writer == nil {
--		return 0, errors.New("Writer not instanciated")
+-// CreateResult contains the response body and error from a Create request.
+-type CreateResult struct {
+-	commonResult
+-}
+-
+-// GetResult contains the response body and error from a Get request.
+-type GetResult struct {
+-	commonResult
+-}
+-
+-// DeleteResult contains the response error from a Delete request.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
+-}
+-
+-// ListResult is a pagination.Pager that is returned from a call to the List function.
+-type ListResult struct {
+-	pagination.SinglePageBase
+-}
+-
+-// IsEmpty returns true if a ListResult contains no Volume Types.
+-func (r ListResult) IsEmpty() (bool, error) {
+-	volumeTypes, err := ExtractVolumeTypes(r)
+-	if err != nil {
+-		return true, err
 -	}
--	binary.BigEndian.PutUint32(w.prefix[4:], uint32(len(buf)))
--	buf = append(w.prefix[:], buf...)
+-	return len(volumeTypes) == 0, nil
+-}
 -
--	n, err = w.Writer.Write(buf)
--	return n - 8, err
+-// ExtractVolumeTypes extracts and returns Volume Types.
+-func ExtractVolumeTypes(page pagination.Page) ([]VolumeType, error) {
+-	var response struct {
+-		VolumeTypes []VolumeType `mapstructure:"volume_types"`
+-	}
+-
+-	err := mapstructure.Decode(page.(ListResult).Body, &response)
+-	return response.VolumeTypes, err
 -}
 -
--func newStdWriter(w io.Writer, t stdType) *stdWriter {
--	if len(t) != 8 {
--		return nil
+-type commonResult struct {
+-	gophercloud.Result
+-}
+-
+-// Extract will get the Volume Type object out of the commonResult object.
+-func (r commonResult) Extract() (*VolumeType, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
 -	}
--	return &stdWriter{Writer: w, prefix: t, sizeBuf: make([]byte, 4)}
+-
+-	var res struct {
+-		VolumeType *VolumeType `json:"volume_type" mapstructure:"volume_type"`
+-	}
+-
+-	err := mapstructure.Decode(r.Body, &res)
+-
+-	return res.VolumeType, err
 -}
-diff --git a/Godeps/_workspace/src/github.com/ghodss/yaml/.gitignore b/Godeps/_workspace/src/github.com/ghodss/yaml/.gitignore
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/urls.go
 deleted file mode 100644
-index e256a31..0000000
---- a/Godeps/_workspace/src/github.com/ghodss/yaml/.gitignore
+index cf8367b..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/urls.go
 +++ /dev/null
-@@ -1,20 +0,0 @@
--# OSX leaves these everywhere on SMB shares
--._*
+@@ -1,19 +0,0 @@
+-package volumetypes
 -
--# Eclipse files
--.classpath
--.project
--.settings/**
+-import "github.com/rackspace/gophercloud"
 -
--# Emacs save files
--*~
+-func listURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL("types")
+-}
 -
--# Vim-related files
--[._]*.s[a-w][a-z]
--[._]s[a-w][a-z]
--*.un~
--Session.vim
--.netrwhist
+-func createURL(c *gophercloud.ServiceClient) string {
+-	return listURL(c)
+-}
 -
--# Go test binaries
--*.test
-diff --git a/Godeps/_workspace/src/github.com/ghodss/yaml/LICENSE b/Godeps/_workspace/src/github.com/ghodss/yaml/LICENSE
+-func getURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL("types", id)
+-}
+-
+-func deleteURL(c *gophercloud.ServiceClient, id string) string {
+-	return getURL(c, id)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/urls_test.go
 deleted file mode 100644
-index 7805d36..0000000
---- a/Godeps/_workspace/src/github.com/ghodss/yaml/LICENSE
+index 44016e2..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes/urls_test.go
 +++ /dev/null
-@@ -1,50 +0,0 @@
--The MIT License (MIT)
--
--Copyright (c) 2014 Sam Ghods
+@@ -1,38 +0,0 @@
+-package volumetypes
 -
--Permission is hereby granted, free of charge, to any person obtaining a copy
--of this software and associated documentation files (the "Software"), to deal
--in the Software without restriction, including without limitation the rights
--to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
--copies of the Software, and to permit persons to whom the Software is
--furnished to do so, subject to the following conditions:
+-import (
+-	"testing"
 -
--The above copyright notice and this permission notice shall be included in all
--copies or substantial portions of the Software.
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
--IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
--FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
--AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
--LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
--OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
--SOFTWARE.
+-const endpoint = "http://localhost:57909"
 -
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint}
+-}
 -
--Copyright (c) 2012 The Go Authors. All rights reserved.
+-func TestListURL(t *testing.T) {
+-	actual := listURL(endpointClient())
+-	expected := endpoint + "types"
+-	th.AssertEquals(t, expected, actual)
+-}
 -
--Redistribution and use in source and binary forms, with or without
--modification, are permitted provided that the following conditions are
--met:
+-func TestCreateURL(t *testing.T) {
+-	actual := createURL(endpointClient())
+-	expected := endpoint + "types"
+-	th.AssertEquals(t, expected, actual)
+-}
 -
--   * Redistributions of source code must retain the above copyright
--notice, this list of conditions and the following disclaimer.
--   * Redistributions in binary form must reproduce the above
--copyright notice, this list of conditions and the following disclaimer
--in the documentation and/or other materials provided with the
--distribution.
--   * Neither the name of Google Inc. nor the names of its
--contributors may be used to endorse or promote products derived from
--this software without specific prior written permission.
+-func TestGetURL(t *testing.T) {
+-	actual := getURL(endpointClient(), "foo")
+-	expected := endpoint + "types/foo"
+-	th.AssertEquals(t, expected, actual)
+-}
 -
--THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
--"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
--LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
--A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
--OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
--SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
--LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
--DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
--THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
--(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
--OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
-diff --git a/Godeps/_workspace/src/github.com/ghodss/yaml/README.md b/Godeps/_workspace/src/github.com/ghodss/yaml/README.md
+-func TestDeleteURL(t *testing.T) {
+-	actual := deleteURL(endpointClient(), "foo")
+-	expected := endpoint + "types/foo"
+-	th.AssertEquals(t, expected, actual)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/client.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/client.go
 deleted file mode 100644
-index 2d60309..0000000
---- a/Godeps/_workspace/src/github.com/ghodss/yaml/README.md
+index 99b3d46..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/client.go
 +++ /dev/null
-@@ -1,114 +0,0 @@
--# YAML marshaling and unmarshaling support for Go
+@@ -1,205 +0,0 @@
+-package openstack
 -
--## Introduction
+-import (
+-	"fmt"
+-	"net/url"
 -
--A wrapper around [go-yaml](https://github.com/go-yaml/yaml) designed to enable a better way of handling YAML when marshaling to and from structs. 
+-	"github.com/rackspace/gophercloud"
+-	tokens2 "github.com/rackspace/gophercloud/openstack/identity/v2/tokens"
+-	tokens3 "github.com/rackspace/gophercloud/openstack/identity/v3/tokens"
+-	"github.com/rackspace/gophercloud/openstack/utils"
+-)
 -
--In short, this library first converts YAML to JSON using go-yaml and then uses `json.Marshal` and `json.Unmarshal` to convert to or from the struct. This means that it effectively reuses the JSON struct tags as well as the custom JSON methods `MarshalJSON` and `UnmarshalJSON` unlike go-yaml. For a detailed overview of the rationale behind this method, [see this blog post](http://ghodss.com/2014/the-right-way-to-handle-yaml-in-golang/).
+-const (
+-	v20 = "v2.0"
+-	v30 = "v3.0"
+-)
 -
--## Compatibility
+-// NewClient prepares an unauthenticated ProviderClient instance.
+-// Most users will probably prefer using the AuthenticatedClient function instead.
+-// This is useful if you wish to explicitly control the version of the identity service that's used for authentication explicitly,
+-// for example.
+-func NewClient(endpoint string) (*gophercloud.ProviderClient, error) {
+-	u, err := url.Parse(endpoint)
+-	if err != nil {
+-		return nil, err
+-	}
+-	hadPath := u.Path != ""
+-	u.Path, u.RawQuery, u.Fragment = "", "", ""
+-	base := u.String()
 -
--This package uses [go-yaml v2](https://github.com/go-yaml/yaml) and therefore supports [everything go-yaml supports](https://github.com/go-yaml/yaml#compatibility).
+-	endpoint = gophercloud.NormalizeURL(endpoint)
+-	base = gophercloud.NormalizeURL(base)
 -
--## Caveats
+-	if hadPath {
+-		return &gophercloud.ProviderClient{
+-			IdentityBase:     base,
+-			IdentityEndpoint: endpoint,
+-		}, nil
+-	}
 -
--**Caveat #1:** When using `yaml.Marshal` and `yaml.Unmarshal`, binary data should NOT be preceded with the `!!binary` YAML tag. If you do, go-yaml will convert the binary data from base64 to native binary data, which is not compatible with JSON. You can still use binary in your YAML files though - just store them without the `!!binary` tag and decode the base64 in your code (e.g. in the custom JSON methods `MarshalJSON` and `UnmarshalJSON`). This also has the benefit that your YAML and your JSON binary data will be decoded exactly the same way. As an example:
+-	return &gophercloud.ProviderClient{
+-		IdentityBase:     base,
+-		IdentityEndpoint: "",
+-	}, nil
+-}
 -
--```
--BAD:
--	exampleKey: !!binary gIGC
+-// AuthenticatedClient logs in to an OpenStack cloud found at the identity endpoint specified by options, acquires a token, and
+-// returns a Client instance that's ready to operate.
+-// It first queries the root identity endpoint to determine which versions of the identity service are supported, then chooses
+-// the most recent identity service available to proceed.
+-func AuthenticatedClient(options gophercloud.AuthOptions) (*gophercloud.ProviderClient, error) {
+-	client, err := NewClient(options.IdentityEndpoint)
+-	if err != nil {
+-		return nil, err
+-	}
 -
--GOOD:
--	exampleKey: gIGC
--... and decode the base64 data in your code.
--```
+-	err = Authenticate(client, options)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return client, nil
+-}
 -
--**Caveat #2:** When using `YAMLToJSON` directly, maps with keys that are maps will result in an error since this is not supported by JSON. This error will occur in `Unmarshal` as well since you can't unmarshal map keys anyways since struct fields can't be keys.
+-// Authenticate or re-authenticate against the most recent identity service supported at the provided endpoint.
+-func Authenticate(client *gophercloud.ProviderClient, options gophercloud.AuthOptions) error {
+-	versions := []*utils.Version{
+-		&utils.Version{ID: v20, Priority: 20, Suffix: "/v2.0/"},
+-		&utils.Version{ID: v30, Priority: 30, Suffix: "/v3/"},
+-	}
 -
--## Installation and usage
+-	chosen, endpoint, err := utils.ChooseVersion(client.IdentityBase, client.IdentityEndpoint, versions)
+-	if err != nil {
+-		return err
+-	}
 -
--To install, run:
+-	switch chosen.ID {
+-	case v20:
+-		return v2auth(client, endpoint, options)
+-	case v30:
+-		return v3auth(client, endpoint, options)
+-	default:
+-		// The switch statement must be out of date from the versions list.
+-		return fmt.Errorf("Unrecognized identity version: %s", chosen.ID)
+-	}
+-}
 -
--```
--$ go get github.com/ghodss/yaml
--```
+-// AuthenticateV2 explicitly authenticates against the identity v2 endpoint.
+-func AuthenticateV2(client *gophercloud.ProviderClient, options gophercloud.AuthOptions) error {
+-	return v2auth(client, "", options)
+-}
 -
--And import using:
+-func v2auth(client *gophercloud.ProviderClient, endpoint string, options gophercloud.AuthOptions) error {
+-	v2Client := NewIdentityV2(client)
+-	if endpoint != "" {
+-		v2Client.Endpoint = endpoint
+-	}
 -
--```
--import "github.com/ghodss/yaml"
--```
+-	result := tokens2.Create(v2Client, tokens2.AuthOptions{AuthOptions: options})
 -
--Usage is very similar to the JSON library:
+-	token, err := result.ExtractToken()
+-	if err != nil {
+-		return err
+-	}
 -
--```go
--import (
--	"fmt"
+-	catalog, err := result.ExtractServiceCatalog()
+-	if err != nil {
+-		return err
+-	}
 -
--	"github.com/ghodss/yaml"
--)
+-	client.TokenID = token.ID
+-	client.EndpointLocator = func(opts gophercloud.EndpointOpts) (string, error) {
+-		return V2EndpointURL(catalog, opts)
+-	}
 -
--type Person struct {
--	Name string `json:"name"`  // Affects YAML field names too.
--	Age int `json:"name"`
+-	return nil
 -}
 -
--func main() {
--	// Marshal a Person struct to YAML.
--	p := Person{"John", 30}
--	y, err := yaml.Marshal(p)
--	if err != nil {
--		fmt.Printf("err: %v\n", err)
--		return
+-// AuthenticateV3 explicitly authenticates against the identity v3 service.
+-func AuthenticateV3(client *gophercloud.ProviderClient, options gophercloud.AuthOptions) error {
+-	return v3auth(client, "", options)
+-}
+-
+-func v3auth(client *gophercloud.ProviderClient, endpoint string, options gophercloud.AuthOptions) error {
+-	// Override the generated service endpoint with the one returned by the version endpoint.
+-	v3Client := NewIdentityV3(client)
+-	if endpoint != "" {
+-		v3Client.Endpoint = endpoint
 -	}
--	fmt.Println(string(y))
--	/* Output:
--	name: John
--	age: 30
--	*/
 -
--	// Unmarshal the YAML back into a Person struct.
--	var p2 Person
--	err := yaml.Unmarshal(y, &p2)
+-	token, err := tokens3.Create(v3Client, options, nil).Extract()
 -	if err != nil {
--		fmt.Printf("err: %v\n", err)
--		return
+-		return err
 -	}
--	fmt.Println(p2)
--	/* Output:
--	{John 30}
--	*/
+-	client.TokenID = token.ID
+-
+-	client.EndpointLocator = func(opts gophercloud.EndpointOpts) (string, error) {
+-		return V3EndpointURL(v3Client, opts)
+-	}
+-
+-	return nil
 -}
--```
 -
--`yaml.YAMLToJSON` and `yaml.JSONToYAML` methods are also available:
+-// NewIdentityV2 creates a ServiceClient that may be used to interact with the v2 identity service.
+-func NewIdentityV2(client *gophercloud.ProviderClient) *gophercloud.ServiceClient {
+-	v2Endpoint := client.IdentityBase + "v2.0/"
 -
--```go
--import (
--	"fmt"
+-	return &gophercloud.ServiceClient{
+-		ProviderClient: client,
+-		Endpoint:       v2Endpoint,
+-	}
+-}
 -
--	"github.com/ghodss/yaml"
--)
--func main() {
--	j := []byte(`{"name": "John", "age": 30}`)
--	y, err := yaml.JSONToYAML(j)
+-// NewIdentityV3 creates a ServiceClient that may be used to access the v3 identity service.
+-func NewIdentityV3(client *gophercloud.ProviderClient) *gophercloud.ServiceClient {
+-	v3Endpoint := client.IdentityBase + "v3/"
+-
+-	return &gophercloud.ServiceClient{
+-		ProviderClient: client,
+-		Endpoint:       v3Endpoint,
+-	}
+-}
+-
+-// NewObjectStorageV1 creates a ServiceClient that may be used with the v1 object storage package.
+-func NewObjectStorageV1(client *gophercloud.ProviderClient, eo gophercloud.EndpointOpts) (*gophercloud.ServiceClient, error) {
+-	eo.ApplyDefaults("object-store")
+-	url, err := client.EndpointLocator(eo)
 -	if err != nil {
--		fmt.Printf("err: %v\n", err)
--		return
+-		return nil, err
 -	}
--	fmt.Println(string(y))
--	/* Output:
--	name: John
--	age: 30
--	*/
--	j2, err := yaml.YAMLToJSON(y)
+-	return &gophercloud.ServiceClient{ProviderClient: client, Endpoint: url}, nil
+-}
+-
+-// NewComputeV2 creates a ServiceClient that may be used with the v2 compute package.
+-func NewComputeV2(client *gophercloud.ProviderClient, eo gophercloud.EndpointOpts) (*gophercloud.ServiceClient, error) {
+-	eo.ApplyDefaults("compute")
+-	url, err := client.EndpointLocator(eo)
 -	if err != nil {
--		fmt.Printf("err: %v\n", err)
--		return
+-		return nil, err
 -	}
--	fmt.Println(string(j2))
--	/* Output:
--	{"age":30,"name":"John"}
--	*/
+-	return &gophercloud.ServiceClient{ProviderClient: client, Endpoint: url}, nil
 -}
--```
-diff --git a/Godeps/_workspace/src/github.com/ghodss/yaml/fields.go b/Godeps/_workspace/src/github.com/ghodss/yaml/fields.go
+-
+-// NewNetworkV2 creates a ServiceClient that may be used with the v2 network package.
+-func NewNetworkV2(client *gophercloud.ProviderClient, eo gophercloud.EndpointOpts) (*gophercloud.ServiceClient, error) {
+-	eo.ApplyDefaults("network")
+-	url, err := client.EndpointLocator(eo)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return &gophercloud.ServiceClient{
+-		ProviderClient: client,
+-		Endpoint:       url,
+-		ResourceBase:   url + "v2.0/",
+-	}, nil
+-}
+-
+-// NewBlockStorageV1 creates a ServiceClient that may be used to access the v1 block storage service.
+-func NewBlockStorageV1(client *gophercloud.ProviderClient, eo gophercloud.EndpointOpts) (*gophercloud.ServiceClient, error) {
+-	eo.ApplyDefaults("volume")
+-	url, err := client.EndpointLocator(eo)
+-	if err != nil {
+-		return nil, err
+-	}
+-	return &gophercloud.ServiceClient{ProviderClient: client, Endpoint: url}, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/client_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/client_test.go
 deleted file mode 100644
-index 0bd3c2b..0000000
---- a/Godeps/_workspace/src/github.com/ghodss/yaml/fields.go
+index 257260c..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/client_test.go
 +++ /dev/null
-@@ -1,497 +0,0 @@
--// Copyright 2013 The Go 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 yaml
+@@ -1,161 +0,0 @@
+-package openstack
 -
 -import (
--	"bytes"
--	"encoding"
--	"encoding/json"
--	"reflect"
--	"sort"
--	"strings"
--	"sync"
--	"unicode"
--	"unicode/utf8"
+-	"fmt"
+-	"net/http"
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--// indirect walks down v allocating pointers as needed,
--// until it gets to a non-pointer.
--// if it encounters an Unmarshaler, indirect stops and returns that.
--// if decodingNull is true, indirect stops at the last pointer so it can be set to nil.
--func indirect(v reflect.Value, decodingNull bool) (json.Unmarshaler, encoding.TextUnmarshaler, reflect.Value) {
--	// If v is a named type and is addressable,
--	// start with its address, so that if the type has pointer methods,
--	// we find them.
--	if v.Kind() != reflect.Ptr && v.Type().Name() != "" && v.CanAddr() {
--		v = v.Addr()
--	}
--	for {
--		// Load value from interface, but only if the result will be
--		// usefully addressable.
--		if v.Kind() == reflect.Interface && !v.IsNil() {
--			e := v.Elem()
--			if e.Kind() == reflect.Ptr && !e.IsNil() && (!decodingNull || e.Elem().Kind() == reflect.Ptr) {
--				v = e
--				continue
+-func TestAuthenticatedClientV3(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	const ID = "0123456789"
+-
+-	th.Mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
+-		fmt.Fprintf(w, `
+-			{
+-				"versions": {
+-					"values": [
+-						{
+-							"status": "stable",
+-							"id": "v3.0",
+-							"links": [
+-								{ "href": "%s", "rel": "self" }
+-							]
+-						},
+-						{
+-							"status": "stable",
+-							"id": "v2.0",
+-							"links": [
+-								{ "href": "%s", "rel": "self" }
+-							]
+-						}
+-					]
+-				}
 -			}
--		}
+-		`, th.Endpoint()+"v3/", th.Endpoint()+"v2.0/")
+-	})
 -
--		if v.Kind() != reflect.Ptr {
--			break
--		}
+-	th.Mux.HandleFunc("/v3/auth/tokens", func(w http.ResponseWriter, r *http.Request) {
+-		w.Header().Add("X-Subject-Token", ID)
 -
--		if v.Elem().Kind() != reflect.Ptr && decodingNull && v.CanSet() {
--			break
--		}
--		if v.IsNil() {
--			v.Set(reflect.New(v.Type().Elem()))
--		}
--		if v.Type().NumMethod() > 0 {
--			if u, ok := v.Interface().(json.Unmarshaler); ok {
--				return u, nil, reflect.Value{}
+-		w.WriteHeader(http.StatusCreated)
+-		fmt.Fprintf(w, `{ "token": { "expires_at": "2013-02-02T18:30:59.000000Z" } }`)
+-	})
+-
+-	options := gophercloud.AuthOptions{
+-		UserID:           "me",
+-		Password:         "secret",
+-		IdentityEndpoint: th.Endpoint(),
+-	}
+-	client, err := AuthenticatedClient(options)
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, ID, client.TokenID)
+-}
+-
+-func TestAuthenticatedClientV2(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
+-		fmt.Fprintf(w, `
+-			{
+-				"versions": {
+-					"values": [
+-						{
+-							"status": "experimental",
+-							"id": "v3.0",
+-							"links": [
+-								{ "href": "%s", "rel": "self" }
+-							]
+-						},
+-						{
+-							"status": "stable",
+-							"id": "v2.0",
+-							"links": [
+-								{ "href": "%s", "rel": "self" }
+-							]
+-						}
+-					]
+-				}
 -			}
--			if u, ok := v.Interface().(encoding.TextUnmarshaler); ok {
--				return nil, u, reflect.Value{}
+-		`, th.Endpoint()+"v3/", th.Endpoint()+"v2.0/")
+-	})
+-
+-	th.Mux.HandleFunc("/v2.0/tokens", func(w http.ResponseWriter, r *http.Request) {
+-		fmt.Fprintf(w, `
+-			{
+-				"access": {
+-					"token": {
+-						"id": "01234567890",
+-						"expires": "2014-10-01T10:00:00.000000Z"
+-					},
+-					"serviceCatalog": [
+-						{
+-							"name": "Cloud Servers",
+-							"type": "compute",
+-							"endpoints": [
+-								{
+-									"tenantId": "t1000",
+-									"publicURL": "https://compute.north.host.com/v1/t1000",
+-									"internalURL": "https://compute.north.internal/v1/t1000",
+-									"region": "North",
+-									"versionId": "1",
+-									"versionInfo": "https://compute.north.host.com/v1/",
+-									"versionList": "https://compute.north.host.com/"
+-								},
+-								{
+-									"tenantId": "t1000",
+-									"publicURL": "https://compute.north.host.com/v1.1/t1000",
+-									"internalURL": "https://compute.north.internal/v1.1/t1000",
+-									"region": "North",
+-									"versionId": "1.1",
+-									"versionInfo": "https://compute.north.host.com/v1.1/",
+-									"versionList": "https://compute.north.host.com/"
+-								}
+-							],
+-							"endpoints_links": []
+-						},
+-						{
+-							"name": "Cloud Files",
+-							"type": "object-store",
+-							"endpoints": [
+-								{
+-									"tenantId": "t1000",
+-									"publicURL": "https://storage.north.host.com/v1/t1000",
+-									"internalURL": "https://storage.north.internal/v1/t1000",
+-									"region": "North",
+-									"versionId": "1",
+-									"versionInfo": "https://storage.north.host.com/v1/",
+-									"versionList": "https://storage.north.host.com/"
+-								},
+-								{
+-									"tenantId": "t1000",
+-									"publicURL": "https://storage.south.host.com/v1/t1000",
+-									"internalURL": "https://storage.south.internal/v1/t1000",
+-									"region": "South",
+-									"versionId": "1",
+-									"versionInfo": "https://storage.south.host.com/v1/",
+-									"versionList": "https://storage.south.host.com/"
+-								}
+-							]
+-						}
+-					]
+-				}
 -			}
--		}
--		v = v.Elem()
+-		`)
+-	})
+-
+-	options := gophercloud.AuthOptions{
+-		Username:         "me",
+-		Password:         "secret",
+-		IdentityEndpoint: th.Endpoint(),
 -	}
--	return nil, nil, v
+-	client, err := AuthenticatedClient(options)
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, "01234567890", client.TokenID)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/README.md b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/README.md
+deleted file mode 100644
+index 7b55795..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/README.md
++++ /dev/null
+@@ -1,3 +0,0 @@
+-# Common Resources
 -
--// A field represents a single field found in a struct.
--type field struct {
--	name      string
--	nameBytes []byte                 // []byte(name)
--	equalFold func(s, t []byte) bool // bytes.EqualFold or equivalent
+-This directory is for resources that are shared by multiple services.
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/doc.go
+deleted file mode 100644
+index 4a168f4..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/doc.go
++++ /dev/null
+@@ -1,15 +0,0 @@
+-// Package extensions provides information and interaction with the different extensions available
+-// for an OpenStack service.
+-//
+-// The purpose of OpenStack API extensions is to:
+-//
+-// - Introduce new features in the API without requiring a version change.
+-// - Introduce vendor-specific niche functionality.
+-// - Act as a proving ground for experimental functionalities that might be included in a future
+-//   version of the API.
+-//
+-// Extensions usually have tags that prevent conflicts with other extensions that define attributes
+-// or resources with the same names, and with core resources and attributes.
+-// Because an extension might not be supported by all plug-ins, its availability varies with deployments
+-// and the specific plug-in.
+-package extensions
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/errors.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/errors.go
+deleted file mode 100644
+index aeec0fa..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/errors.go
++++ /dev/null
+@@ -1 +0,0 @@
+-package extensions
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/fixtures.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/fixtures.go
+deleted file mode 100644
+index 0ed7de9..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/fixtures.go
++++ /dev/null
+@@ -1,91 +0,0 @@
+-// +build fixtures
 -
--	tag       bool
--	index     []int
--	typ       reflect.Type
--	omitEmpty bool
--	quoted    bool
+-package extensions
+-
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
+-
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
+-
+-// ListOutput provides a single page of Extension results.
+-const ListOutput = `
+-{
+-	"extensions": [
+-		{
+-			"updated": "2013-01-20T00:00:00-00:00",
+-			"name": "Neutron Service Type Management",
+-			"links": [],
+-			"namespace": "http://docs.openstack.org/ext/neutron/service-type/api/v1.0",
+-			"alias": "service-type",
+-			"description": "API for retrieving service providers for Neutron advanced services"
+-		}
+-	]
+-}`
+-
+-// GetOutput provides a single Extension result.
+-const GetOutput = `
+-{
+-	"extension": {
+-		"updated": "2013-02-03T10:00:00-00:00",
+-		"name": "agent",
+-		"links": [],
+-		"namespace": "http://docs.openstack.org/ext/agent/api/v2.0",
+-		"alias": "agent",
+-		"description": "The agent management extension."
+-	}
 -}
+-`
 -
--func fillField(f field) field {
--	f.nameBytes = []byte(f.name)
--	f.equalFold = foldFunc(f.nameBytes)
--	return f
+-// ListedExtension is the Extension that should be parsed from ListOutput.
+-var ListedExtension = Extension{
+-	Updated:     "2013-01-20T00:00:00-00:00",
+-	Name:        "Neutron Service Type Management",
+-	Links:       []interface{}{},
+-	Namespace:   "http://docs.openstack.org/ext/neutron/service-type/api/v1.0",
+-	Alias:       "service-type",
+-	Description: "API for retrieving service providers for Neutron advanced services",
 -}
 -
--// byName sorts field by name, breaking ties with depth,
--// then breaking ties with "name came from json tag", then
--// breaking ties with index sequence.
--type byName []field
+-// ExpectedExtensions is a slice containing the Extension that should be parsed from ListOutput.
+-var ExpectedExtensions = []Extension{ListedExtension}
 -
--func (x byName) Len() int { return len(x) }
+-// SingleExtension is the Extension that should be parsed from GetOutput.
+-var SingleExtension = &Extension{
+-	Updated:     "2013-02-03T10:00:00-00:00",
+-	Name:        "agent",
+-	Links:       []interface{}{},
+-	Namespace:   "http://docs.openstack.org/ext/agent/api/v2.0",
+-	Alias:       "agent",
+-	Description: "The agent management extension.",
+-}
 -
--func (x byName) Swap(i, j int) { x[i], x[j] = x[j], x[i] }
+-// HandleListExtensionsSuccessfully creates an HTTP handler at `/extensions` on the test handler
+-// mux that response with a list containing a single tenant.
+-func HandleListExtensionsSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/extensions", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
 -
--func (x byName) Less(i, j int) bool {
--	if x[i].name != x[j].name {
--		return x[i].name < x[j].name
--	}
--	if len(x[i].index) != len(x[j].index) {
--		return len(x[i].index) < len(x[j].index)
--	}
--	if x[i].tag != x[j].tag {
--		return x[i].tag
--	}
--	return byIndex(x).Less(i, j)
+-		w.Header().Add("Content-Type", "application/json")
+-
+-		fmt.Fprintf(w, ListOutput)
+-	})
 -}
 -
--// byIndex sorts field by index sequence.
--type byIndex []field
+-// HandleGetExtensionSuccessfully creates an HTTP handler at `/extensions/agent` that responds with
+-// a JSON payload corresponding to SingleExtension.
+-func HandleGetExtensionSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/extensions/agent", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
 -
--func (x byIndex) Len() int { return len(x) }
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--func (x byIndex) Swap(i, j int) { x[i], x[j] = x[j], x[i] }
+-		fmt.Fprintf(w, GetOutput)
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/requests.go
+deleted file mode 100644
+index 3ca6e12..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/requests.go
++++ /dev/null
+@@ -1,26 +0,0 @@
+-package extensions
 -
--func (x byIndex) Less(i, j int) bool {
--	for k, xik := range x[i].index {
--		if k >= len(x[j].index) {
--			return false
--		}
--		if xik != x[j].index[k] {
--			return xik < x[j].index[k]
--		}
--	}
--	return len(x[i].index) < len(x[j].index)
+-import (
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
+-
+-// Get retrieves information for a specific extension using its alias.
+-func Get(c *gophercloud.ServiceClient, alias string) GetResult {
+-	var res GetResult
+-	_, res.Err = perigee.Request("GET", ExtensionURL(c, alias), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return res
 -}
 -
--// typeFields returns a list of fields that JSON should recognize for the given type.
--// The algorithm is breadth-first search over the set of structs to include - the top struct
--// and then any reachable anonymous structs.
--func typeFields(t reflect.Type) []field {
--	// Anonymous fields to explore at the current level and the next.
--	current := []field{}
--	next := []field{{typ: t}}
+-// List returns a Pager which allows you to iterate over the full collection of extensions.
+-// It does not accept query parameters.
+-func List(c *gophercloud.ServiceClient) pagination.Pager {
+-	return pagination.NewPager(c, ListExtensionURL(c), func(r pagination.PageResult) pagination.Page {
+-		return ExtensionPage{pagination.SinglePageBase(r)}
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/requests_test.go
+deleted file mode 100644
+index 6550283..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/requests_test.go
++++ /dev/null
+@@ -1,38 +0,0 @@
+-package extensions
 -
--	// Count of queued names for current level and the next.
--	count := map[reflect.Type]int{}
--	nextCount := map[reflect.Type]int{}
+-import (
+-	"testing"
 -
--	// Types already visited at an earlier level.
--	visited := map[reflect.Type]bool{}
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--	// Fields found.
--	var fields []field
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleListExtensionsSuccessfully(t)
 -
--	for len(next) > 0 {
--		current, next = next, current[:0]
--		count, nextCount = nextCount, map[reflect.Type]int{}
+-	count := 0
 -
--		for _, f := range current {
--			if visited[f.typ] {
--				continue
--			}
--			visited[f.typ] = true
+-	List(client.ServiceClient()).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractExtensions(page)
+-		th.AssertNoErr(t, err)
+-		th.AssertDeepEquals(t, ExpectedExtensions, actual)
 -
--			// Scan f.typ for fields to include.
--			for i := 0; i < f.typ.NumField(); i++ {
--				sf := f.typ.Field(i)
--				if sf.PkgPath != "" { // unexported
--					continue
--				}
--				tag := sf.Tag.Get("json")
--				if tag == "-" {
--					continue
--				}
--				name, opts := parseTag(tag)
--				if !isValidTag(name) {
--					name = ""
--				}
--				index := make([]int, len(f.index)+1)
--				copy(index, f.index)
--				index[len(f.index)] = i
+-		return true, nil
+-	})
 -
--				ft := sf.Type
--				if ft.Name() == "" && ft.Kind() == reflect.Ptr {
--					// Follow pointer.
--					ft = ft.Elem()
--				}
+-	th.CheckEquals(t, 1, count)
+-}
 -
--				// Record found field and index sequence.
--				if name != "" || !sf.Anonymous || ft.Kind() != reflect.Struct {
--					tagged := name != ""
--					if name == "" {
--						name = sf.Name
--					}
--					fields = append(fields, fillField(field{
--						name:      name,
--						tag:       tagged,
--						index:     index,
--						typ:       ft,
--						omitEmpty: opts.Contains("omitempty"),
--						quoted:    opts.Contains("string"),
--					}))
--					if count[f.typ] > 1 {
--						// If there were multiple instances, add a second,
--						// so that the annihilation code will see a duplicate.
--						// It only cares about the distinction between 1 or 2,
--						// so don't bother generating any more copies.
--						fields = append(fields, fields[len(fields)-1])
--					}
--					continue
--				}
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleGetExtensionSuccessfully(t)
 -
--				// Record new anonymous struct to explore in next round.
--				nextCount[ft]++
--				if nextCount[ft] == 1 {
--					next = append(next, fillField(field{name: ft.Name(), index: index, typ: ft}))
--				}
--			}
--		}
--	}
+-	actual, err := Get(client.ServiceClient(), "agent").Extract()
+-	th.AssertNoErr(t, err)
+-	th.CheckDeepEquals(t, SingleExtension, actual)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/results.go
+deleted file mode 100644
+index 777d083..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/results.go
++++ /dev/null
+@@ -1,65 +0,0 @@
+-package extensions
 -
--	sort.Sort(byName(fields))
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	// Delete all fields that are hidden by the Go rules for embedded fields,
--	// except that fields with JSON tags are promoted.
+-// GetResult temporarily stores the result of a Get call.
+-// Use its Extract() method to interpret it as an Extension.
+-type GetResult struct {
+-	gophercloud.Result
+-}
 -
--	// The fields are sorted in primary order of name, secondary order
--	// of field index length. Loop over names; for each name, delete
--	// hidden fields by choosing the one dominant field that survives.
--	out := fields[:0]
--	for advance, i := 0, 0; i < len(fields); i += advance {
--		// One iteration per name.
--		// Find the sequence of fields with the name of this first field.
--		fi := fields[i]
--		name := fi.name
--		for advance = 1; i+advance < len(fields); advance++ {
--			fj := fields[i+advance]
--			if fj.name != name {
--				break
--			}
--		}
--		if advance == 1 { // Only one field with this name
--			out = append(out, fi)
--			continue
--		}
--		dominant, ok := dominantField(fields[i : i+advance])
--		if ok {
--			out = append(out, dominant)
--		}
+-// Extract interprets a GetResult as an Extension.
+-func (r GetResult) Extract() (*Extension, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
 -	}
 -
--	fields = out
--	sort.Sort(byIndex(fields))
+-	var res struct {
+-		Extension *Extension `json:"extension"`
+-	}
 -
--	return fields
+-	err := mapstructure.Decode(r.Body, &res)
+-
+-	return res.Extension, err
 -}
 -
--// dominantField looks through the fields, all of which are known to
--// have the same name, to find the single field that dominates the
--// others using Go's embedding rules, modified by the presence of
--// JSON tags. If there are multiple top-level fields, the boolean
--// will be false: This condition is an error in Go and we skip all
--// the fields.
--func dominantField(fields []field) (field, bool) {
--	// The fields are sorted in increasing index-length order. The winner
--	// must therefore be one with the shortest index length. Drop all
--	// longer entries, which is easy: just truncate the slice.
--	length := len(fields[0].index)
--	tagged := -1 // Index of first tagged field.
--	for i, f := range fields {
--		if len(f.index) > length {
--			fields = fields[:i]
--			break
--		}
--		if f.tag {
--			if tagged >= 0 {
--				// Multiple tagged fields at the same level: conflict.
--				// Return no field.
--				return field{}, false
--			}
--			tagged = i
--		}
--	}
--	if tagged >= 0 {
--		return fields[tagged], true
--	}
--	// All remaining fields have the same length. If there's more than one,
--	// we have a conflict (two fields named "X" at the same level) and we
--	// return no field.
--	if len(fields) > 1 {
--		return field{}, false
--	}
--	return fields[0], true
+-// Extension is a struct that represents an OpenStack extension.
+-type Extension struct {
+-	Updated     string        `json:"updated" mapstructure:"updated"`
+-	Name        string        `json:"name" mapstructure:"name"`
+-	Links       []interface{} `json:"links" mapstructure:"links"`
+-	Namespace   string        `json:"namespace" mapstructure:"namespace"`
+-	Alias       string        `json:"alias" mapstructure:"alias"`
+-	Description string        `json:"description" mapstructure:"description"`
 -}
 -
--var fieldCache struct {
--	sync.RWMutex
--	m map[reflect.Type][]field
+-// ExtensionPage is the page returned by a pager when traversing over a collection of extensions.
+-type ExtensionPage struct {
+-	pagination.SinglePageBase
 -}
 -
--// cachedTypeFields is like typeFields but uses a cache to avoid repeated work.
--func cachedTypeFields(t reflect.Type) []field {
--	fieldCache.RLock()
--	f := fieldCache.m[t]
--	fieldCache.RUnlock()
--	if f != nil {
--		return f
+-// IsEmpty checks whether an ExtensionPage struct is empty.
+-func (r ExtensionPage) IsEmpty() (bool, error) {
+-	is, err := ExtractExtensions(r)
+-	if err != nil {
+-		return true, err
 -	}
+-	return len(is) == 0, nil
+-}
 -
--	// Compute fields without lock.
--	// Might duplicate effort but won't hold other computations back.
--	f = typeFields(t)
--	if f == nil {
--		f = []field{}
+-// ExtractExtensions accepts a Page struct, specifically an ExtensionPage struct, and extracts the
+-// elements into a slice of Extension structs.
+-// In other words, a generic collection is mapped into a relevant slice.
+-func ExtractExtensions(page pagination.Page) ([]Extension, error) {
+-	var resp struct {
+-		Extensions []Extension `mapstructure:"extensions"`
 -	}
 -
--	fieldCache.Lock()
--	if fieldCache.m == nil {
--		fieldCache.m = map[reflect.Type][]field{}
--	}
--	fieldCache.m[t] = f
--	fieldCache.Unlock()
--	return f
+-	err := mapstructure.Decode(page.(ExtensionPage).Body, &resp)
+-
+-	return resp.Extensions, err
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/urls.go
+deleted file mode 100644
+index 6460c66..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/urls.go
++++ /dev/null
+@@ -1,13 +0,0 @@
+-package extensions
 -
--func isValidTag(s string) bool {
--	if s == "" {
--		return false
--	}
--	for _, c := range s {
--		switch {
--		case strings.ContainsRune("!#$%&()*+-./:<=>?@[]^_{|}~ ", c):
--			// Backslash and quote chars are reserved, but
--			// otherwise any punctuation chars are allowed
--			// in a tag name.
--		default:
--			if !unicode.IsLetter(c) && !unicode.IsDigit(c) {
--				return false
--			}
--		}
--	}
--	return true
+-import "github.com/rackspace/gophercloud"
+-
+-// ExtensionURL generates the URL for an extension resource by name.
+-func ExtensionURL(c *gophercloud.ServiceClient, name string) string {
+-	return c.ServiceURL("extensions", name)
+-}
+-
+-// ListExtensionURL generates the URL for the extensions resource collection.
+-func ListExtensionURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL("extensions")
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/urls_test.go
+deleted file mode 100644
+index 3223b1c..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/common/extensions/urls_test.go
++++ /dev/null
+@@ -1,26 +0,0 @@
+-package extensions
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-const endpoint = "http://localhost:57909/"
+-
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint}
+-}
+-
+-func TestExtensionURL(t *testing.T) {
+-	actual := ExtensionURL(endpointClient(), "agent")
+-	expected := endpoint + "extensions/agent"
+-	th.AssertEquals(t, expected, actual)
+-}
+-
+-func TestListExtensionURL(t *testing.T) {
+-	actual := ListExtensionURL(endpointClient())
+-	expected := endpoint + "extensions"
+-	th.AssertEquals(t, expected, actual)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/requests.go
+deleted file mode 100644
+index 5a976d1..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/requests.go
++++ /dev/null
+@@ -1,111 +0,0 @@
+-package bootfromvolume
+-
+-import (
+-	"errors"
+-	"strconv"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/openstack/compute/v2/servers"
+-
+-	"github.com/racker/perigee"
+-)
+-
+-// SourceType represents the type of medium being used to create the volume.
+-type SourceType string
 -
 -const (
--	caseMask     = ^byte(0x20) // Mask to ignore case in ASCII.
--	kelvin       = '\u212a'
--	smallLongEss = '\u017f'
+-	Volume   SourceType = "volume"
+-	Snapshot SourceType = "snapshot"
+-	Image    SourceType = "image"
 -)
 -
--// foldFunc returns one of four different case folding equivalence
--// functions, from most general (and slow) to fastest:
--//
--// 1) bytes.EqualFold, if the key s contains any non-ASCII UTF-8
--// 2) equalFoldRight, if s contains special folding ASCII ('k', 'K', 's', 'S')
--// 3) asciiEqualFold, no special, but includes non-letters (including _)
--// 4) simpleLetterEqualFold, no specials, no non-letters.
--//
--// The letters S and K are special because they map to 3 runes, not just 2:
--//  * S maps to s and to U+017F 'ſ' Latin small letter long s
--//  * k maps to K and to U+212A 'K' Kelvin sign
--// See http://play.golang.org/p/tTxjOc0OGo
--//
--// The returned function is specialized for matching against s and
--// should only be given s. It's not curried for performance reasons.
--func foldFunc(s []byte) func(s, t []byte) bool {
--	nonLetter := false
--	special := false // special letter
--	for _, b := range s {
--		if b >= utf8.RuneSelf {
--			return bytes.EqualFold
--		}
--		upper := b & caseMask
--		if upper < 'A' || upper > 'Z' {
--			nonLetter = true
--		} else if upper == 'K' || upper == 'S' {
--			// See above for why these letters are special.
--			special = true
--		}
--	}
--	if special {
--		return equalFoldRight
--	}
--	if nonLetter {
--		return asciiEqualFold
--	}
--	return simpleLetterEqualFold
+-// BlockDevice is a structure with options for booting a server instance
+-// from a volume. The volume may be created from an image, snapshot, or another
+-// volume.
+-type BlockDevice struct {
+-	// BootIndex [optional] is the boot index. It defaults to 0.
+-	BootIndex int `json:"boot_index"`
+-
+-	// DeleteOnTermination [optional] specifies whether or not to delete the attached volume
+-	// when the server is deleted. Defaults to `false`.
+-	DeleteOnTermination bool `json:"delete_on_termination"`
+-
+-	// DestinationType [optional] is the type that gets created. Possible values are "volume"
+-	// and "local".
+-	DestinationType string `json:"destination_type"`
+-
+-	// SourceType [required] must be one of: "volume", "snapshot", "image".
+-	SourceType SourceType `json:"source_type"`
+-
+-	// UUID [required] is the unique identifier for the volume, snapshot, or image (see above)
+-	UUID string `json:"uuid"`
+-
+-	// VolumeSize [optional] is the size of the volume to create (in gigabytes).
+-	VolumeSize int `json:"volume_size"`
 -}
 -
--// equalFoldRight is a specialization of bytes.EqualFold when s is
--// known to be all ASCII (including punctuation), but contains an 's',
--// 'S', 'k', or 'K', requiring a Unicode fold on the bytes in t.
--// See comments on foldFunc.
--func equalFoldRight(s, t []byte) bool {
--	for _, sb := range s {
--		if len(t) == 0 {
--			return false
--		}
--		tb := t[0]
--		if tb < utf8.RuneSelf {
--			if sb != tb {
--				sbUpper := sb & caseMask
--				if 'A' <= sbUpper && sbUpper <= 'Z' {
--					if sbUpper != tb&caseMask {
--						return false
--					}
--				} else {
--					return false
--				}
--			}
--			t = t[1:]
--			continue
--		}
--		// sb is ASCII and t is not. t must be either kelvin
--		// sign or long s; sb must be s, S, k, or K.
--		tr, size := utf8.DecodeRune(t)
--		switch sb {
--		case 's', 'S':
--			if tr != smallLongEss {
--				return false
--			}
--		case 'k', 'K':
--			if tr != kelvin {
--				return false
--			}
--		default:
--			return false
--		}
--		t = t[size:]
+-// CreateOptsExt is a structure that extends the server `CreateOpts` structure
+-// by allowing for a block device mapping.
+-type CreateOptsExt struct {
+-	servers.CreateOptsBuilder
+-	BlockDevice []BlockDevice `json:"block_device_mapping_v2,omitempty"`
+-}
 -
+-// ToServerCreateMap adds the block device mapping option to the base server
+-// creation options.
+-func (opts CreateOptsExt) ToServerCreateMap() (map[string]interface{}, error) {
+-	base, err := opts.CreateOptsBuilder.ToServerCreateMap()
+-	if err != nil {
+-		return nil, err
 -	}
--	if len(t) > 0 {
--		return false
--	}
--	return true
--}
 -
--// asciiEqualFold is a specialization of bytes.EqualFold for use when
--// s is all ASCII (but may contain non-letters) and contains no
--// special-folding letters.
--// See comments on foldFunc.
--func asciiEqualFold(s, t []byte) bool {
--	if len(s) != len(t) {
--		return false
+-	if len(opts.BlockDevice) == 0 {
+-		return nil, errors.New("Required fields UUID and SourceType not set.")
 -	}
--	for i, sb := range s {
--		tb := t[i]
--		if sb == tb {
--			continue
--		}
--		if ('a' <= sb && sb <= 'z') || ('A' <= sb && sb <= 'Z') {
--			if sb&caseMask != tb&caseMask {
--				return false
--			}
--		} else {
--			return false
+-
+-	serverMap := base["server"].(map[string]interface{})
+-
+-	blockDevice := make([]map[string]interface{}, len(opts.BlockDevice))
+-
+-	for i, bd := range opts.BlockDevice {
+-		if string(bd.SourceType) == "" {
+-			return nil, errors.New("SourceType must be one of: volume, image, snapshot.")
 -		}
--	}
--	return true
--}
 -
--// simpleLetterEqualFold is a specialization of bytes.EqualFold for
--// use when s is all ASCII letters (no underscores, etc) and also
--// doesn't contain 'k', 'K', 's', or 'S'.
--// See comments on foldFunc.
--func simpleLetterEqualFold(s, t []byte) bool {
--	if len(s) != len(t) {
--		return false
--	}
--	for i, b := range s {
--		if b&caseMask != t[i]&caseMask {
--			return false
+-		blockDevice[i] = make(map[string]interface{})
+-
+-		blockDevice[i]["source_type"] = bd.SourceType
+-		blockDevice[i]["boot_index"] = strconv.Itoa(bd.BootIndex)
+-		blockDevice[i]["delete_on_termination"] = strconv.FormatBool(bd.DeleteOnTermination)
+-		blockDevice[i]["volume_size"] = strconv.Itoa(bd.VolumeSize)
+-		if bd.UUID != "" {
+-			blockDevice[i]["uuid"] = bd.UUID
+-		}
+-		if bd.DestinationType != "" {
+-			blockDevice[i]["destination_type"] = bd.DestinationType
 -		}
+-
 -	}
--	return true
+-	serverMap["block_device_mapping_v2"] = blockDevice
+-
+-	return base, nil
 -}
 -
--// tagOptions is the string following a comma in a struct field's "json"
--// tag, or the empty string. It does not include the leading comma.
--type tagOptions string
+-// Create requests the creation of a server from the given block device mapping.
+-func Create(client *gophercloud.ServiceClient, opts servers.CreateOptsBuilder) servers.CreateResult {
+-	var res servers.CreateResult
 -
--// parseTag splits a struct field's json tag into its name and
--// comma-separated options.
--func parseTag(tag string) (string, tagOptions) {
--	if idx := strings.Index(tag, ","); idx != -1 {
--		return tag[:idx], tagOptions(tag[idx+1:])
+-	reqBody, err := opts.ToServerCreateMap()
+-	if err != nil {
+-		res.Err = err
+-		return res
 -	}
--	return tag, tagOptions("")
+-
+-	_, res.Err = perigee.Request("POST", createURL(client), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		ReqBody:     reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{200, 202},
+-	})
+-	return res
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/requests_test.go
+deleted file mode 100644
+index 5bf9137..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/requests_test.go
++++ /dev/null
+@@ -1,51 +0,0 @@
+-package bootfromvolume
 -
--// Contains reports whether a comma-separated list of options
--// contains a particular substr flag. substr must be surrounded by a
--// string boundary or commas.
--func (o tagOptions) Contains(optionName string) bool {
--	if len(o) == 0 {
--		return false
--	}
--	s := string(o)
--	for s != "" {
--		var next string
--		i := strings.Index(s, ",")
--		if i >= 0 {
--			s, next = s[:i], s[i+1:]
--		}
--		if s == optionName {
--			return true
--		}
--		s = next
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/openstack/compute/v2/servers"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestCreateOpts(t *testing.T) {
+-	base := servers.CreateOpts{
+-		Name:      "createdserver",
+-		ImageRef:  "asdfasdfasdf",
+-		FlavorRef: "performance1-1",
+-	}
+-
+-	ext := CreateOptsExt{
+-		CreateOptsBuilder: base,
+-		BlockDevice: []BlockDevice{
+-			BlockDevice{
+-				UUID:            "123456",
+-				SourceType:      Image,
+-				DestinationType: "volume",
+-				VolumeSize:      10,
+-			},
+-		},
 -	}
--	return false
+-
+-	expected := `
+-    {
+-      "server": {
+-        "name": "createdserver",
+-        "imageRef": "asdfasdfasdf",
+-        "flavorRef": "performance1-1",
+-        "block_device_mapping_v2":[
+-          {
+-            "uuid":"123456",
+-            "source_type":"image",
+-            "destination_type":"volume",
+-            "boot_index": "0",
+-            "delete_on_termination": "false",
+-            "volume_size": "10"
+-          }
+-        ]
+-      }
+-    }
+-  `
+-	actual, err := ext.ToServerCreateMap()
+-	th.AssertNoErr(t, err)
+-	th.CheckJSONEquals(t, expected, actual)
 -}
-diff --git a/Godeps/_workspace/src/github.com/ghodss/yaml/yaml.go b/Godeps/_workspace/src/github.com/ghodss/yaml/yaml.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/results.go
 deleted file mode 100644
-index feab226..0000000
---- a/Godeps/_workspace/src/github.com/ghodss/yaml/yaml.go
+index f60329f..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/results.go
 +++ /dev/null
-@@ -1,250 +0,0 @@
--package yaml
+@@ -1,10 +0,0 @@
+-package bootfromvolume
 -
 -import (
--	"bytes"
--	"encoding/json"
--	"fmt"
--	"reflect"
--	"strconv"
--
--	"gopkg.in/v2/yaml"
+-	os "github.com/rackspace/gophercloud/openstack/compute/v2/servers"
 -)
 -
--// Marshals the object into JSON then converts JSON to YAML and returns the
--// YAML.
--func Marshal(o interface{}) ([]byte, error) {
--	j, err := json.Marshal(o)
--	if err != nil {
--		return nil, fmt.Errorf("error marshaling into JSON: ", err)
--	}
+-// CreateResult temporarily contains the response from a Create call.
+-type CreateResult struct {
+-	os.CreateResult
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/urls.go
+deleted file mode 100644
+index 0cffe25..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/urls.go
++++ /dev/null
+@@ -1,7 +0,0 @@
+-package bootfromvolume
 -
--	y, err := JSONToYAML(j)
--	if err != nil {
--		return nil, fmt.Errorf("error converting JSON to YAML: ", err)
--	}
+-import "github.com/rackspace/gophercloud"
 -
--	return y, nil
+-func createURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL("os-volumes_boot")
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/urls_test.go
+deleted file mode 100644
+index 6ee6477..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume/urls_test.go
++++ /dev/null
+@@ -1,16 +0,0 @@
+-package bootfromvolume
 -
--// Converts YAML to JSON then uses JSON to unmarshal into an object.
--func Unmarshal(y []byte, o interface{}) error {
--	vo := reflect.ValueOf(o)
--	j, err := yamlToJSON(y, &vo)
--	if err != nil {
--		return fmt.Errorf("error converting YAML to JSON: %v", err)
--	}
+-import (
+-	"testing"
 -
--	err = json.Unmarshal(j, o)
--	if err != nil {
--		return fmt.Errorf("error unmarshaling JSON: %v", err)
--	}
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--	return nil
+-func TestCreateURL(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	c := client.ServiceClient()
+-
+-	th.CheckEquals(t, c.Endpoint+"os-volumes_boot", createURL(c))
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/delegate.go
+deleted file mode 100644
+index 1007909..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/delegate.go
++++ /dev/null
+@@ -1,23 +0,0 @@
+-package extensions
 -
--// Convert JSON to YAML.
--func JSONToYAML(j []byte) ([]byte, error) {
--	// Convert the JSON to an object.
--	var jsonObj interface{}
--	err := json.Unmarshal(j, &jsonObj)
--	if err != nil {
--		return nil, err
--	}
+-import (
+-	"github.com/rackspace/gophercloud"
+-	common "github.com/rackspace/gophercloud/openstack/common/extensions"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	// Marshal this object into YAML.
--	return yaml.Marshal(jsonObj)
+-// ExtractExtensions interprets a Page as a slice of Extensions.
+-func ExtractExtensions(page pagination.Page) ([]common.Extension, error) {
+-	return common.ExtractExtensions(page)
 -}
 -
--// Convert YAML to JSON. Since JSON is a subset of YAML, passing JSON through
--// this method should be a no-op.
--//
--// Things YAML can do that are not supported by JSON:
--// * In YAML you can have binary and null keys in your maps. These are invalid
--//   in JSON. (int and float keys are converted to strings.)
--// * Binary data in YAML with the !!binary tag is not supported. If you want to
--//   use binary data with this library, encode the data as base64 as usual but do
--//   not use the !!binary tag in your YAML. This will ensure the original base64
--//   encoded data makes it all the way through to the JSON.
--func YAMLToJSON(y []byte) ([]byte, error) {
--	return yamlToJSON(y, nil)
+-// Get retrieves information for a specific extension using its alias.
+-func Get(c *gophercloud.ServiceClient, alias string) common.GetResult {
+-	return common.Get(c, alias)
 -}
 -
--func yamlToJSON(y []byte, jsonTarget *reflect.Value) ([]byte, error) {
--	// Convert the YAML to an object.
--	var yamlObj interface{}
--	err := yaml.Unmarshal(y, &yamlObj)
--	if err != nil {
--		return nil, err
--	}
+-// List returns a Pager which allows you to iterate over the full collection of extensions.
+-// It does not accept query parameters.
+-func List(c *gophercloud.ServiceClient) pagination.Pager {
+-	return common.List(c)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/delegate_test.go
+deleted file mode 100644
+index c3c525f..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/delegate_test.go
++++ /dev/null
+@@ -1,96 +0,0 @@
+-package extensions
 -
--	// YAML objects are not completely compatible with JSON objects (e.g. you
--	// can have non-string keys in YAML). So, convert the YAML-compatible object
--	// to a JSON-compatible object, failing with an error if irrecoverable
--	// incompatibilties happen along the way.
--	jsonObj, err := convertToJSONableObject(yamlObj, jsonTarget)
--	if err != nil {
--		return nil, err
--	}
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--	// Convert this object to JSON and return the data.
--	return json.Marshal(jsonObj)
--}
+-	common "github.com/rackspace/gophercloud/openstack/common/extensions"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--func convertToJSONableObject(yamlObj interface{}, jsonTarget *reflect.Value) (interface{}, error) {
--	var err error
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	// Resolve jsonTarget to a concrete value (i.e. not a pointer or an
--	// interface). We pass decodingNull as false because we're not actually
--	// decoding into the value, we're just checking if the ultimate target is a
--	// string.
--	if jsonTarget != nil {
--		ju, tu, pv := indirect(*jsonTarget, false)
--		// We have a JSON or Text Umarshaler at this level, so we can't be trying
--		// to decode into a string.
--		if ju != nil || tu != nil {
--			jsonTarget = nil
--		} else {
--			jsonTarget = &pv
--		}
--	}
+-	th.Mux.HandleFunc("/extensions", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
 -
--	// If yamlObj is a number, check if jsonTarget is a string - if so, coerce.
--	// Else return normal.
--	// If yamlObj is a map or array, find the field that each key is
--	// unmarshaling to, and when you recurse pass the reflect.Value for that
--	// field back into this function.
+-		w.Header().Add("Content-Type", "application/json")
 -
--	switch typedYAMLObj := yamlObj.(type) {
--	case map[interface{}]interface{}:
--		// JSON does not support arbitrary keys in a map, so we must convert
--		// these keys to strings.
--		//
--		// From my reading of go-yaml v2 (specifically the resolve function),
--		// keys can only have the types string, int, int64, float64, binary
--		// (unsupported), or null (unsupported).
--		strMap := make(map[string]interface{})
--		for k, v := range typedYAMLObj {
--			// Resolve the key to a string first.
--			var keyString string
--			switch typedKey := k.(type) {
--			case string:
--				keyString = typedKey
--			case int:
--				keyString = strconv.Itoa(typedKey)
--			case int64:
--				// go-yaml will only return an int64 as a key if the system
--				// architecture is 32-bit and the key's value is between 32-bit
--				// and 64-bit. Otherwise the key type will simply be int.
--				keyString = strconv.FormatInt(typedKey, 10)
--			case float64:
--				// Stolen from go-yaml to use the same conversion to string as
--				// the go-yaml library uses to convert float to string when
--				// Marshaling.
--				s := strconv.FormatFloat(typedKey, 'g', -1, 32)
--				switch s {
--				case "+Inf":
--					s = ".inf"
--				case "-Inf":
--					s = "-.inf"
--				case "NaN":
--					s = ".nan"
+-		fmt.Fprintf(w, `
+-{
+-		"extensions": [
+-				{
+-						"updated": "2013-01-20T00:00:00-00:00",
+-						"name": "Neutron Service Type Management",
+-						"links": [],
+-						"namespace": "http://docs.openstack.org/ext/neutron/service-type/api/v1.0",
+-						"alias": "service-type",
+-						"description": "API for retrieving service providers for Neutron advanced services"
 -				}
--				keyString = s
--			default:
--				return nil, fmt.Errorf("Unsupported map key of type: %s, key: %+#v, value: %+#v",
--					reflect.TypeOf(k), k, v)
--			}
+-		]
+-}
+-			`)
+-	})
 -
--			// If jsonTarget is a struct (which it really should be), find the
--			// field it's going to map to. If it's not a struct, just pass nil
--			// - JSON conversion will error for us if it's a real issue.
--			if jsonTarget != nil {
--				t := *jsonTarget
--				if t.Kind() == reflect.Struct {
--					keyBytes := []byte(keyString)
--					// Find the field that the JSON library would use.
--					var f *field
--					fields := cachedTypeFields(t.Type())
--					for i := range fields {
--						ff := &fields[i]
--						if bytes.Equal(ff.nameBytes, keyBytes) {
--							f = ff
--							break
--						}
--						// Do case-insensitive comparison.
--						if f == nil && ff.equalFold(ff.nameBytes, keyBytes) {
--							f = ff
--						}
--					}
--					if f != nil {
--						// Find the reflect.Value of the most preferential
--						// struct field.
--						jtf := t.Field(f.index[0])
--						strMap[keyString], err = convertToJSONableObject(v, &jtf)
--						if err != nil {
--							return nil, err
--						}
--						continue
--					}
--				}
--			}
--			strMap[keyString], err = convertToJSONableObject(v, nil)
--			if err != nil {
--				return nil, err
--			}
+-	count := 0
+-	List(client.ServiceClient()).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractExtensions(page)
+-		th.AssertNoErr(t, err)
+-
+-		expected := []common.Extension{
+-			common.Extension{
+-				Updated:     "2013-01-20T00:00:00-00:00",
+-				Name:        "Neutron Service Type Management",
+-				Links:       []interface{}{},
+-				Namespace:   "http://docs.openstack.org/ext/neutron/service-type/api/v1.0",
+-				Alias:       "service-type",
+-				Description: "API for retrieving service providers for Neutron advanced services",
+-			},
 -		}
--		return strMap, nil
--	case []interface{}:
--		// We need to recurse into arrays in case there are any
--		// map[interface{}]interface{}'s inside and to convert any
--		// numbers to strings.
+-		th.AssertDeepEquals(t, expected, actual)
 -
--		// If jsonTarget is a slice (which it really should be), find the
--		// thing it's going to map to. If it's not a slice, just pass nil
--		// - JSON conversion will error for us if it's a real issue.
--		var jsonSliceElemValue *reflect.Value
--		if jsonTarget != nil {
--			t := *jsonTarget
--			if t.Kind() == reflect.Slice {
--				// By default slices point to nil, but we need a reflect.Value
--				// pointing to a value of the slice type, so we create one here.
--				ev := reflect.Indirect(reflect.New(t.Type().Elem()))
--				jsonSliceElemValue = &ev
--			}
--		}
+-		return true, nil
+-	})
+-	th.CheckEquals(t, 1, count)
+-}
 -
--		// Make and use a new array.
--		arr := make([]interface{}, len(typedYAMLObj))
--		for i, v := range typedYAMLObj {
--			arr[i], err = convertToJSONableObject(v, jsonSliceElemValue)
--			if err != nil {
--				return nil, err
--			}
--		}
--		return arr, nil
--	default:
--		// If the target type is a string and the YAML type is a number,
--		// convert the YAML type to a string.
--		if jsonTarget != nil && (*jsonTarget).Kind() == reflect.String {
--			// Based on my reading of go-yaml, it may return int, int64,
--			// float64, or uint64.
--			var s string
--			switch num := typedYAMLObj.(type) {
--			case int:
--				s = strconv.FormatInt(int64(num), 10)
--			case int64:
--				s = strconv.FormatInt(num, 10)
--			case float64:
--				s = strconv.FormatFloat(num, 'g', -1, 32)
--			case uint64:
--				s = strconv.FormatUint(num, 10)
--			}
--			if len(s) > 0 {
--				yamlObj = interface{}(s)
--			}
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/extensions/agent", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-		"extension": {
+-				"updated": "2013-02-03T10:00:00-00:00",
+-				"name": "agent",
+-				"links": [],
+-				"namespace": "http://docs.openstack.org/ext/agent/api/v2.0",
+-				"alias": "agent",
+-				"description": "The agent management extension."
 -		}
--		return yamlObj, nil
--	}
+-}
+-		`)
+-	})
 -
--	return nil, nil
+-	ext, err := Get(client.ServiceClient(), "agent").Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, ext.Updated, "2013-02-03T10:00:00-00:00")
+-	th.AssertEquals(t, ext.Name, "agent")
+-	th.AssertEquals(t, ext.Namespace, "http://docs.openstack.org/ext/agent/api/v2.0")
+-	th.AssertEquals(t, ext.Alias, "agent")
+-	th.AssertEquals(t, ext.Description, "The agent management extension.")
 -}
-diff --git a/Godeps/_workspace/src/github.com/ghodss/yaml/yaml_test.go b/Godeps/_workspace/src/github.com/ghodss/yaml/yaml_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/doc.go
 deleted file mode 100644
-index c569ebd..0000000
---- a/Godeps/_workspace/src/github.com/ghodss/yaml/yaml_test.go
+index 80785fa..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/doc.go
 +++ /dev/null
-@@ -1,243 +0,0 @@
--package yaml
+@@ -1,3 +0,0 @@
+-// Package diskconfig provides information and interaction with the Disk
+-// Config extension that works with the OpenStack Compute service.
+-package diskconfig
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/requests.go
+deleted file mode 100644
+index 7407e0d..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/requests.go
++++ /dev/null
+@@ -1,114 +0,0 @@
+-package diskconfig
 -
 -import (
--	"reflect"
--	"testing"
+-	"errors"
+-
+-	"github.com/rackspace/gophercloud/openstack/compute/v2/servers"
 -)
 -
--type MarshalTest struct {
--	A string
+-// DiskConfig represents one of the two possible settings for the DiskConfig option when creating,
+-// rebuilding, or resizing servers: Auto or Manual.
+-type DiskConfig string
+-
+-const (
+-	// Auto builds a server with a single partition the size of the target flavor disk and
+-	// automatically adjusts the filesystem to fit the entire partition. Auto may only be used with
+-	// images and servers that use a single EXT3 partition.
+-	Auto DiskConfig = "AUTO"
+-
+-	// Manual builds a server using whatever partition scheme and filesystem are present in the source
+-	// image. If the target flavor disk is larger, the remaining space is left unpartitioned. This
+-	// enables images to have non-EXT3 filesystems, multiple partitions, and so on, and enables you
+-	// to manage the disk configuration. It also results in slightly shorter boot times.
+-	Manual DiskConfig = "MANUAL"
+-)
+-
+-// ErrInvalidDiskConfig is returned if an invalid string is specified for a DiskConfig option.
+-var ErrInvalidDiskConfig = errors.New("DiskConfig must be either diskconfig.Auto or diskconfig.Manual.")
+-
+-// Validate ensures that a DiskConfig contains an appropriate value.
+-func (config DiskConfig) validate() error {
+-	switch config {
+-	case Auto, Manual:
+-		return nil
+-	default:
+-		return ErrInvalidDiskConfig
+-	}
 -}
 -
--func TestMarshal(t *testing.T) {
--	s := MarshalTest{"a"}
--	e := []byte("A: a\n")
+-// CreateOptsExt adds a DiskConfig option to the base CreateOpts.
+-type CreateOptsExt struct {
+-	servers.CreateOptsBuilder
 -
--	y, err := Marshal(s)
+-	// DiskConfig [optional] controls how the created server's disk is partitioned.
+-	DiskConfig DiskConfig `json:"OS-DCF:diskConfig,omitempty"`
+-}
+-
+-// ToServerCreateMap adds the diskconfig option to the base server creation options.
+-func (opts CreateOptsExt) ToServerCreateMap() (map[string]interface{}, error) {
+-	base, err := opts.CreateOptsBuilder.ToServerCreateMap()
 -	if err != nil {
--		t.Errorf("error marshaling YAML: %v", err)
+-		return nil, err
 -	}
 -
--	if !reflect.DeepEqual(y, e) {
--		t.Errorf("marshal YAML was unsuccessful, expected: %#v, got: %#v",
--			string(e), string(y))
+-	if string(opts.DiskConfig) == "" {
+-		return base, nil
 -	}
--}
 -
--type UnmarshalString struct {
--	A string
--}
+-	serverMap := base["server"].(map[string]interface{})
+-	serverMap["OS-DCF:diskConfig"] = string(opts.DiskConfig)
 -
--type UnmarshalNestedString struct {
--	A NestedString
+-	return base, nil
 -}
 -
--type NestedString struct {
--	A string
--}
+-// RebuildOptsExt adds a DiskConfig option to the base RebuildOpts.
+-type RebuildOptsExt struct {
+-	servers.RebuildOptsBuilder
 -
--type UnmarshalSlice struct {
--	A []NestedSlice
+-	// DiskConfig [optional] controls how the rebuilt server's disk is partitioned.
+-	DiskConfig DiskConfig
 -}
 -
--type NestedSlice struct {
--	B string
--	C *string
--}
+-// ToServerRebuildMap adds the diskconfig option to the base server rebuild options.
+-func (opts RebuildOptsExt) ToServerRebuildMap() (map[string]interface{}, error) {
+-	err := opts.DiskConfig.validate()
+-	if err != nil {
+-		return nil, err
+-	}
 -
--func TestUnmarshal(t *testing.T) {
--	y := []byte("a: 1")
--	s1 := UnmarshalString{}
--	e1 := UnmarshalString{"1"}
--	unmarshal(t, y, &s1, &e1)
+-	base, err := opts.RebuildOptsBuilder.ToServerRebuildMap()
+-	if err != nil {
+-		return nil, err
+-	}
 -
--	y = []byte("a:\n  a: 1")
--	s2 := UnmarshalNestedString{}
--	e2 := UnmarshalNestedString{NestedString{"1"}}
--	unmarshal(t, y, &s2, &e2)
+-	serverMap := base["rebuild"].(map[string]interface{})
+-	serverMap["OS-DCF:diskConfig"] = string(opts.DiskConfig)
 -
--	y = []byte("a:\n  - b: abc\n    c: def\n  - b: 123\n    c: 456\n")
--	s3 := UnmarshalSlice{}
--	e3 := UnmarshalSlice{[]NestedSlice{NestedSlice{"abc", strPtr("def")}, NestedSlice{"123", strPtr("456")}}}
--	unmarshal(t, y, &s3, &e3)
+-	return base, nil
 -}
 -
--func unmarshal(t *testing.T, y []byte, s, e interface{}) {
--	err := Unmarshal(y, s)
+-// ResizeOptsExt adds a DiskConfig option to the base server resize options.
+-type ResizeOptsExt struct {
+-	servers.ResizeOptsBuilder
+-
+-	// DiskConfig [optional] controls how the resized server's disk is partitioned.
+-	DiskConfig DiskConfig
+-}
+-
+-// ToServerResizeMap adds the diskconfig option to the base server creation options.
+-func (opts ResizeOptsExt) ToServerResizeMap() (map[string]interface{}, error) {
+-	err := opts.DiskConfig.validate()
 -	if err != nil {
--		t.Errorf("error unmarshaling YAML: %v", err)
+-		return nil, err
 -	}
 -
--	if !reflect.DeepEqual(s, e) {
--		t.Errorf("unmarshal YAML was unsuccessful, expected: %+#v, got: %+#v",
--			e, s)
+-	base, err := opts.ResizeOptsBuilder.ToServerResizeMap()
+-	if err != nil {
+-		return nil, err
 -	}
--}
 -
--type Case struct {
--	input  string
--	output string
--	// By default we test that reversing the output == input. But if there is a
--	// difference in the reversed output, you can optionally specify it here.
--	reverse *string
+-	serverMap := base["resize"].(map[string]interface{})
+-	serverMap["OS-DCF:diskConfig"] = string(opts.DiskConfig)
+-
+-	return base, nil
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/requests_test.go
+deleted file mode 100644
+index e3c26d4..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/requests_test.go
++++ /dev/null
+@@ -1,87 +0,0 @@
+-package diskconfig
 -
--type RunType int
+-import (
+-	"testing"
 -
--const (
--	RunTypeJSONToYAML RunType = iota
--	RunTypeYAMLToJSON
+-	"github.com/rackspace/gophercloud/openstack/compute/v2/servers"
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--func TestJSONToYAML(t *testing.T) {
--	cases := []Case{
--		{
--			`{"t":"a"}`,
--			"t: a\n",
--			nil,
--		}, {
--			`{"t":null}`,
--			"t: null\n",
--			nil,
--		},
+-func TestCreateOpts(t *testing.T) {
+-	base := servers.CreateOpts{
+-		Name:      "createdserver",
+-		ImageRef:  "asdfasdfasdf",
+-		FlavorRef: "performance1-1",
 -	}
 -
--	runCases(t, RunTypeJSONToYAML, cases)
--}
--
--func TestYAMLToJSON(t *testing.T) {
--	cases := []Case{
--		{
--			"t: a\n",
--			`{"t":"a"}`,
--			nil,
--		}, {
--			"t: \n",
--			`{"t":null}`,
--			strPtr("t: null\n"),
--		}, {
--			"t: null\n",
--			`{"t":null}`,
--			nil,
--		}, {
--			"1: a\n",
--			`{"1":"a"}`,
--			strPtr("\"1\": a\n"),
--		}, {
--			"1000000000000000000000000000000000000: a\n",
--			`{"1e+36":"a"}`,
--			strPtr("\"1e+36\": a\n"),
--		}, {
--			"1e+36: a\n",
--			`{"1e+36":"a"}`,
--			strPtr("\"1e+36\": a\n"),
--		}, {
--			"\"1e+36\": a\n",
--			`{"1e+36":"a"}`,
--			nil,
--		}, {
--			"\"1.2\": a\n",
--			`{"1.2":"a"}`,
--			nil,
--		}, {
--			"- t: a\n",
--			`[{"t":"a"}]`,
--			nil,
--		}, {
--			"- t: a\n" +
--				"- t:\n" +
--				"    b: 1\n" +
--				"    c: 2\n",
--			`[{"t":"a"},{"t":{"b":1,"c":2}}]`,
--			nil,
--		}, {
--			`[{t: a}, {t: {b: 1, c: 2}}]`,
--			`[{"t":"a"},{"t":{"b":1,"c":2}}]`,
--			strPtr("- t: a\n" +
--				"- t:\n" +
--				"    b: 1\n" +
--				"    c: 2\n"),
--		}, {
--			"- t: \n",
--			`[{"t":null}]`,
--			strPtr("- t: null\n"),
--		}, {
--			"- t: null\n",
--			`[{"t":null}]`,
--			nil,
--		},
+-	ext := CreateOptsExt{
+-		CreateOptsBuilder: base,
+-		DiskConfig:        Manual,
 -	}
 -
--	// Cases that should produce errors.
--	_ = []Case{
+-	expected := `
 -		{
--			"~: a",
--			`{"null":"a"}`,
--			nil,
--		}, {
--			"a: !!binary gIGC\n",
--			"{\"a\":\"\x80\x81\x82\"}",
--			nil,
--		},
--	}
--
--	runCases(t, RunTypeYAMLToJSON, cases)
+-			"server": {
+-				"name": "createdserver",
+-				"imageRef": "asdfasdfasdf",
+-				"flavorRef": "performance1-1",
+-				"OS-DCF:diskConfig": "MANUAL"
+-			}
+-		}
+-	`
+-	actual, err := ext.ToServerCreateMap()
+-	th.AssertNoErr(t, err)
+-	th.CheckJSONEquals(t, expected, actual)
 -}
 -
--func runCases(t *testing.T, runType RunType, cases []Case) {
--	var f func([]byte) ([]byte, error)
--	var invF func([]byte) ([]byte, error)
--	var msg string
--	var invMsg string
--	if runType == RunTypeJSONToYAML {
--		f = JSONToYAML
--		invF = YAMLToJSON
--		msg = "JSON to YAML"
--		invMsg = "YAML back to JSON"
--	} else {
--		f = YAMLToJSON
--		invF = JSONToYAML
--		msg = "YAML to JSON"
--		invMsg = "JSON back to YAML"
+-func TestRebuildOpts(t *testing.T) {
+-	base := servers.RebuildOpts{
+-		Name:      "rebuiltserver",
+-		AdminPass: "swordfish",
+-		ImageID:   "asdfasdfasdf",
 -	}
 -
--	for _, c := range cases {
--		// Convert the string.
--		t.Logf("converting %s\n", c.input)
--		output, err := f([]byte(c.input))
--		if err != nil {
--			t.Errorf("Failed to convert %s, input: `%s`, err: %v", msg, c.input, err)
--		}
+-	ext := RebuildOptsExt{
+-		RebuildOptsBuilder: base,
+-		DiskConfig:         Auto,
+-	}
 -
--		// Check it against the expected output.
--		if string(output) != c.output {
--			t.Errorf("Failed to convert %s, input: `%s`, expected `%s`, got `%s`",
--				msg, c.input, c.output, string(output))
--		}
+-	actual, err := ext.ToServerRebuildMap()
+-	th.AssertNoErr(t, err)
 -
--		// Set the string that we will compare the reversed output to.
--		reverse := c.input
--		// If a special reverse string was specified, use that instead.
--		if c.reverse != nil {
--			reverse = *c.reverse
+-	expected := `
+-		{
+-			"rebuild": {
+-				"name": "rebuiltserver",
+-				"imageRef": "asdfasdfasdf",
+-				"adminPass": "swordfish",
+-				"OS-DCF:diskConfig": "AUTO"
+-			}
 -		}
+-	`
+-	th.CheckJSONEquals(t, expected, actual)
+-}
 -
--		// Reverse the output.
--		input, err := invF(output)
--		if err != nil {
--			t.Errorf("Failed to convert %s, input: `%s`, err: %v", invMsg, string(output), err)
--		}
+-func TestResizeOpts(t *testing.T) {
+-	base := servers.ResizeOpts{
+-		FlavorRef: "performance1-8",
+-	}
 -
--		// Check the reverse is equal to the input (or to *c.reverse).
--		if string(input) != reverse {
--			t.Errorf("Failed to convert %s, input: `%s`, expected `%s`, got `%s`",
--				invMsg, string(output), reverse, string(input))
--		}
+-	ext := ResizeOptsExt{
+-		ResizeOptsBuilder: base,
+-		DiskConfig:        Auto,
 -	}
 -
--}
+-	actual, err := ext.ToServerResizeMap()
+-	th.AssertNoErr(t, err)
 -
--// To be able to easily fill in the *Case.reverse string above.
--func strPtr(s string) *string {
--	return &s
+-	expected := `
+-		{
+-			"resize": {
+-				"flavorRef": "performance1-8",
+-				"OS-DCF:diskConfig": "AUTO"
+-			}
+-		}
+-	`
+-	th.CheckJSONEquals(t, expected, actual)
 -}
-diff --git a/Godeps/_workspace/src/github.com/golang/glog/LICENSE b/Godeps/_workspace/src/github.com/golang/glog/LICENSE
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/results.go
 deleted file mode 100644
-index 37ec93a..0000000
---- a/Godeps/_workspace/src/github.com/golang/glog/LICENSE
+index 10ec2da..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/results.go
 +++ /dev/null
-@@ -1,191 +0,0 @@
--Apache License
--Version 2.0, January 2004
--http://www.apache.org/licenses/
+@@ -1,60 +0,0 @@
+-package diskconfig
 -
--TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/openstack/compute/v2/servers"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--1. Definitions.
+-func commonExtract(result gophercloud.Result) (*DiskConfig, error) {
+-	var resp struct {
+-		Server struct {
+-			DiskConfig string `mapstructure:"OS-DCF:diskConfig"`
+-		} `mapstructure:"server"`
+-	}
 -
--"License" shall mean the terms and conditions for use, reproduction, and
--distribution as defined by Sections 1 through 9 of this document.
+-	err := mapstructure.Decode(result.Body, &resp)
+-	if err != nil {
+-		return nil, err
+-	}
 -
--"Licensor" shall mean the copyright owner or entity authorized by the copyright
--owner that is granting the License.
+-	config := DiskConfig(resp.Server.DiskConfig)
+-	return &config, nil
+-}
 -
--"Legal Entity" shall mean the union of the acting entity and all other entities
--that control, are controlled by, or are under common control with that entity.
--For the purposes of this definition, "control" means (i) the power, direct or
--indirect, to cause the direction or management of such entity, whether by
--contract or otherwise, or (ii) ownership of fifty percent (50%) or more of the
--outstanding shares, or (iii) beneficial ownership of such entity.
+-// ExtractGet returns the disk configuration from a servers.Get call.
+-func ExtractGet(result servers.GetResult) (*DiskConfig, error) {
+-	return commonExtract(result.Result)
+-}
 -
--"You" (or "Your") shall mean an individual or Legal Entity exercising
--permissions granted by this License.
+-// ExtractUpdate returns the disk configuration from a servers.Update call.
+-func ExtractUpdate(result servers.UpdateResult) (*DiskConfig, error) {
+-	return commonExtract(result.Result)
+-}
 -
--"Source" form shall mean the preferred form for making modifications, including
--but not limited to software source code, documentation source, and configuration
--files.
+-// ExtractRebuild returns the disk configuration from a servers.Rebuild call.
+-func ExtractRebuild(result servers.RebuildResult) (*DiskConfig, error) {
+-	return commonExtract(result.Result)
+-}
 -
--"Object" form shall mean any form resulting from mechanical transformation or
--translation of a Source form, including but not limited to compiled object code,
--generated documentation, and conversions to other media types.
+-// ExtractDiskConfig returns the DiskConfig setting for a specific server acquired from an
+-// servers.ExtractServers call, while iterating through a Pager.
+-func ExtractDiskConfig(page pagination.Page, index int) (*DiskConfig, error) {
+-	casted := page.(servers.ServerPage).Body
 -
--"Work" shall mean the work of authorship, whether in Source or Object form, made
--available under the License, as indicated by a copyright notice that is included
--in or attached to the work (an example is provided in the Appendix below).
+-	type server struct {
+-		DiskConfig string `mapstructure:"OS-DCF:diskConfig"`
+-	}
+-	var response struct {
+-		Servers []server `mapstructure:"servers"`
+-	}
 -
--"Derivative Works" shall mean any work, whether in Source or Object form, that
--is based on (or derived from) the Work and for which the editorial revisions,
--annotations, elaborations, or other modifications represent, as a whole, an
--original work of authorship. For the purposes of this License, Derivative Works
--shall not include works that remain separable from, or merely link (or bind by
--name) to the interfaces of, the Work and Derivative Works thereof.
+-	err := mapstructure.Decode(casted, &response)
+-	if err != nil {
+-		return nil, err
+-	}
 -
--"Contribution" shall mean any work of authorship, including the original version
--of the Work and any modifications or additions to that Work or Derivative Works
--thereof, that is intentionally submitted to Licensor for inclusion in the Work
--by the copyright owner or by an individual or Legal Entity authorized to submit
--on behalf of the copyright owner. For the purposes of this definition,
--"submitted" means any form of electronic, verbal, or written communication sent
--to the Licensor or its representatives, including but not limited to
--communication on electronic mailing lists, source code control systems, and
--issue tracking systems that are managed by, or on behalf of, the Licensor for
--the purpose of discussing and improving the Work, but excluding communication
--that is conspicuously marked or otherwise designated in writing by the copyright
--owner as "Not a Contribution."
+-	config := DiskConfig(response.Servers[index].DiskConfig)
+-	return &config, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/results_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/results_test.go
+deleted file mode 100644
+index dd8d2b7..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig/results_test.go
++++ /dev/null
+@@ -1,68 +0,0 @@
+-package diskconfig
 -
--"Contributor" shall mean Licensor and any individual or Legal Entity on behalf
--of whom a Contribution has been received by Licensor and subsequently
--incorporated within the Work.
+-import (
+-	"testing"
 -
--2. Grant of Copyright License.
+-	"github.com/rackspace/gophercloud/openstack/compute/v2/servers"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--Subject to the terms and conditions of this License, each Contributor hereby
--grants to You a perpetual, worldwide, non-exclusive, no-charge, royalty-free,
--irrevocable copyright license to reproduce, prepare Derivative Works of,
--publicly display, publicly perform, sublicense, and distribute the Work and such
--Derivative Works in Source or Object form.
+-func TestExtractGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	servers.HandleServerGetSuccessfully(t)
 -
--3. Grant of Patent License.
+-	config, err := ExtractGet(servers.Get(client.ServiceClient(), "1234asdf"))
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, Manual, *config)
+-}
 -
--Subject to the terms and conditions of this License, each Contributor hereby
--grants to You a perpetual, worldwide, non-exclusive, no-charge, royalty-free,
--irrevocable (except as stated in this section) patent license to make, have
--made, use, offer to sell, sell, import, and otherwise transfer the Work, where
--such license applies only to those patent claims licensable by such Contributor
--that are necessarily infringed by their Contribution(s) alone or by combination
--of their Contribution(s) with the Work to which such Contribution(s) was
--submitted. If You institute patent litigation against any entity (including a
--cross-claim or counterclaim in a lawsuit) alleging that the Work or a
--Contribution incorporated within the Work constitutes direct or contributory
--patent infringement, then any patent licenses granted to You under this License
--for that Work shall terminate as of the date such litigation is filed.
+-func TestExtractUpdate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	servers.HandleServerUpdateSuccessfully(t)
 -
--4. Redistribution.
+-	r := servers.Update(client.ServiceClient(), "1234asdf", servers.UpdateOpts{
+-		Name: "new-name",
+-	})
+-	config, err := ExtractUpdate(r)
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, Manual, *config)
+-}
 -
--You may reproduce and distribute copies of the Work or Derivative Works thereof
--in any medium, with or without modifications, and in Source or Object form,
--provided that You meet the following conditions:
+-func TestExtractRebuild(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	servers.HandleRebuildSuccessfully(t, servers.SingleServerBody)
 -
--You must give any other recipients of the Work or Derivative Works a copy of
--this License; and
--You must cause any modified files to carry prominent notices stating that You
--changed the files; and
--You must retain, in the Source form of any Derivative Works that You distribute,
--all copyright, patent, trademark, and attribution notices from the Source form
--of the Work, excluding those notices that do not pertain to any part of the
--Derivative Works; and
--If the Work includes a "NOTICE" text file as part of its distribution, then any
--Derivative Works that You distribute must include a readable copy of the
--attribution notices contained within such NOTICE file, excluding those notices
--that do not pertain to any part of the Derivative Works, in at least one of the
--following places: within a NOTICE text file distributed as part of the
--Derivative Works; within the Source form or documentation, if provided along
--with the Derivative Works; or, within a display generated by the Derivative
--Works, if and wherever such third-party notices normally appear. The contents of
--the NOTICE file are for informational purposes only and do not modify the
--License. You may add Your own attribution notices within Derivative Works that
--You distribute, alongside or as an addendum to the NOTICE text from the Work,
--provided that such additional attribution notices cannot be construed as
--modifying the License.
--You may add Your own copyright statement to Your modifications and may provide
--additional or different license terms and conditions for use, reproduction, or
--distribution of Your modifications, or for any such Derivative Works as a whole,
--provided Your use, reproduction, and distribution of the Work otherwise complies
--with the conditions stated in this License.
+-	r := servers.Rebuild(client.ServiceClient(), "1234asdf", servers.RebuildOpts{
+-		Name:       "new-name",
+-		AdminPass:  "swordfish",
+-		ImageID:    "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/images/f90f6034-2570-4974-8351-6b49732ef2eb",
+-		AccessIPv4: "1.2.3.4",
+-	})
+-	config, err := ExtractRebuild(r)
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, Manual, *config)
+-}
 -
--5. Submission of Contributions.
+-func TestExtractList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	servers.HandleServerListSuccessfully(t)
 -
--Unless You explicitly state otherwise, any Contribution intentionally submitted
--for inclusion in the Work by You to the Licensor shall be under the terms and
--conditions of this License, without any additional terms or conditions.
--Notwithstanding the above, nothing herein shall supersede or modify the terms of
--any separate license agreement you may have executed with Licensor regarding
--such Contributions.
+-	pages := 0
+-	err := servers.List(client.ServiceClient(), nil).EachPage(func(page pagination.Page) (bool, error) {
+-		pages++
 -
--6. Trademarks.
+-		config, err := ExtractDiskConfig(page, 0)
+-		th.AssertNoErr(t, err)
+-		th.CheckEquals(t, Manual, *config)
 -
--This License does not grant permission to use the trade names, trademarks,
--service marks, or product names of the Licensor, except as required for
--reasonable and customary use in describing the origin of the Work and
--reproducing the content of the NOTICE file.
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, pages, 1)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/doc.go
+deleted file mode 100644
+index 2b447da..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/doc.go
++++ /dev/null
+@@ -1,3 +0,0 @@
+-// Package extensions provides information and interaction with the
+-// different extensions available for the OpenStack Compute service.
+-package extensions
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/doc.go
+deleted file mode 100644
+index 856f41b..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/doc.go
++++ /dev/null
+@@ -1,3 +0,0 @@
+-// Package keypairs provides information and interaction with the Keypairs
+-// extension for the OpenStack Compute service.
+-package keypairs
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/fixtures.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/fixtures.go
+deleted file mode 100644
+index d10af99..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/fixtures.go
++++ /dev/null
+@@ -1,171 +0,0 @@
+-// +build fixtures
 -
--7. Disclaimer of Warranty.
+-package keypairs
 -
--Unless required by applicable law or agreed to in writing, Licensor provides the
--Work (and each Contributor provides its Contributions) on an "AS IS" BASIS,
--WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied,
--including, without limitation, any warranties or conditions of TITLE,
--NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A PARTICULAR PURPOSE. You are
--solely responsible for determining the appropriateness of using or
--redistributing the Work and assume any risks associated with Your exercise of
--permissions under this License.
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--8. Limitation of Liability.
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--In no event and under no legal theory, whether in tort (including negligence),
--contract, or otherwise, unless required by applicable law (such as deliberate
--and grossly negligent acts) or agreed to in writing, shall any Contributor be
--liable to You for damages, including any direct, indirect, special, incidental,
--or consequential damages of any character arising as a result of this License or
--out of the use or inability to use the Work (including but not limited to
--damages for loss of goodwill, work stoppage, computer failure or malfunction, or
--any and all other commercial damages or losses), even if such Contributor has
--been advised of the possibility of such damages.
+-// ListOutput is a sample response to a List call.
+-const ListOutput = `
+-{
+-	"keypairs": [
+-		{
+-			"keypair": {
+-				"fingerprint": "15:b0:f8:b3:f9:48:63:71:cf:7b:5b:38:6d:44:2d:4a",
+-				"name": "firstkey",
+-				"public_key": "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAAgQC+Eo/RZRngaGTkFs7I62ZjsIlO79KklKbMXi8F+KITD4bVQHHn+kV+4gRgkgCRbdoDqoGfpaDFs877DYX9n4z6FrAIZ4PES8TNKhatifpn9NdQYWA+IkU8CuvlEKGuFpKRi/k7JLos/gHi2hy7QUwgtRvcefvD/vgQZOVw/mGR9Q== Generated by Nova\n"
+-			}
+-		},
+-		{
+-			"keypair": {
+-				"fingerprint": "35:9d:d0:c3:4a:80:d3:d8:86:f1:ca:f7:df:c4:f9:d8",
+-				"name": "secondkey",
+-				"public_key": "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAAgQC9mC3WZN9UGLxgPBpP7H5jZMc6pKwOoSgre8yun6REFktn/Kz7DUt9jaR1UJyRzHxITfCfAIgSxPdGqB/oF1suMyWgu5i0625vavLB5z5kC8Hq3qZJ9zJO1poE1kyD+htiTtPWJ88e12xuH2XB/CZN9OpEiF98hAagiOE0EnOS5Q== Generated by Nova\n"
+-			}
+-		}
+-	]
+-}
+-`
 -
--9. Accepting Warranty or Additional Liability.
+-// GetOutput is a sample response to a Get call.
+-const GetOutput = `
+-{
+-	"keypair": {
+-		"public_key": "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAAgQC+Eo/RZRngaGTkFs7I62ZjsIlO79KklKbMXi8F+KITD4bVQHHn+kV+4gRgkgCRbdoDqoGfpaDFs877DYX9n4z6FrAIZ4PES8TNKhatifpn9NdQYWA+IkU8CuvlEKGuFpKRi/k7JLos/gHi2hy7QUwgtRvcefvD/vgQZOVw/mGR9Q== Generated by Nova\n",
+-		"name": "firstkey",
+-		"fingerprint": "15:b0:f8:b3:f9:48:63:71:cf:7b:5b:38:6d:44:2d:4a"
+-	}
+-}
+-`
 -
--While redistributing the Work or Derivative Works thereof, You may choose to
--offer, and charge a fee for, acceptance of support, warranty, indemnity, or
--other liability obligations and/or rights consistent with this License. However,
--in accepting such obligations, You may act only on Your own behalf and on Your
--sole responsibility, not on behalf of any other Contributor, and only if You
--agree to indemnify, defend, and hold each Contributor harmless for any liability
--incurred by, or claims asserted against, such Contributor by reason of your
--accepting any such warranty or additional liability.
+-// CreateOutput is a sample response to a Create call.
+-const CreateOutput = `
+-{
+-	"keypair": {
+-		"fingerprint": "35:9d:d0:c3:4a:80:d3:d8:86:f1:ca:f7:df:c4:f9:d8",
+-		"name": "createdkey",
+-		"private_key": "-----BEGIN RSA PRIVATE KEY-----\nMIICXAIBAAKBgQC9mC3WZN9UGLxgPBpP7H5jZMc6pKwOoSgre8yun6REFktn/Kz7\nDUt9jaR1UJyRzHxITfCfAIgSxPdGqB/oF1suMyWgu5i0625vavLB5z5kC8Hq3qZJ\n9zJO1poE1kyD+htiTtPWJ88e12xuH2XB/CZN9OpEiF98hAagiOE0EnOS5QIDAQAB\nAoGAE5XO1mDhORy9COvsg+kYPUhB1GsCYxh+v88wG7HeFDKBY6KUc/Kxo6yoGn5T\nTjRjekyi2KoDZHz4VlIzyZPwFS4I1bf3oCunVoAKzgLdmnTtvRNMC5jFOGc2vUgP\n9bSyRj3S1R4ClVk2g0IDeagko/jc8zzLEYuIK+fbkds79YECQQDt3vcevgegnkga\ntF4NsDmmBPRkcSHCqrANP/7vFcBQN3czxeYYWX3DK07alu6GhH1Y4sHbdm616uU0\nll7xbDzxAkEAzAtN2IyftNygV2EGiaGgqLyo/tD9+Vui2qCQplqe4jvWh/5Sparl\nOjmKo+uAW+hLrLVMnHzRWxbWU8hirH5FNQJATO+ZxCK4etXXAnQmG41NCAqANWB2\nB+2HJbH2NcQ2QHvAHUm741JGn/KI/aBlo7KEjFRDWUVUB5ji64BbUwCsMQJBAIku\nLGcjnBf/oLk+XSPZC2eGd2Ph5G5qYmH0Q2vkTx+wtTn3DV+eNsDfgMtWAJVJ5t61\ngU1QSXyhLPVlKpnnxuUCQC+xvvWjWtsLaFtAsZywJiqLxQzHts8XLGZptYJ5tLWV\nrtmYtBcJCN48RrgQHry/xWYeA4K/AFQpXfNPgprQ96Q=\n-----END RSA PRIVATE KEY-----\n",
+-		"public_key": "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAAgQC9mC3WZN9UGLxgPBpP7H5jZMc6pKwOoSgre8yun6REFktn/Kz7DUt9jaR1UJyRzHxITfCfAIgSxPdGqB/oF1suMyWgu5i0625vavLB5z5kC8Hq3qZJ9zJO1poE1kyD+htiTtPWJ88e12xuH2XB/CZN9OpEiF98hAagiOE0EnOS5Q== Generated by Nova\n",
+-		"user_id": "fake"
+-	}
+-}
+-`
 -
--END OF TERMS AND CONDITIONS
+-// ImportOutput is a sample response to a Create call that provides its own public key.
+-const ImportOutput = `
+-{
+-	"keypair": {
+-		"fingerprint": "1e:2c:9b:56:79:4b:45:77:f9:ca:7a:98:2c:b0:d5:3c",
+-		"name": "importedkey",
+-		"public_key": "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAAgQDx8nkQv/zgGgB4rMYmIf+6A4l6Rr+o/6lHBQdW5aYd44bd8JttDCE/F/pNRr0lRE+PiqSPO8nDPHw0010JeMH9gYgnnFlyY3/OcJ02RhIPyyxYpv9FhY+2YiUkpwFOcLImyrxEsYXpD/0d3ac30bNH6Sw9JD9UZHYcpSxsIbECHw== Generated by Nova",
+-		"user_id": "fake"
+-	}
+-}
+-`
 -
--APPENDIX: How to apply the Apache License to your work
+-// FirstKeyPair is the first result in ListOutput.
+-var FirstKeyPair = KeyPair{
+-	Name:        "firstkey",
+-	Fingerprint: "15:b0:f8:b3:f9:48:63:71:cf:7b:5b:38:6d:44:2d:4a",
+-	PublicKey:   "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAAgQC+Eo/RZRngaGTkFs7I62ZjsIlO79KklKbMXi8F+KITD4bVQHHn+kV+4gRgkgCRbdoDqoGfpaDFs877DYX9n4z6FrAIZ4PES8TNKhatifpn9NdQYWA+IkU8CuvlEKGuFpKRi/k7JLos/gHi2hy7QUwgtRvcefvD/vgQZOVw/mGR9Q== Generated by Nova\n",
+-}
 -
--To apply the Apache License to your work, attach the following boilerplate
--notice, with the fields enclosed by brackets "[]" replaced with your own
--identifying information. (Don't include the brackets!) The text should be
--enclosed in the appropriate comment syntax for the file format. We also
--recommend that a file or class name and description of purpose be included on
--the same "printed page" as the copyright notice for easier identification within
--third-party archives.
+-// SecondKeyPair is the second result in ListOutput.
+-var SecondKeyPair = KeyPair{
+-	Name:        "secondkey",
+-	Fingerprint: "35:9d:d0:c3:4a:80:d3:d8:86:f1:ca:f7:df:c4:f9:d8",
+-	PublicKey:   "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAAgQC9mC3WZN9UGLxgPBpP7H5jZMc6pKwOoSgre8yun6REFktn/Kz7DUt9jaR1UJyRzHxITfCfAIgSxPdGqB/oF1suMyWgu5i0625vavLB5z5kC8Hq3qZJ9zJO1poE1kyD+htiTtPWJ88e12xuH2XB/CZN9OpEiF98hAagiOE0EnOS5Q== Generated by Nova\n",
+-}
 -
--   Copyright [yyyy] [name of copyright owner]
+-// ExpectedKeyPairSlice is the slice of results that should be parsed from ListOutput, in the expected
+-// order.
+-var ExpectedKeyPairSlice = []KeyPair{FirstKeyPair, SecondKeyPair}
 -
--   Licensed under the Apache License, Version 2.0 (the "License");
--   you may not use this file except in compliance with the License.
--   You may obtain a copy of the License at
+-// CreatedKeyPair is the parsed result from CreatedOutput.
+-var CreatedKeyPair = KeyPair{
+-	Name:        "createdkey",
+-	Fingerprint: "35:9d:d0:c3:4a:80:d3:d8:86:f1:ca:f7:df:c4:f9:d8",
+-	PublicKey:   "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAAgQC9mC3WZN9UGLxgPBpP7H5jZMc6pKwOoSgre8yun6REFktn/Kz7DUt9jaR1UJyRzHxITfCfAIgSxPdGqB/oF1suMyWgu5i0625vavLB5z5kC8Hq3qZJ9zJO1poE1kyD+htiTtPWJ88e12xuH2XB/CZN9OpEiF98hAagiOE0EnOS5Q== Generated by Nova\n",
+-	PrivateKey:  "-----BEGIN RSA PRIVATE KEY-----\nMIICXAIBAAKBgQC9mC3WZN9UGLxgPBpP7H5jZMc6pKwOoSgre8yun6REFktn/Kz7\nDUt9jaR1UJyRzHxITfCfAIgSxPdGqB/oF1suMyWgu5i0625vavLB5z5kC8Hq3qZJ\n9zJO1poE1kyD+htiTtPWJ88e12xuH2XB/CZN9OpEiF98hAagiOE0EnOS5QIDAQAB\nAoGAE5XO1mDhORy9COvsg+kYPUhB1GsCYxh+v88wG7HeFDKBY6KUc/Kxo6yoGn5T\nTjRjekyi2KoDZHz4VlIzyZPwFS4I1bf3oCunVoAKzgLdmnTtvRNMC5jFOGc2vUgP\n9bSyRj3S1R4ClVk2g0IDeagko/jc8zzLEYuIK+fbkds79YECQQDt3vcevgegnkga\ntF4NsDmmBPRkcSHCqrANP/7vFcBQN3czxeYYWX3DK07alu6GhH1Y4sHbdm616uU0\nll7xbDzxAkEAzAtN2IyftNygV2EGiaGgqLyo/tD9+Vui2qCQplqe4jvWh/5Sparl\nOjmKo+uAW+hLrLVMnHzRWxbWU8hirH5FNQJATO+ZxCK4etXXAnQmG41NCAqANWB2\nB+2HJbH2NcQ2QHvAHUm741JGn/KI/aBlo7KEjFRDWUVUB5ji64BbUwCsMQJBAIku\nLGcjnBf/oLk+XSPZC2eGd2Ph5G5qYmH0Q2vkTx+wtTn3DV+eNsDfgMtWAJVJ5t61\ngU1QSXyhLPVlKpnnxuUCQC+xvvWjWtsLaFtAsZywJiqLxQzHts8XLGZptYJ5tLWV\nrtmYtBcJCN48RrgQHry/xWYeA4K/AFQpXfNPgprQ96Q=\n-----END RSA PRIVATE KEY-----\n",
+-	UserID:      "fake",
+-}
 -
--     http://www.apache.org/licenses/LICENSE-2.0
+-// ImportedKeyPair is the parsed result from ImportOutput.
+-var ImportedKeyPair = KeyPair{
+-	Name:        "importedkey",
+-	Fingerprint: "1e:2c:9b:56:79:4b:45:77:f9:ca:7a:98:2c:b0:d5:3c",
+-	PublicKey:   "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAAgQDx8nkQv/zgGgB4rMYmIf+6A4l6Rr+o/6lHBQdW5aYd44bd8JttDCE/F/pNRr0lRE+PiqSPO8nDPHw0010JeMH9gYgnnFlyY3/OcJ02RhIPyyxYpv9FhY+2YiUkpwFOcLImyrxEsYXpD/0d3ac30bNH6Sw9JD9UZHYcpSxsIbECHw== Generated by Nova",
+-	UserID:      "fake",
+-}
 -
--   Unless required by applicable law or agreed to in writing, software
--   distributed under the License is distributed on an "AS IS" BASIS,
--   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
--   See the License for the specific language governing permissions and
--   limitations under the License.
-diff --git a/Godeps/_workspace/src/github.com/golang/glog/README b/Godeps/_workspace/src/github.com/golang/glog/README
-deleted file mode 100644
-index 5f9c114..0000000
---- a/Godeps/_workspace/src/github.com/golang/glog/README
-+++ /dev/null
-@@ -1,44 +0,0 @@
--glog
--====
+-// HandleListSuccessfully configures the test server to respond to a List request.
+-func HandleListSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/os-keypairs", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
 -
--Leveled execution logs for Go.
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, ListOutput)
+-	})
+-}
 -
--This is an efficient pure Go implementation of leveled logs in the
--manner of the open source C++ package
--	http://code.google.com/p/google-glog
+-// HandleGetSuccessfully configures the test server to respond to a Get request for "firstkey".
+-func HandleGetSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/os-keypairs/firstkey", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
 -
--By binding methods to booleans it is possible to use the log package
--without paying the expense of evaluating the arguments to the log.
--Through the -vmodule flag, the package also provides fine-grained
--control over logging at the file level.
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, GetOutput)
+-	})
+-}
 -
--The comment from glog.go introduces the ideas:
+-// HandleCreateSuccessfully configures the test server to respond to a Create request for a new
+-// keypair called "createdkey".
+-func HandleCreateSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/os-keypairs", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-		th.TestJSONRequest(t, r, `{ "keypair": { "name": "createdkey" } }`)
 -
--	Package glog implements logging analogous to the Google-internal
--	C++ INFO/ERROR/V setup.  It provides functions Info, Warning,
--	Error, Fatal, plus formatting variants such as Infof. It
--	also provides V-style logging controlled by the -v and
--	-vmodule=file=2 flags.
--	
--	Basic examples:
--	
--		glog.Info("Prepare to repel boarders")
--	
--		glog.Fatalf("Initialization failed: %s", err)
--	
--	See the documentation for the V function for an explanation
--	of these examples:
--	
--		if glog.V(2) {
--			glog.Info("Starting transaction...")
--		}
--	
--		glog.V(2).Infoln("Processed", nItems, "elements")
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, CreateOutput)
+-	})
+-}
 -
+-// HandleImportSuccessfully configures the test server to respond to an Import request for an
+-// existing keypair called "importedkey".
+-func HandleImportSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/os-keypairs", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-		th.TestJSONRequest(t, r, `
+-			{
+-				"keypair": {
+-					"name": "importedkey",
+-					"public_key": "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAAgQDx8nkQv/zgGgB4rMYmIf+6A4l6Rr+o/6lHBQdW5aYd44bd8JttDCE/F/pNRr0lRE+PiqSPO8nDPHw0010JeMH9gYgnnFlyY3/OcJ02RhIPyyxYpv9FhY+2YiUkpwFOcLImyrxEsYXpD/0d3ac30bNH6Sw9JD9UZHYcpSxsIbECHw== Generated by Nova"
+-				}
+-			}
+-		`)
 -
--The repository contains an open source version of the log package
--used inside Google. The master copy of the source lives inside
--Google, not here. The code in this repo is for export only and is not itself
--under development. Feature requests will be ignored.
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, ImportOutput)
+-	})
+-}
 -
--Send bug reports to golang-nuts at googlegroups.com.
-diff --git a/Godeps/_workspace/src/github.com/golang/glog/glog.go b/Godeps/_workspace/src/github.com/golang/glog/glog.go
+-// HandleDeleteSuccessfully configures the test server to respond to a Delete request for a
+-// keypair called "deletedkey".
+-func HandleDeleteSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/os-keypairs/deletedkey", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-
+-		w.WriteHeader(http.StatusAccepted)
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/requests.go
 deleted file mode 100644
-index 3e63fff..0000000
---- a/Godeps/_workspace/src/github.com/golang/glog/glog.go
+index 7d1a2ac..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/requests.go
 +++ /dev/null
-@@ -1,1177 +0,0 @@
--// Go support for leveled logs, analogous to https://code.google.com/p/google-glog/
--//
--// Copyright 2013 Google Inc. All Rights Reserved.
--//
--// Licensed under the Apache License, Version 2.0 (the "License");
--// you may not use this file except in compliance with the License.
--// You may obtain a copy of the License at
--//
--//     http://www.apache.org/licenses/LICENSE-2.0
--//
--// Unless required by applicable law or agreed to in writing, software
--// distributed under the License is distributed on an "AS IS" BASIS,
--// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
--// See the License for the specific language governing permissions and
--// limitations under the License.
--
--// Package glog implements logging analogous to the Google-internal C++ INFO/ERROR/V setup.
--// It provides functions Info, Warning, Error, Fatal, plus formatting variants such as
--// Infof. It also provides V-style logging controlled by the -v and -vmodule=file=2 flags.
--//
--// Basic examples:
--//
--//	glog.Info("Prepare to repel boarders")
--//
--//	glog.Fatalf("Initialization failed: %s", err)
--//
--// See the documentation for the V function for an explanation of these examples:
--//
--//	if glog.V(2) {
--//		glog.Info("Starting transaction...")
--//	}
--//
--//	glog.V(2).Infoln("Processed", nItems, "elements")
--//
--// Log output is buffered and written periodically using Flush. Programs
--// should call Flush before exiting to guarantee all log output is written.
--//
--// By default, all log statements write to files in a temporary directory.
--// This package provides several flags that modify this behavior.
--// As a result, flag.Parse must be called before any logging is done.
--//
--//	-logtostderr=false
--//		Logs are written to standard error instead of to files.
--//	-alsologtostderr=false
--//		Logs are written to standard error as well as to files.
--//	-stderrthreshold=ERROR
--//		Log events at or above this severity are logged to standard
--//		error as well as to files.
--//	-log_dir=""
--//		Log files will be written to this directory instead of the
--//		default temporary directory.
--//
--//	Other flags provide aids to debugging.
--//
--//	-log_backtrace_at=""
--//		When set to a file and line number holding a logging statement,
--//		such as
--//			-log_backtrace_at=gopherflakes.go:234
--//		a stack trace will be written to the Info log whenever execution
--//		hits that statement. (Unlike with -vmodule, the ".go" must be
--//		present.)
--//	-v=0
--//		Enable V-leveled logging at the specified level.
--//	-vmodule=""
--//		The syntax of the argument is a comma-separated list of pattern=N,
--//		where pattern is a literal file name (minus the ".go" suffix) or
--//		"glob" pattern and N is a V level. For instance,
--//			-vmodule=gopher*=3
--//		sets the V level to 3 in all Go files whose names begin "gopher".
--//
--package glog
+@@ -1,88 +0,0 @@
+-package keypairs
 -
 -import (
--	"bufio"
--	"bytes"
 -	"errors"
--	"flag"
--	"fmt"
--	"io"
--	stdLog "log"
--	"os"
--	"path/filepath"
--	"runtime"
--	"strconv"
--	"strings"
--	"sync"
--	"sync/atomic"
--	"time"
--)
--
--// severity identifies the sort of log: info, warning etc. It also implements
--// the flag.Value interface. The -stderrthreshold flag is of type severity and
--// should be modified only through the flag.Value interface. The values match
--// the corresponding constants in C++.
--type severity int32 // sync/atomic int32
 -
--// These constants identify the log levels in order of increasing severity.
--// A message written to a high-severity log file is also written to each
--// lower-severity log file.
--const (
--	infoLog severity = iota
--	warningLog
--	errorLog
--	fatalLog
--	numSeverity = 4
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
 -)
 -
--const severityChar = "IWEF"
--
--var severityName = []string{
--	infoLog:    "INFO",
--	warningLog: "WARNING",
--	errorLog:   "ERROR",
--	fatalLog:   "FATAL",
+-// List returns a Pager that allows you to iterate over a collection of KeyPairs.
+-func List(client *gophercloud.ServiceClient) pagination.Pager {
+-	return pagination.NewPager(client, listURL(client), func(r pagination.PageResult) pagination.Page {
+-		return KeyPairPage{pagination.SinglePageBase(r)}
+-	})
 -}
 -
--// get returns the value of the severity.
--func (s *severity) get() severity {
--	return severity(atomic.LoadInt32((*int32)(s)))
+-// CreateOptsBuilder describes struct types that can be accepted by the Create call. Notable, the
+-// CreateOpts struct in this package does.
+-type CreateOptsBuilder interface {
+-	ToKeyPairCreateMap() (map[string]interface{}, error)
 -}
 -
--// set sets the value of the severity.
--func (s *severity) set(val severity) {
--	atomic.StoreInt32((*int32)(s), int32(val))
--}
+-// CreateOpts species keypair creation or import parameters.
+-type CreateOpts struct {
+-	// Name [required] is a friendly name to refer to this KeyPair in other services.
+-	Name string
 -
--// String is part of the flag.Value interface.
--func (s *severity) String() string {
--	return strconv.FormatInt(int64(*s), 10)
+-	// PublicKey [optional] is a pregenerated OpenSSH-formatted public key. If provided, this key
+-	// will be imported and no new key will be created.
+-	PublicKey string
 -}
 -
--// Get is part of the flag.Value interface.
--func (s *severity) Get() interface{} {
--	return *s
--}
+-// ToKeyPairCreateMap constructs a request body from CreateOpts.
+-func (opts CreateOpts) ToKeyPairCreateMap() (map[string]interface{}, error) {
+-	if opts.Name == "" {
+-		return nil, errors.New("Missing field required for keypair creation: Name")
+-	}
 -
--// Set is part of the flag.Value interface.
--func (s *severity) Set(value string) error {
--	var threshold severity
--	// Is it a known name?
--	if v, ok := severityByName(value); ok {
--		threshold = v
--	} else {
--		v, err := strconv.Atoi(value)
--		if err != nil {
--			return err
--		}
--		threshold = severity(v)
+-	keypair := make(map[string]interface{})
+-	keypair["name"] = opts.Name
+-	if opts.PublicKey != "" {
+-		keypair["public_key"] = opts.PublicKey
 -	}
--	logging.stderrThreshold.set(threshold)
--	return nil
+-
+-	return map[string]interface{}{"keypair": keypair}, nil
 -}
 -
--func severityByName(s string) (severity, bool) {
--	s = strings.ToUpper(s)
--	for i, name := range severityName {
--		if name == s {
--			return severity(i), true
--		}
+-// Create requests the creation of a new keypair on the server, or to import a pre-existing
+-// keypair.
+-func Create(client *gophercloud.ServiceClient, opts CreateOptsBuilder) CreateResult {
+-	var res CreateResult
+-
+-	reqBody, err := opts.ToKeyPairCreateMap()
+-	if err != nil {
+-		res.Err = err
+-		return res
 -	}
--	return 0, false
--}
 -
--// OutputStats tracks the number of output lines and bytes written.
--type OutputStats struct {
--	lines int64
--	bytes int64
+-	_, res.Err = perigee.Request("POST", createURL(client), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		ReqBody:     reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return res
 -}
 -
--// Lines returns the number of lines written.
--func (s *OutputStats) Lines() int64 {
--	return atomic.LoadInt64(&s.lines)
+-// Get returns public data about a previously uploaded KeyPair.
+-func Get(client *gophercloud.ServiceClient, name string) GetResult {
+-	var res GetResult
+-	_, res.Err = perigee.Request("GET", getURL(client, name), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return res
 -}
 -
--// Bytes returns the number of bytes written.
--func (s *OutputStats) Bytes() int64 {
--	return atomic.LoadInt64(&s.bytes)
+-// Delete requests the deletion of a previous stored KeyPair from the server.
+-func Delete(client *gophercloud.ServiceClient, name string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", deleteURL(client, name), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{202},
+-	})
+-	return res
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/requests_test.go
+deleted file mode 100644
+index 67d1833..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/requests_test.go
++++ /dev/null
+@@ -1,71 +0,0 @@
+-package keypairs
 -
--// Stats tracks the number of lines of output and number of bytes
--// per severity level. Values must be read with atomic.LoadInt64.
--var Stats struct {
--	Info, Warning, Error OutputStats
--}
+-import (
+-	"testing"
 -
--var severityStats = [numSeverity]*OutputStats{
--	infoLog:    &Stats.Info,
--	warningLog: &Stats.Warning,
--	errorLog:   &Stats.Error,
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
+-
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleListSuccessfully(t)
+-
+-	count := 0
+-	err := List(client.ServiceClient()).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractKeyPairs(page)
+-		th.AssertNoErr(t, err)
+-		th.CheckDeepEquals(t, ExpectedKeyPairSlice, actual)
+-
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, 1, count)
 -}
 -
--// Level is exported because it appears in the arguments to V and is
--// the type of the v flag, which can be set programmatically.
--// It's a distinct type because we want to discriminate it from logType.
--// Variables of type level are only changed under logging.mu.
--// The -v flag is read only with atomic ops, so the state of the logging
--// module is consistent.
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleCreateSuccessfully(t)
 -
--// Level is treated as a sync/atomic int32.
+-	actual, err := Create(client.ServiceClient(), CreateOpts{
+-		Name: "createdkey",
+-	}).Extract()
+-	th.AssertNoErr(t, err)
+-	th.CheckDeepEquals(t, &CreatedKeyPair, actual)
+-}
 -
--// Level specifies a level of verbosity for V logs. *Level implements
--// flag.Value; the -v flag is of type Level and should be modified
--// only through the flag.Value interface.
--type Level int32
+-func TestImport(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleImportSuccessfully(t)
 -
--// get returns the value of the Level.
--func (l *Level) get() Level {
--	return Level(atomic.LoadInt32((*int32)(l)))
+-	actual, err := Create(client.ServiceClient(), CreateOpts{
+-		Name:      "importedkey",
+-		PublicKey: "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAAgQDx8nkQv/zgGgB4rMYmIf+6A4l6Rr+o/6lHBQdW5aYd44bd8JttDCE/F/pNRr0lRE+PiqSPO8nDPHw0010JeMH9gYgnnFlyY3/OcJ02RhIPyyxYpv9FhY+2YiUkpwFOcLImyrxEsYXpD/0d3ac30bNH6Sw9JD9UZHYcpSxsIbECHw== Generated by Nova",
+-	}).Extract()
+-	th.AssertNoErr(t, err)
+-	th.CheckDeepEquals(t, &ImportedKeyPair, actual)
 -}
 -
--// set sets the value of the Level.
--func (l *Level) set(val Level) {
--	atomic.StoreInt32((*int32)(l), int32(val))
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleGetSuccessfully(t)
+-
+-	actual, err := Get(client.ServiceClient(), "firstkey").Extract()
+-	th.AssertNoErr(t, err)
+-	th.CheckDeepEquals(t, &FirstKeyPair, actual)
 -}
 -
--// String is part of the flag.Value interface.
--func (l *Level) String() string {
--	return strconv.FormatInt(int64(*l), 10)
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleDeleteSuccessfully(t)
+-
+-	err := Delete(client.ServiceClient(), "deletedkey").ExtractErr()
+-	th.AssertNoErr(t, err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/results.go
+deleted file mode 100644
+index f1a0d8e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/results.go
++++ /dev/null
+@@ -1,94 +0,0 @@
+-package keypairs
+-
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
+-
+-// KeyPair is an SSH key known to the OpenStack cluster that is available to be injected into
+-// servers.
+-type KeyPair struct {
+-	// Name is used to refer to this keypair from other services within this region.
+-	Name string `mapstructure:"name"`
 -
--// Get is part of the flag.Value interface.
--func (l *Level) Get() interface{} {
--	return *l
--}
+-	// Fingerprint is a short sequence of bytes that can be used to authenticate or validate a longer
+-	// public key.
+-	Fingerprint string `mapstructure:"fingerprint"`
 -
--// Set is part of the flag.Value interface.
--func (l *Level) Set(value string) error {
--	v, err := strconv.Atoi(value)
--	if err != nil {
--		return err
--	}
--	logging.mu.Lock()
--	defer logging.mu.Unlock()
--	logging.setVState(Level(v), logging.vmodule.filter, false)
--	return nil
+-	// PublicKey is the public key from this pair, in OpenSSH format. "ssh-rsa AAAAB3Nz..."
+-	PublicKey string `mapstructure:"public_key"`
+-
+-	// PrivateKey is the private key from this pair, in PEM format.
+-	// "-----BEGIN RSA PRIVATE KEY-----\nMIICXA..." It is only present if this keypair was just
+-	// returned from a Create call
+-	PrivateKey string `mapstructure:"private_key"`
+-
+-	// UserID is the user who owns this keypair.
+-	UserID string `mapstructure:"user_id"`
 -}
 -
--// moduleSpec represents the setting of the -vmodule flag.
--type moduleSpec struct {
--	filter []modulePat
+-// KeyPairPage stores a single, only page of KeyPair results from a List call.
+-type KeyPairPage struct {
+-	pagination.SinglePageBase
 -}
 -
--// modulePat contains a filter for the -vmodule flag.
--// It holds a verbosity level and a file pattern to match.
--type modulePat struct {
--	pattern string
--	literal bool // The pattern is a literal string
--	level   Level
+-// IsEmpty determines whether or not a KeyPairPage is empty.
+-func (page KeyPairPage) IsEmpty() (bool, error) {
+-	ks, err := ExtractKeyPairs(page)
+-	return len(ks) == 0, err
 -}
 -
--// match reports whether the file matches the pattern. It uses a string
--// comparison if the pattern contains no metacharacters.
--func (m *modulePat) match(file string) bool {
--	if m.literal {
--		return file == m.pattern
+-// ExtractKeyPairs interprets a page of results as a slice of KeyPairs.
+-func ExtractKeyPairs(page pagination.Page) ([]KeyPair, error) {
+-	type pair struct {
+-		KeyPair KeyPair `mapstructure:"keypair"`
 -	}
--	match, _ := filepath.Match(m.pattern, file)
--	return match
--}
 -
--func (m *moduleSpec) String() string {
--	// Lock because the type is not atomic. TODO: clean this up.
--	logging.mu.Lock()
--	defer logging.mu.Unlock()
--	var b bytes.Buffer
--	for i, f := range m.filter {
--		if i > 0 {
--			b.WriteRune(',')
--		}
--		fmt.Fprintf(&b, "%s=%d", f.pattern, f.level)
+-	var resp struct {
+-		KeyPairs []pair `mapstructure:"keypairs"`
 -	}
--	return b.String()
+-
+-	err := mapstructure.Decode(page.(KeyPairPage).Body, &resp)
+-	results := make([]KeyPair, len(resp.KeyPairs))
+-	for i, pair := range resp.KeyPairs {
+-		results[i] = pair.KeyPair
+-	}
+-	return results, err
 -}
 -
--// Get is part of the (Go 1.2)  flag.Getter interface. It always returns nil for this flag type since the
--// struct is not exported.
--func (m *moduleSpec) Get() interface{} {
--	return nil
+-type keyPairResult struct {
+-	gophercloud.Result
 -}
 -
--var errVmoduleSyntax = errors.New("syntax error: expect comma-separated list of filename=N")
+-// Extract is a method that attempts to interpret any KeyPair resource response as a KeyPair struct.
+-func (r keyPairResult) Extract() (*KeyPair, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
+-	}
 -
--// Syntax: -vmodule=recordio=2,file=1,gfs*=3
--func (m *moduleSpec) Set(value string) error {
--	var filter []modulePat
--	for _, pat := range strings.Split(value, ",") {
--		if len(pat) == 0 {
--			// Empty strings such as from a trailing comma can be ignored.
--			continue
--		}
--		patLev := strings.Split(pat, "=")
--		if len(patLev) != 2 || len(patLev[0]) == 0 || len(patLev[1]) == 0 {
--			return errVmoduleSyntax
--		}
--		pattern := patLev[0]
--		v, err := strconv.Atoi(patLev[1])
--		if err != nil {
--			return errors.New("syntax error: expect comma-separated list of filename=N")
--		}
--		if v < 0 {
--			return errors.New("negative value for vmodule level")
--		}
--		if v == 0 {
--			continue // Ignore. It's harmless but no point in paying the overhead.
--		}
--		// TODO: check syntax of filter?
--		filter = append(filter, modulePat{pattern, isLiteral(pattern), Level(v)})
+-	var res struct {
+-		KeyPair *KeyPair `json:"keypair" mapstructure:"keypair"`
 -	}
--	logging.mu.Lock()
--	defer logging.mu.Unlock()
--	logging.setVState(logging.verbosity, filter, true)
--	return nil
--}
 -
--// isLiteral reports whether the pattern is a literal string, that is, has no metacharacters
--// that require filepath.Match to be called to match the pattern.
--func isLiteral(pattern string) bool {
--	return !strings.ContainsAny(pattern, `\*?[]`)
+-	err := mapstructure.Decode(r.Body, &res)
+-	return res.KeyPair, err
 -}
 -
--// traceLocation represents the setting of the -log_backtrace_at flag.
--type traceLocation struct {
--	file string
--	line int
+-// CreateResult is the response from a Create operation. Call its Extract method to interpret it
+-// as a KeyPair.
+-type CreateResult struct {
+-	keyPairResult
 -}
 -
--// isSet reports whether the trace location has been specified.
--// logging.mu is held.
--func (t *traceLocation) isSet() bool {
--	return t.line > 0
+-// GetResult is the response from a Get operation. Call its Extract method to interpret it
+-// as a KeyPair.
+-type GetResult struct {
+-	keyPairResult
 -}
 -
--// match reports whether the specified file and line matches the trace location.
--// The argument file name is the full path, not the basename specified in the flag.
--// logging.mu is held.
--func (t *traceLocation) match(file string, line int) bool {
--	if t.line != line {
--		return false
--	}
--	if i := strings.LastIndex(file, "/"); i >= 0 {
--		file = file[i+1:]
--	}
--	return t.file == file
+-// DeleteResult is the response from a Delete operation. Call its Extract method to determine if
+-// the call succeeded or failed.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/urls.go
+deleted file mode 100644
+index 702f532..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/urls.go
++++ /dev/null
+@@ -1,25 +0,0 @@
+-package keypairs
 -
--func (t *traceLocation) String() string {
--	// Lock because the type is not atomic. TODO: clean this up.
--	logging.mu.Lock()
--	defer logging.mu.Unlock()
--	return fmt.Sprintf("%s:%d", t.file, t.line)
+-import "github.com/rackspace/gophercloud"
+-
+-const resourcePath = "os-keypairs"
+-
+-func resourceURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL(resourcePath)
 -}
 -
--// Get is part of the (Go 1.2) flag.Getter interface. It always returns nil for this flag type since the
--// struct is not exported
--func (t *traceLocation) Get() interface{} {
--	return nil
+-func listURL(c *gophercloud.ServiceClient) string {
+-	return resourceURL(c)
 -}
 -
--var errTraceSyntax = errors.New("syntax error: expect file.go:234")
+-func createURL(c *gophercloud.ServiceClient) string {
+-	return resourceURL(c)
+-}
 -
--// Syntax: -log_backtrace_at=gopherflakes.go:234
--// Note that unlike vmodule the file extension is included here.
--func (t *traceLocation) Set(value string) error {
--	if value == "" {
--		// Unset.
--		t.line = 0
--		t.file = ""
--	}
--	fields := strings.Split(value, ":")
--	if len(fields) != 2 {
--		return errTraceSyntax
--	}
--	file, line := fields[0], fields[1]
--	if !strings.Contains(file, ".") {
--		return errTraceSyntax
--	}
--	v, err := strconv.Atoi(line)
--	if err != nil {
--		return errTraceSyntax
--	}
--	if v <= 0 {
--		return errors.New("negative or zero value for level")
--	}
--	logging.mu.Lock()
--	defer logging.mu.Unlock()
--	t.line = v
--	t.file = file
--	return nil
+-func getURL(c *gophercloud.ServiceClient, name string) string {
+-	return c.ServiceURL(resourcePath, name)
 -}
 -
--// flushSyncWriter is the interface satisfied by logging destinations.
--type flushSyncWriter interface {
--	Flush() error
--	Sync() error
--	io.Writer
+-func deleteURL(c *gophercloud.ServiceClient, name string) string {
+-	return getURL(c, name)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/urls_test.go
+deleted file mode 100644
+index 60efd2a..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs/urls_test.go
++++ /dev/null
+@@ -1,40 +0,0 @@
+-package keypairs
 -
--func init() {
--	flag.BoolVar(&logging.toStderr, "logtostderr", false, "log to standard error instead of files")
--	flag.BoolVar(&logging.alsoToStderr, "alsologtostderr", false, "log to standard error as well as files")
--	flag.Var(&logging.verbosity, "v", "log level for V logs")
--	flag.Var(&logging.stderrThreshold, "stderrthreshold", "logs at or above this threshold go to stderr")
--	flag.Var(&logging.vmodule, "vmodule", "comma-separated list of pattern=N settings for file-filtered logging")
--	flag.Var(&logging.traceLocation, "log_backtrace_at", "when logging hits line file:N, emit a stack trace")
+-import (
+-	"testing"
 -
--	// Default stderrThreshold is ERROR.
--	logging.stderrThreshold = errorLog
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--	logging.setVState(0, nil, false)
--	go logging.flushDaemon()
+-func TestListURL(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	c := client.ServiceClient()
+-
+-	th.CheckEquals(t, c.Endpoint+"os-keypairs", listURL(c))
 -}
 -
--// Flush flushes all pending log I/O.
--func Flush() {
--	logging.lockAndFlushAll()
+-func TestCreateURL(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	c := client.ServiceClient()
+-
+-	th.CheckEquals(t, c.Endpoint+"os-keypairs", createURL(c))
 -}
 -
--// loggingT collects all the global state of the logging setup.
--type loggingT struct {
--	// Boolean flags. Not handled atomically because the flag.Value interface
--	// does not let us avoid the =true, and that shorthand is necessary for
--	// compatibility. TODO: does this matter enough to fix? Seems unlikely.
--	toStderr     bool // The -logtostderr flag.
--	alsoToStderr bool // The -alsologtostderr flag.
+-func TestGetURL(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	c := client.ServiceClient()
 -
--	// Level flag. Handled atomically.
--	stderrThreshold severity // The -stderrthreshold flag.
+-	th.CheckEquals(t, c.Endpoint+"os-keypairs/wat", getURL(c, "wat"))
+-}
 -
--	// freeList is a list of byte buffers, maintained under freeListMu.
--	freeList *buffer
--	// freeListMu maintains the free list. It is separate from the main mutex
--	// so buffers can be grabbed and printed to without holding the main lock,
--	// for better parallelization.
--	freeListMu sync.Mutex
+-func TestDeleteURL(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	c := client.ServiceClient()
 -
--	// mu protects the remaining elements of this structure and is
--	// used to synchronize logging.
--	mu sync.Mutex
--	// file holds writer for each of the log types.
--	file [numSeverity]flushSyncWriter
--	// pcs is used in V to avoid an allocation when computing the caller's PC.
--	pcs [1]uintptr
--	// vmap is a cache of the V Level for each V() call site, identified by PC.
--	// It is wiped whenever the vmodule flag changes state.
--	vmap map[uintptr]Level
--	// filterLength stores the length of the vmodule filter chain. If greater
--	// than zero, it means vmodule is enabled. It may be read safely
--	// using sync.LoadInt32, but is only modified under mu.
--	filterLength int32
--	// traceLocation is the state of the -log_backtrace_at flag.
--	traceLocation traceLocation
--	// These flags are modified only under lock, although verbosity may be fetched
--	// safely using atomic.LoadInt32.
--	vmodule   moduleSpec // The state of the -vmodule flag.
--	verbosity Level      // V logging level, the value of the -v flag/
+-	th.CheckEquals(t, c.Endpoint+"os-keypairs/wat", deleteURL(c, "wat"))
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/doc.go
+deleted file mode 100644
+index 5822e1b..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/doc.go
++++ /dev/null
+@@ -1,7 +0,0 @@
+-// Package flavors provides information and interaction with the flavor API
+-// resource in the OpenStack Compute service.
+-//
+-// A flavor is an available hardware configuration for a server. Each flavor
+-// has a unique combination of disk space, memory capacity and priority for CPU
+-// time.
+-package flavors
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/requests.go
+deleted file mode 100644
+index 065a2ec..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/requests.go
++++ /dev/null
+@@ -1,72 +0,0 @@
+-package flavors
 -
--// buffer holds a byte Buffer for reuse. The zero value is ready for use.
--type buffer struct {
--	bytes.Buffer
--	tmp  [64]byte // temporary byte array for creating headers.
--	next *buffer
+-import (
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
+-
+-// ListOptsBuilder allows extensions to add additional parameters to the
+-// List request.
+-type ListOptsBuilder interface {
+-	ToFlavorListQuery() (string, error)
 -}
 -
--var logging loggingT
+-// ListOpts helps control the results returned by the List() function.
+-// For example, a flavor with a minDisk field of 10 will not be returned if you specify MinDisk set to 20.
+-// Typically, software will use the last ID of the previous call to List to set the Marker for the current call.
+-type ListOpts struct {
 -
--// setVState sets a consistent state for V logging.
--// l.mu is held.
--func (l *loggingT) setVState(verbosity Level, filter []modulePat, setFilter bool) {
--	// Turn verbosity off so V will not fire while we are in transition.
--	logging.verbosity.set(0)
--	// Ditto for filter length.
--	atomic.StoreInt32(&logging.filterLength, 0)
+-	// ChangesSince, if provided, instructs List to return only those things which have changed since the timestamp provided.
+-	ChangesSince string `q:"changes-since"`
 -
--	// Set the new filters and wipe the pc->Level map if the filter has changed.
--	if setFilter {
--		logging.vmodule.filter = filter
--		logging.vmap = make(map[uintptr]Level)
--	}
+-	// MinDisk and MinRAM, if provided, elides flavors which do not meet your criteria.
+-	MinDisk int `q:"minDisk"`
+-	MinRAM  int `q:"minRam"`
 -
--	// Things are consistent now, so enable filtering and verbosity.
--	// They are enabled in order opposite to that in V.
--	atomic.StoreInt32(&logging.filterLength, int32(len(filter)))
--	logging.verbosity.set(verbosity)
+-	// Marker and Limit control paging.
+-	// Marker instructs List where to start listing from.
+-	Marker string `q:"marker"`
+-
+-	// Limit instructs List to refrain from sending excessively large lists of flavors.
+-	Limit int `q:"limit"`
 -}
 -
--// getBuffer returns a new, ready-to-use buffer.
--func (l *loggingT) getBuffer() *buffer {
--	l.freeListMu.Lock()
--	b := l.freeList
--	if b != nil {
--		l.freeList = b.next
--	}
--	l.freeListMu.Unlock()
--	if b == nil {
--		b = new(buffer)
--	} else {
--		b.next = nil
--		b.Reset()
+-// ToFlavorListQuery formats a ListOpts into a query string.
+-func (opts ListOpts) ToFlavorListQuery() (string, error) {
+-	q, err := gophercloud.BuildQueryString(opts)
+-	if err != nil {
+-		return "", err
 -	}
--	return b
+-	return q.String(), nil
 -}
 -
--// putBuffer returns a buffer to the free list.
--func (l *loggingT) putBuffer(b *buffer) {
--	if b.Len() >= 256 {
--		// Let big buffers die a natural death.
--		return
+-// ListDetail instructs OpenStack to provide a list of flavors.
+-// You may provide criteria by which List curtails its results for easier processing.
+-// See ListOpts for more details.
+-func ListDetail(client *gophercloud.ServiceClient, opts ListOptsBuilder) pagination.Pager {
+-	url := listURL(client)
+-	if opts != nil {
+-		query, err := opts.ToFlavorListQuery()
+-		if err != nil {
+-			return pagination.Pager{Err: err}
+-		}
+-		url += query
 -	}
--	l.freeListMu.Lock()
--	b.next = l.freeList
--	l.freeList = b
--	l.freeListMu.Unlock()
+-	createPage := func(r pagination.PageResult) pagination.Page {
+-		return FlavorPage{pagination.LinkedPageBase{PageResult: r}}
+-	}
+-
+-	return pagination.NewPager(client, url, createPage)
 -}
 -
--var timeNow = time.Now // Stubbed out for testing.
+-// Get instructs OpenStack to provide details on a single flavor, identified by its ID.
+-// Use ExtractFlavor to convert its result into a Flavor.
+-func Get(client *gophercloud.ServiceClient, id string) GetResult {
+-	var gr GetResult
+-	gr.Err = perigee.Get(getURL(client, id), perigee.Options{
+-		Results:     &gr.Body,
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-	})
+-	return gr
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/requests_test.go
+deleted file mode 100644
+index fbd7c33..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/requests_test.go
++++ /dev/null
+@@ -1,129 +0,0 @@
+-package flavors
 -
--/*
--header formats a log header as defined by the C++ implementation.
--It returns a buffer containing the formatted header and the user's file and line number.
--The depth specifies how many stack frames above lives the source line to be identified in the log message.
+-import (
+-	"fmt"
+-	"net/http"
+-	"reflect"
+-	"testing"
 -
--Log lines have this form:
--	Lmmdd hh:mm:ss.uuuuuu threadid file:line] msg...
--where the fields are defined as follows:
--	L                A single character, representing the log level (eg 'I' for INFO)
--	mm               The month (zero padded; ie May is '05')
--	dd               The day (zero padded)
--	hh:mm:ss.uuuuuu  Time in hours, minutes and fractional seconds
--	threadid         The space-padded thread ID as returned by GetTID()
--	file             The file name
--	line             The line number
--	msg              The user-supplied message
--*/
--func (l *loggingT) header(s severity, depth int) (*buffer, string, int) {
--	_, file, line, ok := runtime.Caller(3 + depth)
--	if !ok {
--		file = "???"
--		line = 1
--	} else {
--		slash := strings.LastIndex(file, "/")
--		if slash >= 0 {
--			file = file[slash+1:]
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
+-
+-const tokenID = "blerb"
+-
+-func TestListFlavors(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/flavors/detail", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		r.ParseForm()
+-		marker := r.Form.Get("marker")
+-		switch marker {
+-		case "":
+-			fmt.Fprintf(w, `
+-					{
+-						"flavors": [
+-							{
+-								"id": "1",
+-								"name": "m1.tiny",
+-								"disk": 1,
+-								"ram": 512,
+-								"vcpus": 1
+-							},
+-							{
+-								"id": "2",
+-								"name": "m2.small",
+-								"disk": 10,
+-								"ram": 1024,
+-								"vcpus": 2
+-							}
+-						],
+-						"flavors_links": [
+-							{
+-								"href": "%s/flavors/detail?marker=2",
+-								"rel": "next"
+-							}
+-						]
+-					}
+-				`, th.Server.URL)
+-		case "2":
+-			fmt.Fprintf(w, `{ "flavors": [] }`)
+-		default:
+-			t.Fatalf("Unexpected marker: [%s]", marker)
+-		}
+-	})
+-
+-	pages := 0
+-	err := ListDetail(fake.ServiceClient(), nil).EachPage(func(page pagination.Page) (bool, error) {
+-		pages++
+-
+-		actual, err := ExtractFlavors(page)
+-		if err != nil {
+-			return false, err
+-		}
+-
+-		expected := []Flavor{
+-			Flavor{ID: "1", Name: "m1.tiny", Disk: 1, RAM: 512, VCPUs: 1},
+-			Flavor{ID: "2", Name: "m2.small", Disk: 10, RAM: 1024, VCPUs: 2},
+-		}
+-
+-		if !reflect.DeepEqual(expected, actual) {
+-			t.Errorf("Expected %#v, but was %#v", expected, actual)
 -		}
+-
+-		return true, nil
+-	})
+-	if err != nil {
+-		t.Fatal(err)
+-	}
+-	if pages != 1 {
+-		t.Errorf("Expected one page, got %d", pages)
 -	}
--	return l.formatHeader(s, file, line), file, line
 -}
 -
--// formatHeader formats a log header using the provided file name and line number.
--func (l *loggingT) formatHeader(s severity, file string, line int) *buffer {
--	now := timeNow()
--	if line < 0 {
--		line = 0 // not a real line number, but acceptable to someDigits
--	}
--	if s > fatalLog {
--		s = infoLog // for safety.
+-func TestGetFlavor(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/flavors/12345", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, `
+-			{
+-				"flavor": {
+-					"id": "1",
+-					"name": "m1.tiny",
+-					"disk": 1,
+-					"ram": 512,
+-					"vcpus": 1,
+-					"rxtx_factor": 1
+-				}
+-			}
+-		`)
+-	})
+-
+-	actual, err := Get(fake.ServiceClient(), "12345").Extract()
+-	if err != nil {
+-		t.Fatalf("Unable to get flavor: %v", err)
 -	}
--	buf := l.getBuffer()
 -
--	// Avoid Fprintf, for speed. The format is so simple that we can do it quickly by hand.
--	// It's worth about 3X. Fprintf is hard.
--	_, month, day := now.Date()
--	hour, minute, second := now.Clock()
--	// Lmmdd hh:mm:ss.uuuuuu threadid file:line]
--	buf.tmp[0] = severityChar[s]
--	buf.twoDigits(1, int(month))
--	buf.twoDigits(3, day)
--	buf.tmp[5] = ' '
--	buf.twoDigits(6, hour)
--	buf.tmp[8] = ':'
--	buf.twoDigits(9, minute)
--	buf.tmp[11] = ':'
--	buf.twoDigits(12, second)
--	buf.tmp[14] = '.'
--	buf.nDigits(6, 15, now.Nanosecond()/1000, '0')
--	buf.tmp[21] = ' '
--	buf.nDigits(7, 22, pid, ' ') // TODO: should be TID
--	buf.tmp[29] = ' '
--	buf.Write(buf.tmp[:30])
--	buf.WriteString(file)
--	buf.tmp[0] = ':'
--	n := buf.someDigits(1, line)
--	buf.tmp[n+1] = ']'
--	buf.tmp[n+2] = ' '
--	buf.Write(buf.tmp[:n+3])
--	return buf
+-	expected := &Flavor{
+-		ID:         "1",
+-		Name:       "m1.tiny",
+-		Disk:       1,
+-		RAM:        512,
+-		VCPUs:      1,
+-		RxTxFactor: 1,
+-	}
+-	if !reflect.DeepEqual(expected, actual) {
+-		t.Errorf("Expected %#v, but was %#v", expected, actual)
+-	}
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/results.go
+deleted file mode 100644
+index 8dddd70..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/results.go
++++ /dev/null
+@@ -1,122 +0,0 @@
+-package flavors
 -
--// Some custom tiny helper functions to print the log header efficiently.
+-import (
+-	"errors"
+-	"reflect"
 -
--const digits = "0123456789"
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--// twoDigits formats a zero-prefixed two-digit integer at buf.tmp[i].
--func (buf *buffer) twoDigits(i, d int) {
--	buf.tmp[i+1] = digits[d%10]
--	d /= 10
--	buf.tmp[i] = digits[d%10]
+-// ErrCannotInterpret is returned by an Extract call if the response body doesn't have the expected structure.
+-var ErrCannotInterpet = errors.New("Unable to interpret a response body.")
+-
+-// GetResult temporarily holds the response from a Get call.
+-type GetResult struct {
+-	gophercloud.Result
 -}
 -
--// nDigits formats an n-digit integer at buf.tmp[i],
--// padding with pad on the left.
--// It assumes d >= 0.
--func (buf *buffer) nDigits(n, i, d int, pad byte) {
--	j := n - 1
--	for ; j >= 0 && d > 0; j-- {
--		buf.tmp[i+j] = digits[d%10]
--		d /= 10
+-// Extract provides access to the individual Flavor returned by the Get function.
+-func (gr GetResult) Extract() (*Flavor, error) {
+-	if gr.Err != nil {
+-		return nil, gr.Err
 -	}
--	for ; j >= 0; j-- {
--		buf.tmp[i+j] = pad
+-
+-	var result struct {
+-		Flavor Flavor `mapstructure:"flavor"`
 -	}
--}
 -
--// someDigits formats a zero-prefixed variable-width integer at buf.tmp[i].
--func (buf *buffer) someDigits(i, d int) int {
--	// Print into the top, then copy down. We know there's space for at least
--	// a 10-digit number.
--	j := len(buf.tmp)
--	for {
--		j--
--		buf.tmp[j] = digits[d%10]
--		d /= 10
--		if d == 0 {
--			break
--		}
+-	cfg := &mapstructure.DecoderConfig{
+-		DecodeHook: defaulter,
+-		Result:     &result,
 -	}
--	return copy(buf.tmp[i:], buf.tmp[j:])
+-	decoder, err := mapstructure.NewDecoder(cfg)
+-	if err != nil {
+-		return nil, err
+-	}
+-	err = decoder.Decode(gr.Body)
+-	return &result.Flavor, err
 -}
 -
--func (l *loggingT) println(s severity, args ...interface{}) {
--	buf, file, line := l.header(s, 0)
--	fmt.Fprintln(buf, args...)
--	l.output(s, buf, file, line, false)
+-// Flavor records represent (virtual) hardware configurations for server resources in a region.
+-type Flavor struct {
+-	// The Id field contains the flavor's unique identifier.
+-	// For example, this identifier will be useful when specifying which hardware configuration to use for a new server instance.
+-	ID string `mapstructure:"id"`
+-
+-	// The Disk and RA< fields provide a measure of storage space offered by the flavor, in GB and MB, respectively.
+-	Disk int `mapstructure:"disk"`
+-	RAM  int `mapstructure:"ram"`
+-
+-	// The Name field provides a human-readable moniker for the flavor.
+-	Name string `mapstructure:"name"`
+-
+-	RxTxFactor float64 `mapstructure:"rxtx_factor"`
+-
+-	// Swap indicates how much space is reserved for swap.
+-	// If not provided, this field will be set to 0.
+-	Swap int `mapstructure:"swap"`
+-
+-	// VCPUs indicates how many (virtual) CPUs are available for this flavor.
+-	VCPUs int `mapstructure:"vcpus"`
 -}
 -
--func (l *loggingT) print(s severity, args ...interface{}) {
--	l.printDepth(s, 1, args...)
+-// FlavorPage contains a single page of the response from a List call.
+-type FlavorPage struct {
+-	pagination.LinkedPageBase
 -}
 -
--func (l *loggingT) printDepth(s severity, depth int, args ...interface{}) {
--	buf, file, line := l.header(s, depth)
--	fmt.Fprint(buf, args...)
--	if buf.Bytes()[buf.Len()-1] != '\n' {
--		buf.WriteByte('\n')
+-// IsEmpty determines if a page contains any results.
+-func (p FlavorPage) IsEmpty() (bool, error) {
+-	flavors, err := ExtractFlavors(p)
+-	if err != nil {
+-		return true, err
 -	}
--	l.output(s, buf, file, line, false)
+-	return len(flavors) == 0, nil
 -}
 -
--func (l *loggingT) printf(s severity, format string, args ...interface{}) {
--	buf, file, line := l.header(s, 0)
--	fmt.Fprintf(buf, format, args...)
--	if buf.Bytes()[buf.Len()-1] != '\n' {
--		buf.WriteByte('\n')
+-// NextPageURL uses the response's embedded link reference to navigate to the next page of results.
+-func (p FlavorPage) NextPageURL() (string, error) {
+-	type resp struct {
+-		Links []gophercloud.Link `mapstructure:"flavors_links"`
 -	}
--	l.output(s, buf, file, line, false)
+-
+-	var r resp
+-	err := mapstructure.Decode(p.Body, &r)
+-	if err != nil {
+-		return "", err
+-	}
+-
+-	return gophercloud.ExtractNextURL(r.Links)
 -}
 -
--// printWithFileLine behaves like print but uses the provided file and line number.  If
--// alsoLogToStderr is true, the log message always appears on standard error; it
--// will also appear in the log file unless --logtostderr is set.
--func (l *loggingT) printWithFileLine(s severity, file string, line int, alsoToStderr bool, args ...interface{}) {
--	buf := l.formatHeader(s, file, line)
--	fmt.Fprint(buf, args...)
--	if buf.Bytes()[buf.Len()-1] != '\n' {
--		buf.WriteByte('\n')
+-func defaulter(from, to reflect.Kind, v interface{}) (interface{}, error) {
+-	if (from == reflect.String) && (to == reflect.Int) {
+-		return 0, nil
 -	}
--	l.output(s, buf, file, line, alsoToStderr)
+-	return v, nil
 -}
 -
--// output writes the data to the log files and releases the buffer.
--func (l *loggingT) output(s severity, buf *buffer, file string, line int, alsoToStderr bool) {
--	l.mu.Lock()
--	if l.traceLocation.isSet() {
--		if l.traceLocation.match(file, line) {
--			buf.Write(stacks(false))
--		}
+-// ExtractFlavors provides access to the list of flavors in a page acquired from the List operation.
+-func ExtractFlavors(page pagination.Page) ([]Flavor, error) {
+-	casted := page.(FlavorPage).Body
+-	var container struct {
+-		Flavors []Flavor `mapstructure:"flavors"`
 -	}
--	data := buf.Bytes()
--	if l.toStderr {
--		os.Stderr.Write(data)
--	} else {
--		if alsoToStderr || l.alsoToStderr || s >= l.stderrThreshold.get() {
--			os.Stderr.Write(data)
--		}
--		if l.file[s] == nil {
--			if err := l.createFiles(s); err != nil {
--				os.Stderr.Write(data) // Make sure the message appears somewhere.
--				l.exit(err)
--			}
--		}
--		switch s {
--		case fatalLog:
--			l.file[fatalLog].Write(data)
--			fallthrough
--		case errorLog:
--			l.file[errorLog].Write(data)
--			fallthrough
--		case warningLog:
--			l.file[warningLog].Write(data)
--			fallthrough
--		case infoLog:
--			l.file[infoLog].Write(data)
--		}
+-
+-	cfg := &mapstructure.DecoderConfig{
+-		DecodeHook: defaulter,
+-		Result:     &container,
 -	}
--	if s == fatalLog {
--		// If we got here via Exit rather than Fatal, print no stacks.
--		if atomic.LoadUint32(&fatalNoStacks) > 0 {
--			l.mu.Unlock()
--			timeoutFlush(10 * time.Second)
--			os.Exit(1)
--		}
--		// Dump all goroutine stacks before exiting.
--		// First, make sure we see the trace for the current goroutine on standard error.
--		// If -logtostderr has been specified, the loop below will do that anyway
--		// as the first stack in the full dump.
--		if !l.toStderr {
--			os.Stderr.Write(stacks(false))
--		}
--		// Write the stack trace for all goroutines to the files.
--		trace := stacks(true)
--		logExitFunc = func(error) {} // If we get a write error, we'll still exit below.
--		for log := fatalLog; log >= infoLog; log-- {
--			if f := l.file[log]; f != nil { // Can be nil if -logtostderr is set.
--				f.Write(trace)
--			}
--		}
--		l.mu.Unlock()
--		timeoutFlush(10 * time.Second)
--		os.Exit(255) // C++ uses -1, which is silly because it's anded with 255 anyway.
+-	decoder, err := mapstructure.NewDecoder(cfg)
+-	if err != nil {
+-		return container.Flavors, err
 -	}
--	l.putBuffer(buf)
--	l.mu.Unlock()
--	if stats := severityStats[s]; stats != nil {
--		atomic.AddInt64(&stats.lines, 1)
--		atomic.AddInt64(&stats.bytes, int64(len(data)))
+-	err = decoder.Decode(casted)
+-	if err != nil {
+-		return container.Flavors, err
 -	}
+-
+-	return container.Flavors, nil
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/urls.go
+deleted file mode 100644
+index 683c107..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/urls.go
++++ /dev/null
+@@ -1,13 +0,0 @@
+-package flavors
 -
--// timeoutFlush calls Flush and returns when it completes or after timeout
--// elapses, whichever happens first.  This is needed because the hooks invoked
--// by Flush may deadlock when glog.Fatal is called from a hook that holds
--// a lock.
--func timeoutFlush(timeout time.Duration) {
--	done := make(chan bool, 1)
--	go func() {
--		Flush() // calls logging.lockAndFlushAll()
--		done <- true
--	}()
--	select {
--	case <-done:
--	case <-time.After(timeout):
--		fmt.Fprintln(os.Stderr, "glog: Flush took longer than", timeout)
--	}
+-import (
+-	"github.com/rackspace/gophercloud"
+-)
+-
+-func getURL(client *gophercloud.ServiceClient, id string) string {
+-	return client.ServiceURL("flavors", id)
 -}
 -
--// stacks is a wrapper for runtime.Stack that attempts to recover the data for all goroutines.
--func stacks(all bool) []byte {
--	// We don't know how big the traces are, so grow a few times if they don't fit. Start large, though.
--	n := 10000
--	if all {
--		n = 100000
--	}
--	var trace []byte
--	for i := 0; i < 5; i++ {
--		trace = make([]byte, n)
--		nbytes := runtime.Stack(trace, all)
--		if nbytes < len(trace) {
--			return trace[:nbytes]
--		}
--		n *= 2
--	}
--	return trace
+-func listURL(client *gophercloud.ServiceClient) string {
+-	return client.ServiceURL("flavors", "detail")
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/urls_test.go
+deleted file mode 100644
+index 069da24..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/flavors/urls_test.go
++++ /dev/null
+@@ -1,26 +0,0 @@
+-package flavors
 -
--// logExitFunc provides a simple mechanism to override the default behavior
--// of exiting on error. Used in testing and to guarantee we reach a required exit
--// for fatal logs. Instead, exit could be a function rather than a method but that
--// would make its use clumsier.
--var logExitFunc func(error)
+-import (
+-	"testing"
 -
--// exit is called if there is trouble creating or writing log files.
--// It flushes the logs and exits the program; there's no point in hanging around.
--// l.mu is held.
--func (l *loggingT) exit(err error) {
--	fmt.Fprintf(os.Stderr, "log: exiting because of error: %s\n", err)
--	// If logExitFunc is set, we do that instead of exiting.
--	if logExitFunc != nil {
--		logExitFunc(err)
--		return
--	}
--	l.flushAll()
--	os.Exit(2)
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-const endpoint = "http://localhost:57909/"
+-
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint}
 -}
 -
--// syncBuffer joins a bufio.Writer to its underlying file, providing access to the
--// file's Sync method and providing a wrapper for the Write method that provides log
--// file rotation. There are conflicting methods, so the file cannot be embedded.
--// l.mu is held for all its methods.
--type syncBuffer struct {
--	logger *loggingT
--	*bufio.Writer
--	file   *os.File
--	sev    severity
--	nbytes uint64 // The number of bytes written to this file
+-func TestGetURL(t *testing.T) {
+-	actual := getURL(endpointClient(), "foo")
+-	expected := endpoint + "flavors/foo"
+-	th.CheckEquals(t, expected, actual)
 -}
 -
--func (sb *syncBuffer) Sync() error {
--	return sb.file.Sync()
+-func TestListURL(t *testing.T) {
+-	actual := listURL(endpointClient())
+-	expected := endpoint + "flavors/detail"
+-	th.CheckEquals(t, expected, actual)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/doc.go
+deleted file mode 100644
+index 0edaa3f..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/doc.go
++++ /dev/null
+@@ -1,7 +0,0 @@
+-// Package images provides information and interaction with the image API
+-// resource in the OpenStack Compute service.
+-//
+-// An image is a collection of files used to create or rebuild a server.
+-// Operators provide a number of pre-built OS images by default. You may also
+-// create custom images from cloud servers you have launched.
+-package images
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/requests.go
+deleted file mode 100644
+index bc61ddb..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/requests.go
++++ /dev/null
+@@ -1,71 +0,0 @@
+-package images
 -
--func (sb *syncBuffer) Write(p []byte) (n int, err error) {
--	if sb.nbytes+uint64(len(p)) >= MaxSize {
--		if err := sb.rotateFile(time.Now()); err != nil {
--			sb.logger.exit(err)
--		}
--	}
--	n, err = sb.Writer.Write(p)
--	sb.nbytes += uint64(n)
+-import (
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-
+-	"github.com/racker/perigee"
+-)
+-
+-// ListOptsBuilder allows extensions to add additional parameters to the
+-// List request.
+-type ListOptsBuilder interface {
+-	ToImageListQuery() (string, error)
+-}
+-
+-// ListOpts contain options for limiting the number of Images returned from a call to ListDetail.
+-type ListOpts struct {
+-	// When the image last changed status (in date-time format).
+-	ChangesSince string `q:"changes-since"`
+-	// The number of Images to return.
+-	Limit int `q:"limit"`
+-	// UUID of the Image at which to set a marker.
+-	Marker string `q:"marker"`
+-	// The name of the Image.
+-	Name string `q:"name:"`
+-	// The name of the Server (in URL format).
+-	Server string `q:"server"`
+-	// The current status of the Image.
+-	Status string `q:"status"`
+-	// The value of the type of image (e.g. BASE, SERVER, ALL)
+-	Type string `q:"type"`
+-}
+-
+-// ToImageListQuery formats a ListOpts into a query string.
+-func (opts ListOpts) ToImageListQuery() (string, error) {
+-	q, err := gophercloud.BuildQueryString(opts)
 -	if err != nil {
--		sb.logger.exit(err)
+-		return "", err
 -	}
--	return
+-	return q.String(), nil
 -}
 -
--// rotateFile closes the syncBuffer's file and starts a new one.
--func (sb *syncBuffer) rotateFile(now time.Time) error {
--	if sb.file != nil {
--		sb.Flush()
--		sb.file.Close()
+-// ListDetail enumerates the available images.
+-func ListDetail(client *gophercloud.ServiceClient, opts ListOptsBuilder) pagination.Pager {
+-	url := listDetailURL(client)
+-	if opts != nil {
+-		query, err := opts.ToImageListQuery()
+-		if err != nil {
+-			return pagination.Pager{Err: err}
+-		}
+-		url += query
 -	}
--	var err error
--	sb.file, _, err = create(severityName[sb.sev], now)
--	sb.nbytes = 0
--	if err != nil {
--		return err
+-
+-	createPage := func(r pagination.PageResult) pagination.Page {
+-		return ImagePage{pagination.LinkedPageBase{PageResult: r}}
 -	}
 -
--	sb.Writer = bufio.NewWriterSize(sb.file, bufferSize)
+-	return pagination.NewPager(client, url, createPage)
+-}
 -
--	// Write header.
--	var buf bytes.Buffer
--	fmt.Fprintf(&buf, "Log file created at: %s\n", now.Format("2006/01/02 15:04:05"))
--	fmt.Fprintf(&buf, "Running on machine: %s\n", host)
--	fmt.Fprintf(&buf, "Binary: Built with %s %s for %s/%s\n", runtime.Compiler, runtime.Version(), runtime.GOOS, runtime.GOARCH)
--	fmt.Fprintf(&buf, "Log line format: [IWEF]mmdd hh:mm:ss.uuuuuu threadid file:line] msg\n")
--	n, err := sb.file.Write(buf.Bytes())
--	sb.nbytes += uint64(n)
--	return err
+-// Get acquires additional detail about a specific image by ID.
+-// Use ExtractImage() to interpret the result as an openstack Image.
+-func Get(client *gophercloud.ServiceClient, id string) GetResult {
+-	var result GetResult
+-	_, result.Err = perigee.Request("GET", getURL(client, id), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		Results:     &result.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return result
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/requests_test.go
+deleted file mode 100644
+index 9a05f97..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/requests_test.go
++++ /dev/null
+@@ -1,175 +0,0 @@
+-package images
 -
--// bufferSize sizes the buffer associated with each log file. It's large
--// so that log records can accumulate without the logging thread blocking
--// on disk I/O. The flushDaemon will block instead.
--const bufferSize = 256 * 1024
+-import (
+-	"encoding/json"
+-	"fmt"
+-	"net/http"
+-	"reflect"
+-	"testing"
 -
--// createFiles creates all the log files for severity from sev down to infoLog.
--// l.mu is held.
--func (l *loggingT) createFiles(sev severity) error {
--	now := time.Now()
--	// Files are created in decreasing severity order, so as soon as we find one
--	// has already been created, we can stop.
--	for s := sev; s >= infoLog && l.file[s] == nil; s-- {
--		sb := &syncBuffer{
--			logger: l,
--			sev:    s,
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
+-
+-func TestListImages(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/images/detail", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		r.ParseForm()
+-		marker := r.Form.Get("marker")
+-		switch marker {
+-		case "":
+-			fmt.Fprintf(w, `
+-				{
+-					"images": [
+-						{
+-							"status": "ACTIVE",
+-							"updated": "2014-09-23T12:54:56Z",
+-							"id": "f3e4a95d-1f4f-4989-97ce-f3a1fb8c04d7",
+-							"OS-EXT-IMG-SIZE:size": 476704768,
+-							"name": "F17-x86_64-cfntools",
+-							"created": "2014-09-23T12:54:52Z",
+-							"minDisk": 0,
+-							"progress": 100,
+-							"minRam": 0,
+-							"metadata": {}
+-						},
+-						{
+-							"status": "ACTIVE",
+-							"updated": "2014-09-23T12:51:43Z",
+-							"id": "f90f6034-2570-4974-8351-6b49732ef2eb",
+-							"OS-EXT-IMG-SIZE:size": 13167616,
+-							"name": "cirros-0.3.2-x86_64-disk",
+-							"created": "2014-09-23T12:51:42Z",
+-							"minDisk": 0,
+-							"progress": 100,
+-							"minRam": 0,
+-							"metadata": {}
+-						}
+-					]
+-				}
+-			`)
+-		case "2":
+-			fmt.Fprintf(w, `{ "images": [] }`)
+-		default:
+-			t.Fatalf("Unexpected marker: [%s]", marker)
 -		}
--		if err := sb.rotateFile(now); err != nil {
--			return err
+-	})
+-
+-	pages := 0
+-	options := &ListOpts{Limit: 2}
+-	err := ListDetail(fake.ServiceClient(), options).EachPage(func(page pagination.Page) (bool, error) {
+-		pages++
+-
+-		actual, err := ExtractImages(page)
+-		if err != nil {
+-			return false, err
 -		}
--		l.file[s] = sb
+-
+-		expected := []Image{
+-			Image{
+-				ID:       "f3e4a95d-1f4f-4989-97ce-f3a1fb8c04d7",
+-				Name:     "F17-x86_64-cfntools",
+-				Created:  "2014-09-23T12:54:52Z",
+-				Updated:  "2014-09-23T12:54:56Z",
+-				MinDisk:  0,
+-				MinRAM:   0,
+-				Progress: 100,
+-				Status:   "ACTIVE",
+-			},
+-			Image{
+-				ID:       "f90f6034-2570-4974-8351-6b49732ef2eb",
+-				Name:     "cirros-0.3.2-x86_64-disk",
+-				Created:  "2014-09-23T12:51:42Z",
+-				Updated:  "2014-09-23T12:51:43Z",
+-				MinDisk:  0,
+-				MinRAM:   0,
+-				Progress: 100,
+-				Status:   "ACTIVE",
+-			},
+-		}
+-
+-		if !reflect.DeepEqual(expected, actual) {
+-			t.Errorf("Unexpected page contents: expected %#v, got %#v", expected, actual)
+-		}
+-
+-		return false, nil
+-	})
+-
+-	if err != nil {
+-		t.Fatalf("EachPage error: %v", err)
+-	}
+-	if pages != 1 {
+-		t.Errorf("Expected one page, got %d", pages)
 -	}
--	return nil
 -}
 -
--const flushInterval = 30 * time.Second
+-func TestGetImage(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--// flushDaemon periodically flushes the log file buffers.
--func (l *loggingT) flushDaemon() {
--	for _ = range time.NewTicker(flushInterval).C {
--		l.lockAndFlushAll()
+-	th.Mux.HandleFunc("/images/12345678", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, `
+-			{
+-				"image": {
+-					"status": "ACTIVE",
+-					"updated": "2014-09-23T12:54:56Z",
+-					"id": "f3e4a95d-1f4f-4989-97ce-f3a1fb8c04d7",
+-					"OS-EXT-IMG-SIZE:size": 476704768,
+-					"name": "F17-x86_64-cfntools",
+-					"created": "2014-09-23T12:54:52Z",
+-					"minDisk": 0,
+-					"progress": 100,
+-					"minRam": 0,
+-					"metadata": {}
+-				}
+-			}
+-		`)
+-	})
+-
+-	actual, err := Get(fake.ServiceClient(), "12345678").Extract()
+-	if err != nil {
+-		t.Fatalf("Unexpected error from Get: %v", err)
 -	}
--}
 -
--// lockAndFlushAll is like flushAll but locks l.mu first.
--func (l *loggingT) lockAndFlushAll() {
--	l.mu.Lock()
--	l.flushAll()
--	l.mu.Unlock()
--}
+-	expected := &Image{
+-		Status:   "ACTIVE",
+-		Updated:  "2014-09-23T12:54:56Z",
+-		ID:       "f3e4a95d-1f4f-4989-97ce-f3a1fb8c04d7",
+-		Name:     "F17-x86_64-cfntools",
+-		Created:  "2014-09-23T12:54:52Z",
+-		MinDisk:  0,
+-		Progress: 100,
+-		MinRAM:   0,
+-	}
 -
--// flushAll flushes all the logs and attempts to "sync" their data to disk.
--// l.mu is held.
--func (l *loggingT) flushAll() {
--	// Flush from fatal down, in case there's trouble flushing.
--	for s := fatalLog; s >= infoLog; s-- {
--		file := l.file[s]
--		if file != nil {
--			file.Flush() // ignore error
--			file.Sync()  // ignore error
--		}
+-	if !reflect.DeepEqual(expected, actual) {
+-		t.Errorf("Expected %#v, but got %#v", expected, actual)
 -	}
 -}
 -
--// CopyStandardLogTo arranges for messages written to the Go "log" package's
--// default logs to also appear in the Google logs for the named and lower
--// severities.  Subsequent changes to the standard log's default output location
--// or format may break this behavior.
--//
--// Valid names are "INFO", "WARNING", "ERROR", and "FATAL".  If the name is not
--// recognized, CopyStandardLogTo panics.
--func CopyStandardLogTo(name string) {
--	sev, ok := severityByName(name)
--	if !ok {
--		panic(fmt.Sprintf("log.CopyStandardLogTo(%q): unrecognized severity name", name))
+-func TestNextPageURL(t *testing.T) {
+-	var page ImagePage
+-	var body map[string]interface{}
+-	bodyString := []byte(`{"images":{"links":[{"href":"http://192.154.23.87/12345/images/image3","rel":"bookmark"}]}, "images_links":[{"href":"http://192.154.23.87/12345/images/image4","rel":"next"}]}`)
+-	err := json.Unmarshal(bodyString, &body)
+-	if err != nil {
+-		t.Fatalf("Error unmarshaling data into page body: %v", err)
 -	}
--	// Set a log format that captures the user's file and line:
--	//   d.go:23: message
--	stdLog.SetFlags(stdLog.Lshortfile)
--	stdLog.SetOutput(logBridge(sev))
+-	page.Body = body
+-
+-	expected := "http://192.154.23.87/12345/images/image4"
+-	actual, err := page.NextPageURL()
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, expected, actual)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/results.go
+deleted file mode 100644
+index 493d511..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/results.go
++++ /dev/null
+@@ -1,90 +0,0 @@
+-package images
 -
--// logBridge provides the Write method that enables CopyStandardLogTo to connect
--// Go's standard logs to the logs provided by this package.
--type logBridge severity
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--// Write parses the standard logging line and passes its components to the
--// logger for severity(lb).
--func (lb logBridge) Write(b []byte) (n int, err error) {
--	var (
--		file = "???"
--		line = 1
--		text string
--	)
--	// Split "d.go:23: message" into "d.go", "23", and "message".
--	if parts := bytes.SplitN(b, []byte{':'}, 3); len(parts) != 3 || len(parts[0]) < 1 || len(parts[2]) < 1 {
--		text = fmt.Sprintf("bad log format: %s", b)
--	} else {
--		file = string(parts[0])
--		text = string(parts[2][1:]) // skip leading space
--		line, err = strconv.Atoi(string(parts[1]))
--		if err != nil {
--			text = fmt.Sprintf("bad line number: %s", b)
--			line = 1
--		}
--	}
--	// printWithFileLine with alsoToStderr=true, so standard log messages
--	// always appear on standard error.
--	logging.printWithFileLine(severity(lb), file, line, true, text)
--	return len(b), nil
+-// GetResult temporarily stores a Get response.
+-type GetResult struct {
+-	gophercloud.Result
 -}
 -
--// setV computes and remembers the V level for a given PC
--// when vmodule is enabled.
--// File pattern matching takes the basename of the file, stripped
--// of its .go suffix, and uses filepath.Match, which is a little more
--// general than the *? matching used in C++.
--// l.mu is held.
--func (l *loggingT) setV(pc uintptr) Level {
--	fn := runtime.FuncForPC(pc)
--	file, _ := fn.FileLine(pc)
--	// The file is something like /a/b/c/d.go. We want just the d.
--	if strings.HasSuffix(file, ".go") {
--		file = file[:len(file)-3]
--	}
--	if slash := strings.LastIndex(file, "/"); slash >= 0 {
--		file = file[slash+1:]
+-// Extract interprets a GetResult as an Image.
+-func (gr GetResult) Extract() (*Image, error) {
+-	if gr.Err != nil {
+-		return nil, gr.Err
 -	}
--	for _, filter := range l.vmodule.filter {
--		if filter.match(file) {
--			l.vmap[pc] = filter.level
--			return filter.level
--		}
+-
+-	var decoded struct {
+-		Image Image `mapstructure:"image"`
 -	}
--	l.vmap[pc] = 0
--	return 0
+-
+-	err := mapstructure.Decode(gr.Body, &decoded)
+-	return &decoded.Image, err
 -}
 -
--// Verbose is a boolean type that implements Infof (like Printf) etc.
--// See the documentation of V for more information.
--type Verbose bool
+-// Image is used for JSON (un)marshalling.
+-// It provides a description of an OS image.
+-type Image struct {
+-	// ID contains the image's unique identifier.
+-	ID string
 -
--// V reports whether verbosity at the call site is at least the requested level.
--// The returned value is a boolean of type Verbose, which implements Info, Infoln
--// and Infof. These methods will write to the Info log if called.
--// Thus, one may write either
--//	if glog.V(2) { glog.Info("log this") }
--// or
--//	glog.V(2).Info("log this")
--// The second form is shorter but the first is cheaper if logging is off because it does
--// not evaluate its arguments.
--//
--// Whether an individual call to V generates a log record depends on the setting of
--// the -v and --vmodule flags; both are off by default. If the level in the call to
--// V is at least the value of -v, or of -vmodule for the source file containing the
--// call, the V call will log.
--func V(level Level) Verbose {
--	// This function tries hard to be cheap unless there's work to do.
--	// The fast path is two atomic loads and compares.
+-	Created string
 -
--	// Here is a cheap but safe test to see if V logging is enabled globally.
--	if logging.verbosity.get() >= level {
--		return Verbose(true)
--	}
+-	// MinDisk and MinRAM specify the minimum resources a server must provide to be able to install the image.
+-	MinDisk int
+-	MinRAM  int
 -
--	// It's off globally but it vmodule may still be set.
--	// Here is another cheap but safe test to see if vmodule is enabled.
--	if atomic.LoadInt32(&logging.filterLength) > 0 {
--		// Now we need a proper lock to use the logging structure. The pcs field
--		// is shared so we must lock before accessing it. This is fairly expensive,
--		// but if V logging is enabled we're slow anyway.
--		logging.mu.Lock()
--		defer logging.mu.Unlock()
--		if runtime.Callers(2, logging.pcs[:]) == 0 {
--			return Verbose(false)
--		}
--		v, ok := logging.vmap[logging.pcs[0]]
--		if !ok {
--			v = logging.setV(logging.pcs[0])
--		}
--		return Verbose(v >= level)
--	}
--	return Verbose(false)
+-	// Name provides a human-readable moniker for the OS image.
+-	Name string
+-
+-	// The Progress and Status fields indicate image-creation status.
+-	// Any usable image will have 100% progress.
+-	Progress int
+-	Status   string
+-
+-	Updated string
 -}
 -
--// Info is equivalent to the global Info function, guarded by the value of v.
--// See the documentation of V for usage.
--func (v Verbose) Info(args ...interface{}) {
--	if v {
--		logging.print(infoLog, args...)
+-// ImagePage contains a single page of results from a List operation.
+-// Use ExtractImages to convert it into a slice of usable structs.
+-type ImagePage struct {
+-	pagination.LinkedPageBase
+-}
+-
+-// IsEmpty returns true if a page contains no Image results.
+-func (page ImagePage) IsEmpty() (bool, error) {
+-	images, err := ExtractImages(page)
+-	if err != nil {
+-		return true, err
 -	}
+-	return len(images) == 0, nil
 -}
 -
--// Infoln is equivalent to the global Infoln function, guarded by the value of v.
--// See the documentation of V for usage.
--func (v Verbose) Infoln(args ...interface{}) {
--	if v {
--		logging.println(infoLog, args...)
+-// NextPageURL uses the response's embedded link reference to navigate to the next page of results.
+-func (page ImagePage) NextPageURL() (string, error) {
+-	type resp struct {
+-		Links []gophercloud.Link `mapstructure:"images_links"`
+-	}
+-
+-	var r resp
+-	err := mapstructure.Decode(page.Body, &r)
+-	if err != nil {
+-		return "", err
 -	}
+-
+-	return gophercloud.ExtractNextURL(r.Links)
 -}
 -
--// Infof is equivalent to the global Infof function, guarded by the value of v.
--// See the documentation of V for usage.
--func (v Verbose) Infof(format string, args ...interface{}) {
--	if v {
--		logging.printf(infoLog, format, args...)
+-// ExtractImages converts a page of List results into a slice of usable Image structs.
+-func ExtractImages(page pagination.Page) ([]Image, error) {
+-	casted := page.(ImagePage).Body
+-	var results struct {
+-		Images []Image `mapstructure:"images"`
 -	}
+-
+-	err := mapstructure.Decode(casted, &results)
+-	return results.Images, err
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/urls.go
+deleted file mode 100644
+index 9b3c86d..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/urls.go
++++ /dev/null
+@@ -1,11 +0,0 @@
+-package images
 -
--// Info logs to the INFO log.
--// Arguments are handled in the manner of fmt.Print; a newline is appended if missing.
--func Info(args ...interface{}) {
--	logging.print(infoLog, args...)
+-import "github.com/rackspace/gophercloud"
+-
+-func listDetailURL(client *gophercloud.ServiceClient) string {
+-	return client.ServiceURL("images", "detail")
 -}
 -
--// InfoDepth acts as Info but uses depth to determine which call frame to log.
--// InfoDepth(0, "msg") is the same as Info("msg").
--func InfoDepth(depth int, args ...interface{}) {
--	logging.printDepth(infoLog, depth, args...)
+-func getURL(client *gophercloud.ServiceClient, id string) string {
+-	return client.ServiceURL("images", id)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/urls_test.go
+deleted file mode 100644
+index b1ab3d6..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/images/urls_test.go
++++ /dev/null
+@@ -1,26 +0,0 @@
+-package images
 -
--// Infoln logs to the INFO log.
--// Arguments are handled in the manner of fmt.Println; a newline is appended if missing.
--func Infoln(args ...interface{}) {
--	logging.println(infoLog, args...)
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-const endpoint = "http://localhost:57909/"
+-
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint}
 -}
 -
--// Infof logs to the INFO log.
--// Arguments are handled in the manner of fmt.Printf; a newline is appended if missing.
--func Infof(format string, args ...interface{}) {
--	logging.printf(infoLog, format, args...)
+-func TestGetURL(t *testing.T) {
+-	actual := getURL(endpointClient(), "foo")
+-	expected := endpoint + "images/foo"
+-	th.CheckEquals(t, expected, actual)
 -}
 -
--// Warning logs to the WARNING and INFO logs.
--// Arguments are handled in the manner of fmt.Print; a newline is appended if missing.
--func Warning(args ...interface{}) {
--	logging.print(warningLog, args...)
+-func TestListDetailURL(t *testing.T) {
+-	actual := listDetailURL(endpointClient())
+-	expected := endpoint + "images/detail"
+-	th.CheckEquals(t, expected, actual)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/doc.go
+deleted file mode 100644
+index fe45671..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/doc.go
++++ /dev/null
+@@ -1,6 +0,0 @@
+-// Package servers provides information and interaction with the server API
+-// resource in the OpenStack Compute service.
+-//
+-// A server is a virtual machine instance in the compute system. In order for
+-// one to be provisioned, a valid flavor and image are required.
+-package servers
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/fixtures.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/fixtures.go
+deleted file mode 100644
+index e872b07..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/fixtures.go
++++ /dev/null
+@@ -1,459 +0,0 @@
+-// +build fixtures
 -
--// WarningDepth acts as Warning but uses depth to determine which call frame to log.
--// WarningDepth(0, "msg") is the same as Warning("msg").
--func WarningDepth(depth int, args ...interface{}) {
--	logging.printDepth(warningLog, depth, args...)
+-package servers
+-
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
+-
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
+-
+-// ServerListBody contains the canned body of a servers.List response.
+-const ServerListBody = `
+-{
+-	"servers": [
+-		{
+-			"status": "ACTIVE",
+-			"updated": "2014-09-25T13:10:10Z",
+-			"hostId": "29d3c8c896a45aa4c34e52247875d7fefc3d94bbcc9f622b5d204362",
+-			"OS-EXT-SRV-ATTR:host": "devstack",
+-			"addresses": {
+-				"private": [
+-					{
+-						"OS-EXT-IPS-MAC:mac_addr": "fa:16:3e:7c:1b:2b",
+-						"version": 4,
+-						"addr": "10.0.0.32",
+-						"OS-EXT-IPS:type": "fixed"
+-					}
+-				]
+-			},
+-			"links": [
+-				{
+-					"href": "http://104.130.131.164:8774/v2/fcad67a6189847c4aecfa3c81a05783b/servers/ef079b0c-e610-4dfb-b1aa-b49f07ac48e5",
+-					"rel": "self"
+-				},
+-				{
+-					"href": "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/servers/ef079b0c-e610-4dfb-b1aa-b49f07ac48e5",
+-					"rel": "bookmark"
+-				}
+-			],
+-			"key_name": null,
+-			"image": {
+-				"id": "f90f6034-2570-4974-8351-6b49732ef2eb",
+-				"links": [
+-					{
+-						"href": "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/images/f90f6034-2570-4974-8351-6b49732ef2eb",
+-						"rel": "bookmark"
+-					}
+-				]
+-			},
+-			"OS-EXT-STS:task_state": null,
+-			"OS-EXT-STS:vm_state": "active",
+-			"OS-EXT-SRV-ATTR:instance_name": "instance-0000001e",
+-			"OS-SRV-USG:launched_at": "2014-09-25T13:10:10.000000",
+-			"OS-EXT-SRV-ATTR:hypervisor_hostname": "devstack",
+-			"flavor": {
+-				"id": "1",
+-				"links": [
+-					{
+-						"href": "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/flavors/1",
+-						"rel": "bookmark"
+-					}
+-				]
+-			},
+-			"id": "ef079b0c-e610-4dfb-b1aa-b49f07ac48e5",
+-			"security_groups": [
+-				{
+-					"name": "default"
+-				}
+-			],
+-			"OS-SRV-USG:terminated_at": null,
+-			"OS-EXT-AZ:availability_zone": "nova",
+-			"user_id": "9349aff8be7545ac9d2f1d00999a23cd",
+-			"name": "herp",
+-			"created": "2014-09-25T13:10:02Z",
+-			"tenant_id": "fcad67a6189847c4aecfa3c81a05783b",
+-			"OS-DCF:diskConfig": "MANUAL",
+-			"os-extended-volumes:volumes_attached": [],
+-			"accessIPv4": "",
+-			"accessIPv6": "",
+-			"progress": 0,
+-			"OS-EXT-STS:power_state": 1,
+-			"config_drive": "",
+-			"metadata": {}
+-		},
+-		{
+-			"status": "ACTIVE",
+-			"updated": "2014-09-25T13:04:49Z",
+-			"hostId": "29d3c8c896a45aa4c34e52247875d7fefc3d94bbcc9f622b5d204362",
+-			"OS-EXT-SRV-ATTR:host": "devstack",
+-			"addresses": {
+-				"private": [
+-					{
+-						"OS-EXT-IPS-MAC:mac_addr": "fa:16:3e:9e:89:be",
+-						"version": 4,
+-						"addr": "10.0.0.31",
+-						"OS-EXT-IPS:type": "fixed"
+-					}
+-				]
+-			},
+-			"links": [
+-				{
+-					"href": "http://104.130.131.164:8774/v2/fcad67a6189847c4aecfa3c81a05783b/servers/9e5476bd-a4ec-4653-93d6-72c93aa682ba",
+-					"rel": "self"
+-				},
+-				{
+-					"href": "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/servers/9e5476bd-a4ec-4653-93d6-72c93aa682ba",
+-					"rel": "bookmark"
+-				}
+-			],
+-			"key_name": null,
+-			"image": {
+-				"id": "f90f6034-2570-4974-8351-6b49732ef2eb",
+-				"links": [
+-					{
+-						"href": "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/images/f90f6034-2570-4974-8351-6b49732ef2eb",
+-						"rel": "bookmark"
+-					}
+-				]
+-			},
+-			"OS-EXT-STS:task_state": null,
+-			"OS-EXT-STS:vm_state": "active",
+-			"OS-EXT-SRV-ATTR:instance_name": "instance-0000001d",
+-			"OS-SRV-USG:launched_at": "2014-09-25T13:04:49.000000",
+-			"OS-EXT-SRV-ATTR:hypervisor_hostname": "devstack",
+-			"flavor": {
+-				"id": "1",
+-				"links": [
+-					{
+-						"href": "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/flavors/1",
+-						"rel": "bookmark"
+-					}
+-				]
+-			},
+-			"id": "9e5476bd-a4ec-4653-93d6-72c93aa682ba",
+-			"security_groups": [
+-				{
+-					"name": "default"
+-				}
+-			],
+-			"OS-SRV-USG:terminated_at": null,
+-			"OS-EXT-AZ:availability_zone": "nova",
+-			"user_id": "9349aff8be7545ac9d2f1d00999a23cd",
+-			"name": "derp",
+-			"created": "2014-09-25T13:04:41Z",
+-			"tenant_id": "fcad67a6189847c4aecfa3c81a05783b",
+-			"OS-DCF:diskConfig": "MANUAL",
+-			"os-extended-volumes:volumes_attached": [],
+-			"accessIPv4": "",
+-			"accessIPv6": "",
+-			"progress": 0,
+-			"OS-EXT-STS:power_state": 1,
+-			"config_drive": "",
+-			"metadata": {}
+-		}
+-	]
+-}
+-`
+-
+-// SingleServerBody is the canned body of a Get request on an existing server.
+-const SingleServerBody = `
+-{
+-	"server": {
+-		"status": "ACTIVE",
+-		"updated": "2014-09-25T13:04:49Z",
+-		"hostId": "29d3c8c896a45aa4c34e52247875d7fefc3d94bbcc9f622b5d204362",
+-		"OS-EXT-SRV-ATTR:host": "devstack",
+-		"addresses": {
+-			"private": [
+-				{
+-					"OS-EXT-IPS-MAC:mac_addr": "fa:16:3e:9e:89:be",
+-					"version": 4,
+-					"addr": "10.0.0.31",
+-					"OS-EXT-IPS:type": "fixed"
+-				}
+-			]
+-		},
+-		"links": [
+-			{
+-				"href": "http://104.130.131.164:8774/v2/fcad67a6189847c4aecfa3c81a05783b/servers/9e5476bd-a4ec-4653-93d6-72c93aa682ba",
+-				"rel": "self"
+-			},
+-			{
+-				"href": "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/servers/9e5476bd-a4ec-4653-93d6-72c93aa682ba",
+-				"rel": "bookmark"
+-			}
+-		],
+-		"key_name": null,
+-		"image": {
+-			"id": "f90f6034-2570-4974-8351-6b49732ef2eb",
+-			"links": [
+-				{
+-					"href": "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/images/f90f6034-2570-4974-8351-6b49732ef2eb",
+-					"rel": "bookmark"
+-				}
+-			]
+-		},
+-		"OS-EXT-STS:task_state": null,
+-		"OS-EXT-STS:vm_state": "active",
+-		"OS-EXT-SRV-ATTR:instance_name": "instance-0000001d",
+-		"OS-SRV-USG:launched_at": "2014-09-25T13:04:49.000000",
+-		"OS-EXT-SRV-ATTR:hypervisor_hostname": "devstack",
+-		"flavor": {
+-			"id": "1",
+-			"links": [
+-				{
+-					"href": "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/flavors/1",
+-					"rel": "bookmark"
+-				}
+-			]
+-		},
+-		"id": "9e5476bd-a4ec-4653-93d6-72c93aa682ba",
+-		"security_groups": [
+-			{
+-				"name": "default"
+-			}
+-		],
+-		"OS-SRV-USG:terminated_at": null,
+-		"OS-EXT-AZ:availability_zone": "nova",
+-		"user_id": "9349aff8be7545ac9d2f1d00999a23cd",
+-		"name": "derp",
+-		"created": "2014-09-25T13:04:41Z",
+-		"tenant_id": "fcad67a6189847c4aecfa3c81a05783b",
+-		"OS-DCF:diskConfig": "MANUAL",
+-		"os-extended-volumes:volumes_attached": [],
+-		"accessIPv4": "",
+-		"accessIPv6": "",
+-		"progress": 0,
+-		"OS-EXT-STS:power_state": 1,
+-		"config_drive": "",
+-		"metadata": {}
+-	}
 -}
+-`
+-
+-var (
+-	// ServerHerp is a Server struct that should correspond to the first result in ServerListBody.
+-	ServerHerp = Server{
+-		Status:  "ACTIVE",
+-		Updated: "2014-09-25T13:10:10Z",
+-		HostID:  "29d3c8c896a45aa4c34e52247875d7fefc3d94bbcc9f622b5d204362",
+-		Addresses: map[string]interface{}{
+-			"private": []interface{}{
+-				map[string]interface{}{
+-					"OS-EXT-IPS-MAC:mac_addr": "fa:16:3e:7c:1b:2b",
+-					"version":                 float64(4),
+-					"addr":                    "10.0.0.32",
+-					"OS-EXT-IPS:type":         "fixed",
+-				},
+-			},
+-		},
+-		Links: []interface{}{
+-			map[string]interface{}{
+-				"href": "http://104.130.131.164:8774/v2/fcad67a6189847c4aecfa3c81a05783b/servers/ef079b0c-e610-4dfb-b1aa-b49f07ac48e5",
+-				"rel":  "self",
+-			},
+-			map[string]interface{}{
+-				"href": "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/servers/ef079b0c-e610-4dfb-b1aa-b49f07ac48e5",
+-				"rel":  "bookmark",
+-			},
+-		},
+-		Image: map[string]interface{}{
+-			"id": "f90f6034-2570-4974-8351-6b49732ef2eb",
+-			"links": []interface{}{
+-				map[string]interface{}{
+-					"href": "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/images/f90f6034-2570-4974-8351-6b49732ef2eb",
+-					"rel":  "bookmark",
+-				},
+-			},
+-		},
+-		Flavor: map[string]interface{}{
+-			"id": "1",
+-			"links": []interface{}{
+-				map[string]interface{}{
+-					"href": "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/flavors/1",
+-					"rel":  "bookmark",
+-				},
+-			},
+-		},
+-		ID:       "ef079b0c-e610-4dfb-b1aa-b49f07ac48e5",
+-		UserID:   "9349aff8be7545ac9d2f1d00999a23cd",
+-		Name:     "herp",
+-		Created:  "2014-09-25T13:10:02Z",
+-		TenantID: "fcad67a6189847c4aecfa3c81a05783b",
+-		Metadata: map[string]interface{}{},
+-	}
+-
+-	// ServerDerp is a Server struct that should correspond to the second server in ServerListBody.
+-	ServerDerp = Server{
+-		Status:  "ACTIVE",
+-		Updated: "2014-09-25T13:04:49Z",
+-		HostID:  "29d3c8c896a45aa4c34e52247875d7fefc3d94bbcc9f622b5d204362",
+-		Addresses: map[string]interface{}{
+-			"private": []interface{}{
+-				map[string]interface{}{
+-					"OS-EXT-IPS-MAC:mac_addr": "fa:16:3e:9e:89:be",
+-					"version":                 float64(4),
+-					"addr":                    "10.0.0.31",
+-					"OS-EXT-IPS:type":         "fixed",
+-				},
+-			},
+-		},
+-		Links: []interface{}{
+-			map[string]interface{}{
+-				"href": "http://104.130.131.164:8774/v2/fcad67a6189847c4aecfa3c81a05783b/servers/9e5476bd-a4ec-4653-93d6-72c93aa682ba",
+-				"rel":  "self",
+-			},
+-			map[string]interface{}{
+-				"href": "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/servers/9e5476bd-a4ec-4653-93d6-72c93aa682ba",
+-				"rel":  "bookmark",
+-			},
+-		},
+-		Image: map[string]interface{}{
+-			"id": "f90f6034-2570-4974-8351-6b49732ef2eb",
+-			"links": []interface{}{
+-				map[string]interface{}{
+-					"href": "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/images/f90f6034-2570-4974-8351-6b49732ef2eb",
+-					"rel":  "bookmark",
+-				},
+-			},
+-		},
+-		Flavor: map[string]interface{}{
+-			"id": "1",
+-			"links": []interface{}{
+-				map[string]interface{}{
+-					"href": "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/flavors/1",
+-					"rel":  "bookmark",
+-				},
+-			},
+-		},
+-		ID:       "9e5476bd-a4ec-4653-93d6-72c93aa682ba",
+-		UserID:   "9349aff8be7545ac9d2f1d00999a23cd",
+-		Name:     "derp",
+-		Created:  "2014-09-25T13:04:41Z",
+-		TenantID: "fcad67a6189847c4aecfa3c81a05783b",
+-		Metadata: map[string]interface{}{},
+-	}
+-)
 -
--// Warningln logs to the WARNING and INFO logs.
--// Arguments are handled in the manner of fmt.Println; a newline is appended if missing.
--func Warningln(args ...interface{}) {
--	logging.println(warningLog, args...)
+-// HandleServerCreationSuccessfully sets up the test server to respond to a server creation request
+-// with a given response.
+-func HandleServerCreationSuccessfully(t *testing.T, response string) {
+-	th.Mux.HandleFunc("/servers", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-		th.TestJSONRequest(t, r, `{
+-			"server": {
+-				"name": "derp",
+-				"imageRef": "f90f6034-2570-4974-8351-6b49732ef2eb",
+-				"flavorRef": "1"
+-			}
+-		}`)
+-
+-		w.WriteHeader(http.StatusAccepted)
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, response)
+-	})
 -}
 -
--// Warningf logs to the WARNING and INFO logs.
--// Arguments are handled in the manner of fmt.Printf; a newline is appended if missing.
--func Warningf(format string, args ...interface{}) {
--	logging.printf(warningLog, format, args...)
+-// HandleServerListSuccessfully sets up the test server to respond to a server List request.
+-func HandleServerListSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/servers/detail", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		r.ParseForm()
+-		marker := r.Form.Get("marker")
+-		switch marker {
+-		case "":
+-			fmt.Fprintf(w, ServerListBody)
+-		case "9e5476bd-a4ec-4653-93d6-72c93aa682ba":
+-			fmt.Fprintf(w, `{ "servers": [] }`)
+-		default:
+-			t.Fatalf("/servers/detail invoked with unexpected marker=[%s]", marker)
+-		}
+-	})
 -}
 -
--// Error logs to the ERROR, WARNING, and INFO logs.
--// Arguments are handled in the manner of fmt.Print; a newline is appended if missing.
--func Error(args ...interface{}) {
--	logging.print(errorLog, args...)
--}
+-// HandleServerDeletionSuccessfully sets up the test server to respond to a server deletion request.
+-func HandleServerDeletionSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/servers/asdfasdfasdf", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
 -
--// ErrorDepth acts as Error but uses depth to determine which call frame to log.
--// ErrorDepth(0, "msg") is the same as Error("msg").
--func ErrorDepth(depth int, args ...interface{}) {
--	logging.printDepth(errorLog, depth, args...)
+-		w.WriteHeader(http.StatusNoContent)
+-	})
 -}
 -
--// Errorln logs to the ERROR, WARNING, and INFO logs.
--// Arguments are handled in the manner of fmt.Println; a newline is appended if missing.
--func Errorln(args ...interface{}) {
--	logging.println(errorLog, args...)
--}
+-// HandleServerGetSuccessfully sets up the test server to respond to a server Get request.
+-func HandleServerGetSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/servers/1234asdf", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-		th.TestHeader(t, r, "Accept", "application/json")
 -
--// Errorf logs to the ERROR, WARNING, and INFO logs.
--// Arguments are handled in the manner of fmt.Printf; a newline is appended if missing.
--func Errorf(format string, args ...interface{}) {
--	logging.printf(errorLog, format, args...)
+-		fmt.Fprintf(w, SingleServerBody)
+-	})
 -}
 -
--// Fatal logs to the FATAL, ERROR, WARNING, and INFO logs,
--// including a stack trace of all running goroutines, then calls os.Exit(255).
--// Arguments are handled in the manner of fmt.Print; a newline is appended if missing.
--func Fatal(args ...interface{}) {
--	logging.print(fatalLog, args...)
--}
+-// HandleServerUpdateSuccessfully sets up the test server to respond to a server Update request.
+-func HandleServerUpdateSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/servers/1234asdf", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestJSONRequest(t, r, `{ "server": { "name": "new-name" } }`)
 -
--// FatalDepth acts as Fatal but uses depth to determine which call frame to log.
--// FatalDepth(0, "msg") is the same as Fatal("msg").
--func FatalDepth(depth int, args ...interface{}) {
--	logging.printDepth(fatalLog, depth, args...)
+-		fmt.Fprintf(w, SingleServerBody)
+-	})
 -}
 -
--// Fatalln logs to the FATAL, ERROR, WARNING, and INFO logs,
--// including a stack trace of all running goroutines, then calls os.Exit(255).
--// Arguments are handled in the manner of fmt.Println; a newline is appended if missing.
--func Fatalln(args ...interface{}) {
--	logging.println(fatalLog, args...)
--}
+-// HandleAdminPasswordChangeSuccessfully sets up the test server to respond to a server password
+-// change request.
+-func HandleAdminPasswordChangeSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/servers/1234asdf/action", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-		th.TestJSONRequest(t, r, `{ "changePassword": { "adminPass": "new-password" } }`)
 -
--// Fatalf logs to the FATAL, ERROR, WARNING, and INFO logs,
--// including a stack trace of all running goroutines, then calls os.Exit(255).
--// Arguments are handled in the manner of fmt.Printf; a newline is appended if missing.
--func Fatalf(format string, args ...interface{}) {
--	logging.printf(fatalLog, format, args...)
+-		w.WriteHeader(http.StatusAccepted)
+-	})
 -}
 -
--// fatalNoStacks is non-zero if we are to exit without dumping goroutine stacks.
--// It allows Exit and relatives to use the Fatal logs.
--var fatalNoStacks uint32
--
--// Exit logs to the FATAL, ERROR, WARNING, and INFO logs, then calls os.Exit(1).
--// Arguments are handled in the manner of fmt.Print; a newline is appended if missing.
--func Exit(args ...interface{}) {
--	atomic.StoreUint32(&fatalNoStacks, 1)
--	logging.print(fatalLog, args...)
--}
+-// HandleRebootSuccessfully sets up the test server to respond to a reboot request with success.
+-func HandleRebootSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/servers/1234asdf/action", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-		th.TestJSONRequest(t, r, `{ "reboot": { "type": "SOFT" } }`)
 -
--// ExitDepth acts as Exit but uses depth to determine which call frame to log.
--// ExitDepth(0, "msg") is the same as Exit("msg").
--func ExitDepth(depth int, args ...interface{}) {
--	atomic.StoreUint32(&fatalNoStacks, 1)
--	logging.printDepth(fatalLog, depth, args...)
+-		w.WriteHeader(http.StatusAccepted)
+-	})
 -}
 -
--// Exitln logs to the FATAL, ERROR, WARNING, and INFO logs, then calls os.Exit(1).
--func Exitln(args ...interface{}) {
--	atomic.StoreUint32(&fatalNoStacks, 1)
--	logging.println(fatalLog, args...)
--}
+-// HandleRebuildSuccessfully sets up the test server to respond to a rebuild request with success.
+-func HandleRebuildSuccessfully(t *testing.T, response string) {
+-	th.Mux.HandleFunc("/servers/1234asdf/action", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-		th.TestJSONRequest(t, r, `
+-			{
+-				"rebuild": {
+-					"name": "new-name",
+-					"adminPass": "swordfish",
+-					"imageRef": "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/images/f90f6034-2570-4974-8351-6b49732ef2eb",
+-					"accessIPv4": "1.2.3.4"
+-				}
+-			}
+-		`)
 -
--// Exitf logs to the FATAL, ERROR, WARNING, and INFO logs, then calls os.Exit(1).
--// Arguments are handled in the manner of fmt.Printf; a newline is appended if missing.
--func Exitf(format string, args ...interface{}) {
--	atomic.StoreUint32(&fatalNoStacks, 1)
--	logging.printf(fatalLog, format, args...)
+-		w.WriteHeader(http.StatusAccepted)
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, response)
+-	})
 -}
-diff --git a/Godeps/_workspace/src/github.com/golang/glog/glog_file.go b/Godeps/_workspace/src/github.com/golang/glog/glog_file.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/requests.go
 deleted file mode 100644
-index 65075d2..0000000
---- a/Godeps/_workspace/src/github.com/golang/glog/glog_file.go
+index 95a4188..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/requests.go
 +++ /dev/null
-@@ -1,124 +0,0 @@
--// Go support for leveled logs, analogous to https://code.google.com/p/google-glog/
--//
--// Copyright 2013 Google Inc. All Rights Reserved.
--//
--// Licensed under the Apache License, Version 2.0 (the "License");
--// you may not use this file except in compliance with the License.
--// You may obtain a copy of the License at
--//
--//     http://www.apache.org/licenses/LICENSE-2.0
--//
--// Unless required by applicable law or agreed to in writing, software
--// distributed under the License is distributed on an "AS IS" BASIS,
--// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
--// See the License for the specific language governing permissions and
--// limitations under the License.
--
--// File I/O for logs.
--
--package glog
+@@ -1,538 +0,0 @@
+-package servers
 -
 -import (
--	"errors"
--	"flag"
+-	"encoding/base64"
 -	"fmt"
--	"os"
--	"os/user"
--	"path/filepath"
--	"strings"
--	"sync"
--	"time"
+-
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
 -)
 -
--// MaxSize is the maximum size of a log file in bytes.
--var MaxSize uint64 = 1024 * 1024 * 1800
+-// ListOptsBuilder allows extensions to add additional parameters to the
+-// List request.
+-type ListOptsBuilder interface {
+-	ToServerListQuery() (string, error)
+-}
 -
--// logDirs lists the candidate directories for new log files.
--var logDirs []string
+-// ListOpts allows the filtering and sorting of paginated collections through
+-// the API. Filtering is achieved by passing in struct field values that map to
+-// the server attributes you want to see returned. Marker and Limit are used
+-// for pagination.
+-type ListOpts struct {
+-	// A time/date stamp for when the server last changed status.
+-	ChangesSince string `q:"changes-since"`
 -
--// If non-empty, overrides the choice of directory in which to write logs.
--// See createLogDirs for the full list of possible destinations.
--var logDir = flag.String("log_dir", "", "If non-empty, write log files in this directory")
+-	// Name of the image in URL format.
+-	Image string `q:"image"`
 -
--func createLogDirs() {
--	if *logDir != "" {
--		logDirs = append(logDirs, *logDir)
+-	// Name of the flavor in URL format.
+-	Flavor string `q:"flavor"`
+-
+-	// Name of the server as a string; can be queried with regular expressions.
+-	// Realize that ?name=bob returns both bob and bobb. If you need to match bob
+-	// only, you can use a regular expression matching the syntax of the
+-	// underlying database server implemented for Compute.
+-	Name string `q:"name"`
+-
+-	// Value of the status of the server so that you can filter on "ACTIVE" for example.
+-	Status string `q:"status"`
+-
+-	// Name of the host as a string.
+-	Host string `q:"host"`
+-
+-	// UUID of the server at which you want to set a marker.
+-	Marker string `q:"marker"`
+-
+-	// Integer value for the limit of values to return.
+-	Limit int `q:"limit"`
+-}
+-
+-// ToServerListQuery formats a ListOpts into a query string.
+-func (opts ListOpts) ToServerListQuery() (string, error) {
+-	q, err := gophercloud.BuildQueryString(opts)
+-	if err != nil {
+-		return "", err
 -	}
--	logDirs = append(logDirs, os.TempDir())
+-	return q.String(), nil
 -}
 -
--var (
--	pid      = os.Getpid()
--	program  = filepath.Base(os.Args[0])
--	host     = "unknownhost"
--	userName = "unknownuser"
--)
+-// List makes a request against the API to list servers accessible to you.
+-func List(client *gophercloud.ServiceClient, opts ListOptsBuilder) pagination.Pager {
+-	url := listDetailURL(client)
 -
--func init() {
--	h, err := os.Hostname()
--	if err == nil {
--		host = shortHostname(h)
+-	if opts != nil {
+-		query, err := opts.ToServerListQuery()
+-		if err != nil {
+-			return pagination.Pager{Err: err}
+-		}
+-		url += query
 -	}
 -
--	current, err := user.Current()
--	if err == nil {
--		userName = current.Username
+-	createPageFn := func(r pagination.PageResult) pagination.Page {
+-		return ServerPage{pagination.LinkedPageBase{PageResult: r}}
 -	}
 -
--	// Sanitize userName since it may contain filepath separators on Windows.
--	userName = strings.Replace(userName, `\`, "_", -1)
+-	return pagination.NewPager(client, url, createPageFn)
 -}
 -
--// shortHostname returns its argument, truncating at the first period.
--// For instance, given "www.google.com" it returns "www".
--func shortHostname(hostname string) string {
--	if i := strings.Index(hostname, "."); i >= 0 {
--		return hostname[:i]
--	}
--	return hostname
+-// CreateOptsBuilder describes struct types that can be accepted by the Create call.
+-// The CreateOpts struct in this package does.
+-type CreateOptsBuilder interface {
+-	ToServerCreateMap() (map[string]interface{}, error)
 -}
 -
--// logName returns a new log file name containing tag, with start time t, and
--// the name for the symlink for tag.
--func logName(tag string, t time.Time) (name, link string) {
--	name = fmt.Sprintf("%s.%s.%s.log.%s.%04d%02d%02d-%02d%02d%02d.%d",
--		program,
--		host,
--		userName,
--		tag,
--		t.Year(),
--		t.Month(),
--		t.Day(),
--		t.Hour(),
--		t.Minute(),
--		t.Second(),
--		pid)
--	return name, program + "." + tag
--}
+-// Network is used within CreateOpts to control a new server's network attachments.
+-type Network struct {
+-	// UUID of a nova-network to attach to the newly provisioned server.
+-	// Required unless Port is provided.
+-	UUID string
 -
--var onceLogDirs sync.Once
+-	// Port of a neutron network to attach to the newly provisioned server.
+-	// Required unless UUID is provided.
+-	Port string
 -
--// create creates a new log file and returns the file and its filename, which
--// contains tag ("INFO", "FATAL", etc.) and t.  If the file is created
--// successfully, create also attempts to update the symlink for that tag, ignoring
--// errors.
--func create(tag string, t time.Time) (f *os.File, filename string, err error) {
--	onceLogDirs.Do(createLogDirs)
--	if len(logDirs) == 0 {
--		return nil, "", errors.New("log: no log dirs")
--	}
--	name, link := logName(tag, t)
--	var lastErr error
--	for _, dir := range logDirs {
--		fname := filepath.Join(dir, name)
--		f, err := os.Create(fname)
--		if err == nil {
--			symlink := filepath.Join(dir, link)
--			os.Remove(symlink)        // ignore err
--			os.Symlink(name, symlink) // ignore err
--			return f, fname, nil
--		}
--		lastErr = err
--	}
--	return nil, "", fmt.Errorf("log: cannot create log: %v", lastErr)
+-	// FixedIP [optional] specifies a fixed IPv4 address to be used on this network.
+-	FixedIP string
 -}
-diff --git a/Godeps/_workspace/src/github.com/golang/glog/glog_test.go b/Godeps/_workspace/src/github.com/golang/glog/glog_test.go
-deleted file mode 100644
-index 0fb376e..0000000
---- a/Godeps/_workspace/src/github.com/golang/glog/glog_test.go
-+++ /dev/null
-@@ -1,415 +0,0 @@
--// Go support for leveled logs, analogous to https://code.google.com/p/google-glog/
--//
--// Copyright 2013 Google Inc. All Rights Reserved.
--//
--// Licensed under the Apache License, Version 2.0 (the "License");
--// you may not use this file except in compliance with the License.
--// You may obtain a copy of the License at
--//
--//     http://www.apache.org/licenses/LICENSE-2.0
--//
--// Unless required by applicable law or agreed to in writing, software
--// distributed under the License is distributed on an "AS IS" BASIS,
--// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
--// See the License for the specific language governing permissions and
--// limitations under the License.
 -
--package glog
+-// CreateOpts specifies server creation parameters.
+-type CreateOpts struct {
+-	// Name [required] is the name to assign to the newly launched server.
+-	Name string
 -
--import (
--	"bytes"
--	"fmt"
--	stdLog "log"
--	"path/filepath"
--	"runtime"
--	"strconv"
--	"strings"
--	"testing"
--	"time"
--)
+-	// ImageRef [required] is the ID or full URL to the image that contains the server's OS and initial state.
+-	// Optional if using the boot-from-volume extension.
+-	ImageRef string
 -
--// Test that shortHostname works as advertised.
--func TestShortHostname(t *testing.T) {
--	for hostname, expect := range map[string]string{
--		"":                "",
--		"host":            "host",
--		"host.google.com": "host",
--	} {
--		if got := shortHostname(hostname); expect != got {
--			t.Errorf("shortHostname(%q): expected %q, got %q", hostname, expect, got)
--		}
--	}
--}
+-	// FlavorRef [required] is the ID or full URL to the flavor that describes the server's specs.
+-	FlavorRef string
 -
--// flushBuffer wraps a bytes.Buffer to satisfy flushSyncWriter.
--type flushBuffer struct {
--	bytes.Buffer
--}
+-	// SecurityGroups [optional] lists the names of the security groups to which this server should belong.
+-	SecurityGroups []string
 -
--func (f *flushBuffer) Flush() error {
--	return nil
--}
+-	// UserData [optional] contains configuration information or scripts to use upon launch.
+-	// Create will base64-encode it for you.
+-	UserData []byte
 -
--func (f *flushBuffer) Sync() error {
--	return nil
--}
+-	// AvailabilityZone [optional] in which to launch the server.
+-	AvailabilityZone string
 -
--// swap sets the log writers and returns the old array.
--func (l *loggingT) swap(writers [numSeverity]flushSyncWriter) (old [numSeverity]flushSyncWriter) {
--	l.mu.Lock()
--	defer l.mu.Unlock()
--	old = l.file
--	for i, w := range writers {
--		logging.file[i] = w
--	}
--	return
--}
+-	// Networks [optional] dictates how this server will be attached to available networks.
+-	// By default, the server will be attached to all isolated networks for the tenant.
+-	Networks []Network
 -
--// newBuffers sets the log writers to all new byte buffers and returns the old array.
--func (l *loggingT) newBuffers() [numSeverity]flushSyncWriter {
--	return l.swap([numSeverity]flushSyncWriter{new(flushBuffer), new(flushBuffer), new(flushBuffer), new(flushBuffer)})
--}
+-	// Metadata [optional] contains key-value pairs (up to 255 bytes each) to attach to the server.
+-	Metadata map[string]string
 -
--// contents returns the specified log value as a string.
--func contents(s severity) string {
--	return logging.file[s].(*flushBuffer).String()
--}
+-	// Personality [optional] includes the path and contents of a file to inject into the server at launch.
+-	// The maximum size of the file is 255 bytes (decoded).
+-	Personality []byte
 -
--// contains reports whether the string is contained in the log.
--func contains(s severity, str string, t *testing.T) bool {
--	return strings.Contains(contents(s), str)
+-	// ConfigDrive [optional] enables metadata injection through a configuration drive.
+-	ConfigDrive bool
 -}
 -
--// setFlags configures the logging flags how the test expects them.
--func setFlags() {
--	logging.toStderr = false
--}
+-// ToServerCreateMap assembles a request body based on the contents of a CreateOpts.
+-func (opts CreateOpts) ToServerCreateMap() (map[string]interface{}, error) {
+-	server := make(map[string]interface{})
 -
--// Test that Info works as advertised.
--func TestInfo(t *testing.T) {
--	setFlags()
--	defer logging.swap(logging.newBuffers())
--	Info("test")
--	if !contains(infoLog, "I", t) {
--		t.Errorf("Info has wrong character: %q", contents(infoLog))
+-	server["name"] = opts.Name
+-	server["imageRef"] = opts.ImageRef
+-	server["flavorRef"] = opts.FlavorRef
+-
+-	if opts.UserData != nil {
+-		encoded := base64.StdEncoding.EncodeToString(opts.UserData)
+-		server["user_data"] = &encoded
 -	}
--	if !contains(infoLog, "test", t) {
--		t.Error("Info failed")
+-	if opts.Personality != nil {
+-		encoded := base64.StdEncoding.EncodeToString(opts.Personality)
+-		server["personality"] = &encoded
+-	}
+-	if opts.ConfigDrive {
+-		server["config_drive"] = "true"
+-	}
+-	if opts.AvailabilityZone != "" {
+-		server["availability_zone"] = opts.AvailabilityZone
+-	}
+-	if opts.Metadata != nil {
+-		server["metadata"] = opts.Metadata
 -	}
--}
 -
--func TestInfoDepth(t *testing.T) {
--	setFlags()
--	defer logging.swap(logging.newBuffers())
+-	if len(opts.SecurityGroups) > 0 {
+-		securityGroups := make([]map[string]interface{}, len(opts.SecurityGroups))
+-		for i, groupName := range opts.SecurityGroups {
+-			securityGroups[i] = map[string]interface{}{"name": groupName}
+-		}
+-	}
 -
--	f := func() { InfoDepth(1, "depth-test1") }
+-	if len(opts.Networks) > 0 {
+-		networks := make([]map[string]interface{}, len(opts.Networks))
+-		for i, net := range opts.Networks {
+-			networks[i] = make(map[string]interface{})
+-			if net.UUID != "" {
+-				networks[i]["uuid"] = net.UUID
+-			}
+-			if net.Port != "" {
+-				networks[i]["port"] = net.Port
+-			}
+-			if net.FixedIP != "" {
+-				networks[i]["fixed_ip"] = net.FixedIP
+-			}
+-		}
+-		server["networks"] = networks
+-	}
 -
--	// The next three lines must stay together
--	_, _, wantLine, _ := runtime.Caller(0)
--	InfoDepth(0, "depth-test0")
--	f()
+-	return map[string]interface{}{"server": server}, nil
+-}
 -
--	msgs := strings.Split(strings.TrimSuffix(contents(infoLog), "\n"), "\n")
--	if len(msgs) != 2 {
--		t.Fatalf("Got %d lines, expected 2", len(msgs))
+-// Create requests a server to be provisioned to the user in the current tenant.
+-func Create(client *gophercloud.ServiceClient, opts CreateOptsBuilder) CreateResult {
+-	var res CreateResult
+-
+-	reqBody, err := opts.ToServerCreateMap()
+-	if err != nil {
+-		res.Err = err
+-		return res
 -	}
 -
--	for i, m := range msgs {
--		if !strings.HasPrefix(m, "I") {
--			t.Errorf("InfoDepth[%d] has wrong character: %q", i, m)
--		}
--		w := fmt.Sprintf("depth-test%d", i)
--		if !strings.Contains(m, w) {
--			t.Errorf("InfoDepth[%d] missing %q: %q", i, w, m)
--		}
+-	_, res.Err = perigee.Request("POST", listURL(client), perigee.Options{
+-		Results:     &res.Body,
+-		ReqBody:     reqBody,
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{202},
+-	})
+-	return res
+-}
 -
--		// pull out the line number (between : and ])
--		msg := m[strings.LastIndex(m, ":")+1:]
--		x := strings.Index(msg, "]")
--		if x < 0 {
--			t.Errorf("InfoDepth[%d]: missing ']': %q", i, m)
--			continue
--		}
--		line, err := strconv.Atoi(msg[:x])
--		if err != nil {
--			t.Errorf("InfoDepth[%d]: bad line number: %q", i, m)
--			continue
--		}
--		wantLine++
--		if wantLine != line {
--			t.Errorf("InfoDepth[%d]: got line %d, want %d", i, line, wantLine)
--		}
--	}
+-// Delete requests that a server previously provisioned be removed from your account.
+-func Delete(client *gophercloud.ServiceClient, id string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", deleteURL(client, id), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{204},
+-	})
+-	return res
 -}
 -
--func init() {
--	CopyStandardLogTo("INFO")
+-// Get requests details on a single server, by ID.
+-func Get(client *gophercloud.ServiceClient, id string) GetResult {
+-	var result GetResult
+-	_, result.Err = perigee.Request("GET", getURL(client, id), perigee.Options{
+-		Results:     &result.Body,
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-	})
+-	return result
 -}
 -
--// Test that CopyStandardLogTo panics on bad input.
--func TestCopyStandardLogToPanic(t *testing.T) {
--	defer func() {
--		if s, ok := recover().(string); !ok || !strings.Contains(s, "LOG") {
--			t.Errorf(`CopyStandardLogTo("LOG") should have panicked: %v`, s)
--		}
--	}()
--	CopyStandardLogTo("LOG")
+-// UpdateOptsBuilder allows extensions to add additional attributes to the Update request.
+-type UpdateOptsBuilder interface {
+-	ToServerUpdateMap() map[string]interface{}
 -}
 -
--// Test that using the standard log package logs to INFO.
--func TestStandardLog(t *testing.T) {
--	setFlags()
--	defer logging.swap(logging.newBuffers())
--	stdLog.Print("test")
--	if !contains(infoLog, "I", t) {
--		t.Errorf("Info has wrong character: %q", contents(infoLog))
--	}
--	if !contains(infoLog, "test", t) {
--		t.Error("Info failed")
--	}
+-// UpdateOpts specifies the base attributes that may be updated on an existing server.
+-type UpdateOpts struct {
+-	// Name [optional] changes the displayed name of the server.
+-	// The server host name will *not* change.
+-	// Server names are not constrained to be unique, even within the same tenant.
+-	Name string
+-
+-	// AccessIPv4 [optional] provides a new IPv4 address for the instance.
+-	AccessIPv4 string
+-
+-	// AccessIPv6 [optional] provides a new IPv6 address for the instance.
+-	AccessIPv6 string
 -}
 -
--// Test that the header has the correct format.
--func TestHeader(t *testing.T) {
--	setFlags()
--	defer logging.swap(logging.newBuffers())
--	defer func(previous func() time.Time) { timeNow = previous }(timeNow)
--	timeNow = func() time.Time {
--		return time.Date(2006, 1, 2, 15, 4, 5, .067890e9, time.Local)
+-// ToServerUpdateMap formats an UpdateOpts structure into a request body.
+-func (opts UpdateOpts) ToServerUpdateMap() map[string]interface{} {
+-	server := make(map[string]string)
+-	if opts.Name != "" {
+-		server["name"] = opts.Name
 -	}
--	pid = 1234
--	Info("test")
--	var line int
--	format := "I0102 15:04:05.067890    1234 glog_test.go:%d] test\n"
--	n, err := fmt.Sscanf(contents(infoLog), format, &line)
--	if n != 1 || err != nil {
--		t.Errorf("log format error: %d elements, error %s:\n%s", n, err, contents(infoLog))
+-	if opts.AccessIPv4 != "" {
+-		server["accessIPv4"] = opts.AccessIPv4
 -	}
--	// Scanf treats multiple spaces as equivalent to a single space,
--	// so check for correct space-padding also.
--	want := fmt.Sprintf(format, line)
--	if contents(infoLog) != want {
--		t.Errorf("log format error: got:\n\t%q\nwant:\t%q", contents(infoLog), want)
+-	if opts.AccessIPv6 != "" {
+-		server["accessIPv6"] = opts.AccessIPv6
 -	}
+-	return map[string]interface{}{"server": server}
 -}
 -
--// Test that an Error log goes to Warning and Info.
--// Even in the Info log, the source character will be E, so the data should
--// all be identical.
--func TestError(t *testing.T) {
--	setFlags()
--	defer logging.swap(logging.newBuffers())
--	Error("test")
--	if !contains(errorLog, "E", t) {
--		t.Errorf("Error has wrong character: %q", contents(errorLog))
--	}
--	if !contains(errorLog, "test", t) {
--		t.Error("Error failed")
--	}
--	str := contents(errorLog)
--	if !contains(warningLog, str, t) {
--		t.Error("Warning failed")
--	}
--	if !contains(infoLog, str, t) {
--		t.Error("Info failed")
--	}
+-// Update requests that various attributes of the indicated server be changed.
+-func Update(client *gophercloud.ServiceClient, id string, opts UpdateOptsBuilder) UpdateResult {
+-	var result UpdateResult
+-	_, result.Err = perigee.Request("PUT", updateURL(client, id), perigee.Options{
+-		Results:     &result.Body,
+-		ReqBody:     opts.ToServerUpdateMap(),
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-	})
+-	return result
 -}
 -
--// Test that a Warning log goes to Info.
--// Even in the Info log, the source character will be W, so the data should
--// all be identical.
--func TestWarning(t *testing.T) {
--	setFlags()
--	defer logging.swap(logging.newBuffers())
--	Warning("test")
--	if !contains(warningLog, "W", t) {
--		t.Errorf("Warning has wrong character: %q", contents(warningLog))
--	}
--	if !contains(warningLog, "test", t) {
--		t.Error("Warning failed")
--	}
--	str := contents(warningLog)
--	if !contains(infoLog, str, t) {
--		t.Error("Info failed")
+-// ChangeAdminPassword alters the administrator or root password for a specified server.
+-func ChangeAdminPassword(client *gophercloud.ServiceClient, id, newPassword string) ActionResult {
+-	var req struct {
+-		ChangePassword struct {
+-			AdminPass string `json:"adminPass"`
+-		} `json:"changePassword"`
 -	}
+-
+-	req.ChangePassword.AdminPass = newPassword
+-
+-	var res ActionResult
+-
+-	_, res.Err = perigee.Request("POST", actionURL(client, id), perigee.Options{
+-		ReqBody:     req,
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{202},
+-	})
+-
+-	return res
 -}
 -
--// Test that a V log goes to Info.
--func TestV(t *testing.T) {
--	setFlags()
--	defer logging.swap(logging.newBuffers())
--	logging.verbosity.Set("2")
--	defer logging.verbosity.Set("0")
--	V(2).Info("test")
--	if !contains(infoLog, "I", t) {
--		t.Errorf("Info has wrong character: %q", contents(infoLog))
--	}
--	if !contains(infoLog, "test", t) {
--		t.Error("Info failed")
--	}
+-// ErrArgument errors occur when an argument supplied to a package function
+-// fails to fall within acceptable values.  For example, the Reboot() function
+-// expects the "how" parameter to be one of HardReboot or SoftReboot.  These
+-// constants are (currently) strings, leading someone to wonder if they can pass
+-// other string values instead, perhaps in an effort to break the API of their
+-// provider.  Reboot() returns this error in this situation.
+-//
+-// Function identifies which function was called/which function is generating
+-// the error.
+-// Argument identifies which formal argument was responsible for producing the
+-// error.
+-// Value provides the value as it was passed into the function.
+-type ErrArgument struct {
+-	Function, Argument string
+-	Value              interface{}
 -}
 -
--// Test that a vmodule enables a log in this file.
--func TestVmoduleOn(t *testing.T) {
--	setFlags()
--	defer logging.swap(logging.newBuffers())
--	logging.vmodule.Set("glog_test=2")
--	defer logging.vmodule.Set("")
--	if !V(1) {
--		t.Error("V not enabled for 1")
--	}
--	if !V(2) {
--		t.Error("V not enabled for 2")
--	}
--	if V(3) {
--		t.Error("V enabled for 3")
--	}
--	V(2).Info("test")
--	if !contains(infoLog, "I", t) {
--		t.Errorf("Info has wrong character: %q", contents(infoLog))
--	}
--	if !contains(infoLog, "test", t) {
--		t.Error("Info failed")
--	}
+-// Error yields a useful diagnostic for debugging purposes.
+-func (e *ErrArgument) Error() string {
+-	return fmt.Sprintf("Bad argument in call to %s, formal parameter %s, value %#v", e.Function, e.Argument, e.Value)
 -}
 -
--// Test that a vmodule of another file does not enable a log in this file.
--func TestVmoduleOff(t *testing.T) {
--	setFlags()
--	defer logging.swap(logging.newBuffers())
--	logging.vmodule.Set("notthisfile=2")
--	defer logging.vmodule.Set("")
--	for i := 1; i <= 3; i++ {
--		if V(Level(i)) {
--			t.Errorf("V enabled for %d", i)
+-func (e *ErrArgument) String() string {
+-	return e.Error()
+-}
+-
+-// RebootMethod describes the mechanisms by which a server reboot can be requested.
+-type RebootMethod string
+-
+-// These constants determine how a server should be rebooted.
+-// See the Reboot() function for further details.
+-const (
+-	SoftReboot RebootMethod = "SOFT"
+-	HardReboot RebootMethod = "HARD"
+-	OSReboot                = SoftReboot
+-	PowerCycle              = HardReboot
+-)
+-
+-// Reboot requests that a given server reboot.
+-// Two methods exist for rebooting a server:
+-//
+-// HardReboot (aka PowerCycle) restarts the server instance by physically cutting power to the machine, or if a VM,
+-// terminating it at the hypervisor level.
+-// It's done. Caput. Full stop.
+-// Then, after a brief while, power is restored or the VM instance restarted.
+-//
+-// SoftReboot (aka OSReboot) simply tells the OS to restart under its own procedures.
+-// E.g., in Linux, asking it to enter runlevel 6, or executing "sudo shutdown -r now", or by asking Windows to restart the machine.
+-func Reboot(client *gophercloud.ServiceClient, id string, how RebootMethod) ActionResult {
+-	var res ActionResult
+-
+-	if (how != SoftReboot) && (how != HardReboot) {
+-		res.Err = &ErrArgument{
+-			Function: "Reboot",
+-			Argument: "how",
+-			Value:    how,
 -		}
+-		return res
 -	}
--	V(2).Info("test")
--	if contents(infoLog) != "" {
--		t.Error("V logged incorrectly")
--	}
--}
 -
--// vGlobs are patterns that match/don't match this file at V=2.
--var vGlobs = map[string]bool{
--	// Easy to test the numeric match here.
--	"glog_test=1": false, // If -vmodule sets V to 1, V(2) will fail.
--	"glog_test=2": true,
--	"glog_test=3": true, // If -vmodule sets V to 1, V(3) will succeed.
--	// These all use 2 and check the patterns. All are true.
--	"*=2":           true,
--	"?l*=2":         true,
--	"????_*=2":      true,
--	"??[mno]?_*t=2": true,
--	// These all use 2 and check the patterns. All are false.
--	"*x=2":         false,
--	"m*=2":         false,
--	"??_*=2":       false,
--	"?[abc]?_*t=2": false,
+-	_, res.Err = perigee.Request("POST", actionURL(client, id), perigee.Options{
+-		ReqBody: struct {
+-			C map[string]string `json:"reboot"`
+-		}{
+-			map[string]string{"type": string(how)},
+-		},
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{202},
+-	})
+-
+-	return res
 -}
 -
--// Test that vmodule globbing works as advertised.
--func testVmoduleGlob(pat string, match bool, t *testing.T) {
--	setFlags()
--	defer logging.swap(logging.newBuffers())
--	defer logging.vmodule.Set("")
--	logging.vmodule.Set(pat)
--	if V(2) != Verbose(match) {
--		t.Errorf("incorrect match for %q: got %t expected %t", pat, V(2), match)
--	}
+-// RebuildOptsBuilder is an interface that allows extensions to override the
+-// default behaviour of rebuild options
+-type RebuildOptsBuilder interface {
+-	ToServerRebuildMap() (map[string]interface{}, error)
 -}
 -
--// Test that a vmodule globbing works as advertised.
--func TestVmoduleGlob(t *testing.T) {
--	for glob, match := range vGlobs {
--		testVmoduleGlob(glob, match, t)
--	}
+-// RebuildOpts represents the configuration options used in a server rebuild
+-// operation
+-type RebuildOpts struct {
+-	// Required. The ID of the image you want your server to be provisioned on
+-	ImageID string
+-
+-	// Name to set the server to
+-	Name string
+-
+-	// Required. The server's admin password
+-	AdminPass string
+-
+-	// AccessIPv4 [optional] provides a new IPv4 address for the instance.
+-	AccessIPv4 string
+-
+-	// AccessIPv6 [optional] provides a new IPv6 address for the instance.
+-	AccessIPv6 string
+-
+-	// Metadata [optional] contains key-value pairs (up to 255 bytes each) to attach to the server.
+-	Metadata map[string]string
+-
+-	// Personality [optional] includes the path and contents of a file to inject into the server at launch.
+-	// The maximum size of the file is 255 bytes (decoded).
+-	Personality []byte
 -}
 -
--func TestRollover(t *testing.T) {
--	setFlags()
+-// ToServerRebuildMap formats a RebuildOpts struct into a map for use in JSON
+-func (opts RebuildOpts) ToServerRebuildMap() (map[string]interface{}, error) {
 -	var err error
--	defer func(previous func(error)) { logExitFunc = previous }(logExitFunc)
--	logExitFunc = func(e error) {
--		err = e
--	}
--	defer func(previous uint64) { MaxSize = previous }(MaxSize)
--	MaxSize = 512
+-	server := make(map[string]interface{})
 -
--	Info("x") // Be sure we have a file.
--	info, ok := logging.file[infoLog].(*syncBuffer)
--	if !ok {
--		t.Fatal("info wasn't created")
+-	if opts.AdminPass == "" {
+-		err = fmt.Errorf("AdminPass is required")
 -	}
--	if err != nil {
--		t.Fatalf("info has initial error: %v", err)
+-
+-	if opts.ImageID == "" {
+-		err = fmt.Errorf("ImageID is required")
 -	}
--	fname0 := info.file.Name()
--	Info(strings.Repeat("x", int(MaxSize))) // force a rollover
+-
 -	if err != nil {
--		t.Fatalf("info has error after big write: %v", err)
+-		return server, err
 -	}
 -
--	// Make sure the next log file gets a file name with a different
--	// time stamp.
--	//
--	// TODO: determine whether we need to support subsecond log
--	// rotation.  C++ does not appear to handle this case (nor does it
--	// handle Daylight Savings Time properly).
--	time.Sleep(1 * time.Second)
+-	server["name"] = opts.Name
+-	server["adminPass"] = opts.AdminPass
+-	server["imageRef"] = opts.ImageID
 -
--	Info("x") // create a new file
--	if err != nil {
--		t.Fatalf("error after rotation: %v", err)
--	}
--	fname1 := info.file.Name()
--	if fname0 == fname1 {
--		t.Errorf("info.f.Name did not change: %v", fname0)
--	}
--	if info.nbytes >= MaxSize {
--		t.Errorf("file size was not reset: %d", info.nbytes)
+-	if opts.AccessIPv4 != "" {
+-		server["accessIPv4"] = opts.AccessIPv4
 -	}
--}
 -
--func TestLogBacktraceAt(t *testing.T) {
--	setFlags()
--	defer logging.swap(logging.newBuffers())
--	// The peculiar style of this code simplifies line counting and maintenance of the
--	// tracing block below.
--	var infoLine string
--	setTraceLocation := func(file string, line int, ok bool, delta int) {
--		if !ok {
--			t.Fatal("could not get file:line")
--		}
--		_, file = filepath.Split(file)
--		infoLine = fmt.Sprintf("%s:%d", file, line+delta)
--		err := logging.traceLocation.Set(infoLine)
--		if err != nil {
--			t.Fatal("error setting log_backtrace_at: ", err)
--		}
+-	if opts.AccessIPv6 != "" {
+-		server["accessIPv6"] = opts.AccessIPv6
 -	}
--	{
--		// Start of tracing block. These lines know about each other's relative position.
--		_, file, line, ok := runtime.Caller(0)
--		setTraceLocation(file, line, ok, +2) // Two lines between Caller and Info calls.
--		Info("we want a stack trace here")
+-
+-	if opts.Metadata != nil {
+-		server["metadata"] = opts.Metadata
 -	}
--	numAppearances := strings.Count(contents(infoLog), infoLine)
--	if numAppearances < 2 {
--		// Need 2 appearances, one in the log header and one in the trace:
--		//   log_test.go:281: I0511 16:36:06.952398 02238 log_test.go:280] we want a stack trace here
--		//   ...
--		//   github.com/glog/glog_test.go:280 (0x41ba91)
--		//   ...
--		// We could be more precise but that would require knowing the details
--		// of the traceback format, which may not be dependable.
--		t.Fatal("got no trace back; log is ", contents(infoLog))
+-
+-	if opts.Personality != nil {
+-		encoded := base64.StdEncoding.EncodeToString(opts.Personality)
+-		server["personality"] = &encoded
 -	}
+-
+-	return map[string]interface{}{"rebuild": server}, nil
 -}
 -
--func BenchmarkHeader(b *testing.B) {
--	for i := 0; i < b.N; i++ {
--		buf, _, _ := logging.header(infoLog, 0)
--		logging.putBuffer(buf)
+-// Rebuild will reprovision the server according to the configuration options
+-// provided in the RebuildOpts struct.
+-func Rebuild(client *gophercloud.ServiceClient, id string, opts RebuildOptsBuilder) RebuildResult {
+-	var result RebuildResult
+-
+-	if id == "" {
+-		result.Err = fmt.Errorf("ID is required")
+-		return result
 -	}
--}
-diff --git a/Godeps/_workspace/src/github.com/google/cadvisor/client/README.md b/Godeps/_workspace/src/github.com/google/cadvisor/client/README.md
-deleted file mode 100644
-index fededef..0000000
---- a/Godeps/_workspace/src/github.com/google/cadvisor/client/README.md
-+++ /dev/null
-@@ -1,54 +0,0 @@
--# Example REST API Client
 -
--This is an implementation of a cAdvisor REST API in Go.  You can use it like this:
+-	reqBody, err := opts.ToServerRebuildMap()
+-	if err != nil {
+-		result.Err = err
+-		return result
+-	}
 -
--```go
--client, err := client.NewClient("http://192.168.59.103:8080/")
--```
+-	_, result.Err = perigee.Request("POST", actionURL(client, id), perigee.Options{
+-		ReqBody:     &reqBody,
+-		Results:     &result.Body,
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{202},
+-	})
 -
--Obviously, replace the URL with the path to your actual cAdvisor REST endpoint.
+-	return result
+-}
 -
+-// ResizeOptsBuilder is an interface that allows extensions to override the default structure of
+-// a Resize request.
+-type ResizeOptsBuilder interface {
+-	ToServerResizeMap() (map[string]interface{}, error)
+-}
 -
--### MachineInfo
+-// ResizeOpts represents the configuration options used to control a Resize operation.
+-type ResizeOpts struct {
+-	// FlavorRef is the ID of the flavor you wish your server to become.
+-	FlavorRef string
+-}
 -
--```go
--client.MachineInfo()
--```
+-// ToServerResizeMap formats a ResizeOpts as a map that can be used as a JSON request body to the
+-// Resize request.
+-func (opts ResizeOpts) ToServerResizeMap() (map[string]interface{}, error) {
+-	resize := map[string]interface{}{
+-		"flavorRef": opts.FlavorRef,
+-	}
 -
--This method returns a cadvisor/info.MachineInfo struct with all the fields filled in.  Here is an example return value:
+-	return map[string]interface{}{"resize": resize}, nil
+-}
 -
--```
--(*info.MachineInfo)(0xc208022b10)({
-- NumCores: (int) 4,
-- MemoryCapacity: (int64) 2106028032,
-- Filesystems: ([]info.FsInfo) (len=1 cap=4) {
--  (info.FsInfo) {
--   Device: (string) (len=9) "/dev/sda1",
--   Capacity: (uint64) 19507089408
--  }
-- }
--})
--```
+-// Resize instructs the provider to change the flavor of the server.
+-// Note that this implies rebuilding it.
+-// Unfortunately, one cannot pass rebuild parameters to the resize function.
+-// When the resize completes, the server will be in RESIZE_VERIFY state.
+-// While in this state, you can explore the use of the new server's configuration.
+-// If you like it, call ConfirmResize() to commit the resize permanently.
+-// Otherwise, call RevertResize() to restore the old configuration.
+-func Resize(client *gophercloud.ServiceClient, id string, opts ResizeOptsBuilder) ActionResult {
+-	var res ActionResult
+-	reqBody, err := opts.ToServerResizeMap()
+-	if err != nil {
+-		res.Err = err
+-		return res
+-	}
 -
--You can see the full specification of the [MachineInfo struct in the source](../info/container.go)
+-	_, res.Err = perigee.Request("POST", actionURL(client, id), perigee.Options{
+-		ReqBody:     reqBody,
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{202},
+-	})
 -
--### ContainerInfo
+-	return res
+-}
 -
--Given a container name and a ContainerInfoRequest, will return all information about the specified container.  The ContainerInfoRequest struct just has one field, NumStats, which is the number of stat entries that you want returned.
+-// ConfirmResize confirms a previous resize operation on a server.
+-// See Resize() for more details.
+-func ConfirmResize(client *gophercloud.ServiceClient, id string) ActionResult {
+-	var res ActionResult
 -
--```go
--request := info.ContainerInfoRequest{10}
--sInfo, err := client.ContainerInfo("/docker/d9d3eb10179e6f93a...", &request)
--```
--Returns a [ContainerInfo struct](../info/container.go)
+-	_, res.Err = perigee.Request("POST", actionURL(client, id), perigee.Options{
+-		ReqBody:     map[string]interface{}{"confirmResize": nil},
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{204},
+-	})
 -
--### SubcontainersInfo
+-	return res
+-}
 -
--Given a container name and a ContainerInfoRequest, will recursively return all info about the container and all subcontainers contained within the container.  The ContainerInfoRequest struct just has one field, NumStats, which is the number of stat entries that you want returned.
+-// RevertResize cancels a previous resize operation on a server.
+-// See Resize() for more details.
+-func RevertResize(client *gophercloud.ServiceClient, id string) ActionResult {
+-	var res ActionResult
 -
--```go
--request := info.ContainerInfoRequest{10}
--sInfo, err := client.SubcontainersInfo("/docker", &request)
--```
+-	_, res.Err = perigee.Request("POST", actionURL(client, id), perigee.Options{
+-		ReqBody:     map[string]interface{}{"revertResize": nil},
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{202},
+-	})
 -
--Returns a [ContainerInfo struct](../info/container.go) with the Subcontainers field populated.
-diff --git a/Godeps/_workspace/src/github.com/google/cadvisor/client/client.go b/Godeps/_workspace/src/github.com/google/cadvisor/client/client.go
+-	return res
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/requests_test.go
 deleted file mode 100644
-index 5c016e0..0000000
---- a/Godeps/_workspace/src/github.com/google/cadvisor/client/client.go
+index 392e2d8..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/requests_test.go
 +++ /dev/null
-@@ -1,161 +0,0 @@
--// Copyright 2014 Google Inc. All Rights Reserved.
--//
--// Licensed under the Apache License, Version 2.0 (the "License");
--// you may not use this file except in compliance with the License.
--// You may obtain a copy of the License at
--//
--//     http://www.apache.org/licenses/LICENSE-2.0
--//
--// Unless required by applicable law or agreed to in writing, software
--// distributed under the License is distributed on an "AS IS" BASIS,
--// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
--// See the License for the specific language governing permissions and
--// limitations under the License.
--
--// TODO(cAdvisor): Package comment.
--package client
+@@ -1,176 +0,0 @@
+-package servers
 -
 -import (
--	"bytes"
--	"encoding/json"
--	"fmt"
--	"io/ioutil"
 -	"net/http"
--	"path"
--	"strings"
+-	"testing"
 -
--	"github.com/google/cadvisor/info"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
 -)
 -
--// Client represents the base URL for a cAdvisor client.
--type Client struct {
--	baseUrl string
--}
+-func TestListServers(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleServerListSuccessfully(t)
 -
--// NewClient returns a new client with the specified base URL.
--func NewClient(url string) (*Client, error) {
--	if !strings.HasSuffix(url, "/") {
--		url += "/"
--	}
+-	pages := 0
+-	err := List(client.ServiceClient(), ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		pages++
 -
--	return &Client{
--		baseUrl: fmt.Sprintf("%sapi/v1.2/", url),
--	}, nil
--}
+-		actual, err := ExtractServers(page)
+-		if err != nil {
+-			return false, err
+-		}
 -
--// MachineInfo returns the JSON machine information for this client.
--// A non-nil error result indicates a problem with obtaining
--// the JSON machine information data.
--func (self *Client) MachineInfo() (minfo *info.MachineInfo, err error) {
--	u := self.machineInfoUrl()
--	ret := new(info.MachineInfo)
--	if err = self.httpGetJsonData(ret, nil, u, "machine info"); err != nil {
--		return
+-		if len(actual) != 2 {
+-			t.Fatalf("Expected 2 servers, got %d", len(actual))
+-		}
+-		th.CheckDeepEquals(t, ServerHerp, actual[0])
+-		th.CheckDeepEquals(t, ServerDerp, actual[1])
+-
+-		return true, nil
+-	})
+-
+-	th.AssertNoErr(t, err)
+-
+-	if pages != 1 {
+-		t.Errorf("Expected 1 page, saw %d", pages)
 -	}
--	minfo = ret
--	return
 -}
 -
--// ContainerInfo returns the JSON container information for the specified
--// container and request.
--func (self *Client) ContainerInfo(name string, query *info.ContainerInfoRequest) (cinfo *info.ContainerInfo, err error) {
--	u := self.containerInfoUrl(name)
--	ret := new(info.ContainerInfo)
--	if err = self.httpGetJsonData(ret, query, u, fmt.Sprintf("container info for %q", name)); err != nil {
--		return
--	}
--	cinfo = ret
--	return
+-func TestCreateServer(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleServerCreationSuccessfully(t, SingleServerBody)
+-
+-	actual, err := Create(client.ServiceClient(), CreateOpts{
+-		Name:      "derp",
+-		ImageRef:  "f90f6034-2570-4974-8351-6b49732ef2eb",
+-		FlavorRef: "1",
+-	}).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.CheckDeepEquals(t, ServerDerp, *actual)
 -}
 -
--// Returns the information about all subcontainers (recursive) of the specified container (including itself).
--func (self *Client) SubcontainersInfo(name string, query *info.ContainerInfoRequest) ([]info.ContainerInfo, error) {
--	var response []info.ContainerInfo
--	url := self.subcontainersInfoUrl(name)
--	err := self.httpGetJsonData(&response, query, url, fmt.Sprintf("subcontainers container info for %q", name))
--	if err != nil {
--		return []info.ContainerInfo{}, err
+-func TestDeleteServer(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleServerDeletionSuccessfully(t)
 -
--	}
--	return response, nil
+-	res := Delete(client.ServiceClient(), "asdfasdfasdf")
+-	th.AssertNoErr(t, res.Err)
 -}
 -
--// Returns the JSON container information for the specified
--// Docker container and request.
--func (self *Client) DockerContainer(name string, query *info.ContainerInfoRequest) (cinfo info.ContainerInfo, err error) {
--	u := self.dockerInfoUrl(name)
--	ret := make(map[string]info.ContainerInfo)
--	if err = self.httpGetJsonData(&ret, query, u, fmt.Sprintf("Docker container info for %q", name)); err != nil {
--		return
--	}
--	if len(ret) != 1 {
--		err = fmt.Errorf("expected to only receive 1 Docker container: %+v", ret)
--		return
--	}
--	for _, cont := range ret {
--		cinfo = cont
+-func TestGetServer(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleServerGetSuccessfully(t)
+-
+-	client := client.ServiceClient()
+-	actual, err := Get(client, "1234asdf").Extract()
+-	if err != nil {
+-		t.Fatalf("Unexpected Get error: %v", err)
 -	}
--	return
+-
+-	th.CheckDeepEquals(t, ServerDerp, *actual)
 -}
 -
--// Returns the JSON container information for all Docker containers.
--func (self *Client) AllDockerContainers(query *info.ContainerInfoRequest) (cinfo []info.ContainerInfo, err error) {
--	u := self.dockerInfoUrl("/")
--	ret := make(map[string]info.ContainerInfo)
--	if err = self.httpGetJsonData(&ret, query, u, "all Docker containers info"); err != nil {
--		return
--	}
--	cinfo = make([]info.ContainerInfo, 0, len(ret))
--	for _, cont := range ret {
--		cinfo = append(cinfo, cont)
+-func TestUpdateServer(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleServerUpdateSuccessfully(t)
+-
+-	client := client.ServiceClient()
+-	actual, err := Update(client, "1234asdf", UpdateOpts{Name: "new-name"}).Extract()
+-	if err != nil {
+-		t.Fatalf("Unexpected Update error: %v", err)
 -	}
--	return
--}
 -
--func (self *Client) machineInfoUrl() string {
--	return self.baseUrl + path.Join("machine")
+-	th.CheckDeepEquals(t, ServerDerp, *actual)
 -}
 -
--func (self *Client) containerInfoUrl(name string) string {
--	return self.baseUrl + path.Join("containers", name)
--}
+-func TestChangeServerAdminPassword(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleAdminPasswordChangeSuccessfully(t)
 -
--func (self *Client) subcontainersInfoUrl(name string) string {
--	return self.baseUrl + path.Join("subcontainers", name)
+-	res := ChangeAdminPassword(client.ServiceClient(), "1234asdf", "new-password")
+-	th.AssertNoErr(t, res.Err)
 -}
 -
--func (self *Client) dockerInfoUrl(name string) string {
--	return self.baseUrl + path.Join("docker", name)
+-func TestRebootServer(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleRebootSuccessfully(t)
+-
+-	res := Reboot(client.ServiceClient(), "1234asdf", SoftReboot)
+-	th.AssertNoErr(t, res.Err)
 -}
 -
--func (self *Client) httpGetJsonData(data, postData interface{}, url, infoName string) error {
--	var resp *http.Response
--	var err error
+-func TestRebuildServer(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleRebuildSuccessfully(t, SingleServerBody)
 -
--	if postData != nil {
--		data, err := json.Marshal(postData)
--		if err != nil {
--			return fmt.Errorf("unable to marshal data: %v", err)
--		}
--		resp, err = http.Post(url, "application/json", bytes.NewBuffer(data))
--	} else {
--		resp, err = http.Get(url)
--	}
--	if err != nil {
--		return fmt.Errorf("unable to get %q: %v", infoName, err)
--	}
--	if resp == nil {
--		return fmt.Errorf("received empty response from %q", infoName)
+-	opts := RebuildOpts{
+-		Name:       "new-name",
+-		AdminPass:  "swordfish",
+-		ImageID:    "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/images/f90f6034-2570-4974-8351-6b49732ef2eb",
+-		AccessIPv4: "1.2.3.4",
 -	}
--	defer resp.Body.Close()
--	body, err := ioutil.ReadAll(resp.Body)
--	if err != nil {
--		err = fmt.Errorf("unable to read all %q: %v", infoName, err)
--		return err
--	}
--	if err = json.Unmarshal(body, data); err != nil {
--		err = fmt.Errorf("unable to unmarshal %q (%v): %v", infoName, string(body), err)
--		return err
--	}
--	return nil
+-
+-	actual, err := Rebuild(client.ServiceClient(), "1234asdf", opts).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.CheckDeepEquals(t, ServerDerp, *actual)
 -}
-diff --git a/Godeps/_workspace/src/github.com/google/cadvisor/client/client_test.go b/Godeps/_workspace/src/github.com/google/cadvisor/client/client_test.go
-deleted file mode 100644
-index 67bf3c2..0000000
---- a/Godeps/_workspace/src/github.com/google/cadvisor/client/client_test.go
-+++ /dev/null
-@@ -1,154 +0,0 @@
--// Copyright 2014 Google Inc. All Rights Reserved.
--//
--// Licensed under the Apache License, Version 2.0 (the "License");
--// you may not use this file except in compliance with the License.
--// You may obtain a copy of the License at
--//
--//     http://www.apache.org/licenses/LICENSE-2.0
--//
--// Unless required by applicable law or agreed to in writing, software
--// distributed under the License is distributed on an "AS IS" BASIS,
--// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
--// See the License for the specific language governing permissions and
--// limitations under the License.
 -
--package client
+-func TestResizeServer(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--import (
--	"encoding/json"
--	"fmt"
--	"net/http"
--	"net/http/httptest"
--	"path"
--	"reflect"
--	"testing"
--	"time"
+-	th.Mux.HandleFunc("/servers/1234asdf/action", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-		th.TestJSONRequest(t, r, `{ "resize": { "flavorRef": "2" } }`)
 -
--	"github.com/google/cadvisor/info"
--	itest "github.com/google/cadvisor/info/test"
--	"github.com/kr/pretty"
--)
+-		w.WriteHeader(http.StatusAccepted)
+-	})
 -
--func testGetJsonData(
--	expected interface{},
--	f func() (interface{}, error),
--) error {
--	reply, err := f()
--	if err != nil {
--		return fmt.Errorf("unable to retrieve data: %v", err)
--	}
--	if !reflect.DeepEqual(reply, expected) {
--		return pretty.Errorf("retrieved wrong data: %# v != %# v", reply, expected)
--	}
--	return nil
+-	res := Resize(client.ServiceClient(), "1234asdf", ResizeOpts{FlavorRef: "2"})
+-	th.AssertNoErr(t, res.Err)
 -}
 -
--func cadvisorTestClient(path string, expectedPostObj, expectedPostObjEmpty, replyObj interface{}, t *testing.T) (*Client, *httptest.Server, error) {
--	ts := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
--		if r.URL.Path == path {
--			if expectedPostObj != nil {
--				decoder := json.NewDecoder(r.Body)
--				if err := decoder.Decode(expectedPostObjEmpty); err != nil {
--					t.Errorf("Received invalid object: %v", err)
--				}
--				if !reflect.DeepEqual(expectedPostObj, expectedPostObjEmpty) {
--					t.Errorf("Received unexpected object: %+v", expectedPostObjEmpty)
--				}
--			}
--			encoder := json.NewEncoder(w)
--			encoder.Encode(replyObj)
--		} else if r.URL.Path == "/api/v1.2/machine" {
--			fmt.Fprint(w, `{"num_cores":8,"memory_capacity":31625871360}`)
--		} else {
--			w.WriteHeader(http.StatusNotFound)
--			fmt.Fprintf(w, "Page not found.")
--		}
--	}))
--	client, err := NewClient(ts.URL)
--	if err != nil {
--		ts.Close()
--		return nil, nil, err
--	}
--	return client, ts, err
+-func TestConfirmResize(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/servers/1234asdf/action", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-		th.TestJSONRequest(t, r, `{ "confirmResize": null }`)
+-
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-
+-	res := ConfirmResize(client.ServiceClient(), "1234asdf")
+-	th.AssertNoErr(t, res.Err)
 -}
 -
--// TestGetMachineInfo performs one test to check if MachineInfo()
--// in a cAdvisor client returns the correct result.
--func TestGetMachineinfo(t *testing.T) {
--	minfo := &info.MachineInfo{
--		NumCores:       8,
--		MemoryCapacity: 31625871360,
--	}
--	client, server, err := cadvisorTestClient("/api/v1.2/machine", nil, nil, minfo, t)
--	if err != nil {
--		t.Fatalf("unable to get a client %v", err)
--	}
--	defer server.Close()
--	returned, err := client.MachineInfo()
--	if err != nil {
--		t.Fatal(err)
--	}
--	if !reflect.DeepEqual(returned, minfo) {
--		t.Fatalf("received unexpected machine info")
--	}
+-func TestRevertResize(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/servers/1234asdf/action", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-		th.TestJSONRequest(t, r, `{ "revertResize": null }`)
+-
+-		w.WriteHeader(http.StatusAccepted)
+-	})
+-
+-	res := RevertResize(client.ServiceClient(), "1234asdf")
+-	th.AssertNoErr(t, res.Err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/results.go
+deleted file mode 100644
+index 53946ba..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/results.go
++++ /dev/null
+@@ -1,150 +0,0 @@
+-package servers
 -
--// TestGetContainerInfo generates a random container information object
--// and then checks that ContainerInfo returns the expected result.
--func TestGetContainerInfo(t *testing.T) {
--	query := &info.ContainerInfoRequest{
--		NumStats: 3,
--	}
--	containerName := "/some/container"
--	cinfo := itest.GenerateRandomContainerInfo(containerName, 4, query, 1*time.Second)
--	client, server, err := cadvisorTestClient(fmt.Sprintf("/api/v1.2/containers%v", containerName), query, &info.ContainerInfoRequest{}, cinfo, t)
--	if err != nil {
--		t.Fatalf("unable to get a client %v", err)
--	}
--	defer server.Close()
--	returned, err := client.ContainerInfo(containerName, query)
--	if err != nil {
--		t.Fatal(err)
--	}
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	if !returned.Eq(cinfo) {
--		t.Error("received unexpected ContainerInfo")
--	}
+-type serverResult struct {
+-	gophercloud.Result
 -}
 -
--func TestGetSubcontainersInfo(t *testing.T) {
--	query := &info.ContainerInfoRequest{
--		NumStats: 3,
--	}
--	containerName := "/some/container"
--	cinfo := itest.GenerateRandomContainerInfo(containerName, 4, query, 1*time.Second)
--	cinfo1 := itest.GenerateRandomContainerInfo(path.Join(containerName, "sub1"), 4, query, 1*time.Second)
--	cinfo2 := itest.GenerateRandomContainerInfo(path.Join(containerName, "sub2"), 4, query, 1*time.Second)
--	response := []info.ContainerInfo{
--		*cinfo,
--		*cinfo1,
--		*cinfo2,
--	}
--	client, server, err := cadvisorTestClient(fmt.Sprintf("/api/v1.2/subcontainers%v", containerName), query, &info.ContainerInfoRequest{}, response, t)
--	if err != nil {
--		t.Fatalf("unable to get a client %v", err)
--	}
--	defer server.Close()
--	returned, err := client.SubcontainersInfo(containerName, query)
--	if err != nil {
--		t.Fatal(err)
+-// Extract interprets any serverResult as a Server, if possible.
+-func (r serverResult) Extract() (*Server, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
 -	}
 -
--	if len(returned) != 3 {
--		t.Errorf("unexpected number of results: got %d, expected 3", len(returned))
--	}
--	if !returned[0].Eq(cinfo) {
--		t.Error("received unexpected ContainerInfo")
--	}
--	if !returned[1].Eq(cinfo1) {
--		t.Error("received unexpected ContainerInfo")
--	}
--	if !returned[2].Eq(cinfo2) {
--		t.Error("received unexpected ContainerInfo")
+-	var response struct {
+-		Server Server `mapstructure:"server"`
 -	}
+-
+-	err := mapstructure.Decode(r.Body, &response)
+-	return &response.Server, err
 -}
-diff --git a/Godeps/_workspace/src/github.com/google/cadvisor/info/container.go b/Godeps/_workspace/src/github.com/google/cadvisor/info/container.go
-deleted file mode 100644
-index 5a4fbbd..0000000
---- a/Godeps/_workspace/src/github.com/google/cadvisor/info/container.go
-+++ /dev/null
-@@ -1,379 +0,0 @@
--// Copyright 2014 Google Inc. All Rights Reserved.
--//
--// Licensed under the Apache License, Version 2.0 (the "License");
--// you may not use this file except in compliance with the License.
--// You may obtain a copy of the License at
--//
--//     http://www.apache.org/licenses/LICENSE-2.0
--//
--// Unless required by applicable law or agreed to in writing, software
--// distributed under the License is distributed on an "AS IS" BASIS,
--// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
--// See the License for the specific language governing permissions and
--// limitations under the License.
 -
--package info
+-// CreateResult temporarily contains the response from a Create call.
+-type CreateResult struct {
+-	serverResult
+-}
 -
--import (
--	"reflect"
--	"time"
--)
+-// GetResult temporarily contains the response from a Get call.
+-type GetResult struct {
+-	serverResult
+-}
 -
--type CpuSpec struct {
--	Limit    uint64 `json:"limit"`
--	MaxLimit uint64 `json:"max_limit"`
--	Mask     string `json:"mask,omitempty"`
+-// UpdateResult temporarily contains the response from an Update call.
+-type UpdateResult struct {
+-	serverResult
 -}
 -
--type MemorySpec struct {
--	// The amount of memory requested. Default is unlimited (-1).
--	// Units: bytes.
--	Limit uint64 `json:"limit,omitempty"`
+-// DeleteResult temporarily contains the response from an Delete call.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
+-}
 -
--	// The amount of guaranteed memory.  Default is 0.
--	// Units: bytes.
--	Reservation uint64 `json:"reservation,omitempty"`
+-// RebuildResult temporarily contains the response from a Rebuild call.
+-type RebuildResult struct {
+-	serverResult
+-}
 -
--	// The amount of swap space requested. Default is unlimited (-1).
--	// Units: bytes.
--	SwapLimit uint64 `json:"swap_limit,omitempty"`
+-// ActionResult represents the result of server action operations, like reboot
+-type ActionResult struct {
+-	gophercloud.ErrResult
 -}
 -
--type ContainerSpec struct {
--	HasCpu bool    `json:"has_cpu"`
--	Cpu    CpuSpec `json:"cpu,omitempty"`
+-// Server exposes only the standard OpenStack fields corresponding to a given server on the user's account.
+-type Server struct {
+-	// ID uniquely identifies this server amongst all other servers, including those not accessible to the current tenant.
+-	ID string
 -
--	HasMemory bool       `json:"has_memory"`
--	Memory    MemorySpec `json:"memory,omitempty"`
+-	// TenantID identifies the tenant owning this server resource.
+-	TenantID string `mapstructure:"tenant_id"`
 -
--	HasNetwork bool `json:"has_network"`
+-	// UserID uniquely identifies the user account owning the tenant.
+-	UserID string `mapstructure:"user_id"`
 -
--	HasFilesystem bool `json:"has_filesystem"`
--}
+-	// Name contains the human-readable name for the server.
+-	Name string
 -
--// Container reference contains enough information to uniquely identify a container
--type ContainerReference struct {
--	// The absolute name of the container. This is unique on the machine.
--	Name string `json:"name"`
+-	// Updated and Created contain ISO-8601 timestamps of when the state of the server last changed, and when it was created.
+-	Updated string
+-	Created string
 -
--	// Other names by which the container is known within a certain namespace.
--	// This is unique within that namespace.
--	Aliases []string `json:"aliases,omitempty"`
+-	HostID string
 -
--	// Namespace under which the aliases of a container are unique.
--	// An example of a namespace is "docker" for Docker containers.
--	Namespace string `json:"namespace,omitempty"`
--}
+-	// Status contains the current operational status of the server, such as IN_PROGRESS or ACTIVE.
+-	Status string
 -
--// ContainerInfoQuery is used when users check a container info from the REST api.
--// It specifies how much data users want to get about a container
--type ContainerInfoRequest struct {
--	// Max number of stats to return.
--	NumStats int `json:"num_stats,omitempty"`
--}
+-	// Progress ranges from 0..100.
+-	// A request made against the server completes only once Progress reaches 100.
+-	Progress int
 -
--type ContainerInfo struct {
--	ContainerReference
+-	// AccessIPv4 and AccessIPv6 contain the IP addresses of the server, suitable for remote access for administration.
+-	AccessIPv4, AccessIPv6 string
 -
--	// The direct subcontainers of the current container.
--	Subcontainers []ContainerReference `json:"subcontainers,omitempty"`
+-	// Image refers to a JSON object, which itself indicates the OS image used to deploy the server.
+-	Image map[string]interface{}
 -
--	// The isolation used in the container.
--	Spec ContainerSpec `json:"spec,omitempty"`
+-	// Flavor refers to a JSON object, which itself indicates the hardware configuration of the deployed server.
+-	Flavor map[string]interface{}
 -
--	// Historical statistics gathered from the container.
--	Stats []*ContainerStats `json:"stats,omitempty"`
+-	// Addresses includes a list of all IP addresses assigned to the server, keyed by pool.
+-	Addresses map[string]interface{}
+-
+-	// Metadata includes a list of all user-specified key-value pairs attached to the server.
+-	Metadata map[string]interface{}
+-
+-	// Links includes HTTP references to the itself, useful for passing along to other APIs that might want a server reference.
+-	Links []interface{}
+-
+-	// KeyName indicates which public key was injected into the server on launch.
+-	KeyName string `json:"key_name" mapstructure:"key_name"`
+-
+-	// AdminPass will generally be empty ("").  However, it will contain the administrative password chosen when provisioning a new server without a set AdminPass setting in the first place.
+-	// Note that this is the ONLY time this field will be valid.
+-	AdminPass string `json:"adminPass" mapstructure:"adminPass"`
 -}
 -
--// ContainerInfo may be (un)marshaled by json or other en/decoder. In that
--// case, the Timestamp field in each stats/sample may not be precisely
--// en/decoded.  This will lead to small but acceptable differences between a
--// ContainerInfo and its encode-then-decode version.  Eq() is used to compare
--// two ContainerInfo accepting small difference (<10ms) of Time fields.
--func (self *ContainerInfo) Eq(b *ContainerInfo) bool {
+-// ServerPage abstracts the raw results of making a List() request against the API.
+-// As OpenStack extensions may freely alter the response bodies of structures returned to the client, you may only safely access the
+-// data provided through the ExtractServers call.
+-type ServerPage struct {
+-	pagination.LinkedPageBase
+-}
 -
--	// If both self and b are nil, then Eq() returns true
--	if self == nil {
--		return b == nil
--	}
--	if b == nil {
--		return self == nil
+-// IsEmpty returns true if a page contains no Server results.
+-func (page ServerPage) IsEmpty() (bool, error) {
+-	servers, err := ExtractServers(page)
+-	if err != nil {
+-		return true, err
 -	}
+-	return len(servers) == 0, nil
+-}
 -
--	// For fields other than time.Time, we will compare them precisely.
--	// This would require that any slice should have same order.
--	if !reflect.DeepEqual(self.ContainerReference, b.ContainerReference) {
--		return false
--	}
--	if !reflect.DeepEqual(self.Subcontainers, b.Subcontainers) {
--		return false
--	}
--	if !reflect.DeepEqual(self.Spec, b.Spec) {
--		return false
+-// NextPageURL uses the response's embedded link reference to navigate to the next page of results.
+-func (page ServerPage) NextPageURL() (string, error) {
+-	type resp struct {
+-		Links []gophercloud.Link `mapstructure:"servers_links"`
 -	}
 -
--	for i, expectedStats := range b.Stats {
--		selfStats := self.Stats[i]
--		if !expectedStats.Eq(selfStats) {
--			return false
--		}
+-	var r resp
+-	err := mapstructure.Decode(page.Body, &r)
+-	if err != nil {
+-		return "", err
 -	}
 -
--	return true
+-	return gophercloud.ExtractNextURL(r.Links)
 -}
 -
--func (self *ContainerInfo) StatsAfter(ref time.Time) []*ContainerStats {
--	n := len(self.Stats) + 1
--	for i, s := range self.Stats {
--		if s.Timestamp.After(ref) {
--			n = i
--			break
--		}
--	}
--	if n > len(self.Stats) {
--		return nil
--	}
--	return self.Stats[n:]
--}
+-// ExtractServers interprets the results of a single page from a List() call, producing a slice of Server entities.
+-func ExtractServers(page pagination.Page) ([]Server, error) {
+-	casted := page.(ServerPage).Body
 -
--func (self *ContainerInfo) StatsStartTime() time.Time {
--	var ret time.Time
--	for _, s := range self.Stats {
--		if s.Timestamp.Before(ret) || ret.IsZero() {
--			ret = s.Timestamp
--		}
+-	var response struct {
+-		Servers []Server `mapstructure:"servers"`
 -	}
--	return ret
+-	err := mapstructure.Decode(casted, &response)
+-	return response.Servers, err
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/urls.go
+deleted file mode 100644
+index 57587ab..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/urls.go
++++ /dev/null
+@@ -1,31 +0,0 @@
+-package servers
 -
--func (self *ContainerInfo) StatsEndTime() time.Time {
--	var ret time.Time
--	for i := len(self.Stats) - 1; i >= 0; i-- {
--		s := self.Stats[i]
--		if s.Timestamp.After(ret) {
--			ret = s.Timestamp
--		}
--	}
--	return ret
+-import "github.com/rackspace/gophercloud"
+-
+-func createURL(client *gophercloud.ServiceClient) string {
+-	return client.ServiceURL("servers")
 -}
 -
--// All CPU usage metrics are cumulative from the creation of the container
--type CpuStats struct {
--	Usage struct {
--		// Total CPU usage.
--		// Units: nanoseconds
--		Total uint64 `json:"total"`
+-func listURL(client *gophercloud.ServiceClient) string {
+-	return createURL(client)
+-}
 -
--		// Per CPU/core usage of the container.
--		// Unit: nanoseconds.
--		PerCpu []uint64 `json:"per_cpu_usage,omitempty"`
+-func listDetailURL(client *gophercloud.ServiceClient) string {
+-	return client.ServiceURL("servers", "detail")
+-}
 -
--		// Time spent in user space.
--		// Unit: nanoseconds
--		User uint64 `json:"user"`
+-func deleteURL(client *gophercloud.ServiceClient, id string) string {
+-	return client.ServiceURL("servers", id)
+-}
 -
--		// Time spent in kernel space.
--		// Unit: nanoseconds
--		System uint64 `json:"system"`
--	} `json:"usage"`
--	Load int32 `json:"load"`
+-func getURL(client *gophercloud.ServiceClient, id string) string {
+-	return deleteURL(client, id)
 -}
 -
--type PerDiskStats struct {
--	Major uint64            `json:"major"`
--	Minor uint64            `json:"minor"`
--	Stats map[string]uint64 `json:"stats"`
+-func updateURL(client *gophercloud.ServiceClient, id string) string {
+-	return deleteURL(client, id)
 -}
 -
--type DiskIoStats struct {
--	IoServiceBytes []PerDiskStats `json:"io_service_bytes,omitempty"`
--	IoServiced     []PerDiskStats `json:"io_serviced,omitempty"`
--	IoQueued       []PerDiskStats `json:"io_queued,omitempty"`
--	Sectors        []PerDiskStats `json:"sectors,omitempty"`
--	IoServiceTime  []PerDiskStats `json:"io_service_time,omitempty"`
--	IoWaitTime     []PerDiskStats `json:"io_wait_time,omitempty"`
--	IoMerged       []PerDiskStats `json:"io_merged,omitempty"`
--	IoTime         []PerDiskStats `json:"io_time,omitempty"`
+-func actionURL(client *gophercloud.ServiceClient, id string) string {
+-	return client.ServiceURL("servers", id, "action")
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/urls_test.go
+deleted file mode 100644
+index cc895c9..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/urls_test.go
++++ /dev/null
+@@ -1,56 +0,0 @@
+-package servers
 -
--type MemoryStats struct {
--	// Current memory usage, this includes all memory regardless of when it was
--	// accessed.
--	// Units: Bytes.
--	Usage uint64 `json:"usage"`
+-import (
+-	"testing"
 -
--	// The amount of working set memory, this includes recently accessed memory,
--	// dirty memory, and kernel memory. Working set is <= "usage".
--	// Units: Bytes.
--	WorkingSet uint64 `json:"working_set"`
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--	ContainerData    MemoryStatsMemoryData `json:"container_data,omitempty"`
--	HierarchicalData MemoryStatsMemoryData `json:"hierarchical_data,omitempty"`
+-const endpoint = "http://localhost:57909"
+-
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint}
 -}
 -
--type MemoryStatsMemoryData struct {
--	Pgfault    uint64 `json:"pgfault"`
--	Pgmajfault uint64 `json:"pgmajfault"`
+-func TestCreateURL(t *testing.T) {
+-	actual := createURL(endpointClient())
+-	expected := endpoint + "servers"
+-	th.CheckEquals(t, expected, actual)
 -}
 -
--type NetworkStats struct {
--	// Cumulative count of bytes received.
--	RxBytes uint64 `json:"rx_bytes"`
--	// Cumulative count of packets received.
--	RxPackets uint64 `json:"rx_packets"`
--	// Cumulative count of receive errors encountered.
--	RxErrors uint64 `json:"rx_errors"`
--	// Cumulative count of packets dropped while receiving.
--	RxDropped uint64 `json:"rx_dropped"`
--	// Cumulative count of bytes transmitted.
--	TxBytes uint64 `json:"tx_bytes"`
--	// Cumulative count of packets transmitted.
--	TxPackets uint64 `json:"tx_packets"`
--	// Cumulative count of transmit errors encountered.
--	TxErrors uint64 `json:"tx_errors"`
--	// Cumulative count of packets dropped while transmitting.
--	TxDropped uint64 `json:"tx_dropped"`
+-func TestListURL(t *testing.T) {
+-	actual := listURL(endpointClient())
+-	expected := endpoint + "servers"
+-	th.CheckEquals(t, expected, actual)
 -}
 -
--type FsStats struct {
--	// The block device name associated with the filesystem.
--	Device string `json:"device,omitempty"`
+-func TestListDetailURL(t *testing.T) {
+-	actual := listDetailURL(endpointClient())
+-	expected := endpoint + "servers/detail"
+-	th.CheckEquals(t, expected, actual)
+-}
 -
--	// Number of bytes that can be consumed by the container on this filesystem.
--	Limit uint64 `json:"capacity"`
+-func TestDeleteURL(t *testing.T) {
+-	actual := deleteURL(endpointClient(), "foo")
+-	expected := endpoint + "servers/foo"
+-	th.CheckEquals(t, expected, actual)
+-}
 -
--	// Number of bytes that is consumed by the container on this filesystem.
--	Usage uint64 `json:"usage"`
+-func TestGetURL(t *testing.T) {
+-	actual := getURL(endpointClient(), "foo")
+-	expected := endpoint + "servers/foo"
+-	th.CheckEquals(t, expected, actual)
+-}
 -
--	// Number of reads completed
--	// This is the total number of reads completed successfully.
--	ReadsCompleted uint64 `json:"reads_completed"`
+-func TestUpdateURL(t *testing.T) {
+-	actual := updateURL(endpointClient(), "foo")
+-	expected := endpoint + "servers/foo"
+-	th.CheckEquals(t, expected, actual)
+-}
 -
--	// Number of reads merged
--	// Reads and writes which are adjacent to each other may be merged for
--	// efficiency.  Thus two 4K reads may become one 8K read before it is
--	// ultimately handed to the disk, and so it will be counted (and queued)
--	// as only one I/O.  This field lets you know how often this was done.
--	ReadsMerged uint64 `json:"reads_merged"`
+-func TestActionURL(t *testing.T) {
+-	actual := actionURL(endpointClient(), "foo")
+-	expected := endpoint + "servers/foo/action"
+-	th.CheckEquals(t, expected, actual)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/util.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/util.go
+deleted file mode 100644
+index e6baf74..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/util.go
++++ /dev/null
+@@ -1,20 +0,0 @@
+-package servers
 -
--	// Number of sectors read
--	// This is the total number of sectors read successfully.
--	SectorsRead uint64 `json:"sectors_read"`
+-import "github.com/rackspace/gophercloud"
 -
--	// Number of milliseconds spent reading
--	// This is the total number of milliseconds spent by all reads (as
--	// measured from __make_request() to end_that_request_last()).
--	ReadTime uint64 `json:"read_time"`
+-// WaitForStatus will continually poll a server until it successfully transitions to a specified
+-// status. It will do this for at most the number of seconds specified.
+-func WaitForStatus(c *gophercloud.ServiceClient, id, status string, secs int) error {
+-	return gophercloud.WaitFor(secs, func() (bool, error) {
+-		current, err := Get(c, id).Extract()
+-		if err != nil {
+-			return false, err
+-		}
 -
--	// Number of writes completed
--	// This is the total number of writes completed successfully.
--	WritesCompleted uint64 `json:"writes_completed"`
+-		if current.Status == status {
+-			return true, nil
+-		}
 -
--	// Number of writes merged
--	// See the description of reads merged.
--	WritesMerged uint64 `json:"writes_merged"`
+-		return false, nil
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/util_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/util_test.go
+deleted file mode 100644
+index e192ae3..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/compute/v2/servers/util_test.go
++++ /dev/null
+@@ -1,38 +0,0 @@
+-package servers
 -
--	// Number of sectors written
--	// This is the total number of sectors written successfully.
--	SectorsWritten uint64 `json:"sectors_written"`
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
+-	"time"
 -
--	// Number of milliseconds spent writing
--	// This is the total number of milliseconds spent by all writes (as
--	// measured from __make_request() to end_that_request_last()).
--	WriteTime uint64 `json:"write_time"`
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--	// Number of I/Os currently in progress
--	// The only field that should go to zero. Incremented as requests are
--	// given to appropriate struct request_queue and decremented as they finish.
--	IoInProgress uint64 `json:"io_in_progress"`
+-func TestWaitForStatus(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	// Number of milliseconds spent doing I/Os
--	// This field increases so long as field 9 is nonzero.
--	IoTime uint64 `json:"io_time"`
+-	th.Mux.HandleFunc("/servers/4321", func(w http.ResponseWriter, r *http.Request) {
+-		time.Sleep(2 * time.Second)
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-		fmt.Fprintf(w, `
+-		{
+-			"server": {
+-				"name": "the-server",
+-				"id": "4321",
+-				"status": "ACTIVE"
+-			}
+-		}`)
+-	})
 -
--	// weighted number of milliseconds spent doing I/Os
--	// This field is incremented at each I/O start, I/O completion, I/O
--	// merge, or read of these stats by the number of I/Os in progress
--	// (field 9) times the number of milliseconds spent doing I/O since the
--	// last update of this field.  This can provide an easy measure of both
--	// I/O completion time and the backlog that may be accumulating.
--	WeightedIoTime uint64 `json:"weighted_io_time"`
+-	err := WaitForStatus(client.ServiceClient(), "4321", "ACTIVE", 0)
+-	if err == nil {
+-		t.Errorf("Expected error: 'Time Out in WaitFor'")
+-	}
+-
+-	err = WaitForStatus(client.ServiceClient(), "4321", "ACTIVE", 3)
+-	th.CheckNoErr(t, err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/endpoint_location.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/endpoint_location.go
+deleted file mode 100644
+index 5a311e4..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/endpoint_location.go
++++ /dev/null
+@@ -1,124 +0,0 @@
+-package openstack
 -
--type ContainerStats struct {
--	// The time of this stat point.
--	Timestamp time.Time    `json:"timestamp"`
--	Cpu       CpuStats     `json:"cpu,omitempty"`
--	DiskIo    DiskIoStats  `json:"diskio,omitempty"`
--	Memory    MemoryStats  `json:"memory,omitempty"`
--	Network   NetworkStats `json:"network,omitempty"`
+-import (
+-	"fmt"
 -
--	// Filesystem statistics
--	Filesystem []FsStats `json:"filesystem,omitempty"`
--}
+-	"github.com/rackspace/gophercloud"
+-	tokens2 "github.com/rackspace/gophercloud/openstack/identity/v2/tokens"
+-	endpoints3 "github.com/rackspace/gophercloud/openstack/identity/v3/endpoints"
+-	services3 "github.com/rackspace/gophercloud/openstack/identity/v3/services"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--func timeEq(t1, t2 time.Time, tolerance time.Duration) bool {
--	// t1 should not be later than t2
--	if t1.After(t2) {
--		t1, t2 = t2, t1
--	}
--	diff := t2.Sub(t1)
--	if diff <= tolerance {
--		return true
+-// V2EndpointURL discovers the endpoint URL for a specific service from a ServiceCatalog acquired
+-// during the v2 identity service. The specified EndpointOpts are used to identify a unique,
+-// unambiguous endpoint to return. It's an error both when multiple endpoints match the provided
+-// criteria and when none do. The minimum that can be specified is a Type, but you will also often
+-// need to specify a Name and/or a Region depending on what's available on your OpenStack
+-// deployment.
+-func V2EndpointURL(catalog *tokens2.ServiceCatalog, opts gophercloud.EndpointOpts) (string, error) {
+-	// Extract Endpoints from the catalog entries that match the requested Type, Name if provided, and Region if provided.
+-	var endpoints = make([]tokens2.Endpoint, 0, 1)
+-	for _, entry := range catalog.Entries {
+-		if (entry.Type == opts.Type) && (opts.Name == "" || entry.Name == opts.Name) {
+-			for _, endpoint := range entry.Endpoints {
+-				if opts.Region == "" || endpoint.Region == opts.Region {
+-					endpoints = append(endpoints, endpoint)
+-				}
+-			}
+-		}
 -	}
--	return false
--}
 -
--func durationEq(a, b time.Duration, tolerance time.Duration) bool {
--	if a > b {
--		a, b = b, a
+-	// Report an error if the options were ambiguous.
+-	if len(endpoints) > 1 {
+-		return "", fmt.Errorf("Discovered %d matching endpoints: %#v", len(endpoints), endpoints)
 -	}
--	diff := a - b
--	if diff <= tolerance {
--		return true
+-
+-	// Extract the appropriate URL from the matching Endpoint.
+-	for _, endpoint := range endpoints {
+-		switch opts.Availability {
+-		case gophercloud.AvailabilityPublic:
+-			return gophercloud.NormalizeURL(endpoint.PublicURL), nil
+-		case gophercloud.AvailabilityInternal:
+-			return gophercloud.NormalizeURL(endpoint.InternalURL), nil
+-		case gophercloud.AvailabilityAdmin:
+-			return gophercloud.NormalizeURL(endpoint.AdminURL), nil
+-		default:
+-			return "", fmt.Errorf("Unexpected availability in endpoint query: %s", opts.Availability)
+-		}
 -	}
--	return false
+-
+-	// Report an error if there were no matching endpoints.
+-	return "", gophercloud.ErrEndpointNotFound
 -}
 -
--const (
--	// 10ms, i.e. 0.01s
--	timePrecision time.Duration = 10 * time.Millisecond
--)
+-// V3EndpointURL discovers the endpoint URL for a specific service using multiple calls against
+-// an identity v3 service endpoint. The specified EndpointOpts are used to identify a unique,
+-// unambiguous endpoint to return. It's an error both when multiple endpoints match the provided
+-// criteria and when none do. The minimum that can be specified is a Type, but you will also often
+-// need to specify a Name and/or a Region depending on what's available on your OpenStack
+-// deployment.
+-func V3EndpointURL(v3Client *gophercloud.ServiceClient, opts gophercloud.EndpointOpts) (string, error) {
+-	// Discover the service we're interested in.
+-	var services = make([]services3.Service, 0, 1)
+-	servicePager := services3.List(v3Client, services3.ListOpts{ServiceType: opts.Type})
+-	err := servicePager.EachPage(func(page pagination.Page) (bool, error) {
+-		part, err := services3.ExtractServices(page)
+-		if err != nil {
+-			return false, err
+-		}
 -
--// This function is useful because we do not require precise time
--// representation.
--func (a *ContainerStats) Eq(b *ContainerStats) bool {
--	if !timeEq(a.Timestamp, b.Timestamp, timePrecision) {
--		return false
+-		for _, service := range part {
+-			if service.Name == opts.Name {
+-				services = append(services, service)
+-			}
+-		}
+-
+-		return true, nil
+-	})
+-	if err != nil {
+-		return "", err
 -	}
--	return a.StatsEq(b)
--}
 -
--// Checks equality of the stats values.
--func (a *ContainerStats) StatsEq(b *ContainerStats) bool {
--	// TODO(vmarmol): Consider using this through reflection.
--	if !reflect.DeepEqual(a.Cpu, b.Cpu) {
--		return false
+-	if len(services) == 0 {
+-		return "", gophercloud.ErrServiceNotFound
 -	}
--	if !reflect.DeepEqual(a.Memory, b.Memory) {
--		return false
+-	if len(services) > 1 {
+-		return "", fmt.Errorf("Discovered %d matching services: %#v", len(services), services)
 -	}
--	if !reflect.DeepEqual(a.DiskIo, b.DiskIo) {
--		return false
+-	service := services[0]
+-
+-	// Enumerate the endpoints available for this service.
+-	var endpoints []endpoints3.Endpoint
+-	endpointPager := endpoints3.List(v3Client, endpoints3.ListOpts{
+-		Availability: opts.Availability,
+-		ServiceID:    service.ID,
+-	})
+-	err = endpointPager.EachPage(func(page pagination.Page) (bool, error) {
+-		part, err := endpoints3.ExtractEndpoints(page)
+-		if err != nil {
+-			return false, err
+-		}
+-
+-		for _, endpoint := range part {
+-			if opts.Region == "" || endpoint.Region == opts.Region {
+-				endpoints = append(endpoints, endpoint)
+-			}
+-		}
+-
+-		return true, nil
+-	})
+-	if err != nil {
+-		return "", err
 -	}
--	if !reflect.DeepEqual(a.Network, b.Network) {
--		return false
+-
+-	if len(endpoints) == 0 {
+-		return "", gophercloud.ErrEndpointNotFound
 -	}
--	if !reflect.DeepEqual(a.Filesystem, b.Filesystem) {
--		return false
+-	if len(endpoints) > 1 {
+-		return "", fmt.Errorf("Discovered %d matching endpoints: %#v", len(endpoints), endpoints)
 -	}
--	return true
--}
+-	endpoint := endpoints[0]
 -
--// Saturate CPU usage to 0.
--func calculateCpuUsage(prev, cur uint64) uint64 {
--	if prev > cur {
--		return 0
--	}
--	return cur - prev
+-	return gophercloud.NormalizeURL(endpoint.URL), nil
 -}
-diff --git a/Godeps/_workspace/src/github.com/google/cadvisor/info/container_test.go b/Godeps/_workspace/src/github.com/google/cadvisor/info/container_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/endpoint_location_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/endpoint_location_test.go
 deleted file mode 100644
-index 2ff38e6..0000000
---- a/Godeps/_workspace/src/github.com/google/cadvisor/info/container_test.go
+index 4e0569a..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/endpoint_location_test.go
 +++ /dev/null
-@@ -1,79 +0,0 @@
--// Copyright 2014 Google Inc. All Rights Reserved.
--//
--// Licensed under the Apache License, Version 2.0 (the "License");
--// you may not use this file except in compliance with the License.
--// You may obtain a copy of the License at
--//
--//     http://www.apache.org/licenses/LICENSE-2.0
--//
--// Unless required by applicable law or agreed to in writing, software
--// distributed under the License is distributed on an "AS IS" BASIS,
--// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
--// See the License for the specific language governing permissions and
--// limitations under the License.
--
--package info
+@@ -1,225 +0,0 @@
+-package openstack
 -
 -import (
+-	"fmt"
+-	"net/http"
+-	"strings"
 -	"testing"
--	"time"
+-
+-	"github.com/rackspace/gophercloud"
+-	tokens2 "github.com/rackspace/gophercloud/openstack/identity/v2/tokens"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
 -)
 -
--func TestStatsStartTime(t *testing.T) {
--	N := 10
--	stats := make([]*ContainerStats, 0, N)
--	ct := time.Now()
--	for i := 0; i < N; i++ {
--		s := &ContainerStats{
--			Timestamp: ct.Add(time.Duration(i) * time.Second),
--		}
--		stats = append(stats, s)
--	}
--	cinfo := &ContainerInfo{
--		ContainerReference: ContainerReference{
--			Name: "/some/container",
+-// Service catalog fixtures take too much vertical space!
+-var catalog2 = tokens2.ServiceCatalog{
+-	Entries: []tokens2.CatalogEntry{
+-		tokens2.CatalogEntry{
+-			Type: "same",
+-			Name: "same",
+-			Endpoints: []tokens2.Endpoint{
+-				tokens2.Endpoint{
+-					Region:      "same",
+-					PublicURL:   "https://public.correct.com/",
+-					InternalURL: "https://internal.correct.com/",
+-					AdminURL:    "https://admin.correct.com/",
+-				},
+-				tokens2.Endpoint{
+-					Region:    "different",
+-					PublicURL: "https://badregion.com/",
+-				},
+-			},
 -		},
--		Stats: stats,
+-		tokens2.CatalogEntry{
+-			Type: "same",
+-			Name: "different",
+-			Endpoints: []tokens2.Endpoint{
+-				tokens2.Endpoint{
+-					Region:    "same",
+-					PublicURL: "https://badname.com/",
+-				},
+-				tokens2.Endpoint{
+-					Region:    "different",
+-					PublicURL: "https://badname.com/+badregion",
+-				},
+-			},
+-		},
+-		tokens2.CatalogEntry{
+-			Type: "different",
+-			Name: "different",
+-			Endpoints: []tokens2.Endpoint{
+-				tokens2.Endpoint{
+-					Region:    "same",
+-					PublicURL: "https://badtype.com/+badname",
+-				},
+-				tokens2.Endpoint{
+-					Region:    "different",
+-					PublicURL: "https://badtype.com/+badregion+badname",
+-				},
+-			},
+-		},
+-	},
+-}
+-
+-func TestV2EndpointExact(t *testing.T) {
+-	expectedURLs := map[gophercloud.Availability]string{
+-		gophercloud.AvailabilityPublic:   "https://public.correct.com/",
+-		gophercloud.AvailabilityAdmin:    "https://admin.correct.com/",
+-		gophercloud.AvailabilityInternal: "https://internal.correct.com/",
 -	}
--	ref := ct.Add(time.Duration(N-1) * time.Second)
--	end := cinfo.StatsEndTime()
 -
--	if !ref.Equal(end) {
--		t.Errorf("end time is %v; should be %v", end, ref)
+-	for availability, expected := range expectedURLs {
+-		actual, err := V2EndpointURL(&catalog2, gophercloud.EndpointOpts{
+-			Type:         "same",
+-			Name:         "same",
+-			Region:       "same",
+-			Availability: availability,
+-		})
+-		th.AssertNoErr(t, err)
+-		th.CheckEquals(t, expected, actual)
 -	}
 -}
 -
--func TestStatsEndTime(t *testing.T) {
--	N := 10
--	stats := make([]*ContainerStats, 0, N)
--	ct := time.Now()
--	for i := 0; i < N; i++ {
--		s := &ContainerStats{
--			Timestamp: ct.Add(time.Duration(i) * time.Second),
--		}
--		stats = append(stats, s)
--	}
--	cinfo := &ContainerInfo{
--		ContainerReference: ContainerReference{
--			Name: "/some/container",
--		},
--		Stats: stats,
--	}
--	ref := ct
--	start := cinfo.StatsStartTime()
+-func TestV2EndpointNone(t *testing.T) {
+-	_, err := V2EndpointURL(&catalog2, gophercloud.EndpointOpts{
+-		Type:         "nope",
+-		Availability: gophercloud.AvailabilityPublic,
+-	})
+-	th.CheckEquals(t, gophercloud.ErrEndpointNotFound, err)
+-}
 -
--	if !ref.Equal(start) {
--		t.Errorf("start time is %v; should be %v", start, ref)
+-func TestV2EndpointMultiple(t *testing.T) {
+-	_, err := V2EndpointURL(&catalog2, gophercloud.EndpointOpts{
+-		Type:         "same",
+-		Region:       "same",
+-		Availability: gophercloud.AvailabilityPublic,
+-	})
+-	if !strings.HasPrefix(err.Error(), "Discovered 2 matching endpoints:") {
+-		t.Errorf("Received unexpected error: %v", err)
 -	}
 -}
 -
--func createStats(cpuUsage, memUsage uint64, timestamp time.Time) *ContainerStats {
--	stats := &ContainerStats{}
--	stats.Cpu.Usage.PerCpu = []uint64{cpuUsage}
--	stats.Cpu.Usage.Total = cpuUsage
--	stats.Cpu.Usage.System = 0
--	stats.Cpu.Usage.User = cpuUsage
--	stats.Memory.Usage = memUsage
--	stats.Timestamp = timestamp
--	return stats
+-func TestV2EndpointBadAvailability(t *testing.T) {
+-	_, err := V2EndpointURL(&catalog2, gophercloud.EndpointOpts{
+-		Type:         "same",
+-		Name:         "same",
+-		Region:       "same",
+-		Availability: "wat",
+-	})
+-	th.CheckEquals(t, err.Error(), "Unexpected availability in endpoint query: wat")
 -}
-diff --git a/Godeps/_workspace/src/github.com/google/cadvisor/info/machine.go b/Godeps/_workspace/src/github.com/google/cadvisor/info/machine.go
+-
+-func setupV3Responses(t *testing.T) {
+-	// Mock the service query.
+-	th.Mux.HandleFunc("/services", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, `
+-			{
+-				"links": {
+-					"next": null,
+-					"previous": null
+-				},
+-				"services": [
+-					{
+-						"description": "Correct",
+-						"id": "1234",
+-						"name": "same",
+-						"type": "same"
+-					},
+-					{
+-						"description": "Bad Name",
+-						"id": "9876",
+-						"name": "different",
+-						"type": "same"
+-					}
+-				]
+-			}
+-		`)
+-	})
+-
+-	// Mock the endpoint query.
+-	th.Mux.HandleFunc("/endpoints", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestFormValues(t, r, map[string]string{
+-			"service_id": "1234",
+-			"interface":  "public",
+-		})
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, `
+-			{
+-				"endpoints": [
+-					{
+-						"id": "12",
+-						"interface": "public",
+-						"name": "the-right-one",
+-						"region": "same",
+-						"service_id": "1234",
+-						"url": "https://correct:9000/"
+-					},
+-					{
+-						"id": "14",
+-						"interface": "public",
+-						"name": "bad-region",
+-						"region": "different",
+-						"service_id": "1234",
+-						"url": "https://bad-region:9001/"
+-					}
+-				],
+-				"links": {
+-					"next": null,
+-					"previous": null
+-				}
+-			}
+-    `)
+-	})
+-}
+-
+-func TestV3EndpointExact(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	setupV3Responses(t)
+-
+-	actual, err := V3EndpointURL(fake.ServiceClient(), gophercloud.EndpointOpts{
+-		Type:         "same",
+-		Name:         "same",
+-		Region:       "same",
+-		Availability: gophercloud.AvailabilityPublic,
+-	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, actual, "https://correct:9000/")
+-}
+-
+-func TestV3EndpointNoService(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/services", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, `
+-      {
+-        "links": {
+-          "next": null,
+-          "previous": null
+-        },
+-        "services": []
+-      }
+-    `)
+-	})
+-
+-	_, err := V3EndpointURL(fake.ServiceClient(), gophercloud.EndpointOpts{
+-		Type:         "nope",
+-		Name:         "same",
+-		Region:       "same",
+-		Availability: gophercloud.AvailabilityPublic,
+-	})
+-	th.CheckEquals(t, gophercloud.ErrServiceNotFound, err)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/extensions/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/extensions/delegate.go
 deleted file mode 100644
-index 0e73a8e..0000000
---- a/Godeps/_workspace/src/github.com/google/cadvisor/info/machine.go
+index fd6e80e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/extensions/delegate.go
 +++ /dev/null
-@@ -1,53 +0,0 @@
--// Copyright 2014 Google Inc. All Rights Reserved.
--//
--// Licensed under the Apache License, Version 2.0 (the "License");
--// you may not use this file except in compliance with the License.
--// You may obtain a copy of the License at
--//
--//     http://www.apache.org/licenses/LICENSE-2.0
--//
--// Unless required by applicable law or agreed to in writing, software
--// distributed under the License is distributed on an "AS IS" BASIS,
--// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
--// See the License for the specific language governing permissions and
--// limitations under the License.
+@@ -1,52 +0,0 @@
+-package extensions
 -
--package info
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	common "github.com/rackspace/gophercloud/openstack/common/extensions"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--type FsInfo struct {
--	// Block device associated with the filesystem.
--	Device string `json:"device"`
+-// ExtensionPage is a single page of Extension results.
+-type ExtensionPage struct {
+-	common.ExtensionPage
+-}
 -
--	// Total number of bytes available on the filesystem.
--	Capacity uint64 `json:"capacity"`
+-// IsEmpty returns true if the current page contains at least one Extension.
+-func (page ExtensionPage) IsEmpty() (bool, error) {
+-	is, err := ExtractExtensions(page)
+-	if err != nil {
+-		return true, err
+-	}
+-	return len(is) == 0, nil
 -}
 -
--type MachineInfo struct {
--	// The number of cores in this machine.
--	NumCores int `json:"num_cores"`
+-// ExtractExtensions accepts a Page struct, specifically an ExtensionPage struct, and extracts the
+-// elements into a slice of Extension structs.
+-func ExtractExtensions(page pagination.Page) ([]common.Extension, error) {
+-	// Identity v2 adds an intermediate "values" object.
 -
--	// The amount of memory (in bytes) in this machine
--	MemoryCapacity int64 `json:"memory_capacity"`
+-	var resp struct {
+-		Extensions struct {
+-			Values []common.Extension `mapstructure:"values"`
+-		} `mapstructure:"extensions"`
+-	}
 -
--	// Filesystems on this machine.
--	Filesystems []FsInfo `json:"filesystems"`
+-	err := mapstructure.Decode(page.(ExtensionPage).Body, &resp)
+-	return resp.Extensions.Values, err
 -}
 -
--type VersionInfo struct {
--	// Kernel version.
--	KernelVersion string `json:"kernel_version"`
+-// Get retrieves information for a specific extension using its alias.
+-func Get(c *gophercloud.ServiceClient, alias string) common.GetResult {
+-	return common.Get(c, alias)
+-}
 -
--	// OS image being used for cadvisor container, or host image if running on host directly.
--	ContainerOsVersion string `json:"container_os_version"`
+-// List returns a Pager which allows you to iterate over the full collection of extensions.
+-// It does not accept query parameters.
+-func List(c *gophercloud.ServiceClient) pagination.Pager {
+-	return common.List(c).WithPageCreator(func(r pagination.PageResult) pagination.Page {
+-		return ExtensionPage{
+-			ExtensionPage: common.ExtensionPage{SinglePageBase: pagination.SinglePageBase(r)},
+-		}
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/extensions/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/extensions/delegate_test.go
+deleted file mode 100644
+index 504118a..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/extensions/delegate_test.go
++++ /dev/null
+@@ -1,38 +0,0 @@
+-package extensions
 -
--	// Docker version.
--	DockerVersion string `json:"docker_version"`
+-import (
+-	"testing"
 -
--	// cAdvisor version.
--	CadvisorVersion string `json:"cadvisor_version"`
+-	common "github.com/rackspace/gophercloud/openstack/common/extensions"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
+-
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleListExtensionsSuccessfully(t)
+-
+-	count := 0
+-	err := List(client.ServiceClient()).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractExtensions(page)
+-		th.AssertNoErr(t, err)
+-		th.CheckDeepEquals(t, common.ExpectedExtensions, actual)
+-
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, 1, count)
 -}
 -
--type MachineInfoFactory interface {
--	GetMachineInfo() (*MachineInfo, error)
--	GetVersionInfo() (*VersionInfo, error)
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	common.HandleGetExtensionSuccessfully(t)
+-
+-	actual, err := Get(client.ServiceClient(), "agent").Extract()
+-	th.AssertNoErr(t, err)
+-	th.CheckDeepEquals(t, common.SingleExtension, actual)
 -}
-diff --git a/Godeps/_workspace/src/github.com/google/cadvisor/info/test/datagen.go b/Godeps/_workspace/src/github.com/google/cadvisor/info/test/datagen.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/extensions/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/extensions/doc.go
 deleted file mode 100644
-index 519e28c..0000000
---- a/Godeps/_workspace/src/github.com/google/cadvisor/info/test/datagen.go
+index 791e4e3..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/extensions/doc.go
 +++ /dev/null
-@@ -1,76 +0,0 @@
--// Copyright 2014 Google Inc. All Rights Reserved.
--//
--// Licensed under the Apache License, Version 2.0 (the "License");
--// you may not use this file except in compliance with the License.
--// You may obtain a copy of the License at
--//
--//     http://www.apache.org/licenses/LICENSE-2.0
--//
--// Unless required by applicable law or agreed to in writing, software
--// distributed under the License is distributed on an "AS IS" BASIS,
--// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
--// See the License for the specific language governing permissions and
--// limitations under the License.
+@@ -1,3 +0,0 @@
+-// Package extensions provides information and interaction with the
+-// different extensions available for the OpenStack Identity service.
+-package extensions
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/extensions/fixtures.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/extensions/fixtures.go
+deleted file mode 100644
+index 96cb7d2..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/extensions/fixtures.go
++++ /dev/null
+@@ -1,60 +0,0 @@
+-// +build fixtures
 -
--package test
+-package extensions
 -
 -import (
 -	"fmt"
--	"math/rand"
--	"time"
+-	"net/http"
+-	"testing"
 -
--	"github.com/google/cadvisor/info"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
 -)
 -
--func GenerateRandomStats(numStats, numCores int, duration time.Duration) []*info.ContainerStats {
--	ret := make([]*info.ContainerStats, numStats)
--	perCoreUsages := make([]uint64, numCores)
--	currentTime := time.Now()
--	for i := range perCoreUsages {
--		perCoreUsages[i] = uint64(rand.Int63n(1000))
--	}
--	for i := 0; i < numStats; i++ {
--		stats := new(info.ContainerStats)
--		stats.Timestamp = currentTime
--		currentTime = currentTime.Add(duration)
--
--		percore := make([]uint64, numCores)
--		for i := range perCoreUsages {
--			perCoreUsages[i] += uint64(rand.Int63n(1000))
--			percore[i] = perCoreUsages[i]
--			stats.Cpu.Usage.Total += percore[i]
--		}
--		stats.Cpu.Usage.PerCpu = percore
--		stats.Cpu.Usage.User = stats.Cpu.Usage.Total
--		stats.Cpu.Usage.System = 0
--		stats.Memory.Usage = uint64(rand.Int63n(4096))
--		ret[i] = stats
+-// ListOutput provides a single Extension result. It differs from the delegated implementation
+-// by the introduction of an intermediate "values" member.
+-const ListOutput = `
+-{
+-	"extensions": {
+-		"values": [
+-			{
+-				"updated": "2013-01-20T00:00:00-00:00",
+-				"name": "Neutron Service Type Management",
+-				"links": [],
+-				"namespace": "http://docs.openstack.org/ext/neutron/service-type/api/v1.0",
+-				"alias": "service-type",
+-				"description": "API for retrieving service providers for Neutron advanced services"
+-			}
+-		]
 -	}
--	return ret
 -}
+-`
 -
--func GenerateRandomContainerSpec(numCores int) info.ContainerSpec {
--	ret := info.ContainerSpec{
--		Cpu:    info.CpuSpec{},
--		Memory: info.MemorySpec{},
--	}
--	ret.Cpu.Limit = uint64(1000 + rand.Int63n(2000))
--	ret.Cpu.MaxLimit = uint64(1000 + rand.Int63n(2000))
--	ret.Cpu.Mask = fmt.Sprintf("0-%d", numCores-1)
--	ret.Memory.Limit = uint64(4096 + rand.Int63n(4096))
--	return ret
--}
+-// HandleListExtensionsSuccessfully creates an HTTP handler that returns ListOutput for a List
+-// call.
+-func HandleListExtensionsSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/extensions", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
 -
--func GenerateRandomContainerInfo(containerName string, numCores int, query *info.ContainerInfoRequest, duration time.Duration) *info.ContainerInfo {
--	stats := GenerateRandomStats(query.NumStats, numCores, duration)
--	spec := GenerateRandomContainerSpec(numCores)
+-		w.Header().Add("Content-Type", "application/json")
 -
--	ret := &info.ContainerInfo{
--		ContainerReference: info.ContainerReference{
--			Name: containerName,
--		},
--		Spec:  spec,
--		Stats: stats,
--	}
--	return ret
+-		fmt.Fprintf(w, `
+-{
+-  "extensions": {
+-    "values": [
+-      {
+-        "updated": "2013-01-20T00:00:00-00:00",
+-        "name": "Neutron Service Type Management",
+-        "links": [],
+-        "namespace": "http://docs.openstack.org/ext/neutron/service-type/api/v1.0",
+-        "alias": "service-type",
+-        "description": "API for retrieving service providers for Neutron advanced services"
+-      }
+-    ]
+-  }
 -}
-diff --git a/Godeps/_workspace/src/github.com/google/cadvisor/info/version.go b/Godeps/_workspace/src/github.com/google/cadvisor/info/version.go
+-    `)
+-	})
+-
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/doc.go
 deleted file mode 100644
-index 771382a..0000000
---- a/Godeps/_workspace/src/github.com/google/cadvisor/info/version.go
+index 0c2d49d..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/doc.go
 +++ /dev/null
-@@ -1,18 +0,0 @@
--// Copyright 2014 Google Inc. All Rights Reserved.
--//
--// Licensed under the Apache License, Version 2.0 (the "License");
--// you may not use this file except in compliance with the License.
--// You may obtain a copy of the License at
--//
--//     http://www.apache.org/licenses/LICENSE-2.0
+@@ -1,7 +0,0 @@
+-// Package tenants provides information and interaction with the
+-// tenants API resource for the OpenStack Identity service.
 -//
--// Unless required by applicable law or agreed to in writing, software
--// distributed under the License is distributed on an "AS IS" BASIS,
--// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
--// See the License for the specific language governing permissions and
--// limitations under the License.
--
--package info
--
--// Version of cAdvisor.
--const VERSION = "0.6.2"
-diff --git a/Godeps/_workspace/src/github.com/google/gofuzz/.travis.yml b/Godeps/_workspace/src/github.com/google/gofuzz/.travis.yml
+-// See http://developer.openstack.org/api-ref-identity-v2.html#identity-auth-v2
+-// and http://developer.openstack.org/api-ref-identity-v2.html#admin-tenants
+-// for more information.
+-package tenants
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/fixtures.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/fixtures.go
 deleted file mode 100644
-index 9384a54..0000000
---- a/Godeps/_workspace/src/github.com/google/gofuzz/.travis.yml
+index 7f044ac..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/fixtures.go
 +++ /dev/null
-@@ -1,12 +0,0 @@
--language: go
+@@ -1,65 +0,0 @@
+-// +build fixtures
 -
--go:
--  - 1.3
--  - 1.2
--  - tip
+-package tenants
 -
--install: 
--  - go get code.google.com/p/go.tools/cmd/cover
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--script:
--  - go test -cover
-diff --git a/Godeps/_workspace/src/github.com/google/gofuzz/CONTRIBUTING.md b/Godeps/_workspace/src/github.com/google/gofuzz/CONTRIBUTING.md
-deleted file mode 100644
-index 51cf5cd..0000000
---- a/Godeps/_workspace/src/github.com/google/gofuzz/CONTRIBUTING.md
-+++ /dev/null
-@@ -1,67 +0,0 @@
--# How to contribute #
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--We'd love to accept your patches and contributions to this project.  There are
--a just a few small guidelines you need to follow.
+-// ListOutput provides a single page of Tenant results.
+-const ListOutput = `
+-{
+-	"tenants": [
+-		{
+-			"id": "1234",
+-			"name": "Red Team",
+-			"description": "The team that is red",
+-			"enabled": true
+-		},
+-		{
+-			"id": "9876",
+-			"name": "Blue Team",
+-			"description": "The team that is blue",
+-			"enabled": false
+-		}
+-	]
+-}
+-`
 -
+-// RedTeam is a Tenant fixture.
+-var RedTeam = Tenant{
+-	ID:          "1234",
+-	Name:        "Red Team",
+-	Description: "The team that is red",
+-	Enabled:     true,
+-}
 -
--## Contributor License Agreement ##
+-// BlueTeam is a Tenant fixture.
+-var BlueTeam = Tenant{
+-	ID:          "9876",
+-	Name:        "Blue Team",
+-	Description: "The team that is blue",
+-	Enabled:     false,
+-}
 -
--Contributions to any Google project must be accompanied by a Contributor
--License Agreement.  This is not a copyright **assignment**, it simply gives
--Google permission to use and redistribute your contributions as part of the
--project.
+-// ExpectedTenantSlice is the slice of tenants expected to be returned from ListOutput.
+-var ExpectedTenantSlice = []Tenant{RedTeam, BlueTeam}
 -
--  * If you are an individual writing original source code and you're sure you
--    own the intellectual property, then you'll need to sign an [individual
--    CLA][].
+-// HandleListTenantsSuccessfully creates an HTTP handler at `/tenants` on the test handler mux that
+-// responds with a list of two tenants.
+-func HandleListTenantsSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/tenants", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
 -
--  * If you work for a company that wants to allow you to contribute your work,
--    then you'll need to sign a [corporate CLA][].
+-		w.Header().Set("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-		fmt.Fprintf(w, ListOutput)
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/requests.go
+deleted file mode 100644
+index 5a359f5..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/requests.go
++++ /dev/null
+@@ -1,33 +0,0 @@
+-package tenants
 -
--You generally only need to submit a CLA once, so if you've already submitted
--one (even if it was for a different project), you probably don't need to do it
--again.
+-import (
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--[individual CLA]: https://developers.google.com/open-source/cla/individual
--[corporate CLA]: https://developers.google.com/open-source/cla/corporate
+-// ListOpts filters the Tenants that are returned by the List call.
+-type ListOpts struct {
+-	// Marker is the ID of the last Tenant on the previous page.
+-	Marker string `q:"marker"`
 -
+-	// Limit specifies the page size.
+-	Limit int `q:"limit"`
+-}
 -
--## Submitting a patch ##
+-// List enumerates the Tenants to which the current token has access.
+-func List(client *gophercloud.ServiceClient, opts *ListOpts) pagination.Pager {
+-	createPage := func(r pagination.PageResult) pagination.Page {
+-		return TenantPage{pagination.LinkedPageBase{PageResult: r}}
+-	}
 -
--  1. It's generally best to start by opening a new issue describing the bug or
--     feature you're intending to fix.  Even if you think it's relatively minor,
--     it's helpful to know what people are working on.  Mention in the initial
--     issue that you are planning to work on that bug or feature so that it can
--     be assigned to you.
+-	url := listURL(client)
+-	if opts != nil {
+-		q, err := gophercloud.BuildQueryString(opts)
+-		if err != nil {
+-			return pagination.Pager{Err: err}
+-		}
+-		url += q.String()
+-	}
 -
--  1. Follow the normal process of [forking][] the project, and setup a new
--     branch to work in.  It's important that each group of changes be done in
--     separate branches in order to ensure that a pull request only includes the
--     commits related to that bug or feature.
+-	return pagination.NewPager(client, url, createPage)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/requests_test.go
+deleted file mode 100644
+index e8f172d..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/requests_test.go
++++ /dev/null
+@@ -1,29 +0,0 @@
+-package tenants
 -
--  1. Go makes it very simple to ensure properly formatted code, so always run
--     `go fmt` on your code before committing it.  You should also run
--     [golint][] over your code.  As noted in the [golint readme][], it's not
--     strictly necessary that your code be completely "lint-free", but this will
--     help you find common style issues.
+-import (
+-	"testing"
 -
--  1. Any significant changes should almost always be accompanied by tests.  The
--     project already has good test coverage, so look at some of the existing
--     tests if you're unsure how to go about it.  [gocov][] and [gocov-html][]
--     are invaluable tools for seeing which parts of your code aren't being
--     exercised by your tests.
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--  1. Do your best to have [well-formed commit messages][] for each change.
--     This provides consistency throughout the project, and ensures that commit
--     messages are able to be formatted properly by various git tools.
+-func TestListTenants(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleListTenantsSuccessfully(t)
 -
--  1. Finally, push the commits to your fork and submit a [pull request][].
+-	count := 0
+-	err := List(client.ServiceClient(), nil).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
 -
--[forking]: https://help.github.com/articles/fork-a-repo
--[golint]: https://github.com/golang/lint
--[golint readme]: https://github.com/golang/lint/blob/master/README
--[gocov]: https://github.com/axw/gocov
--[gocov-html]: https://github.com/matm/gocov-html
--[well-formed commit messages]: http://tbaggery.com/2008/04/19/a-note-about-git-commit-messages.html
--[squash]: http://git-scm.com/book/en/Git-Tools-Rewriting-History#Squashing-Commits
--[pull request]: https://help.github.com/articles/creating-a-pull-request
-diff --git a/Godeps/_workspace/src/github.com/google/gofuzz/LICENSE b/Godeps/_workspace/src/github.com/google/gofuzz/LICENSE
+-		actual, err := ExtractTenants(page)
+-		th.AssertNoErr(t, err)
+-
+-		th.CheckDeepEquals(t, ExpectedTenantSlice, actual)
+-
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, count, 1)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/results.go
 deleted file mode 100644
-index d645695..0000000
---- a/Godeps/_workspace/src/github.com/google/gofuzz/LICENSE
+index c1220c3..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/results.go
 +++ /dev/null
-@@ -1,202 +0,0 @@
--
--                                 Apache License
--                           Version 2.0, January 2004
--                        http://www.apache.org/licenses/
+@@ -1,62 +0,0 @@
+-package tenants
 -
--   TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--   1. Definitions.
+-// Tenant is a grouping of users in the identity service.
+-type Tenant struct {
+-	// ID is a unique identifier for this tenant.
+-	ID string `mapstructure:"id"`
 -
--      "License" shall mean the terms and conditions for use, reproduction,
--      and distribution as defined by Sections 1 through 9 of this document.
+-	// Name is a friendlier user-facing name for this tenant.
+-	Name string `mapstructure:"name"`
 -
--      "Licensor" shall mean the copyright owner or entity authorized by
--      the copyright owner that is granting the License.
+-	// Description is a human-readable explanation of this Tenant's purpose.
+-	Description string `mapstructure:"description"`
 -
--      "Legal Entity" shall mean the union of the acting entity and all
--      other entities that control, are controlled by, or are under common
--      control with that entity. For the purposes of this definition,
--      "control" means (i) the power, direct or indirect, to cause the
--      direction or management of such entity, whether by contract or
--      otherwise, or (ii) ownership of fifty percent (50%) or more of the
--      outstanding shares, or (iii) beneficial ownership of such entity.
+-	// Enabled indicates whether or not a tenant is active.
+-	Enabled bool `mapstructure:"enabled"`
+-}
 -
--      "You" (or "Your") shall mean an individual or Legal Entity
--      exercising permissions granted by this License.
+-// TenantPage is a single page of Tenant results.
+-type TenantPage struct {
+-	pagination.LinkedPageBase
+-}
 -
--      "Source" form shall mean the preferred form for making modifications,
--      including but not limited to software source code, documentation
--      source, and configuration files.
+-// IsEmpty determines whether or not a page of Tenants contains any results.
+-func (page TenantPage) IsEmpty() (bool, error) {
+-	tenants, err := ExtractTenants(page)
+-	if err != nil {
+-		return false, err
+-	}
+-	return len(tenants) == 0, nil
+-}
 -
--      "Object" form shall mean any form resulting from mechanical
--      transformation or translation of a Source form, including but
--      not limited to compiled object code, generated documentation,
--      and conversions to other media types.
+-// NextPageURL extracts the "next" link from the tenants_links section of the result.
+-func (page TenantPage) NextPageURL() (string, error) {
+-	type resp struct {
+-		Links []gophercloud.Link `mapstructure:"tenants_links"`
+-	}
 -
--      "Work" shall mean the work of authorship, whether in Source or
--      Object form, made available under the License, as indicated by a
--      copyright notice that is included in or attached to the work
--      (an example is provided in the Appendix below).
+-	var r resp
+-	err := mapstructure.Decode(page.Body, &r)
+-	if err != nil {
+-		return "", err
+-	}
 -
--      "Derivative Works" shall mean any work, whether in Source or Object
--      form, that is based on (or derived from) the Work and for which the
--      editorial revisions, annotations, elaborations, or other modifications
--      represent, as a whole, an original work of authorship. For the purposes
--      of this License, Derivative Works shall not include works that remain
--      separable from, or merely link (or bind by name) to the interfaces of,
--      the Work and Derivative Works thereof.
+-	return gophercloud.ExtractNextURL(r.Links)
+-}
 -
--      "Contribution" shall mean any work of authorship, including
--      the original version of the Work and any modifications or additions
--      to that Work or Derivative Works thereof, that is intentionally
--      submitted to Licensor for inclusion in the Work by the copyright owner
--      or by an individual or Legal Entity authorized to submit on behalf of
--      the copyright owner. For the purposes of this definition, "submitted"
--      means any form of electronic, verbal, or written communication sent
--      to the Licensor or its representatives, including but not limited to
--      communication on electronic mailing lists, source code control systems,
--      and issue tracking systems that are managed by, or on behalf of, the
--      Licensor for the purpose of discussing and improving the Work, but
--      excluding communication that is conspicuously marked or otherwise
--      designated in writing by the copyright owner as "Not a Contribution."
+-// ExtractTenants returns a slice of Tenants contained in a single page of results.
+-func ExtractTenants(page pagination.Page) ([]Tenant, error) {
+-	casted := page.(TenantPage).Body
+-	var response struct {
+-		Tenants []Tenant `mapstructure:"tenants"`
+-	}
 -
--      "Contributor" shall mean Licensor and any individual or Legal Entity
--      on behalf of whom a Contribution has been received by Licensor and
--      subsequently incorporated within the Work.
+-	err := mapstructure.Decode(casted, &response)
+-	return response.Tenants, err
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/urls.go
+deleted file mode 100644
+index 1dd6ce0..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tenants/urls.go
++++ /dev/null
+@@ -1,7 +0,0 @@
+-package tenants
 -
--   2. Grant of Copyright License. Subject to the terms and conditions of
--      this License, each Contributor hereby grants to You a perpetual,
--      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
--      copyright license to reproduce, prepare Derivative Works of,
--      publicly display, publicly perform, sublicense, and distribute the
--      Work and such Derivative Works in Source or Object form.
+-import "github.com/rackspace/gophercloud"
 -
--   3. Grant of Patent License. Subject to the terms and conditions of
--      this License, each Contributor hereby grants to You a perpetual,
--      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
--      (except as stated in this section) patent license to make, have made,
--      use, offer to sell, sell, import, and otherwise transfer the Work,
--      where such license applies only to those patent claims licensable
--      by such Contributor that are necessarily infringed by their
--      Contribution(s) alone or by combination of their Contribution(s)
--      with the Work to which such Contribution(s) was submitted. If You
--      institute patent litigation against any entity (including a
--      cross-claim or counterclaim in a lawsuit) alleging that the Work
--      or a Contribution incorporated within the Work constitutes direct
--      or contributory patent infringement, then any patent licenses
--      granted to You under this License for that Work shall terminate
--      as of the date such litigation is filed.
+-func listURL(client *gophercloud.ServiceClient) string {
+-	return client.ServiceURL("tenants")
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/doc.go
+deleted file mode 100644
+index 31cacc5..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/doc.go
++++ /dev/null
+@@ -1,5 +0,0 @@
+-// Package tokens provides information and interaction with the token API
+-// resource for the OpenStack Identity service.
+-// For more information, see:
+-// http://developer.openstack.org/api-ref-identity-v2.html#identity-auth-v2
+-package tokens
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/errors.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/errors.go
+deleted file mode 100644
+index 3a9172e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/errors.go
++++ /dev/null
+@@ -1,30 +0,0 @@
+-package tokens
 -
--   4. Redistribution. You may reproduce and distribute copies of the
--      Work or Derivative Works thereof in any medium, with or without
--      modifications, and in Source or Object form, provided that You
--      meet the following conditions:
+-import (
+-	"errors"
+-	"fmt"
+-)
 -
--      (a) You must give any other recipients of the Work or
--          Derivative Works a copy of this License; and
+-var (
+-	// ErrUserIDProvided is returned if you attempt to authenticate with a UserID.
+-	ErrUserIDProvided = unacceptedAttributeErr("UserID")
 -
--      (b) You must cause any modified files to carry prominent notices
--          stating that You changed the files; and
+-	// ErrAPIKeyProvided is returned if you attempt to authenticate with an APIKey.
+-	ErrAPIKeyProvided = unacceptedAttributeErr("APIKey")
 -
--      (c) You must retain, in the Source form of any Derivative Works
--          that You distribute, all copyright, patent, trademark, and
--          attribution notices from the Source form of the Work,
--          excluding those notices that do not pertain to any part of
--          the Derivative Works; and
+-	// ErrDomainIDProvided is returned if you attempt to authenticate with a DomainID.
+-	ErrDomainIDProvided = unacceptedAttributeErr("DomainID")
 -
--      (d) If the Work includes a "NOTICE" text file as part of its
--          distribution, then any Derivative Works that You distribute must
--          include a readable copy of the attribution notices contained
--          within such NOTICE file, excluding those notices that do not
--          pertain to any part of the Derivative Works, in at least one
--          of the following places: within a NOTICE text file distributed
--          as part of the Derivative Works; within the Source form or
--          documentation, if provided along with the Derivative Works; or,
--          within a display generated by the Derivative Works, if and
--          wherever such third-party notices normally appear. The contents
--          of the NOTICE file are for informational purposes only and
--          do not modify the License. You may add Your own attribution
--          notices within Derivative Works that You distribute, alongside
--          or as an addendum to the NOTICE text from the Work, provided
--          that such additional attribution notices cannot be construed
--          as modifying the License.
+-	// ErrDomainNameProvided is returned if you attempt to authenticate with a DomainName.
+-	ErrDomainNameProvided = unacceptedAttributeErr("DomainName")
 -
--      You may add Your own copyright statement to Your modifications and
--      may provide additional or different license terms and conditions
--      for use, reproduction, or distribution of Your modifications, or
--      for any such Derivative Works as a whole, provided Your use,
--      reproduction, and distribution of the Work otherwise complies with
--      the conditions stated in this License.
+-	// ErrUsernameRequired is returned if you attempt ot authenticate without a Username.
+-	ErrUsernameRequired = errors.New("You must supply a Username in your AuthOptions.")
 -
--   5. Submission of Contributions. Unless You explicitly state otherwise,
--      any Contribution intentionally submitted for inclusion in the Work
--      by You to the Licensor shall be under the terms and conditions of
--      this License, without any additional terms or conditions.
--      Notwithstanding the above, nothing herein shall supersede or modify
--      the terms of any separate license agreement you may have executed
--      with Licensor regarding such Contributions.
+-	// ErrPasswordRequired is returned if you don't provide a password.
+-	ErrPasswordRequired = errors.New("Please supply a Password in your AuthOptions.")
+-)
 -
--   6. Trademarks. This License does not grant permission to use the trade
--      names, trademarks, service marks, or product names of the Licensor,
--      except as required for reasonable and customary use in describing the
--      origin of the Work and reproducing the content of the NOTICE file.
+-func unacceptedAttributeErr(attribute string) error {
+-	return fmt.Errorf("The base Identity V2 API does not accept authentication by %s", attribute)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/fixtures.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/fixtures.go
+deleted file mode 100644
+index 1cb0d05..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/fixtures.go
++++ /dev/null
+@@ -1,128 +0,0 @@
+-// +build fixtures
 -
--   7. Disclaimer of Warranty. Unless required by applicable law or
--      agreed to in writing, Licensor provides the Work (and each
--      Contributor provides its Contributions) on an "AS IS" BASIS,
--      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
--      implied, including, without limitation, any warranties or conditions
--      of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
--      PARTICULAR PURPOSE. You are solely responsible for determining the
--      appropriateness of using or redistributing the Work and assume any
--      risks associated with Your exercise of permissions under this License.
+-package tokens
 -
--   8. Limitation of Liability. In no event and under no legal theory,
--      whether in tort (including negligence), contract, or otherwise,
--      unless required by applicable law (such as deliberate and grossly
--      negligent acts) or agreed to in writing, shall any Contributor be
--      liable to You for damages, including any direct, indirect, special,
--      incidental, or consequential damages of any character arising as a
--      result of this License or out of the use or inability to use the
--      Work (including but not limited to damages for loss of goodwill,
--      work stoppage, computer failure or malfunction, or any and all
--      other commercial damages or losses), even if such Contributor
--      has been advised of the possibility of such damages.
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
+-	"time"
 -
--   9. Accepting Warranty or Additional Liability. While redistributing
--      the Work or Derivative Works thereof, You may choose to offer,
--      and charge a fee for, acceptance of support, warranty, indemnity,
--      or other liability obligations and/or rights consistent with this
--      License. However, in accepting such obligations, You may act only
--      on Your own behalf and on Your sole responsibility, not on behalf
--      of any other Contributor, and only if You agree to indemnify,
--      defend, and hold each Contributor harmless for any liability
--      incurred by, or claims asserted against, such Contributor by reason
--      of your accepting any such warranty or additional liability.
+-	"github.com/rackspace/gophercloud/openstack/identity/v2/tenants"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--   END OF TERMS AND CONDITIONS
+-// ExpectedToken is the token that should be parsed from TokenCreationResponse.
+-var ExpectedToken = &Token{
+-	ID:        "aaaabbbbccccdddd",
+-	ExpiresAt: time.Date(2014, time.January, 31, 15, 30, 58, 0, time.UTC),
+-	Tenant: tenants.Tenant{
+-		ID:          "fc394f2ab2df4114bde39905f800dc57",
+-		Name:        "test",
+-		Description: "There are many tenants. This one is yours.",
+-		Enabled:     true,
+-	},
+-}
 -
--   APPENDIX: How to apply the Apache License to your work.
+-// ExpectedServiceCatalog is the service catalog that should be parsed from TokenCreationResponse.
+-var ExpectedServiceCatalog = &ServiceCatalog{
+-	Entries: []CatalogEntry{
+-		CatalogEntry{
+-			Name: "inscrutablewalrus",
+-			Type: "something",
+-			Endpoints: []Endpoint{
+-				Endpoint{
+-					PublicURL: "http://something0:1234/v2/",
+-					Region:    "region0",
+-				},
+-				Endpoint{
+-					PublicURL: "http://something1:1234/v2/",
+-					Region:    "region1",
+-				},
+-			},
+-		},
+-		CatalogEntry{
+-			Name: "arbitrarypenguin",
+-			Type: "else",
+-			Endpoints: []Endpoint{
+-				Endpoint{
+-					PublicURL: "http://else0:4321/v3/",
+-					Region:    "region0",
+-				},
+-			},
+-		},
+-	},
+-}
 -
--      To apply the Apache License to your work, attach the following
--      boilerplate notice, with the fields enclosed by brackets "[]"
--      replaced with your own identifying information. (Don't include
--      the brackets!)  The text should be enclosed in the appropriate
--      comment syntax for the file format. We also recommend that a
--      file or class name and description of purpose be included on the
--      same "printed page" as the copyright notice for easier
--      identification within third-party archives.
+-// TokenCreationResponse is a JSON response that contains ExpectedToken and ExpectedServiceCatalog.
+-const TokenCreationResponse = `
+-{
+-	"access": {
+-		"token": {
+-			"issued_at": "2014-01-30T15:30:58.000000Z",
+-			"expires": "2014-01-31T15:30:58Z",
+-			"id": "aaaabbbbccccdddd",
+-			"tenant": {
+-				"description": "There are many tenants. This one is yours.",
+-				"enabled": true,
+-				"id": "fc394f2ab2df4114bde39905f800dc57",
+-				"name": "test"
+-			}
+-		},
+-		"serviceCatalog": [
+-			{
+-				"endpoints": [
+-					{
+-						"publicURL": "http://something0:1234/v2/",
+-						"region": "region0"
+-					},
+-					{
+-						"publicURL": "http://something1:1234/v2/",
+-						"region": "region1"
+-					}
+-				],
+-				"type": "something",
+-				"name": "inscrutablewalrus"
+-			},
+-			{
+-				"endpoints": [
+-					{
+-						"publicURL": "http://else0:4321/v3/",
+-						"region": "region0"
+-					}
+-				],
+-				"type": "else",
+-				"name": "arbitrarypenguin"
+-			}
+-		]
+-	}
+-}
+-`
 -
--   Copyright [yyyy] [name of copyright owner]
+-// HandleTokenPost expects a POST against a /tokens handler, ensures that the request body has been
+-// constructed properly given certain auth options, and returns the result.
+-func HandleTokenPost(t *testing.T, requestJSON string) {
+-	th.Mux.HandleFunc("/tokens", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		if requestJSON != "" {
+-			th.TestJSONRequest(t, r, requestJSON)
+-		}
 -
--   Licensed under the Apache License, Version 2.0 (the "License");
--   you may not use this file except in compliance with the License.
--   You may obtain a copy of the License at
+-		w.WriteHeader(http.StatusOK)
+-		fmt.Fprintf(w, TokenCreationResponse)
+-	})
+-}
 -
--       http://www.apache.org/licenses/LICENSE-2.0
+-// IsSuccessful ensures that a CreateResult was successful and contains the correct token and
+-// service catalog.
+-func IsSuccessful(t *testing.T, result CreateResult) {
+-	token, err := result.ExtractToken()
+-	th.AssertNoErr(t, err)
+-	th.CheckDeepEquals(t, ExpectedToken, token)
 -
--   Unless required by applicable law or agreed to in writing, software
--   distributed under the License is distributed on an "AS IS" BASIS,
--   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
--   See the License for the specific language governing permissions and
--   limitations under the License.
-diff --git a/Godeps/_workspace/src/github.com/google/gofuzz/README.md b/Godeps/_workspace/src/github.com/google/gofuzz/README.md
+-	serviceCatalog, err := result.ExtractServiceCatalog()
+-	th.AssertNoErr(t, err)
+-	th.CheckDeepEquals(t, ExpectedServiceCatalog, serviceCatalog)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/requests.go
 deleted file mode 100644
-index 68fcf2c..0000000
---- a/Godeps/_workspace/src/github.com/google/gofuzz/README.md
+index 87c923a..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/requests.go
 +++ /dev/null
-@@ -1,71 +0,0 @@
--gofuzz
--======
--
--gofuzz is a library for populating go objects with random values.
--
--[![GoDoc](https://godoc.org/github.com/google/gofuzz?status.png)](https://godoc.org/github.com/google/gofuzz)
--[![Travis](https://travis-ci.org/google/gofuzz.svg?branch=master)](https://travis-ci.org/google/gofuzz)
+@@ -1,87 +0,0 @@
+-package tokens
 -
--This is useful for testing:
--
--* Do your project's objects really serialize/unserialize correctly in all cases?
--* Is there an incorrectly formatted object that will cause your project to panic?
--
--Import with ```import "github.com/google/gofuzz"```
+-import (
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-)
 -
--You can use it on single variables:
--```
--f := fuzz.New()
--var myInt int
--f.Fuzz(&myInt) // myInt gets a random value.
--```
+-// AuthOptionsBuilder describes any argument that may be passed to the Create call.
+-type AuthOptionsBuilder interface {
 -
--You can use it on maps:
--```
--f := fuzz.New().NilChance(0).NumElements(1, 1)
--var myMap map[ComplexKeyType]string
--f.Fuzz(&myMap) // myMap will have exactly one element.
--```
+-	// ToTokenCreateMap assembles the Create request body, returning an error if parameters are
+-	// missing or inconsistent.
+-	ToTokenCreateMap() (map[string]interface{}, error)
+-}
 -
--Customize the chance of getting a nil pointer:
--```
--f := fuzz.New().NilChance(.5)
--var fancyStruct struct {
--  A, B, C, D *string
+-// AuthOptions wraps a gophercloud AuthOptions in order to adhere to the AuthOptionsBuilder
+-// interface.
+-type AuthOptions struct {
+-	gophercloud.AuthOptions
 -}
--f.Fuzz(&fancyStruct) // About half the pointers should be set.
--```
 -
--You can even customize the randomization completely if needed:
--```
--type MyEnum string
--const (
--        A MyEnum = "A"
--        B MyEnum = "B"
--)
--type MyInfo struct {
--        Type MyEnum
--        AInfo *string
--        BInfo *string
+-// WrapOptions embeds a root AuthOptions struct in a package-specific one.
+-func WrapOptions(original gophercloud.AuthOptions) AuthOptions {
+-	return AuthOptions{AuthOptions: original}
 -}
 -
--f := fuzz.New().NilChance(0).Funcs(
--        func(e *MyInfo, c fuzz.Continue) {
--                switch c.Intn(2) {
--                case 0:
--                        e.Type = A
--                        c.Fuzz(&e.AInfo)
--                case 1:
--                        e.Type = B
--                        c.Fuzz(&e.BInfo)
--                }
--        },
--)
+-// ToTokenCreateMap converts AuthOptions into nested maps that can be serialized into a JSON
+-// request.
+-func (auth AuthOptions) ToTokenCreateMap() (map[string]interface{}, error) {
+-	// Error out if an unsupported auth option is present.
+-	if auth.UserID != "" {
+-		return nil, ErrUserIDProvided
+-	}
+-	if auth.APIKey != "" {
+-		return nil, ErrAPIKeyProvided
+-	}
+-	if auth.DomainID != "" {
+-		return nil, ErrDomainIDProvided
+-	}
+-	if auth.DomainName != "" {
+-		return nil, ErrDomainNameProvided
+-	}
 -
--var myObject MyInfo
--f.Fuzz(&myObject) // Type will correspond to whether A or B info is set.
--```
+-	// Username and Password are always required.
+-	if auth.Username == "" {
+-		return nil, ErrUsernameRequired
+-	}
+-	if auth.Password == "" {
+-		return nil, ErrPasswordRequired
+-	}
 -
--See more examples in ```example_test.go```.
+-	// Populate the request map.
+-	authMap := make(map[string]interface{})
 -
--Happy testing!
-diff --git a/Godeps/_workspace/src/github.com/google/gofuzz/doc.go b/Godeps/_workspace/src/github.com/google/gofuzz/doc.go
-deleted file mode 100644
-index 9f9956d..0000000
---- a/Godeps/_workspace/src/github.com/google/gofuzz/doc.go
-+++ /dev/null
-@@ -1,18 +0,0 @@
--/*
--Copyright 2014 Google Inc. All rights reserved.
+-	authMap["passwordCredentials"] = map[string]interface{}{
+-		"username": auth.Username,
+-		"password": auth.Password,
+-	}
 -
--Licensed under the Apache License, Version 2.0 (the "License");
--you may not use this file except in compliance with the License.
--You may obtain a copy of the License at
+-	if auth.TenantID != "" {
+-		authMap["tenantId"] = auth.TenantID
+-	}
+-	if auth.TenantName != "" {
+-		authMap["tenantName"] = auth.TenantName
+-	}
 -
--    http://www.apache.org/licenses/LICENSE-2.0
+-	return map[string]interface{}{"auth": authMap}, nil
+-}
 -
--Unless required by applicable law or agreed to in writing, software
--distributed under the License is distributed on an "AS IS" BASIS,
--WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
--See the License for the specific language governing permissions and
--limitations under the License.
--*/
+-// Create authenticates to the identity service and attempts to acquire a Token.
+-// If successful, the CreateResult
+-// Generally, rather than interact with this call directly, end users should call openstack.AuthenticatedClient(),
+-// which abstracts all of the gory details about navigating service catalogs and such.
+-func Create(client *gophercloud.ServiceClient, auth AuthOptionsBuilder) CreateResult {
+-	request, err := auth.ToTokenCreateMap()
+-	if err != nil {
+-		return CreateResult{gophercloud.Result{Err: err}}
+-	}
 -
--// Package fuzz is a library for populating go objects with random values.
--package fuzz
-diff --git a/Godeps/_workspace/src/github.com/google/gofuzz/example_test.go b/Godeps/_workspace/src/github.com/google/gofuzz/example_test.go
+-	var result CreateResult
+-	_, result.Err = perigee.Request("POST", CreateURL(client), perigee.Options{
+-		ReqBody: &request,
+-		Results: &result.Body,
+-		OkCodes: []int{200, 203},
+-	})
+-	return result
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/requests_test.go
 deleted file mode 100644
-index 792707a..0000000
---- a/Godeps/_workspace/src/github.com/google/gofuzz/example_test.go
+index 2f02825..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/requests_test.go
 +++ /dev/null
-@@ -1,225 +0,0 @@
--/*
--Copyright 2014 Google Inc. All rights reserved.
+@@ -1,140 +0,0 @@
+-package tokens
 -
--Licensed under the Apache License, Version 2.0 (the "License");
--you may not use this file except in compliance with the License.
--You may obtain a copy of the License at
+-import (
+-	"testing"
 -
--    http://www.apache.org/licenses/LICENSE-2.0
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--Unless required by applicable law or agreed to in writing, software
--distributed under the License is distributed on an "AS IS" BASIS,
--WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
--See the License for the specific language governing permissions and
--limitations under the License.
--*/
+-func tokenPost(t *testing.T, options gophercloud.AuthOptions, requestJSON string) CreateResult {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleTokenPost(t, requestJSON)
 -
--package fuzz_test
+-	return Create(client.ServiceClient(), AuthOptions{options})
+-}
 -
--import (
--	"encoding/json"
--	"fmt"
--	"math/rand"
+-func tokenPostErr(t *testing.T, options gophercloud.AuthOptions, expectedErr error) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleTokenPost(t, "")
 -
--	"github.com/google/gofuzz"
--)
+-	actualErr := Create(client.ServiceClient(), AuthOptions{options}).Err
+-	th.CheckEquals(t, expectedErr, actualErr)
+-}
 -
--func ExampleSimple() {
--	type MyType struct {
--		A string
--		B string
--		C int
--		D struct {
--			E float64
--		}
+-func TestCreateWithPassword(t *testing.T) {
+-	options := gophercloud.AuthOptions{
+-		Username: "me",
+-		Password: "swordfish",
 -	}
 -
--	f := fuzz.New()
--	object := MyType{}
--
--	uniqueObjects := map[MyType]int{}
+-	IsSuccessful(t, tokenPost(t, options, `
+-    {
+-      "auth": {
+-        "passwordCredentials": {
+-          "username": "me",
+-          "password": "swordfish"
+-        }
+-      }
+-    }
+-  `))
+-}
 -
--	for i := 0; i < 1000; i++ {
--		f.Fuzz(&object)
--		uniqueObjects[object]++
+-func TestCreateTokenWithTenantID(t *testing.T) {
+-	options := gophercloud.AuthOptions{
+-		Username: "me",
+-		Password: "opensesame",
+-		TenantID: "fc394f2ab2df4114bde39905f800dc57",
 -	}
--	fmt.Printf("Got %v unique objects.\n", len(uniqueObjects))
--	// Output:
--	// Got 1000 unique objects.
+-
+-	IsSuccessful(t, tokenPost(t, options, `
+-    {
+-      "auth": {
+-        "tenantId": "fc394f2ab2df4114bde39905f800dc57",
+-        "passwordCredentials": {
+-          "username": "me",
+-          "password": "opensesame"
+-        }
+-      }
+-    }
+-  `))
 -}
 -
--func ExampleCustom() {
--	type MyType struct {
--		A int
--		B string
+-func TestCreateTokenWithTenantName(t *testing.T) {
+-	options := gophercloud.AuthOptions{
+-		Username:   "me",
+-		Password:   "opensesame",
+-		TenantName: "demo",
 -	}
 -
--	counter := 0
--	f := fuzz.New().Funcs(
--		func(i *int, c fuzz.Continue) {
--			*i = counter
--			counter++
--		},
--	)
--	object := MyType{}
--
--	uniqueObjects := map[MyType]int{}
+-	IsSuccessful(t, tokenPost(t, options, `
+-    {
+-      "auth": {
+-        "tenantName": "demo",
+-        "passwordCredentials": {
+-          "username": "me",
+-          "password": "opensesame"
+-        }
+-      }
+-    }
+-  `))
+-}
 -
--	for i := 0; i < 100; i++ {
--		f.Fuzz(&object)
--		if object.A != i {
--			fmt.Printf("Unexpected value: %#v\n", object)
--		}
--		uniqueObjects[object]++
+-func TestProhibitUserID(t *testing.T) {
+-	options := gophercloud.AuthOptions{
+-		Username: "me",
+-		UserID:   "1234",
+-		Password: "thing",
 -	}
--	fmt.Printf("Got %v unique objects.\n", len(uniqueObjects))
--	// Output:
--	// Got 100 unique objects.
+-
+-	tokenPostErr(t, options, ErrUserIDProvided)
 -}
 -
--func ExampleComplex() {
--	type OtherType struct {
--		A string
--		B string
--	}
--	type MyType struct {
--		Pointer             *OtherType
--		Map                 map[string]OtherType
--		PointerMap          *map[string]OtherType
--		Slice               []OtherType
--		SlicePointer        []*OtherType
--		PointerSlicePointer *[]*OtherType
+-func TestProhibitAPIKey(t *testing.T) {
+-	options := gophercloud.AuthOptions{
+-		Username: "me",
+-		Password: "thing",
+-		APIKey:   "123412341234",
 -	}
 -
--	f := fuzz.New().RandSource(rand.NewSource(0)).NilChance(0).NumElements(1, 1).Funcs(
--		func(o *OtherType, c fuzz.Continue) {
--			o.A = "Foo"
--			o.B = "Bar"
--		},
--		func(op **OtherType, c fuzz.Continue) {
--			*op = &OtherType{"A", "B"}
--		},
--		func(m map[string]OtherType, c fuzz.Continue) {
--			m["Works Because"] = OtherType{
--				"Fuzzer",
--				"Preallocated",
--			}
--		},
--	)
--	object := MyType{}
--	f.Fuzz(&object)
--	bytes, err := json.MarshalIndent(&object, "", "    ")
--	if err != nil {
--		fmt.Printf("error: %v\n", err)
--	}
--	fmt.Printf("%s\n", string(bytes))
--	// Output:
--	// {
--	//     "Pointer": {
--	//         "A": "A",
--	//         "B": "B"
--	//     },
--	//     "Map": {
--	//         "Works Because": {
--	//             "A": "Fuzzer",
--	//             "B": "Preallocated"
--	//         }
--	//     },
--	//     "PointerMap": {
--	//         "Works Because": {
--	//             "A": "Fuzzer",
--	//             "B": "Preallocated"
--	//         }
--	//     },
--	//     "Slice": [
--	//         {
--	//             "A": "Foo",
--	//             "B": "Bar"
--	//         }
--	//     ],
--	//     "SlicePointer": [
--	//         {
--	//             "A": "A",
--	//             "B": "B"
--	//         }
--	//     ],
--	//     "PointerSlicePointer": [
--	//         {
--	//             "A": "A",
--	//             "B": "B"
--	//         }
--	//     ]
--	// }
+-	tokenPostErr(t, options, ErrAPIKeyProvided)
 -}
 -
--func ExampleMap() {
--	f := fuzz.New().NilChance(0).NumElements(1, 1)
--	var myMap map[struct{ A, B, C int }]string
--	f.Fuzz(&myMap)
--	fmt.Printf("myMap has %v element(s).\n", len(myMap))
--	// Output:
--	// myMap has 1 element(s).
+-func TestProhibitDomainID(t *testing.T) {
+-	options := gophercloud.AuthOptions{
+-		Username: "me",
+-		Password: "thing",
+-		DomainID: "1234",
+-	}
+-
+-	tokenPostErr(t, options, ErrDomainIDProvided)
 -}
 -
--func ExampleSingle() {
--	f := fuzz.New()
--	var i int
--	f.Fuzz(&i)
+-func TestProhibitDomainName(t *testing.T) {
+-	options := gophercloud.AuthOptions{
+-		Username:   "me",
+-		Password:   "thing",
+-		DomainName: "wat",
+-	}
 -
--	// Technically, we'd expect this to fail one out of 2 billion attempts...
--	fmt.Printf("(i == 0) == %v", i == 0)
--	// Output:
--	// (i == 0) == false
+-	tokenPostErr(t, options, ErrDomainNameProvided)
 -}
 -
--func ExampleEnum() {
--	type MyEnum string
--	const (
--		A MyEnum = "A"
--		B MyEnum = "B"
--	)
--	type MyInfo struct {
--		Type  MyEnum
--		AInfo *string
--		BInfo *string
+-func TestRequireUsername(t *testing.T) {
+-	options := gophercloud.AuthOptions{
+-		Password: "thing",
 -	}
 -
--	f := fuzz.New().NilChance(0).Funcs(
--		func(e *MyInfo, c fuzz.Continue) {
--			// Note c's embedded Rand allows for direct use.
--			// We could also use c.RandBool() here.
--			switch c.Intn(2) {
--			case 0:
--				e.Type = A
--				c.Fuzz(&e.AInfo)
--			case 1:
--				e.Type = B
--				c.Fuzz(&e.BInfo)
--			}
--		},
--	)
+-	tokenPostErr(t, options, ErrUsernameRequired)
+-}
 -
--	for i := 0; i < 100; i++ {
--		var myObject MyInfo
--		f.Fuzz(&myObject)
--		switch myObject.Type {
--		case A:
--			if myObject.AInfo == nil {
--				fmt.Println("AInfo should have been set!")
--			}
--			if myObject.BInfo != nil {
--				fmt.Println("BInfo should NOT have been set!")
--			}
--		case B:
--			if myObject.BInfo == nil {
--				fmt.Println("BInfo should have been set!")
--			}
--			if myObject.AInfo != nil {
--				fmt.Println("AInfo should NOT have been set!")
--			}
--		default:
--			fmt.Println("Invalid enum value!")
--		}
+-func TestRequirePassword(t *testing.T) {
+-	options := gophercloud.AuthOptions{
+-		Username: "me",
 -	}
--	// Output:
+-
+-	tokenPostErr(t, options, ErrPasswordRequired)
 -}
-diff --git a/Godeps/_workspace/src/github.com/google/gofuzz/fuzz.go b/Godeps/_workspace/src/github.com/google/gofuzz/fuzz.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/results.go
 deleted file mode 100644
-index 31c2838..0000000
---- a/Godeps/_workspace/src/github.com/google/gofuzz/fuzz.go
+index 1eddb9d..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/results.go
 +++ /dev/null
-@@ -1,366 +0,0 @@
--/*
--Copyright 2014 Google Inc. All rights reserved.
--
--Licensed under the Apache License, Version 2.0 (the "License");
--you may not use this file except in compliance with the License.
--You may obtain a copy of the License at
--
--    http://www.apache.org/licenses/LICENSE-2.0
--
--Unless required by applicable law or agreed to in writing, software
--distributed under the License is distributed on an "AS IS" BASIS,
--WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
--See the License for the specific language governing permissions and
--limitations under the License.
--*/
--
--package fuzz
+@@ -1,133 +0,0 @@
+-package tokens
 -
 -import (
--	"fmt"
--	"math/rand"
--	"reflect"
 -	"time"
+-
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/openstack/identity/v2/tenants"
 -)
 -
--// fuzzFuncMap is a map from a type to a fuzzFunc that handles that type.
--type fuzzFuncMap map[reflect.Type]reflect.Value
+-// Token provides only the most basic information related to an authentication token.
+-type Token struct {
+-	// ID provides the primary means of identifying a user to the OpenStack API.
+-	// OpenStack defines this field as an opaque value, so do not depend on its content.
+-	// It is safe, however, to compare for equality.
+-	ID string
 -
--// Fuzzer knows how to fill any object with random fields.
--type Fuzzer struct {
--	fuzzFuncs   fuzzFuncMap
--	r           *rand.Rand
--	nilChance   float64
--	minElements int
--	maxElements int
--}
+-	// ExpiresAt provides a timestamp in ISO 8601 format, indicating when the authentication token becomes invalid.
+-	// After this point in time, future API requests made using this authentication token will respond with errors.
+-	// Either the caller will need to reauthenticate manually, or more preferably, the caller should exploit automatic re-authentication.
+-	// See the AuthOptions structure for more details.
+-	ExpiresAt time.Time
 -
--// New returns a new Fuzzer. Customize your Fuzzer further by calling Funcs,
--// RandSource, NilChance, or NumElements in any order.
--func New() *Fuzzer {
--	f := &Fuzzer{
--		fuzzFuncs:   fuzzFuncMap{},
--		r:           rand.New(rand.NewSource(time.Now().UnixNano())),
--		nilChance:   .2,
--		minElements: 1,
--		maxElements: 10,
--	}
--	return f
+-	// Tenant provides information about the tenant to which this token grants access.
+-	Tenant tenants.Tenant
 -}
 -
--// Funcs adds each entry in fuzzFuncs as a custom fuzzing function.
+-// Endpoint represents a single API endpoint offered by a service.
+-// It provides the public and internal URLs, if supported, along with a region specifier, again if provided.
+-// The significance of the Region field will depend upon your provider.
 -//
--// Each entry in fuzzFuncs must be a function taking two parameters.
--// The first parameter must be a pointer or map. It is the variable that
--// function will fill with random data. The second parameter must be a
--// fuzz.Continue, which will provide a source of randomness and a way
--// to automatically continue fuzzing smaller pieces of the first parameter.
+-// In addition, the interface offered by the service will have version information associated with it
+-// through the VersionId, VersionInfo, and VersionList fields, if provided or supported.
 -//
--// These functions are called sensibly, e.g., if you wanted custom string
--// fuzzing, the function `func(s *string, c fuzz.Continue)` would get
--// called and passed the address of strings. Maps and pointers will always
--// be made/new'd for you, ignoring the NilChange option. For slices, it
--// doesn't make much sense to  pre-create them--Fuzzer doesn't know how
--// long you want your slice--so take a pointer to a slice, and make it
--// yourself. (If you don't want your map/pointer type pre-made, take a
--// pointer to it, and make it yourself.) See the examples for a range of
--// custom functions.
--func (f *Fuzzer) Funcs(fuzzFuncs ...interface{}) *Fuzzer {
--	for i := range fuzzFuncs {
--		v := reflect.ValueOf(fuzzFuncs[i])
--		if v.Kind() != reflect.Func {
--			panic("Need only funcs!")
--		}
--		t := v.Type()
--		if t.NumIn() != 2 || t.NumOut() != 0 {
--			panic("Need 2 in and 0 out params!")
--		}
--		argT := t.In(0)
--		switch argT.Kind() {
--		case reflect.Ptr, reflect.Map:
--		default:
--			panic("fuzzFunc must take pointer or map type")
--		}
--		if t.In(1) != reflect.TypeOf(Continue{}) {
--			panic("fuzzFunc's second parameter must be type fuzz.Continue")
--		}
--		f.fuzzFuncs[argT] = v
--	}
--	return f
+-// In all cases, fields which aren't supported by the provider and service combined will assume a zero-value ("").
+-type Endpoint struct {
+-	TenantID    string `mapstructure:"tenantId"`
+-	PublicURL   string `mapstructure:"publicURL"`
+-	InternalURL string `mapstructure:"internalURL"`
+-	AdminURL    string `mapstructure:"adminURL"`
+-	Region      string `mapstructure:"region"`
+-	VersionID   string `mapstructure:"versionId"`
+-	VersionInfo string `mapstructure:"versionInfo"`
+-	VersionList string `mapstructure:"versionList"`
 -}
 -
--// RandSource causes f to get values from the given source of randomness.
--// Use if you want deterministic fuzzing.
--func (f *Fuzzer) RandSource(s rand.Source) *Fuzzer {
--	f.r = rand.New(s)
--	return f
--}
+-// CatalogEntry provides a type-safe interface to an Identity API V2 service catalog listing.
+-// Each class of service, such as cloud DNS or block storage services, will have a single
+-// CatalogEntry representing it.
+-//
+-// Note: when looking for the desired service, try, whenever possible, to key off the type field.
+-// Otherwise, you'll tie the representation of the service to a specific provider.
+-type CatalogEntry struct {
+-	// Name will contain the provider-specified name for the service.
+-	Name string `mapstructure:"name"`
 -
--// NilChance sets the probability of creating a nil pointer, map, or slice to
--// 'p'. 'p' should be between 0 (no nils) and 1 (all nils), inclusive.
--func (f *Fuzzer) NilChance(p float64) *Fuzzer {
--	if p < 0 || p > 1 {
--		panic("p should be between 0 and 1, inclusive.")
--	}
--	f.nilChance = p
--	return f
--}
+-	// Type will contain a type string if OpenStack defines a type for the service.
+-	// Otherwise, for provider-specific services, the provider may assign their own type strings.
+-	Type string `mapstructure:"type"`
 -
--// NumElements sets the minimum and maximum number of elements that will be
--// added to a non-nil map or slice.
--func (f *Fuzzer) NumElements(atLeast, atMost int) *Fuzzer {
--	if atLeast > atMost {
--		panic("atLeast must be <= atMost")
--	}
--	if atLeast < 0 {
--		panic("atLeast must be >= 0")
--	}
--	f.minElements = atLeast
--	f.maxElements = atMost
--	return f
+-	// Endpoints will let the caller iterate over all the different endpoints that may exist for
+-	// the service.
+-	Endpoints []Endpoint `mapstructure:"endpoints"`
 -}
 -
--func (f *Fuzzer) genElementCount() int {
--	if f.minElements == f.maxElements {
--		return f.minElements
--	}
--	return f.minElements + f.r.Intn(f.maxElements-f.minElements)
+-// ServiceCatalog provides a view into the service catalog from a previous, successful authentication.
+-type ServiceCatalog struct {
+-	Entries []CatalogEntry
 -}
 -
--func (f *Fuzzer) genShouldFill() bool {
--	return f.r.Float64() > f.nilChance
+-// CreateResult defers the interpretation of a created token.
+-// Use ExtractToken() to interpret it as a Token, or ExtractServiceCatalog() to interpret it as a service catalog.
+-type CreateResult struct {
+-	gophercloud.Result
 -}
 -
--// Fuzz recursively fills all of obj's fields with something random.
--// Not safe for cyclic or tree-like structs!
--// obj must be a pointer. Only exported (public) fields can be set (thanks, golang :/ )
--// Intended for tests, so will panic on bad input or unimplemented fields.
--func (f *Fuzzer) Fuzz(obj interface{}) {
--	v := reflect.ValueOf(obj)
--	if v.Kind() != reflect.Ptr {
--		panic("needed ptr!")
+-// ExtractToken returns the just-created Token from a CreateResult.
+-func (result CreateResult) ExtractToken() (*Token, error) {
+-	if result.Err != nil {
+-		return nil, result.Err
 -	}
--	v = v.Elem()
--	f.doFuzz(v)
--}
 -
--func (f *Fuzzer) doFuzz(v reflect.Value) {
--	if !v.CanSet() {
--		return
--	}
--	// Check for both pointer and non-pointer custom functions.
--	if v.CanAddr() && f.tryCustom(v.Addr()) {
--		return
--	}
--	if f.tryCustom(v) {
--		return
--	}
--	if fn, ok := fillFuncMap[v.Kind()]; ok {
--		fn(v, f.r)
--		return
--	}
--	switch v.Kind() {
--	case reflect.Map:
--		if f.genShouldFill() {
--			v.Set(reflect.MakeMap(v.Type()))
--			n := f.genElementCount()
--			for i := 0; i < n; i++ {
--				key := reflect.New(v.Type().Key()).Elem()
--				f.doFuzz(key)
--				val := reflect.New(v.Type().Elem()).Elem()
--				f.doFuzz(val)
--				v.SetMapIndex(key, val)
--			}
--			return
--		}
--		v.Set(reflect.Zero(v.Type()))
--	case reflect.Ptr:
--		if f.genShouldFill() {
--			v.Set(reflect.New(v.Type().Elem()))
--			f.doFuzz(v.Elem())
--			return
--		}
--		v.Set(reflect.Zero(v.Type()))
--	case reflect.Slice:
--		if f.genShouldFill() {
--			n := f.genElementCount()
--			v.Set(reflect.MakeSlice(v.Type(), n, n))
--			for i := 0; i < n; i++ {
--				f.doFuzz(v.Index(i))
--			}
--			return
--		}
--		v.Set(reflect.Zero(v.Type()))
--	case reflect.Struct:
--		for i := 0; i < v.NumField(); i++ {
--			f.doFuzz(v.Field(i))
--		}
--	case reflect.Array:
--		fallthrough
--	case reflect.Chan:
--		fallthrough
--	case reflect.Func:
--		fallthrough
--	case reflect.Interface:
--		fallthrough
--	default:
--		panic(fmt.Sprintf("Can't handle %#v", v.Interface()))
+-	var response struct {
+-		Access struct {
+-			Token struct {
+-				Expires string         `mapstructure:"expires"`
+-				ID      string         `mapstructure:"id"`
+-				Tenant  tenants.Tenant `mapstructure:"tenant"`
+-			} `mapstructure:"token"`
+-		} `mapstructure:"access"`
 -	}
--}
 -
--// tryCustom searches for custom handlers, and returns true iff it finds a match
--// and successfully randomizes v.
--func (f *Fuzzer) tryCustom(v reflect.Value) bool {
--	doCustom, ok := f.fuzzFuncs[v.Type()]
--	if !ok {
--		return false
+-	err := mapstructure.Decode(result.Body, &response)
+-	if err != nil {
+-		return nil, err
 -	}
 -
--	switch v.Kind() {
--	case reflect.Ptr:
--		if v.IsNil() {
--			if !v.CanSet() {
--				return false
--			}
--			v.Set(reflect.New(v.Type().Elem()))
--		}
--	case reflect.Map:
--		if v.IsNil() {
--			if !v.CanSet() {
--				return false
--			}
--			v.Set(reflect.MakeMap(v.Type()))
--		}
--	default:
--		return false
+-	expiresTs, err := time.Parse(gophercloud.RFC3339Milli, response.Access.Token.Expires)
+-	if err != nil {
+-		return nil, err
 -	}
 -
--	doCustom.Call([]reflect.Value{v, reflect.ValueOf(Continue{
--		f:    f,
--		Rand: f.r,
--	})})
--	return true
+-	return &Token{
+-		ID:        response.Access.Token.ID,
+-		ExpiresAt: expiresTs,
+-		Tenant:    response.Access.Token.Tenant,
+-	}, nil
 -}
 -
--// Continue can be passed to custom fuzzing functions to allow them to use
--// the correct source of randomness and to continue fuzzing their members.
--type Continue struct {
--	f *Fuzzer
+-// ExtractServiceCatalog returns the ServiceCatalog that was generated along with the user's Token.
+-func (result CreateResult) ExtractServiceCatalog() (*ServiceCatalog, error) {
+-	if result.Err != nil {
+-		return nil, result.Err
+-	}
 -
--	// For convenience, Continue implements rand.Rand via embedding.
--	// Use this for generating any randomness if you want your fuzzing
--	// to be repeatable for a given seed.
--	*rand.Rand
--}
+-	var response struct {
+-		Access struct {
+-			Entries []CatalogEntry `mapstructure:"serviceCatalog"`
+-		} `mapstructure:"access"`
+-	}
 -
--// Fuzz continues fuzzing obj. obj must be a pointer.
--func (c Continue) Fuzz(obj interface{}) {
--	v := reflect.ValueOf(obj)
--	if v.Kind() != reflect.Ptr {
--		panic("needed ptr!")
+-	err := mapstructure.Decode(result.Body, &response)
+-	if err != nil {
+-		return nil, err
 -	}
--	v = v.Elem()
--	c.f.doFuzz(v)
--}
 -
--// RandString makes a random string up to 20 characters long. The returned string
--// may include a variety of (valid) UTF-8 encodings.
--func (c Continue) RandString() string {
--	return randString(c.Rand)
+-	return &ServiceCatalog{Entries: response.Access.Entries}, nil
 -}
 -
--// RandUint64 makes random 64 bit numbers.
--// Weirdly, rand doesn't have a function that gives you 64 random bits.
--func (c Continue) RandUint64() uint64 {
--	return randUint64(c.Rand)
+-// createErr quickly packs an error in a CreateResult.
+-func createErr(err error) CreateResult {
+-	return CreateResult{gophercloud.Result{Err: err}}
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/urls.go
+deleted file mode 100644
+index cd4c696..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v2/tokens/urls.go
++++ /dev/null
+@@ -1,8 +0,0 @@
+-package tokens
 -
--// RandBool returns true or false randomly.
--func (c Continue) RandBool() bool {
--	return randBool(c.Rand)
--}
+-import "github.com/rackspace/gophercloud"
 -
--func fuzzInt(v reflect.Value, r *rand.Rand) {
--	v.SetInt(int64(randUint64(r)))
+-// CreateURL generates the URL used to create new Tokens.
+-func CreateURL(client *gophercloud.ServiceClient) string {
+-	return client.ServiceURL("tokens")
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/doc.go
+deleted file mode 100644
+index 8516394..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/doc.go
++++ /dev/null
+@@ -1,6 +0,0 @@
+-// Package endpoints provides information and interaction with the service
+-// endpoints API resource in the OpenStack Identity service.
+-//
+-// For more information, see:
+-// http://developer.openstack.org/api-ref-identity-v3.html#endpoints-v3
+-package endpoints
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/errors.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/errors.go
+deleted file mode 100644
+index 854957f..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/errors.go
++++ /dev/null
+@@ -1,21 +0,0 @@
+-package endpoints
 -
--func fuzzUint(v reflect.Value, r *rand.Rand) {
--	v.SetUint(randUint64(r))
+-import "fmt"
+-
+-func requiredAttribute(attribute string) error {
+-	return fmt.Errorf("You must specify %s for this endpoint.", attribute)
 -}
 -
--var fillFuncMap = map[reflect.Kind]func(reflect.Value, *rand.Rand){
--	reflect.Bool: func(v reflect.Value, r *rand.Rand) {
--		v.SetBool(randBool(r))
--	},
--	reflect.Int:     fuzzInt,
--	reflect.Int8:    fuzzInt,
--	reflect.Int16:   fuzzInt,
--	reflect.Int32:   fuzzInt,
--	reflect.Int64:   fuzzInt,
--	reflect.Uint:    fuzzUint,
--	reflect.Uint8:   fuzzUint,
--	reflect.Uint16:  fuzzUint,
--	reflect.Uint32:  fuzzUint,
--	reflect.Uint64:  fuzzUint,
--	reflect.Uintptr: fuzzUint,
--	reflect.Float32: func(v reflect.Value, r *rand.Rand) {
--		v.SetFloat(float64(r.Float32()))
--	},
--	reflect.Float64: func(v reflect.Value, r *rand.Rand) {
--		v.SetFloat(r.Float64())
--	},
--	reflect.Complex64: func(v reflect.Value, r *rand.Rand) {
--		panic("unimplemented")
--	},
--	reflect.Complex128: func(v reflect.Value, r *rand.Rand) {
--		panic("unimplemented")
--	},
--	reflect.String: func(v reflect.Value, r *rand.Rand) {
--		v.SetString(randString(r))
--	},
--	reflect.UnsafePointer: func(v reflect.Value, r *rand.Rand) {
--		panic("unimplemented")
--	},
+-var (
+-	// ErrAvailabilityRequired is reported if an Endpoint is created without an Availability.
+-	ErrAvailabilityRequired = requiredAttribute("an availability")
+-
+-	// ErrNameRequired is reported if an Endpoint is created without a Name.
+-	ErrNameRequired = requiredAttribute("a name")
+-
+-	// ErrURLRequired is reported if an Endpoint is created without a URL.
+-	ErrURLRequired = requiredAttribute("a URL")
+-
+-	// ErrServiceIDRequired is reported if an Endpoint is created without a ServiceID.
+-	ErrServiceIDRequired = requiredAttribute("a serviceID")
+-)
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/requests.go
+deleted file mode 100644
+index 7bdb7ce..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/requests.go
++++ /dev/null
+@@ -1,133 +0,0 @@
+-package endpoints
+-
+-import (
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
+-
+-// EndpointOpts contains the subset of Endpoint attributes that should be used to create or update an Endpoint.
+-type EndpointOpts struct {
+-	Availability gophercloud.Availability
+-	Name         string
+-	Region       string
+-	URL          string
+-	ServiceID    string
 -}
 -
--// randBool returns true or false randomly.
--func randBool(r *rand.Rand) bool {
--	if r.Int()&1 == 1 {
--		return true
+-// Create inserts a new Endpoint into the service catalog.
+-// Within EndpointOpts, Region may be omitted by being left as "", but all other fields are required.
+-func Create(client *gophercloud.ServiceClient, opts EndpointOpts) CreateResult {
+-	// Redefined so that Region can be re-typed as a *string, which can be omitted from the JSON output.
+-	type endpoint struct {
+-		Interface string  `json:"interface"`
+-		Name      string  `json:"name"`
+-		Region    *string `json:"region,omitempty"`
+-		URL       string  `json:"url"`
+-		ServiceID string  `json:"service_id"`
 -	}
--	return false
--}
 -
--type charRange struct {
--	first, last rune
--}
+-	type request struct {
+-		Endpoint endpoint `json:"endpoint"`
+-	}
 -
--// choose returns a random unicode character from the given range, using the
--// given randomness source.
--func (r *charRange) choose(rand *rand.Rand) rune {
--	count := int64(r.last - r.first)
--	return r.first + rune(rand.Int63n(count))
+-	// Ensure that EndpointOpts is fully populated.
+-	if opts.Availability == "" {
+-		return createErr(ErrAvailabilityRequired)
+-	}
+-	if opts.Name == "" {
+-		return createErr(ErrNameRequired)
+-	}
+-	if opts.URL == "" {
+-		return createErr(ErrURLRequired)
+-	}
+-	if opts.ServiceID == "" {
+-		return createErr(ErrServiceIDRequired)
+-	}
+-
+-	// Populate the request body.
+-	reqBody := request{
+-		Endpoint: endpoint{
+-			Interface: string(opts.Availability),
+-			Name:      opts.Name,
+-			URL:       opts.URL,
+-			ServiceID: opts.ServiceID,
+-		},
+-	}
+-	reqBody.Endpoint.Region = gophercloud.MaybeString(opts.Region)
+-
+-	var result CreateResult
+-	_, result.Err = perigee.Request("POST", listURL(client), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &result.Body,
+-		OkCodes:     []int{201},
+-	})
+-	return result
 -}
 -
--var unicodeRanges = []charRange{
--	{' ', '~'},           // ASCII characters
--	{'\u00a0', '\u02af'}, // Multi-byte encoded characters
--	{'\u4e00', '\u9fff'}, // Common CJK (even longer encodings)
+-// ListOpts allows finer control over the endpoints returned by a List call.
+-// All fields are optional.
+-type ListOpts struct {
+-	Availability gophercloud.Availability `q:"interface"`
+-	ServiceID    string                   `q:"service_id"`
+-	Page         int                      `q:"page"`
+-	PerPage      int                      `q:"per_page"`
 -}
 -
--// randString makes a random string up to 20 characters long. The returned string
--// may include a variety of (valid) UTF-8 encodings.
--func randString(r *rand.Rand) string {
--	n := r.Intn(20)
--	runes := make([]rune, n)
--	for i := range runes {
--		runes[i] = unicodeRanges[r.Intn(len(unicodeRanges))].choose(r)
+-// List enumerates endpoints in a paginated collection, optionally filtered by ListOpts criteria.
+-func List(client *gophercloud.ServiceClient, opts ListOpts) pagination.Pager {
+-	u := listURL(client)
+-	q, err := gophercloud.BuildQueryString(opts)
+-	if err != nil {
+-		return pagination.Pager{Err: err}
+-	}
+-	u += q.String()
+-	createPage := func(r pagination.PageResult) pagination.Page {
+-		return EndpointPage{pagination.LinkedPageBase{PageResult: r}}
 -	}
--	return string(runes)
--}
 -
--// randUint64 makes random 64 bit numbers.
--// Weirdly, rand doesn't have a function that gives you 64 random bits.
--func randUint64(r *rand.Rand) uint64 {
--	return uint64(r.Uint32())<<32 | uint64(r.Uint32())
+-	return pagination.NewPager(client, u, createPage)
 -}
-diff --git a/Godeps/_workspace/src/github.com/google/gofuzz/fuzz_test.go b/Godeps/_workspace/src/github.com/google/gofuzz/fuzz_test.go
-deleted file mode 100644
-index 4f0d4db..0000000
---- a/Godeps/_workspace/src/github.com/google/gofuzz/fuzz_test.go
-+++ /dev/null
-@@ -1,258 +0,0 @@
--/*
--Copyright 2014 Google Inc. All rights reserved.
 -
--Licensed under the Apache License, Version 2.0 (the "License");
--you may not use this file except in compliance with the License.
--You may obtain a copy of the License at
+-// Update changes an existing endpoint with new data.
+-// All fields are optional in the provided EndpointOpts.
+-func Update(client *gophercloud.ServiceClient, endpointID string, opts EndpointOpts) UpdateResult {
+-	type endpoint struct {
+-		Interface *string `json:"interface,omitempty"`
+-		Name      *string `json:"name,omitempty"`
+-		Region    *string `json:"region,omitempty"`
+-		URL       *string `json:"url,omitempty"`
+-		ServiceID *string `json:"service_id,omitempty"`
+-	}
 -
--    http://www.apache.org/licenses/LICENSE-2.0
+-	type request struct {
+-		Endpoint endpoint `json:"endpoint"`
+-	}
 -
--Unless required by applicable law or agreed to in writing, software
--distributed under the License is distributed on an "AS IS" BASIS,
--WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
--See the License for the specific language governing permissions and
--limitations under the License.
--*/
+-	reqBody := request{Endpoint: endpoint{}}
+-	reqBody.Endpoint.Interface = gophercloud.MaybeString(string(opts.Availability))
+-	reqBody.Endpoint.Name = gophercloud.MaybeString(opts.Name)
+-	reqBody.Endpoint.Region = gophercloud.MaybeString(opts.Region)
+-	reqBody.Endpoint.URL = gophercloud.MaybeString(opts.URL)
+-	reqBody.Endpoint.ServiceID = gophercloud.MaybeString(opts.ServiceID)
 -
--package fuzz
+-	var result UpdateResult
+-	_, result.Err = perigee.Request("PATCH", endpointURL(client, endpointID), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &result.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return result
+-}
+-
+-// Delete removes an endpoint from the service catalog.
+-func Delete(client *gophercloud.ServiceClient, endpointID string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", endpointURL(client, endpointID), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{204},
+-	})
+-	return res
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/requests_test.go
+deleted file mode 100644
+index 80687c4..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/requests_test.go
++++ /dev/null
+@@ -1,226 +0,0 @@
+-package endpoints
 -
 -import (
+-	"fmt"
+-	"net/http"
 -	"reflect"
 -	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-	"github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
 -)
 -
--func TestFuzz_basic(t *testing.T) {
--	obj := &struct {
--		I    int
--		I8   int8
--		I16  int16
--		I32  int32
--		I64  int64
--		U    uint
--		U8   uint8
--		U16  uint16
--		U32  uint32
--		U64  uint64
--		Uptr uintptr
--		S    string
--		B    bool
--	}{}
+-func TestCreateSuccessful(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
 -
--	failed := map[string]int{}
--	for i := 0; i < 10; i++ {
--		New().Fuzz(obj)
+-	testhelper.Mux.HandleFunc("/endpoints", func(w http.ResponseWriter, r *http.Request) {
+-		testhelper.TestMethod(t, r, "POST")
+-		testhelper.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-		testhelper.TestJSONRequest(t, r, `
+-      {
+-        "endpoint": {
+-          "interface": "public",
+-          "name": "the-endiest-of-points",
+-          "region": "underground",
+-          "url": "https://1.2.3.4:9000/",
+-          "service_id": "asdfasdfasdfasdf"
+-        }
+-      }
+-    `)
 -
--		if n, v := "i", obj.I; v == 0 {
--			failed[n] = failed[n] + 1
--		}
--		if n, v := "i8", obj.I8; v == 0 {
--			failed[n] = failed[n] + 1
--		}
--		if n, v := "i16", obj.I16; v == 0 {
--			failed[n] = failed[n] + 1
--		}
--		if n, v := "i32", obj.I32; v == 0 {
--			failed[n] = failed[n] + 1
--		}
--		if n, v := "i64", obj.I64; v == 0 {
--			failed[n] = failed[n] + 1
--		}
--		if n, v := "u", obj.U; v == 0 {
--			failed[n] = failed[n] + 1
--		}
--		if n, v := "u8", obj.U8; v == 0 {
--			failed[n] = failed[n] + 1
--		}
--		if n, v := "u16", obj.U16; v == 0 {
--			failed[n] = failed[n] + 1
--		}
--		if n, v := "u32", obj.U32; v == 0 {
--			failed[n] = failed[n] + 1
--		}
--		if n, v := "u64", obj.U64; v == 0 {
--			failed[n] = failed[n] + 1
--		}
--		if n, v := "uptr", obj.Uptr; v == 0 {
--			failed[n] = failed[n] + 1
--		}
--		if n, v := "s", obj.S; v == "" {
--			failed[n] = failed[n] + 1
--		}
--		if n, v := "b", obj.B; v == false {
--			failed[n] = failed[n] + 1
--		}
+-		w.WriteHeader(http.StatusCreated)
+-		fmt.Fprintf(w, `
+-      {
+-        "endpoint": {
+-          "id": "12",
+-          "interface": "public",
+-          "links": {
+-            "self": "https://localhost:5000/v3/endpoints/12"
+-          },
+-          "name": "the-endiest-of-points",
+-          "region": "underground",
+-          "service_id": "asdfasdfasdfasdf",
+-          "url": "https://1.2.3.4:9000/"
+-        }
+-      }
+-    `)
+-	})
+-
+-	actual, err := Create(client.ServiceClient(), EndpointOpts{
+-		Availability: gophercloud.AvailabilityPublic,
+-		Name:         "the-endiest-of-points",
+-		Region:       "underground",
+-		URL:          "https://1.2.3.4:9000/",
+-		ServiceID:    "asdfasdfasdfasdf",
+-	}).Extract()
+-	if err != nil {
+-		t.Fatalf("Unable to create an endpoint: %v", err)
 -	}
--	checkFailed(t, failed)
--}
 -
--func checkFailed(t *testing.T, failed map[string]int) {
--	for k, v := range failed {
--		if v > 8 {
--			t.Errorf("%v seems to not be getting set, was zero value %v times", k, v)
--		}
+-	expected := &Endpoint{
+-		ID:           "12",
+-		Availability: gophercloud.AvailabilityPublic,
+-		Name:         "the-endiest-of-points",
+-		Region:       "underground",
+-		ServiceID:    "asdfasdfasdfasdf",
+-		URL:          "https://1.2.3.4:9000/",
+-	}
+-
+-	if !reflect.DeepEqual(actual, expected) {
+-		t.Errorf("Expected %#v, was %#v", expected, actual)
 -	}
 -}
 -
--func TestFuzz_structptr(t *testing.T) {
--	obj := &struct {
--		A *struct {
--			S string
--		}
--	}{}
+-func TestListEndpoints(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
 -
--	f := New().NilChance(.5)
--	failed := map[string]int{}
--	for i := 0; i < 10; i++ {
--		f.Fuzz(obj)
+-	testhelper.Mux.HandleFunc("/endpoints", func(w http.ResponseWriter, r *http.Request) {
+-		testhelper.TestMethod(t, r, "GET")
+-		testhelper.TestHeader(t, r, "X-Auth-Token", client.TokenID)
 -
--		if n, v := "a not nil", obj.A; v == nil {
--			failed[n] = failed[n] + 1
--		}
--		if n, v := "a nil", obj.A; v != nil {
--			failed[n] = failed[n] + 1
--		}
--		if n, v := "as", obj.A; v == nil || v.S == "" {
--			failed[n] = failed[n] + 1
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, `
+-			{
+-				"endpoints": [
+-					{
+-						"id": "12",
+-						"interface": "public",
+-						"links": {
+-							"self": "https://localhost:5000/v3/endpoints/12"
+-						},
+-						"name": "the-endiest-of-points",
+-						"region": "underground",
+-						"service_id": "asdfasdfasdfasdf",
+-						"url": "https://1.2.3.4:9000/"
+-					},
+-					{
+-						"id": "13",
+-						"interface": "internal",
+-						"links": {
+-							"self": "https://localhost:5000/v3/endpoints/13"
+-						},
+-						"name": "shhhh",
+-						"region": "underground",
+-						"service_id": "asdfasdfasdfasdf",
+-						"url": "https://1.2.3.4:9001/"
+-					}
+-				],
+-				"links": {
+-					"next": null,
+-					"previous": null
+-				}
+-			}
+-		`)
+-	})
+-
+-	count := 0
+-	List(client.ServiceClient(), ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractEndpoints(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract endpoints: %v", err)
+-			return false, err
 -		}
--	}
--	checkFailed(t, failed)
--}
 -
--// tryFuzz tries fuzzing up to 20 times. Fail if check() never passes, report the highest
--// stage it ever got to.
--func tryFuzz(t *testing.T, f *Fuzzer, obj interface{}, check func() (stage int, passed bool)) {
--	maxStage := 0
--	for i := 0; i < 20; i++ {
--		f.Fuzz(obj)
--		stage, passed := check()
--		if stage > maxStage {
--			maxStage = stage
+-		expected := []Endpoint{
+-			Endpoint{
+-				ID:           "12",
+-				Availability: gophercloud.AvailabilityPublic,
+-				Name:         "the-endiest-of-points",
+-				Region:       "underground",
+-				ServiceID:    "asdfasdfasdfasdf",
+-				URL:          "https://1.2.3.4:9000/",
+-			},
+-			Endpoint{
+-				ID:           "13",
+-				Availability: gophercloud.AvailabilityInternal,
+-				Name:         "shhhh",
+-				Region:       "underground",
+-				ServiceID:    "asdfasdfasdfasdf",
+-				URL:          "https://1.2.3.4:9001/",
+-			},
 -		}
--		if passed {
--			return
+-
+-		if !reflect.DeepEqual(expected, actual) {
+-			t.Errorf("Expected %#v, got %#v", expected, actual)
 -		}
+-
+-		return true, nil
+-	})
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
 -	}
--	t.Errorf("Only ever got to stage %v", maxStage)
 -}
 -
--func TestFuzz_structmap(t *testing.T) {
--	obj := &struct {
--		A map[struct {
--			S string
--		}]struct {
--			S2 string
--		}
--		B map[string]string
--	}{}
+-func TestUpdateEndpoint(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
 -
--	tryFuzz(t, New(), obj, func() (int, bool) {
--		if obj.A == nil {
--			return 1, false
--		}
--		if len(obj.A) == 0 {
--			return 2, false
--		}
--		for k, v := range obj.A {
--			if k.S == "" {
--				return 3, false
--			}
--			if v.S2 == "" {
--				return 4, false
--			}
+-	testhelper.Mux.HandleFunc("/endpoints/12", func(w http.ResponseWriter, r *http.Request) {
+-		testhelper.TestMethod(t, r, "PATCH")
+-		testhelper.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-		testhelper.TestJSONRequest(t, r, `
+-		{
+-	    "endpoint": {
+-	      "name": "renamed",
+-				"region": "somewhere-else"
+-	    }
 -		}
+-	`)
 -
--		if obj.B == nil {
--			return 5, false
--		}
--		if len(obj.B) == 0 {
--			return 6, false
--		}
--		for k, v := range obj.B {
--			if k == "" {
--				return 7, false
--			}
--			if v == "" {
--				return 8, false
+-		fmt.Fprintf(w, `
+-		{
+-			"endpoint": {
+-				"id": "12",
+-				"interface": "public",
+-				"links": {
+-					"self": "https://localhost:5000/v3/endpoints/12"
+-				},
+-				"name": "renamed",
+-				"region": "somewhere-else",
+-				"service_id": "asdfasdfasdfasdf",
+-				"url": "https://1.2.3.4:9000/"
 -			}
 -		}
--		return 9, true
+-	`)
 -	})
+-
+-	actual, err := Update(client.ServiceClient(), "12", EndpointOpts{
+-		Name:   "renamed",
+-		Region: "somewhere-else",
+-	}).Extract()
+-	if err != nil {
+-		t.Fatalf("Unexpected error from Update: %v", err)
+-	}
+-
+-	expected := &Endpoint{
+-		ID:           "12",
+-		Availability: gophercloud.AvailabilityPublic,
+-		Name:         "renamed",
+-		Region:       "somewhere-else",
+-		ServiceID:    "asdfasdfasdfasdf",
+-		URL:          "https://1.2.3.4:9000/",
+-	}
+-	if !reflect.DeepEqual(expected, actual) {
+-		t.Errorf("Expected %#v, was %#v", expected, actual)
+-	}
 -}
 -
--func TestFuzz_structslice(t *testing.T) {
--	obj := &struct {
--		A []struct {
--			S string
--		}
--		B []string
--	}{}
+-func TestDeleteEndpoint(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
 -
--	tryFuzz(t, New(), obj, func() (int, bool) {
--		if obj.A == nil {
--			return 1, false
--		}
--		if len(obj.A) == 0 {
--			return 2, false
--		}
--		for _, v := range obj.A {
--			if v.S == "" {
--				return 3, false
--			}
--		}
+-	testhelper.Mux.HandleFunc("/endpoints/34", func(w http.ResponseWriter, r *http.Request) {
+-		testhelper.TestMethod(t, r, "DELETE")
+-		testhelper.TestHeader(t, r, "X-Auth-Token", client.TokenID)
 -
--		if obj.B == nil {
--			return 4, false
--		}
--		if len(obj.B) == 0 {
--			return 5, false
--		}
--		for _, v := range obj.B {
--			if v == "" {
--				return 6, false
--			}
--		}
--		return 7, true
+-		w.WriteHeader(http.StatusNoContent)
 -	})
+-
+-	res := Delete(client.ServiceClient(), "34")
+-	testhelper.AssertNoErr(t, res.Err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/results.go
+deleted file mode 100644
+index 1281122..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/results.go
++++ /dev/null
+@@ -1,82 +0,0 @@
+-package endpoints
 -
--func TestFuzz_custom(t *testing.T) {
--	obj := &struct {
--		A string
--		B *string
--		C map[string]string
--		D *map[string]string
--	}{}
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	testPhrase := "gotcalled"
--	testMap := map[string]string{"C": "D"}
--	f := New().Funcs(
--		func(s *string, c Continue) {
--			*s = testPhrase
--		},
--		func(m map[string]string, c Continue) {
--			m["C"] = "D"
--		},
--	)
+-type commonResult struct {
+-	gophercloud.Result
+-}
 -
--	tryFuzz(t, f, obj, func() (int, bool) {
--		if obj.A != testPhrase {
--			return 1, false
--		}
--		if obj.B == nil {
--			return 2, false
--		}
--		if *obj.B != testPhrase {
--			return 3, false
--		}
--		if e, a := testMap, obj.C; !reflect.DeepEqual(e, a) {
--			return 4, false
--		}
--		if obj.D == nil {
--			return 5, false
--		}
--		if e, a := testMap, *obj.D; !reflect.DeepEqual(e, a) {
--			return 6, false
--		}
--		return 7, true
--	})
+-// Extract interprets a GetResult, CreateResult or UpdateResult as a concrete Endpoint.
+-// An error is returned if the original call or the extraction failed.
+-func (r commonResult) Extract() (*Endpoint, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
+-	}
+-
+-	var res struct {
+-		Endpoint `json:"endpoint"`
+-	}
+-
+-	err := mapstructure.Decode(r.Body, &res)
+-
+-	return &res.Endpoint, err
+-}
+-
+-// CreateResult is the deferred result of a Create call.
+-type CreateResult struct {
+-	commonResult
+-}
+-
+-// createErr quickly wraps an error in a CreateResult.
+-func createErr(err error) CreateResult {
+-	return CreateResult{commonResult{gophercloud.Result{Err: err}}}
+-}
+-
+-// UpdateResult is the deferred result of an Update call.
+-type UpdateResult struct {
+-	commonResult
+-}
+-
+-// DeleteResult is the deferred result of an Delete call.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
+-}
+-
+-// Endpoint describes the entry point for another service's API.
+-type Endpoint struct {
+-	ID           string                   `mapstructure:"id" json:"id"`
+-	Availability gophercloud.Availability `mapstructure:"interface" json:"interface"`
+-	Name         string                   `mapstructure:"name" json:"name"`
+-	Region       string                   `mapstructure:"region" json:"region"`
+-	ServiceID    string                   `mapstructure:"service_id" json:"service_id"`
+-	URL          string                   `mapstructure:"url" json:"url"`
+-}
+-
+-// EndpointPage is a single page of Endpoint results.
+-type EndpointPage struct {
+-	pagination.LinkedPageBase
+-}
+-
+-// IsEmpty returns true if no Endpoints were returned.
+-func (p EndpointPage) IsEmpty() (bool, error) {
+-	es, err := ExtractEndpoints(p)
+-	if err != nil {
+-		return true, err
+-	}
+-	return len(es) == 0, nil
+-}
+-
+-// ExtractEndpoints extracts an Endpoint slice from a Page.
+-func ExtractEndpoints(page pagination.Page) ([]Endpoint, error) {
+-	var response struct {
+-		Endpoints []Endpoint `mapstructure:"endpoints"`
+-	}
+-
+-	err := mapstructure.Decode(page.(EndpointPage).Body, &response)
+-
+-	return response.Endpoints, err
 -}
-diff --git a/Godeps/_workspace/src/github.com/kr/text/License b/Godeps/_workspace/src/github.com/kr/text/License
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/urls.go
 deleted file mode 100644
-index 480a328..0000000
---- a/Godeps/_workspace/src/github.com/kr/text/License
+index 547d7b1..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/urls.go
 +++ /dev/null
-@@ -1,19 +0,0 @@
--Copyright 2012 Keith Rarick
+@@ -1,11 +0,0 @@
+-package endpoints
 -
--Permission is hereby granted, free of charge, to any person obtaining a copy
--of this software and associated documentation files (the "Software"), to deal
--in the Software without restriction, including without limitation the rights
--to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
--copies of the Software, and to permit persons to whom the Software is
--furnished to do so, subject to the following conditions:
+-import "github.com/rackspace/gophercloud"
 -
--The above copyright notice and this permission notice shall be included in
--all copies or substantial portions of the Software.
+-func listURL(client *gophercloud.ServiceClient) string {
+-	return client.ServiceURL("endpoints")
+-}
 -
--THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
--IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
--FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
--AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
--LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
--OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
--THE SOFTWARE.
-diff --git a/Godeps/_workspace/src/github.com/kr/text/Readme b/Godeps/_workspace/src/github.com/kr/text/Readme
+-func endpointURL(client *gophercloud.ServiceClient, endpointID string) string {
+-	return client.ServiceURL("endpoints", endpointID)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/urls_test.go
 deleted file mode 100644
-index 7e6e7c0..0000000
---- a/Godeps/_workspace/src/github.com/kr/text/Readme
+index 0b183b7..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/endpoints/urls_test.go
 +++ /dev/null
-@@ -1,3 +0,0 @@
--This is a Go package for manipulating paragraphs of text.
+@@ -1,23 +0,0 @@
+-package endpoints
+-
+-import (
+-	"testing"
 -
--See http://go.pkgdoc.org/github.com/kr/text for full documentation.
-diff --git a/Godeps/_workspace/src/github.com/kr/text/colwriter/Readme b/Godeps/_workspace/src/github.com/kr/text/colwriter/Readme
+-	"github.com/rackspace/gophercloud"
+-)
+-
+-func TestGetListURL(t *testing.T) {
+-	client := gophercloud.ServiceClient{Endpoint: "http://localhost:5000/v3/"}
+-	url := listURL(&client)
+-	if url != "http://localhost:5000/v3/endpoints" {
+-		t.Errorf("Unexpected list URL generated: [%s]", url)
+-	}
+-}
+-
+-func TestGetEndpointURL(t *testing.T) {
+-	client := gophercloud.ServiceClient{Endpoint: "http://localhost:5000/v3/"}
+-	url := endpointURL(&client, "1234")
+-	if url != "http://localhost:5000/v3/endpoints/1234" {
+-		t.Errorf("Unexpected service URL generated: [%s]", url)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/doc.go
 deleted file mode 100644
-index 1c1f4e6..0000000
---- a/Godeps/_workspace/src/github.com/kr/text/colwriter/Readme
+index fa56411..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/doc.go
 +++ /dev/null
-@@ -1,5 +0,0 @@
--Package colwriter provides a write filter that formats
--input lines in multiple columns.
--
--The package is a straightforward translation from
--/src/cmd/draw/mc.c in Plan 9 from User Space.
-diff --git a/Godeps/_workspace/src/github.com/kr/text/colwriter/column.go b/Godeps/_workspace/src/github.com/kr/text/colwriter/column.go
+@@ -1,3 +0,0 @@
+-// Package services provides information and interaction with the services API
+-// resource for the OpenStack Identity service.
+-package services
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/requests.go
 deleted file mode 100644
-index 7302ce9..0000000
---- a/Godeps/_workspace/src/github.com/kr/text/colwriter/column.go
+index 1d9aaa8..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/requests.go
 +++ /dev/null
-@@ -1,147 +0,0 @@
--// Package colwriter provides a write filter that formats
--// input lines in multiple columns.
--//
--// The package is a straightforward translation from
--// /src/cmd/draw/mc.c in Plan 9 from User Space.
--package colwriter
+@@ -1,91 +0,0 @@
+-package services
 -
 -import (
--	"bytes"
--	"io"
--	"unicode/utf8"
--)
--
--const (
--	tab = 4
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
 -)
 -
--const (
--	// Print each input line ending in a colon ':' separately.
--	BreakOnColon uint = 1 << iota
--)
+-type response struct {
+-	Service Service `json:"service"`
+-}
 -
--// A Writer is a filter that arranges input lines in as many columns as will
--// fit in its width. Tab '\t' chars in the input are translated to sequences
--// of spaces ending at multiples of 4 positions.
--//
--// If BreakOnColon is set, each input line ending in a colon ':' is written
--// separately.
--//
--// The Writer assumes that all Unicode code points have the same width; this
--// may not be true in some fonts.
--type Writer struct {
--	w     io.Writer
--	buf   []byte
--	width int
--	flag  uint
--}
--
--// NewWriter allocates and initializes a new Writer writing to w.
--// Parameter width controls the total number of characters on each line
--// across all columns.
--func NewWriter(w io.Writer, width int, flag uint) *Writer {
--	return &Writer{
--		w:     w,
--		width: width,
--		flag:  flag,
--	}
--}
--
--// Write writes p to the writer w. The only errors returned are ones
--// encountered while writing to the underlying output stream.
--func (w *Writer) Write(p []byte) (n int, err error) {
--	var linelen int
--	var lastWasColon bool
--	for i, c := range p {
--		w.buf = append(w.buf, c)
--		linelen++
--		if c == '\t' {
--			w.buf[len(w.buf)-1] = ' '
--			for linelen%tab != 0 {
--				w.buf = append(w.buf, ' ')
--				linelen++
--			}
--		}
--		if w.flag&BreakOnColon != 0 && c == ':' {
--			lastWasColon = true
--		} else if lastWasColon {
--			if c == '\n' {
--				pos := bytes.LastIndex(w.buf[:len(w.buf)-1], []byte{'\n'})
--				if pos < 0 {
--					pos = 0
--				}
--				line := w.buf[pos:]
--				w.buf = w.buf[:pos]
--				if err = w.columnate(); err != nil {
--					if len(line) < i {
--						return i - len(line), err
--					}
--					return 0, err
--				}
--				if n, err := w.w.Write(line); err != nil {
--					if r := len(line) - n; r < i {
--						return i - r, err
--					}
--					return 0, err
--				}
--			}
--			lastWasColon = false
--		}
--		if c == '\n' {
--			linelen = 0
--		}
+-// Create adds a new service of the requested type to the catalog.
+-func Create(client *gophercloud.ServiceClient, serviceType string) CreateResult {
+-	type request struct {
+-		Type string `json:"type"`
 -	}
--	return len(p), nil
+-
+-	req := request{Type: serviceType}
+-
+-	var result CreateResult
+-	_, result.Err = perigee.Request("POST", listURL(client), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		ReqBody:     &req,
+-		Results:     &result.Body,
+-		OkCodes:     []int{201},
+-	})
+-	return result
 -}
 -
--// Flush should be called after the last call to Write to ensure that any data
--// buffered in the Writer is written to output.
--func (w *Writer) Flush() error {
--	return w.columnate()
+-// ListOpts allows you to query the List method.
+-type ListOpts struct {
+-	ServiceType string `q:"type"`
+-	PerPage     int    `q:"perPage"`
+-	Page        int    `q:"page"`
 -}
 -
--func (w *Writer) columnate() error {
--	words := bytes.Split(w.buf, []byte{'\n'})
--	w.buf = nil
--	if len(words[len(words)-1]) == 0 {
--		words = words[:len(words)-1]
--	}
--	maxwidth := 0
--	for _, wd := range words {
--		if n := utf8.RuneCount(wd); n > maxwidth {
--			maxwidth = n
--		}
+-// List enumerates the services available to a specific user.
+-func List(client *gophercloud.ServiceClient, opts ListOpts) pagination.Pager {
+-	u := listURL(client)
+-	q, err := gophercloud.BuildQueryString(opts)
+-	if err != nil {
+-		return pagination.Pager{Err: err}
 -	}
--	maxwidth++ // space char
--	wordsPerLine := w.width / maxwidth
--	if wordsPerLine <= 0 {
--		wordsPerLine = 1
+-	u += q.String()
+-	createPage := func(r pagination.PageResult) pagination.Page {
+-		return ServicePage{pagination.LinkedPageBase{PageResult: r}}
 -	}
--	nlines := (len(words) + wordsPerLine - 1) / wordsPerLine
--	for i := 0; i < nlines; i++ {
--		col := 0
--		endcol := 0
--		for j := i; j < len(words); j += nlines {
--			endcol += maxwidth
--			_, err := w.w.Write(words[j])
--			if err != nil {
--				return err
--			}
--			col += utf8.RuneCount(words[j])
--			if j+nlines < len(words) {
--				for col < endcol {
--					_, err := w.w.Write([]byte{' '})
--					if err != nil {
--						return err
--					}
--					col++
--				}
--			}
--		}
--		_, err := w.w.Write([]byte{'\n'})
--		if err != nil {
--			return err
--		}
+-
+-	return pagination.NewPager(client, u, createPage)
+-}
+-
+-// Get returns additional information about a service, given its ID.
+-func Get(client *gophercloud.ServiceClient, serviceID string) GetResult {
+-	var result GetResult
+-	_, result.Err = perigee.Request("GET", serviceURL(client, serviceID), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		Results:     &result.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return result
+-}
+-
+-// Update changes the service type of an existing service.
+-func Update(client *gophercloud.ServiceClient, serviceID string, serviceType string) UpdateResult {
+-	type request struct {
+-		Type string `json:"type"`
 -	}
--	return nil
+-
+-	req := request{Type: serviceType}
+-
+-	var result UpdateResult
+-	_, result.Err = perigee.Request("PATCH", serviceURL(client, serviceID), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		ReqBody:     &req,
+-		Results:     &result.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return result
+-}
+-
+-// Delete removes an existing service.
+-// It either deletes all associated endpoints, or fails until all endpoints are deleted.
+-func Delete(client *gophercloud.ServiceClient, serviceID string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", serviceURL(client, serviceID), perigee.Options{
+-		MoreHeaders: client.AuthenticatedHeaders(),
+-		OkCodes:     []int{204},
+-	})
+-	return res
 -}
-diff --git a/Godeps/_workspace/src/github.com/kr/text/colwriter/column_test.go b/Godeps/_workspace/src/github.com/kr/text/colwriter/column_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/requests_test.go
 deleted file mode 100644
-index 8d0bf8f..0000000
---- a/Godeps/_workspace/src/github.com/kr/text/colwriter/column_test.go
+index 32e6d1b..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/requests_test.go
 +++ /dev/null
-@@ -1,90 +0,0 @@
--package colwriter
+@@ -1,209 +0,0 @@
+-package services
 -
 -import (
--	"bytes"
+-	"fmt"
+-	"net/http"
+-	"reflect"
 -	"testing"
+-
+-	"github.com/rackspace/gophercloud/pagination"
+-	"github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
 -)
 -
--var src = `
--.git
--.gitignore
--.godir
--Procfile:
--README.md
--api.go
--apps.go
--auth.go
--darwin.go
--data.go
--dyno.go:
--env.go
--git.go
--help.go
--hkdist
--linux.go
--ls.go
--main.go
--plugin.go
--run.go
--scale.go
--ssh.go
--tail.go
--term
--unix.go
--update.go
--version.go
--windows.go
--`[1:]
--
--var tests = []struct{
--	wid  int
--	flag uint
--	src  string
--	want string
--}{
--	{80, 0, "", ""},
--	{80, 0, src, `
--.git       README.md  darwin.go  git.go     ls.go      scale.go   unix.go
--.gitignore api.go     data.go    help.go    main.go    ssh.go     update.go
--.godir     apps.go    dyno.go:   hkdist     plugin.go  tail.go    version.go
--Procfile:  auth.go    env.go     linux.go   run.go     term       windows.go
--`[1:]},
--	{80, BreakOnColon, src, `
--.git       .gitignore .godir
--
--Procfile:
--README.md api.go    apps.go   auth.go   darwin.go data.go
--
--dyno.go:
--env.go     hkdist     main.go    scale.go   term       version.go
--git.go     linux.go   plugin.go  ssh.go     unix.go    windows.go
--help.go    ls.go      run.go     tail.go    update.go
--`[1:]},
--	{20, 0, `
--Hello
--Γειά σου
--안녕
--今日は
--`[1:], `
--Hello    안녕
--Γειά σου 今日は
--`[1:]},
+-func TestCreateSuccessful(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
+-
+-	testhelper.Mux.HandleFunc("/services", func(w http.ResponseWriter, r *http.Request) {
+-		testhelper.TestMethod(t, r, "POST")
+-		testhelper.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-		testhelper.TestJSONRequest(t, r, `{ "type": "compute" }`)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
+-		fmt.Fprintf(w, `{
+-        "service": {
+-          "description": "Here's your service",
+-          "id": "1234",
+-          "name": "InscrutableOpenStackProjectName",
+-          "type": "compute"
+-        }
+-    }`)
+-	})
+-
+-	result, err := Create(client.ServiceClient(), "compute").Extract()
+-	if err != nil {
+-		t.Fatalf("Unexpected error from Create: %v", err)
+-	}
+-
+-	if result.Description == nil || *result.Description != "Here's your service" {
+-		t.Errorf("Service description was unexpected [%s]", result.Description)
+-	}
+-	if result.ID != "1234" {
+-		t.Errorf("Service ID was unexpected [%s]", result.ID)
+-	}
+-	if result.Name != "InscrutableOpenStackProjectName" {
+-		t.Errorf("Service name was unexpected [%s]", result.Name)
+-	}
+-	if result.Type != "compute" {
+-		t.Errorf("Service type was unexpected [%s]", result.Type)
+-	}
 -}
 -
--func TestWriter(t *testing.T) {
--	for _, test := range tests {
--		b := new(bytes.Buffer)
--		w := NewWriter(b, test.wid, test.flag)
--		if _, err := w.Write([]byte(test.src)); err != nil {
--			t.Error(err)
+-func TestListSinglePage(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
+-
+-	testhelper.Mux.HandleFunc("/services", func(w http.ResponseWriter, r *http.Request) {
+-		testhelper.TestMethod(t, r, "GET")
+-		testhelper.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, `
+-			{
+-				"links": {
+-					"next": null,
+-					"previous": null
+-				},
+-				"services": [
+-					{
+-						"description": "Service One",
+-						"id": "1234",
+-						"name": "service-one",
+-						"type": "identity"
+-					},
+-					{
+-						"description": "Service Two",
+-						"id": "9876",
+-						"name": "service-two",
+-						"type": "compute"
+-					}
+-				]
+-			}
+-		`)
+-	})
+-
+-	count := 0
+-	err := List(client.ServiceClient(), ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractServices(page)
+-		if err != nil {
+-			return false, err
 -		}
--		if err := w.Flush(); err != nil {
--			t.Error(err)
+-
+-		desc0 := "Service One"
+-		desc1 := "Service Two"
+-		expected := []Service{
+-			Service{
+-				Description: &desc0,
+-				ID:          "1234",
+-				Name:        "service-one",
+-				Type:        "identity",
+-			},
+-			Service{
+-				Description: &desc1,
+-				ID:          "9876",
+-				Name:        "service-two",
+-				Type:        "compute",
+-			},
 -		}
--		if g := b.String(); test.want != g {
--			t.Log("\n" + test.want)
--			t.Log("\n" + g)
--			t.Errorf("%q != %q", test.want, g)
+-
+-		if !reflect.DeepEqual(expected, actual) {
+-			t.Errorf("Expected %#v, got %#v", expected, actual)
 -		}
+-
+-		return true, nil
+-	})
+-	if err != nil {
+-		t.Errorf("Unexpected error while paging: %v", err)
+-	}
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/kr/text/doc.go b/Godeps/_workspace/src/github.com/kr/text/doc.go
-deleted file mode 100644
-index cf4c198..0000000
---- a/Godeps/_workspace/src/github.com/kr/text/doc.go
-+++ /dev/null
-@@ -1,3 +0,0 @@
--// Package text provides rudimentary functions for manipulating text in
--// paragraphs.
--package text
-diff --git a/Godeps/_workspace/src/github.com/kr/text/indent.go b/Godeps/_workspace/src/github.com/kr/text/indent.go
+-
+-func TestGetSuccessful(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
+-
+-	testhelper.Mux.HandleFunc("/services/12345", func(w http.ResponseWriter, r *http.Request) {
+-		testhelper.TestMethod(t, r, "GET")
+-		testhelper.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, `
+-			{
+-				"service": {
+-						"description": "Service One",
+-						"id": "12345",
+-						"name": "service-one",
+-						"type": "identity"
+-				}
+-			}
+-		`)
+-	})
+-
+-	result, err := Get(client.ServiceClient(), "12345").Extract()
+-	if err != nil {
+-		t.Fatalf("Error fetching service information: %v", err)
+-	}
+-
+-	if result.ID != "12345" {
+-		t.Errorf("Unexpected service ID: %s", result.ID)
+-	}
+-	if *result.Description != "Service One" {
+-		t.Errorf("Unexpected service description: [%s]", *result.Description)
+-	}
+-	if result.Name != "service-one" {
+-		t.Errorf("Unexpected service name: [%s]", result.Name)
+-	}
+-	if result.Type != "identity" {
+-		t.Errorf("Unexpected service type: [%s]", result.Type)
+-	}
+-}
+-
+-func TestUpdateSuccessful(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
+-
+-	testhelper.Mux.HandleFunc("/services/12345", func(w http.ResponseWriter, r *http.Request) {
+-		testhelper.TestMethod(t, r, "PATCH")
+-		testhelper.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-		testhelper.TestJSONRequest(t, r, `{ "type": "lasermagic" }`)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, `
+-			{
+-				"service": {
+-						"id": "12345",
+-						"type": "lasermagic"
+-				}
+-			}
+-		`)
+-	})
+-
+-	result, err := Update(client.ServiceClient(), "12345", "lasermagic").Extract()
+-	if err != nil {
+-		t.Fatalf("Unable to update service: %v", err)
+-	}
+-
+-	if result.ID != "12345" {
+-		t.Fatalf("Expected ID 12345, was %s", result.ID)
+-	}
+-}
+-
+-func TestDeleteSuccessful(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
+-
+-	testhelper.Mux.HandleFunc("/services/12345", func(w http.ResponseWriter, r *http.Request) {
+-		testhelper.TestMethod(t, r, "DELETE")
+-		testhelper.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-
+-	res := Delete(client.ServiceClient(), "12345")
+-	testhelper.AssertNoErr(t, res.Err)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/results.go
 deleted file mode 100644
-index 4ebac45..0000000
---- a/Godeps/_workspace/src/github.com/kr/text/indent.go
+index 1d0d141..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/results.go
 +++ /dev/null
-@@ -1,74 +0,0 @@
--package text
+@@ -1,80 +0,0 @@
+-package services
 -
 -import (
--	"io"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-
+-	"github.com/mitchellh/mapstructure"
 -)
 -
--// Indent inserts prefix at the beginning of each non-empty line of s. The
--// end-of-line marker is NL.
--func Indent(s, prefix string) string {
--	return string(IndentBytes([]byte(s), []byte(prefix)))
+-type commonResult struct {
+-	gophercloud.Result
 -}
 -
--// IndentBytes inserts prefix at the beginning of each non-empty line of b.
--// The end-of-line marker is NL.
--func IndentBytes(b, prefix []byte) []byte {
--	var res []byte
--	bol := true
--	for _, c := range b {
--		if bol && c != '\n' {
--			res = append(res, prefix...)
--		}
--		res = append(res, c)
--		bol = c == '\n'
+-// Extract interprets a GetResult, CreateResult or UpdateResult as a concrete Service.
+-// An error is returned if the original call or the extraction failed.
+-func (r commonResult) Extract() (*Service, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
 -	}
--	return res
+-
+-	var res struct {
+-		Service `json:"service"`
+-	}
+-
+-	err := mapstructure.Decode(r.Body, &res)
+-
+-	return &res.Service, err
+-}
+-
+-// CreateResult is the deferred result of a Create call.
+-type CreateResult struct {
+-	commonResult
+-}
+-
+-// GetResult is the deferred result of a Get call.
+-type GetResult struct {
+-	commonResult
+-}
+-
+-// UpdateResult is the deferred result of an Update call.
+-type UpdateResult struct {
+-	commonResult
+-}
+-
+-// DeleteResult is the deferred result of an Delete call.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
+-}
+-
+-// Service is the result of a list or information query.
+-type Service struct {
+-	Description *string `json:"description,omitempty"`
+-	ID          string  `json:"id"`
+-	Name        string  `json:"name"`
+-	Type        string  `json:"type"`
 -}
 -
--// Writer indents each line of its input.
--type indentWriter struct {
--	w   io.Writer
--	bol bool
--	pre [][]byte
--	sel int
--	off int
+-// ServicePage is a single page of Service results.
+-type ServicePage struct {
+-	pagination.LinkedPageBase
 -}
 -
--// NewIndentWriter makes a new write filter that indents the input
--// lines. Each line is prefixed in order with the corresponding
--// element of pre. If there are more lines than elements, the last
--// element of pre is repeated for each subsequent line.
--func NewIndentWriter(w io.Writer, pre ...[]byte) io.Writer {
--	return &indentWriter{
--		w:   w,
--		pre: pre,
--		bol: true,
+-// IsEmpty returns true if the page contains no results.
+-func (p ServicePage) IsEmpty() (bool, error) {
+-	services, err := ExtractServices(p)
+-	if err != nil {
+-		return true, err
 -	}
+-	return len(services) == 0, nil
 -}
 -
--// The only errors returned are from the underlying indentWriter.
--func (w *indentWriter) Write(p []byte) (n int, err error) {
--	for _, c := range p {
--		if w.bol {
--			var i int
--			i, err = w.w.Write(w.pre[w.sel][w.off:])
--			w.off += i
--			if err != nil {
--				return n, err
--			}
--		}
--		_, err = w.w.Write([]byte{c})
--		if err != nil {
--			return n, err
--		}
--		n++
--		w.bol = c == '\n'
--		if w.bol {
--			w.off = 0
--			if w.sel < len(w.pre)-1 {
--				w.sel++
--			}
--		}
+-// ExtractServices extracts a slice of Services from a Collection acquired from List.
+-func ExtractServices(page pagination.Page) ([]Service, error) {
+-	var response struct {
+-		Services []Service `mapstructure:"services"`
 -	}
--	return n, nil
+-
+-	err := mapstructure.Decode(page.(ServicePage).Body, &response)
+-	return response.Services, err
 -}
-diff --git a/Godeps/_workspace/src/github.com/kr/text/indent_test.go b/Godeps/_workspace/src/github.com/kr/text/indent_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/urls.go
 deleted file mode 100644
-index 5c723ee..0000000
---- a/Godeps/_workspace/src/github.com/kr/text/indent_test.go
+index 85443a4..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/urls.go
 +++ /dev/null
-@@ -1,119 +0,0 @@
--package text
+@@ -1,11 +0,0 @@
+-package services
+-
+-import "github.com/rackspace/gophercloud"
+-
+-func listURL(client *gophercloud.ServiceClient) string {
+-	return client.ServiceURL("services")
+-}
+-
+-func serviceURL(client *gophercloud.ServiceClient, serviceID string) string {
+-	return client.ServiceURL("services", serviceID)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/urls_test.go
+deleted file mode 100644
+index 5a31b32..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/services/urls_test.go
++++ /dev/null
+@@ -1,23 +0,0 @@
+-package services
 -
 -import (
--	"bytes"
 -	"testing"
--)
 -
--type T struct {
--	inp, exp, pre string
--}
+-	"github.com/rackspace/gophercloud"
+-)
 -
--var tests = []T{
--	{
--		"The quick brown fox\njumps over the lazy\ndog.\nBut not quickly.\n",
--		"xxxThe quick brown fox\nxxxjumps over the lazy\nxxxdog.\nxxxBut not quickly.\n",
--		"xxx",
--	},
--	{
--		"The quick brown fox\njumps over the lazy\ndog.\n\nBut not quickly.",
--		"xxxThe quick brown fox\nxxxjumps over the lazy\nxxxdog.\n\nxxxBut not quickly.",
--		"xxx",
--	},
+-func TestListURL(t *testing.T) {
+-	client := gophercloud.ServiceClient{Endpoint: "http://localhost:5000/v3/"}
+-	url := listURL(&client)
+-	if url != "http://localhost:5000/v3/services" {
+-		t.Errorf("Unexpected list URL generated: [%s]", url)
+-	}
 -}
 -
--func TestIndent(t *testing.T) {
--	for _, test := range tests {
--		got := Indent(test.inp, test.pre)
--		if got != test.exp {
--			t.Errorf("mismatch %q != %q", got, test.exp)
--		}
+-func TestServiceURL(t *testing.T) {
+-	client := gophercloud.ServiceClient{Endpoint: "http://localhost:5000/v3/"}
+-	url := serviceURL(&client, "1234")
+-	if url != "http://localhost:5000/v3/services/1234" {
+-		t.Errorf("Unexpected service URL generated: [%s]", url)
 -	}
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/doc.go
+deleted file mode 100644
+index 76ff5f4..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/doc.go
++++ /dev/null
+@@ -1,6 +0,0 @@
+-// Package tokens provides information and interaction with the token API
+-// resource for the OpenStack Identity service.
+-//
+-// For more information, see:
+-// http://developer.openstack.org/api-ref-identity-v3.html#tokens-v3
+-package tokens
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/errors.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/errors.go
+deleted file mode 100644
+index 4476109..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/errors.go
++++ /dev/null
+@@ -1,72 +0,0 @@
+-package tokens
 -
--type IndentWriterTest struct {
--	inp, exp string
--	pre      []string
+-import (
+-	"errors"
+-	"fmt"
+-)
+-
+-func unacceptedAttributeErr(attribute string) error {
+-	return fmt.Errorf("The base Identity V3 API does not accept authentication by %s", attribute)
 -}
 -
--var ts = []IndentWriterTest{
--	{
--		`
--The quick brown fox
--jumps over the lazy
--dog.
--But not quickly.
--`[1:],
--		`
--xxxThe quick brown fox
--xxxjumps over the lazy
--xxxdog.
--xxxBut not quickly.
--`[1:],
--		[]string{"xxx"},
--	},
--	{
--		`
--The quick brown fox
--jumps over the lazy
--dog.
--But not quickly.
--`[1:],
--		`
--xxaThe quick brown fox
--xxxjumps over the lazy
--xxxdog.
--xxxBut not quickly.
--`[1:],
--		[]string{"xxa", "xxx"},
--	},
--	{
--		`
--The quick brown fox
--jumps over the lazy
--dog.
--But not quickly.
--`[1:],
--		`
--xxaThe quick brown fox
--xxbjumps over the lazy
--xxcdog.
--xxxBut not quickly.
--`[1:],
--		[]string{"xxa", "xxb", "xxc", "xxx"},
--	},
--	{
--		`
--The quick brown fox
--jumps over the lazy
--dog.
--
--But not quickly.`[1:],
--		`
--xxaThe quick brown fox
--xxxjumps over the lazy
--xxxdog.
--xxx
--xxxBut not quickly.`[1:],
--		[]string{"xxa", "xxx"},
--	},
+-func redundantWithTokenErr(attribute string) error {
+-	return fmt.Errorf("%s may not be provided when authenticating with a TokenID", attribute)
 -}
 -
--func TestIndentWriter(t *testing.T) {
--	for _, test := range ts {
--		b := new(bytes.Buffer)
--		pre := make([][]byte, len(test.pre))
--		for i := range test.pre {
--			pre[i] = []byte(test.pre[i])
--		}
--		w := NewIndentWriter(b, pre...)
--		if _, err := w.Write([]byte(test.inp)); err != nil {
--			t.Error(err)
--		}
--		if got := b.String(); got != test.exp {
--			t.Errorf("mismatch %q != %q", got, test.exp)
--			t.Log(got)
--			t.Log(test.exp)
--		}
--	}
+-func redundantWithUserID(attribute string) error {
+-	return fmt.Errorf("%s may not be provided when authenticating with a UserID", attribute)
 -}
-diff --git a/Godeps/_workspace/src/github.com/kr/text/mc/Readme b/Godeps/_workspace/src/github.com/kr/text/mc/Readme
-deleted file mode 100644
-index 519ddc0..0000000
---- a/Godeps/_workspace/src/github.com/kr/text/mc/Readme
-+++ /dev/null
-@@ -1,9 +0,0 @@
--Command mc prints in multiple columns.
 -
--  Usage: mc [-] [-N] [file...]
+-var (
+-	// ErrAPIKeyProvided indicates that an APIKey was provided but can't be used.
+-	ErrAPIKeyProvided = unacceptedAttributeErr("APIKey")
+-
+-	// ErrTenantIDProvided indicates that a TenantID was provided but can't be used.
+-	ErrTenantIDProvided = unacceptedAttributeErr("TenantID")
+-
+-	// ErrTenantNameProvided indicates that a TenantName was provided but can't be used.
+-	ErrTenantNameProvided = unacceptedAttributeErr("TenantName")
+-
+-	// ErrUsernameWithToken indicates that a Username was provided, but token authentication is being used instead.
+-	ErrUsernameWithToken = redundantWithTokenErr("Username")
+-
+-	// ErrUserIDWithToken indicates that a UserID was provided, but token authentication is being used instead.
+-	ErrUserIDWithToken = redundantWithTokenErr("UserID")
+-
+-	// ErrDomainIDWithToken indicates that a DomainID was provided, but token authentication is being used instead.
+-	ErrDomainIDWithToken = redundantWithTokenErr("DomainID")
+-
+-	// ErrDomainNameWithToken indicates that a DomainName was provided, but token authentication is being used instead.s
+-	ErrDomainNameWithToken = redundantWithTokenErr("DomainName")
+-
+-	// ErrUsernameOrUserID indicates that neither username nor userID are specified, or both are at once.
+-	ErrUsernameOrUserID = errors.New("Exactly one of Username and UserID must be provided for password authentication")
+-
+-	// ErrDomainIDWithUserID indicates that a DomainID was provided, but unnecessary because a UserID is being used.
+-	ErrDomainIDWithUserID = redundantWithUserID("DomainID")
+-
+-	// ErrDomainNameWithUserID indicates that a DomainName was provided, but unnecessary because a UserID is being used.
+-	ErrDomainNameWithUserID = redundantWithUserID("DomainName")
+-
+-	// ErrDomainIDOrDomainName indicates that a username was provided, but no domain to scope it.
+-	// It may also indicate that both a DomainID and a DomainName were provided at once.
+-	ErrDomainIDOrDomainName = errors.New("You must provide exactly one of DomainID or DomainName to authenticate by Username")
 -
--Mc splits the input into as many columns as will fit in N
--print positions. If the output is a tty, the default N is
--the number of characters in a terminal line; otherwise the
--default N is 80. Under option - each input line ending in
--a colon ':' is printed separately.
-diff --git a/Godeps/_workspace/src/github.com/kr/text/mc/mc.go b/Godeps/_workspace/src/github.com/kr/text/mc/mc.go
+-	// ErrMissingPassword indicates that no password was provided and no token is available.
+-	ErrMissingPassword = errors.New("You must provide a password to authenticate")
+-
+-	// ErrScopeDomainIDOrDomainName indicates that a domain ID or Name was required in a Scope, but not present.
+-	ErrScopeDomainIDOrDomainName = errors.New("You must provide exactly one of DomainID or DomainName in a Scope with ProjectName")
+-
+-	// ErrScopeProjectIDOrProjectName indicates that both a ProjectID and a ProjectName were provided in a Scope.
+-	ErrScopeProjectIDOrProjectName = errors.New("You must provide at most one of ProjectID or ProjectName in a Scope")
+-
+-	// ErrScopeProjectIDAlone indicates that a ProjectID was provided with other constraints in a Scope.
+-	ErrScopeProjectIDAlone = errors.New("ProjectID must be supplied alone in a Scope")
+-
+-	// ErrScopeDomainName indicates that a DomainName was provided alone in a Scope.
+-	ErrScopeDomainName = errors.New("DomainName must be supplied with a ProjectName or ProjectID in a Scope.")
+-
+-	// ErrScopeEmpty indicates that no credentials were provided in a Scope.
+-	ErrScopeEmpty = errors.New("You must provide either a Project or Domain in a Scope")
+-)
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/requests.go
 deleted file mode 100644
-index 00169a3..0000000
---- a/Godeps/_workspace/src/github.com/kr/text/mc/mc.go
+index 5ca1031..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/requests.go
 +++ /dev/null
-@@ -1,62 +0,0 @@
--// Command mc prints in multiple columns.
--//
--//   Usage: mc [-] [-N] [file...]
--//
--// Mc splits the input into as many columns as will fit in N
--// print positions. If the output is a tty, the default N is
--// the number of characters in a terminal line; otherwise the
--// default N is 80. Under option - each input line ending in
--// a colon ':' is printed separately.
--package main
+@@ -1,286 +0,0 @@
+-package tokens
 -
 -import (
--	"github.com/kr/pty"
--	"github.com/kr/text/colwriter"
--	"io"
--	"log"
--	"os"
--	"strconv"
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
 -)
 -
--func main() {
--	var width int
--	var flag uint
--	args := os.Args[1:]
--	for len(args) > 0 && len(args[0]) > 0 && args[0][0] == '-' {
--		if len(args[0]) > 1 {
--			width, _ = strconv.Atoi(args[0][1:])
--		} else {
--			flag |= colwriter.BreakOnColon
--		}
--		args = args[1:]
+-// Scope allows a created token to be limited to a specific domain or project.
+-type Scope struct {
+-	ProjectID   string
+-	ProjectName string
+-	DomainID    string
+-	DomainName  string
+-}
+-
+-func subjectTokenHeaders(c *gophercloud.ServiceClient, subjectToken string) map[string]string {
+-	h := c.AuthenticatedHeaders()
+-	h["X-Subject-Token"] = subjectToken
+-	return h
+-}
+-
+-// Create authenticates and either generates a new token, or changes the Scope of an existing token.
+-func Create(c *gophercloud.ServiceClient, options gophercloud.AuthOptions, scope *Scope) CreateResult {
+-	type domainReq struct {
+-		ID   *string `json:"id,omitempty"`
+-		Name *string `json:"name,omitempty"`
 -	}
--	if width < 1 {
--		_, width, _ = pty.Getsize(os.Stdout)
+-
+-	type projectReq struct {
+-		Domain *domainReq `json:"domain,omitempty"`
+-		Name   *string    `json:"name,omitempty"`
+-		ID     *string    `json:"id,omitempty"`
 -	}
--	if width < 1 {
--		width = 80
+-
+-	type userReq struct {
+-		ID       *string    `json:"id,omitempty"`
+-		Name     *string    `json:"name,omitempty"`
+-		Password string     `json:"password"`
+-		Domain   *domainReq `json:"domain,omitempty"`
 -	}
 -
--	w := colwriter.NewWriter(os.Stdout, width, flag)
--	if len(args) > 0 {
--		for _, s := range args {
--			if f, err := os.Open(s); err == nil {
--				copyin(w, f)
--				f.Close()
--			} else {
--				log.Println(err)
+-	type passwordReq struct {
+-		User userReq `json:"user"`
+-	}
+-
+-	type tokenReq struct {
+-		ID string `json:"id"`
+-	}
+-
+-	type identityReq struct {
+-		Methods  []string     `json:"methods"`
+-		Password *passwordReq `json:"password,omitempty"`
+-		Token    *tokenReq    `json:"token,omitempty"`
+-	}
+-
+-	type scopeReq struct {
+-		Domain  *domainReq  `json:"domain,omitempty"`
+-		Project *projectReq `json:"project,omitempty"`
+-	}
+-
+-	type authReq struct {
+-		Identity identityReq `json:"identity"`
+-		Scope    *scopeReq   `json:"scope,omitempty"`
+-	}
+-
+-	type request struct {
+-		Auth authReq `json:"auth"`
+-	}
+-
+-	// Populate the request structure based on the provided arguments. Create and return an error
+-	// if insufficient or incompatible information is present.
+-	var req request
+-
+-	// Test first for unrecognized arguments.
+-	if options.APIKey != "" {
+-		return createErr(ErrAPIKeyProvided)
+-	}
+-	if options.TenantID != "" {
+-		return createErr(ErrTenantIDProvided)
+-	}
+-	if options.TenantName != "" {
+-		return createErr(ErrTenantNameProvided)
+-	}
+-
+-	if options.Password == "" {
+-		if c.TokenID != "" {
+-			// Because we aren't using password authentication, it's an error to also provide any of the user-based authentication
+-			// parameters.
+-			if options.Username != "" {
+-				return createErr(ErrUsernameWithToken)
 -			}
+-			if options.UserID != "" {
+-				return createErr(ErrUserIDWithToken)
+-			}
+-			if options.DomainID != "" {
+-				return createErr(ErrDomainIDWithToken)
+-			}
+-			if options.DomainName != "" {
+-				return createErr(ErrDomainNameWithToken)
+-			}
+-
+-			// Configure the request for Token authentication.
+-			req.Auth.Identity.Methods = []string{"token"}
+-			req.Auth.Identity.Token = &tokenReq{
+-				ID: c.TokenID,
+-			}
+-		} else {
+-			// If no password or token ID are available, authentication can't continue.
+-			return createErr(ErrMissingPassword)
 -		}
 -	} else {
--		copyin(w, os.Stdin)
+-		// Password authentication.
+-		req.Auth.Identity.Methods = []string{"password"}
+-
+-		// At least one of Username and UserID must be specified.
+-		if options.Username == "" && options.UserID == "" {
+-			return createErr(ErrUsernameOrUserID)
+-		}
+-
+-		if options.Username != "" {
+-			// If Username is provided, UserID may not be provided.
+-			if options.UserID != "" {
+-				return createErr(ErrUsernameOrUserID)
+-			}
+-
+-			// Either DomainID or DomainName must also be specified.
+-			if options.DomainID == "" && options.DomainName == "" {
+-				return createErr(ErrDomainIDOrDomainName)
+-			}
+-
+-			if options.DomainID != "" {
+-				if options.DomainName != "" {
+-					return createErr(ErrDomainIDOrDomainName)
+-				}
+-
+-				// Configure the request for Username and Password authentication with a DomainID.
+-				req.Auth.Identity.Password = &passwordReq{
+-					User: userReq{
+-						Name:     &options.Username,
+-						Password: options.Password,
+-						Domain:   &domainReq{ID: &options.DomainID},
+-					},
+-				}
+-			}
+-
+-			if options.DomainName != "" {
+-				// Configure the request for Username and Password authentication with a DomainName.
+-				req.Auth.Identity.Password = &passwordReq{
+-					User: userReq{
+-						Name:     &options.Username,
+-						Password: options.Password,
+-						Domain:   &domainReq{Name: &options.DomainName},
+-					},
+-				}
+-			}
+-		}
+-
+-		if options.UserID != "" {
+-			// If UserID is specified, neither DomainID nor DomainName may be.
+-			if options.DomainID != "" {
+-				return createErr(ErrDomainIDWithUserID)
+-			}
+-			if options.DomainName != "" {
+-				return createErr(ErrDomainNameWithUserID)
+-			}
+-
+-			// Configure the request for UserID and Password authentication.
+-			req.Auth.Identity.Password = &passwordReq{
+-				User: userReq{ID: &options.UserID, Password: options.Password},
+-			}
+-		}
+-	}
+-
+-	// Add a "scope" element if a Scope has been provided.
+-	if scope != nil {
+-		if scope.ProjectName != "" {
+-			// ProjectName provided: either DomainID or DomainName must also be supplied.
+-			// ProjectID may not be supplied.
+-			if scope.DomainID == "" && scope.DomainName == "" {
+-				return createErr(ErrScopeDomainIDOrDomainName)
+-			}
+-			if scope.ProjectID != "" {
+-				return createErr(ErrScopeProjectIDOrProjectName)
+-			}
+-
+-			if scope.DomainID != "" {
+-				// ProjectName + DomainID
+-				req.Auth.Scope = &scopeReq{
+-					Project: &projectReq{
+-						Name:   &scope.ProjectName,
+-						Domain: &domainReq{ID: &scope.DomainID},
+-					},
+-				}
+-			}
+-
+-			if scope.DomainName != "" {
+-				// ProjectName + DomainName
+-				req.Auth.Scope = &scopeReq{
+-					Project: &projectReq{
+-						Name:   &scope.ProjectName,
+-						Domain: &domainReq{Name: &scope.DomainName},
+-					},
+-				}
+-			}
+-		} else if scope.ProjectID != "" {
+-			// ProjectID provided. ProjectName, DomainID, and DomainName may not be provided.
+-			if scope.DomainID != "" {
+-				return createErr(ErrScopeProjectIDAlone)
+-			}
+-			if scope.DomainName != "" {
+-				return createErr(ErrScopeProjectIDAlone)
+-			}
+-
+-			// ProjectID
+-			req.Auth.Scope = &scopeReq{
+-				Project: &projectReq{ID: &scope.ProjectID},
+-			}
+-		} else if scope.DomainID != "" {
+-			// DomainID provided. ProjectID, ProjectName, and DomainName may not be provided.
+-			if scope.DomainName != "" {
+-				return createErr(ErrScopeDomainIDOrDomainName)
+-			}
+-
+-			// DomainID
+-			req.Auth.Scope = &scopeReq{
+-				Domain: &domainReq{ID: &scope.DomainID},
+-			}
+-		} else if scope.DomainName != "" {
+-			return createErr(ErrScopeDomainName)
+-		} else {
+-			return createErr(ErrScopeEmpty)
+-		}
+-	}
+-
+-	var result CreateResult
+-	var response *perigee.Response
+-	response, result.Err = perigee.Request("POST", tokenURL(c), perigee.Options{
+-		ReqBody: &req,
+-		Results: &result.Body,
+-		OkCodes: []int{201},
+-	})
+-	if result.Err != nil {
+-		return result
 -	}
+-	result.Header = response.HttpResponse.Header
+-	return result
 -}
 -
--func copyin(w *colwriter.Writer, r io.Reader) {
--	if _, err := io.Copy(w, r); err != nil {
--		log.Println(err)
+-// Get validates and retrieves information about another token.
+-func Get(c *gophercloud.ServiceClient, token string) GetResult {
+-	var result GetResult
+-	var response *perigee.Response
+-	response, result.Err = perigee.Request("GET", tokenURL(c), perigee.Options{
+-		MoreHeaders: subjectTokenHeaders(c, token),
+-		Results:     &result.Body,
+-		OkCodes:     []int{200, 203},
+-	})
+-	if result.Err != nil {
+-		return result
 -	}
--	if err := w.Flush(); err != nil {
--		log.Println(err)
+-	result.Header = response.HttpResponse.Header
+-	return result
+-}
+-
+-// Validate determines if a specified token is valid or not.
+-func Validate(c *gophercloud.ServiceClient, token string) (bool, error) {
+-	response, err := perigee.Request("HEAD", tokenURL(c), perigee.Options{
+-		MoreHeaders: subjectTokenHeaders(c, token),
+-		OkCodes:     []int{204, 404},
+-	})
+-	if err != nil {
+-		return false, err
 -	}
+-
+-	return response.StatusCode == 204, nil
+-}
+-
+-// Revoke immediately makes specified token invalid.
+-func Revoke(c *gophercloud.ServiceClient, token string) RevokeResult {
+-	var res RevokeResult
+-	_, res.Err = perigee.Request("DELETE", tokenURL(c), perigee.Options{
+-		MoreHeaders: subjectTokenHeaders(c, token),
+-		OkCodes:     []int{204},
+-	})
+-	return res
 -}
-diff --git a/Godeps/_workspace/src/github.com/kr/text/wrap.go b/Godeps/_workspace/src/github.com/kr/text/wrap.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/requests_test.go
 deleted file mode 100644
-index ca88565..0000000
---- a/Godeps/_workspace/src/github.com/kr/text/wrap.go
+index 2b26e4a..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/requests_test.go
 +++ /dev/null
-@@ -1,86 +0,0 @@
--package text
+@@ -1,514 +0,0 @@
+-package tokens
 -
 -import (
--	"bytes"
--	"math"
--)
+-	"fmt"
+-	"net/http"
+-	"testing"
+-	"time"
 -
--var (
--	nl = []byte{'\n'}
--	sp = []byte{' '}
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/testhelper"
 -)
 -
--const defaultPenalty = 1e5
+-// authTokenPost verifies that providing certain AuthOptions and Scope results in an expected JSON structure.
+-func authTokenPost(t *testing.T, options gophercloud.AuthOptions, scope *Scope, requestJSON string) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
 -
--// Wrap wraps s into a paragraph of lines of length lim, with minimal
--// raggedness.
--func Wrap(s string, lim int) string {
--	return string(WrapBytes([]byte(s), lim))
--}
+-	client := gophercloud.ServiceClient{
+-		ProviderClient: &gophercloud.ProviderClient{
+-			TokenID: "12345abcdef",
+-		},
+-		Endpoint: testhelper.Endpoint(),
+-	}
+-
+-	testhelper.Mux.HandleFunc("/auth/tokens", func(w http.ResponseWriter, r *http.Request) {
+-		testhelper.TestMethod(t, r, "POST")
+-		testhelper.TestHeader(t, r, "Content-Type", "application/json")
+-		testhelper.TestHeader(t, r, "Accept", "application/json")
+-		testhelper.TestJSONRequest(t, r, requestJSON)
 -
--// WrapBytes wraps b into a paragraph of lines of length lim, with minimal
--// raggedness.
--func WrapBytes(b []byte, lim int) []byte {
--	words := bytes.Split(bytes.Replace(bytes.TrimSpace(b), nl, sp, -1), sp)
--	var lines [][]byte
--	for _, line := range WrapWords(words, 1, lim, defaultPenalty) {
--		lines = append(lines, bytes.Join(line, sp))
+-		w.WriteHeader(http.StatusCreated)
+-		fmt.Fprintf(w, `{
+-			"token": {
+-				"expires_at": "2014-10-02T13:45:00.000000Z"
+-			}
+-		}`)
+-	})
+-
+-	_, err := Create(&client, options, scope).Extract()
+-	if err != nil {
+-		t.Errorf("Create returned an error: %v", err)
 -	}
--	return bytes.Join(lines, nl)
 -}
 -
--// WrapWords is the low-level line-breaking algorithm, useful if you need more
--// control over the details of the text wrapping process. For most uses, either
--// Wrap or WrapBytes will be sufficient and more convenient. 
--//
--// WrapWords splits a list of words into lines with minimal "raggedness",
--// treating each byte as one unit, accounting for spc units between adjacent
--// words on each line, and attempting to limit lines to lim units. Raggedness
--// is the total error over all lines, where error is the square of the
--// difference of the length of the line and lim. Too-long lines (which only
--// happen when a single word is longer than lim units) have pen penalty units
--// added to the error.
--func WrapWords(words [][]byte, spc, lim, pen int) [][][]byte {
--	n := len(words)
+-func authTokenPostErr(t *testing.T, options gophercloud.AuthOptions, scope *Scope, includeToken bool, expectedErr error) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
 -
--	length := make([][]int, n)
--	for i := 0; i < n; i++ {
--		length[i] = make([]int, n)
--		length[i][i] = len(words[i])
--		for j := i + 1; j < n; j++ {
--			length[i][j] = length[i][j-1] + spc + len(words[j])
--		}
+-	client := gophercloud.ServiceClient{
+-		ProviderClient: &gophercloud.ProviderClient{},
+-		Endpoint:       testhelper.Endpoint(),
+-	}
+-	if includeToken {
+-		client.TokenID = "abcdef123456"
 -	}
 -
--	nbrk := make([]int, n)
--	cost := make([]int, n)
--	for i := range cost {
--		cost[i] = math.MaxInt32
+-	_, err := Create(&client, options, scope).Extract()
+-	if err == nil {
+-		t.Errorf("Create did NOT return an error")
 -	}
--	for i := n - 1; i >= 0; i-- {
--		if length[i][n-1] <= lim {
--			cost[i] = 0
--			nbrk[i] = n
--		} else {
--			for j := i + 1; j < n; j++ {
--				d := lim - length[i][j-1]
--				c := d*d + cost[j]
--				if length[i][j-1] > lim {
--					c += pen // too-long lines get a worse penalty
+-	if err != expectedErr {
+-		t.Errorf("Create returned an unexpected error: wanted %v, got %v", expectedErr, err)
+-	}
+-}
+-
+-func TestCreateUserIDAndPassword(t *testing.T) {
+-	authTokenPost(t, gophercloud.AuthOptions{UserID: "me", Password: "squirrel!"}, nil, `
+-		{
+-			"auth": {
+-				"identity": {
+-					"methods": ["password"],
+-					"password": {
+-						"user": { "id": "me", "password": "squirrel!" }
+-					}
+-				}
+-			}
+-		}
+-	`)
+-}
+-
+-func TestCreateUsernameDomainIDPassword(t *testing.T) {
+-	authTokenPost(t, gophercloud.AuthOptions{Username: "fakey", Password: "notpassword", DomainID: "abc123"}, nil, `
+-		{
+-			"auth": {
+-				"identity": {
+-					"methods": ["password"],
+-					"password": {
+-						"user": {
+-							"domain": {
+-								"id": "abc123"
+-							},
+-							"name": "fakey",
+-							"password": "notpassword"
+-						}
+-					}
+-				}
+-			}
+-		}
+-	`)
+-}
+-
+-func TestCreateUsernameDomainNamePassword(t *testing.T) {
+-	authTokenPost(t, gophercloud.AuthOptions{Username: "frank", Password: "swordfish", DomainName: "spork.net"}, nil, `
+-		{
+-			"auth": {
+-				"identity": {
+-					"methods": ["password"],
+-					"password": {
+-						"user": {
+-							"domain": {
+-								"name": "spork.net"
+-							},
+-							"name": "frank",
+-							"password": "swordfish"
+-						}
+-					}
+-				}
+-			}
+-		}
+-	`)
+-}
+-
+-func TestCreateTokenID(t *testing.T) {
+-	authTokenPost(t, gophercloud.AuthOptions{}, nil, `
+-		{
+-			"auth": {
+-				"identity": {
+-					"methods": ["token"],
+-					"token": {
+-						"id": "12345abcdef"
+-					}
+-				}
+-			}
+-		}
+-	`)
+-}
+-
+-func TestCreateProjectIDScope(t *testing.T) {
+-	options := gophercloud.AuthOptions{UserID: "fenris", Password: "g0t0h311"}
+-	scope := &Scope{ProjectID: "123456"}
+-	authTokenPost(t, options, scope, `
+-		{
+-			"auth": {
+-				"identity": {
+-					"methods": ["password"],
+-					"password": {
+-						"user": {
+-							"id": "fenris",
+-							"password": "g0t0h311"
+-						}
+-					}
+-				},
+-				"scope": {
+-					"project": {
+-						"id": "123456"
+-					}
+-				}
+-			}
+-		}
+-	`)
+-}
+-
+-func TestCreateDomainIDScope(t *testing.T) {
+-	options := gophercloud.AuthOptions{UserID: "fenris", Password: "g0t0h311"}
+-	scope := &Scope{DomainID: "1000"}
+-	authTokenPost(t, options, scope, `
+-		{
+-			"auth": {
+-				"identity": {
+-					"methods": ["password"],
+-					"password": {
+-						"user": {
+-							"id": "fenris",
+-							"password": "g0t0h311"
+-						}
+-					}
+-				},
+-				"scope": {
+-					"domain": {
+-						"id": "1000"
+-					}
+-				}
+-			}
+-		}
+-	`)
+-}
+-
+-func TestCreateProjectNameAndDomainIDScope(t *testing.T) {
+-	options := gophercloud.AuthOptions{UserID: "fenris", Password: "g0t0h311"}
+-	scope := &Scope{ProjectName: "world-domination", DomainID: "1000"}
+-	authTokenPost(t, options, scope, `
+-		{
+-			"auth": {
+-				"identity": {
+-					"methods": ["password"],
+-					"password": {
+-						"user": {
+-							"id": "fenris",
+-							"password": "g0t0h311"
+-						}
+-					}
+-				},
+-				"scope": {
+-					"project": {
+-						"domain": {
+-							"id": "1000"
+-						},
+-						"name": "world-domination"
+-					}
 -				}
--				if c < cost[i] {
--					cost[i] = c
--					nbrk[i] = j
+-			}
+-		}
+-	`)
+-}
+-
+-func TestCreateProjectNameAndDomainNameScope(t *testing.T) {
+-	options := gophercloud.AuthOptions{UserID: "fenris", Password: "g0t0h311"}
+-	scope := &Scope{ProjectName: "world-domination", DomainName: "evil-plans"}
+-	authTokenPost(t, options, scope, `
+-		{
+-			"auth": {
+-				"identity": {
+-					"methods": ["password"],
+-					"password": {
+-						"user": {
+-							"id": "fenris",
+-							"password": "g0t0h311"
+-						}
+-					}
+-				},
+-				"scope": {
+-					"project": {
+-						"domain": {
+-							"name": "evil-plans"
+-						},
+-						"name": "world-domination"
+-					}
 -				}
 -			}
 -		}
+-	`)
+-}
+-
+-func TestCreateExtractsTokenFromResponse(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
+-
+-	client := gophercloud.ServiceClient{
+-		ProviderClient: &gophercloud.ProviderClient{},
+-		Endpoint:       testhelper.Endpoint(),
 -	}
 -
--	var lines [][][]byte
--	i := 0
--	for i < n {
--		lines = append(lines, words[i:nbrk[i]])
--		i = nbrk[i]
+-	testhelper.Mux.HandleFunc("/auth/tokens", func(w http.ResponseWriter, r *http.Request) {
+-		w.Header().Add("X-Subject-Token", "aaa111")
+-
+-		w.WriteHeader(http.StatusCreated)
+-		fmt.Fprintf(w, `{
+-			"token": {
+-				"expires_at": "2014-10-02T13:45:00.000000Z"
+-			}
+-		}`)
+-	})
+-
+-	options := gophercloud.AuthOptions{UserID: "me", Password: "shhh"}
+-	token, err := Create(&client, options, nil).Extract()
+-	if err != nil {
+-		t.Fatalf("Create returned an error: %v", err)
+-	}
+-
+-	if token.ID != "aaa111" {
+-		t.Errorf("Expected token to be aaa111, but was %s", token.ID)
 -	}
--	return lines
 -}
-diff --git a/Godeps/_workspace/src/github.com/kr/text/wrap_test.go b/Godeps/_workspace/src/github.com/kr/text/wrap_test.go
-deleted file mode 100644
-index 90f065c..0000000
---- a/Godeps/_workspace/src/github.com/kr/text/wrap_test.go
-+++ /dev/null
-@@ -1,44 +0,0 @@
--package text
 -
--import (
--	"bytes"
--	"testing"
--)
+-func TestCreateFailureEmptyAuth(t *testing.T) {
+-	authTokenPostErr(t, gophercloud.AuthOptions{}, nil, false, ErrMissingPassword)
+-}
+-
+-func TestCreateFailureAPIKey(t *testing.T) {
+-	authTokenPostErr(t, gophercloud.AuthOptions{APIKey: "something"}, nil, false, ErrAPIKeyProvided)
+-}
+-
+-func TestCreateFailureTenantID(t *testing.T) {
+-	authTokenPostErr(t, gophercloud.AuthOptions{TenantID: "something"}, nil, false, ErrTenantIDProvided)
+-}
 -
--var text = "The quick brown fox jumps over the lazy dog."
+-func TestCreateFailureTenantName(t *testing.T) {
+-	authTokenPostErr(t, gophercloud.AuthOptions{TenantName: "something"}, nil, false, ErrTenantNameProvided)
+-}
+-
+-func TestCreateFailureTokenIDUsername(t *testing.T) {
+-	authTokenPostErr(t, gophercloud.AuthOptions{Username: "something"}, nil, true, ErrUsernameWithToken)
+-}
+-
+-func TestCreateFailureTokenIDUserID(t *testing.T) {
+-	authTokenPostErr(t, gophercloud.AuthOptions{UserID: "something"}, nil, true, ErrUserIDWithToken)
+-}
+-
+-func TestCreateFailureTokenIDDomainID(t *testing.T) {
+-	authTokenPostErr(t, gophercloud.AuthOptions{DomainID: "something"}, nil, true, ErrDomainIDWithToken)
+-}
+-
+-func TestCreateFailureTokenIDDomainName(t *testing.T) {
+-	authTokenPostErr(t, gophercloud.AuthOptions{DomainName: "something"}, nil, true, ErrDomainNameWithToken)
+-}
+-
+-func TestCreateFailureMissingUser(t *testing.T) {
+-	options := gophercloud.AuthOptions{Password: "supersecure"}
+-	authTokenPostErr(t, options, nil, false, ErrUsernameOrUserID)
+-}
 -
--func TestWrap(t *testing.T) {
--	exp := [][]string{
--		{"The", "quick", "brown", "fox"},
--		{"jumps", "over", "the", "lazy", "dog."},
+-func TestCreateFailureBothUser(t *testing.T) {
+-	options := gophercloud.AuthOptions{
+-		Password: "supersecure",
+-		Username: "oops",
+-		UserID:   "redundancy",
 -	}
--	words := bytes.Split([]byte(text), sp)
--	got := WrapWords(words, 1, 24, defaultPenalty)
--	if len(exp) != len(got) {
--		t.Fail()
+-	authTokenPostErr(t, options, nil, false, ErrUsernameOrUserID)
+-}
+-
+-func TestCreateFailureMissingDomain(t *testing.T) {
+-	options := gophercloud.AuthOptions{
+-		Password: "supersecure",
+-		Username: "notuniqueenough",
 -	}
--	for i := range exp {
--		if len(exp[i]) != len(got[i]) {
--			t.Fail()
--		}
--		for j := range exp[i] {
--			if exp[i][j] != string(got[i][j]) {
--				t.Fatal(i, exp[i][j], got[i][j])
--			}
--		}
+-	authTokenPostErr(t, options, nil, false, ErrDomainIDOrDomainName)
+-}
+-
+-func TestCreateFailureBothDomain(t *testing.T) {
+-	options := gophercloud.AuthOptions{
+-		Password:   "supersecure",
+-		Username:   "someone",
+-		DomainID:   "hurf",
+-		DomainName: "durf",
 -	}
+-	authTokenPostErr(t, options, nil, false, ErrDomainIDOrDomainName)
 -}
 -
--func TestWrapNarrow(t *testing.T) {
--	exp := "The\nquick\nbrown\nfox\njumps\nover\nthe\nlazy\ndog."
--	if Wrap(text, 5) != exp {
--		t.Fail()
+-func TestCreateFailureUserIDDomainID(t *testing.T) {
+-	options := gophercloud.AuthOptions{
+-		UserID:   "100",
+-		Password: "stuff",
+-		DomainID: "oops",
 -	}
+-	authTokenPostErr(t, options, nil, false, ErrDomainIDWithUserID)
 -}
 -
--func TestWrapOneLine(t *testing.T) {
--	exp := "The quick brown fox jumps over the lazy dog."
--	if Wrap(text, 500) != exp {
--		t.Fail()
+-func TestCreateFailureUserIDDomainName(t *testing.T) {
+-	options := gophercloud.AuthOptions{
+-		UserID:     "100",
+-		Password:   "sssh",
+-		DomainName: "oops",
 -	}
+-	authTokenPostErr(t, options, nil, false, ErrDomainNameWithUserID)
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/attempt.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/attempt.go
-deleted file mode 100644
-index c0654f5..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/attempt.go
-+++ /dev/null
-@@ -1,74 +0,0 @@
--package aws
 -
--import (
--	"time"
--)
+-func TestCreateFailureScopeProjectNameAlone(t *testing.T) {
+-	options := gophercloud.AuthOptions{UserID: "myself", Password: "swordfish"}
+-	scope := &Scope{ProjectName: "notenough"}
+-	authTokenPostErr(t, options, scope, false, ErrScopeDomainIDOrDomainName)
+-}
 -
--// AttemptStrategy represents a strategy for waiting for an action
--// to complete successfully. This is an internal type used by the
--// implementation of other goamz packages.
--type AttemptStrategy struct {
--	Total time.Duration // total duration of attempt.
--	Delay time.Duration // interval between each try in the burst.
--	Min   int           // minimum number of retries; overrides Total
+-func TestCreateFailureScopeProjectNameAndID(t *testing.T) {
+-	options := gophercloud.AuthOptions{UserID: "myself", Password: "swordfish"}
+-	scope := &Scope{ProjectName: "whoops", ProjectID: "toomuch", DomainID: "1234"}
+-	authTokenPostErr(t, options, scope, false, ErrScopeProjectIDOrProjectName)
 -}
 -
--type Attempt struct {
--	strategy AttemptStrategy
--	last     time.Time
--	end      time.Time
--	force    bool
--	count    int
+-func TestCreateFailureScopeProjectIDAndDomainID(t *testing.T) {
+-	options := gophercloud.AuthOptions{UserID: "myself", Password: "swordfish"}
+-	scope := &Scope{ProjectID: "toomuch", DomainID: "notneeded"}
+-	authTokenPostErr(t, options, scope, false, ErrScopeProjectIDAlone)
 -}
 -
--// Start begins a new sequence of attempts for the given strategy.
--func (s AttemptStrategy) Start() *Attempt {
--	now := time.Now()
--	return &Attempt{
--		strategy: s,
--		last:     now,
--		end:      now.Add(s.Total),
--		force:    true,
--	}
+-func TestCreateFailureScopeProjectIDAndDomainNAme(t *testing.T) {
+-	options := gophercloud.AuthOptions{UserID: "myself", Password: "swordfish"}
+-	scope := &Scope{ProjectID: "toomuch", DomainName: "notneeded"}
+-	authTokenPostErr(t, options, scope, false, ErrScopeProjectIDAlone)
 -}
 -
--// Next waits until it is time to perform the next attempt or returns
--// false if it is time to stop trying.
--func (a *Attempt) Next() bool {
--	now := time.Now()
--	sleep := a.nextSleep(now)
--	if !a.force && !now.Add(sleep).Before(a.end) && a.strategy.Min <= a.count {
--		return false
+-func TestCreateFailureScopeDomainIDAndDomainName(t *testing.T) {
+-	options := gophercloud.AuthOptions{UserID: "myself", Password: "swordfish"}
+-	scope := &Scope{DomainID: "toomuch", DomainName: "notneeded"}
+-	authTokenPostErr(t, options, scope, false, ErrScopeDomainIDOrDomainName)
+-}
+-
+-func TestCreateFailureScopeDomainNameAlone(t *testing.T) {
+-	options := gophercloud.AuthOptions{UserID: "myself", Password: "swordfish"}
+-	scope := &Scope{DomainName: "notenough"}
+-	authTokenPostErr(t, options, scope, false, ErrScopeDomainName)
+-}
+-
+-func TestCreateFailureEmptyScope(t *testing.T) {
+-	options := gophercloud.AuthOptions{UserID: "myself", Password: "swordfish"}
+-	scope := &Scope{}
+-	authTokenPostErr(t, options, scope, false, ErrScopeEmpty)
+-}
+-
+-func TestGetRequest(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
+-
+-	client := gophercloud.ServiceClient{
+-		ProviderClient: &gophercloud.ProviderClient{
+-			TokenID: "12345abcdef",
+-		},
+-		Endpoint: testhelper.Endpoint(),
 -	}
--	a.force = false
--	if sleep > 0 && a.count > 0 {
--		time.Sleep(sleep)
--		now = time.Now()
+-
+-	testhelper.Mux.HandleFunc("/auth/tokens", func(w http.ResponseWriter, r *http.Request) {
+-		testhelper.TestMethod(t, r, "GET")
+-		testhelper.TestHeader(t, r, "Content-Type", "")
+-		testhelper.TestHeader(t, r, "Accept", "application/json")
+-		testhelper.TestHeader(t, r, "X-Auth-Token", "12345abcdef")
+-		testhelper.TestHeader(t, r, "X-Subject-Token", "abcdef12345")
+-
+-		w.WriteHeader(http.StatusOK)
+-		fmt.Fprintf(w, `
+-			{ "token": { "expires_at": "2014-08-29T13:10:01.000000Z" } }
+-		`)
+-	})
+-
+-	token, err := Get(&client, "abcdef12345").Extract()
+-	if err != nil {
+-		t.Errorf("Info returned an error: %v", err)
+-	}
+-
+-	expected, _ := time.Parse(time.UnixDate, "Fri Aug 29 13:10:01 UTC 2014")
+-	if token.ExpiresAt != expected {
+-		t.Errorf("Expected expiration time %s, but was %s", expected.Format(time.UnixDate), token.ExpiresAt.Format(time.UnixDate))
 -	}
--	a.count++
--	a.last = now
--	return true
 -}
 -
--func (a *Attempt) nextSleep(now time.Time) time.Duration {
--	sleep := a.strategy.Delay - now.Sub(a.last)
--	if sleep < 0 {
--		return 0
+-func prepareAuthTokenHandler(t *testing.T, expectedMethod string, status int) gophercloud.ServiceClient {
+-	client := gophercloud.ServiceClient{
+-		ProviderClient: &gophercloud.ProviderClient{
+-			TokenID: "12345abcdef",
+-		},
+-		Endpoint: testhelper.Endpoint(),
 -	}
--	return sleep
+-
+-	testhelper.Mux.HandleFunc("/auth/tokens", func(w http.ResponseWriter, r *http.Request) {
+-		testhelper.TestMethod(t, r, expectedMethod)
+-		testhelper.TestHeader(t, r, "Content-Type", "")
+-		testhelper.TestHeader(t, r, "Accept", "application/json")
+-		testhelper.TestHeader(t, r, "X-Auth-Token", "12345abcdef")
+-		testhelper.TestHeader(t, r, "X-Subject-Token", "abcdef12345")
+-
+-		w.WriteHeader(status)
+-	})
+-
+-	return client
 -}
 -
--// HasNext returns whether another attempt will be made if the current
--// one fails. If it returns true, the following call to Next is
--// guaranteed to return true.
--func (a *Attempt) HasNext() bool {
--	if a.force || a.strategy.Min > a.count {
--		return true
+-func TestValidateRequestSuccessful(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
+-	client := prepareAuthTokenHandler(t, "HEAD", http.StatusNoContent)
+-
+-	ok, err := Validate(&client, "abcdef12345")
+-	if err != nil {
+-		t.Errorf("Unexpected error from Validate: %v", err)
 -	}
--	now := time.Now()
--	if now.Add(a.nextSleep(now)).Before(a.end) {
--		a.force = true
--		return true
+-
+-	if !ok {
+-		t.Errorf("Validate returned false for a valid token")
 -	}
--	return false
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/attempt_test.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/attempt_test.go
-deleted file mode 100644
-index 1fda5bf..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/attempt_test.go
-+++ /dev/null
-@@ -1,57 +0,0 @@
--package aws_test
 -
--import (
--	"github.com/mitchellh/goamz/aws"
--	. "github.com/motain/gocheck"
--	"time"
--)
+-func TestValidateRequestFailure(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
+-	client := prepareAuthTokenHandler(t, "HEAD", http.StatusNotFound)
 -
--func (S) TestAttemptTiming(c *C) {
--	testAttempt := aws.AttemptStrategy{
--		Total: 0.25e9,
--		Delay: 0.1e9,
+-	ok, err := Validate(&client, "abcdef12345")
+-	if err != nil {
+-		t.Errorf("Unexpected error from Validate: %v", err)
 -	}
--	want := []time.Duration{0, 0.1e9, 0.2e9, 0.2e9}
--	got := make([]time.Duration, 0, len(want)) // avoid allocation when testing timing
--	t0 := time.Now()
--	for a := testAttempt.Start(); a.Next(); {
--		got = append(got, time.Now().Sub(t0))
+-
+-	if ok {
+-		t.Errorf("Validate returned true for an invalid token")
 -	}
--	got = append(got, time.Now().Sub(t0))
--	c.Assert(got, HasLen, len(want))
--	const margin = 0.01e9
--	for i, got := range want {
--		lo := want[i] - margin
--		hi := want[i] + margin
--		if got < lo || got > hi {
--			c.Errorf("attempt %d want %g got %g", i, want[i].Seconds(), got.Seconds())
--		}
+-}
+-
+-func TestValidateRequestError(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
+-	client := prepareAuthTokenHandler(t, "HEAD", http.StatusUnauthorized)
+-
+-	_, err := Validate(&client, "abcdef12345")
+-	if err == nil {
+-		t.Errorf("Missing expected error from Validate")
 -	}
 -}
 -
--func (S) TestAttemptNextHasNext(c *C) {
--	a := aws.AttemptStrategy{}.Start()
--	c.Assert(a.Next(), Equals, true)
--	c.Assert(a.Next(), Equals, false)
+-func TestRevokeRequestSuccessful(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
+-	client := prepareAuthTokenHandler(t, "DELETE", http.StatusNoContent)
 -
--	a = aws.AttemptStrategy{}.Start()
--	c.Assert(a.Next(), Equals, true)
--	c.Assert(a.HasNext(), Equals, false)
--	c.Assert(a.Next(), Equals, false)
+-	res := Revoke(&client, "abcdef12345")
+-	testhelper.AssertNoErr(t, res.Err)
+-}
 -
--	a = aws.AttemptStrategy{Total: 2e8}.Start()
--	c.Assert(a.Next(), Equals, true)
--	c.Assert(a.HasNext(), Equals, true)
--	time.Sleep(2e8)
--	c.Assert(a.HasNext(), Equals, true)
--	c.Assert(a.Next(), Equals, true)
--	c.Assert(a.Next(), Equals, false)
+-func TestRevokeRequestError(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
+-	client := prepareAuthTokenHandler(t, "DELETE", http.StatusNotFound)
 -
--	a = aws.AttemptStrategy{Total: 1e8, Min: 2}.Start()
--	time.Sleep(1e8)
--	c.Assert(a.Next(), Equals, true)
--	c.Assert(a.HasNext(), Equals, true)
--	c.Assert(a.Next(), Equals, true)
--	c.Assert(a.HasNext(), Equals, false)
--	c.Assert(a.Next(), Equals, false)
+-	res := Revoke(&client, "abcdef12345")
+-	if res.Err == nil {
+-		t.Errorf("Missing expected error from Revoke")
+-	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/aws.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/aws.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/results.go
 deleted file mode 100644
-index c304d55..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/aws.go
+index d1fff4c..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/results.go
 +++ /dev/null
-@@ -1,423 +0,0 @@
--//
--// goamz - Go packages to interact with the Amazon Web Services.
--//
--//   https://wiki.ubuntu.com/goamz
--//
--// Copyright (c) 2011 Canonical Ltd.
--//
--// Written by Gustavo Niemeyer <gustavo.niemeyer at canonical.com>
--//
--package aws
+@@ -1,73 +0,0 @@
+-package tokens
 -
 -import (
--	"encoding/json"
--	"errors"
--	"fmt"
--	"github.com/vaughan0/go-ini"
--	"io/ioutil"
--	"os"
+-	"time"
+-
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
 -)
 -
--// Region defines the URLs where AWS services may be accessed.
--//
--// See http://goo.gl/d8BP1 for more details.
--type Region struct {
--	Name                 string // the canonical name of this region.
--	EC2Endpoint          string
--	S3Endpoint           string
--	S3BucketEndpoint     string // Not needed by AWS S3. Use ${bucket} for bucket name.
--	S3LocationConstraint bool   // true if this region requires a LocationConstraint declaration.
--	S3LowercaseBucket    bool   // true if the region requires bucket names to be lower case.
--	SDBEndpoint          string
--	SNSEndpoint          string
--	SQSEndpoint          string
--	IAMEndpoint          string
--	ELBEndpoint          string
--	AutoScalingEndpoint  string
--	RdsEndpoint          string
--	Route53Endpoint      string
+-// commonResult is the deferred result of a Create or a Get call.
+-type commonResult struct {
+-	gophercloud.Result
 -}
 -
--var USGovWest = Region{
--	"us-gov-west-1",
--	"https://ec2.us-gov-west-1.amazonaws.com",
--	"https://s3-fips-us-gov-west-1.amazonaws.com",
--	"",
--	true,
--	true,
--	"",
--	"https://sns.us-gov-west-1.amazonaws.com",
--	"https://sqs.us-gov-west-1.amazonaws.com",
--	"https://iam.us-gov.amazonaws.com",
--	"https://elasticloadbalancing.us-gov-west-1.amazonaws.com",
--	"https://autoscaling.us-gov-west-1.amazonaws.com",
--	"https://rds.us-gov-west-1.amazonaws.com",
--	"https://route53.amazonaws.com",
--}
+-// Extract interprets a commonResult as a Token.
+-func (r commonResult) Extract() (*Token, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
+-	}
 -
--var USEast = Region{
--	"us-east-1",
--	"https://ec2.us-east-1.amazonaws.com",
--	"https://s3.amazonaws.com",
--	"",
--	false,
--	false,
--	"https://sdb.amazonaws.com",
--	"https://sns.us-east-1.amazonaws.com",
--	"https://sqs.us-east-1.amazonaws.com",
--	"https://iam.amazonaws.com",
--	"https://elasticloadbalancing.us-east-1.amazonaws.com",
--	"https://autoscaling.us-east-1.amazonaws.com",
--	"https://rds.us-east-1.amazonaws.com",
--	"https://route53.amazonaws.com",
--}
+-	var response struct {
+-		Token struct {
+-			ExpiresAt string `mapstructure:"expires_at"`
+-		} `mapstructure:"token"`
+-	}
 -
--var USWest = Region{
--	"us-west-1",
--	"https://ec2.us-west-1.amazonaws.com",
--	"https://s3-us-west-1.amazonaws.com",
--	"",
--	true,
--	true,
--	"https://sdb.us-west-1.amazonaws.com",
--	"https://sns.us-west-1.amazonaws.com",
--	"https://sqs.us-west-1.amazonaws.com",
--	"https://iam.amazonaws.com",
--	"https://elasticloadbalancing.us-west-1.amazonaws.com",
--	"https://autoscaling.us-west-1.amazonaws.com",
--	"https://rds.us-west-1.amazonaws.com",
--	"https://route53.amazonaws.com",
+-	var token Token
+-
+-	// Parse the token itself from the stored headers.
+-	token.ID = r.Header.Get("X-Subject-Token")
+-
+-	err := mapstructure.Decode(r.Body, &response)
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	// Attempt to parse the timestamp.
+-	token.ExpiresAt, err = time.Parse(gophercloud.RFC3339Milli, response.Token.ExpiresAt)
+-
+-	return &token, err
 -}
 -
--var USWest2 = Region{
--	"us-west-2",
--	"https://ec2.us-west-2.amazonaws.com",
--	"https://s3-us-west-2.amazonaws.com",
--	"",
--	true,
--	true,
--	"https://sdb.us-west-2.amazonaws.com",
--	"https://sns.us-west-2.amazonaws.com",
--	"https://sqs.us-west-2.amazonaws.com",
--	"https://iam.amazonaws.com",
--	"https://elasticloadbalancing.us-west-2.amazonaws.com",
--	"https://autoscaling.us-west-2.amazonaws.com",
--	"https://rds.us-west-2.amazonaws.com",
--	"https://route53.amazonaws.com",
+-// CreateResult is the deferred response from a Create call.
+-type CreateResult struct {
+-	commonResult
 -}
 -
--var EUWest = Region{
--	"eu-west-1",
--	"https://ec2.eu-west-1.amazonaws.com",
--	"https://s3-eu-west-1.amazonaws.com",
--	"",
--	true,
--	true,
--	"https://sdb.eu-west-1.amazonaws.com",
--	"https://sns.eu-west-1.amazonaws.com",
--	"https://sqs.eu-west-1.amazonaws.com",
--	"https://iam.amazonaws.com",
--	"https://elasticloadbalancing.eu-west-1.amazonaws.com",
--	"https://autoscaling.eu-west-1.amazonaws.com",
--	"https://rds.eu-west-1.amazonaws.com",
--	"https://route53.amazonaws.com",
+-// createErr quickly creates a CreateResult that reports an error.
+-func createErr(err error) CreateResult {
+-	return CreateResult{
+-		commonResult: commonResult{Result: gophercloud.Result{Err: err}},
+-	}
 -}
 -
--var APSoutheast = Region{
--	"ap-southeast-1",
--	"https://ec2.ap-southeast-1.amazonaws.com",
--	"https://s3-ap-southeast-1.amazonaws.com",
--	"",
--	true,
--	true,
--	"https://sdb.ap-southeast-1.amazonaws.com",
--	"https://sns.ap-southeast-1.amazonaws.com",
--	"https://sqs.ap-southeast-1.amazonaws.com",
--	"https://iam.amazonaws.com",
--	"https://elasticloadbalancing.ap-southeast-1.amazonaws.com",
--	"https://autoscaling.ap-southeast-1.amazonaws.com",
--	"https://rds.ap-southeast-1.amazonaws.com",
--	"https://route53.amazonaws.com",
+-// GetResult is the deferred response from a Get call.
+-type GetResult struct {
+-	commonResult
 -}
 -
--var APSoutheast2 = Region{
--	"ap-southeast-2",
--	"https://ec2.ap-southeast-2.amazonaws.com",
--	"https://s3-ap-southeast-2.amazonaws.com",
--	"",
--	true,
--	true,
--	"https://sdb.ap-southeast-2.amazonaws.com",
--	"https://sns.ap-southeast-2.amazonaws.com",
--	"https://sqs.ap-southeast-2.amazonaws.com",
--	"https://iam.amazonaws.com",
--	"https://elasticloadbalancing.ap-southeast-2.amazonaws.com",
--	"https://autoscaling.ap-southeast-2.amazonaws.com",
--	"https://rds.ap-southeast-2.amazonaws.com",
--	"https://route53.amazonaws.com",
+-// RevokeResult is the deferred response from a Revoke call.
+-type RevokeResult struct {
+-	commonResult
 -}
 -
--var APNortheast = Region{
--	"ap-northeast-1",
--	"https://ec2.ap-northeast-1.amazonaws.com",
--	"https://s3-ap-northeast-1.amazonaws.com",
--	"",
--	true,
--	true,
--	"https://sdb.ap-northeast-1.amazonaws.com",
--	"https://sns.ap-northeast-1.amazonaws.com",
--	"https://sqs.ap-northeast-1.amazonaws.com",
--	"https://iam.amazonaws.com",
--	"https://elasticloadbalancing.ap-northeast-1.amazonaws.com",
--	"https://autoscaling.ap-northeast-1.amazonaws.com",
--	"https://rds.ap-northeast-1.amazonaws.com",
--	"https://route53.amazonaws.com",
+-// Token is a string that grants a user access to a controlled set of services in an OpenStack provider.
+-// Each Token is valid for a set length of time.
+-type Token struct {
+-	// ID is the issued token.
+-	ID string
+-
+-	// ExpiresAt is the timestamp at which this token will no longer be accepted.
+-	ExpiresAt time.Time
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/urls.go
+deleted file mode 100644
+index 360b60a..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/urls.go
++++ /dev/null
+@@ -1,7 +0,0 @@
+-package tokens
 -
--var SAEast = Region{
--	"sa-east-1",
--	"https://ec2.sa-east-1.amazonaws.com",
--	"https://s3-sa-east-1.amazonaws.com",
--	"",
--	true,
--	true,
--	"https://sdb.sa-east-1.amazonaws.com",
--	"https://sns.sa-east-1.amazonaws.com",
--	"https://sqs.sa-east-1.amazonaws.com",
--	"https://iam.amazonaws.com",
--	"https://elasticloadbalancing.sa-east-1.amazonaws.com",
--	"https://autoscaling.sa-east-1.amazonaws.com",
--	"https://rds.sa-east-1.amazonaws.com",
--	"https://route53.amazonaws.com",
+-import "github.com/rackspace/gophercloud"
+-
+-func tokenURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL("auth", "tokens")
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/urls_test.go
+deleted file mode 100644
+index 549c398..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/identity/v3/tokens/urls_test.go
++++ /dev/null
+@@ -1,21 +0,0 @@
+-package tokens
 -
--var CNNorth = Region{
--	"cn-north-1",
--	"https://ec2.cn-north-1.amazonaws.com.cn",
--	"https://s3.cn-north-1.amazonaws.com.cn",
--	"",
--	true,
--	true,
--	"",
--	"https://sns.cn-north-1.amazonaws.com.cn",
--	"https://sqs.cn-north-1.amazonaws.com.cn",
--	"https://iam.cn-north-1.amazonaws.com.cn",
--	"https://elasticloadbalancing.cn-north-1.amazonaws.com.cn",
--	"https://autoscaling.cn-north-1.amazonaws.com.cn",
--	"https://rds.cn-north-1.amazonaws.com.cn",
--	"https://route53.amazonaws.com",
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestTokenURL(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
+-
+-	client := gophercloud.ServiceClient{Endpoint: testhelper.Endpoint()}
+-
+-	expected := testhelper.Endpoint() + "auth/tokens"
+-	actual := tokenURL(&client)
+-	if actual != expected {
+-		t.Errorf("Expected URL %s, but was %s", expected, actual)
+-	}
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/doc.go
+deleted file mode 100644
+index 0208ee2..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/doc.go
++++ /dev/null
+@@ -1,4 +0,0 @@
+-// Package apiversions provides information and interaction with the different
+-// API versions for the OpenStack Neutron service. This functionality is not
+-// restricted to this particular version.
+-package apiversions
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/errors.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/errors.go
+deleted file mode 100644
+index 76bdb14..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/errors.go
++++ /dev/null
+@@ -1 +0,0 @@
+-package apiversions
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/requests.go
+deleted file mode 100644
+index 9fb6de1..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/requests.go
++++ /dev/null
+@@ -1,21 +0,0 @@
+-package apiversions
 -
--var Regions = map[string]Region{
--	APNortheast.Name:  APNortheast,
--	APSoutheast.Name:  APSoutheast,
--	APSoutheast2.Name: APSoutheast2,
--	EUWest.Name:       EUWest,
--	USEast.Name:       USEast,
--	USWest.Name:       USWest,
--	USWest2.Name:      USWest2,
--	SAEast.Name:       SAEast,
--	USGovWest.Name:    USGovWest,
--	CNNorth.Name:      CNNorth,
+-import (
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
+-
+-// ListVersions lists all the Neutron API versions available to end-users
+-func ListVersions(c *gophercloud.ServiceClient) pagination.Pager {
+-	return pagination.NewPager(c, apiVersionsURL(c), func(r pagination.PageResult) pagination.Page {
+-		return APIVersionPage{pagination.SinglePageBase(r)}
+-	})
 -}
 -
--type Auth struct {
--	AccessKey, SecretKey, Token string
+-// ListVersionResources lists all of the different API resources for a particular
+-// API versions. Typical resources for Neutron might be: networks, subnets, etc.
+-func ListVersionResources(c *gophercloud.ServiceClient, v string) pagination.Pager {
+-	return pagination.NewPager(c, apiInfoURL(c, v), func(r pagination.PageResult) pagination.Page {
+-		return APIVersionResourcePage{pagination.SinglePageBase(r)}
+-	})
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/requests_test.go
+deleted file mode 100644
+index d35af9f..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/requests_test.go
++++ /dev/null
+@@ -1,182 +0,0 @@
+-package apiversions
 -
--var unreserved = make([]bool, 128)
--var hex = "0123456789ABCDEF"
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--func init() {
--	// RFC3986
--	u := "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz01234567890-_.~"
--	for _, c := range u {
--		unreserved[c] = true
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
+-
+-func TestListVersions(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "versions": [
+-        {
+-            "status": "CURRENT",
+-            "id": "v2.0",
+-            "links": [
+-                {
+-                    "href": "http://23.253.228.211:9696/v2.0",
+-                    "rel": "self"
+-                }
+-            ]
+-        }
+-    ]
+-}`)
+-	})
+-
+-	count := 0
+-
+-	ListVersions(fake.ServiceClient()).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractAPIVersions(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract API versions: %v", err)
+-			return false, err
+-		}
+-
+-		expected := []APIVersion{
+-			APIVersion{
+-				Status: "CURRENT",
+-				ID:     "v2.0",
+-			},
+-		}
+-
+-		th.AssertDeepEquals(t, expected, actual)
+-
+-		return true, nil
+-	})
+-
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
 -	}
 -}
 -
--type credentials struct {
--	Code            string
--	LastUpdated     string
--	Type            string
--	AccessKeyId     string
--	SecretAccessKey string
--	Token           string
--	Expiration      string
+-func TestNonJSONCannotBeExtractedIntoAPIVersions(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
+-		w.WriteHeader(http.StatusOK)
+-	})
+-
+-	ListVersions(fake.ServiceClient()).EachPage(func(page pagination.Page) (bool, error) {
+-		if _, err := ExtractAPIVersions(page); err == nil {
+-			t.Fatalf("Expected error, got nil")
+-		}
+-		return true, nil
+-	})
 -}
 -
--// GetMetaData retrieves instance metadata about the current machine.
--//
--// See http://docs.aws.amazon.com/AWSEC2/latest/UserGuide/AESDG-chapter-instancedata.html for more details.
--func GetMetaData(path string) (contents []byte, err error) {
--	url := "http://169.254.169.254/latest/meta-data/" + path
+-func TestAPIInfo(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	resp, err := RetryingClient.Get(url)
--	if err != nil {
--		return
--	}
--	defer resp.Body.Close()
+-	th.Mux.HandleFunc("/v2.0/", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--	if resp.StatusCode != 200 {
--		err = fmt.Errorf("Code %d returned for url %s", resp.StatusCode, url)
--		return
--	}
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--	body, err := ioutil.ReadAll(resp.Body)
--	if err != nil {
--		return
--	}
--	return []byte(body), err
+-		fmt.Fprintf(w, `
+-{
+-    "resources": [
+-        {
+-            "links": [
+-                {
+-                    "href": "http://23.253.228.211:9696/v2.0/subnets",
+-                    "rel": "self"
+-                }
+-            ],
+-            "name": "subnet",
+-            "collection": "subnets"
+-        },
+-        {
+-            "links": [
+-                {
+-                    "href": "http://23.253.228.211:9696/v2.0/networks",
+-                    "rel": "self"
+-                }
+-            ],
+-            "name": "network",
+-            "collection": "networks"
+-        },
+-        {
+-            "links": [
+-                {
+-                    "href": "http://23.253.228.211:9696/v2.0/ports",
+-                    "rel": "self"
+-                }
+-            ],
+-            "name": "port",
+-            "collection": "ports"
+-        }
+-    ]
 -}
+-			`)
+-	})
 -
--func getInstanceCredentials() (cred credentials, err error) {
--	credentialPath := "iam/security-credentials/"
+-	count := 0
 -
--	// Get the instance role
--	role, err := GetMetaData(credentialPath)
--	if err != nil {
--		return
--	}
+-	ListVersionResources(fake.ServiceClient(), "v2.0").EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractVersionResources(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract version resources: %v", err)
+-			return false, err
+-		}
 -
--	// Get the instance role credentials
--	credentialJSON, err := GetMetaData(credentialPath + string(role))
--	if err != nil {
--		return
--	}
+-		expected := []APIVersionResource{
+-			APIVersionResource{
+-				Name:       "subnet",
+-				Collection: "subnets",
+-			},
+-			APIVersionResource{
+-				Name:       "network",
+-				Collection: "networks",
+-			},
+-			APIVersionResource{
+-				Name:       "port",
+-				Collection: "ports",
+-			},
+-		}
 -
--	err = json.Unmarshal([]byte(credentialJSON), &cred)
--	return
--}
+-		th.AssertDeepEquals(t, expected, actual)
+-
+-		return true, nil
+-	})
 -
--// GetAuth creates an Auth based on either passed in credentials,
--// environment information or instance based role credentials.
--func GetAuth(accessKey string, secretKey string) (auth Auth, err error) {
--	// First try passed in credentials
--	if accessKey != "" && secretKey != "" {
--		return Auth{accessKey, secretKey, ""}, nil
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
 -	}
+-}
 -
--	// Next try to get auth from the environment
--	auth, err = SharedAuth()
--	if err == nil {
--		// Found auth, return
--		return
--	}
+-func TestNonJSONCannotBeExtractedIntoAPIVersionResources(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	// Next try to get auth from the environment
--	auth, err = EnvAuth()
--	if err == nil {
--		// Found auth, return
--		return
--	}
+-	th.Mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
+-		w.WriteHeader(http.StatusOK)
+-	})
 -
--	// Next try getting auth from the instance role
--	cred, err := getInstanceCredentials()
--	if err == nil {
--		// Found auth, return
--		auth.AccessKey = cred.AccessKeyId
--		auth.SecretKey = cred.SecretAccessKey
--		auth.Token = cred.Token
--		return
--	}
--	err = errors.New("No valid AWS authentication found")
--	return
+-	ListVersionResources(fake.ServiceClient(), "v2.0").EachPage(func(page pagination.Page) (bool, error) {
+-		if _, err := ExtractVersionResources(page); err == nil {
+-			t.Fatalf("Expected error, got nil")
+-		}
+-		return true, nil
+-	})
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/results.go
+deleted file mode 100644
+index 9715934..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/results.go
++++ /dev/null
+@@ -1,77 +0,0 @@
+-package apiversions
 -
--// SharedAuth creates an Auth based on shared credentials stored in
--// $HOME/.aws/credentials. The AWS_PROFILE environment variables is used to
--// select the profile.
--func SharedAuth() (auth Auth, err error) {
--	var profileName = os.Getenv("AWS_PROFILE")
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	if profileName == "" {
--		profileName = "default"
--	}
+-// APIVersion represents an API version for Neutron. It contains the status of
+-// the API, and its unique ID.
+-type APIVersion struct {
+-	Status string `mapstructure:"status" json:"status"`
+-	ID     string `mapstructure:"id" json:"id"`
+-}
 -
--	var homeDir = os.Getenv("HOME")
--	if homeDir == "" {
--		err = errors.New("Could not get HOME")
--		return
--	}
+-// APIVersionPage is the page returned by a pager when traversing over a
+-// collection of API versions.
+-type APIVersionPage struct {
+-	pagination.SinglePageBase
+-}
 -
--	var credentialsFile = homeDir + "/.aws/credentials"
--	file, err := ini.LoadFile(credentialsFile)
+-// IsEmpty checks whether an APIVersionPage struct is empty.
+-func (r APIVersionPage) IsEmpty() (bool, error) {
+-	is, err := ExtractAPIVersions(r)
 -	if err != nil {
--		err = errors.New("Couldn't parse AWS credentials file")
--		return
+-		return true, err
 -	}
+-	return len(is) == 0, nil
+-}
 -
--	var profile = file[profileName]
--	if profile == nil {
--		err = errors.New("Couldn't find profile in AWS credentials file")
--		return
+-// ExtractAPIVersions takes a collection page, extracts all of the elements,
+-// and returns them a slice of APIVersion structs. It is effectively a cast.
+-func ExtractAPIVersions(page pagination.Page) ([]APIVersion, error) {
+-	var resp struct {
+-		Versions []APIVersion `mapstructure:"versions"`
 -	}
 -
--	auth.AccessKey = profile["aws_access_key_id"]
--	auth.SecretKey = profile["aws_secret_access_key"]
+-	err := mapstructure.Decode(page.(APIVersionPage).Body, &resp)
 -
--	if auth.AccessKey == "" {
--		err = errors.New("AWS_ACCESS_KEY_ID not found in environment in credentials file")
--	}
--	if auth.SecretKey == "" {
--		err = errors.New("AWS_SECRET_ACCESS_KEY not found in credentials file")
--	}
--	return
+-	return resp.Versions, err
 -}
 -
--// EnvAuth creates an Auth based on environment information.
--// The AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment
--// For accounts that require a security token, it is read from AWS_SECURITY_TOKEN
--// variables are used.
--func EnvAuth() (auth Auth, err error) {
--	auth.AccessKey = os.Getenv("AWS_ACCESS_KEY_ID")
--	if auth.AccessKey == "" {
--		auth.AccessKey = os.Getenv("AWS_ACCESS_KEY")
--	}
--
--	auth.SecretKey = os.Getenv("AWS_SECRET_ACCESS_KEY")
--	if auth.SecretKey == "" {
--		auth.SecretKey = os.Getenv("AWS_SECRET_KEY")
--	}
+-// APIVersionResource represents a generic API resource. It contains the name
+-// of the resource and its plural collection name.
+-type APIVersionResource struct {
+-	Name       string `mapstructure:"name" json:"name"`
+-	Collection string `mapstructure:"collection" json:"collection"`
+-}
 -
--	auth.Token = os.Getenv("AWS_SECURITY_TOKEN")
+-// APIVersionResourcePage is a concrete type which embeds the common
+-// SinglePageBase struct, and is used when traversing API versions collections.
+-type APIVersionResourcePage struct {
+-	pagination.SinglePageBase
+-}
 -
--	if auth.AccessKey == "" {
--		err = errors.New("AWS_ACCESS_KEY_ID or AWS_ACCESS_KEY not found in environment")
--	}
--	if auth.SecretKey == "" {
--		err = errors.New("AWS_SECRET_ACCESS_KEY or AWS_SECRET_KEY not found in environment")
+-// IsEmpty is a concrete function which indicates whether an
+-// APIVersionResourcePage is empty or not.
+-func (r APIVersionResourcePage) IsEmpty() (bool, error) {
+-	is, err := ExtractVersionResources(r)
+-	if err != nil {
+-		return true, err
 -	}
--	return
+-	return len(is) == 0, nil
 -}
 -
--// Encode takes a string and URI-encodes it in a way suitable
--// to be used in AWS signatures.
--func Encode(s string) string {
--	encode := false
--	for i := 0; i != len(s); i++ {
--		c := s[i]
--		if c > 127 || !unreserved[c] {
--			encode = true
--			break
--		}
--	}
--	if !encode {
--		return s
+-// ExtractVersionResources accepts a Page struct, specifically a
+-// APIVersionResourcePage struct, and extracts the elements into a slice of
+-// APIVersionResource structs. In other words, the collection is mapped into
+-// a relevant slice.
+-func ExtractVersionResources(page pagination.Page) ([]APIVersionResource, error) {
+-	var resp struct {
+-		APIVersionResources []APIVersionResource `mapstructure:"resources"`
 -	}
--	e := make([]byte, len(s)*3)
--	ei := 0
--	for i := 0; i != len(s); i++ {
--		c := s[i]
--		if c > 127 || !unreserved[c] {
--			e[ei] = '%'
--			e[ei+1] = hex[c>>4]
--			e[ei+2] = hex[c&0xF]
--			ei += 3
--		} else {
--			e[ei] = c
--			ei += 1
--		}
--	}
--	return string(e[:ei])
+-
+-	err := mapstructure.Decode(page.(APIVersionResourcePage).Body, &resp)
+-
+-	return resp.APIVersionResources, err
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/aws_test.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/aws_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/urls.go
 deleted file mode 100644
-index 78cbbaf..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/aws_test.go
+index 58aa2b6..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/urls.go
 +++ /dev/null
-@@ -1,203 +0,0 @@
--package aws_test
+@@ -1,15 +0,0 @@
+-package apiversions
 -
 -import (
--	"github.com/mitchellh/goamz/aws"
--	. "github.com/motain/gocheck"
--	"io/ioutil"
--	"os"
 -	"strings"
--	"testing"
+-
+-	"github.com/rackspace/gophercloud"
 -)
 -
--func Test(t *testing.T) {
--	TestingT(t)
+-func apiVersionsURL(c *gophercloud.ServiceClient) string {
+-	return c.Endpoint
 -}
 -
--var _ = Suite(&S{})
--
--type S struct {
--	environ []string
+-func apiInfoURL(c *gophercloud.ServiceClient, version string) string {
+-	return c.Endpoint + strings.TrimRight(version, "/") + "/"
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/urls_test.go
+deleted file mode 100644
+index 7dd069c..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/apiversions/urls_test.go
++++ /dev/null
+@@ -1,26 +0,0 @@
+-package apiversions
 -
--func (s *S) SetUpSuite(c *C) {
--	s.environ = os.Environ()
--}
+-import (
+-	"testing"
 -
--func (s *S) TearDownTest(c *C) {
--	os.Clearenv()
--	for _, kv := range s.environ {
--		l := strings.SplitN(kv, "=", 2)
--		os.Setenv(l[0], l[1])
--	}
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-const endpoint = "http://localhost:57909/"
+-
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint}
 -}
 -
--func (s *S) TestSharedAuthNoHome(c *C) {
--	os.Clearenv()
--	os.Setenv("AWS_PROFILE", "foo")
--	_, err := aws.SharedAuth()
--	c.Assert(err, ErrorMatches, "Could not get HOME")
+-func TestAPIVersionsURL(t *testing.T) {
+-	actual := apiVersionsURL(endpointClient())
+-	expected := endpoint
+-	th.AssertEquals(t, expected, actual)
 -}
 -
--func (s *S) TestSharedAuthNoCredentialsFile(c *C) {
--	os.Clearenv()
--	os.Setenv("AWS_PROFILE", "foo")
--	os.Setenv("HOME", "/tmp")
--	_, err := aws.SharedAuth()
--	c.Assert(err, ErrorMatches, "Couldn't parse AWS credentials file")
+-func TestAPIInfoURL(t *testing.T) {
+-	actual := apiInfoURL(endpointClient(), "v2.0")
+-	expected := endpoint + "v2.0/"
+-	th.AssertEquals(t, expected, actual)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/common/common_tests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/common/common_tests.go
+deleted file mode 100644
+index 4160351..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/common/common_tests.go
++++ /dev/null
+@@ -1,14 +0,0 @@
+-package common
 -
--func (s *S) TestSharedAuthNoProfileInFile(c *C) {
--	os.Clearenv()
--	os.Setenv("AWS_PROFILE", "foo")
+-import (
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--	d, err := ioutil.TempDir("", "")
--	if err != nil {
--		panic(err)
--	}
--	defer os.RemoveAll(d)
+-const TokenID = client.TokenID
 -
--	err = os.Mkdir(d+"/.aws", 0755)
--	if err != nil {
--		panic(err)
--	}
+-func ServiceClient() *gophercloud.ServiceClient {
+-	sc := client.ServiceClient()
+-	sc.ResourceBase = sc.Endpoint + "v2.0/"
+-	return sc
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/delegate.go
+deleted file mode 100644
+index d08e1fd..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/delegate.go
++++ /dev/null
+@@ -1,41 +0,0 @@
+-package extensions
 -
--	ioutil.WriteFile(d+"/.aws/credentials", []byte("[bar]\n"), 0644)
--	os.Setenv("HOME", d)
+-import (
+-	"github.com/rackspace/gophercloud"
+-	common "github.com/rackspace/gophercloud/openstack/common/extensions"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	_, err = aws.SharedAuth()
--	c.Assert(err, ErrorMatches, "Couldn't find profile in AWS credentials file")
+-// Extension is a single OpenStack extension.
+-type Extension struct {
+-	common.Extension
 -}
 -
--func (s *S) TestSharedAuthNoKeysInProfile(c *C) {
--	os.Clearenv()
--	os.Setenv("AWS_PROFILE", "bar")
+-// GetResult wraps a GetResult from common.
+-type GetResult struct {
+-	common.GetResult
+-}
 -
--	d, err := ioutil.TempDir("", "")
+-// ExtractExtensions interprets a Page as a slice of Extensions.
+-func ExtractExtensions(page pagination.Page) ([]Extension, error) {
+-	inner, err := common.ExtractExtensions(page)
 -	if err != nil {
--		panic(err)
+-		return nil, err
 -	}
--	defer os.RemoveAll(d)
--
--	err = os.Mkdir(d+"/.aws", 0755)
--	if err != nil {
--		panic(err)
+-	outer := make([]Extension, len(inner))
+-	for index, ext := range inner {
+-		outer[index] = Extension{ext}
 -	}
+-	return outer, nil
+-}
 -
--	ioutil.WriteFile(d+"/.aws/credentials", []byte("[bar]\nawsaccesskeyid = AK.."), 0644)
--	os.Setenv("HOME", d)
+-// Get retrieves information for a specific extension using its alias.
+-func Get(c *gophercloud.ServiceClient, alias string) GetResult {
+-	return GetResult{common.Get(c, alias)}
+-}
 -
--	_, err = aws.SharedAuth()
--	c.Assert(err, ErrorMatches, "AWS_SECRET_ACCESS_KEY not found in credentials file")
+-// List returns a Pager which allows you to iterate over the full collection of extensions.
+-// It does not accept query parameters.
+-func List(c *gophercloud.ServiceClient) pagination.Pager {
+-	return common.List(c)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/delegate_test.go
+deleted file mode 100644
+index 3d2ac78..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/delegate_test.go
++++ /dev/null
+@@ -1,105 +0,0 @@
+-package extensions
 -
--func (s *S) TestSharedAuthDefaultCredentials(c *C) {
--	os.Clearenv()
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--	d, err := ioutil.TempDir("", "")
--	if err != nil {
--		panic(err)
--	}
--	defer os.RemoveAll(d)
+-	common "github.com/rackspace/gophercloud/openstack/common/extensions"
+-	fake "github.com/rackspace/gophercloud/openstack/networking/v2/common"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--	err = os.Mkdir(d+"/.aws", 0755)
--	if err != nil {
--		panic(err)
--	}
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	ioutil.WriteFile(d+"/.aws/credentials", []byte("[default]\naws_access_key_id = access\naws_secret_access_key = secret\n"), 0644)
--	os.Setenv("HOME", d)
+-	th.Mux.HandleFunc("/v2.0/extensions", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--	auth, err := aws.SharedAuth()
--	c.Assert(err, IsNil)
--	c.Assert(auth, Equals, aws.Auth{SecretKey: "secret", AccessKey: "access"})
+-		w.Header().Add("Content-Type", "application/json")
+-
+-		fmt.Fprintf(w, `
+-{
+-    "extensions": [
+-        {
+-            "updated": "2013-01-20T00:00:00-00:00",
+-            "name": "Neutron Service Type Management",
+-            "links": [],
+-            "namespace": "http://docs.openstack.org/ext/neutron/service-type/api/v1.0",
+-            "alias": "service-type",
+-            "description": "API for retrieving service providers for Neutron advanced services"
+-        }
+-    ]
 -}
+-      `)
+-	})
 -
--func (s *S) TestSharedAuth(c *C) {
--	os.Clearenv()
--	os.Setenv("AWS_PROFILE", "bar")
+-	count := 0
 -
--	d, err := ioutil.TempDir("", "")
--	if err != nil {
--		panic(err)
--	}
--	defer os.RemoveAll(d)
+-	List(fake.ServiceClient()).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractExtensions(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract extensions: %v", err)
+-		}
+-
+-		expected := []Extension{
+-			Extension{
+-				common.Extension{
+-					Updated:     "2013-01-20T00:00:00-00:00",
+-					Name:        "Neutron Service Type Management",
+-					Links:       []interface{}{},
+-					Namespace:   "http://docs.openstack.org/ext/neutron/service-type/api/v1.0",
+-					Alias:       "service-type",
+-					Description: "API for retrieving service providers for Neutron advanced services",
+-				},
+-			},
+-		}
 -
--	err = os.Mkdir(d+"/.aws", 0755)
--	if err != nil {
--		panic(err)
--	}
+-		th.AssertDeepEquals(t, expected, actual)
 -
--	ioutil.WriteFile(d+"/.aws/credentials", []byte("[bar]\naws_access_key_id = access\naws_secret_access_key = secret\n"), 0644)
--	os.Setenv("HOME", d)
+-		return true, nil
+-	})
 -
--	auth, err := aws.SharedAuth()
--	c.Assert(err, IsNil)
--	c.Assert(auth, Equals, aws.Auth{SecretKey: "secret", AccessKey: "access"})
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
+-	}
 -}
 -
--func (s *S) TestEnvAuthNoSecret(c *C) {
--	os.Clearenv()
--	_, err := aws.EnvAuth()
--	c.Assert(err, ErrorMatches, "AWS_SECRET_ACCESS_KEY or AWS_SECRET_KEY not found in environment")
--}
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--func (s *S) TestEnvAuthNoAccess(c *C) {
--	os.Clearenv()
--	os.Setenv("AWS_SECRET_ACCESS_KEY", "foo")
--	_, err := aws.EnvAuth()
--	c.Assert(err, ErrorMatches, "AWS_ACCESS_KEY_ID or AWS_ACCESS_KEY not found in environment")
--}
+-	th.Mux.HandleFunc("/v2.0/extensions/agent", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--func (s *S) TestEnvAuth(c *C) {
--	os.Clearenv()
--	os.Setenv("AWS_SECRET_ACCESS_KEY", "secret")
--	os.Setenv("AWS_ACCESS_KEY_ID", "access")
--	auth, err := aws.EnvAuth()
--	c.Assert(err, IsNil)
--	c.Assert(auth, Equals, aws.Auth{SecretKey: "secret", AccessKey: "access"})
--}
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--func (s *S) TestEnvAuthWithToken(c *C) {
--	os.Clearenv()
--	os.Setenv("AWS_SECRET_ACCESS_KEY", "secret")
--	os.Setenv("AWS_ACCESS_KEY_ID", "access")
--	os.Setenv("AWS_SECURITY_TOKEN", "token")
--	auth, err := aws.EnvAuth()
--	c.Assert(err, IsNil)
--	c.Assert(auth, Equals, aws.Auth{SecretKey: "secret", AccessKey: "access", Token: "token"})
+-		fmt.Fprintf(w, `
+-{
+-    "extension": {
+-        "updated": "2013-02-03T10:00:00-00:00",
+-        "name": "agent",
+-        "links": [],
+-        "namespace": "http://docs.openstack.org/ext/agent/api/v2.0",
+-        "alias": "agent",
+-        "description": "The agent management extension."
+-    }
 -}
+-    `)
+-	})
 -
--func (s *S) TestEnvAuthAlt(c *C) {
--	os.Clearenv()
--	os.Setenv("AWS_SECRET_KEY", "secret")
--	os.Setenv("AWS_ACCESS_KEY", "access")
--	auth, err := aws.EnvAuth()
--	c.Assert(err, IsNil)
--	c.Assert(auth, Equals, aws.Auth{SecretKey: "secret", AccessKey: "access"})
+-	ext, err := Get(fake.ServiceClient(), "agent").Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, ext.Updated, "2013-02-03T10:00:00-00:00")
+-	th.AssertEquals(t, ext.Name, "agent")
+-	th.AssertEquals(t, ext.Namespace, "http://docs.openstack.org/ext/agent/api/v2.0")
+-	th.AssertEquals(t, ext.Alias, "agent")
+-	th.AssertEquals(t, ext.Description, "The agent management extension.")
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/external/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/external/doc.go
+deleted file mode 100644
+index dad3a84..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/external/doc.go
++++ /dev/null
+@@ -1,3 +0,0 @@
+-// Package external provides information and interaction with the external
+-// extension for the OpenStack Networking service.
+-package external
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/external/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/external/requests.go
+deleted file mode 100644
+index 2f04593..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/external/requests.go
++++ /dev/null
+@@ -1,56 +0,0 @@
+-package external
 -
--func (s *S) TestGetAuthStatic(c *C) {
--	auth, err := aws.GetAuth("access", "secret")
--	c.Assert(err, IsNil)
--	c.Assert(auth, Equals, aws.Auth{SecretKey: "secret", AccessKey: "access"})
+-import "github.com/rackspace/gophercloud/openstack/networking/v2/networks"
+-
+-// AdminState gives users a solid type to work with for create and update
+-// operations. It is recommended that users use the `Up` and `Down` enums.
+-type AdminState *bool
+-
+-// Convenience vars for AdminStateUp values.
+-var (
+-	iTrue  = true
+-	iFalse = false
+-
+-	Up   AdminState = &iTrue
+-	Down AdminState = &iFalse
+-)
+-
+-// CreateOpts is the structure used when creating new external network
+-// resources. It embeds networks.CreateOpts and so inherits all of its required
+-// and optional fields, with the addition of the External field.
+-type CreateOpts struct {
+-	Parent   networks.CreateOpts
+-	External bool
 -}
 -
--func (s *S) TestGetAuthEnv(c *C) {
--	os.Clearenv()
--	os.Setenv("AWS_SECRET_ACCESS_KEY", "secret")
--	os.Setenv("AWS_ACCESS_KEY_ID", "access")
--	auth, err := aws.GetAuth("", "")
--	c.Assert(err, IsNil)
--	c.Assert(auth, Equals, aws.Auth{SecretKey: "secret", AccessKey: "access"})
+-// ToNetworkCreateMap casts a CreateOpts struct to a map.
+-func (o CreateOpts) ToNetworkCreateMap() (map[string]interface{}, error) {
+-	outer, err := o.Parent.ToNetworkCreateMap()
+-	if err != nil {
+-		return nil, err
+-	}
+-
+-	outer["network"].(map[string]interface{})["router:external"] = o.External
+-
+-	return outer, nil
 -}
 -
--func (s *S) TestEncode(c *C) {
--	c.Assert(aws.Encode("foo"), Equals, "foo")
--	c.Assert(aws.Encode("/"), Equals, "%2F")
+-// UpdateOpts is the structure used when updating existing external network
+-// resources. It embeds networks.UpdateOpts and so inherits all of its required
+-// and optional fields, with the addition of the External field.
+-type UpdateOpts struct {
+-	Parent   networks.UpdateOpts
+-	External bool
 -}
 -
--func (s *S) TestRegionsAreNamed(c *C) {
--	for n, r := range aws.Regions {
--		c.Assert(n, Equals, r.Name)
+-// ToNetworkUpdateMap casts an UpdateOpts struct to a map.
+-func (o UpdateOpts) ToNetworkUpdateMap() (map[string]interface{}, error) {
+-	outer, err := o.Parent.ToNetworkUpdateMap()
+-	if err != nil {
+-		return nil, err
 -	}
+-
+-	outer["network"].(map[string]interface{})["router:external"] = o.External
+-
+-	return outer, nil
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/client.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/client.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/external/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/external/results.go
 deleted file mode 100644
-index ee53238..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/client.go
+index 1c173c0..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/external/results.go
 +++ /dev/null
-@@ -1,125 +0,0 @@
--package aws
+@@ -1,81 +0,0 @@
+-package external
 -
 -import (
--	"math"
--	"net"
--	"net/http"
--	"time"
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/networks"
+-	"github.com/rackspace/gophercloud/pagination"
 -)
 -
--type RetryableFunc func(*http.Request, *http.Response, error) bool
--type WaitFunc func(try int)
--type DeadlineFunc func() time.Time
+-// NetworkExternal represents a decorated form of a Network with based on the
+-// "external-net" extension.
+-type NetworkExternal struct {
+-	// UUID for the network
+-	ID string `mapstructure:"id" json:"id"`
 -
--type ResilientTransport struct {
--	// Timeout is the maximum amount of time a dial will wait for
--	// a connect to complete.
--	//
--	// The default is no timeout.
--	//
--	// With or without a timeout, the operating system may impose
--	// its own earlier timeout. For instance, TCP timeouts are
--	// often around 3 minutes.
--	DialTimeout time.Duration
+-	// Human-readable name for the network. Might not be unique.
+-	Name string `mapstructure:"name" json:"name"`
 -
--	// MaxTries, if non-zero, specifies the number of times we will retry on
--	// failure. Retries are only attempted for temporary network errors or known
--	// safe failures.
--	MaxTries    int
--	Deadline    DeadlineFunc
--	ShouldRetry RetryableFunc
--	Wait        WaitFunc
--	transport   *http.Transport
--}
+-	// The administrative state of network. If false (down), the network does not forward packets.
+-	AdminStateUp bool `mapstructure:"admin_state_up" json:"admin_state_up"`
 -
--// Convenience method for creating an http client
--func NewClient(rt *ResilientTransport) *http.Client {
--	rt.transport = &http.Transport{
--		Dial: func(netw, addr string) (net.Conn, error) {
--			c, err := net.DialTimeout(netw, addr, rt.DialTimeout)
--			if err != nil {
--				return nil, err
--			}
--			c.SetDeadline(rt.Deadline())
--			return c, nil
--		},
--		DisableKeepAlives: true,
--		Proxy:             http.ProxyFromEnvironment,
--	}
--	// TODO: Would be nice is ResilientTransport allowed clients to initialize
--	// with http.Transport attributes.
--	return &http.Client{
--		Transport: rt,
--	}
--}
+-	// Indicates whether network is currently operational. Possible values include
+-	// `ACTIVE', `DOWN', `BUILD', or `ERROR'. Plug-ins might define additional values.
+-	Status string `mapstructure:"status" json:"status"`
 -
--var retryingTransport = &ResilientTransport{
--	Deadline: func() time.Time {
--		return time.Now().Add(5 * time.Second)
--	},
--	DialTimeout: 10 * time.Second,
--	MaxTries:    3,
--	ShouldRetry: awsRetry,
--	Wait:        ExpBackoff,
--}
+-	// Subnets associated with this network.
+-	Subnets []string `mapstructure:"subnets" json:"subnets"`
 -
--// Exported default client
--var RetryingClient = NewClient(retryingTransport)
+-	// Owner of network. Only admin users can specify a tenant_id other than its own.
+-	TenantID string `mapstructure:"tenant_id" json:"tenant_id"`
 -
--func (t *ResilientTransport) RoundTrip(req *http.Request) (*http.Response, error) {
--	return t.tries(req)
+-	// Specifies whether the network resource can be accessed by any tenant or not.
+-	Shared bool `mapstructure:"shared" json:"shared"`
+-
+-	// Specifies whether the network is an external network or not.
+-	External bool `mapstructure:"router:external" json:"router:external"`
 -}
 -
--// Retry a request a maximum of t.MaxTries times.
--// We'll only retry if the proper criteria are met.
--// If a wait function is specified, wait that amount of time
--// In between requests.
--func (t *ResilientTransport) tries(req *http.Request) (res *http.Response, err error) {
--	for try := 0; try < t.MaxTries; try += 1 {
--		res, err = t.transport.RoundTrip(req)
+-func commonExtract(e error, response interface{}) (*NetworkExternal, error) {
+-	if e != nil {
+-		return nil, e
+-	}
 -
--		if !t.ShouldRetry(req, res, err) {
--			break
--		}
--		if res != nil {
--			res.Body.Close()
--		}
--		if t.Wait != nil {
--			t.Wait(try)
--		}
+-	var res struct {
+-		Network *NetworkExternal `json:"network"`
 -	}
 -
--	return
+-	err := mapstructure.Decode(response, &res)
+-
+-	return res.Network, err
 -}
 -
--func ExpBackoff(try int) {
--	time.Sleep(100 * time.Millisecond *
--		time.Duration(math.Exp2(float64(try))))
+-// ExtractGet decorates a GetResult struct returned from a networks.Get()
+-// function with extended attributes.
+-func ExtractGet(r networks.GetResult) (*NetworkExternal, error) {
+-	return commonExtract(r.Err, r.Body)
 -}
 -
--func LinearBackoff(try int) {
--	time.Sleep(time.Duration(try*100) * time.Millisecond)
+-// ExtractCreate decorates a CreateResult struct returned from a networks.Create()
+-// function with extended attributes.
+-func ExtractCreate(r networks.CreateResult) (*NetworkExternal, error) {
+-	return commonExtract(r.Err, r.Body)
 -}
 -
--// Decide if we should retry a request.
--// In general, the criteria for retrying a request is described here
--// http://docs.aws.amazon.com/general/latest/gr/api-retries.html
--func awsRetry(req *http.Request, res *http.Response, err error) bool {
--	retry := false
+-// ExtractUpdate decorates a UpdateResult struct returned from a
+-// networks.Update() function with extended attributes.
+-func ExtractUpdate(r networks.UpdateResult) (*NetworkExternal, error) {
+-	return commonExtract(r.Err, r.Body)
+-}
 -
--	// Retry if there's a temporary network error.
--	if neterr, ok := err.(net.Error); ok {
--		if neterr.Temporary() {
--			retry = true
--		}
+-// ExtractList accepts a Page struct, specifically a NetworkPage struct, and
+-// extracts the elements into a slice of NetworkExtAttrs structs. In other
+-// words, a generic collection is mapped into a relevant slice.
+-func ExtractList(page pagination.Page) ([]NetworkExternal, error) {
+-	var resp struct {
+-		Networks []NetworkExternal `mapstructure:"networks" json:"networks"`
 -	}
 -
--	// Retry if we get a 5xx series error.
--	if res != nil {
--		if res.StatusCode >= 500 && res.StatusCode < 600 {
--			retry = true
--		}
--	}
+-	err := mapstructure.Decode(page.(networks.NetworkPage).Body, &resp)
 -
--	return retry
+-	return resp.Networks, err
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/client_test.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/client_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/external/results_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/external/results_test.go
 deleted file mode 100644
-index 2f6b39c..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/goamz/aws/client_test.go
+index 916cd2c..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/external/results_test.go
 +++ /dev/null
-@@ -1,121 +0,0 @@
--package aws_test
+@@ -1,254 +0,0 @@
+-package external
 -
 -import (
+-	"errors"
 -	"fmt"
--	"github.com/mitchellh/goamz/aws"
--	"io/ioutil"
 -	"net/http"
--	"net/http/httptest"
--	"strings"
 -	"testing"
--	"time"
+-
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/networks"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
 -)
 -
--// Retrieve the response from handler using aws.RetryingClient
--func serveAndGet(handler http.HandlerFunc) (body string, err error) {
--	ts := httptest.NewServer(handler)
--	defer ts.Close()
--	resp, err := aws.RetryingClient.Get(ts.URL)
--	if err != nil {
--		return
--	}
--	if resp.StatusCode != 200 {
--		return "", fmt.Errorf("Bad status code: %d", resp.StatusCode)
--	}
--	greeting, err := ioutil.ReadAll(resp.Body)
--	resp.Body.Close()
--	if err != nil {
--		return
--	}
--	return strings.TrimSpace(string(greeting)), nil
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/networks", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "networks": [
+-        {
+-            "admin_state_up": true,
+-            "id": "0f38d5ad-10a6-428f-a5fc-825cfe0f1970",
+-            "name": "net1",
+-            "router:external": false,
+-            "shared": false,
+-            "status": "ACTIVE",
+-            "subnets": [
+-                "25778974-48a8-46e7-8998-9dc8c70d2f06"
+-            ],
+-            "tenant_id": "b575417a6c444a6eb5cc3a58eb4f714a"
+-        },
+-        {
+-            "admin_state_up": true,
+-            "id": "8d05a1b1-297a-46ca-8974-17debf51ca3c",
+-            "name": "ext_net",
+-            "router:external": true,
+-            "shared": false,
+-            "status": "ACTIVE",
+-            "subnets": [
+-                "2f1fb918-9b0e-4bf9-9a50-6cebbb4db2c5"
+-            ],
+-            "tenant_id": "5eb8995cf717462c9df8d1edfa498010"
+-        }
+-    ]
 -}
+-			`)
+-	})
 -
--func TestClient_expected(t *testing.T) {
--	body := "foo bar"
+-	count := 0
 -
--	resp, err := serveAndGet(func(w http.ResponseWriter, r *http.Request) {
--		fmt.Fprintln(w, body)
+-	networks.List(fake.ServiceClient(), networks.ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractList(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract networks: %v", err)
+-			return false, err
+-		}
+-
+-		expected := []NetworkExternal{
+-			NetworkExternal{
+-				Status:       "ACTIVE",
+-				Subnets:      []string{"25778974-48a8-46e7-8998-9dc8c70d2f06"},
+-				Name:         "net1",
+-				AdminStateUp: true,
+-				TenantID:     "b575417a6c444a6eb5cc3a58eb4f714a",
+-				Shared:       false,
+-				ID:           "0f38d5ad-10a6-428f-a5fc-825cfe0f1970",
+-				External:     false,
+-			},
+-			NetworkExternal{
+-				Status:       "ACTIVE",
+-				Subnets:      []string{"2f1fb918-9b0e-4bf9-9a50-6cebbb4db2c5"},
+-				Name:         "ext_net",
+-				AdminStateUp: true,
+-				TenantID:     "5eb8995cf717462c9df8d1edfa498010",
+-				Shared:       false,
+-				ID:           "8d05a1b1-297a-46ca-8974-17debf51ca3c",
+-				External:     true,
+-			},
+-		}
+-
+-		th.CheckDeepEquals(t, expected, actual)
+-
+-		return true, nil
 -	})
--	if err != nil {
--		t.Fatal(err)
--	}
--	if resp != body {
--		t.Fatal("Body not as expected.")
+-
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
 -	}
 -}
 -
--func TestClient_delay(t *testing.T) {
--	body := "baz"
--	wait := 4
--	resp, err := serveAndGet(func(w http.ResponseWriter, r *http.Request) {
--		if wait < 0 {
--			// If we dipped to zero delay and still failed.
--			t.Fatal("Never succeeded.")
--		}
--		wait -= 1
--		time.Sleep(time.Second * time.Duration(wait))
--		fmt.Fprintln(w, body)
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/networks/d32019d3-bc6e-4319-9c1d-6722fc136a22", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "network": {
+-        "admin_state_up": true,
+-        "id": "8d05a1b1-297a-46ca-8974-17debf51ca3c",
+-        "name": "ext_net",
+-        "router:external": true,
+-        "shared": false,
+-        "status": "ACTIVE",
+-        "subnets": [
+-            "2f1fb918-9b0e-4bf9-9a50-6cebbb4db2c5"
+-        ],
+-        "tenant_id": "5eb8995cf717462c9df8d1edfa498010"
+-    }
+-}
+-			`)
 -	})
--	if err != nil {
--		t.Fatal(err)
--	}
--	if resp != body {
--		t.Fatal("Body not as expected.", resp)
--	}
+-
+-	res := networks.Get(fake.ServiceClient(), "d32019d3-bc6e-4319-9c1d-6722fc136a22")
+-	n, err := ExtractGet(res)
+-
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, true, n.External)
 -}
 -
--func TestClient_no4xxRetry(t *testing.T) {
--	tries := 0
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/networks", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "network": {
+-        "admin_state_up": true,
+-        "name": "ext_net",
+-        "router:external": true
+-    }
+-}
+-			`)
 -
--	// Fail once before succeeding.
--	_, err := serveAndGet(func(w http.ResponseWriter, r *http.Request) {
--		tries += 1
--		http.Error(w, "error", 404)
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
+-
+-		fmt.Fprintf(w, `
+-{
+-	"network": {
+-			"admin_state_up": true,
+-			"id": "8d05a1b1-297a-46ca-8974-17debf51ca3c",
+-			"name": "ext_net",
+-			"router:external": true,
+-			"shared": false,
+-			"status": "ACTIVE",
+-			"subnets": [
+-					"2f1fb918-9b0e-4bf9-9a50-6cebbb4db2c5"
+-			],
+-			"tenant_id": "5eb8995cf717462c9df8d1edfa498010"
+-	}
+-}
+-		`)
 -	})
 -
--	if err == nil {
--		t.Fatal("should have error")
--	}
+-	options := CreateOpts{networks.CreateOpts{Name: "ext_net", AdminStateUp: Up}, true}
+-	res := networks.Create(fake.ServiceClient(), options)
 -
--	if tries != 1 {
--		t.Fatalf("should only try once: %d", tries)
--	}
+-	n, err := ExtractCreate(res)
+-
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, true, n.External)
 -}
 -
--func TestClient_retries(t *testing.T) {
--	body := "biz"
--	failed := false
--	// Fail once before succeeding.
--	resp, err := serveAndGet(func(w http.ResponseWriter, r *http.Request) {
--		if !failed {
--			http.Error(w, "error", 500)
--			failed = true
--		} else {
--			fmt.Fprintln(w, body)
+-func TestUpdate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/networks/4e8e5957-649f-477b-9e5b-f1f75b21c03c", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-		"network": {
+-				"router:external": true,
+-				"name": "new_name"
 -		}
--	})
--	if failed != true {
--		t.Error("We didn't retry!")
--	}
--	if err != nil {
--		t.Fatal(err)
--	}
--	if resp != body {
--		t.Fatal("Body not as expected.")
--	}
 -}
+-			`)
 -
--func TestClient_fails(t *testing.T) {
--	tries := 0
--	// Fail 3 times and return the last error.
--	_, err := serveAndGet(func(w http.ResponseWriter, r *http.Request) {
--		tries += 1
--		http.Error(w, "error", 500)
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-	"network": {
+-			"admin_state_up": true,
+-			"id": "8d05a1b1-297a-46ca-8974-17debf51ca3c",
+-			"name": "new_name",
+-			"router:external": true,
+-			"shared": false,
+-			"status": "ACTIVE",
+-			"subnets": [
+-					"2f1fb918-9b0e-4bf9-9a50-6cebbb4db2c5"
+-			],
+-			"tenant_id": "5eb8995cf717462c9df8d1edfa498010"
+-	}
+-}
+-		`)
 -	})
--	if err == nil {
--		t.Fatal(err)
+-
+-	options := UpdateOpts{networks.UpdateOpts{Name: "new_name"}, true}
+-	res := networks.Update(fake.ServiceClient(), "4e8e5957-649f-477b-9e5b-f1f75b21c03c", options)
+-	n, err := ExtractUpdate(res)
+-
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, true, n.External)
+-}
+-
+-func TestExtractFnsReturnsErrWhenResultContainsErr(t *testing.T) {
+-	gr := networks.GetResult{}
+-	gr.Err = errors.New("")
+-
+-	if _, err := ExtractGet(gr); err == nil {
+-		t.Fatalf("Expected error, got one")
 -	}
--	if tries != 3 {
--		t.Fatal("Didn't retry enough")
+-
+-	ur := networks.UpdateResult{}
+-	ur.Err = errors.New("")
+-
+-	if _, err := ExtractUpdate(ur); err == nil {
+-		t.Fatalf("Expected error, got one")
+-	}
+-
+-	cr := networks.CreateResult{}
+-	cr.Err = errors.New("")
+-
+-	if _, err := ExtractCreate(cr); err == nil {
+-		t.Fatalf("Expected error, got one")
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/doc.go
 deleted file mode 100644
-index 8f94ad5..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2.go
+index d533458..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/doc.go
 +++ /dev/null
-@@ -1,2599 +0,0 @@
--//
--// goamz - Go packages to interact with the Amazon Web Services.
--//
--//   https://wiki.ubuntu.com/goamz
--//
--// Copyright (c) 2011 Canonical Ltd.
--//
--// Written by Gustavo Niemeyer <gustavo.niemeyer at canonical.com>
--//
--
--package ec2
+@@ -1,5 +0,0 @@
+-// Package layer3 provides access to the Layer-3 networking extension for the
+-// OpenStack Neutron service. This extension allows API users to route packets
+-// between subnets, forward packets from internal networks to external ones,
+-// and access instances from external networks through floating IPs.
+-package layer3
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/floatingips/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/floatingips/requests.go
+deleted file mode 100644
+index d23f9e2..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/floatingips/requests.go
++++ /dev/null
+@@ -1,190 +0,0 @@
+-package floatingips
 -
 -import (
--	"crypto/rand"
--	"encoding/base64"
--	"encoding/hex"
--	"encoding/xml"
 -	"fmt"
--	"log"
--	"net/http"
--	"net/http/httputil"
--	"net/url"
--	"sort"
--	"strconv"
--	"strings"
--	"time"
 -
--	"github.com/mitchellh/goamz/aws"
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
 -)
 -
--const debug = false
--
--// The EC2 type encapsulates operations with a specific EC2 region.
--type EC2 struct {
--	aws.Auth
--	aws.Region
--	httpClient *http.Client
--	private    byte // Reserve the right of using private data.
+-// ListOpts allows the filtering and sorting of paginated collections through
+-// the API. Filtering is achieved by passing in struct field values that map to
+-// the floating IP attributes you want to see returned. SortKey allows you to
+-// sort by a particular network attribute. SortDir sets the direction, and is
+-// either `asc' or `desc'. Marker and Limit are used for pagination.
+-type ListOpts struct {
+-	ID                string `q:"id"`
+-	FloatingNetworkID string `q:"floating_network_id"`
+-	PortID            string `q:"port_id"`
+-	FixedIP           string `q:"fixed_ip_address"`
+-	FloatingIP        string `q:"floating_ip_address"`
+-	TenantID          string `q:"tenant_id"`
+-	Limit             int    `q:"limit"`
+-	Marker            string `q:"marker"`
+-	SortKey           string `q:"sort_key"`
+-	SortDir           string `q:"sort_dir"`
+-}
+-
+-// List returns a Pager which allows you to iterate over a collection of
+-// floating IP resources. It accepts a ListOpts struct, which allows you to
+-// filter and sort the returned collection for greater efficiency.
+-func List(c *gophercloud.ServiceClient, opts ListOpts) pagination.Pager {
+-	q, err := gophercloud.BuildQueryString(&opts)
+-	if err != nil {
+-		return pagination.Pager{Err: err}
+-	}
+-	u := rootURL(c) + q.String()
+-	return pagination.NewPager(c, u, func(r pagination.PageResult) pagination.Page {
+-		return FloatingIPPage{pagination.LinkedPageBase{PageResult: r}}
+-	})
 -}
 -
--// New creates a new EC2.
--func NewWithClient(auth aws.Auth, region aws.Region, client *http.Client) *EC2 {
--	return &EC2{auth, region, client, 0}
+-// CreateOpts contains all the values needed to create a new floating IP
+-// resource. The only required fields are FloatingNetworkID and PortID which
+-// refer to the external network and internal port respectively.
+-type CreateOpts struct {
+-	FloatingNetworkID string
+-	FloatingIP        string
+-	PortID            string
+-	FixedIP           string
+-	TenantID          string
 -}
 -
--func New(auth aws.Auth, region aws.Region) *EC2 {
--	return NewWithClient(auth, region, aws.RetryingClient)
--}
+-var (
+-	errFloatingNetworkIDRequired = fmt.Errorf("A NetworkID is required")
+-	errPortIDRequired            = fmt.Errorf("A PortID is required")
+-)
 -
--// ----------------------------------------------------------------------------
--// Filtering helper.
+-// Create accepts a CreateOpts struct and uses the values provided to create a
+-// new floating IP resource. You can create floating IPs on external networks
+-// only. If you provide a FloatingNetworkID which refers to a network that is
+-// not external (i.e. its `router:external' attribute is False), the operation
+-// will fail and return a 400 error.
+-//
+-// If you do not specify a FloatingIP address value, the operation will
+-// automatically allocate an available address for the new resource. If you do
+-// choose to specify one, it must fall within the subnet range for the external
+-// network - otherwise the operation returns a 400 error. If the FloatingIP
+-// address is already in use, the operation returns a 409 error code.
+-//
+-// You can associate the new resource with an internal port by using the PortID
+-// field. If you specify a PortID that is not valid, the operation will fail and
+-// return 404 error code.
+-//
+-// You must also configure an IP address for the port associated with the PortID
+-// you have provided - this is what the FixedIP refers to: an IP fixed to a port.
+-// Because a port might be associated with multiple IP addresses, you can use
+-// the FixedIP field to associate a particular IP address rather than have the
+-// API assume for you. If you specify an IP address that is not valid, the
+-// operation will fail and return a 400 error code. If the PortID and FixedIP
+-// are already associated with another resource, the operation will fail and
+-// returns a 409 error code.
+-func Create(c *gophercloud.ServiceClient, opts CreateOpts) CreateResult {
+-	var res CreateResult
+-
+-	// Validate
+-	if opts.FloatingNetworkID == "" {
+-		res.Err = errFloatingNetworkIDRequired
+-		return res
+-	}
+-	if opts.PortID == "" {
+-		res.Err = errPortIDRequired
+-		return res
+-	}
+-
+-	// Define structures
+-	type floatingIP struct {
+-		FloatingNetworkID string `json:"floating_network_id"`
+-		FloatingIP        string `json:"floating_ip_address,omitempty"`
+-		PortID            string `json:"port_id"`
+-		FixedIP           string `json:"fixed_ip_address,omitempty"`
+-		TenantID          string `json:"tenant_id,omitempty"`
+-	}
+-	type request struct {
+-		FloatingIP floatingIP `json:"floatingip"`
+-	}
+-
+-	// Populate request body
+-	reqBody := request{FloatingIP: floatingIP{
+-		FloatingNetworkID: opts.FloatingNetworkID,
+-		PortID:            opts.PortID,
+-		FixedIP:           opts.FixedIP,
+-		TenantID:          opts.TenantID,
+-	}}
 -
--// Filter builds filtering parameters to be used in an EC2 query which supports
--// filtering.  For example:
--//
--//     filter := NewFilter()
--//     filter.Add("architecture", "i386")
--//     filter.Add("launch-index", "0")
--//     resp, err := ec2.Instances(nil, filter)
--//
--type Filter struct {
--	m map[string][]string
--}
+-	// Send request to API
+-	_, res.Err = perigee.Request("POST", rootURL(c), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{201},
+-	})
 -
--// NewFilter creates a new Filter.
--func NewFilter() *Filter {
--	return &Filter{make(map[string][]string)}
+-	return res
 -}
 -
--// Add appends a filtering parameter with the given name and value(s).
--func (f *Filter) Add(name string, value ...string) {
--	f.m[name] = append(f.m[name], value...)
+-// Get retrieves a particular floating IP resource based on its unique ID.
+-func Get(c *gophercloud.ServiceClient, id string) GetResult {
+-	var res GetResult
+-	_, res.Err = perigee.Request("GET", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return res
 -}
 -
--func (f *Filter) addParams(params map[string]string) {
--	if f != nil {
--		a := make([]string, len(f.m))
--		i := 0
--		for k := range f.m {
--			a[i] = k
--			i++
--		}
--		sort.StringSlice(a).Sort()
--		for i, k := range a {
--			prefix := "Filter." + strconv.Itoa(i+1)
--			params[prefix+".Name"] = k
--			for j, v := range f.m[k] {
--				params[prefix+".Value."+strconv.Itoa(j+1)] = v
--			}
--		}
--	}
+-// UpdateOpts contains the values used when updating a floating IP resource. The
+-// only value that can be updated is which internal port the floating IP is
+-// linked to. To associate the floating IP with a new internal port, provide its
+-// ID. To disassociate the floating IP from all ports, provide an empty string.
+-type UpdateOpts struct {
+-	PortID string
 -}
 -
--// ----------------------------------------------------------------------------
--// Request dispatching logic.
+-// Update allows floating IP resources to be updated. Currently, the only way to
+-// "update" a floating IP is to associate it with a new internal port, or
+-// disassociated it from all ports. See UpdateOpts for instructions of how to
+-// do this.
+-func Update(c *gophercloud.ServiceClient, id string, opts UpdateOpts) UpdateResult {
+-	type floatingIP struct {
+-		PortID *string `json:"port_id"`
+-	}
 -
--// Error encapsulates an error returned by EC2.
--//
--// See http://goo.gl/VZGuC for more details.
--type Error struct {
--	// HTTP status code (200, 403, ...)
--	StatusCode int
--	// EC2 error code ("UnsupportedOperation", ...)
--	Code string
--	// The human-oriented error message
--	Message   string
--	RequestId string `xml:"RequestID"`
--}
+-	type request struct {
+-		FloatingIP floatingIP `json:"floatingip"`
+-	}
 -
--func (err *Error) Error() string {
--	if err.Code == "" {
--		return err.Message
+-	var portID *string
+-	if opts.PortID == "" {
+-		portID = nil
+-	} else {
+-		portID = &opts.PortID
 -	}
 -
--	return fmt.Sprintf("%s (%s)", err.Message, err.Code)
--}
+-	reqBody := request{FloatingIP: floatingIP{PortID: portID}}
 -
--// For now a single error inst is being exposed. In the future it may be useful
--// to provide access to all of them, but rather than doing it as an array/slice,
--// use a *next pointer, so that it's backward compatible and it continues to be
--// easy to handle the first error, which is what most people will want.
--type xmlErrors struct {
--	RequestId string  `xml:"RequestID"`
--	Errors    []Error `xml:"Errors>Error"`
--}
+-	// Send request to API
+-	var res UpdateResult
+-	_, res.Err = perigee.Request("PUT", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
 -
--var timeNow = time.Now
+-	return res
+-}
 -
--func (ec2 *EC2) query(params map[string]string, resp interface{}) error {
--	params["Version"] = "2014-05-01"
--	params["Timestamp"] = timeNow().In(time.UTC).Format(time.RFC3339)
--	endpoint, err := url.Parse(ec2.Region.EC2Endpoint)
--	if err != nil {
--		return err
--	}
--	if endpoint.Path == "" {
--		endpoint.Path = "/"
--	}
--	sign(ec2.Auth, "GET", endpoint.Path, params, endpoint.Host)
--	endpoint.RawQuery = multimap(params).Encode()
--	if debug {
--		log.Printf("get { %v } -> {\n", endpoint.String())
--	}
+-// Delete will permanently delete a particular floating IP resource. Please
+-// ensure this is what you want - you can also disassociate the IP from existing
+-// internal ports.
+-func Delete(c *gophercloud.ServiceClient, id string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{204},
+-	})
+-	return res
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/floatingips/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/floatingips/requests_test.go
+deleted file mode 100644
+index 19614be..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/floatingips/requests_test.go
++++ /dev/null
+@@ -1,306 +0,0 @@
+-package floatingips
 -
--	r, err := ec2.httpClient.Get(endpoint.String())
--	if err != nil {
--		return err
--	}
--	defer r.Body.Close()
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--	if debug {
--		dump, _ := httputil.DumpResponse(r, true)
--		log.Printf("response:\n")
--		log.Printf("%v\n}\n", string(dump))
--	}
--	if r.StatusCode != 200 {
--		return buildError(r)
--	}
--	err = xml.NewDecoder(r.Body).Decode(resp)
--	return err
--}
+-	fake "github.com/rackspace/gophercloud/openstack/networking/v2/common"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--func multimap(p map[string]string) url.Values {
--	q := make(url.Values, len(p))
--	for k, v := range p {
--		q[k] = []string{v}
--	}
--	return q
--}
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--func buildError(r *http.Response) error {
--	errors := xmlErrors{}
--	xml.NewDecoder(r.Body).Decode(&errors)
--	var err Error
--	if len(errors.Errors) > 0 {
--		err = errors.Errors[0]
--	}
--	err.RequestId = errors.RequestId
--	err.StatusCode = r.StatusCode
--	if err.Message == "" {
--		err.Message = r.Status
--	}
--	return &err
--}
+-	th.Mux.HandleFunc("/v2.0/floatingips", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--func makeParams(action string) map[string]string {
--	params := make(map[string]string)
--	params["Action"] = action
--	return params
--}
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--func addParamsList(params map[string]string, label string, ids []string) {
--	for i, id := range ids {
--		params[label+"."+strconv.Itoa(i+1)] = id
--	}
+-		fmt.Fprintf(w, `
+-{
+-    "floatingips": [
+-        {
+-            "floating_network_id": "6d67c30a-ddb4-49a1-bec3-a65b286b4170",
+-            "router_id": null,
+-            "fixed_ip_address": null,
+-            "floating_ip_address": "192.0.0.4",
+-            "tenant_id": "017d8de156df4177889f31a9bd6edc00",
+-            "status": "DOWN",
+-            "port_id": null,
+-            "id": "2f95fd2b-9f6a-4e8e-9e9a-2cbe286cbf9e"
+-        },
+-        {
+-            "floating_network_id": "90f742b1-6d17-487b-ba95-71881dbc0b64",
+-            "router_id": "0a24cb83-faf5-4d7f-b723-3144ed8a2167",
+-            "fixed_ip_address": "192.0.0.2",
+-            "floating_ip_address": "10.0.0.3",
+-            "tenant_id": "017d8de156df4177889f31a9bd6edc00",
+-            "status": "DOWN",
+-            "port_id": "74a342ce-8e07-4e91-880c-9f834b68fa25",
+-            "id": "ada25a95-f321-4f59-b0e0-f3a970dd3d63"
+-        }
+-    ]
 -}
+-			`)
+-	})
 -
--func addBlockDeviceParams(prename string, params map[string]string, blockdevices []BlockDeviceMapping) {
--	for i, k := range blockdevices {
--		// Fixup index since Amazon counts these from 1
--		prefix := prename + "BlockDeviceMapping." + strconv.Itoa(i+1) + "."
+-	count := 0
 -
--		if k.DeviceName != "" {
--			params[prefix+"DeviceName"] = k.DeviceName
--		}
--		if k.VirtualName != "" {
--			params[prefix+"VirtualName"] = k.VirtualName
--		}
--		if k.SnapshotId != "" {
--			params[prefix+"Ebs.SnapshotId"] = k.SnapshotId
--		}
--		if k.VolumeType != "" {
--			params[prefix+"Ebs.VolumeType"] = k.VolumeType
--		}
--		if k.IOPS != 0 {
--			params[prefix+"Ebs.Iops"] = strconv.FormatInt(k.IOPS, 10)
--		}
--		if k.VolumeSize != 0 {
--			params[prefix+"Ebs.VolumeSize"] = strconv.FormatInt(k.VolumeSize, 10)
--		}
--		if k.DeleteOnTermination {
--			params[prefix+"Ebs.DeleteOnTermination"] = "true"
--		}
--		if k.Encrypted {
--			params[prefix+"Ebs.Encrypted"] = "true"
+-	List(fake.ServiceClient(), ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractFloatingIPs(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract floating IPs: %v", err)
+-			return false, err
 -		}
--		if k.NoDevice {
--			params[prefix+"NoDevice"] = ""
+-
+-		expected := []FloatingIP{
+-			FloatingIP{
+-				FloatingNetworkID: "6d67c30a-ddb4-49a1-bec3-a65b286b4170",
+-				FixedIP:           "",
+-				FloatingIP:        "192.0.0.4",
+-				TenantID:          "017d8de156df4177889f31a9bd6edc00",
+-				Status:            "DOWN",
+-				PortID:            "",
+-				ID:                "2f95fd2b-9f6a-4e8e-9e9a-2cbe286cbf9e",
+-			},
+-			FloatingIP{
+-				FloatingNetworkID: "90f742b1-6d17-487b-ba95-71881dbc0b64",
+-				FixedIP:           "192.0.0.2",
+-				FloatingIP:        "10.0.0.3",
+-				TenantID:          "017d8de156df4177889f31a9bd6edc00",
+-				Status:            "DOWN",
+-				PortID:            "74a342ce-8e07-4e91-880c-9f834b68fa25",
+-				ID:                "ada25a95-f321-4f59-b0e0-f3a970dd3d63",
+-			},
 -		}
--	}
--}
 -
--// ----------------------------------------------------------------------------
--// Instance management functions and types.
+-		th.CheckDeepEquals(t, expected, actual)
 -
--// The RunInstances type encapsulates options for the respective request in EC2.
--//
--// See http://goo.gl/Mcm3b for more details.
--type RunInstances struct {
--	ImageId                  string
--	MinCount                 int
--	MaxCount                 int
--	KeyName                  string
--	InstanceType             string
--	SecurityGroups           []SecurityGroup
--	IamInstanceProfile       string
--	KernelId                 string
--	RamdiskId                string
--	UserData                 []byte
--	AvailZone                string
--	PlacementGroupName       string
--	Monitoring               bool
--	SubnetId                 string
--	AssociatePublicIpAddress bool
--	DisableAPITermination    bool
--	ShutdownBehavior         string
--	PrivateIPAddress         string
--	BlockDevices             []BlockDeviceMapping
--}
+-		return true, nil
+-	})
 -
--// Response to a RunInstances request.
--//
--// See http://goo.gl/Mcm3b for more details.
--type RunInstancesResp struct {
--	RequestId      string          `xml:"requestId"`
--	ReservationId  string          `xml:"reservationId"`
--	OwnerId        string          `xml:"ownerId"`
--	SecurityGroups []SecurityGroup `xml:"groupSet>item"`
--	Instances      []Instance      `xml:"instancesSet>item"`
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
+-	}
 -}
 -
--// Instance encapsulates a running instance in EC2.
--//
--// See http://goo.gl/OCH8a for more details.
--type Instance struct {
--	InstanceId         string          `xml:"instanceId"`
--	InstanceType       string          `xml:"instanceType"`
--	ImageId            string          `xml:"imageId"`
--	PrivateDNSName     string          `xml:"privateDnsName"`
--	DNSName            string          `xml:"dnsName"`
--	KeyName            string          `xml:"keyName"`
--	AMILaunchIndex     int             `xml:"amiLaunchIndex"`
--	Hypervisor         string          `xml:"hypervisor"`
--	VirtType           string          `xml:"virtualizationType"`
--	Monitoring         string          `xml:"monitoring>state"`
--	AvailZone          string          `xml:"placement>availabilityZone"`
--	PlacementGroupName string          `xml:"placement>groupName"`
--	State              InstanceState   `xml:"instanceState"`
--	Tags               []Tag           `xml:"tagSet>item"`
--	VpcId              string          `xml:"vpcId"`
--	SubnetId           string          `xml:"subnetId"`
--	IamInstanceProfile string          `xml:"iamInstanceProfile"`
--	PrivateIpAddress   string          `xml:"privateIpAddress"`
--	PublicIpAddress    string          `xml:"ipAddress"`
--	Architecture       string          `xml:"architecture"`
--	LaunchTime         time.Time       `xml:"launchTime"`
--	SourceDestCheck    bool            `xml:"sourceDestCheck"`
--	SecurityGroups     []SecurityGroup `xml:"groupSet>item"`
+-func TestInvalidNextPageURLs(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/floatingips", func(w http.ResponseWriter, r *http.Request) {
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-		fmt.Fprintf(w, `{"floatingips": [{}], "floatingips_links": {}}`)
+-	})
+-
+-	List(fake.ServiceClient(), ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		ExtractFloatingIPs(page)
+-		return true, nil
+-	})
 -}
 -
--// RunInstances starts new instances in EC2.
--// If options.MinCount and options.MaxCount are both zero, a single instance
--// will be started; otherwise if options.MaxCount is zero, options.MinCount
--// will be used insteead.
--//
--// See http://goo.gl/Mcm3b for more details.
--func (ec2 *EC2) RunInstances(options *RunInstances) (resp *RunInstancesResp, err error) {
--	params := makeParams("RunInstances")
--	params["ImageId"] = options.ImageId
--	params["InstanceType"] = options.InstanceType
--	var min, max int
--	if options.MinCount == 0 && options.MaxCount == 0 {
--		min = 1
--		max = 1
--	} else if options.MaxCount == 0 {
--		min = options.MinCount
--		max = min
--	} else {
--		min = options.MinCount
--		max = options.MaxCount
--	}
--	params["MinCount"] = strconv.Itoa(min)
--	params["MaxCount"] = strconv.Itoa(max)
--	token, err := clientToken()
--	if err != nil {
--		return nil, err
+-func TestRequiredFieldsForCreate(t *testing.T) {
+-	res1 := Create(fake.ServiceClient(), CreateOpts{FloatingNetworkID: ""})
+-	if res1.Err == nil {
+-		t.Fatalf("Expected error, got none")
 -	}
--	params["ClientToken"] = token
 -
--	if options.KeyName != "" {
--		params["KeyName"] = options.KeyName
--	}
--	if options.KernelId != "" {
--		params["KernelId"] = options.KernelId
--	}
--	if options.RamdiskId != "" {
--		params["RamdiskId"] = options.RamdiskId
--	}
--	if options.UserData != nil {
--		userData := make([]byte, b64.EncodedLen(len(options.UserData)))
--		b64.Encode(userData, options.UserData)
--		params["UserData"] = string(userData)
--	}
--	if options.AvailZone != "" {
--		params["Placement.AvailabilityZone"] = options.AvailZone
--	}
--	if options.PlacementGroupName != "" {
--		params["Placement.GroupName"] = options.PlacementGroupName
+-	res2 := Create(fake.ServiceClient(), CreateOpts{FloatingNetworkID: "foo", PortID: ""})
+-	if res2.Err == nil {
+-		t.Fatalf("Expected error, got none")
 -	}
--	if options.Monitoring {
--		params["Monitoring.Enabled"] = "true"
--	}
--	if options.SubnetId != "" && options.AssociatePublicIpAddress {
--		// If we have a non-default VPC / Subnet specified, we can flag
--		// AssociatePublicIpAddress to get a Public IP assigned. By default these are not provided.
--		// You cannot specify both SubnetId and the NetworkInterface.0.* parameters though, otherwise
--		// you get: Network interfaces and an instance-level subnet ID may not be specified on the same request
--		// You also need to attach Security Groups to the NetworkInterface instead of the instance,
--		// to avoid: Network interfaces and an instance-level security groups may not be specified on
--		// the same request
--		params["NetworkInterface.0.DeviceIndex"] = "0"
--		params["NetworkInterface.0.AssociatePublicIpAddress"] = "true"
--		params["NetworkInterface.0.SubnetId"] = options.SubnetId
--
--		i := 1
--		for _, g := range options.SecurityGroups {
--			// We only have SecurityGroupId's on NetworkInterface's, no SecurityGroup params.
--			if g.Id != "" {
--				params["NetworkInterface.0.SecurityGroupId."+strconv.Itoa(i)] = g.Id
--				i++
--			}
--		}
--	} else {
--		if options.SubnetId != "" {
--			params["SubnetId"] = options.SubnetId
--		}
+-}
 -
--		i, j := 1, 1
--		for _, g := range options.SecurityGroups {
--			if g.Id != "" {
--				params["SecurityGroupId."+strconv.Itoa(i)] = g.Id
--				i++
--			} else {
--				params["SecurityGroup."+strconv.Itoa(j)] = g.Name
--				j++
--			}
--		}
--	}
--	if options.IamInstanceProfile != "" {
--		params["IamInstanceProfile.Name"] = options.IamInstanceProfile
--	}
--	if options.DisableAPITermination {
--		params["DisableApiTermination"] = "true"
--	}
--	if options.ShutdownBehavior != "" {
--		params["InstanceInitiatedShutdownBehavior"] = options.ShutdownBehavior
--	}
--	if options.PrivateIPAddress != "" {
--		params["PrivateIpAddress"] = options.PrivateIPAddress
--	}
--	addBlockDeviceParams("", params, options.BlockDevices)
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/floatingips", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "floatingip": {
+-        "floating_network_id": "376da547-b977-4cfe-9cba-275c80debf57",
+-        "port_id": "ce705c24-c1ef-408a-bda3-7bbd946164ab"
+-    }
+-}
+-			`)
 -
--	resp = &RunInstancesResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "floatingip": {
+-        "router_id": "d23abc8d-2991-4a55-ba98-2aaea84cc72f",
+-        "tenant_id": "4969c491a3c74ee4af974e6d800c62de",
+-        "floating_network_id": "376da547-b977-4cfe-9cba-275c80debf57",
+-        "fixed_ip_address": "10.0.0.3",
+-        "floating_ip_address": "",
+-        "port_id": "ce705c24-c1ef-408a-bda3-7bbd946164ab",
+-        "id": "2f245a7b-796b-4f26-9cf9-9e82d248fda7"
+-    }
+-}
+-		`)
+-	})
+-
+-	options := CreateOpts{
+-		FloatingNetworkID: "376da547-b977-4cfe-9cba-275c80debf57",
+-		PortID:            "ce705c24-c1ef-408a-bda3-7bbd946164ab",
 -	}
--	return
+-
+-	ip, err := Create(fake.ServiceClient(), options).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, "2f245a7b-796b-4f26-9cf9-9e82d248fda7", ip.ID)
+-	th.AssertEquals(t, "4969c491a3c74ee4af974e6d800c62de", ip.TenantID)
+-	th.AssertEquals(t, "376da547-b977-4cfe-9cba-275c80debf57", ip.FloatingNetworkID)
+-	th.AssertEquals(t, "", ip.FloatingIP)
+-	th.AssertEquals(t, "ce705c24-c1ef-408a-bda3-7bbd946164ab", ip.PortID)
+-	th.AssertEquals(t, "10.0.0.3", ip.FixedIP)
 -}
 -
--func clientToken() (string, error) {
--	// Maximum EC2 client token size is 64 bytes.
--	// Each byte expands to two when hex encoded.
--	buf := make([]byte, 32)
--	_, err := rand.Read(buf)
--	if err != nil {
--		return "", err
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/floatingips/2f245a7b-796b-4f26-9cf9-9e82d248fda7", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "floatingip": {
+-        "floating_network_id": "90f742b1-6d17-487b-ba95-71881dbc0b64",
+-        "fixed_ip_address": "192.0.0.2",
+-        "floating_ip_address": "10.0.0.3",
+-        "tenant_id": "017d8de156df4177889f31a9bd6edc00",
+-        "status": "DOWN",
+-        "port_id": "74a342ce-8e07-4e91-880c-9f834b68fa25",
+-        "id": "2f245a7b-796b-4f26-9cf9-9e82d248fda7"
+-    }
+-}
+-      `)
+-	})
+-
+-	ip, err := Get(fake.ServiceClient(), "2f245a7b-796b-4f26-9cf9-9e82d248fda7").Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, "90f742b1-6d17-487b-ba95-71881dbc0b64", ip.FloatingNetworkID)
+-	th.AssertEquals(t, "10.0.0.3", ip.FloatingIP)
+-	th.AssertEquals(t, "74a342ce-8e07-4e91-880c-9f834b68fa25", ip.PortID)
+-	th.AssertEquals(t, "192.0.0.2", ip.FixedIP)
+-	th.AssertEquals(t, "017d8de156df4177889f31a9bd6edc00", ip.TenantID)
+-	th.AssertEquals(t, "DOWN", ip.Status)
+-	th.AssertEquals(t, "2f245a7b-796b-4f26-9cf9-9e82d248fda7", ip.ID)
+-}
+-
+-func TestAssociate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/floatingips/2f245a7b-796b-4f26-9cf9-9e82d248fda7", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-	"floatingip": {
+-		"port_id": "423abc8d-2991-4a55-ba98-2aaea84cc72e"
 -	}
--	return hex.EncodeToString(buf), nil
 -}
+-		`)
 -
--// ----------------------------------------------------------------------------
--// Spot Instance management functions and types.
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--// The RequestSpotInstances type encapsulates options for the respective request in EC2.
--//
--// See http://goo.gl/GRZgCD for more details.
--type RequestSpotInstances struct {
--	SpotPrice                string
--	InstanceCount            int
--	Type                     string
--	ImageId                  string
--	KeyName                  string
--	InstanceType             string
--	SecurityGroups           []SecurityGroup
--	IamInstanceProfile       string
--	KernelId                 string
--	RamdiskId                string
--	UserData                 []byte
--	AvailZone                string
--	PlacementGroupName       string
--	Monitoring               bool
--	SubnetId                 string
--	AssociatePublicIpAddress bool
--	PrivateIPAddress         string
--	BlockDevices             []BlockDeviceMapping
+-		fmt.Fprintf(w, `
+-{
+-	"floatingip": {
+-			"router_id": "d23abc8d-2991-4a55-ba98-2aaea84cc72f",
+-			"tenant_id": "4969c491a3c74ee4af974e6d800c62de",
+-			"floating_network_id": "376da547-b977-4cfe-9cba-275c80debf57",
+-			"fixed_ip_address": null,
+-			"floating_ip_address": "172.24.4.228",
+-			"port_id": "423abc8d-2991-4a55-ba98-2aaea84cc72e",
+-			"id": "2f245a7b-796b-4f26-9cf9-9e82d248fda7"
+-	}
 -}
+-	`)
+-	})
 -
--type SpotInstanceSpec struct {
--	ImageId                  string
--	KeyName                  string
--	InstanceType             string
--	SecurityGroups           []SecurityGroup
--	IamInstanceProfile       string
--	KernelId                 string
--	RamdiskId                string
--	UserData                 []byte
--	AvailZone                string
--	PlacementGroupName       string
--	Monitoring               bool
--	SubnetId                 string
--	AssociatePublicIpAddress bool
--	PrivateIPAddress         string
--	BlockDevices             []BlockDeviceMapping
+-	ip, err := Update(fake.ServiceClient(), "2f245a7b-796b-4f26-9cf9-9e82d248fda7", UpdateOpts{PortID: "423abc8d-2991-4a55-ba98-2aaea84cc72e"}).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertDeepEquals(t, "423abc8d-2991-4a55-ba98-2aaea84cc72e", ip.PortID)
 -}
 -
--type SpotLaunchSpec struct {
--	ImageId            string               `xml:"imageId"`
--	KeyName            string               `xml:"keyName"`
--	InstanceType       string               `xml:"instanceType"`
--	SecurityGroups     []SecurityGroup      `xml:"groupSet>item"`
--	IamInstanceProfile string               `xml:"iamInstanceProfile"`
--	KernelId           string               `xml:"kernelId"`
--	RamdiskId          string               `xml:"ramdiskId"`
--	PlacementGroupName string               `xml:"placement>groupName"`
--	Monitoring         bool                 `xml:"monitoring>enabled"`
--	SubnetId           string               `xml:"subnetId"`
--	BlockDevices       []BlockDeviceMapping `xml:"blockDeviceMapping>item"`
+-func TestDisassociate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/floatingips/2f245a7b-796b-4f26-9cf9-9e82d248fda7", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "floatingip": {
+-      "port_id": null
+-    }
 -}
+-      `)
 -
--type SpotStatus struct {
--	Code       string `xml:"code"`
--	UpdateTime string `xml:"updateTime"`
--	Message    string `xml:"message"`
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "floatingip": {
+-        "router_id": "d23abc8d-2991-4a55-ba98-2aaea84cc72f",
+-        "tenant_id": "4969c491a3c74ee4af974e6d800c62de",
+-        "floating_network_id": "376da547-b977-4cfe-9cba-275c80debf57",
+-        "fixed_ip_address": null,
+-        "floating_ip_address": "172.24.4.228",
+-        "port_id": null,
+-        "id": "2f245a7b-796b-4f26-9cf9-9e82d248fda7"
+-    }
 -}
+-    `)
+-	})
 -
--type SpotRequestResult struct {
--	SpotRequestId  string         `xml:"spotInstanceRequestId"`
--	SpotPrice      string         `xml:"spotPrice"`
--	Type           string         `xml:"type"`
--	AvailZone      string         `xml:"launchedAvailabilityZone"`
--	InstanceId     string         `xml:"instanceId"`
--	State          string         `xml:"state"`
--	Status         SpotStatus     `xml:"status"`
--	SpotLaunchSpec SpotLaunchSpec `xml:"launchSpecification"`
--	CreateTime     string         `xml:"createTime"`
--	Tags           []Tag          `xml:"tagSet>item"`
+-	ip, err := Update(fake.ServiceClient(), "2f245a7b-796b-4f26-9cf9-9e82d248fda7", UpdateOpts{}).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertDeepEquals(t, "", ip.FixedIP)
+-	th.AssertDeepEquals(t, "", ip.PortID)
 -}
 -
--// Response to a RequestSpotInstances request.
--//
--// See http://goo.gl/GRZgCD for more details.
--type RequestSpotInstancesResp struct {
--	RequestId          string              `xml:"requestId"`
--	SpotRequestResults []SpotRequestResult `xml:"spotInstanceRequestSet>item"`
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/floatingips/2f245a7b-796b-4f26-9cf9-9e82d248fda7", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-
+-	res := Delete(fake.ServiceClient(), "2f245a7b-796b-4f26-9cf9-9e82d248fda7")
+-	th.AssertNoErr(t, res.Err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/floatingips/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/floatingips/results.go
+deleted file mode 100644
+index a1c7afe..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/floatingips/results.go
++++ /dev/null
+@@ -1,127 +0,0 @@
+-package floatingips
 -
--// RequestSpotInstances requests a new spot instances in EC2.
--func (ec2 *EC2) RequestSpotInstances(options *RequestSpotInstances) (resp *RequestSpotInstancesResp, err error) {
--	params := makeParams("RequestSpotInstances")
--	prefix := "LaunchSpecification" + "."
+-import (
+-	"fmt"
 -
--	params["SpotPrice"] = options.SpotPrice
--	params[prefix+"ImageId"] = options.ImageId
--	params[prefix+"InstanceType"] = options.InstanceType
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	if options.InstanceCount != 0 {
--		params["InstanceCount"] = strconv.Itoa(options.InstanceCount)
--	}
--	if options.KeyName != "" {
--		params[prefix+"KeyName"] = options.KeyName
--	}
--	if options.KernelId != "" {
--		params[prefix+"KernelId"] = options.KernelId
--	}
--	if options.RamdiskId != "" {
--		params[prefix+"RamdiskId"] = options.RamdiskId
--	}
--	if options.UserData != nil {
--		userData := make([]byte, b64.EncodedLen(len(options.UserData)))
--		b64.Encode(userData, options.UserData)
--		params[prefix+"UserData"] = string(userData)
--	}
--	if options.AvailZone != "" {
--		params[prefix+"Placement.AvailabilityZone"] = options.AvailZone
--	}
--	if options.PlacementGroupName != "" {
--		params[prefix+"Placement.GroupName"] = options.PlacementGroupName
--	}
--	if options.Monitoring {
--		params[prefix+"Monitoring.Enabled"] = "true"
--	}
--	if options.SubnetId != "" && options.AssociatePublicIpAddress {
--		// If we have a non-default VPC / Subnet specified, we can flag
--		// AssociatePublicIpAddress to get a Public IP assigned. By default these are not provided.
--		// You cannot specify both SubnetId and the NetworkInterface.0.* parameters though, otherwise
--		// you get: Network interfaces and an instance-level subnet ID may not be specified on the same request
--		// You also need to attach Security Groups to the NetworkInterface instead of the instance,
--		// to avoid: Network interfaces and an instance-level security groups may not be specified on
--		// the same request
--		params[prefix+"NetworkInterface.0.DeviceIndex"] = "0"
--		params[prefix+"NetworkInterface.0.AssociatePublicIpAddress"] = "true"
--		params[prefix+"NetworkInterface.0.SubnetId"] = options.SubnetId
+-// FloatingIP represents a floating IP resource. A floating IP is an external
+-// IP address that is mapped to an internal port and, optionally, a specific
+-// IP address on a private network. In other words, it enables access to an
+-// instance on a private network from an external network. For this reason,
+-// floating IPs can only be defined on networks where the `router:external'
+-// attribute (provided by the external network extension) is set to True.
+-type FloatingIP struct {
+-	// Unique identifier for the floating IP instance.
+-	ID string `json:"id" mapstructure:"id"`
 -
--		i := 1
--		for _, g := range options.SecurityGroups {
--			// We only have SecurityGroupId's on NetworkInterface's, no SecurityGroup params.
--			if g.Id != "" {
--				params[prefix+"NetworkInterface.0.SecurityGroupId."+strconv.Itoa(i)] = g.Id
--				i++
--			}
--		}
--	} else {
--		if options.SubnetId != "" {
--			params[prefix+"SubnetId"] = options.SubnetId
--		}
+-	// UUID of the external network where the floating IP is to be created.
+-	FloatingNetworkID string `json:"floating_network_id" mapstructure:"floating_network_id"`
 -
--		i, j := 1, 1
--		for _, g := range options.SecurityGroups {
--			if g.Id != "" {
--				params[prefix+"SecurityGroupId."+strconv.Itoa(i)] = g.Id
--				i++
--			} else {
--				params[prefix+"SecurityGroup."+strconv.Itoa(j)] = g.Name
--				j++
--			}
--		}
--	}
--	if options.IamInstanceProfile != "" {
--		params[prefix+"IamInstanceProfile.Name"] = options.IamInstanceProfile
+-	// Address of the floating IP on the external network.
+-	FloatingIP string `json:"floating_ip_address" mapstructure:"floating_ip_address"`
+-
+-	// UUID of the port on an internal network that is associated with the floating IP.
+-	PortID string `json:"port_id" mapstructure:"port_id"`
+-
+-	// The specific IP address of the internal port which should be associated
+-	// with the floating IP.
+-	FixedIP string `json:"fixed_ip_address" mapstructure:"fixed_ip_address"`
+-
+-	// Owner of the floating IP. Only admin users can specify a tenant identifier
+-	// other than its own.
+-	TenantID string `json:"tenant_id" mapstructure:"tenant_id"`
+-
+-	// The condition of the API resource.
+-	Status string `json:"status" mapstructure:"status"`
+-}
+-
+-type commonResult struct {
+-	gophercloud.Result
+-}
+-
+-// Extract a result and extracts a FloatingIP resource.
+-func (r commonResult) Extract() (*FloatingIP, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
 -	}
--	if options.PrivateIPAddress != "" {
--		params[prefix+"PrivateIpAddress"] = options.PrivateIPAddress
+-
+-	var res struct {
+-		FloatingIP *FloatingIP `json:"floatingip"`
 -	}
--	addBlockDeviceParams(prefix, params, options.BlockDevices)
 -
--	resp = &RequestSpotInstancesResp{}
--	err = ec2.query(params, resp)
+-	err := mapstructure.Decode(r.Body, &res)
 -	if err != nil {
--		return nil, err
+-		return nil, fmt.Errorf("Error decoding Neutron floating IP: %v", err)
 -	}
--	return
+-
+-	return res.FloatingIP, nil
 -}
 -
--// Response to a DescribeSpotInstanceRequests request.
--//
--// See http://goo.gl/KsKJJk for more details.
--type SpotRequestsResp struct {
--	RequestId          string              `xml:"requestId"`
--	SpotRequestResults []SpotRequestResult `xml:"spotInstanceRequestSet>item"`
+-// CreateResult represents the result of a create operation.
+-type CreateResult struct {
+-	commonResult
 -}
 -
--// DescribeSpotInstanceRequests returns details about spot requests in EC2.  Both parameters
--// are optional, and if provided will limit the spot requests returned to those
--// matching the given spot request ids or filtering rules.
--//
--// See http://goo.gl/KsKJJk for more details.
--func (ec2 *EC2) DescribeSpotRequests(spotrequestIds []string, filter *Filter) (resp *SpotRequestsResp, err error) {
--	params := makeParams("DescribeSpotInstanceRequests")
--	addParamsList(params, "SpotInstanceRequestId", spotrequestIds)
--	filter.addParams(params)
--	resp = &SpotRequestsResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return
+-// GetResult represents the result of a get operation.
+-type GetResult struct {
+-	commonResult
 -}
 -
--// Response to a CancelSpotInstanceRequests request.
--//
--// See http://goo.gl/3BKHj for more details.
--type CancelSpotRequestResult struct {
--	SpotRequestId string `xml:"spotInstanceRequestId"`
--	State         string `xml:"state"`
+-// UpdateResult represents the result of an update operation.
+-type UpdateResult struct {
+-	commonResult
 -}
--type CancelSpotRequestsResp struct {
--	RequestId                string                    `xml:"requestId"`
--	CancelSpotRequestResults []CancelSpotRequestResult `xml:"spotInstanceRequestSet>item"`
+-
+-// DeleteResult represents the result of an update operation.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
 -}
 -
--// CancelSpotRequests requests the cancellation of spot requests when the given ids.
--//
--// See http://goo.gl/3BKHj for more details.
--func (ec2 *EC2) CancelSpotRequests(spotrequestIds []string) (resp *CancelSpotRequestsResp, err error) {
--	params := makeParams("CancelSpotInstanceRequests")
--	addParamsList(params, "SpotInstanceRequestId", spotrequestIds)
--	resp = &CancelSpotRequestsResp{}
--	err = ec2.query(params, resp)
+-// FloatingIPPage is the page returned by a pager when traversing over a
+-// collection of floating IPs.
+-type FloatingIPPage struct {
+-	pagination.LinkedPageBase
+-}
+-
+-// NextPageURL is invoked when a paginated collection of floating IPs has reached
+-// the end of a page and the pager seeks to traverse over a new one. In order
+-// to do this, it needs to construct the next page's URL.
+-func (p FloatingIPPage) NextPageURL() (string, error) {
+-	type resp struct {
+-		Links []gophercloud.Link `mapstructure:"floatingips_links"`
+-	}
+-
+-	var r resp
+-	err := mapstructure.Decode(p.Body, &r)
 -	if err != nil {
--		return nil, err
+-		return "", err
 -	}
--	return
+-
+-	return gophercloud.ExtractNextURL(r.Links)
 -}
 -
--// Response to a TerminateInstances request.
--//
--// See http://goo.gl/3BKHj for more details.
--type TerminateInstancesResp struct {
--	RequestId    string                `xml:"requestId"`
--	StateChanges []InstanceStateChange `xml:"instancesSet>item"`
+-// IsEmpty checks whether a NetworkPage struct is empty.
+-func (p FloatingIPPage) IsEmpty() (bool, error) {
+-	is, err := ExtractFloatingIPs(p)
+-	if err != nil {
+-		return true, nil
+-	}
+-	return len(is) == 0, nil
 -}
 -
--// InstanceState encapsulates the state of an instance in EC2.
--//
--// See http://goo.gl/y3ZBq for more details.
--type InstanceState struct {
--	Code int    `xml:"code"` // Watch out, bits 15-8 have unpublished meaning.
--	Name string `xml:"name"`
+-// ExtractFloatingIPs accepts a Page struct, specifically a FloatingIPPage struct,
+-// and extracts the elements into a slice of FloatingIP structs. In other words,
+-// a generic collection is mapped into a relevant slice.
+-func ExtractFloatingIPs(page pagination.Page) ([]FloatingIP, error) {
+-	var resp struct {
+-		FloatingIPs []FloatingIP `mapstructure:"floatingips" json:"floatingips"`
+-	}
+-
+-	err := mapstructure.Decode(page.(FloatingIPPage).Body, &resp)
+-
+-	return resp.FloatingIPs, err
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/floatingips/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/floatingips/urls.go
+deleted file mode 100644
+index 355f20d..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/floatingips/urls.go
++++ /dev/null
+@@ -1,13 +0,0 @@
+-package floatingips
 -
--// InstanceStateChange informs of the previous and current states
--// for an instance when a state change is requested.
--type InstanceStateChange struct {
--	InstanceId    string        `xml:"instanceId"`
--	CurrentState  InstanceState `xml:"currentState"`
--	PreviousState InstanceState `xml:"previousState"`
+-import "github.com/rackspace/gophercloud"
+-
+-const resourcePath = "floatingips"
+-
+-func rootURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL(resourcePath)
 -}
 -
--// TerminateInstances requests the termination of instances when the given ids.
--//
--// See http://goo.gl/3BKHj for more details.
--func (ec2 *EC2) TerminateInstances(instIds []string) (resp *TerminateInstancesResp, err error) {
--	params := makeParams("TerminateInstances")
--	addParamsList(params, "InstanceId", instIds)
--	resp = &TerminateInstancesResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return
+-func resourceURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL(resourcePath, id)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/routers/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/routers/requests.go
+deleted file mode 100644
+index e3a1441..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/routers/requests.go
++++ /dev/null
+@@ -1,246 +0,0 @@
+-package routers
 -
--// Response to a DescribeInstances request.
--//
--// See http://goo.gl/mLbmw for more details.
--type InstancesResp struct {
--	RequestId    string        `xml:"requestId"`
--	Reservations []Reservation `xml:"reservationSet>item"`
+-import (
+-	"errors"
+-
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
+-
+-// ListOpts allows the filtering and sorting of paginated collections through
+-// the API. Filtering is achieved by passing in struct field values that map to
+-// the floating IP attributes you want to see returned. SortKey allows you to
+-// sort by a particular network attribute. SortDir sets the direction, and is
+-// either `asc' or `desc'. Marker and Limit are used for pagination.
+-type ListOpts struct {
+-	ID           string `q:"id"`
+-	Name         string `q:"name"`
+-	AdminStateUp *bool  `q:"admin_state_up"`
+-	Status       string `q:"status"`
+-	TenantID     string `q:"tenant_id"`
+-	Limit        int    `q:"limit"`
+-	Marker       string `q:"marker"`
+-	SortKey      string `q:"sort_key"`
+-	SortDir      string `q:"sort_dir"`
+-}
+-
+-// List returns a Pager which allows you to iterate over a collection of
+-// routers. It accepts a ListOpts struct, which allows you to filter and sort
+-// the returned collection for greater efficiency.
+-//
+-// Default policy settings return only those routers that are owned by the
+-// tenant who submits the request, unless an admin user submits the request.
+-func List(c *gophercloud.ServiceClient, opts ListOpts) pagination.Pager {
+-	q, err := gophercloud.BuildQueryString(&opts)
+-	if err != nil {
+-		return pagination.Pager{Err: err}
+-	}
+-	u := rootURL(c) + q.String()
+-	return pagination.NewPager(c, u, func(r pagination.PageResult) pagination.Page {
+-		return RouterPage{pagination.LinkedPageBase{PageResult: r}}
+-	})
 -}
 -
--// Reservation represents details about a reservation in EC2.
--//
--// See http://goo.gl/0ItPT for more details.
--type Reservation struct {
--	ReservationId  string          `xml:"reservationId"`
--	OwnerId        string          `xml:"ownerId"`
--	RequesterId    string          `xml:"requesterId"`
--	SecurityGroups []SecurityGroup `xml:"groupSet>item"`
--	Instances      []Instance      `xml:"instancesSet>item"`
+-// CreateOpts contains all the values needed to create a new router. There are
+-// no required values.
+-type CreateOpts struct {
+-	Name         string
+-	AdminStateUp *bool
+-	TenantID     string
+-	GatewayInfo  *GatewayInfo
 -}
 -
--// Instances returns details about instances in EC2.  Both parameters
--// are optional, and if provided will limit the instances returned to those
--// matching the given instance ids or filtering rules.
+-// Create accepts a CreateOpts struct and uses the values to create a new
+-// logical router. When it is created, the router does not have an internal
+-// interface - it is not associated to any subnet.
 -//
--// See http://goo.gl/4No7c for more details.
--func (ec2 *EC2) Instances(instIds []string, filter *Filter) (resp *InstancesResp, err error) {
--	params := makeParams("DescribeInstances")
--	addParamsList(params, "InstanceId", instIds)
--	filter.addParams(params)
--	resp = &InstancesResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
+-// You can optionally specify an external gateway for a router using the
+-// GatewayInfo struct. The external gateway for the router must be plugged into
+-// an external network (it is external if its `router:external' field is set to
+-// true).
+-func Create(c *gophercloud.ServiceClient, opts CreateOpts) CreateResult {
+-	type router struct {
+-		Name         *string      `json:"name,omitempty"`
+-		AdminStateUp *bool        `json:"admin_state_up,omitempty"`
+-		TenantID     *string      `json:"tenant_id,omitempty"`
+-		GatewayInfo  *GatewayInfo `json:"external_gateway_info,omitempty"`
 -	}
--	return
--}
 -
--// ----------------------------------------------------------------------------
--// Volume management
+-	type request struct {
+-		Router router `json:"router"`
+-	}
 -
--// The CreateVolume request parameters
--//
--// See http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-CreateVolume.html
--type CreateVolume struct {
--	AvailZone  string
--	Size       int64
--	SnapshotId string
--	VolumeType string
--	IOPS       int64
--	Encrypted  bool
+-	reqBody := request{Router: router{
+-		Name:         gophercloud.MaybeString(opts.Name),
+-		AdminStateUp: opts.AdminStateUp,
+-		TenantID:     gophercloud.MaybeString(opts.TenantID),
+-	}}
+-
+-	if opts.GatewayInfo != nil {
+-		reqBody.Router.GatewayInfo = opts.GatewayInfo
+-	}
+-
+-	var res CreateResult
+-	_, res.Err = perigee.Request("POST", rootURL(c), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{201},
+-	})
+-	return res
 -}
 -
--// Response to an AttachVolume request
--type AttachVolumeResp struct {
--	RequestId  string `xml:"requestId"`
--	VolumeId   string `xml:"volumeId"`
--	InstanceId string `xml:"instanceId"`
--	Device     string `xml:"device"`
--	Status     string `xml:"status"`
--	AttachTime string `xml:"attachTime"`
+-// Get retrieves a particular router based on its unique ID.
+-func Get(c *gophercloud.ServiceClient, id string) GetResult {
+-	var res GetResult
+-	_, res.Err = perigee.Request("GET", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return res
 -}
 -
--// Response to a CreateVolume request
--type CreateVolumeResp struct {
--	RequestId  string `xml:"requestId"`
--	VolumeId   string `xml:"volumeId"`
--	Size       int64  `xml:"size"`
--	SnapshotId string `xml:"snapshotId"`
--	AvailZone  string `xml:"availabilityZone"`
--	Status     string `xml:"status"`
--	CreateTime string `xml:"createTime"`
--	VolumeType string `xml:"volumeType"`
--	IOPS       int64  `xml:"iops"`
--	Encrypted  bool   `xml:"encrypted"`
+-// UpdateOpts contains the values used when updating a router.
+-type UpdateOpts struct {
+-	Name         string
+-	AdminStateUp *bool
+-	GatewayInfo  *GatewayInfo
 -}
 -
--// Volume is a single volume.
--type Volume struct {
--	VolumeId    string             `xml:"volumeId"`
--	Size        string             `xml:"size"`
--	SnapshotId  string             `xml:"snapshotId"`
--	AvailZone   string             `xml:"availabilityZone"`
--	Status      string             `xml:"status"`
--	Attachments []VolumeAttachment `xml:"attachmentSet>item"`
--	VolumeType  string             `xml:"volumeType"`
--	IOPS        int64              `xml:"iops"`
--	Encrypted   bool               `xml:"encrypted"`
--	Tags        []Tag              `xml:"tagSet>item"`
+-// Update allows routers to be updated. You can update the name, administrative
+-// state, and the external gateway. For more information about how to set the
+-// external gateway for a router, see Create. This operation does not enable
+-// the update of router interfaces. To do this, use the AddInterface and
+-// RemoveInterface functions.
+-func Update(c *gophercloud.ServiceClient, id string, opts UpdateOpts) UpdateResult {
+-	type router struct {
+-		Name         *string      `json:"name,omitempty"`
+-		AdminStateUp *bool        `json:"admin_state_up,omitempty"`
+-		GatewayInfo  *GatewayInfo `json:"external_gateway_info,omitempty"`
+-	}
+-
+-	type request struct {
+-		Router router `json:"router"`
+-	}
+-
+-	reqBody := request{Router: router{
+-		Name:         gophercloud.MaybeString(opts.Name),
+-		AdminStateUp: opts.AdminStateUp,
+-	}}
+-
+-	if opts.GatewayInfo != nil {
+-		reqBody.Router.GatewayInfo = opts.GatewayInfo
+-	}
+-
+-	// Send request to API
+-	var res UpdateResult
+-	_, res.Err = perigee.Request("PUT", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
+-
+-	return res
 -}
 -
--type VolumeAttachment struct {
--	VolumeId   string `xml:"volumeId"`
--	InstanceId string `xml:"instanceId"`
--	Device     string `xml:"device"`
--	Status     string `xml:"status"`
+-// Delete will permanently delete a particular router based on its unique ID.
+-func Delete(c *gophercloud.ServiceClient, id string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{204},
+-	})
+-	return res
 -}
 -
--// Response to a DescribeVolumes request
--type VolumesResp struct {
--	RequestId string   `xml:"requestId"`
--	Volumes   []Volume `xml:"volumeSet>item"`
+-var errInvalidInterfaceOpts = errors.New("When adding a router interface you must provide either a subnet ID or a port ID")
+-
+-// InterfaceOpts allow you to work with operations that either add or remote
+-// an internal interface from a router.
+-type InterfaceOpts struct {
+-	SubnetID string
+-	PortID   string
 -}
 -
--// Attach a volume.
--func (ec2 *EC2) AttachVolume(volumeId string, instanceId string, device string) (resp *AttachVolumeResp, err error) {
--	params := makeParams("AttachVolume")
--	params["VolumeId"] = volumeId
--	params["InstanceId"] = instanceId
--	params["Device"] = device
+-// AddInterface attaches a subnet to an internal router interface. You must
+-// specify either a SubnetID or PortID in the request body. If you specify both,
+-// the operation will fail and an error will be returned.
+-//
+-// If you specify a SubnetID, the gateway IP address for that particular subnet
+-// is used to create the router interface. Alternatively, if you specify a
+-// PortID, the IP address associated with the port is used to create the router
+-// interface.
+-//
+-// If you reference a port that is associated with multiple IP addresses, or
+-// if the port is associated with zero IP addresses, the operation will fail and
+-// a 400 Bad Request error will be returned.
+-//
+-// If you reference a port already in use, the operation will fail and a 409
+-// Conflict error will be returned.
+-//
+-// The PortID that is returned after using Extract() on the result of this
+-// operation can either be the same PortID passed in or, on the other hand, the
+-// identifier of a new port created by this operation. After the operation
+-// completes, the device ID of the port is set to the router ID, and the
+-// device owner attribute is set to `network:router_interface'.
+-func AddInterface(c *gophercloud.ServiceClient, id string, opts InterfaceOpts) InterfaceResult {
+-	var res InterfaceResult
 -
--	resp = &AttachVolumeResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
+-	// Validate
+-	if (opts.SubnetID == "" && opts.PortID == "") || (opts.SubnetID != "" && opts.PortID != "") {
+-		res.Err = errInvalidInterfaceOpts
+-		return res
 -	}
 -
--	return
+-	type request struct {
+-		SubnetID string `json:"subnet_id,omitempty"`
+-		PortID   string `json:"port_id,omitempty"`
+-	}
+-
+-	body := request{SubnetID: opts.SubnetID, PortID: opts.PortID}
+-
+-	_, res.Err = perigee.Request("PUT", addInterfaceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &body,
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
+-
+-	return res
 -}
 -
--// Create a new volume.
--func (ec2 *EC2) CreateVolume(options *CreateVolume) (resp *CreateVolumeResp, err error) {
--	params := makeParams("CreateVolume")
--	params["AvailabilityZone"] = options.AvailZone
--	if options.Size > 0 {
--		params["Size"] = strconv.FormatInt(options.Size, 10)
--	}
+-// RemoveInterface removes an internal router interface, which detaches a
+-// subnet from the router. You must specify either a SubnetID or PortID, since
+-// these values are used to identify the router interface to remove.
+-//
+-// Unlike AddInterface, you can also specify both a SubnetID and PortID. If you
+-// choose to specify both, the subnet ID must correspond to the subnet ID of
+-// the first IP address on the port specified by the port ID. Otherwise, the
+-// operation will fail and return a 409 Conflict error.
+-//
+-// If the router, subnet or port which are referenced do not exist or are not
+-// visible to you, the operation will fail and a 404 Not Found error will be
+-// returned. After this operation completes, the port connecting the router
+-// with the subnet is removed from the subnet for the network.
+-func RemoveInterface(c *gophercloud.ServiceClient, id string, opts InterfaceOpts) InterfaceResult {
+-	var res InterfaceResult
 -
--	if options.SnapshotId != "" {
--		params["SnapshotId"] = options.SnapshotId
+-	type request struct {
+-		SubnetID string `json:"subnet_id,omitempty"`
+-		PortID   string `json:"port_id,omitempty"`
 -	}
 -
--	if options.VolumeType != "" {
--		params["VolumeType"] = options.VolumeType
--	}
+-	body := request{SubnetID: opts.SubnetID, PortID: opts.PortID}
 -
--	if options.IOPS > 0 {
--		params["Iops"] = strconv.FormatInt(options.IOPS, 10)
--	}
+-	_, res.Err = perigee.Request("PUT", removeInterfaceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &body,
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
 -
--	if options.Encrypted {
--		params["Encrypted"] = "true"
--	}
+-	return res
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/routers/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/routers/requests_test.go
+deleted file mode 100644
+index c34264d..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/routers/requests_test.go
++++ /dev/null
+@@ -1,338 +0,0 @@
+-package routers
 -
--	resp = &CreateVolumeResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--	return
+-	fake "github.com/rackspace/gophercloud/openstack/networking/v2/common"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestURLs(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.AssertEquals(t, th.Endpoint()+"v2.0/routers", rootURL(fake.ServiceClient()))
 -}
 -
--// Delete an EBS volume.
--func (ec2 *EC2) DeleteVolume(id string) (resp *SimpleResp, err error) {
--	params := makeParams("DeleteVolume")
--	params["VolumeId"] = id
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return
+-	th.Mux.HandleFunc("/v2.0/routers", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "routers": [
+-        {
+-            "status": "ACTIVE",
+-            "external_gateway_info": null,
+-            "name": "second_routers",
+-            "admin_state_up": true,
+-            "tenant_id": "6b96ff0cb17a4b859e1e575d221683d3",
+-            "id": "7177abc4-5ae9-4bb7-b0d4-89e94a4abf3b"
+-        },
+-        {
+-            "status": "ACTIVE",
+-            "external_gateway_info": {
+-                "network_id": "3c5bcddd-6af9-4e6b-9c3e-c153e521cab8"
+-            },
+-            "name": "router1",
+-            "admin_state_up": true,
+-            "tenant_id": "33a40233088643acb66ff6eb0ebea679",
+-            "id": "a9254bdb-2613-4a13-ac4c-adc581fba50d"
+-        }
+-    ]
 -}
+-			`)
+-	})
 -
--// Detaches an EBS volume.
--func (ec2 *EC2) DetachVolume(id string) (resp *SimpleResp, err error) {
--	params := makeParams("DetachVolume")
--	params["VolumeId"] = id
+-	count := 0
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
+-	List(fake.ServiceClient(), ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractRouters(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract routers: %v", err)
+-			return false, err
+-		}
+-
+-		expected := []Router{
+-			Router{
+-				Status:       "ACTIVE",
+-				GatewayInfo:  GatewayInfo{NetworkID: ""},
+-				AdminStateUp: true,
+-				Name:         "second_routers",
+-				ID:           "7177abc4-5ae9-4bb7-b0d4-89e94a4abf3b",
+-				TenantID:     "6b96ff0cb17a4b859e1e575d221683d3",
+-			},
+-			Router{
+-				Status:       "ACTIVE",
+-				GatewayInfo:  GatewayInfo{NetworkID: "3c5bcddd-6af9-4e6b-9c3e-c153e521cab8"},
+-				AdminStateUp: true,
+-				Name:         "router1",
+-				ID:           "a9254bdb-2613-4a13-ac4c-adc581fba50d",
+-				TenantID:     "33a40233088643acb66ff6eb0ebea679",
+-			},
+-		}
+-
+-		th.CheckDeepEquals(t, expected, actual)
+-
+-		return true, nil
+-	})
+-
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
 -	}
--	return
 -}
 -
--// Finds or lists all volumes.
--func (ec2 *EC2) Volumes(volIds []string, filter *Filter) (resp *VolumesResp, err error) {
--	params := makeParams("DescribeVolumes")
--	addParamsList(params, "VolumeId", volIds)
--	filter.addParams(params)
--	resp = &VolumesResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/routers", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-   "router":{
+-      "name": "foo_router",
+-      "admin_state_up": false,
+-      "external_gateway_info":{
+-         "network_id":"8ca37218-28ff-41cb-9b10-039601ea7e6b"
+-      }
+-   }
 -}
+-			`)
 -
--// ----------------------------------------------------------------------------
--// ElasticIp management (for VPC)
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
 -
--// The AllocateAddress request parameters
--//
--// see http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-AllocateAddress.html
--type AllocateAddress struct {
--	Domain string
+-		fmt.Fprintf(w, `
+-{
+-    "router": {
+-        "status": "ACTIVE",
+-        "external_gateway_info": {
+-            "network_id": "8ca37218-28ff-41cb-9b10-039601ea7e6b"
+-        },
+-        "name": "foo_router",
+-        "admin_state_up": false,
+-        "tenant_id": "6b96ff0cb17a4b859e1e575d221683d3",
+-        "id": "8604a0de-7f6b-409a-a47c-a1cc7bc77b2e"
+-    }
 -}
+-		`)
+-	})
 -
--// Response to an AllocateAddress request
--type AllocateAddressResp struct {
--	RequestId    string `xml:"requestId"`
--	PublicIp     string `xml:"publicIp"`
--	Domain       string `xml:"domain"`
--	AllocationId string `xml:"allocationId"`
+-	asu := false
+-	gwi := GatewayInfo{NetworkID: "8ca37218-28ff-41cb-9b10-039601ea7e6b"}
+-
+-	options := CreateOpts{
+-		Name:         "foo_router",
+-		AdminStateUp: &asu,
+-		GatewayInfo:  &gwi,
+-	}
+-	r, err := Create(fake.ServiceClient(), options).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, "foo_router", r.Name)
+-	th.AssertEquals(t, false, r.AdminStateUp)
+-	th.AssertDeepEquals(t, GatewayInfo{NetworkID: "8ca37218-28ff-41cb-9b10-039601ea7e6b"}, r.GatewayInfo)
 -}
 -
--// The AssociateAddress request parameters
--//
--// http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-AssociateAddress.html
--type AssociateAddress struct {
--	InstanceId         string
--	PublicIp           string
--	AllocationId       string
--	AllowReassociation bool
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/routers/a07eea83-7710-4860-931b-5fe220fae533", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "router": {
+-        "status": "ACTIVE",
+-        "external_gateway_info": {
+-            "network_id": "85d76829-6415-48ff-9c63-5c5ca8c61ac6"
+-        },
+-        "name": "router1",
+-        "admin_state_up": true,
+-        "tenant_id": "d6554fe62e2f41efbb6e026fad5c1542",
+-        "id": "a07eea83-7710-4860-931b-5fe220fae533"
+-    }
 -}
+-			`)
+-	})
 -
--// Response to an AssociateAddress request
--type AssociateAddressResp struct {
--	RequestId     string `xml:"requestId"`
--	Return        bool   `xml:"return"`
--	AssociationId string `xml:"associationId"`
+-	n, err := Get(fake.ServiceClient(), "a07eea83-7710-4860-931b-5fe220fae533").Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, n.Status, "ACTIVE")
+-	th.AssertDeepEquals(t, n.GatewayInfo, GatewayInfo{NetworkID: "85d76829-6415-48ff-9c63-5c5ca8c61ac6"})
+-	th.AssertEquals(t, n.Name, "router1")
+-	th.AssertEquals(t, n.AdminStateUp, true)
+-	th.AssertEquals(t, n.TenantID, "d6554fe62e2f41efbb6e026fad5c1542")
+-	th.AssertEquals(t, n.ID, "a07eea83-7710-4860-931b-5fe220fae533")
 -}
 -
--// Address represents an Elastic IP Address
--// See http://goo.gl/uxCjp7 for more details
--type Address struct {
--	PublicIp                string `xml:"publicIp"`
--	AllocationId            string `xml:"allocationId"`
--	Domain                  string `xml:"domain"`
--	InstanceId              string `xml:"instanceId"`
--	AssociationId           string `xml:"associationId"`
--	NetworkInterfaceId      string `xml:"networkInterfaceId"`
--	NetworkInterfaceOwnerId string `xml:"networkInterfaceOwnerId"`
--	PrivateIpAddress        string `xml:"privateIpAddress"`
+-func TestUpdate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/routers/4e8e5957-649f-477b-9e5b-f1f75b21c03c", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "router": {
+-			"name": "new_name",
+-        "external_gateway_info": {
+-            "network_id": "8ca37218-28ff-41cb-9b10-039601ea7e6b"
+-        }
+-    }
 -}
+-			`)
 -
--type DescribeAddressesResp struct {
--	RequestId string    `xml:"requestId"`
--	Addresses []Address `xml:"addressesSet>item"`
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "router": {
+-        "status": "ACTIVE",
+-        "external_gateway_info": {
+-            "network_id": "8ca37218-28ff-41cb-9b10-039601ea7e6b"
+-        },
+-        "name": "new_name",
+-        "admin_state_up": true,
+-        "tenant_id": "6b96ff0cb17a4b859e1e575d221683d3",
+-        "id": "8604a0de-7f6b-409a-a47c-a1cc7bc77b2e"
+-    }
 -}
+-		`)
+-	})
 -
--// Allocate a new Elastic IP.
--func (ec2 *EC2) AllocateAddress(options *AllocateAddress) (resp *AllocateAddressResp, err error) {
--	params := makeParams("AllocateAddress")
--	params["Domain"] = options.Domain
+-	gwi := GatewayInfo{NetworkID: "8ca37218-28ff-41cb-9b10-039601ea7e6b"}
+-	options := UpdateOpts{Name: "new_name", GatewayInfo: &gwi}
 -
--	resp = &AllocateAddressResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
+-	n, err := Update(fake.ServiceClient(), "4e8e5957-649f-477b-9e5b-f1f75b21c03c", options).Extract()
+-	th.AssertNoErr(t, err)
 -
--	return
+-	th.AssertEquals(t, n.Name, "new_name")
+-	th.AssertDeepEquals(t, n.GatewayInfo, GatewayInfo{NetworkID: "8ca37218-28ff-41cb-9b10-039601ea7e6b"})
 -}
 -
--// Release an Elastic IP (VPC).
--func (ec2 *EC2) ReleaseAddress(id string) (resp *SimpleResp, err error) {
--	params := makeParams("ReleaseAddress")
--	params["AllocationId"] = id
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
+-	th.Mux.HandleFunc("/v2.0/routers/4e8e5957-649f-477b-9e5b-f1f75b21c03c", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		w.WriteHeader(http.StatusNoContent)
+-	})
 -
--	return
+-	res := Delete(fake.ServiceClient(), "4e8e5957-649f-477b-9e5b-f1f75b21c03c")
+-	th.AssertNoErr(t, res.Err)
 -}
 -
--// Release an Elastic IP (Public)
--func (ec2 *EC2) ReleasePublicAddress(publicIp string) (resp *SimpleResp, err error) {
--	params := makeParams("ReleaseAddress")
--	params["PublicIp"] = publicIp
+-func TestAddInterface(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
+-	th.Mux.HandleFunc("/v2.0/routers/4e8e5957-649f-477b-9e5b-f1f75b21c03c/add_router_interface", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "subnet_id": "a2f1f29d-571b-4533-907f-5803ab96ead1"
+-}
+-	`)
 -
--	return
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "subnet_id": "0d32a837-8069-4ec3-84c4-3eef3e10b188",
+-    "tenant_id": "017d8de156df4177889f31a9bd6edc00",
+-    "port_id": "3f990102-4485-4df1-97a0-2c35bdb85b31",
+-    "id": "9a83fa11-8da5-436e-9afe-3d3ac5ce7770"
 -}
+-`)
+-	})
 -
--// Associate an address with a VPC instance.
--func (ec2 *EC2) AssociateAddress(options *AssociateAddress) (resp *AssociateAddressResp, err error) {
--	params := makeParams("AssociateAddress")
--	params["InstanceId"] = options.InstanceId
--	if options.PublicIp != "" {
--		params["PublicIp"] = options.PublicIp
--	}
--	if options.AllocationId != "" {
--		params["AllocationId"] = options.AllocationId
+-	opts := InterfaceOpts{SubnetID: "a2f1f29d-571b-4533-907f-5803ab96ead1"}
+-	res, err := AddInterface(fake.ServiceClient(), "4e8e5957-649f-477b-9e5b-f1f75b21c03c", opts).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, "0d32a837-8069-4ec3-84c4-3eef3e10b188", res.SubnetID)
+-	th.AssertEquals(t, "017d8de156df4177889f31a9bd6edc00", res.TenantID)
+-	th.AssertEquals(t, "3f990102-4485-4df1-97a0-2c35bdb85b31", res.PortID)
+-	th.AssertEquals(t, "9a83fa11-8da5-436e-9afe-3d3ac5ce7770", res.ID)
+-}
+-
+-func TestAddInterfaceRequiredOpts(t *testing.T) {
+-	_, err := AddInterface(fake.ServiceClient(), "foo", InterfaceOpts{}).Extract()
+-	if err == nil {
+-		t.Fatalf("Expected error, got none")
 -	}
--	if options.AllowReassociation {
--		params["AllowReassociation"] = "true"
+-	_, err = AddInterface(fake.ServiceClient(), "foo", InterfaceOpts{SubnetID: "bar", PortID: "baz"}).Extract()
+-	if err == nil {
+-		t.Fatalf("Expected error, got none")
 -	}
+-}
 -
--	resp = &AssociateAddressResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
+-func TestRemoveInterface(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	return
+-	th.Mux.HandleFunc("/v2.0/routers/4e8e5957-649f-477b-9e5b-f1f75b21c03c/remove_router_interface", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-		"subnet_id": "a2f1f29d-571b-4533-907f-5803ab96ead1"
 -}
+-	`)
 -
--// Disassociate an address from a VPC instance.
--func (ec2 *EC2) DisassociateAddress(id string) (resp *SimpleResp, err error) {
--	params := makeParams("DisassociateAddress")
--	params["AssociationId"] = id
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
+-		fmt.Fprintf(w, `
+-{
+-		"subnet_id": "0d32a837-8069-4ec3-84c4-3eef3e10b188",
+-		"tenant_id": "017d8de156df4177889f31a9bd6edc00",
+-		"port_id": "3f990102-4485-4df1-97a0-2c35bdb85b31",
+-		"id": "9a83fa11-8da5-436e-9afe-3d3ac5ce7770"
+-}
+-`)
+-	})
+-
+-	opts := InterfaceOpts{SubnetID: "a2f1f29d-571b-4533-907f-5803ab96ead1"}
+-	res, err := RemoveInterface(fake.ServiceClient(), "4e8e5957-649f-477b-9e5b-f1f75b21c03c", opts).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, "0d32a837-8069-4ec3-84c4-3eef3e10b188", res.SubnetID)
+-	th.AssertEquals(t, "017d8de156df4177889f31a9bd6edc00", res.TenantID)
+-	th.AssertEquals(t, "3f990102-4485-4df1-97a0-2c35bdb85b31", res.PortID)
+-	th.AssertEquals(t, "9a83fa11-8da5-436e-9afe-3d3ac5ce7770", res.ID)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/routers/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/routers/results.go
+deleted file mode 100644
+index bdad4cb..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/routers/results.go
++++ /dev/null
+@@ -1,161 +0,0 @@
+-package routers
+-
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
+-
+-// GatewayInfo represents the information of an external gateway for any
+-// particular network router.
+-type GatewayInfo struct {
+-	NetworkID string `json:"network_id" mapstructure:"network_id"`
+-}
+-
+-// Router represents a Neutron router. A router is a logical entity that
+-// forwards packets across internal subnets and NATs (network address
+-// translation) them on external networks through an appropriate gateway.
+-//
+-// A router has an interface for each subnet with which it is associated. By
+-// default, the IP address of such interface is the subnet's gateway IP. Also,
+-// whenever a router is associated with a subnet, a port for that router
+-// interface is added to the subnet's network.
+-type Router struct {
+-	// Indicates whether or not a router is currently operational.
+-	Status string `json:"status" mapstructure:"status"`
+-
+-	// Information on external gateway for the router.
+-	GatewayInfo GatewayInfo `json:"external_gateway_info" mapstructure:"external_gateway_info"`
+-
+-	// Administrative state of the router.
+-	AdminStateUp bool `json:"admin_state_up" mapstructure:"admin_state_up"`
+-
+-	// Human readable name for the router. Does not have to be unique.
+-	Name string `json:"name" mapstructure:"name"`
+-
+-	// Unique identifier for the router.
+-	ID string `json:"id" mapstructure:"id"`
+-
+-	// Owner of the router. Only admin users can specify a tenant identifier
+-	// other than its own.
+-	TenantID string `json:"tenant_id" mapstructure:"tenant_id"`
+-}
+-
+-// RouterPage is the page returned by a pager when traversing over a
+-// collection of routers.
+-type RouterPage struct {
+-	pagination.LinkedPageBase
+-}
+-
+-// NextPageURL is invoked when a paginated collection of routers has reached
+-// the end of a page and the pager seeks to traverse over a new one. In order
+-// to do this, it needs to construct the next page's URL.
+-func (p RouterPage) NextPageURL() (string, error) {
+-	type resp struct {
+-		Links []gophercloud.Link `mapstructure:"routers_links"`
+-	}
+-
+-	var r resp
+-	err := mapstructure.Decode(p.Body, &r)
 -	if err != nil {
--		return nil, err
+-		return "", err
 -	}
 -
--	return
+-	return gophercloud.ExtractNextURL(r.Links)
 -}
 -
--// DescribeAddresses returns details about one or more
--// Elastic IP Addresses. Returned addresses can be
--// filtered by Public IP, Allocation ID or multiple filters
--//
--// See http://goo.gl/zW7J4p for more details.
--func (ec2 *EC2) Addresses(publicIps []string, allocationIds []string, filter *Filter) (resp *DescribeAddressesResp, err error) {
--	params := makeParams("DescribeAddresses")
--	addParamsList(params, "PublicIp", publicIps)
--	addParamsList(params, "AllocationId", allocationIds)
--	filter.addParams(params)
--	resp = &DescribeAddressesResp{}
--	err = ec2.query(params, resp)
+-// IsEmpty checks whether a RouterPage struct is empty.
+-func (p RouterPage) IsEmpty() (bool, error) {
+-	is, err := ExtractRouters(p)
 -	if err != nil {
--		return nil, err
+-		return true, nil
 -	}
--	return
+-	return len(is) == 0, nil
 -}
 -
--// ----------------------------------------------------------------------------
--// Image and snapshot management functions and types.
+-// ExtractRouters accepts a Page struct, specifically a RouterPage struct,
+-// and extracts the elements into a slice of Router structs. In other words,
+-// a generic collection is mapped into a relevant slice.
+-func ExtractRouters(page pagination.Page) ([]Router, error) {
+-	var resp struct {
+-		Routers []Router `mapstructure:"routers" json:"routers"`
+-	}
 -
--// The CreateImage request parameters.
--//
--// See http://goo.gl/cxU41 for more details.
--type CreateImage struct {
--	InstanceId   string
--	Name         string
--	Description  string
--	NoReboot     bool
--	BlockDevices []BlockDeviceMapping
+-	err := mapstructure.Decode(page.(RouterPage).Body, &resp)
+-
+-	return resp.Routers, err
 -}
 -
--// Response to a CreateImage request.
--//
--// See http://goo.gl/cxU41 for more details.
--type CreateImageResp struct {
--	RequestId string `xml:"requestId"`
--	ImageId   string `xml:"imageId"`
+-type commonResult struct {
+-	gophercloud.Result
 -}
 -
--// Response to a DescribeImages request.
--//
--// See http://goo.gl/hLnyg for more details.
--type ImagesResp struct {
--	RequestId string  `xml:"requestId"`
--	Images    []Image `xml:"imagesSet>item"`
+-// Extract is a function that accepts a result and extracts a router.
+-func (r commonResult) Extract() (*Router, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
+-	}
+-
+-	var res struct {
+-		Router *Router `json:"router"`
+-	}
+-
+-	err := mapstructure.Decode(r.Body, &res)
+-
+-	return res.Router, err
 -}
 -
--// Response to a DescribeImageAttribute request.
--//
--// See http://goo.gl/bHO3zT for more details.
--type ImageAttributeResp struct {
--	RequestId    string               `xml:"requestId"`
--	ImageId      string               `xml:"imageId"`
--	Kernel       string               `xml:"kernel>value"`
--	RamDisk      string               `xml:"ramdisk>value"`
--	Description  string               `xml:"description>value"`
--	Group        string               `xml:"launchPermission>item>group"`
--	UserIds      []string             `xml:"launchPermission>item>userId"`
--	ProductCodes []string             `xml:"productCodes>item>productCode"`
--	BlockDevices []BlockDeviceMapping `xml:"blockDeviceMapping>item"`
+-// CreateResult represents the result of a create operation.
+-type CreateResult struct {
+-	commonResult
 -}
 -
--// The RegisterImage request parameters.
--type RegisterImage struct {
--	ImageLocation   string
--	Name            string
--	Description     string
--	Architecture    string
--	KernelId        string
--	RamdiskId       string
--	RootDeviceName  string
--	VirtType        string
--	SriovNetSupport string
--	BlockDevices    []BlockDeviceMapping
+-// GetResult represents the result of a get operation.
+-type GetResult struct {
+-	commonResult
 -}
 -
--// Response to a RegisterImage request.
--type RegisterImageResp struct {
--	RequestId string `xml:"requestId"`
--	ImageId   string `xml:"imageId"`
+-// UpdateResult represents the result of an update operation.
+-type UpdateResult struct {
+-	commonResult
 -}
 -
--// Response to a DegisterImage request.
--//
--// See http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DeregisterImage.html
--type DeregisterImageResp struct {
--	RequestId string `xml:"requestId"`
--	Return    bool   `xml:"return"`
+-// DeleteResult represents the result of a delete operation.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
 -}
 -
--// BlockDeviceMapping represents the association of a block device with an image.
--//
--// See http://goo.gl/wnDBf for more details.
--type BlockDeviceMapping struct {
--	DeviceName          string `xml:"deviceName"`
--	VirtualName         string `xml:"virtualName"`
--	SnapshotId          string `xml:"ebs>snapshotId"`
--	VolumeType          string `xml:"ebs>volumeType"`
--	VolumeSize          int64  `xml:"ebs>volumeSize"`
--	DeleteOnTermination bool   `xml:"ebs>deleteOnTermination"`
--	Encrypted           bool   `xml:"ebs>encrypted"`
--	NoDevice            bool   `xml:"noDevice"`
+-// InterfaceInfo represents information about a particular router interface. As
+-// mentioned above, in order for a router to forward to a subnet, it needs an
+-// interface.
+-type InterfaceInfo struct {
+-	// The ID of the subnet which this interface is associated with.
+-	SubnetID string `json:"subnet_id" mapstructure:"subnet_id"`
 -
--	// The number of I/O operations per second (IOPS) that the volume supports.
--	IOPS int64 `xml:"ebs>iops"`
+-	// The ID of the port that is a part of the subnet.
+-	PortID string `json:"port_id" mapstructure:"port_id"`
+-
+-	// The UUID of the interface.
+-	ID string `json:"id" mapstructure:"id"`
+-
+-	// Owner of the interface.
+-	TenantID string `json:"tenant_id" mapstructure:"tenant_id"`
 -}
 -
--// Image represents details about an image.
--//
--// See http://goo.gl/iSqJG for more details.
--type Image struct {
--	Id                 string               `xml:"imageId"`
--	Name               string               `xml:"name"`
--	Description        string               `xml:"description"`
--	Type               string               `xml:"imageType"`
--	State              string               `xml:"imageState"`
--	Location           string               `xml:"imageLocation"`
--	Public             bool                 `xml:"isPublic"`
--	Architecture       string               `xml:"architecture"`
--	Platform           string               `xml:"platform"`
--	ProductCodes       []string             `xml:"productCode>item>productCode"`
--	KernelId           string               `xml:"kernelId"`
--	RamdiskId          string               `xml:"ramdiskId"`
--	StateReason        string               `xml:"stateReason"`
--	OwnerId            string               `xml:"imageOwnerId"`
--	OwnerAlias         string               `xml:"imageOwnerAlias"`
--	RootDeviceType     string               `xml:"rootDeviceType"`
--	RootDeviceName     string               `xml:"rootDeviceName"`
--	VirtualizationType string               `xml:"virtualizationType"`
--	Hypervisor         string               `xml:"hypervisor"`
--	BlockDevices       []BlockDeviceMapping `xml:"blockDeviceMapping>item"`
--	Tags               []Tag                `xml:"tagSet>item"`
+-// InterfaceResult represents the result of interface operations, such as
+-// AddInterface() and RemoveInterface().
+-type InterfaceResult struct {
+-	gophercloud.Result
 -}
 -
--// The ModifyImageAttribute request parameters.
--type ModifyImageAttribute struct {
--	AddUsers     []string
--	RemoveUsers  []string
--	AddGroups    []string
--	RemoveGroups []string
--	ProductCodes []string
--	Description  string
+-// Extract is a function that accepts a result and extracts an information struct.
+-func (r InterfaceResult) Extract() (*InterfaceInfo, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
+-	}
+-
+-	var res *InterfaceInfo
+-	err := mapstructure.Decode(r.Body, &res)
+-
+-	return res, err
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/routers/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/routers/urls.go
+deleted file mode 100644
+index bc22c2a..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/layer3/routers/urls.go
++++ /dev/null
+@@ -1,21 +0,0 @@
+-package routers
 -
--// The CopyImage request parameters.
--//
--// See http://goo.gl/hQwPCK for more details.
--type CopyImage struct {
--	SourceRegion  string
--	SourceImageId string
--	Name          string
--	Description   string
--	ClientToken   string
+-import "github.com/rackspace/gophercloud"
+-
+-const resourcePath = "routers"
+-
+-func rootURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL(resourcePath)
 -}
 -
--// Response to a CopyImage request.
--//
--// See http://goo.gl/hQwPCK for more details.
--type CopyImageResp struct {
--	RequestId string `xml:"requestId"`
--	ImageId   string `xml:"imageId"`
+-func resourceURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL(resourcePath, id)
 -}
 -
--// Creates an Amazon EBS-backed AMI from an Amazon EBS-backed instance
--// that is either running or stopped.
--//
--// See http://goo.gl/cxU41 for more details.
--func (ec2 *EC2) CreateImage(options *CreateImage) (resp *CreateImageResp, err error) {
--	params := makeParams("CreateImage")
--	params["InstanceId"] = options.InstanceId
--	params["Name"] = options.Name
--	if options.Description != "" {
--		params["Description"] = options.Description
+-func addInterfaceURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL(resourcePath, id, "add_router_interface")
+-}
+-
+-func removeInterfaceURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL(resourcePath, id, "remove_router_interface")
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/doc.go
+deleted file mode 100644
+index bc1fc28..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/doc.go
++++ /dev/null
+@@ -1,3 +0,0 @@
+-// Package lbaas provides information and interaction with the Load Balancer
+-// as a Service extension for the OpenStack Networking service.
+-package lbaas
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/members/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/members/requests.go
+deleted file mode 100644
+index 58ec580..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/members/requests.go
++++ /dev/null
+@@ -1,139 +0,0 @@
+-package members
+-
+-import (
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
+-
+-// ListOpts allows the filtering and sorting of paginated collections through
+-// the API. Filtering is achieved by passing in struct field values that map to
+-// the floating IP attributes you want to see returned. SortKey allows you to
+-// sort by a particular network attribute. SortDir sets the direction, and is
+-// either `asc' or `desc'. Marker and Limit are used for pagination.
+-type ListOpts struct {
+-	Status       string `q:"status"`
+-	Weight       int    `q:"weight"`
+-	AdminStateUp *bool  `q:"admin_state_up"`
+-	TenantID     string `q:"tenant_id"`
+-	PoolID       string `q:"pool_id"`
+-	Address      string `q:"address"`
+-	ProtocolPort int    `q:"protocol_port"`
+-	ID           string `q:"id"`
+-	Limit        int    `q:"limit"`
+-	Marker       string `q:"marker"`
+-	SortKey      string `q:"sort_key"`
+-	SortDir      string `q:"sort_dir"`
+-}
+-
+-// List returns a Pager which allows you to iterate over a collection of
+-// pools. It accepts a ListOpts struct, which allows you to filter and sort
+-// the returned collection for greater efficiency.
+-//
+-// Default policy settings return only those pools that are owned by the
+-// tenant who submits the request, unless an admin user submits the request.
+-func List(c *gophercloud.ServiceClient, opts ListOpts) pagination.Pager {
+-	q, err := gophercloud.BuildQueryString(&opts)
+-	if err != nil {
+-		return pagination.Pager{Err: err}
+-	}
+-	u := rootURL(c) + q.String()
+-	return pagination.NewPager(c, u, func(r pagination.PageResult) pagination.Page {
+-		return MemberPage{pagination.LinkedPageBase{PageResult: r}}
+-	})
+-}
+-
+-// CreateOpts contains all the values needed to create a new pool member.
+-type CreateOpts struct {
+-	// Only required if the caller has an admin role and wants to create a pool
+-	// for another tenant.
+-	TenantID string
+-
+-	// Required. The IP address of the member.
+-	Address string
+-
+-	// Required. The port on which the application is hosted.
+-	ProtocolPort int
+-
+-	// Required. The pool to which this member will belong.
+-	PoolID string
+-}
+-
+-// Create accepts a CreateOpts struct and uses the values to create a new
+-// load balancer pool member.
+-func Create(c *gophercloud.ServiceClient, opts CreateOpts) CreateResult {
+-	type member struct {
+-		TenantID     string `json:"tenant_id"`
+-		ProtocolPort int    `json:"protocol_port"`
+-		Address      string `json:"address"`
+-		PoolID       string `json:"pool_id"`
 -	}
--	if options.NoReboot {
--		params["NoReboot"] = "true"
+-	type request struct {
+-		Member member `json:"member"`
 -	}
--	addBlockDeviceParams("", params, options.BlockDevices)
 -
--	resp = &CreateImageResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
+-	reqBody := request{Member: member{
+-		Address:      opts.Address,
+-		TenantID:     opts.TenantID,
+-		ProtocolPort: opts.ProtocolPort,
+-		PoolID:       opts.PoolID,
+-	}}
 -
--	return
+-	var res CreateResult
+-	_, res.Err = perigee.Request("POST", rootURL(c), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{201},
+-	})
+-	return res
 -}
 -
--// Images returns details about available images.
--// The ids and filter parameters, if provided, will limit the images returned.
--// For example, to get all the private images associated with this account set
--// the boolean filter "is-public" to 0.
--// For list of filters: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeImages.html
--//
--// Note: calling this function with nil ids and filter parameters will result in
--// a very large number of images being returned.
--//
--// See http://goo.gl/SRBhW for more details.
--func (ec2 *EC2) Images(ids []string, filter *Filter) (resp *ImagesResp, err error) {
--	params := makeParams("DescribeImages")
--	for i, id := range ids {
--		params["ImageId."+strconv.Itoa(i+1)] = id
--	}
--	filter.addParams(params)
+-// Get retrieves a particular pool member based on its unique ID.
+-func Get(c *gophercloud.ServiceClient, id string) GetResult {
+-	var res GetResult
+-	_, res.Err = perigee.Request("GET", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return res
+-}
 -
--	resp = &ImagesResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return
+-// UpdateOpts contains the values used when updating a pool member.
+-type UpdateOpts struct {
+-	// The administrative state of the member, which is up (true) or down (false).
+-	AdminStateUp bool
 -}
 -
--// ImagesByOwners returns details about available images.
--// The ids, owners, and filter parameters, if provided, will limit the images returned.
--// For example, to get all the private images associated with this account set
--// the boolean filter "is-public" to 0.
--// For list of filters: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeImages.html
--//
--// Note: calling this function with nil ids and filter parameters will result in
--// a very large number of images being returned.
--//
--// See http://goo.gl/SRBhW for more details.
--func (ec2 *EC2) ImagesByOwners(ids []string, owners []string, filter *Filter) (resp *ImagesResp, err error) {
--	params := makeParams("DescribeImages")
--	for i, id := range ids {
--		params["ImageId."+strconv.Itoa(i+1)] = id
+-// Update allows members to be updated.
+-func Update(c *gophercloud.ServiceClient, id string, opts UpdateOpts) UpdateResult {
+-	type member struct {
+-		AdminStateUp bool `json:"admin_state_up"`
 -	}
--	for i, owner := range owners {
--		params[fmt.Sprintf("Owner.%d", i+1)] = owner
+-	type request struct {
+-		Member member `json:"member"`
 -	}
 -
--	filter.addParams(params)
+-	reqBody := request{Member: member{AdminStateUp: opts.AdminStateUp}}
 -
--	resp = &ImagesResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return
+-	// Send request to API
+-	var res UpdateResult
+-	_, res.Err = perigee.Request("PUT", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return res
 -}
 -
--// ImageAttribute describes an attribute of an AMI.
--// You can specify only one attribute at a time.
--// Valid attributes are:
--//    description | kernel | ramdisk | launchPermission | productCodes | blockDeviceMapping
--//
--// See http://goo.gl/bHO3zT for more details.
--func (ec2 *EC2) ImageAttribute(imageId, attribute string) (resp *ImageAttributeResp, err error) {
--	params := makeParams("DescribeImageAttribute")
--	params["ImageId"] = imageId
--	params["Attribute"] = attribute
+-// Delete will permanently delete a particular member based on its unique ID.
+-func Delete(c *gophercloud.ServiceClient, id string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{204},
+-	})
+-	return res
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/members/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/members/requests_test.go
+deleted file mode 100644
+index dc1ece3..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/members/requests_test.go
++++ /dev/null
+@@ -1,243 +0,0 @@
+-package members
 -
--	resp = &ImageAttributeResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
+-
+-	fake "github.com/rackspace/gophercloud/openstack/networking/v2/common"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestURLs(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.AssertEquals(t, th.Endpoint()+"v2.0/lb/members", rootURL(fake.ServiceClient()))
 -}
 -
--// ModifyImageAttribute sets attributes for an image.
--//
--// See http://goo.gl/YUjO4G for more details.
--func (ec2 *EC2) ModifyImageAttribute(imageId string, options *ModifyImageAttribute) (resp *SimpleResp, err error) {
--	params := makeParams("ModifyImageAttribute")
--	params["ImageId"] = imageId
--	if options.Description != "" {
--		params["Description.Value"] = options.Description
--	}
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	if options.AddUsers != nil {
--		for i, user := range options.AddUsers {
--			p := fmt.Sprintf("LaunchPermission.Add.%d.UserId", i+1)
--			params[p] = user
--		}
--	}
+-	th.Mux.HandleFunc("/v2.0/lb/members", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--	if options.RemoveUsers != nil {
--		for i, user := range options.RemoveUsers {
--			p := fmt.Sprintf("LaunchPermission.Remove.%d.UserId", i+1)
--			params[p] = user
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-   "members":[
+-      {
+-         "status":"ACTIVE",
+-         "weight":1,
+-         "admin_state_up":true,
+-         "tenant_id":"83657cfcdfe44cd5920adaf26c48ceea",
+-         "pool_id":"72741b06-df4d-4715-b142-276b6bce75ab",
+-         "address":"10.0.0.4",
+-         "protocol_port":80,
+-         "id":"701b531b-111a-4f21-ad85-4795b7b12af6"
+-      },
+-      {
+-         "status":"ACTIVE",
+-         "weight":1,
+-         "admin_state_up":true,
+-         "tenant_id":"83657cfcdfe44cd5920adaf26c48ceea",
+-         "pool_id":"72741b06-df4d-4715-b142-276b6bce75ab",
+-         "address":"10.0.0.3",
+-         "protocol_port":80,
+-         "id":"beb53b4d-230b-4abd-8118-575b8fa006ef"
+-      }
+-   ]
+-}
+-      `)
+-	})
+-
+-	count := 0
+-
+-	List(fake.ServiceClient(), ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractMembers(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract members: %v", err)
+-			return false, err
 -		}
--	}
 -
--	if options.AddGroups != nil {
--		for i, group := range options.AddGroups {
--			p := fmt.Sprintf("LaunchPermission.Add.%d.Group", i+1)
--			params[p] = group
+-		expected := []Member{
+-			Member{
+-				Status:       "ACTIVE",
+-				Weight:       1,
+-				AdminStateUp: true,
+-				TenantID:     "83657cfcdfe44cd5920adaf26c48ceea",
+-				PoolID:       "72741b06-df4d-4715-b142-276b6bce75ab",
+-				Address:      "10.0.0.4",
+-				ProtocolPort: 80,
+-				ID:           "701b531b-111a-4f21-ad85-4795b7b12af6",
+-			},
+-			Member{
+-				Status:       "ACTIVE",
+-				Weight:       1,
+-				AdminStateUp: true,
+-				TenantID:     "83657cfcdfe44cd5920adaf26c48ceea",
+-				PoolID:       "72741b06-df4d-4715-b142-276b6bce75ab",
+-				Address:      "10.0.0.3",
+-				ProtocolPort: 80,
+-				ID:           "beb53b4d-230b-4abd-8118-575b8fa006ef",
+-			},
 -		}
--	}
 -
--	if options.RemoveGroups != nil {
--		for i, group := range options.RemoveGroups {
--			p := fmt.Sprintf("LaunchPermission.Remove.%d.Group", i+1)
--			params[p] = group
--		}
--	}
+-		th.CheckDeepEquals(t, expected, actual)
 -
--	if options.ProductCodes != nil {
--		addParamsList(params, "ProductCode", options.ProductCodes)
--	}
+-		return true, nil
+-	})
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		resp = nil
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
 -	}
+-}
 -
--	return
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/lb/members", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-  "member": {
+-    "tenant_id": "453105b9-1754-413f-aab1-55f1af620750",
+-		"pool_id": "foo",
+-    "address": "192.0.2.14",
+-    "protocol_port":8080
+-  }
 -}
+-      `)
 -
--// Registers a new AMI with EC2.
--//
--// See: http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-RegisterImage.html
--func (ec2 *EC2) RegisterImage(options *RegisterImage) (resp *RegisterImageResp, err error) {
--	params := makeParams("RegisterImage")
--	params["Name"] = options.Name
--	if options.ImageLocation != "" {
--		params["ImageLocation"] = options.ImageLocation
--	}
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
 -
--	if options.Description != "" {
--		params["Description"] = options.Description
--	}
+-		fmt.Fprintf(w, `
+-{
+-  "member": {
+-    "id": "975592ca-e308-48ad-8298-731935ee9f45",
+-    "address": "192.0.2.14",
+-    "protocol_port": 8080,
+-    "tenant_id": "453105b9-1754-413f-aab1-55f1af620750",
+-    "admin_state_up":true,
+-    "weight": 1,
+-    "status": "DOWN"
+-  }
+-}
+-    `)
+-	})
 -
--	if options.Architecture != "" {
--		params["Architecture"] = options.Architecture
+-	options := CreateOpts{
+-		TenantID:     "453105b9-1754-413f-aab1-55f1af620750",
+-		Address:      "192.0.2.14",
+-		ProtocolPort: 8080,
+-		PoolID:       "foo",
 -	}
+-	_, err := Create(fake.ServiceClient(), options).Extract()
+-	th.AssertNoErr(t, err)
+-}
 -
--	if options.KernelId != "" {
--		params["KernelId"] = options.KernelId
--	}
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	if options.RamdiskId != "" {
--		params["RamdiskId"] = options.RamdiskId
--	}
+-	th.Mux.HandleFunc("/v2.0/lb/members/975592ca-e308-48ad-8298-731935ee9f45", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--	if options.RootDeviceName != "" {
--		params["RootDeviceName"] = options.RootDeviceName
--	}
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--	if options.VirtType != "" {
--		params["VirtualizationType"] = options.VirtType
--	}
+-		fmt.Fprintf(w, `
+-{
+-   "member":{
+-      "id":"975592ca-e308-48ad-8298-731935ee9f45",
+-      "address":"192.0.2.14",
+-      "protocol_port":8080,
+-      "tenant_id":"453105b9-1754-413f-aab1-55f1af620750",
+-      "admin_state_up":true,
+-      "weight":1,
+-      "status":"DOWN"
+-   }
+-}
+-      `)
+-	})
 -
--	if options.SriovNetSupport != "" {
--		params["SriovNetSupport"] = "simple"
--	}
+-	m, err := Get(fake.ServiceClient(), "975592ca-e308-48ad-8298-731935ee9f45").Extract()
+-	th.AssertNoErr(t, err)
 -
--	addBlockDeviceParams("", params, options.BlockDevices)
+-	th.AssertEquals(t, "975592ca-e308-48ad-8298-731935ee9f45", m.ID)
+-	th.AssertEquals(t, "192.0.2.14", m.Address)
+-	th.AssertEquals(t, 8080, m.ProtocolPort)
+-	th.AssertEquals(t, "453105b9-1754-413f-aab1-55f1af620750", m.TenantID)
+-	th.AssertEquals(t, true, m.AdminStateUp)
+-	th.AssertEquals(t, 1, m.Weight)
+-	th.AssertEquals(t, "DOWN", m.Status)
+-}
 -
--	resp = &RegisterImageResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
+-func TestUpdate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/lb/members/332abe93-f488-41ba-870b-2ac66be7f853", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-   "member":{
+-      "admin_state_up":false
+-   }
+-}
+-      `)
 -
--	return
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-   "member":{
+-      "status":"PENDING_UPDATE",
+-      "protocol_port":8080,
+-      "weight":1,
+-      "admin_state_up":false,
+-      "tenant_id":"4fd44f30292945e481c7b8a0c8908869",
+-      "pool_id":"7803631d-f181-4500-b3a2-1b68ba2a75fd",
+-      "address":"10.0.0.5",
+-      "status_description":null,
+-      "id":"48a471ea-64f1-4eb6-9be7-dae6bbe40a0f"
+-   }
 -}
+-    `)
+-	})
 -
--// Degisters an image. Note that this does not delete the backing stores of the AMI.
--//
--// See http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DeregisterImage.html
--func (ec2 *EC2) DeregisterImage(imageId string) (resp *DeregisterImageResp, err error) {
--	params := makeParams("DeregisterImage")
--	params["ImageId"] = imageId
+-	options := UpdateOpts{AdminStateUp: false}
 -
--	resp = &DeregisterImageResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
+-	_, err := Update(fake.ServiceClient(), "332abe93-f488-41ba-870b-2ac66be7f853", options).Extract()
+-	th.AssertNoErr(t, err)
+-}
 -
--	return
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/lb/members/332abe93-f488-41ba-870b-2ac66be7f853", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-
+-	res := Delete(fake.ServiceClient(), "332abe93-f488-41ba-870b-2ac66be7f853")
+-	th.AssertNoErr(t, res.Err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/members/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/members/results.go
+deleted file mode 100644
+index 3cad339..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/members/results.go
++++ /dev/null
+@@ -1,122 +0,0 @@
+-package members
 -
--// Copy and Image from one region to another.
--//
--// See http://goo.gl/hQwPCK for more details.
--func (ec2 *EC2) CopyImage(options *CopyImage) (resp *CopyImageResp, err error) {
--	params := makeParams("CopyImage")
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	if options.SourceRegion != "" {
--		params["SourceRegion"] = options.SourceRegion
--	}
+-// Member represents the application running on a backend server.
+-type Member struct {
+-	// The status of the member. Indicates whether the member is operational.
+-	Status string
 -
--	if options.SourceImageId != "" {
--		params["SourceImageId"] = options.SourceImageId
--	}
+-	// Weight of member.
+-	Weight int
 -
--	if options.Name != "" {
--		params["Name"] = options.Name
--	}
+-	// The administrative state of the member, which is up (true) or down (false).
+-	AdminStateUp bool `json:"admin_state_up" mapstructure:"admin_state_up"`
 -
--	if options.Description != "" {
--		params["Description"] = options.Description
--	}
+-	// Owner of the member. Only an administrative user can specify a tenant ID
+-	// other than its own.
+-	TenantID string `json:"tenant_id" mapstructure:"tenant_id"`
 -
--	if options.ClientToken != "" {
--		params["ClientToken"] = options.ClientToken
--	}
+-	// The pool to which the member belongs.
+-	PoolID string `json:"pool_id" mapstructure:"pool_id"`
 -
--	resp = &CopyImageResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
+-	// The IP address of the member.
+-	Address string
 -
--	return
+-	// The port on which the application is hosted.
+-	ProtocolPort int `json:"protocol_port" mapstructure:"protocol_port"`
+-
+-	// The unique ID for the member.
+-	ID string
 -}
 -
--// Response to a CreateSnapshot request.
--//
--// See http://goo.gl/ttcda for more details.
--type CreateSnapshotResp struct {
--	RequestId string `xml:"requestId"`
--	Snapshot
+-// MemberPage is the page returned by a pager when traversing over a
+-// collection of pool members.
+-type MemberPage struct {
+-	pagination.LinkedPageBase
 -}
 -
--// CreateSnapshot creates a volume snapshot and stores it in S3.
--//
--// See http://goo.gl/ttcda for more details.
--func (ec2 *EC2) CreateSnapshot(volumeId, description string) (resp *CreateSnapshotResp, err error) {
--	params := makeParams("CreateSnapshot")
--	params["VolumeId"] = volumeId
--	params["Description"] = description
+-// NextPageURL is invoked when a paginated collection of members has reached
+-// the end of a page and the pager seeks to traverse over a new one. In order
+-// to do this, it needs to construct the next page's URL.
+-func (p MemberPage) NextPageURL() (string, error) {
+-	type resp struct {
+-		Links []gophercloud.Link `mapstructure:"members_links"`
+-	}
 -
--	resp = &CreateSnapshotResp{}
--	err = ec2.query(params, resp)
+-	var r resp
+-	err := mapstructure.Decode(p.Body, &r)
 -	if err != nil {
--		return nil, err
+-		return "", err
 -	}
--	return
+-
+-	return gophercloud.ExtractNextURL(r.Links)
 -}
 -
--// DeleteSnapshots deletes the volume snapshots with the given ids.
--//
--// Note: If you make periodic snapshots of a volume, the snapshots are
--// incremental so that only the blocks on the device that have changed
--// since your last snapshot are incrementally saved in the new snapshot.
--// Even though snapshots are saved incrementally, the snapshot deletion
--// process is designed so that you need to retain only the most recent
--// snapshot in order to restore the volume.
--//
--// See http://goo.gl/vwU1y for more details.
--func (ec2 *EC2) DeleteSnapshots(ids []string) (resp *SimpleResp, err error) {
--	params := makeParams("DeleteSnapshot")
--	for i, id := range ids {
--		params["SnapshotId."+strconv.Itoa(i+1)] = id
+-// IsEmpty checks whether a MemberPage struct is empty.
+-func (p MemberPage) IsEmpty() (bool, error) {
+-	is, err := ExtractMembers(p)
+-	if err != nil {
+-		return true, nil
+-	}
+-	return len(is) == 0, nil
+-}
+-
+-// ExtractMembers accepts a Page struct, specifically a MemberPage struct,
+-// and extracts the elements into a slice of Member structs. In other words,
+-// a generic collection is mapped into a relevant slice.
+-func ExtractMembers(page pagination.Page) ([]Member, error) {
+-	var resp struct {
+-		Members []Member `mapstructure:"members" json:"members"`
 -	}
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
+-	err := mapstructure.Decode(page.(MemberPage).Body, &resp)
 -	if err != nil {
 -		return nil, err
 -	}
--	return
--}
 -
--// Response to a DescribeSnapshots request.
--//
--// See http://goo.gl/nClDT for more details.
--type SnapshotsResp struct {
--	RequestId string     `xml:"requestId"`
--	Snapshots []Snapshot `xml:"snapshotSet>item"`
+-	return resp.Members, nil
 -}
 -
--// Snapshot represents details about a volume snapshot.
--//
--// See http://goo.gl/nkovs for more details.
--type Snapshot struct {
--	Id          string `xml:"snapshotId"`
--	VolumeId    string `xml:"volumeId"`
--	VolumeSize  string `xml:"volumeSize"`
--	Status      string `xml:"status"`
--	StartTime   string `xml:"startTime"`
--	Description string `xml:"description"`
--	Progress    string `xml:"progress"`
--	OwnerId     string `xml:"ownerId"`
--	OwnerAlias  string `xml:"ownerAlias"`
--	Encrypted   bool   `xml:"encrypted"`
--	Tags        []Tag  `xml:"tagSet>item"`
+-type commonResult struct {
+-	gophercloud.Result
 -}
 -
--// Snapshots returns details about volume snapshots available to the user.
--// The ids and filter parameters, if provided, limit the snapshots returned.
--//
--// See http://goo.gl/ogJL4 for more details.
--func (ec2 *EC2) Snapshots(ids []string, filter *Filter) (resp *SnapshotsResp, err error) {
--	params := makeParams("DescribeSnapshots")
--	for i, id := range ids {
--		params["SnapshotId."+strconv.Itoa(i+1)] = id
+-// Extract is a function that accepts a result and extracts a router.
+-func (r commonResult) Extract() (*Member, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
 -	}
--	filter.addParams(params)
 -
--	resp = &SnapshotsResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
+-	var res struct {
+-		Member *Member `json:"member"`
 -	}
--	return
--}
 -
--// ----------------------------------------------------------------------------
--// KeyPair management functions and types.
+-	err := mapstructure.Decode(r.Body, &res)
 -
--type KeyPair struct {
--	Name        string `xml:"keyName"`
--	Fingerprint string `xml:"keyFingerprint"`
+-	return res.Member, err
 -}
 -
--type KeyPairsResp struct {
--	RequestId string    `xml:"requestId"`
--	Keys      []KeyPair `xml:"keySet>item"`
+-// CreateResult represents the result of a create operation.
+-type CreateResult struct {
+-	commonResult
 -}
 -
--type CreateKeyPairResp struct {
--	RequestId      string `xml:"requestId"`
--	KeyName        string `xml:"keyName"`
--	KeyFingerprint string `xml:"keyFingerprint"`
--	KeyMaterial    string `xml:"keyMaterial"`
+-// GetResult represents the result of a get operation.
+-type GetResult struct {
+-	commonResult
 -}
 -
--type ImportKeyPairResponse struct {
--	RequestId      string `xml:"requestId"`
--	KeyName        string `xml:"keyName"`
--	KeyFingerprint string `xml:"keyFingerprint"`
+-// UpdateResult represents the result of an update operation.
+-type UpdateResult struct {
+-	commonResult
 -}
 -
--// CreateKeyPair creates a new key pair and returns the private key contents.
--//
--// See http://goo.gl/0S6hV
--func (ec2 *EC2) CreateKeyPair(keyName string) (resp *CreateKeyPairResp, err error) {
--	params := makeParams("CreateKeyPair")
--	params["KeyName"] = keyName
--
--	resp = &CreateKeyPairResp{}
--	err = ec2.query(params, resp)
--	if err == nil {
--		resp.KeyFingerprint = strings.TrimSpace(resp.KeyFingerprint)
--	}
--	return
+-// DeleteResult represents the result of a delete operation.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/members/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/members/urls.go
+deleted file mode 100644
+index 94b57e4..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/members/urls.go
++++ /dev/null
+@@ -1,16 +0,0 @@
+-package members
 -
--// DeleteKeyPair deletes a key pair.
--//
--// See http://goo.gl/0bqok
--func (ec2 *EC2) DeleteKeyPair(name string) (resp *SimpleResp, err error) {
--	params := makeParams("DeleteKeyPair")
--	params["KeyName"] = name
+-import "github.com/rackspace/gophercloud"
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
--	return
+-const (
+-	rootPath     = "lb"
+-	resourcePath = "members"
+-)
+-
+-func rootURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL(rootPath, resourcePath)
 -}
 -
--// KeyPairs returns list of key pairs for this account
--//
--// See http://goo.gl/Apzsfz
--func (ec2 *EC2) KeyPairs(keynames []string, filter *Filter) (resp *KeyPairsResp, err error) {
--	params := makeParams("DescribeKeyPairs")
--	for i, name := range keynames {
--		params["KeyName."+strconv.Itoa(i)] = name
--	}
--	filter.addParams(params)
+-func resourceURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL(rootPath, resourcePath, id)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/monitors/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/monitors/requests.go
+deleted file mode 100644
+index e2b590e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/monitors/requests.go
++++ /dev/null
+@@ -1,282 +0,0 @@
+-package monitors
 -
--	resp = &KeyPairsResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
+-import (
+-	"fmt"
 -
--	return resp, nil
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
+-
+-// ListOpts allows the filtering and sorting of paginated collections through
+-// the API. Filtering is achieved by passing in struct field values that map to
+-// the floating IP attributes you want to see returned. SortKey allows you to
+-// sort by a particular network attribute. SortDir sets the direction, and is
+-// either `asc' or `desc'. Marker and Limit are used for pagination.
+-type ListOpts struct {
+-	ID            string `q:"id"`
+-	TenantID      string `q:"tenant_id"`
+-	Type          string `q:"type"`
+-	Delay         int    `q:"delay"`
+-	Timeout       int    `q:"timeout"`
+-	MaxRetries    int    `q:"max_retries"`
+-	HTTPMethod    string `q:"http_method"`
+-	URLPath       string `q:"url_path"`
+-	ExpectedCodes string `q:"expected_codes"`
+-	AdminStateUp  *bool  `q:"admin_state_up"`
+-	Status        string `q:"status"`
+-	Limit         int    `q:"limit"`
+-	Marker        string `q:"marker"`
+-	SortKey       string `q:"sort_key"`
+-	SortDir       string `q:"sort_dir"`
+-}
+-
+-// List returns a Pager which allows you to iterate over a collection of
+-// routers. It accepts a ListOpts struct, which allows you to filter and sort
+-// the returned collection for greater efficiency.
+-//
+-// Default policy settings return only those routers that are owned by the
+-// tenant who submits the request, unless an admin user submits the request.
+-func List(c *gophercloud.ServiceClient, opts ListOpts) pagination.Pager {
+-	q, err := gophercloud.BuildQueryString(&opts)
+-	if err != nil {
+-		return pagination.Pager{Err: err}
+-	}
+-	u := rootURL(c) + q.String()
+-
+-	return pagination.NewPager(c, u, func(r pagination.PageResult) pagination.Page {
+-		return MonitorPage{pagination.LinkedPageBase{PageResult: r}}
+-	})
 -}
 -
--// ImportKeyPair imports a key into AWS
--//
--// See http://goo.gl/NbZUvw
--func (ec2 *EC2) ImportKeyPair(keyname string, key string) (resp *ImportKeyPairResponse, err error) {
--	params := makeParams("ImportKeyPair")
--	params["KeyName"] = keyname
+-// Constants that represent approved monitoring types.
+-const (
+-	TypePING  = "PING"
+-	TypeTCP   = "TCP"
+-	TypeHTTP  = "HTTP"
+-	TypeHTTPS = "HTTPS"
+-)
 -
--	// Oddly, AWS requires the key material to be base64-encoded, even if it was
--	// already encoded. So, we force another round of encoding...
--	// c.f. https://groups.google.com/forum/?fromgroups#!topic/boto-dev/IczrStO9Q8M
--	params["PublicKeyMaterial"] = base64.StdEncoding.EncodeToString([]byte(key))
+-var (
+-	errValidTypeRequired     = fmt.Errorf("A valid Type is required. Supported values are PING, TCP, HTTP and HTTPS")
+-	errDelayRequired         = fmt.Errorf("Delay is required")
+-	errTimeoutRequired       = fmt.Errorf("Timeout is required")
+-	errMaxRetriesRequired    = fmt.Errorf("MaxRetries is required")
+-	errURLPathRequired       = fmt.Errorf("URL path is required")
+-	errExpectedCodesRequired = fmt.Errorf("ExpectedCodes is required")
+-	errDelayMustGETimeout    = fmt.Errorf("Delay must be greater than or equal to timeout")
+-)
 -
--	resp = &ImportKeyPairResponse{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return resp, nil
--}
+-// CreateOpts contains all the values needed to create a new health monitor.
+-type CreateOpts struct {
+-	// Required for admins. Indicates the owner of the VIP.
+-	TenantID string
 -
--// ----------------------------------------------------------------------------
--// Security group management functions and types.
+-	// Required. The type of probe, which is PING, TCP, HTTP, or HTTPS, that is
+-	// sent by the load balancer to verify the member state.
+-	Type string
 -
--// SimpleResp represents a response to an EC2 request which on success will
--// return no other information besides a request id.
--type SimpleResp struct {
--	XMLName   xml.Name
--	RequestId string `xml:"requestId"`
--}
+-	// Required. The time, in seconds, between sending probes to members.
+-	Delay int
 -
--// CreateSecurityGroupResp represents a response to a CreateSecurityGroup request.
--type CreateSecurityGroupResp struct {
--	SecurityGroup
--	RequestId string `xml:"requestId"`
+-	// Required. Maximum number of seconds for a monitor to wait for a ping reply
+-	// before it times out. The value must be less than the delay value.
+-	Timeout int
+-
+-	// Required. Number of permissible ping failures before changing the member's
+-	// status to INACTIVE. Must be a number between 1 and 10.
+-	MaxRetries int
+-
+-	// Required for HTTP(S) types. URI path that will be accessed if monitor type
+-	// is HTTP or HTTPS.
+-	URLPath string
+-
+-	// Required for HTTP(S) types. The HTTP method used for requests by the
+-	// monitor. If this attribute is not specified, it defaults to "GET".
+-	HTTPMethod string
+-
+-	// Required for HTTP(S) types. Expected HTTP codes for a passing HTTP(S)
+-	// monitor. You can either specify a single status like "200", or a range
+-	// like "200-202".
+-	ExpectedCodes string
+-
+-	AdminStateUp *bool
 -}
 -
--// CreateSecurityGroup run a CreateSecurityGroup request in EC2, with the provided
--// name and description.
+-// Create is an operation which provisions a new health monitor. There are
+-// different types of monitor you can provision: PING, TCP or HTTP(S). Below
+-// are examples of how to create each one.
 -//
--// See http://goo.gl/Eo7Yl for more details.
--func (ec2 *EC2) CreateSecurityGroup(group SecurityGroup) (resp *CreateSecurityGroupResp, err error) {
--	params := makeParams("CreateSecurityGroup")
--	params["GroupName"] = group.Name
--	params["GroupDescription"] = group.Description
--	if group.VpcId != "" {
--		params["VpcId"] = group.VpcId
+-// Here is an example config struct to use when creating a PING or TCP monitor:
+-//
+-// CreateOpts{Type: TypePING, Delay: 20, Timeout: 10, MaxRetries: 3}
+-// CreateOpts{Type: TypeTCP, Delay: 20, Timeout: 10, MaxRetries: 3}
+-//
+-// Here is an example config struct to use when creating a HTTP(S) monitor:
+-//
+-// CreateOpts{Type: TypeHTTP, Delay: 20, Timeout: 10, MaxRetries: 3,
+-//  HttpMethod: "HEAD", ExpectedCodes: "200"}
+-//
+-func Create(c *gophercloud.ServiceClient, opts CreateOpts) CreateResult {
+-	var res CreateResult
+-
+-	// Validate inputs
+-	allowed := map[string]bool{TypeHTTP: true, TypeHTTPS: true, TypeTCP: true, TypePING: true}
+-	if opts.Type == "" || allowed[opts.Type] == false {
+-		res.Err = errValidTypeRequired
+-	}
+-	if opts.Delay == 0 {
+-		res.Err = errDelayRequired
+-	}
+-	if opts.Timeout == 0 {
+-		res.Err = errTimeoutRequired
+-	}
+-	if opts.MaxRetries == 0 {
+-		res.Err = errMaxRetriesRequired
+-	}
+-	if opts.Type == TypeHTTP || opts.Type == TypeHTTPS {
+-		if opts.URLPath == "" {
+-			res.Err = errURLPathRequired
+-		}
+-		if opts.ExpectedCodes == "" {
+-			res.Err = errExpectedCodesRequired
+-		}
+-	}
+-	if opts.Delay < opts.Timeout {
+-		res.Err = errDelayMustGETimeout
+-	}
+-	if res.Err != nil {
+-		return res
 -	}
 -
--	resp = &CreateSecurityGroupResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
+-	type monitor struct {
+-		Type          string  `json:"type"`
+-		Delay         int     `json:"delay"`
+-		Timeout       int     `json:"timeout"`
+-		MaxRetries    int     `json:"max_retries"`
+-		TenantID      *string `json:"tenant_id,omitempty"`
+-		URLPath       *string `json:"url_path,omitempty"`
+-		ExpectedCodes *string `json:"expected_codes,omitempty"`
+-		HTTPMethod    *string `json:"http_method,omitempty"`
+-		AdminStateUp  *bool   `json:"admin_state_up,omitempty"`
 -	}
--	resp.Name = group.Name
--	return resp, nil
--}
 -
--// SecurityGroupsResp represents a response to a DescribeSecurityGroups
--// request in EC2.
--//
--// See http://goo.gl/k12Uy for more details.
--type SecurityGroupsResp struct {
--	RequestId string              `xml:"requestId"`
--	Groups    []SecurityGroupInfo `xml:"securityGroupInfo>item"`
--}
+-	type request struct {
+-		Monitor monitor `json:"health_monitor"`
+-	}
 -
--// SecurityGroup encapsulates details for a security group in EC2.
--//
--// See http://goo.gl/CIdyP for more details.
--type SecurityGroupInfo struct {
--	SecurityGroup
--	OwnerId     string   `xml:"ownerId"`
--	Description string   `xml:"groupDescription"`
--	IPPerms     []IPPerm `xml:"ipPermissions>item"`
--}
+-	reqBody := request{Monitor: monitor{
+-		Type:          opts.Type,
+-		Delay:         opts.Delay,
+-		Timeout:       opts.Timeout,
+-		MaxRetries:    opts.MaxRetries,
+-		TenantID:      gophercloud.MaybeString(opts.TenantID),
+-		URLPath:       gophercloud.MaybeString(opts.URLPath),
+-		ExpectedCodes: gophercloud.MaybeString(opts.ExpectedCodes),
+-		HTTPMethod:    gophercloud.MaybeString(opts.HTTPMethod),
+-		AdminStateUp:  opts.AdminStateUp,
+-	}}
 -
--// IPPerm represents an allowance within an EC2 security group.
--//
--// See http://goo.gl/4oTxv for more details.
--type IPPerm struct {
--	Protocol     string              `xml:"ipProtocol"`
--	FromPort     int                 `xml:"fromPort"`
--	ToPort       int                 `xml:"toPort"`
--	SourceIPs    []string            `xml:"ipRanges>item>cidrIp"`
--	SourceGroups []UserSecurityGroup `xml:"groups>item"`
--}
+-	_, res.Err = perigee.Request("POST", rootURL(c), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{201},
+-	})
 -
--// UserSecurityGroup holds a security group and the owner
--// of that group.
--type UserSecurityGroup struct {
--	Id      string `xml:"groupId"`
--	Name    string `xml:"groupName"`
--	OwnerId string `xml:"userId"`
+-	return res
 -}
 -
--// SecurityGroup represents an EC2 security group.
--// If SecurityGroup is used as a parameter, then one of Id or Name
--// may be empty. If both are set, then Id is used.
--type SecurityGroup struct {
--	Id          string `xml:"groupId"`
--	Name        string `xml:"groupName"`
--	Description string `xml:"groupDescription"`
--	VpcId       string `xml:"vpcId"`
+-// Get retrieves a particular health monitor based on its unique ID.
+-func Get(c *gophercloud.ServiceClient, id string) GetResult {
+-	var res GetResult
+-	_, res.Err = perigee.Request("GET", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return res
 -}
 -
--// SecurityGroupNames is a convenience function that
--// returns a slice of security groups with the given names.
--func SecurityGroupNames(names ...string) []SecurityGroup {
--	g := make([]SecurityGroup, len(names))
--	for i, name := range names {
--		g[i] = SecurityGroup{Name: name}
--	}
--	return g
--}
+-// UpdateOpts contains all the values needed to update an existing virtual IP.
+-// Attributes not listed here but appear in CreateOpts are immutable and cannot
+-// be updated.
+-type UpdateOpts struct {
+-	// Required. The time, in seconds, between sending probes to members.
+-	Delay int
 -
--// SecurityGroupNames is a convenience function that
--// returns a slice of security groups with the given ids.
--func SecurityGroupIds(ids ...string) []SecurityGroup {
--	g := make([]SecurityGroup, len(ids))
--	for i, id := range ids {
--		g[i] = SecurityGroup{Id: id}
--	}
--	return g
+-	// Required. Maximum number of seconds for a monitor to wait for a ping reply
+-	// before it times out. The value must be less than the delay value.
+-	Timeout int
+-
+-	// Required. Number of permissible ping failures before changing the member's
+-	// status to INACTIVE. Must be a number between 1 and 10.
+-	MaxRetries int
+-
+-	// Required for HTTP(S) types. URI path that will be accessed if monitor type
+-	// is HTTP or HTTPS.
+-	URLPath string
+-
+-	// Required for HTTP(S) types. The HTTP method used for requests by the
+-	// monitor. If this attribute is not specified, it defaults to "GET".
+-	HTTPMethod string
+-
+-	// Required for HTTP(S) types. Expected HTTP codes for a passing HTTP(S)
+-	// monitor. You can either specify a single status like "200", or a range
+-	// like "200-202".
+-	ExpectedCodes string
+-
+-	AdminStateUp *bool
 -}
 -
--// SecurityGroups returns details about security groups in EC2.  Both parameters
--// are optional, and if provided will limit the security groups returned to those
--// matching the given groups or filtering rules.
--//
--// See http://goo.gl/k12Uy for more details.
--func (ec2 *EC2) SecurityGroups(groups []SecurityGroup, filter *Filter) (resp *SecurityGroupsResp, err error) {
--	params := makeParams("DescribeSecurityGroups")
--	i, j := 1, 1
--	for _, g := range groups {
--		if g.Id != "" {
--			params["GroupId."+strconv.Itoa(i)] = g.Id
--			i++
--		} else {
--			params["GroupName."+strconv.Itoa(j)] = g.Name
--			j++
--		}
--	}
--	filter.addParams(params)
+-// Update is an operation which modifies the attributes of the specified monitor.
+-func Update(c *gophercloud.ServiceClient, id string, opts UpdateOpts) UpdateResult {
+-	var res UpdateResult
 -
--	resp = &SecurityGroupsResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
+-	if opts.Delay > 0 && opts.Timeout > 0 && opts.Delay < opts.Timeout {
+-		res.Err = errDelayMustGETimeout
 -	}
--	return resp, nil
--}
 -
--// DeleteSecurityGroup removes the given security group in EC2.
--//
--// See http://goo.gl/QJJDO for more details.
--func (ec2 *EC2) DeleteSecurityGroup(group SecurityGroup) (resp *SimpleResp, err error) {
--	params := makeParams("DeleteSecurityGroup")
--	if group.Id != "" {
--		params["GroupId"] = group.Id
--	} else {
--		params["GroupName"] = group.Name
+-	type monitor struct {
+-		Delay         int     `json:"delay"`
+-		Timeout       int     `json:"timeout"`
+-		MaxRetries    int     `json:"max_retries"`
+-		URLPath       *string `json:"url_path,omitempty"`
+-		ExpectedCodes *string `json:"expected_codes,omitempty"`
+-		HTTPMethod    *string `json:"http_method,omitempty"`
+-		AdminStateUp  *bool   `json:"admin_state_up,omitempty"`
 -	}
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
+-	type request struct {
+-		Monitor monitor `json:"health_monitor"`
 -	}
--	return resp, nil
+-
+-	reqBody := request{Monitor: monitor{
+-		Delay:         opts.Delay,
+-		Timeout:       opts.Timeout,
+-		MaxRetries:    opts.MaxRetries,
+-		URLPath:       gophercloud.MaybeString(opts.URLPath),
+-		ExpectedCodes: gophercloud.MaybeString(opts.ExpectedCodes),
+-		HTTPMethod:    gophercloud.MaybeString(opts.HTTPMethod),
+-		AdminStateUp:  opts.AdminStateUp,
+-	}}
+-
+-	_, res.Err = perigee.Request("PUT", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{200, 202},
+-	})
+-
+-	return res
 -}
 -
--// AuthorizeSecurityGroup creates an allowance for clients matching the provided
--// rules to access instances within the given security group.
--//
--// See http://goo.gl/u2sDJ for more details.
--func (ec2 *EC2) AuthorizeSecurityGroup(group SecurityGroup, perms []IPPerm) (resp *SimpleResp, err error) {
--	return ec2.authOrRevoke("AuthorizeSecurityGroupIngress", group, perms)
+-// Delete will permanently delete a particular monitor based on its unique ID.
+-func Delete(c *gophercloud.ServiceClient, id string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{204},
+-	})
+-	return res
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/monitors/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/monitors/requests_test.go
+deleted file mode 100644
+index 79a99bf..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/monitors/requests_test.go
++++ /dev/null
+@@ -1,312 +0,0 @@
+-package monitors
 -
--// AuthorizeSecurityGroupEgress creates an allowance for clients matching the provided
--// rules for egress access.
--//
--// See http://goo.gl/UHnH4L for more details.
--func (ec2 *EC2) AuthorizeSecurityGroupEgress(group SecurityGroup, perms []IPPerm) (resp *SimpleResp, err error) {
--	return ec2.authOrRevoke("AuthorizeSecurityGroupEgress", group, perms)
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
+-
+-	fake "github.com/rackspace/gophercloud/openstack/networking/v2/common"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func TestURLs(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	th.AssertEquals(t, th.Endpoint()+"v2.0/lb/health_monitors", rootURL(fake.ServiceClient()))
 -}
 -
--// RevokeSecurityGroup revokes permissions from a group.
--//
--// See http://goo.gl/ZgdxA for more details.
--func (ec2 *EC2) RevokeSecurityGroup(group SecurityGroup, perms []IPPerm) (resp *SimpleResp, err error) {
--	return ec2.authOrRevoke("RevokeSecurityGroupIngress", group, perms)
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/lb/health_monitors", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-   "health_monitors":[
+-      {
+-         "admin_state_up":true,
+-         "tenant_id":"83657cfcdfe44cd5920adaf26c48ceea",
+-         "delay":10,
+-         "max_retries":1,
+-         "timeout":1,
+-         "type":"PING",
+-         "id":"466c8345-28d8-4f84-a246-e04380b0461d"
+-      },
+-      {
+-         "admin_state_up":true,
+-         "tenant_id":"83657cfcdfe44cd5920adaf26c48ceea",
+-         "delay":5,
+-         "expected_codes":"200",
+-         "max_retries":2,
+-         "http_method":"GET",
+-         "timeout":2,
+-         "url_path":"/",
+-         "type":"HTTP",
+-         "id":"5d4b5228-33b0-4e60-b225-9b727c1a20e7"
+-      }
+-   ]
 -}
+-			`)
+-	})
 -
--func (ec2 *EC2) authOrRevoke(op string, group SecurityGroup, perms []IPPerm) (resp *SimpleResp, err error) {
--	params := makeParams(op)
--	if group.Id != "" {
--		params["GroupId"] = group.Id
--	} else {
--		params["GroupName"] = group.Name
--	}
+-	count := 0
 -
--	for i, perm := range perms {
--		prefix := "IpPermissions." + strconv.Itoa(i+1)
--		params[prefix+".IpProtocol"] = perm.Protocol
--		params[prefix+".FromPort"] = strconv.Itoa(perm.FromPort)
--		params[prefix+".ToPort"] = strconv.Itoa(perm.ToPort)
--		for j, ip := range perm.SourceIPs {
--			params[prefix+".IpRanges."+strconv.Itoa(j+1)+".CidrIp"] = ip
+-	List(fake.ServiceClient(), ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractMonitors(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract monitors: %v", err)
+-			return false, err
 -		}
--		for j, g := range perm.SourceGroups {
--			subprefix := prefix + ".Groups." + strconv.Itoa(j+1)
--			if g.OwnerId != "" {
--				params[subprefix+".UserId"] = g.OwnerId
--			}
--			if g.Id != "" {
--				params[subprefix+".GroupId"] = g.Id
--			} else {
--				params[subprefix+".GroupName"] = g.Name
--			}
+-
+-		expected := []Monitor{
+-			Monitor{
+-				AdminStateUp: true,
+-				TenantID:     "83657cfcdfe44cd5920adaf26c48ceea",
+-				Delay:        10,
+-				MaxRetries:   1,
+-				Timeout:      1,
+-				Type:         "PING",
+-				ID:           "466c8345-28d8-4f84-a246-e04380b0461d",
+-			},
+-			Monitor{
+-				AdminStateUp:  true,
+-				TenantID:      "83657cfcdfe44cd5920adaf26c48ceea",
+-				Delay:         5,
+-				ExpectedCodes: "200",
+-				MaxRetries:    2,
+-				Timeout:       2,
+-				URLPath:       "/",
+-				Type:          "HTTP",
+-				HTTPMethod:    "GET",
+-				ID:            "5d4b5228-33b0-4e60-b225-9b727c1a20e7",
+-			},
 -		}
--	}
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return resp, nil
--}
+-		th.CheckDeepEquals(t, expected, actual)
 -
--// ResourceTag represents key-value metadata used to classify and organize
--// EC2 instances.
--//
--// See http://goo.gl/bncl3 for more details
--type Tag struct {
--	Key   string `xml:"key"`
--	Value string `xml:"value"`
+-		return true, nil
+-	})
+-
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
+-	}
 -}
 -
--// CreateTags adds or overwrites one or more tags for the specified taggable resources.
--// For a list of tagable resources, see: http://docs.aws.amazon.com/AWSEC2/latest/UserGuide/Using_Tags.html
--//
--// See http://goo.gl/Vmkqc for more details
--func (ec2 *EC2) CreateTags(resourceIds []string, tags []Tag) (resp *SimpleResp, err error) {
--	params := makeParams("CreateTags")
--	addParamsList(params, "ResourceId", resourceIds)
+-func TestDelayMustBeGreaterOrEqualThanTimeout(t *testing.T) {
+-	_, err := Create(fake.ServiceClient(), CreateOpts{
+-		Type:          "HTTP",
+-		Delay:         1,
+-		Timeout:       10,
+-		MaxRetries:    5,
+-		URLPath:       "/check",
+-		ExpectedCodes: "200-299",
+-	}).Extract()
 -
--	for j, tag := range tags {
--		params["Tag."+strconv.Itoa(j+1)+".Key"] = tag.Key
--		params["Tag."+strconv.Itoa(j+1)+".Value"] = tag.Value
+-	if err == nil {
+-		t.Fatalf("Expected error, got none")
 -	}
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
+-	_, err = Update(fake.ServiceClient(), "453105b9-1754-413f-aab1-55f1af620750", UpdateOpts{
+-		Delay:   1,
+-		Timeout: 10,
+-	}).Extract()
+-
+-	if err == nil {
+-		t.Fatalf("Expected error, got none")
 -	}
--	return resp, nil
 -}
 -
--type TagsResp struct {
--	RequestId string        `xml:"requestId"`
--	Tags      []ResourceTag `xml:"tagSet>item"`
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/lb/health_monitors", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-   "health_monitor":{
+-      "type":"HTTP",
+-      "tenant_id":"453105b9-1754-413f-aab1-55f1af620750",
+-      "delay":20,
+-      "timeout":10,
+-      "max_retries":5,
+-      "url_path":"/check",
+-      "expected_codes":"200-299"
+-   }
 -}
+-			`)
 -
--type ResourceTag struct {
--	Tag
--	ResourceId   string `xml:"resourceId"`
--	ResourceType string `xml:"resourceType"`
--}
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
 -
--func (ec2 *EC2) Tags(filter *Filter) (*TagsResp, error) {
--	params := makeParams("DescribeTags")
--	filter.addParams(params)
+-		fmt.Fprintf(w, `
+-{
+-   "health_monitor":{
+-      "id":"f3eeab00-8367-4524-b662-55e64d4cacb5",
+-      "tenant_id":"453105b9-1754-413f-aab1-55f1af620750",
+-      "type":"HTTP",
+-      "delay":20,
+-      "timeout":10,
+-      "max_retries":5,
+-      "http_method":"GET",
+-      "url_path":"/check",
+-      "expected_codes":"200-299",
+-      "admin_state_up":true,
+-      "status":"ACTIVE"
+-   }
+-}
+-		`)
+-	})
 -
--	resp := &TagsResp{}
--	if err := ec2.query(params, resp); err != nil {
--		return nil, err
--	}
+-	_, err := Create(fake.ServiceClient(), CreateOpts{
+-		Type:          "HTTP",
+-		TenantID:      "453105b9-1754-413f-aab1-55f1af620750",
+-		Delay:         20,
+-		Timeout:       10,
+-		MaxRetries:    5,
+-		URLPath:       "/check",
+-		ExpectedCodes: "200-299",
+-	}).Extract()
 -
--	return resp, nil
+-	th.AssertNoErr(t, err)
 -}
 -
--// Response to a StartInstances request.
--//
--// See http://goo.gl/awKeF for more details.
--type StartInstanceResp struct {
--	RequestId    string                `xml:"requestId"`
--	StateChanges []InstanceStateChange `xml:"instancesSet>item"`
+-func TestRequiredCreateOpts(t *testing.T) {
+-	res := Create(fake.ServiceClient(), CreateOpts{})
+-	if res.Err == nil {
+-		t.Fatalf("Expected error, got none")
+-	}
+-	res = Create(fake.ServiceClient(), CreateOpts{Type: TypeHTTP})
+-	if res.Err == nil {
+-		t.Fatalf("Expected error, got none")
+-	}
 -}
 -
--// Response to a StopInstances request.
--//
--// See http://goo.gl/436dJ for more details.
--type StopInstanceResp struct {
--	RequestId    string                `xml:"requestId"`
--	StateChanges []InstanceStateChange `xml:"instancesSet>item"`
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/lb/health_monitors/f3eeab00-8367-4524-b662-55e64d4cacb5", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-   "health_monitor":{
+-      "id":"f3eeab00-8367-4524-b662-55e64d4cacb5",
+-      "tenant_id":"453105b9-1754-413f-aab1-55f1af620750",
+-      "type":"HTTP",
+-      "delay":20,
+-      "timeout":10,
+-      "max_retries":5,
+-      "http_method":"GET",
+-      "url_path":"/check",
+-      "expected_codes":"200-299",
+-      "admin_state_up":true,
+-      "status":"ACTIVE"
+-   }
 -}
+-			`)
+-	})
 -
--// StartInstances starts an Amazon EBS-backed AMI that you've previously stopped.
--//
--// See http://goo.gl/awKeF for more details.
--func (ec2 *EC2) StartInstances(ids ...string) (resp *StartInstanceResp, err error) {
--	params := makeParams("StartInstances")
--	addParamsList(params, "InstanceId", ids)
--	resp = &StartInstanceResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return resp, nil
+-	hm, err := Get(fake.ServiceClient(), "f3eeab00-8367-4524-b662-55e64d4cacb5").Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, "f3eeab00-8367-4524-b662-55e64d4cacb5", hm.ID)
+-	th.AssertEquals(t, "453105b9-1754-413f-aab1-55f1af620750", hm.TenantID)
+-	th.AssertEquals(t, "HTTP", hm.Type)
+-	th.AssertEquals(t, 20, hm.Delay)
+-	th.AssertEquals(t, 10, hm.Timeout)
+-	th.AssertEquals(t, 5, hm.MaxRetries)
+-	th.AssertEquals(t, "GET", hm.HTTPMethod)
+-	th.AssertEquals(t, "/check", hm.URLPath)
+-	th.AssertEquals(t, "200-299", hm.ExpectedCodes)
+-	th.AssertEquals(t, true, hm.AdminStateUp)
+-	th.AssertEquals(t, "ACTIVE", hm.Status)
 -}
 -
--// StopInstances requests stopping one or more Amazon EBS-backed instances.
--//
--// See http://goo.gl/436dJ for more details.
--func (ec2 *EC2) StopInstances(ids ...string) (resp *StopInstanceResp, err error) {
--	params := makeParams("StopInstances")
--	addParamsList(params, "InstanceId", ids)
--	resp = &StopInstanceResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return resp, nil
+-func TestUpdate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/lb/health_monitors/b05e44b5-81f9-4551-b474-711a722698f7", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-   "health_monitor":{
+-      "delay": 3,
+-      "timeout": 20,
+-      "max_retries": 10,
+-      "url_path": "/another_check",
+-      "expected_codes": "301"
+-   }
 -}
+-			`)
 -
--// RebootInstance requests a reboot of one or more instances. This operation is asynchronous;
--// it only queues a request to reboot the specified instance(s). The operation will succeed
--// if the instances are valid and belong to you.
--//
--// Requests to reboot terminated instances are ignored.
--//
--// See http://goo.gl/baoUf for more details.
--func (ec2 *EC2) RebootInstances(ids ...string) (resp *SimpleResp, err error) {
--	params := makeParams("RebootInstances")
--	addParamsList(params, "InstanceId", ids)
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return resp, nil
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusAccepted)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "health_monitor": {
+-        "admin_state_up": true,
+-        "tenant_id": "4fd44f30292945e481c7b8a0c8908869",
+-        "delay": 3,
+-        "max_retries": 10,
+-        "http_method": "GET",
+-        "timeout": 20,
+-        "pools": [
+-            {
+-                "status": "PENDING_CREATE",
+-                "status_description": null,
+-                "pool_id": "6e55751f-6ad4-4e53-b8d4-02e442cd21df"
+-            }
+-        ],
+-        "type": "PING",
+-        "id": "b05e44b5-81f9-4551-b474-711a722698f7"
+-    }
 -}
+-		`)
+-	})
 -
--// The ModifyInstanceAttribute request parameters.
--type ModifyInstance struct {
--	InstanceType          string
--	BlockDevices          []BlockDeviceMapping
--	DisableAPITermination bool
--	EbsOptimized          bool
--	SecurityGroups        []SecurityGroup
--	ShutdownBehavior      string
--	KernelId              string
--	RamdiskId             string
--	SourceDestCheck       bool
--	SriovNetSupport       bool
--	UserData              []byte
+-	_, err := Update(fake.ServiceClient(), "b05e44b5-81f9-4551-b474-711a722698f7", UpdateOpts{
+-		Delay:         3,
+-		Timeout:       20,
+-		MaxRetries:    10,
+-		URLPath:       "/another_check",
+-		ExpectedCodes: "301",
+-	}).Extract()
 -
--	SetSourceDestCheck bool
+-	th.AssertNoErr(t, err)
 -}
 -
--// Response to a ModifyInstanceAttribute request.
--//
--// http://goo.gl/icuXh5 for more details.
--type ModifyInstanceResp struct {
--	RequestId string `xml:"requestId"`
--	Return    bool   `xml:"return"`
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/lb/health_monitors/b05e44b5-81f9-4551-b474-711a722698f7", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-
+-	res := Delete(fake.ServiceClient(), "b05e44b5-81f9-4551-b474-711a722698f7")
+-	th.AssertNoErr(t, res.Err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/monitors/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/monitors/results.go
+deleted file mode 100644
+index d595abd..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/monitors/results.go
++++ /dev/null
+@@ -1,147 +0,0 @@
+-package monitors
 -
--// ModifyImageAttribute modifies the specified attribute of the specified instance.
--// You can specify only one attribute at a time. To modify some attributes, the
--// instance must be stopped.
--//
--// See http://goo.gl/icuXh5 for more details.
--func (ec2 *EC2) ModifyInstance(instId string, options *ModifyInstance) (resp *ModifyInstanceResp, err error) {
--	params := makeParams("ModifyInstanceAttribute")
--	params["InstanceId"] = instId
--	addBlockDeviceParams("", params, options.BlockDevices)
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	if options.InstanceType != "" {
--		params["InstanceType.Value"] = options.InstanceType
--	}
+-// Monitor represents a load balancer health monitor. A health monitor is used
+-// to determine whether or not back-end members of the VIP's pool are usable
+-// for processing a request. A pool can have several health monitors associated
+-// with it. There are different types of health monitors supported:
+-//
+-// PING: used to ping the members using ICMP.
+-// TCP: used to connect to the members using TCP.
+-// HTTP: used to send an HTTP request to the member.
+-// HTTPS: used to send a secure HTTP request to the member.
+-//
+-// When a pool has several monitors associated with it, each member of the pool
+-// is monitored by all these monitors. If any monitor declares the member as
+-// unhealthy, then the member status is changed to INACTIVE and the member
+-// won't participate in its pool's load balancing. In other words, ALL monitors
+-// must declare the member to be healthy for it to stay ACTIVE.
+-type Monitor struct {
+-	// The unique ID for the VIP.
+-	ID string
 -
--	if options.DisableAPITermination {
--		params["DisableApiTermination.Value"] = "true"
--	}
+-	// Owner of the VIP. Only an administrative user can specify a tenant ID
+-	// other than its own.
+-	TenantID string `json:"tenant_id" mapstructure:"tenant_id"`
 -
--	if options.EbsOptimized {
--		params["EbsOptimized"] = "true"
--	}
+-	// The type of probe sent by the load balancer to verify the member state,
+-	// which is PING, TCP, HTTP, or HTTPS.
+-	Type string
 -
--	if options.ShutdownBehavior != "" {
--		params["InstanceInitiatedShutdownBehavior.Value"] = options.ShutdownBehavior
--	}
+-	// The time, in seconds, between sending probes to members.
+-	Delay int
 -
--	if options.KernelId != "" {
--		params["Kernel.Value"] = options.KernelId
--	}
+-	// The maximum number of seconds for a monitor to wait for a connection to be
+-	// established before it times out. This value must be less than the delay value.
+-	Timeout int
 -
--	if options.RamdiskId != "" {
--		params["Ramdisk.Value"] = options.RamdiskId
--	}
+-	// Number of allowed connection failures before changing the status of the
+-	// member to INACTIVE. A valid value is from 1 to 10.
+-	MaxRetries int `json:"max_retries" mapstructure:"max_retries"`
 -
--	if options.SourceDestCheck || options.SetSourceDestCheck {
--		if options.SourceDestCheck {
--			params["SourceDestCheck.Value"] = "true"
--		} else {
--			params["SourceDestCheck.Value"] = "false"
--		}
--	}
+-	// The HTTP method that the monitor uses for requests.
+-	HTTPMethod string `json:"http_method" mapstructure:"http_method"`
 -
--	if options.SriovNetSupport {
--		params["SriovNetSupport.Value"] = "simple"
--	}
+-	// The HTTP path of the request sent by the monitor to test the health of a
+-	// member. Must be a string beginning with a forward slash (/).
+-	URLPath string `json:"url_path" mapstructure:"url_path"`
 -
--	if options.UserData != nil {
--		userData := make([]byte, b64.EncodedLen(len(options.UserData)))
--		b64.Encode(userData, options.UserData)
--		params["UserData"] = string(userData)
--	}
+-	// Expected HTTP codes for a passing HTTP(S) monitor.
+-	ExpectedCodes string `json:"expected_codes" mapstructure:"expected_codes"`
 -
--	i := 1
--	for _, g := range options.SecurityGroups {
--		if g.Id != "" {
--			params["GroupId."+strconv.Itoa(i)] = g.Id
--			i++
--		}
+-	// The administrative state of the health monitor, which is up (true) or down (false).
+-	AdminStateUp bool `json:"admin_state_up" mapstructure:"admin_state_up"`
+-
+-	// The status of the health monitor. Indicates whether the health monitor is
+-	// operational.
+-	Status string
+-}
+-
+-// MonitorPage is the page returned by a pager when traversing over a
+-// collection of health monitors.
+-type MonitorPage struct {
+-	pagination.LinkedPageBase
+-}
+-
+-// NextPageURL is invoked when a paginated collection of monitors has reached
+-// the end of a page and the pager seeks to traverse over a new one. In order
+-// to do this, it needs to construct the next page's URL.
+-func (p MonitorPage) NextPageURL() (string, error) {
+-	type resp struct {
+-		Links []gophercloud.Link `mapstructure:"health_monitors_links"`
 -	}
 -
--	resp = &ModifyInstanceResp{}
--	err = ec2.query(params, resp)
+-	var r resp
+-	err := mapstructure.Decode(p.Body, &r)
 -	if err != nil {
--		resp = nil
+-		return "", err
 -	}
--	return
--}
--
--// ----------------------------------------------------------------------------
--// VPC management functions and types.
 -
--// The CreateVpc request parameters
--//
--// See http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-CreateVpc.html
--type CreateVpc struct {
--	CidrBlock       string
--	InstanceTenancy string
+-	return gophercloud.ExtractNextURL(r.Links)
 -}
 -
--// Response to a CreateVpc request
--type CreateVpcResp struct {
--	RequestId string `xml:"requestId"`
--	VPC       VPC    `xml:"vpc"`
+-// IsEmpty checks whether a PoolPage struct is empty.
+-func (p MonitorPage) IsEmpty() (bool, error) {
+-	is, err := ExtractMonitors(p)
+-	if err != nil {
+-		return true, nil
+-	}
+-	return len(is) == 0, nil
 -}
 -
--// The ModifyVpcAttribute request parameters.
--//
--// See http://docs.amazonwebservices.com/AWSEC2/latest/APIReference/index.html?ApiReference-query-DescribeVpcAttribute.html for more details.
--type ModifyVpcAttribute struct {
--	EnableDnsSupport   bool
--	EnableDnsHostnames bool
+-// ExtractMonitors accepts a Page struct, specifically a MonitorPage struct,
+-// and extracts the elements into a slice of Monitor structs. In other words,
+-// a generic collection is mapped into a relevant slice.
+-func ExtractMonitors(page pagination.Page) ([]Monitor, error) {
+-	var resp struct {
+-		Monitors []Monitor `mapstructure:"health_monitors" json:"health_monitors"`
+-	}
 -
--	SetEnableDnsSupport   bool
--	SetEnableDnsHostnames bool
+-	err := mapstructure.Decode(page.(MonitorPage).Body, &resp)
+-
+-	return resp.Monitors, err
 -}
 -
--// Response to a DescribeVpcAttribute request.
--//
--// See http://docs.amazonwebservices.com/AWSEC2/latest/APIReference/index.html?ApiReference-query-DescribeVpcAttribute.html for more details.
--type VpcAttributeResp struct {
--	RequestId          string `xml:"requestId"`
--	VpcId              string `xml:"vpcId"`
--	EnableDnsSupport   bool   `xml:"enableDnsSupport>value"`
--	EnableDnsHostnames bool   `xml:"enableDnsHostnames>value"`
+-type commonResult struct {
+-	gophercloud.Result
 -}
 -
--// CreateInternetGateway request parameters.
--//
--// http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-CreateInternetGateway.html
--type CreateInternetGateway struct{}
+-// Extract is a function that accepts a result and extracts a monitor.
+-func (r commonResult) Extract() (*Monitor, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
+-	}
 -
--// CreateInternetGateway response
--type CreateInternetGatewayResp struct {
--	RequestId       string          `xml:"requestId"`
--	InternetGateway InternetGateway `xml:"internetGateway"`
--}
+-	var res struct {
+-		Monitor *Monitor `json:"health_monitor" mapstructure:"health_monitor"`
+-	}
 -
--// The CreateRouteTable request parameters.
--//
--// http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-CreateRouteTable.html
--type CreateRouteTable struct {
--	VpcId string
--}
+-	err := mapstructure.Decode(r.Body, &res)
 -
--// Response to a CreateRouteTable request.
--type CreateRouteTableResp struct {
--	RequestId  string     `xml:"requestId"`
--	RouteTable RouteTable `xml:"routeTable"`
+-	return res.Monitor, err
 -}
 -
--// CreateRoute request parameters
--//
--// http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-CreateRoute.html
--type CreateRoute struct {
--	RouteTableId           string
--	DestinationCidrBlock   string
--	GatewayId              string
--	InstanceId             string
--	NetworkInterfaceId     string
--	VpcPeeringConnectionId string
--}
--type ReplaceRoute struct {
--	RouteTableId           string
--	DestinationCidrBlock   string
--	GatewayId              string
--	InstanceId             string
--	NetworkInterfaceId     string
--	VpcPeeringConnectionId string
+-// CreateResult represents the result of a create operation.
+-type CreateResult struct {
+-	commonResult
 -}
 -
--type AssociateRouteTableResp struct {
--	RequestId     string `xml:"requestId"`
--	AssociationId string `xml:"associationId"`
--}
--type ReassociateRouteTableResp struct {
--	RequestId     string `xml:"requestId"`
--	AssociationId string `xml:"newAssociationId"`
+-// GetResult represents the result of a get operation.
+-type GetResult struct {
+-	commonResult
 -}
 -
--// The CreateSubnet request parameters
--//
--// http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-CreateSubnet.html
--type CreateSubnet struct {
--	VpcId            string
--	CidrBlock        string
--	AvailabilityZone string
+-// UpdateResult represents the result of an update operation.
+-type UpdateResult struct {
+-	commonResult
 -}
 -
--// Response to a CreateSubnet request
--type CreateSubnetResp struct {
--	RequestId string `xml:"requestId"`
--	Subnet    Subnet `xml:"subnet"`
+-// DeleteResult represents the result of a delete operation.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/monitors/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/monitors/urls.go
+deleted file mode 100644
+index 46e84bb..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/monitors/urls.go
++++ /dev/null
+@@ -1,16 +0,0 @@
+-package monitors
 -
--// Response to a DescribeInternetGateways request.
--type InternetGatewaysResp struct {
--	RequestId        string            `xml:"requestId"`
--	InternetGateways []InternetGateway `xml:"internetGatewaySet>item"`
+-import "github.com/rackspace/gophercloud"
+-
+-const (
+-	rootPath     = "lb"
+-	resourcePath = "health_monitors"
+-)
+-
+-func rootURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL(rootPath, resourcePath)
 -}
 -
--// Response to a DescribeRouteTables request.
--type RouteTablesResp struct {
--	RequestId   string       `xml:"requestId"`
--	RouteTables []RouteTable `xml:"routeTableSet>item"`
+-func resourceURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL(rootPath, resourcePath, id)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/pools/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/pools/requests.go
+deleted file mode 100644
+index ca8d33b..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/pools/requests.go
++++ /dev/null
+@@ -1,205 +0,0 @@
+-package pools
 -
--// Response to a DescribeVpcs request.
--type VpcsResp struct {
--	RequestId string `xml:"requestId"`
--	VPCs      []VPC  `xml:"vpcSet>item"`
+-import (
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
+-
+-// ListOpts allows the filtering and sorting of paginated collections through
+-// the API. Filtering is achieved by passing in struct field values that map to
+-// the floating IP attributes you want to see returned. SortKey allows you to
+-// sort by a particular network attribute. SortDir sets the direction, and is
+-// either `asc' or `desc'. Marker and Limit are used for pagination.
+-type ListOpts struct {
+-	Status       string `q:"status"`
+-	LBMethod     string `q:"lb_method"`
+-	Protocol     string `q:"protocol"`
+-	SubnetID     string `q:"subnet_id"`
+-	TenantID     string `q:"tenant_id"`
+-	AdminStateUp *bool  `q:"admin_state_up"`
+-	Name         string `q:"name"`
+-	ID           string `q:"id"`
+-	VIPID        string `q:"vip_id"`
+-	Limit        int    `q:"limit"`
+-	Marker       string `q:"marker"`
+-	SortKey      string `q:"sort_key"`
+-	SortDir      string `q:"sort_dir"`
+-}
+-
+-// List returns a Pager which allows you to iterate over a collection of
+-// pools. It accepts a ListOpts struct, which allows you to filter and sort
+-// the returned collection for greater efficiency.
+-//
+-// Default policy settings return only those pools that are owned by the
+-// tenant who submits the request, unless an admin user submits the request.
+-func List(c *gophercloud.ServiceClient, opts ListOpts) pagination.Pager {
+-	q, err := gophercloud.BuildQueryString(&opts)
+-	if err != nil {
+-		return pagination.Pager{Err: err}
+-	}
+-	u := rootURL(c) + q.String()
+-	return pagination.NewPager(c, u, func(r pagination.PageResult) pagination.Page {
+-		return PoolPage{pagination.LinkedPageBase{PageResult: r}}
+-	})
 -}
 -
--// Internet Gateway
--type InternetGateway struct {
--	InternetGatewayId string                      `xml:"internetGatewayId"`
--	Attachments       []InternetGatewayAttachment `xml:"attachmentSet>item"`
--	Tags              []Tag                       `xml:"tagSet>item"`
+-// Supported attributes for create/update operations.
+-const (
+-	LBMethodRoundRobin       = "ROUND_ROBIN"
+-	LBMethodLeastConnections = "LEAST_CONNECTIONS"
+-
+-	ProtocolTCP   = "TCP"
+-	ProtocolHTTP  = "HTTP"
+-	ProtocolHTTPS = "HTTPS"
+-)
+-
+-// CreateOpts contains all the values needed to create a new pool.
+-type CreateOpts struct {
+-	// Only required if the caller has an admin role and wants to create a pool
+-	// for another tenant.
+-	TenantID string
+-
+-	// Required. Name of the pool.
+-	Name string
+-
+-	// Required. The protocol used by the pool members, you can use either
+-	// ProtocolTCP, ProtocolHTTP, or ProtocolHTTPS.
+-	Protocol string
+-
+-	// The network on which the members of the pool will be located. Only members
+-	// that are on this network can be added to the pool.
+-	SubnetID string
+-
+-	// The algorithm used to distribute load between the members of the pool. The
+-	// current specification supports LBMethodRoundRobin and
+-	// LBMethodLeastConnections as valid values for this attribute.
+-	LBMethod string
 -}
 -
--type InternetGatewayAttachment struct {
--	VpcId string `xml:"vpcId"`
--	State string `xml:"state"`
+-// Create accepts a CreateOpts struct and uses the values to create a new
+-// load balancer pool.
+-func Create(c *gophercloud.ServiceClient, opts CreateOpts) CreateResult {
+-	type pool struct {
+-		Name     string `json:"name"`
+-		TenantID string `json:"tenant_id,omitempty"`
+-		Protocol string `json:"protocol"`
+-		SubnetID string `json:"subnet_id"`
+-		LBMethod string `json:"lb_method"`
+-	}
+-	type request struct {
+-		Pool pool `json:"pool"`
+-	}
+-
+-	reqBody := request{Pool: pool{
+-		Name:     opts.Name,
+-		TenantID: opts.TenantID,
+-		Protocol: opts.Protocol,
+-		SubnetID: opts.SubnetID,
+-		LBMethod: opts.LBMethod,
+-	}}
+-
+-	var res CreateResult
+-	_, res.Err = perigee.Request("POST", rootURL(c), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{201},
+-	})
+-	return res
 -}
 -
--// Routing Table
--type RouteTable struct {
--	RouteTableId string                  `xml:"routeTableId"`
--	VpcId        string                  `xml:"vpcId"`
--	Associations []RouteTableAssociation `xml:"associationSet>item"`
--	Routes       []Route                 `xml:"routeSet>item"`
--	Tags         []Tag                   `xml:"tagSet>item"`
+-// Get retrieves a particular pool based on its unique ID.
+-func Get(c *gophercloud.ServiceClient, id string) GetResult {
+-	var res GetResult
+-	_, res.Err = perigee.Request("GET", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return res
 -}
 -
--type RouteTableAssociation struct {
--	AssociationId string `xml:"routeTableAssociationId"`
--	RouteTableId  string `xml:"routeTableId"`
--	SubnetId      string `xml:"subnetId"`
--	Main          bool   `xml:"main"`
+-// UpdateOpts contains the values used when updating a pool.
+-type UpdateOpts struct {
+-	// Required. Name of the pool.
+-	Name string
+-
+-	// The algorithm used to distribute load between the members of the pool. The
+-	// current specification supports LBMethodRoundRobin and
+-	// LBMethodLeastConnections as valid values for this attribute.
+-	LBMethod string
 -}
 -
--type Route struct {
--	DestinationCidrBlock   string `xml:"destinationCidrBlock"`
--	GatewayId              string `xml:"gatewayId"`
--	InstanceId             string `xml:"instanceId"`
--	InstanceOwnerId        string `xml:"instanceOwnerId"`
--	NetworkInterfaceId     string `xml:"networkInterfaceId"`
--	State                  string `xml:"state"`
--	Origin                 string `xml:"origin"`
--	VpcPeeringConnectionId string `xml:"vpcPeeringConnectionId"`
+-// Update allows pools to be updated.
+-func Update(c *gophercloud.ServiceClient, id string, opts UpdateOpts) UpdateResult {
+-	type pool struct {
+-		Name     string `json:"name,"`
+-		LBMethod string `json:"lb_method"`
+-	}
+-	type request struct {
+-		Pool pool `json:"pool"`
+-	}
+-
+-	reqBody := request{Pool: pool{
+-		Name:     opts.Name,
+-		LBMethod: opts.LBMethod,
+-	}}
+-
+-	// Send request to API
+-	var res UpdateResult
+-	_, res.Err = perigee.Request("PUT", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return res
 -}
 -
--// Subnet
--type Subnet struct {
--	SubnetId                string `xml:"subnetId"`
--	State                   string `xml:"state"`
--	VpcId                   string `xml:"vpcId"`
--	CidrBlock               string `xml:"cidrBlock"`
--	AvailableIpAddressCount int    `xml:"availableIpAddressCount"`
--	AvailabilityZone        string `xml:"availabilityZone"`
--	DefaultForAZ            bool   `xml:"defaultForAz"`
--	MapPublicIpOnLaunch     bool   `xml:"mapPublicIpOnLaunch"`
--	Tags                    []Tag  `xml:"tagSet>item"`
+-// Delete will permanently delete a particular pool based on its unique ID.
+-func Delete(c *gophercloud.ServiceClient, id string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{204},
+-	})
+-	return res
 -}
 -
--// VPC represents a single VPC.
--type VPC struct {
--	VpcId           string `xml:"vpcId"`
--	State           string `xml:"state"`
--	CidrBlock       string `xml:"cidrBlock"`
--	DHCPOptionsID   string `xml:"dhcpOptionsId"`
--	InstanceTenancy string `xml:"instanceTenancy"`
--	IsDefault       bool   `xml:"isDefault"`
--	Tags            []Tag  `xml:"tagSet>item"`
+-// AssociateMonitor will associate a health monitor with a particular pool.
+-// Once associated, the health monitor will start monitoring the members of the
+-// pool and will deactivate these members if they are deemed unhealthy. A
+-// member can be deactivated (status set to INACTIVE) if any of health monitors
+-// finds it unhealthy.
+-func AssociateMonitor(c *gophercloud.ServiceClient, poolID, monitorID string) AssociateResult {
+-	type hm struct {
+-		ID string `json:"id"`
+-	}
+-	type request struct {
+-		Monitor hm `json:"health_monitor"`
+-	}
+-
+-	reqBody := request{hm{ID: monitorID}}
+-
+-	var res AssociateResult
+-	_, res.Err = perigee.Request("POST", associateURL(c, poolID), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{201},
+-	})
+-	return res
 -}
 -
--// Response to a DescribeSubnets request.
--type SubnetsResp struct {
--	RequestId string   `xml:"requestId"`
--	Subnets   []Subnet `xml:"subnetSet>item"`
+-// DisassociateMonitor will disassociate a health monitor with a particular
+-// pool. When dissociation is successful, the health monitor will no longer
+-// check for the health of the members of the pool.
+-func DisassociateMonitor(c *gophercloud.ServiceClient, poolID, monitorID string) AssociateResult {
+-	var res AssociateResult
+-	_, res.Err = perigee.Request("DELETE", disassociateURL(c, poolID, monitorID), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{204},
+-	})
+-	return res
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/pools/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/pools/requests_test.go
+deleted file mode 100644
+index 6da29a6..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/pools/requests_test.go
++++ /dev/null
+@@ -1,317 +0,0 @@
+-package pools
 -
--// Create a new VPC.
--func (ec2 *EC2) CreateVpc(options *CreateVpc) (resp *CreateVpcResp, err error) {
--	params := makeParams("CreateVpc")
--	params["CidrBlock"] = options.CidrBlock
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--	if options.InstanceTenancy != "" {
--		params["InstanceTenancy"] = options.InstanceTenancy
--	}
+-	fake "github.com/rackspace/gophercloud/openstack/networking/v2/common"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--	resp = &CreateVpcResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
+-func TestURLs(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	return
+-	th.AssertEquals(t, th.Endpoint()+"v2.0/lb/pools", rootURL(fake.ServiceClient()))
 -}
 -
--// Delete a VPC.
--func (ec2 *EC2) DeleteVpc(id string) (resp *SimpleResp, err error) {
--	params := makeParams("DeleteVpc")
--	params["VpcId"] = id
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return
--}
+-	th.Mux.HandleFunc("/v2.0/lb/pools", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--// DescribeVpcs
--//
--// See http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeVpcs.html
--func (ec2 *EC2) DescribeVpcs(ids []string, filter *Filter) (resp *VpcsResp, err error) {
--	params := makeParams("DescribeVpcs")
--	addParamsList(params, "VpcId", ids)
--	filter.addParams(params)
--	resp = &VpcsResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--	return
+-		fmt.Fprintf(w, `
+-{
+-   "pools":[
+-      {
+-         "status":"ACTIVE",
+-         "lb_method":"ROUND_ROBIN",
+-         "protocol":"HTTP",
+-         "description":"",
+-         "health_monitors":[
+-            "466c8345-28d8-4f84-a246-e04380b0461d",
+-            "5d4b5228-33b0-4e60-b225-9b727c1a20e7"
+-         ],
+-         "members":[
+-            "701b531b-111a-4f21-ad85-4795b7b12af6",
+-            "beb53b4d-230b-4abd-8118-575b8fa006ef"
+-         ],
+-         "status_description": null,
+-         "id":"72741b06-df4d-4715-b142-276b6bce75ab",
+-         "vip_id":"4ec89087-d057-4e2c-911f-60a3b47ee304",
+-         "name":"app_pool",
+-         "admin_state_up":true,
+-         "subnet_id":"8032909d-47a1-4715-90af-5153ffe39861",
+-         "tenant_id":"83657cfcdfe44cd5920adaf26c48ceea",
+-         "health_monitors_status": [],
+-         "provider": "haproxy"
+-      }
+-   ]
 -}
+-			`)
+-	})
 -
--// VpcAttribute describes an attribute of a VPC.
--// You can specify only one attribute at a time.
--// Valid attributes are:
--//    enableDnsSupport | enableDnsHostnames
--//
--// See http://docs.amazonwebservices.com/AWSEC2/latest/APIReference/index.html?ApiReference-query-DescribeVpcAttribute.html for more details.
--func (ec2 *EC2) VpcAttribute(vpcId, attribute string) (resp *VpcAttributeResp, err error) {
--	params := makeParams("DescribeVpcAttribute")
--	params["VpcId"] = vpcId
--	params["Attribute"] = attribute
+-	count := 0
+-
+-	List(fake.ServiceClient(), ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractPools(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract pools: %v", err)
+-			return false, err
+-		}
+-
+-		expected := []Pool{
+-			Pool{
+-				Status:      "ACTIVE",
+-				LBMethod:    "ROUND_ROBIN",
+-				Protocol:    "HTTP",
+-				Description: "",
+-				MonitorIDs: []string{
+-					"466c8345-28d8-4f84-a246-e04380b0461d",
+-					"5d4b5228-33b0-4e60-b225-9b727c1a20e7",
+-				},
+-				SubnetID:     "8032909d-47a1-4715-90af-5153ffe39861",
+-				TenantID:     "83657cfcdfe44cd5920adaf26c48ceea",
+-				AdminStateUp: true,
+-				Name:         "app_pool",
+-				MemberIDs: []string{
+-					"701b531b-111a-4f21-ad85-4795b7b12af6",
+-					"beb53b4d-230b-4abd-8118-575b8fa006ef",
+-				},
+-				ID:       "72741b06-df4d-4715-b142-276b6bce75ab",
+-				VIPID:    "4ec89087-d057-4e2c-911f-60a3b47ee304",
+-				Provider: "haproxy",
+-			},
+-		}
 -
--	resp = &VpcAttributeResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
+-		th.CheckDeepEquals(t, expected, actual)
+-
+-		return true, nil
+-	})
+-
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
 -	}
--	return
 -}
 -
--// ModifyVpcAttribute modifies the specified attribute of the specified VPC.
--//
--// See http://docs.amazonwebservices.com/AWSEC2/latest/APIReference/index.html?ApiReference-query-ModifyVpcAttribute.html for more details.
--func (ec2 *EC2) ModifyVpcAttribute(vpcId string, options *ModifyVpcAttribute) (*SimpleResp, error) {
--	params := makeParams("ModifyVpcAttribute")
--
--	params["VpcId"] = vpcId
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/lb/pools", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "pool": {
+-        "lb_method": "ROUND_ROBIN",
+-        "protocol": "HTTP",
+-        "name": "Example pool",
+-        "subnet_id": "1981f108-3c48-48d2-b908-30f7d28532c9",
+-        "tenant_id": "2ffc6e22aae24e4795f87155d24c896f"
+-    }
+-}
+-			`)
 -
--	if options.SetEnableDnsSupport {
--		params["EnableDnsSupport.Value"] = strconv.FormatBool(options.EnableDnsSupport)
--	}
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
 -
--	if options.SetEnableDnsHostnames {
--		params["EnableDnsHostnames.Value"] = strconv.FormatBool(options.EnableDnsHostnames)
--	}
+-		fmt.Fprintf(w, `
+-{
+-    "pool": {
+-        "status": "PENDING_CREATE",
+-        "lb_method": "ROUND_ROBIN",
+-        "protocol": "HTTP",
+-        "description": "",
+-        "health_monitors": [],
+-        "members": [],
+-        "status_description": null,
+-        "id": "69055154-f603-4a28-8951-7cc2d9e54a9a",
+-        "vip_id": null,
+-        "name": "Example pool",
+-        "admin_state_up": true,
+-        "subnet_id": "1981f108-3c48-48d2-b908-30f7d28532c9",
+-        "tenant_id": "2ffc6e22aae24e4795f87155d24c896f",
+-        "health_monitors_status": []
+-    }
+-}
+-		`)
+-	})
 -
--	resp := &SimpleResp{}
--	if err := ec2.query(params, resp); err != nil {
--		return nil, err
+-	options := CreateOpts{
+-		LBMethod: LBMethodRoundRobin,
+-		Protocol: "HTTP",
+-		Name:     "Example pool",
+-		SubnetID: "1981f108-3c48-48d2-b908-30f7d28532c9",
+-		TenantID: "2ffc6e22aae24e4795f87155d24c896f",
 -	}
+-	p, err := Create(fake.ServiceClient(), options).Extract()
+-	th.AssertNoErr(t, err)
 -
--	return resp, nil
+-	th.AssertEquals(t, "PENDING_CREATE", p.Status)
+-	th.AssertEquals(t, "ROUND_ROBIN", p.LBMethod)
+-	th.AssertEquals(t, "HTTP", p.Protocol)
+-	th.AssertEquals(t, "", p.Description)
+-	th.AssertDeepEquals(t, []string{}, p.MonitorIDs)
+-	th.AssertDeepEquals(t, []string{}, p.MemberIDs)
+-	th.AssertEquals(t, "69055154-f603-4a28-8951-7cc2d9e54a9a", p.ID)
+-	th.AssertEquals(t, "Example pool", p.Name)
+-	th.AssertEquals(t, "1981f108-3c48-48d2-b908-30f7d28532c9", p.SubnetID)
+-	th.AssertEquals(t, "2ffc6e22aae24e4795f87155d24c896f", p.TenantID)
 -}
 -
--// Create a new subnet.
--func (ec2 *EC2) CreateSubnet(options *CreateSubnet) (resp *CreateSubnetResp, err error) {
--	params := makeParams("CreateSubnet")
--	params["AvailabilityZone"] = options.AvailabilityZone
--	params["CidrBlock"] = options.CidrBlock
--	params["VpcId"] = options.VpcId
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	resp = &CreateSubnetResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
+-	th.Mux.HandleFunc("/v2.0/lb/pools/332abe93-f488-41ba-870b-2ac66be7f853", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--	return
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-   "pool":{
+-      "id":"332abe93-f488-41ba-870b-2ac66be7f853",
+-      "tenant_id":"19eaa775-cf5d-49bc-902e-2f85f668d995",
+-      "name":"Example pool",
+-      "description":"",
+-      "protocol":"tcp",
+-      "lb_algorithm":"ROUND_ROBIN",
+-      "session_persistence":{
+-      },
+-      "healthmonitor_id":null,
+-      "members":[
+-      ],
+-      "admin_state_up":true,
+-      "status":"ACTIVE"
+-   }
 -}
+-			`)
+-	})
 -
--// Delete a Subnet.
--func (ec2 *EC2) DeleteSubnet(id string) (resp *SimpleResp, err error) {
--	params := makeParams("DeleteSubnet")
--	params["SubnetId"] = id
+-	n, err := Get(fake.ServiceClient(), "332abe93-f488-41ba-870b-2ac66be7f853").Extract()
+-	th.AssertNoErr(t, err)
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return
+-	th.AssertEquals(t, n.ID, "332abe93-f488-41ba-870b-2ac66be7f853")
 -}
 -
--// DescribeSubnets
--//
--// http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeSubnets.html
--func (ec2 *EC2) DescribeSubnets(ids []string, filter *Filter) (resp *SubnetsResp, err error) {
--	params := makeParams("DescribeSubnets")
--	addParamsList(params, "SubnetId", ids)
--	filter.addParams(params)
+-func TestUpdate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/lb/pools/332abe93-f488-41ba-870b-2ac66be7f853", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-   "pool":{
+-      "name":"SuperPool",
+-      "lb_method": "LEAST_CONNECTIONS"
+-   }
+-}
+-			`)
 -
--	resp = &SubnetsResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--	return
+-		fmt.Fprintf(w, `
+-{
+-   "pool":{
+-      "status":"PENDING_UPDATE",
+-      "lb_method":"LEAST_CONNECTIONS",
+-      "protocol":"TCP",
+-      "description":"",
+-      "health_monitors":[
+-
+-      ],
+-      "subnet_id":"8032909d-47a1-4715-90af-5153ffe39861",
+-      "tenant_id":"83657cfcdfe44cd5920adaf26c48ceea",
+-      "admin_state_up":true,
+-      "name":"SuperPool",
+-      "members":[
+-
+-      ],
+-      "id":"61b1f87a-7a21-4ad3-9dda-7f81d249944f",
+-      "vip_id":null
+-   }
 -}
+-		`)
+-	})
 -
--// Create a new internet gateway.
--func (ec2 *EC2) CreateInternetGateway(
--	options *CreateInternetGateway) (resp *CreateInternetGatewayResp, err error) {
--	params := makeParams("CreateInternetGateway")
+-	options := UpdateOpts{Name: "SuperPool", LBMethod: LBMethodLeastConnections}
 -
--	resp = &CreateInternetGatewayResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
+-	n, err := Update(fake.ServiceClient(), "332abe93-f488-41ba-870b-2ac66be7f853", options).Extract()
+-	th.AssertNoErr(t, err)
 -
--	return
+-	th.AssertEquals(t, "SuperPool", n.Name)
+-	th.AssertDeepEquals(t, "LEAST_CONNECTIONS", n.LBMethod)
 -}
 -
--// Attach an InternetGateway.
--func (ec2 *EC2) AttachInternetGateway(id, vpcId string) (resp *SimpleResp, err error) {
--	params := makeParams("AttachInternetGateway")
--	params["InternetGatewayId"] = id
--	params["VpcId"] = vpcId
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return
+-	th.Mux.HandleFunc("/v2.0/lb/pools/332abe93-f488-41ba-870b-2ac66be7f853", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-
+-	res := Delete(fake.ServiceClient(), "332abe93-f488-41ba-870b-2ac66be7f853")
+-	th.AssertNoErr(t, res.Err)
 -}
 -
--// Detach an InternetGateway.
--func (ec2 *EC2) DetachInternetGateway(id, vpcId string) (resp *SimpleResp, err error) {
--	params := makeParams("DetachInternetGateway")
--	params["InternetGatewayId"] = id
--	params["VpcId"] = vpcId
+-func TestAssociateHealthMonitor(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return
+-	th.Mux.HandleFunc("/v2.0/lb/pools/332abe93-f488-41ba-870b-2ac66be7f853/health_monitors", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-   "health_monitor":{
+-      "id":"b624decf-d5d3-4c66-9a3d-f047e7786181"
+-   }
 -}
+-			`)
 -
--// Delete an InternetGateway.
--func (ec2 *EC2) DeleteInternetGateway(id string) (resp *SimpleResp, err error) {
--	params := makeParams("DeleteInternetGateway")
--	params["InternetGatewayId"] = id
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
+-	})
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return
+-	_, err := AssociateMonitor(fake.ServiceClient(), "332abe93-f488-41ba-870b-2ac66be7f853", "b624decf-d5d3-4c66-9a3d-f047e7786181").Extract()
+-	th.AssertNoErr(t, err)
 -}
 -
--// DescribeInternetGateways
--//
--// http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeInternetGateways.html
--func (ec2 *EC2) DescribeInternetGateways(ids []string, filter *Filter) (resp *InternetGatewaysResp, err error) {
--	params := makeParams("DescribeInternetGateways")
--	addParamsList(params, "InternetGatewayId", ids)
--	filter.addParams(params)
+-func TestDisassociateHealthMonitor(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	resp = &InternetGatewaysResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
+-	th.Mux.HandleFunc("/v2.0/lb/pools/332abe93-f488-41ba-870b-2ac66be7f853/health_monitors/b624decf-d5d3-4c66-9a3d-f047e7786181", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		w.WriteHeader(http.StatusNoContent)
+-	})
 -
--	return
+-	res := DisassociateMonitor(fake.ServiceClient(), "332abe93-f488-41ba-870b-2ac66be7f853", "b624decf-d5d3-4c66-9a3d-f047e7786181")
+-	th.AssertNoErr(t, res.Err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/pools/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/pools/results.go
+deleted file mode 100644
+index 07ec85e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/pools/results.go
++++ /dev/null
+@@ -1,146 +0,0 @@
+-package pools
 -
--// Create a new routing table.
--func (ec2 *EC2) CreateRouteTable(
--	options *CreateRouteTable) (resp *CreateRouteTableResp, err error) {
--	params := makeParams("CreateRouteTable")
--	params["VpcId"] = options.VpcId
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	resp = &CreateRouteTableResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
+-// Pool represents a logical set of devices, such as web servers, that you
+-// group together to receive and process traffic. The load balancing function
+-// chooses a member of the pool according to the configured load balancing
+-// method to handle the new requests or connections received on the VIP address.
+-// There is only one pool per virtual IP.
+-type Pool struct {
+-	// The status of the pool. Indicates whether the pool is operational.
+-	Status string
 -
--	return
--}
+-	// The load-balancer algorithm, which is round-robin, least-connections, and
+-	// so on. This value, which must be supported, is dependent on the provider.
+-	// Round-robin must be supported.
+-	LBMethod string `json:"lb_method" mapstructure:"lb_method"`
 -
--// Delete a RouteTable.
--func (ec2 *EC2) DeleteRouteTable(id string) (resp *SimpleResp, err error) {
--	params := makeParams("DeleteRouteTable")
--	params["RouteTableId"] = id
+-	// The protocol of the pool, which is TCP, HTTP, or HTTPS.
+-	Protocol string
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return
--}
+-	// Description for the pool.
+-	Description string
 -
--// DescribeRouteTables
--//
--// http://docs.aws.amazon.com/AWSEC2/latest/APIReference/ApiReference-query-DescribeRouteTables.html
--func (ec2 *EC2) DescribeRouteTables(ids []string, filter *Filter) (resp *RouteTablesResp, err error) {
--	params := makeParams("DescribeRouteTables")
--	addParamsList(params, "RouteTableId", ids)
--	filter.addParams(params)
+-	// The IDs of associated monitors which check the health of the pool members.
+-	MonitorIDs []string `json:"health_monitors" mapstructure:"health_monitors"`
 -
--	resp = &RouteTablesResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
+-	// The network on which the members of the pool will be located. Only members
+-	// that are on this network can be added to the pool.
+-	SubnetID string `json:"subnet_id" mapstructure:"subnet_id"`
 -
--	return
--}
+-	// Owner of the pool. Only an administrative user can specify a tenant ID
+-	// other than its own.
+-	TenantID string `json:"tenant_id" mapstructure:"tenant_id"`
 -
--// Associate a routing table.
--func (ec2 *EC2) AssociateRouteTable(id, subnetId string) (*AssociateRouteTableResp, error) {
--	params := makeParams("AssociateRouteTable")
--	params["RouteTableId"] = id
--	params["SubnetId"] = subnetId
+-	// The administrative state of the pool, which is up (true) or down (false).
+-	AdminStateUp bool `json:"admin_state_up" mapstructure:"admin_state_up"`
 -
--	resp := &AssociateRouteTableResp{}
--	err := ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return resp, nil
--}
+-	// Pool name. Does not have to be unique.
+-	Name string
 -
--// Disassociate a routing table.
--func (ec2 *EC2) DisassociateRouteTable(id string) (*SimpleResp, error) {
--	params := makeParams("DisassociateRouteTable")
--	params["AssociationId"] = id
+-	// List of member IDs that belong to the pool.
+-	MemberIDs []string `json:"members" mapstructure:"members"`
 -
--	resp := &SimpleResp{}
--	err := ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return resp, nil
--}
+-	// The unique ID for the pool.
+-	ID string
 -
--// Re-associate a routing table.
--func (ec2 *EC2) ReassociateRouteTable(id, routeTableId string) (*ReassociateRouteTableResp, error) {
--	params := makeParams("ReplaceRouteTableAssociation")
--	params["AssociationId"] = id
--	params["RouteTableId"] = routeTableId
+-	// The ID of the virtual IP associated with this pool
+-	VIPID string `json:"vip_id" mapstructure:"vip_id"`
 -
--	resp := &ReassociateRouteTableResp{}
--	err := ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return resp, nil
+-	// The provider
+-	Provider string
 -}
 -
--// Create a new route.
--func (ec2 *EC2) CreateRoute(options *CreateRoute) (resp *SimpleResp, err error) {
--	params := makeParams("CreateRoute")
--	params["RouteTableId"] = options.RouteTableId
--	params["DestinationCidrBlock"] = options.DestinationCidrBlock
+-// PoolPage is the page returned by a pager when traversing over a
+-// collection of pools.
+-type PoolPage struct {
+-	pagination.LinkedPageBase
+-}
 -
--	if v := options.GatewayId; v != "" {
--		params["GatewayId"] = v
--	}
--	if v := options.InstanceId; v != "" {
--		params["InstanceId"] = v
--	}
--	if v := options.NetworkInterfaceId; v != "" {
--		params["NetworkInterfaceId"] = v
--	}
--	if v := options.VpcPeeringConnectionId; v != "" {
--		params["VpcPeeringConnectionId"] = v
+-// NextPageURL is invoked when a paginated collection of pools has reached
+-// the end of a page and the pager seeks to traverse over a new one. In order
+-// to do this, it needs to construct the next page's URL.
+-func (p PoolPage) NextPageURL() (string, error) {
+-	type resp struct {
+-		Links []gophercloud.Link `mapstructure:"pools_links"`
 -	}
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
+-	var r resp
+-	err := mapstructure.Decode(p.Body, &r)
 -	if err != nil {
--		return nil, err
+-		return "", err
 -	}
--	return
--}
 -
--// Delete a Route.
--func (ec2 *EC2) DeleteRoute(routeTableId, cidr string) (resp *SimpleResp, err error) {
--	params := makeParams("DeleteRoute")
--	params["RouteTableId"] = routeTableId
--	params["DestinationCidrBlock"] = cidr
+-	return gophercloud.ExtractNextURL(r.Links)
+-}
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
+-// IsEmpty checks whether a PoolPage struct is empty.
+-func (p PoolPage) IsEmpty() (bool, error) {
+-	is, err := ExtractPools(p)
 -	if err != nil {
--		return nil, err
+-		return true, nil
 -	}
--	return
+-	return len(is) == 0, nil
 -}
 -
--// Replace a new route.
--func (ec2 *EC2) ReplaceRoute(options *ReplaceRoute) (resp *SimpleResp, err error) {
--	params := makeParams("ReplaceRoute")
--	params["RouteTableId"] = options.RouteTableId
--	params["DestinationCidrBlock"] = options.DestinationCidrBlock
--
--	if v := options.GatewayId; v != "" {
--		params["GatewayId"] = v
--	}
--	if v := options.InstanceId; v != "" {
--		params["InstanceId"] = v
--	}
--	if v := options.NetworkInterfaceId; v != "" {
--		params["NetworkInterfaceId"] = v
+-// ExtractPools accepts a Page struct, specifically a RouterPage struct,
+-// and extracts the elements into a slice of Router structs. In other words,
+-// a generic collection is mapped into a relevant slice.
+-func ExtractPools(page pagination.Page) ([]Pool, error) {
+-	var resp struct {
+-		Pools []Pool `mapstructure:"pools" json:"pools"`
 -	}
--	if v := options.VpcPeeringConnectionId; v != "" {
--		params["VpcPeeringConnectionId"] = v
+-
+-	err := mapstructure.Decode(page.(PoolPage).Body, &resp)
+-
+-	return resp.Pools, err
+-}
+-
+-type commonResult struct {
+-	gophercloud.Result
+-}
+-
+-// Extract is a function that accepts a result and extracts a router.
+-func (r commonResult) Extract() (*Pool, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
 -	}
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
+-	var res struct {
+-		Pool *Pool `json:"pool"`
 -	}
--	return
+-
+-	err := mapstructure.Decode(r.Body, &res)
+-
+-	return res.Pool, err
 -}
 -
--// The ResetImageAttribute request parameters.
--type ResetImageAttribute struct {
--	Attribute string
+-// CreateResult represents the result of a create operation.
+-type CreateResult struct {
+-	commonResult
 -}
 -
--// ResetImageAttribute resets an attribute of an AMI to its default value.
--//
--// http://goo.gl/r6ZCPm for more details.
--func (ec2 *EC2) ResetImageAttribute(imageId string, options *ResetImageAttribute) (resp *SimpleResp, err error) {
--	params := makeParams("ResetImageAttribute")
--	params["ImageId"] = imageId
+-// GetResult represents the result of a get operation.
+-type GetResult struct {
+-	commonResult
+-}
 -
--	if options.Attribute != "" {
--		params["Attribute"] = options.Attribute
--	}
+-// UpdateResult represents the result of an update operation.
+-type UpdateResult struct {
+-	commonResult
+-}
 -
--	resp = &SimpleResp{}
--	err = ec2.query(params, resp)
--	if err != nil {
--		return nil, err
--	}
--	return
+-// DeleteResult represents the result of a delete operation.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2_test.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2_test.go
+-
+-// AssociateResult represents the result of an association operation.
+-type AssociateResult struct {
+-	commonResult
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/pools/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/pools/urls.go
 deleted file mode 100644
-index 849bfe2..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2_test.go
+index 6cd15b0..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/pools/urls.go
 +++ /dev/null
-@@ -1,1243 +0,0 @@
--package ec2_test
+@@ -1,25 +0,0 @@
+-package pools
 -
--import (
--	"testing"
+-import "github.com/rackspace/gophercloud"
 -
--	"github.com/mitchellh/goamz/aws"
--	"github.com/mitchellh/goamz/ec2"
--	"github.com/mitchellh/goamz/testutil"
--	. "github.com/motain/gocheck"
+-const (
+-	rootPath     = "lb"
+-	resourcePath = "pools"
+-	monitorPath  = "health_monitors"
 -)
 -
--func Test(t *testing.T) {
--	TestingT(t)
+-func rootURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL(rootPath, resourcePath)
 -}
 -
--var _ = Suite(&S{})
--
--type S struct {
--	ec2 *ec2.EC2
+-func resourceURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL(rootPath, resourcePath, id)
 -}
 -
--var testServer = testutil.NewHTTPServer()
--
--func (s *S) SetUpSuite(c *C) {
--	testServer.Start()
--	auth := aws.Auth{"abc", "123", ""}
--	s.ec2 = ec2.NewWithClient(
--		auth,
--		aws.Region{EC2Endpoint: testServer.URL},
--		testutil.DefaultClient,
--	)
+-func associateURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL(rootPath, resourcePath, id, monitorPath)
 -}
 -
--func (s *S) TearDownTest(c *C) {
--	testServer.Flush()
+-func disassociateURL(c *gophercloud.ServiceClient, poolID, monitorID string) string {
+-	return c.ServiceURL(rootPath, resourcePath, poolID, monitorPath, monitorID)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/vips/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/vips/requests.go
+deleted file mode 100644
+index ec929d6..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/vips/requests.go
++++ /dev/null
+@@ -1,273 +0,0 @@
+-package vips
 -
--func (s *S) TestRunInstancesErrorDump(c *C) {
--	testServer.Response(400, nil, ErrorDump)
--
--	options := ec2.RunInstances{
--		ImageId:      "ami-a6f504cf", // Ubuntu Maverick, i386, instance store
--		InstanceType: "t1.micro",     // Doesn't work with micro, results in 400.
--	}
+-import (
+-	"fmt"
 -
--	msg := `AMIs with an instance-store root device are not supported for the instance type 't1\.micro'\.`
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	resp, err := s.ec2.RunInstances(&options)
+-// AdminState gives users a solid type to work with for create and update
+-// operations. It is recommended that users use the `Up` and `Down` enums.
+-type AdminState *bool
 -
--	testServer.WaitRequest()
+-// Convenience vars for AdminStateUp values.
+-var (
+-	iTrue  = true
+-	iFalse = false
 -
--	c.Assert(resp, IsNil)
--	c.Assert(err, ErrorMatches, msg+` \(UnsupportedOperation\)`)
+-	Up   AdminState = &iTrue
+-	Down AdminState = &iFalse
+-)
 -
--	ec2err, ok := err.(*ec2.Error)
--	c.Assert(ok, Equals, true)
--	c.Assert(ec2err.StatusCode, Equals, 400)
--	c.Assert(ec2err.Code, Equals, "UnsupportedOperation")
--	c.Assert(ec2err.Message, Matches, msg)
--	c.Assert(ec2err.RequestId, Equals, "0503f4e9-bbd6-483c-b54f-c4ae9f3b30f4")
+-// ListOpts allows the filtering and sorting of paginated collections through
+-// the API. Filtering is achieved by passing in struct field values that map to
+-// the floating IP attributes you want to see returned. SortKey allows you to
+-// sort by a particular network attribute. SortDir sets the direction, and is
+-// either `asc' or `desc'. Marker and Limit are used for pagination.
+-type ListOpts struct {
+-	ID              string `q:"id"`
+-	Name            string `q:"name"`
+-	AdminStateUp    *bool  `q:"admin_state_up"`
+-	Status          string `q:"status"`
+-	TenantID        string `q:"tenant_id"`
+-	SubnetID        string `q:"subnet_id"`
+-	Address         string `q:"address"`
+-	PortID          string `q:"port_id"`
+-	Protocol        string `q:"protocol"`
+-	ProtocolPort    int    `q:"protocol_port"`
+-	ConnectionLimit int    `q:"connection_limit"`
+-	Limit           int    `q:"limit"`
+-	Marker          string `q:"marker"`
+-	SortKey         string `q:"sort_key"`
+-	SortDir         string `q:"sort_dir"`
+-}
+-
+-// List returns a Pager which allows you to iterate over a collection of
+-// routers. It accepts a ListOpts struct, which allows you to filter and sort
+-// the returned collection for greater efficiency.
+-//
+-// Default policy settings return only those routers that are owned by the
+-// tenant who submits the request, unless an admin user submits the request.
+-func List(c *gophercloud.ServiceClient, opts ListOpts) pagination.Pager {
+-	q, err := gophercloud.BuildQueryString(&opts)
+-	if err != nil {
+-		return pagination.Pager{Err: err}
+-	}
+-	u := rootURL(c) + q.String()
+-	return pagination.NewPager(c, u, func(r pagination.PageResult) pagination.Page {
+-		return VIPPage{pagination.LinkedPageBase{PageResult: r}}
+-	})
 -}
 -
--func (s *S) TestRequestSpotInstancesErrorDump(c *C) {
--	testServer.Response(400, nil, ErrorDump)
+-var (
+-	errNameRequired         = fmt.Errorf("Name is required")
+-	errSubnetIDRequried     = fmt.Errorf("SubnetID is required")
+-	errProtocolRequired     = fmt.Errorf("Protocol is required")
+-	errProtocolPortRequired = fmt.Errorf("Protocol port is required")
+-	errPoolIDRequired       = fmt.Errorf("PoolID is required")
+-)
 -
--	options := ec2.RequestSpotInstances{
--		SpotPrice:    "0.01",
--		ImageId:      "ami-a6f504cf", // Ubuntu Maverick, i386, instance store
--		InstanceType: "t1.micro",     // Doesn't work with micro, results in 400.
--	}
+-// CreateOpts contains all the values needed to create a new virtual IP.
+-type CreateOpts struct {
+-	// Required. Human-readable name for the VIP. Does not have to be unique.
+-	Name string
 -
--	msg := `AMIs with an instance-store root device are not supported for the instance type 't1\.micro'\.`
+-	// Required. The network on which to allocate the VIP's address. A tenant can
+-	// only create VIPs on networks authorized by policy (e.g. networks that
+-	// belong to them or networks that are shared).
+-	SubnetID string
 -
--	resp, err := s.ec2.RequestSpotInstances(&options)
+-	// Required. The protocol - can either be TCP, HTTP or HTTPS.
+-	Protocol string
 -
--	testServer.WaitRequest()
+-	// Required. The port on which to listen for client traffic.
+-	ProtocolPort int
 -
--	c.Assert(resp, IsNil)
--	c.Assert(err, ErrorMatches, msg+` \(UnsupportedOperation\)`)
+-	// Required. The ID of the pool with which the VIP is associated.
+-	PoolID string
 -
--	ec2err, ok := err.(*ec2.Error)
--	c.Assert(ok, Equals, true)
--	c.Assert(ec2err.StatusCode, Equals, 400)
--	c.Assert(ec2err.Code, Equals, "UnsupportedOperation")
--	c.Assert(ec2err.Message, Matches, msg)
--	c.Assert(ec2err.RequestId, Equals, "0503f4e9-bbd6-483c-b54f-c4ae9f3b30f4")
--}
+-	// Required for admins. Indicates the owner of the VIP.
+-	TenantID string
 -
--func (s *S) TestRunInstancesErrorWithoutXML(c *C) {
--	testServer.Responses(5, 500, nil, "")
--	options := ec2.RunInstances{ImageId: "image-id"}
+-	// Optional. The IP address of the VIP.
+-	Address string
 -
--	resp, err := s.ec2.RunInstances(&options)
+-	// Optional. Human-readable description for the VIP.
+-	Description string
 -
--	testServer.WaitRequest()
+-	// Optional. Omit this field to prevent session persistence.
+-	Persistence *SessionPersistence
 -
--	c.Assert(resp, IsNil)
--	c.Assert(err, ErrorMatches, "500 Internal Server Error")
+-	// Optional. The maximum number of connections allowed for the VIP.
+-	ConnLimit *int
 -
--	ec2err, ok := err.(*ec2.Error)
--	c.Assert(ok, Equals, true)
--	c.Assert(ec2err.StatusCode, Equals, 500)
--	c.Assert(ec2err.Code, Equals, "")
--	c.Assert(ec2err.Message, Equals, "500 Internal Server Error")
--	c.Assert(ec2err.RequestId, Equals, "")
+-	// Optional. The administrative state of the VIP. A valid value is true (UP)
+-	// or false (DOWN).
+-	AdminStateUp *bool
 -}
 -
--func (s *S) TestRequestSpotInstancesErrorWithoutXML(c *C) {
--	testServer.Responses(5, 500, nil, "")
--	options := ec2.RequestSpotInstances{SpotPrice: "spot-price", ImageId: "image-id"}
+-// Create is an operation which provisions a new virtual IP based on the
+-// configuration defined in the CreateOpts struct. Once the request is
+-// validated and progress has started on the provisioning process, a
+-// CreateResult will be returned.
+-//
+-// Please note that the PoolID should refer to a pool that is not already
+-// associated with another vip. If the pool is already used by another vip,
+-// then the operation will fail with a 409 Conflict error will be returned.
+-//
+-// Users with an admin role can create VIPs on behalf of other tenants by
+-// specifying a TenantID attribute different than their own.
+-func Create(c *gophercloud.ServiceClient, opts CreateOpts) CreateResult {
+-	var res CreateResult
 -
--	resp, err := s.ec2.RequestSpotInstances(&options)
+-	// Validate required opts
+-	if opts.Name == "" {
+-		res.Err = errNameRequired
+-		return res
+-	}
+-	if opts.SubnetID == "" {
+-		res.Err = errSubnetIDRequried
+-		return res
+-	}
+-	if opts.Protocol == "" {
+-		res.Err = errProtocolRequired
+-		return res
+-	}
+-	if opts.ProtocolPort == 0 {
+-		res.Err = errProtocolPortRequired
+-		return res
+-	}
+-	if opts.PoolID == "" {
+-		res.Err = errPoolIDRequired
+-		return res
+-	}
+-
+-	type vip struct {
+-		Name         string              `json:"name"`
+-		SubnetID     string              `json:"subnet_id"`
+-		Protocol     string              `json:"protocol"`
+-		ProtocolPort int                 `json:"protocol_port"`
+-		PoolID       string              `json:"pool_id"`
+-		Description  *string             `json:"description,omitempty"`
+-		TenantID     *string             `json:"tenant_id,omitempty"`
+-		Address      *string             `json:"address,omitempty"`
+-		Persistence  *SessionPersistence `json:"session_persistence,omitempty"`
+-		ConnLimit    *int                `json:"connection_limit,omitempty"`
+-		AdminStateUp *bool               `json:"admin_state_up,omitempty"`
+-	}
+-
+-	type request struct {
+-		VirtualIP vip `json:"vip"`
+-	}
+-
+-	reqBody := request{VirtualIP: vip{
+-		Name:         opts.Name,
+-		SubnetID:     opts.SubnetID,
+-		Protocol:     opts.Protocol,
+-		ProtocolPort: opts.ProtocolPort,
+-		PoolID:       opts.PoolID,
+-		Description:  gophercloud.MaybeString(opts.Description),
+-		TenantID:     gophercloud.MaybeString(opts.TenantID),
+-		Address:      gophercloud.MaybeString(opts.Address),
+-		ConnLimit:    opts.ConnLimit,
+-		AdminStateUp: opts.AdminStateUp,
+-	}}
 -
--	testServer.WaitRequest()
+-	if opts.Persistence != nil {
+-		reqBody.VirtualIP.Persistence = opts.Persistence
+-	}
 -
--	c.Assert(resp, IsNil)
--	c.Assert(err, ErrorMatches, "500 Internal Server Error")
+-	_, res.Err = perigee.Request("POST", rootURL(c), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{201},
+-	})
 -
--	ec2err, ok := err.(*ec2.Error)
--	c.Assert(ok, Equals, true)
--	c.Assert(ec2err.StatusCode, Equals, 500)
--	c.Assert(ec2err.Code, Equals, "")
--	c.Assert(ec2err.Message, Equals, "500 Internal Server Error")
--	c.Assert(ec2err.RequestId, Equals, "")
+-	return res
 -}
 -
--func (s *S) TestRunInstancesExample(c *C) {
--	testServer.Response(200, nil, RunInstancesExample)
+-// Get retrieves a particular virtual IP based on its unique ID.
+-func Get(c *gophercloud.ServiceClient, id string) GetResult {
+-	var res GetResult
+-	_, res.Err = perigee.Request("GET", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return res
+-}
 -
--	options := ec2.RunInstances{
--		KeyName:               "my-keys",
--		ImageId:               "image-id",
--		InstanceType:          "inst-type",
--		SecurityGroups:        []ec2.SecurityGroup{{Name: "g1"}, {Id: "g2"}, {Name: "g3"}, {Id: "g4"}},
--		UserData:              []byte("1234"),
--		KernelId:              "kernel-id",
--		RamdiskId:             "ramdisk-id",
--		AvailZone:             "zone",
--		PlacementGroupName:    "group",
--		Monitoring:            true,
--		SubnetId:              "subnet-id",
--		DisableAPITermination: true,
--		ShutdownBehavior:      "terminate",
--		PrivateIPAddress:      "10.0.0.25",
--		BlockDevices: []ec2.BlockDeviceMapping{
--			{DeviceName: "/dev/sdb", VirtualName: "ephemeral0"},
--			{DeviceName: "/dev/sdc", SnapshotId: "snap-a08912c9", DeleteOnTermination: true},
--		},
--	}
--	resp, err := s.ec2.RunInstances(&options)
+-// UpdateOpts contains all the values needed to update an existing virtual IP.
+-// Attributes not listed here but appear in CreateOpts are immutable and cannot
+-// be updated.
+-type UpdateOpts struct {
+-	// Human-readable name for the VIP. Does not have to be unique.
+-	Name string
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"RunInstances"})
--	c.Assert(req.Form["ImageId"], DeepEquals, []string{"image-id"})
--	c.Assert(req.Form["MinCount"], DeepEquals, []string{"1"})
--	c.Assert(req.Form["MaxCount"], DeepEquals, []string{"1"})
--	c.Assert(req.Form["KeyName"], DeepEquals, []string{"my-keys"})
--	c.Assert(req.Form["InstanceType"], DeepEquals, []string{"inst-type"})
--	c.Assert(req.Form["SecurityGroup.1"], DeepEquals, []string{"g1"})
--	c.Assert(req.Form["SecurityGroup.2"], DeepEquals, []string{"g3"})
--	c.Assert(req.Form["SecurityGroupId.1"], DeepEquals, []string{"g2"})
--	c.Assert(req.Form["SecurityGroupId.2"], DeepEquals, []string{"g4"})
--	c.Assert(req.Form["UserData"], DeepEquals, []string{"MTIzNA=="})
--	c.Assert(req.Form["KernelId"], DeepEquals, []string{"kernel-id"})
--	c.Assert(req.Form["RamdiskId"], DeepEquals, []string{"ramdisk-id"})
--	c.Assert(req.Form["Placement.AvailabilityZone"], DeepEquals, []string{"zone"})
--	c.Assert(req.Form["Placement.GroupName"], DeepEquals, []string{"group"})
--	c.Assert(req.Form["Monitoring.Enabled"], DeepEquals, []string{"true"})
--	c.Assert(req.Form["SubnetId"], DeepEquals, []string{"subnet-id"})
--	c.Assert(req.Form["DisableApiTermination"], DeepEquals, []string{"true"})
--	c.Assert(req.Form["InstanceInitiatedShutdownBehavior"], DeepEquals, []string{"terminate"})
--	c.Assert(req.Form["PrivateIpAddress"], DeepEquals, []string{"10.0.0.25"})
--	c.Assert(req.Form["BlockDeviceMapping.1.DeviceName"], DeepEquals, []string{"/dev/sdb"})
--	c.Assert(req.Form["BlockDeviceMapping.1.VirtualName"], DeepEquals, []string{"ephemeral0"})
--	c.Assert(req.Form["BlockDeviceMapping.2.Ebs.SnapshotId"], DeepEquals, []string{"snap-a08912c9"})
--	c.Assert(req.Form["BlockDeviceMapping.2.Ebs.DeleteOnTermination"], DeepEquals, []string{"true"})
+-	// Required. The ID of the pool with which the VIP is associated.
+-	PoolID string
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
--	c.Assert(resp.ReservationId, Equals, "r-47a5402e")
--	c.Assert(resp.OwnerId, Equals, "999988887777")
--	c.Assert(resp.SecurityGroups, DeepEquals, []ec2.SecurityGroup{{Name: "default", Id: "sg-67ad940e"}})
--	c.Assert(resp.Instances, HasLen, 3)
+-	// Optional. Human-readable description for the VIP.
+-	Description string
 -
--	i0 := resp.Instances[0]
--	c.Assert(i0.InstanceId, Equals, "i-2ba64342")
--	c.Assert(i0.InstanceType, Equals, "m1.small")
--	c.Assert(i0.ImageId, Equals, "ami-60a54009")
--	c.Assert(i0.Monitoring, Equals, "enabled")
--	c.Assert(i0.KeyName, Equals, "example-key-name")
--	c.Assert(i0.AMILaunchIndex, Equals, 0)
--	c.Assert(i0.VirtType, Equals, "paravirtual")
--	c.Assert(i0.Hypervisor, Equals, "xen")
+-	// Optional. Omit this field to prevent session persistence.
+-	Persistence *SessionPersistence
 -
--	i1 := resp.Instances[1]
--	c.Assert(i1.InstanceId, Equals, "i-2bc64242")
--	c.Assert(i1.InstanceType, Equals, "m1.small")
--	c.Assert(i1.ImageId, Equals, "ami-60a54009")
--	c.Assert(i1.Monitoring, Equals, "enabled")
--	c.Assert(i1.KeyName, Equals, "example-key-name")
--	c.Assert(i1.AMILaunchIndex, Equals, 1)
--	c.Assert(i1.VirtType, Equals, "paravirtual")
--	c.Assert(i1.Hypervisor, Equals, "xen")
+-	// Optional. The maximum number of connections allowed for the VIP.
+-	ConnLimit *int
 -
--	i2 := resp.Instances[2]
--	c.Assert(i2.InstanceId, Equals, "i-2be64332")
--	c.Assert(i2.InstanceType, Equals, "m1.small")
--	c.Assert(i2.ImageId, Equals, "ami-60a54009")
--	c.Assert(i2.Monitoring, Equals, "enabled")
--	c.Assert(i2.KeyName, Equals, "example-key-name")
--	c.Assert(i2.AMILaunchIndex, Equals, 2)
--	c.Assert(i2.VirtType, Equals, "paravirtual")
--	c.Assert(i2.Hypervisor, Equals, "xen")
+-	// Optional. The administrative state of the VIP. A valid value is true (UP)
+-	// or false (DOWN).
+-	AdminStateUp *bool
 -}
 -
--func (s *S) TestRequestSpotInstancesExample(c *C) {
--	testServer.Response(200, nil, RequestSpotInstancesExample)
--
--	options := ec2.RequestSpotInstances{
--		SpotPrice:          "0.5",
--		KeyName:            "my-keys",
--		ImageId:            "image-id",
--		InstanceType:       "inst-type",
--		SecurityGroups:     []ec2.SecurityGroup{{Name: "g1"}, {Id: "g2"}, {Name: "g3"}, {Id: "g4"}},
--		UserData:           []byte("1234"),
--		KernelId:           "kernel-id",
--		RamdiskId:          "ramdisk-id",
--		AvailZone:          "zone",
--		PlacementGroupName: "group",
--		Monitoring:         true,
--		SubnetId:           "subnet-id",
--		PrivateIPAddress:   "10.0.0.25",
--		BlockDevices: []ec2.BlockDeviceMapping{
--			{DeviceName: "/dev/sdb", VirtualName: "ephemeral0"},
--			{DeviceName: "/dev/sdc", SnapshotId: "snap-a08912c9", DeleteOnTermination: true},
--		},
+-// Update is an operation which modifies the attributes of the specified VIP.
+-func Update(c *gophercloud.ServiceClient, id string, opts UpdateOpts) UpdateResult {
+-	type vip struct {
+-		Name         string              `json:"name,omitempty"`
+-		PoolID       string              `json:"pool_id,omitempty"`
+-		Description  *string             `json:"description,omitempty"`
+-		Persistence  *SessionPersistence `json:"session_persistence,omitempty"`
+-		ConnLimit    *int                `json:"connection_limit,omitempty"`
+-		AdminStateUp *bool               `json:"admin_state_up,omitempty"`
 -	}
--	resp, err := s.ec2.RequestSpotInstances(&options)
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"RequestSpotInstances"})
--	c.Assert(req.Form["SpotPrice"], DeepEquals, []string{"0.5"})
--	c.Assert(req.Form["LaunchSpecification.ImageId"], DeepEquals, []string{"image-id"})
--	c.Assert(req.Form["LaunchSpecification.KeyName"], DeepEquals, []string{"my-keys"})
--	c.Assert(req.Form["LaunchSpecification.InstanceType"], DeepEquals, []string{"inst-type"})
--	c.Assert(req.Form["LaunchSpecification.SecurityGroup.1"], DeepEquals, []string{"g1"})
--	c.Assert(req.Form["LaunchSpecification.SecurityGroup.2"], DeepEquals, []string{"g3"})
--	c.Assert(req.Form["LaunchSpecification.SecurityGroupId.1"], DeepEquals, []string{"g2"})
--	c.Assert(req.Form["LaunchSpecification.SecurityGroupId.2"], DeepEquals, []string{"g4"})
--	c.Assert(req.Form["LaunchSpecification.UserData"], DeepEquals, []string{"MTIzNA=="})
--	c.Assert(req.Form["LaunchSpecification.KernelId"], DeepEquals, []string{"kernel-id"})
--	c.Assert(req.Form["LaunchSpecification.RamdiskId"], DeepEquals, []string{"ramdisk-id"})
--	c.Assert(req.Form["LaunchSpecification.Placement.AvailabilityZone"], DeepEquals, []string{"zone"})
--	c.Assert(req.Form["LaunchSpecification.Placement.GroupName"], DeepEquals, []string{"group"})
--	c.Assert(req.Form["LaunchSpecification.Monitoring.Enabled"], DeepEquals, []string{"true"})
--	c.Assert(req.Form["LaunchSpecification.SubnetId"], DeepEquals, []string{"subnet-id"})
--	c.Assert(req.Form["LaunchSpecification.PrivateIpAddress"], DeepEquals, []string{"10.0.0.25"})
--	c.Assert(req.Form["LaunchSpecification.BlockDeviceMapping.1.DeviceName"], DeepEquals, []string{"/dev/sdb"})
--	c.Assert(req.Form["LaunchSpecification.BlockDeviceMapping.1.VirtualName"], DeepEquals, []string{"ephemeral0"})
--	c.Assert(req.Form["LaunchSpecification.BlockDeviceMapping.2.Ebs.SnapshotId"], DeepEquals, []string{"snap-a08912c9"})
--	c.Assert(req.Form["LaunchSpecification.BlockDeviceMapping.2.Ebs.DeleteOnTermination"], DeepEquals, []string{"true"})
+-	type request struct {
+-		VirtualIP vip `json:"vip"`
+-	}
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
--	c.Assert(resp.SpotRequestResults[0].SpotRequestId, Equals, "sir-1a2b3c4d")
--	c.Assert(resp.SpotRequestResults[0].SpotPrice, Equals, "0.5")
--	c.Assert(resp.SpotRequestResults[0].State, Equals, "open")
--	c.Assert(resp.SpotRequestResults[0].SpotLaunchSpec.ImageId, Equals, "ami-1a2b3c4d")
--	c.Assert(resp.SpotRequestResults[0].Status.Code, Equals, "pending-evaluation")
--	c.Assert(resp.SpotRequestResults[0].Status.UpdateTime, Equals, "2008-05-07T12:51:50.000Z")
--	c.Assert(resp.SpotRequestResults[0].Status.Message, Equals, "Your Spot request has been submitted for review, and is pending evaluation.")
--}
+-	reqBody := request{VirtualIP: vip{
+-		Name:         opts.Name,
+-		PoolID:       opts.PoolID,
+-		Description:  gophercloud.MaybeString(opts.Description),
+-		ConnLimit:    opts.ConnLimit,
+-		AdminStateUp: opts.AdminStateUp,
+-	}}
 -
--func (s *S) TestCancelSpotRequestsExample(c *C) {
--	testServer.Response(200, nil, CancelSpotRequestsExample)
+-	if opts.Persistence != nil {
+-		reqBody.VirtualIP.Persistence = opts.Persistence
+-	}
 -
--	resp, err := s.ec2.CancelSpotRequests([]string{"s-1", "s-2"})
+-	var res UpdateResult
+-	_, res.Err = perigee.Request("PUT", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{200, 202},
+-	})
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"CancelSpotInstanceRequests"})
--	c.Assert(req.Form["SpotInstanceRequestId.1"], DeepEquals, []string{"s-1"})
--	c.Assert(req.Form["SpotInstanceRequestId.2"], DeepEquals, []string{"s-2"})
+-	return res
+-}
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
--	c.Assert(resp.CancelSpotRequestResults[0].SpotRequestId, Equals, "sir-1a2b3c4d")
--	c.Assert(resp.CancelSpotRequestResults[0].State, Equals, "cancelled")
+-// Delete will permanently delete a particular virtual IP based on its unique ID.
+-func Delete(c *gophercloud.ServiceClient, id string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{204},
+-	})
+-	return res
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/vips/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/vips/requests_test.go
+deleted file mode 100644
+index 430f1a1..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/vips/requests_test.go
++++ /dev/null
+@@ -1,336 +0,0 @@
+-package vips
 -
--func (s *S) TestTerminateInstancesExample(c *C) {
--	testServer.Response(200, nil, TerminateInstancesExample)
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--	resp, err := s.ec2.TerminateInstances([]string{"i-1", "i-2"})
+-	fake "github.com/rackspace/gophercloud/openstack/networking/v2/common"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"TerminateInstances"})
--	c.Assert(req.Form["InstanceId.1"], DeepEquals, []string{"i-1"})
--	c.Assert(req.Form["InstanceId.2"], DeepEquals, []string{"i-2"})
--	c.Assert(req.Form["UserData"], IsNil)
--	c.Assert(req.Form["KernelId"], IsNil)
--	c.Assert(req.Form["RamdiskId"], IsNil)
--	c.Assert(req.Form["Placement.AvailabilityZone"], IsNil)
--	c.Assert(req.Form["Placement.GroupName"], IsNil)
--	c.Assert(req.Form["Monitoring.Enabled"], IsNil)
--	c.Assert(req.Form["SubnetId"], IsNil)
--	c.Assert(req.Form["DisableApiTermination"], IsNil)
--	c.Assert(req.Form["InstanceInitiatedShutdownBehavior"], IsNil)
--	c.Assert(req.Form["PrivateIpAddress"], IsNil)
+-func TestURLs(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
--	c.Assert(resp.StateChanges, HasLen, 1)
--	c.Assert(resp.StateChanges[0].InstanceId, Equals, "i-3ea74257")
--	c.Assert(resp.StateChanges[0].CurrentState.Code, Equals, 32)
--	c.Assert(resp.StateChanges[0].CurrentState.Name, Equals, "shutting-down")
--	c.Assert(resp.StateChanges[0].PreviousState.Code, Equals, 16)
--	c.Assert(resp.StateChanges[0].PreviousState.Name, Equals, "running")
+-	th.AssertEquals(t, th.Endpoint()+"v2.0/lb/vips", rootURL(fake.ServiceClient()))
+-	th.AssertEquals(t, th.Endpoint()+"v2.0/lb/vips/foo", resourceURL(fake.ServiceClient(), "foo"))
 -}
 -
--func (s *S) TestDescribeSpotRequestsExample(c *C) {
--	testServer.Response(200, nil, DescribeSpotRequestsExample)
--
--	filter := ec2.NewFilter()
--	filter.Add("key1", "value1")
--	filter.Add("key2", "value2", "value3")
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	resp, err := s.ec2.DescribeSpotRequests([]string{"s-1", "s-2"}, filter)
+-	th.Mux.HandleFunc("/v2.0/lb/vips", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeSpotInstanceRequests"})
--	c.Assert(req.Form["SpotInstanceRequestId.1"], DeepEquals, []string{"s-1"})
--	c.Assert(req.Form["SpotInstanceRequestId.2"], DeepEquals, []string{"s-2"})
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "b1719f2a-5334-4479-b2f1-26926EXAMPLE")
--	c.Assert(resp.SpotRequestResults[0].SpotRequestId, Equals, "sir-1a2b3c4d")
--	c.Assert(resp.SpotRequestResults[0].State, Equals, "active")
--	c.Assert(resp.SpotRequestResults[0].SpotPrice, Equals, "0.5")
--	c.Assert(resp.SpotRequestResults[0].SpotLaunchSpec.ImageId, Equals, "ami-1a2b3c4d")
--	c.Assert(resp.SpotRequestResults[0].Status.Code, Equals, "fulfilled")
--	c.Assert(resp.SpotRequestResults[0].Status.UpdateTime, Equals, "2008-05-07T12:51:50.000Z")
--	c.Assert(resp.SpotRequestResults[0].Status.Message, Equals, "Your Spot request is fulfilled.")
+-		fmt.Fprintf(w, `
+-{
+-  "vips":[
+-         {
+-           "id": "db902c0c-d5ff-4753-b465-668ad9656918",
+-           "tenant_id": "310df60f-2a10-4ee5-9554-98393092194c",
+-           "name": "web_vip",
+-           "description": "lb config for the web tier",
+-           "subnet_id": "96a4386a-f8c3-42ed-afce-d7954eee77b3",
+-           "address" : "10.30.176.47",
+-           "port_id" : "cd1f7a47-4fa6-449c-9ee7-632838aedfea",
+-           "protocol": "HTTP",
+-           "protocol_port": 80,
+-           "pool_id" : "cfc6589d-f949-4c66-99d2-c2da56ef3764",
+-           "admin_state_up": true,
+-           "status": "ACTIVE"
+-         },
+-         {
+-           "id": "36e08a3e-a78f-4b40-a229-1e7e23eee1ab",
+-           "tenant_id": "310df60f-2a10-4ee5-9554-98393092194c",
+-           "name": "db_vip",
+-					 "description": "lb config for the db tier",
+-           "subnet_id": "9cedb85d-0759-4898-8a4b-fa5a5ea10086",
+-           "address" : "10.30.176.48",
+-           "port_id" : "cd1f7a47-4fa6-449c-9ee7-632838aedfea",
+-           "protocol": "TCP",
+-           "protocol_port": 3306,
+-           "pool_id" : "41efe233-7591-43c5-9cf7-923964759f9e",
+-           "session_persistence" : {"type" : "SOURCE_IP"},
+-           "connection_limit" : 2000,
+-           "admin_state_up": true,
+-           "status": "INACTIVE"
+-         }
+-      ]
 -}
+-			`)
+-	})
 -
--func (s *S) TestDescribeInstancesExample1(c *C) {
--	testServer.Response(200, nil, DescribeInstancesExample1)
--
--	filter := ec2.NewFilter()
--	filter.Add("key1", "value1")
--	filter.Add("key2", "value2", "value3")
+-	count := 0
 -
--	resp, err := s.ec2.Instances([]string{"i-1", "i-2"}, nil)
+-	List(fake.ServiceClient(), ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractVIPs(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract LBs: %v", err)
+-			return false, err
+-		}
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeInstances"})
--	c.Assert(req.Form["InstanceId.1"], DeepEquals, []string{"i-1"})
--	c.Assert(req.Form["InstanceId.2"], DeepEquals, []string{"i-2"})
+-		expected := []VirtualIP{
+-			VirtualIP{
+-				ID:           "db902c0c-d5ff-4753-b465-668ad9656918",
+-				TenantID:     "310df60f-2a10-4ee5-9554-98393092194c",
+-				Name:         "web_vip",
+-				Description:  "lb config for the web tier",
+-				SubnetID:     "96a4386a-f8c3-42ed-afce-d7954eee77b3",
+-				Address:      "10.30.176.47",
+-				PortID:       "cd1f7a47-4fa6-449c-9ee7-632838aedfea",
+-				Protocol:     "HTTP",
+-				ProtocolPort: 80,
+-				PoolID:       "cfc6589d-f949-4c66-99d2-c2da56ef3764",
+-				Persistence:  SessionPersistence{},
+-				ConnLimit:    0,
+-				AdminStateUp: true,
+-				Status:       "ACTIVE",
+-			},
+-			VirtualIP{
+-				ID:           "36e08a3e-a78f-4b40-a229-1e7e23eee1ab",
+-				TenantID:     "310df60f-2a10-4ee5-9554-98393092194c",
+-				Name:         "db_vip",
+-				Description:  "lb config for the db tier",
+-				SubnetID:     "9cedb85d-0759-4898-8a4b-fa5a5ea10086",
+-				Address:      "10.30.176.48",
+-				PortID:       "cd1f7a47-4fa6-449c-9ee7-632838aedfea",
+-				Protocol:     "TCP",
+-				ProtocolPort: 3306,
+-				PoolID:       "41efe233-7591-43c5-9cf7-923964759f9e",
+-				Persistence:  SessionPersistence{Type: "SOURCE_IP"},
+-				ConnLimit:    2000,
+-				AdminStateUp: true,
+-				Status:       "INACTIVE",
+-			},
+-		}
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "98e3c9a4-848c-4d6d-8e8a-b1bdEXAMPLE")
--	c.Assert(resp.Reservations, HasLen, 2)
+-		th.CheckDeepEquals(t, expected, actual)
 -
--	r0 := resp.Reservations[0]
--	c.Assert(r0.ReservationId, Equals, "r-b27e30d9")
--	c.Assert(r0.OwnerId, Equals, "999988887777")
--	c.Assert(r0.RequesterId, Equals, "854251627541")
--	c.Assert(r0.SecurityGroups, DeepEquals, []ec2.SecurityGroup{{Name: "default", Id: "sg-67ad940e"}})
--	c.Assert(r0.Instances, HasLen, 1)
+-		return true, nil
+-	})
 -
--	r0i := r0.Instances[0]
--	c.Assert(r0i.InstanceId, Equals, "i-c5cd56af")
--	c.Assert(r0i.PrivateDNSName, Equals, "domU-12-31-39-10-56-34.compute-1.internal")
--	c.Assert(r0i.DNSName, Equals, "ec2-174-129-165-232.compute-1.amazonaws.com")
--	c.Assert(r0i.AvailZone, Equals, "us-east-1b")
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
+-	}
 -}
 -
--func (s *S) TestDescribeInstancesExample2(c *C) {
--	testServer.Response(200, nil, DescribeInstancesExample2)
--
--	filter := ec2.NewFilter()
--	filter.Add("key1", "value1")
--	filter.Add("key2", "value2", "value3")
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/lb/vips", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "vip": {
+-        "protocol": "HTTP",
+-        "name": "NewVip",
+-        "admin_state_up": true,
+-        "subnet_id": "8032909d-47a1-4715-90af-5153ffe39861",
+-        "pool_id": "61b1f87a-7a21-4ad3-9dda-7f81d249944f",
+-        "protocol_port": 80,
+-				"session_persistence": {"type": "SOURCE_IP"}
+-    }
+-}
+-			`)
 -
--	resp, err := s.ec2.Instances([]string{"i-1", "i-2"}, filter)
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeInstances"})
--	c.Assert(req.Form["InstanceId.1"], DeepEquals, []string{"i-1"})
--	c.Assert(req.Form["InstanceId.2"], DeepEquals, []string{"i-2"})
--	c.Assert(req.Form["Filter.1.Name"], DeepEquals, []string{"key1"})
--	c.Assert(req.Form["Filter.1.Value.1"], DeepEquals, []string{"value1"})
--	c.Assert(req.Form["Filter.1.Value.2"], IsNil)
--	c.Assert(req.Form["Filter.2.Name"], DeepEquals, []string{"key2"})
--	c.Assert(req.Form["Filter.2.Value.1"], DeepEquals, []string{"value2"})
--	c.Assert(req.Form["Filter.2.Value.2"], DeepEquals, []string{"value3"})
+-		fmt.Fprintf(w, `
+-{
+-    "vip": {
+-        "status": "PENDING_CREATE",
+-        "protocol": "HTTP",
+-        "description": "",
+-        "admin_state_up": true,
+-        "subnet_id": "8032909d-47a1-4715-90af-5153ffe39861",
+-        "tenant_id": "83657cfcdfe44cd5920adaf26c48ceea",
+-        "connection_limit": -1,
+-        "pool_id": "61b1f87a-7a21-4ad3-9dda-7f81d249944f",
+-        "address": "10.0.0.11",
+-        "protocol_port": 80,
+-        "port_id": "f7e6fe6a-b8b5-43a8-8215-73456b32e0f5",
+-        "id": "c987d2be-9a3c-4ac9-a046-e8716b1350e2",
+-        "name": "NewVip"
+-    }
+-}
+-		`)
+-	})
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
--	c.Assert(resp.Reservations, HasLen, 1)
+-	opts := CreateOpts{
+-		Protocol:     "HTTP",
+-		Name:         "NewVip",
+-		AdminStateUp: Up,
+-		SubnetID:     "8032909d-47a1-4715-90af-5153ffe39861",
+-		PoolID:       "61b1f87a-7a21-4ad3-9dda-7f81d249944f",
+-		ProtocolPort: 80,
+-		Persistence:  &SessionPersistence{Type: "SOURCE_IP"},
+-	}
 -
--	r0 := resp.Reservations[0]
--	r0i := r0.Instances[0]
--	c.Assert(r0i.State.Code, Equals, 16)
--	c.Assert(r0i.State.Name, Equals, "running")
+-	r, err := Create(fake.ServiceClient(), opts).Extract()
+-	th.AssertNoErr(t, err)
 -
--	r0t0 := r0i.Tags[0]
--	r0t1 := r0i.Tags[1]
--	c.Assert(r0t0.Key, Equals, "webserver")
--	c.Assert(r0t0.Value, Equals, "")
--	c.Assert(r0t1.Key, Equals, "stack")
--	c.Assert(r0t1.Value, Equals, "Production")
+-	th.AssertEquals(t, "PENDING_CREATE", r.Status)
+-	th.AssertEquals(t, "HTTP", r.Protocol)
+-	th.AssertEquals(t, "", r.Description)
+-	th.AssertEquals(t, true, r.AdminStateUp)
+-	th.AssertEquals(t, "8032909d-47a1-4715-90af-5153ffe39861", r.SubnetID)
+-	th.AssertEquals(t, "83657cfcdfe44cd5920adaf26c48ceea", r.TenantID)
+-	th.AssertEquals(t, -1, r.ConnLimit)
+-	th.AssertEquals(t, "61b1f87a-7a21-4ad3-9dda-7f81d249944f", r.PoolID)
+-	th.AssertEquals(t, "10.0.0.11", r.Address)
+-	th.AssertEquals(t, 80, r.ProtocolPort)
+-	th.AssertEquals(t, "f7e6fe6a-b8b5-43a8-8215-73456b32e0f5", r.PortID)
+-	th.AssertEquals(t, "c987d2be-9a3c-4ac9-a046-e8716b1350e2", r.ID)
+-	th.AssertEquals(t, "NewVip", r.Name)
 -}
 -
--func (s *S) TestCreateImageExample(c *C) {
--	testServer.Response(200, nil, CreateImageExample)
--
--	options := &ec2.CreateImage{
--		InstanceId:  "i-123456",
--		Name:        "foo",
--		Description: "Test CreateImage",
--		NoReboot:    true,
--		BlockDevices: []ec2.BlockDeviceMapping{
--			{DeviceName: "/dev/sdb", VirtualName: "ephemeral0"},
--			{DeviceName: "/dev/sdc", SnapshotId: "snap-a08912c9", DeleteOnTermination: true},
--		},
+-func TestRequiredCreateOpts(t *testing.T) {
+-	res := Create(fake.ServiceClient(), CreateOpts{})
+-	if res.Err == nil {
+-		t.Fatalf("Expected error, got none")
 -	}
+-	res = Create(fake.ServiceClient(), CreateOpts{Name: "foo"})
+-	if res.Err == nil {
+-		t.Fatalf("Expected error, got none")
+-	}
+-	res = Create(fake.ServiceClient(), CreateOpts{Name: "foo", SubnetID: "bar"})
+-	if res.Err == nil {
+-		t.Fatalf("Expected error, got none")
+-	}
+-	res = Create(fake.ServiceClient(), CreateOpts{Name: "foo", SubnetID: "bar", Protocol: "bar"})
+-	if res.Err == nil {
+-		t.Fatalf("Expected error, got none")
+-	}
+-	res = Create(fake.ServiceClient(), CreateOpts{Name: "foo", SubnetID: "bar", Protocol: "bar", ProtocolPort: 80})
+-	if res.Err == nil {
+-		t.Fatalf("Expected error, got none")
+-	}
+-}
 -
--	resp, err := s.ec2.CreateImage(options)
--
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"CreateImage"})
--	c.Assert(req.Form["InstanceId"], DeepEquals, []string{options.InstanceId})
--	c.Assert(req.Form["Name"], DeepEquals, []string{options.Name})
--	c.Assert(req.Form["Description"], DeepEquals, []string{options.Description})
--	c.Assert(req.Form["NoReboot"], DeepEquals, []string{"true"})
--	c.Assert(req.Form["BlockDeviceMapping.1.DeviceName"], DeepEquals, []string{"/dev/sdb"})
--	c.Assert(req.Form["BlockDeviceMapping.1.VirtualName"], DeepEquals, []string{"ephemeral0"})
--	c.Assert(req.Form["BlockDeviceMapping.2.DeviceName"], DeepEquals, []string{"/dev/sdc"})
--	c.Assert(req.Form["BlockDeviceMapping.2.Ebs.SnapshotId"], DeepEquals, []string{"snap-a08912c9"})
--	c.Assert(req.Form["BlockDeviceMapping.2.Ebs.DeleteOnTermination"], DeepEquals, []string{"true"})
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
--	c.Assert(resp.ImageId, Equals, "ami-4fa54026")
--}
+-	th.Mux.HandleFunc("/v2.0/lb/vips/4ec89087-d057-4e2c-911f-60a3b47ee304", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--func (s *S) TestDescribeImagesExample(c *C) {
--	testServer.Response(200, nil, DescribeImagesExample)
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--	filter := ec2.NewFilter()
--	filter.Add("key1", "value1")
--	filter.Add("key2", "value2", "value3")
+-		fmt.Fprintf(w, `
+-{
+-    "vip": {
+-        "status": "ACTIVE",
+-        "protocol": "HTTP",
+-        "description": "",
+-        "admin_state_up": true,
+-        "subnet_id": "8032909d-47a1-4715-90af-5153ffe39861",
+-        "tenant_id": "83657cfcdfe44cd5920adaf26c48ceea",
+-        "connection_limit": 1000,
+-        "pool_id": "72741b06-df4d-4715-b142-276b6bce75ab",
+-        "session_persistence": {
+-            "cookie_name": "MyAppCookie",
+-            "type": "APP_COOKIE"
+-        },
+-        "address": "10.0.0.10",
+-        "protocol_port": 80,
+-        "port_id": "b5a743d6-056b-468b-862d-fb13a9aa694e",
+-        "id": "4ec89087-d057-4e2c-911f-60a3b47ee304",
+-        "name": "my-vip"
+-    }
+-}
+-			`)
+-	})
 -
--	resp, err := s.ec2.Images([]string{"ami-1", "ami-2"}, filter)
+-	vip, err := Get(fake.ServiceClient(), "4ec89087-d057-4e2c-911f-60a3b47ee304").Extract()
+-	th.AssertNoErr(t, err)
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeImages"})
--	c.Assert(req.Form["ImageId.1"], DeepEquals, []string{"ami-1"})
--	c.Assert(req.Form["ImageId.2"], DeepEquals, []string{"ami-2"})
--	c.Assert(req.Form["Filter.1.Name"], DeepEquals, []string{"key1"})
--	c.Assert(req.Form["Filter.1.Value.1"], DeepEquals, []string{"value1"})
--	c.Assert(req.Form["Filter.1.Value.2"], IsNil)
--	c.Assert(req.Form["Filter.2.Name"], DeepEquals, []string{"key2"})
--	c.Assert(req.Form["Filter.2.Value.1"], DeepEquals, []string{"value2"})
--	c.Assert(req.Form["Filter.2.Value.2"], DeepEquals, []string{"value3"})
+-	th.AssertEquals(t, "ACTIVE", vip.Status)
+-	th.AssertEquals(t, "HTTP", vip.Protocol)
+-	th.AssertEquals(t, "", vip.Description)
+-	th.AssertEquals(t, true, vip.AdminStateUp)
+-	th.AssertEquals(t, 1000, vip.ConnLimit)
+-	th.AssertEquals(t, SessionPersistence{Type: "APP_COOKIE", CookieName: "MyAppCookie"}, vip.Persistence)
+-}
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "4a4a27a2-2e7c-475d-b35b-ca822EXAMPLE")
--	c.Assert(resp.Images, HasLen, 1)
+-func TestUpdate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/lb/vips/4ec89087-d057-4e2c-911f-60a3b47ee304", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "vip": {
+-        "connection_limit": 1000,
+-				"session_persistence": {"type": "SOURCE_IP"}
+-    }
+-}
+-			`)
 -
--	i0 := resp.Images[0]
--	c.Assert(i0.Id, Equals, "ami-a2469acf")
--	c.Assert(i0.Type, Equals, "machine")
--	c.Assert(i0.Name, Equals, "example-marketplace-amzn-ami.1")
--	c.Assert(i0.Description, Equals, "Amazon Linux AMI i386 EBS")
--	c.Assert(i0.Location, Equals, "aws-marketplace/example-marketplace-amzn-ami.1")
--	c.Assert(i0.State, Equals, "available")
--	c.Assert(i0.Public, Equals, true)
--	c.Assert(i0.OwnerId, Equals, "123456789999")
--	c.Assert(i0.OwnerAlias, Equals, "aws-marketplace")
--	c.Assert(i0.Architecture, Equals, "i386")
--	c.Assert(i0.KernelId, Equals, "aki-805ea7e9")
--	c.Assert(i0.RootDeviceType, Equals, "ebs")
--	c.Assert(i0.RootDeviceName, Equals, "/dev/sda1")
--	c.Assert(i0.VirtualizationType, Equals, "paravirtual")
--	c.Assert(i0.Hypervisor, Equals, "xen")
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusAccepted)
 -
--	c.Assert(i0.BlockDevices, HasLen, 1)
--	c.Assert(i0.BlockDevices[0].DeviceName, Equals, "/dev/sda1")
--	c.Assert(i0.BlockDevices[0].SnapshotId, Equals, "snap-787e9403")
--	c.Assert(i0.BlockDevices[0].VolumeSize, Equals, int64(8))
--	c.Assert(i0.BlockDevices[0].DeleteOnTermination, Equals, true)
+-		fmt.Fprintf(w, `
+-{
+-    "vip": {
+-        "status": "PENDING_UPDATE",
+-        "protocol": "HTTP",
+-        "description": "",
+-        "admin_state_up": true,
+-        "subnet_id": "8032909d-47a1-4715-90af-5153ffe39861",
+-        "tenant_id": "83657cfcdfe44cd5920adaf26c48ceea",
+-        "connection_limit": 1000,
+-        "pool_id": "61b1f87a-7a21-4ad3-9dda-7f81d249944f",
+-        "address": "10.0.0.11",
+-        "protocol_port": 80,
+-        "port_id": "f7e6fe6a-b8b5-43a8-8215-73456b32e0f5",
+-        "id": "c987d2be-9a3c-4ac9-a046-e8716b1350e2",
+-        "name": "NewVip"
+-    }
+-}
+-		`)
+-	})
 -
--	testServer.Response(200, nil, DescribeImagesExample)
--	resp2, err := s.ec2.ImagesByOwners([]string{"ami-1", "ami-2"}, []string{"123456789999", "id2"}, filter)
+-	i1000 := 1000
+-	options := UpdateOpts{
+-		ConnLimit:   &i1000,
+-		Persistence: &SessionPersistence{Type: "SOURCE_IP"},
+-	}
+-	vip, err := Update(fake.ServiceClient(), "4ec89087-d057-4e2c-911f-60a3b47ee304", options).Extract()
+-	th.AssertNoErr(t, err)
 -
--	req2 := testServer.WaitRequest()
--	c.Assert(req2.Form["Action"], DeepEquals, []string{"DescribeImages"})
--	c.Assert(req2.Form["ImageId.1"], DeepEquals, []string{"ami-1"})
--	c.Assert(req2.Form["ImageId.2"], DeepEquals, []string{"ami-2"})
--	c.Assert(req2.Form["Owner.1"], DeepEquals, []string{"123456789999"})
--	c.Assert(req2.Form["Owner.2"], DeepEquals, []string{"id2"})
--	c.Assert(req2.Form["Filter.1.Name"], DeepEquals, []string{"key1"})
--	c.Assert(req2.Form["Filter.1.Value.1"], DeepEquals, []string{"value1"})
--	c.Assert(req2.Form["Filter.1.Value.2"], IsNil)
--	c.Assert(req2.Form["Filter.2.Name"], DeepEquals, []string{"key2"})
--	c.Assert(req2.Form["Filter.2.Value.1"], DeepEquals, []string{"value2"})
--	c.Assert(req2.Form["Filter.2.Value.2"], DeepEquals, []string{"value3"})
+-	th.AssertEquals(t, "PENDING_UPDATE", vip.Status)
+-	th.AssertEquals(t, 1000, vip.ConnLimit)
+-}
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp2.RequestId, Equals, "4a4a27a2-2e7c-475d-b35b-ca822EXAMPLE")
--	c.Assert(resp2.Images, HasLen, 1)
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	i1 := resp2.Images[0]
--	c.Assert(i1.Id, Equals, "ami-a2469acf")
--	c.Assert(i1.Type, Equals, "machine")
--	c.Assert(i1.Name, Equals, "example-marketplace-amzn-ami.1")
--	c.Assert(i1.Description, Equals, "Amazon Linux AMI i386 EBS")
--	c.Assert(i1.Location, Equals, "aws-marketplace/example-marketplace-amzn-ami.1")
--	c.Assert(i1.State, Equals, "available")
--	c.Assert(i1.Public, Equals, true)
--	c.Assert(i1.OwnerId, Equals, "123456789999")
--	c.Assert(i1.OwnerAlias, Equals, "aws-marketplace")
--	c.Assert(i1.Architecture, Equals, "i386")
--	c.Assert(i1.KernelId, Equals, "aki-805ea7e9")
--	c.Assert(i1.RootDeviceType, Equals, "ebs")
--	c.Assert(i1.RootDeviceName, Equals, "/dev/sda1")
--	c.Assert(i1.VirtualizationType, Equals, "paravirtual")
--	c.Assert(i1.Hypervisor, Equals, "xen")
+-	th.Mux.HandleFunc("/v2.0/lb/vips/4ec89087-d057-4e2c-911f-60a3b47ee304", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		w.WriteHeader(http.StatusNoContent)
+-	})
 -
--	c.Assert(i1.BlockDevices, HasLen, 1)
--	c.Assert(i1.BlockDevices[0].DeviceName, Equals, "/dev/sda1")
--	c.Assert(i1.BlockDevices[0].SnapshotId, Equals, "snap-787e9403")
--	c.Assert(i1.BlockDevices[0].VolumeSize, Equals, int64(8))
--	c.Assert(i1.BlockDevices[0].DeleteOnTermination, Equals, true)
+-	res := Delete(fake.ServiceClient(), "4ec89087-d057-4e2c-911f-60a3b47ee304")
+-	th.AssertNoErr(t, res.Err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/vips/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/vips/results.go
+deleted file mode 100644
+index e1092e7..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/vips/results.go
++++ /dev/null
+@@ -1,166 +0,0 @@
+-package vips
 -
--func (s *S) TestImageAttributeExample(c *C) {
--	testServer.Response(200, nil, ImageAttributeExample)
--
--	resp, err := s.ec2.ImageAttribute("ami-61a54008", "launchPermission")
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeImageAttribute"})
+-// SessionPersistence represents the session persistence feature of the load
+-// balancing service. It attempts to force connections or requests in the same
+-// session to be processed by the same member as long as it is ative. Three
+-// types of persistence are supported:
+-//
+-// SOURCE_IP:   With this mode, all connections originating from the same source
+-//              IP address, will be handled by the same member of the pool.
+-// HTTP_COOKIE: With this persistence mode, the load balancing function will
+-//              create a cookie on the first request from a client. Subsequent
+-//              requests containing the same cookie value will be handled by
+-//              the same member of the pool.
+-// APP_COOKIE:  With this persistence mode, the load balancing function will
+-//              rely on a cookie established by the backend application. All
+-//              requests carrying the same cookie value will be handled by the
+-//              same member of the pool.
+-type SessionPersistence struct {
+-	// The type of persistence mode
+-	Type string `mapstructure:"type" json:"type"`
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
--	c.Assert(resp.ImageId, Equals, "ami-61a54008")
--	c.Assert(resp.Group, Equals, "all")
--	c.Assert(resp.UserIds[0], Equals, "495219933132")
+-	// Name of cookie if persistence mode is set appropriately
+-	CookieName string `mapstructure:"cookie_name" json:"cookie_name,omitempty"`
 -}
 -
--func (s *S) TestCreateSnapshotExample(c *C) {
--	testServer.Response(200, nil, CreateSnapshotExample)
--
--	resp, err := s.ec2.CreateSnapshot("vol-4d826724", "Daily Backup")
+-// VirtualIP is the primary load balancing configuration object that specifies
+-// the virtual IP address and port on which client traffic is received, as well
+-// as other details such as the load balancing method to be use, protocol, etc.
+-// This entity is sometimes known in LB products under the name of a "virtual
+-// server", a "vserver" or a "listener".
+-type VirtualIP struct {
+-	// The unique ID for the VIP.
+-	ID string `mapstructure:"id" json:"id"`
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"CreateSnapshot"})
--	c.Assert(req.Form["VolumeId"], DeepEquals, []string{"vol-4d826724"})
--	c.Assert(req.Form["Description"], DeepEquals, []string{"Daily Backup"})
+-	// Owner of the VIP. Only an admin user can specify a tenant ID other than its own.
+-	TenantID string `mapstructure:"tenant_id" json:"tenant_id"`
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
--	c.Assert(resp.Snapshot.Id, Equals, "snap-78a54011")
--	c.Assert(resp.Snapshot.VolumeId, Equals, "vol-4d826724")
--	c.Assert(resp.Snapshot.Status, Equals, "pending")
--	c.Assert(resp.Snapshot.StartTime, Equals, "2008-05-07T12:51:50.000Z")
--	c.Assert(resp.Snapshot.Progress, Equals, "60%")
--	c.Assert(resp.Snapshot.OwnerId, Equals, "111122223333")
--	c.Assert(resp.Snapshot.VolumeSize, Equals, "10")
--	c.Assert(resp.Snapshot.Description, Equals, "Daily Backup")
--}
+-	// Human-readable name for the VIP. Does not have to be unique.
+-	Name string `mapstructure:"name" json:"name"`
 -
--func (s *S) TestDeleteSnapshotsExample(c *C) {
--	testServer.Response(200, nil, DeleteSnapshotExample)
+-	// Human-readable description for the VIP.
+-	Description string `mapstructure:"description" json:"description"`
 -
--	resp, err := s.ec2.DeleteSnapshots([]string{"snap-78a54011"})
+-	// The ID of the subnet on which to allocate the VIP address.
+-	SubnetID string `mapstructure:"subnet_id" json:"subnet_id"`
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"DeleteSnapshot"})
--	c.Assert(req.Form["SnapshotId.1"], DeepEquals, []string{"snap-78a54011"})
+-	// The IP address of the VIP.
+-	Address string `mapstructure:"address" json:"address"`
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
--}
+-	// The protocol of the VIP address. A valid value is TCP, HTTP, or HTTPS.
+-	Protocol string `mapstructure:"protocol" json:"protocol"`
 -
--func (s *S) TestDescribeSnapshotsExample(c *C) {
--	testServer.Response(200, nil, DescribeSnapshotsExample)
+-	// The port on which to listen to client traffic that is associated with the
+-	// VIP address. A valid value is from 0 to 65535.
+-	ProtocolPort int `mapstructure:"protocol_port" json:"protocol_port"`
 -
--	filter := ec2.NewFilter()
--	filter.Add("key1", "value1")
--	filter.Add("key2", "value2", "value3")
+-	// The ID of the pool with which the VIP is associated.
+-	PoolID string `mapstructure:"pool_id" json:"pool_id"`
 -
--	resp, err := s.ec2.Snapshots([]string{"snap-1", "snap-2"}, filter)
+-	// The ID of the port which belongs to the load balancer
+-	PortID string `mapstructure:"port_id" json:"port_id"`
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeSnapshots"})
--	c.Assert(req.Form["SnapshotId.1"], DeepEquals, []string{"snap-1"})
--	c.Assert(req.Form["SnapshotId.2"], DeepEquals, []string{"snap-2"})
--	c.Assert(req.Form["Filter.1.Name"], DeepEquals, []string{"key1"})
--	c.Assert(req.Form["Filter.1.Value.1"], DeepEquals, []string{"value1"})
--	c.Assert(req.Form["Filter.1.Value.2"], IsNil)
--	c.Assert(req.Form["Filter.2.Name"], DeepEquals, []string{"key2"})
--	c.Assert(req.Form["Filter.2.Value.1"], DeepEquals, []string{"value2"})
--	c.Assert(req.Form["Filter.2.Value.2"], DeepEquals, []string{"value3"})
+-	// Indicates whether connections in the same session will be processed by the
+-	// same pool member or not.
+-	Persistence SessionPersistence `mapstructure:"session_persistence" json:"session_persistence"`
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
--	c.Assert(resp.Snapshots, HasLen, 1)
+-	// The maximum number of connections allowed for the VIP. Default is -1,
+-	// meaning no limit.
+-	ConnLimit int `mapstructure:"connection_limit" json:"connection_limit"`
 -
--	s0 := resp.Snapshots[0]
--	c.Assert(s0.Id, Equals, "snap-1a2b3c4d")
--	c.Assert(s0.VolumeId, Equals, "vol-8875daef")
--	c.Assert(s0.VolumeSize, Equals, "15")
--	c.Assert(s0.Status, Equals, "pending")
--	c.Assert(s0.StartTime, Equals, "2010-07-29T04:12:01.000Z")
--	c.Assert(s0.Progress, Equals, "30%")
--	c.Assert(s0.OwnerId, Equals, "111122223333")
--	c.Assert(s0.Description, Equals, "Daily Backup")
+-	// The administrative state of the VIP. A valid value is true (UP) or false (DOWN).
+-	AdminStateUp bool `mapstructure:"admin_state_up" json:"admin_state_up"`
 -
--	c.Assert(s0.Tags, HasLen, 1)
--	c.Assert(s0.Tags[0].Key, Equals, "Purpose")
--	c.Assert(s0.Tags[0].Value, Equals, "demo_db_14_backup")
+-	// The status of the VIP. Indicates whether the VIP is operational.
+-	Status string `mapstructure:"status" json:"status"`
 -}
 -
--func (s *S) TestModifyImageAttributeExample(c *C) {
--	testServer.Response(200, nil, ModifyImageAttributeExample)
+-// VIPPage is the page returned by a pager when traversing over a
+-// collection of routers.
+-type VIPPage struct {
+-	pagination.LinkedPageBase
+-}
 -
--	options := ec2.ModifyImageAttribute{
--		Description: "Test Description",
+-// NextPageURL is invoked when a paginated collection of routers has reached
+-// the end of a page and the pager seeks to traverse over a new one. In order
+-// to do this, it needs to construct the next page's URL.
+-func (p VIPPage) NextPageURL() (string, error) {
+-	type resp struct {
+-		Links []gophercloud.Link `mapstructure:"vips_links"`
 -	}
 -
--	resp, err := s.ec2.ModifyImageAttribute("ami-4fa54026", &options)
--
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"ModifyImageAttribute"})
+-	var r resp
+-	err := mapstructure.Decode(p.Body, &r)
+-	if err != nil {
+-		return "", err
+-	}
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	return gophercloud.ExtractNextURL(r.Links)
 -}
 -
--func (s *S) TestModifyImageAttributeExample_complex(c *C) {
--	testServer.Response(200, nil, ModifyImageAttributeExample)
--
--	options := ec2.ModifyImageAttribute{
--		AddUsers:     []string{"u1", "u2"},
--		RemoveUsers:  []string{"u3"},
--		AddGroups:    []string{"g1", "g3"},
--		RemoveGroups: []string{"g2"},
--		Description:  "Test Description",
+-// IsEmpty checks whether a RouterPage struct is empty.
+-func (p VIPPage) IsEmpty() (bool, error) {
+-	is, err := ExtractVIPs(p)
+-	if err != nil {
+-		return true, nil
 -	}
+-	return len(is) == 0, nil
+-}
 -
--	resp, err := s.ec2.ModifyImageAttribute("ami-4fa54026", &options)
+-// ExtractVIPs accepts a Page struct, specifically a VIPPage struct,
+-// and extracts the elements into a slice of VirtualIP structs. In other words,
+-// a generic collection is mapped into a relevant slice.
+-func ExtractVIPs(page pagination.Page) ([]VirtualIP, error) {
+-	var resp struct {
+-		VIPs []VirtualIP `mapstructure:"vips" json:"vips"`
+-	}
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"ModifyImageAttribute"})
--	c.Assert(req.Form["LaunchPermission.Add.1.UserId"], DeepEquals, []string{"u1"})
--	c.Assert(req.Form["LaunchPermission.Add.2.UserId"], DeepEquals, []string{"u2"})
--	c.Assert(req.Form["LaunchPermission.Remove.1.UserId"], DeepEquals, []string{"u3"})
--	c.Assert(req.Form["LaunchPermission.Add.1.Group"], DeepEquals, []string{"g1"})
--	c.Assert(req.Form["LaunchPermission.Add.2.Group"], DeepEquals, []string{"g3"})
--	c.Assert(req.Form["LaunchPermission.Remove.1.Group"], DeepEquals, []string{"g2"})
+-	err := mapstructure.Decode(page.(VIPPage).Body, &resp)
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	return resp.VIPs, err
 -}
 -
--func (s *S) TestCopyImageExample(c *C) {
--	testServer.Response(200, nil, CopyImageExample)
+-type commonResult struct {
+-	gophercloud.Result
+-}
 -
--	options := ec2.CopyImage{
--		SourceRegion:  "us-west-2",
--		SourceImageId: "ami-1a2b3c4d",
--		Description:   "Test Description",
+-// Extract is a function that accepts a result and extracts a router.
+-func (r commonResult) Extract() (*VirtualIP, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
 -	}
 -
--	resp, err := s.ec2.CopyImage(&options)
+-	var res struct {
+-		VirtualIP *VirtualIP `mapstructure:"vip" json:"vip"`
+-	}
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"CopyImage"})
+-	err := mapstructure.Decode(r.Body, &res)
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "60bc441d-fa2c-494d-b155-5d6a3EXAMPLE")
+-	return res.VirtualIP, err
 -}
 -
--func (s *S) TestCreateKeyPairExample(c *C) {
--	testServer.Response(200, nil, CreateKeyPairExample)
+-// CreateResult represents the result of a create operation.
+-type CreateResult struct {
+-	commonResult
+-}
 -
--	resp, err := s.ec2.CreateKeyPair("foo")
+-// GetResult represents the result of a get operation.
+-type GetResult struct {
+-	commonResult
+-}
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"CreateKeyPair"})
--	c.Assert(req.Form["KeyName"], DeepEquals, []string{"foo"})
+-// UpdateResult represents the result of an update operation.
+-type UpdateResult struct {
+-	commonResult
+-}
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
--	c.Assert(resp.KeyName, Equals, "foo")
--	c.Assert(resp.KeyFingerprint, Equals, "00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00")
+-// DeleteResult represents the result of a delete operation.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/vips/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/vips/urls.go
+deleted file mode 100644
+index 2b6f67e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/lbaas/vips/urls.go
++++ /dev/null
+@@ -1,16 +0,0 @@
+-package vips
 -
--func (s *S) TestDeleteKeyPairExample(c *C) {
--	testServer.Response(200, nil, DeleteKeyPairExample)
+-import "github.com/rackspace/gophercloud"
 -
--	resp, err := s.ec2.DeleteKeyPair("foo")
+-const (
+-	rootPath     = "lb"
+-	resourcePath = "vips"
+-)
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"DeleteKeyPair"})
--	c.Assert(req.Form["KeyName"], DeepEquals, []string{"foo"})
+-func rootURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL(rootPath, resourcePath)
+-}
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-func resourceURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL(rootPath, resourcePath, id)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/provider/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/provider/doc.go
+deleted file mode 100644
+index 373da44..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/provider/doc.go
++++ /dev/null
+@@ -1,21 +0,0 @@
+-// Package provider gives access to the provider Neutron plugin, allowing
+-// network extended attributes. The provider extended attributes for networks
+-// enable administrative users to specify how network objects map to the
+-// underlying networking infrastructure. These extended attributes also appear
+-// when administrative users query networks.
+-//
+-// For more information about extended attributes, see the NetworkExtAttrs
+-// struct. The actual semantics of these attributes depend on the technology
+-// back end of the particular plug-in. See the plug-in documentation and the
+-// OpenStack Cloud Administrator Guide to understand which values should be
+-// specific for each of these attributes when OpenStack Networking is deployed
+-// with a particular plug-in. The examples shown in this chapter refer to the
+-// Open vSwitch plug-in.
+-//
+-// The default policy settings enable only users with administrative rights to
+-// specify these parameters in requests and to see their values in responses. By
+-// default, the provider network extension attributes are completely hidden from
+-// regular tenants. As a rule of thumb, if these attributes are not visible in a
+-// GET /networks/<network-id> operation, this implies the user submitting the
+-// request is not authorized to view or manipulate provider network attributes.
+-package provider
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/provider/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/provider/results.go
+deleted file mode 100644
+index 3453584..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/provider/results.go
++++ /dev/null
+@@ -1,124 +0,0 @@
+-package provider
 -
--func (s *S) TestCreateSecurityGroupExample(c *C) {
--	testServer.Response(200, nil, CreateSecurityGroupExample)
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/networks"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	resp, err := s.ec2.CreateSecurityGroup(ec2.SecurityGroup{Name: "websrv", Description: "Web Servers"})
+-// AdminState gives users a solid type to work with for create and update
+-// operations. It is recommended that users use the `Up` and `Down` enums.
+-type AdminState *bool
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"CreateSecurityGroup"})
--	c.Assert(req.Form["GroupName"], DeepEquals, []string{"websrv"})
--	c.Assert(req.Form["GroupDescription"], DeepEquals, []string{"Web Servers"})
+-// Convenience vars for AdminStateUp values.
+-var (
+-	iTrue  = true
+-	iFalse = false
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
--	c.Assert(resp.Name, Equals, "websrv")
--	c.Assert(resp.Id, Equals, "sg-67ad940e")
--}
+-	Up   AdminState = &iTrue
+-	Down AdminState = &iFalse
+-)
+-
+-// NetworkExtAttrs represents an extended form of a Network with additional fields.
+-type NetworkExtAttrs struct {
+-	// UUID for the network
+-	ID string `mapstructure:"id" json:"id"`
 -
--func (s *S) TestDescribeSecurityGroupsExample(c *C) {
--	testServer.Response(200, nil, DescribeSecurityGroupsExample)
+-	// Human-readable name for the network. Might not be unique.
+-	Name string `mapstructure:"name" json:"name"`
 -
--	resp, err := s.ec2.SecurityGroups([]ec2.SecurityGroup{{Name: "WebServers"}, {Name: "RangedPortsBySource"}}, nil)
+-	// The administrative state of network. If false (down), the network does not forward packets.
+-	AdminStateUp bool `mapstructure:"admin_state_up" json:"admin_state_up"`
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeSecurityGroups"})
--	c.Assert(req.Form["GroupName.1"], DeepEquals, []string{"WebServers"})
--	c.Assert(req.Form["GroupName.2"], DeepEquals, []string{"RangedPortsBySource"})
+-	// Indicates whether network is currently operational. Possible values include
+-	// `ACTIVE', `DOWN', `BUILD', or `ERROR'. Plug-ins might define additional values.
+-	Status string `mapstructure:"status" json:"status"`
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
--	c.Assert(resp.Groups, HasLen, 2)
+-	// Subnets associated with this network.
+-	Subnets []string `mapstructure:"subnets" json:"subnets"`
 -
--	g0 := resp.Groups[0]
--	c.Assert(g0.OwnerId, Equals, "999988887777")
--	c.Assert(g0.Name, Equals, "WebServers")
--	c.Assert(g0.Id, Equals, "sg-67ad940e")
--	c.Assert(g0.Description, Equals, "Web Servers")
--	c.Assert(g0.IPPerms, HasLen, 1)
+-	// Owner of network. Only admin users can specify a tenant_id other than its own.
+-	TenantID string `mapstructure:"tenant_id" json:"tenant_id"`
 -
--	g0ipp := g0.IPPerms[0]
--	c.Assert(g0ipp.Protocol, Equals, "tcp")
--	c.Assert(g0ipp.FromPort, Equals, 80)
--	c.Assert(g0ipp.ToPort, Equals, 80)
--	c.Assert(g0ipp.SourceIPs, DeepEquals, []string{"0.0.0.0/0"})
+-	// Specifies whether the network resource can be accessed by any tenant or not.
+-	Shared bool `mapstructure:"shared" json:"shared"`
 -
--	g1 := resp.Groups[1]
--	c.Assert(g1.OwnerId, Equals, "999988887777")
--	c.Assert(g1.Name, Equals, "RangedPortsBySource")
--	c.Assert(g1.Id, Equals, "sg-76abc467")
--	c.Assert(g1.Description, Equals, "Group A")
--	c.Assert(g1.IPPerms, HasLen, 1)
+-	// Specifies the nature of the physical network mapped to this network
+-	// resource. Examples are flat, vlan, or gre.
+-	NetworkType string `json:"provider:network_type" mapstructure:"provider:network_type"`
 -
--	g1ipp := g1.IPPerms[0]
--	c.Assert(g1ipp.Protocol, Equals, "tcp")
--	c.Assert(g1ipp.FromPort, Equals, 6000)
--	c.Assert(g1ipp.ToPort, Equals, 7000)
--	c.Assert(g1ipp.SourceIPs, IsNil)
--}
+-	// Identifies the physical network on top of which this network object is
+-	// being implemented. The OpenStack Networking API does not expose any facility
+-	// for retrieving the list of available physical networks. As an example, in
+-	// the Open vSwitch plug-in this is a symbolic name which is then mapped to
+-	// specific bridges on each compute host through the Open vSwitch plug-in
+-	// configuration file.
+-	PhysicalNetwork string `json:"provider:physical_network" mapstructure:"provider:physical_network"`
 -
--func (s *S) TestDescribeSecurityGroupsExampleWithFilter(c *C) {
--	testServer.Response(200, nil, DescribeSecurityGroupsExample)
+-	// Identifies an isolated segment on the physical network; the nature of the
+-	// segment depends on the segmentation model defined by network_type. For
+-	// instance, if network_type is vlan, then this is a vlan identifier;
+-	// otherwise, if network_type is gre, then this will be a gre key.
+-	SegmentationID string `json:"provider:segmentation_id" mapstructure:"provider:segmentation_id"`
+-}
 -
--	filter := ec2.NewFilter()
--	filter.Add("ip-permission.protocol", "tcp")
--	filter.Add("ip-permission.from-port", "22")
--	filter.Add("ip-permission.to-port", "22")
--	filter.Add("ip-permission.group-name", "app_server_group", "database_group")
+-// ExtractGet decorates a GetResult struct returned from a networks.Get()
+-// function with extended attributes.
+-func ExtractGet(r networks.GetResult) (*NetworkExtAttrs, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
+-	}
 -
--	_, err := s.ec2.SecurityGroups(nil, filter)
+-	var res struct {
+-		Network *NetworkExtAttrs `json:"network"`
+-	}
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeSecurityGroups"})
--	c.Assert(req.Form["Filter.1.Name"], DeepEquals, []string{"ip-permission.from-port"})
--	c.Assert(req.Form["Filter.1.Value.1"], DeepEquals, []string{"22"})
--	c.Assert(req.Form["Filter.2.Name"], DeepEquals, []string{"ip-permission.group-name"})
--	c.Assert(req.Form["Filter.2.Value.1"], DeepEquals, []string{"app_server_group"})
--	c.Assert(req.Form["Filter.2.Value.2"], DeepEquals, []string{"database_group"})
--	c.Assert(req.Form["Filter.3.Name"], DeepEquals, []string{"ip-permission.protocol"})
--	c.Assert(req.Form["Filter.3.Value.1"], DeepEquals, []string{"tcp"})
--	c.Assert(req.Form["Filter.4.Name"], DeepEquals, []string{"ip-permission.to-port"})
--	c.Assert(req.Form["Filter.4.Value.1"], DeepEquals, []string{"22"})
+-	err := mapstructure.Decode(r.Body, &res)
 -
--	c.Assert(err, IsNil)
+-	return res.Network, err
 -}
 -
--func (s *S) TestDescribeSecurityGroupsDumpWithGroup(c *C) {
--	testServer.Response(200, nil, DescribeSecurityGroupsDump)
--
--	resp, err := s.ec2.SecurityGroups(nil, nil)
+-// ExtractCreate decorates a CreateResult struct returned from a networks.Create()
+-// function with extended attributes.
+-func ExtractCreate(r networks.CreateResult) (*NetworkExtAttrs, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
+-	}
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeSecurityGroups"})
--	c.Assert(err, IsNil)
--	c.Check(resp.Groups, HasLen, 1)
--	c.Check(resp.Groups[0].IPPerms, HasLen, 2)
+-	var res struct {
+-		Network *NetworkExtAttrs `json:"network"`
+-	}
 -
--	ipp0 := resp.Groups[0].IPPerms[0]
--	c.Assert(ipp0.SourceIPs, IsNil)
--	c.Check(ipp0.Protocol, Equals, "icmp")
--	c.Assert(ipp0.SourceGroups, HasLen, 1)
--	c.Check(ipp0.SourceGroups[0].OwnerId, Equals, "12345")
--	c.Check(ipp0.SourceGroups[0].Name, Equals, "default")
--	c.Check(ipp0.SourceGroups[0].Id, Equals, "sg-67ad940e")
+-	err := mapstructure.Decode(r.Body, &res)
 -
--	ipp1 := resp.Groups[0].IPPerms[1]
--	c.Check(ipp1.Protocol, Equals, "tcp")
--	c.Assert(ipp0.SourceIPs, IsNil)
--	c.Assert(ipp0.SourceGroups, HasLen, 1)
--	c.Check(ipp1.SourceGroups[0].Id, Equals, "sg-76abc467")
--	c.Check(ipp1.SourceGroups[0].OwnerId, Equals, "12345")
--	c.Check(ipp1.SourceGroups[0].Name, Equals, "other")
+-	return res.Network, err
 -}
 -
--func (s *S) TestDeleteSecurityGroupExample(c *C) {
--	testServer.Response(200, nil, DeleteSecurityGroupExample)
+-// ExtractUpdate decorates a UpdateResult struct returned from a
+-// networks.Update() function with extended attributes.
+-func ExtractUpdate(r networks.UpdateResult) (*NetworkExtAttrs, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
+-	}
 -
--	resp, err := s.ec2.DeleteSecurityGroup(ec2.SecurityGroup{Name: "websrv"})
--	req := testServer.WaitRequest()
+-	var res struct {
+-		Network *NetworkExtAttrs `json:"network"`
+-	}
 -
--	c.Assert(req.Form["Action"], DeepEquals, []string{"DeleteSecurityGroup"})
--	c.Assert(req.Form["GroupName"], DeepEquals, []string{"websrv"})
--	c.Assert(req.Form["GroupId"], IsNil)
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	err := mapstructure.Decode(r.Body, &res)
+-
+-	return res.Network, err
 -}
 -
--func (s *S) TestDeleteSecurityGroupExampleWithId(c *C) {
--	testServer.Response(200, nil, DeleteSecurityGroupExample)
+-// ExtractList accepts a Page struct, specifically a NetworkPage struct, and
+-// extracts the elements into a slice of NetworkExtAttrs structs. In other
+-// words, a generic collection is mapped into a relevant slice.
+-func ExtractList(page pagination.Page) ([]NetworkExtAttrs, error) {
+-	var resp struct {
+-		Networks []NetworkExtAttrs `mapstructure:"networks" json:"networks"`
+-	}
 -
--	// ignore return and error - we're only want to check the parameter handling.
--	s.ec2.DeleteSecurityGroup(ec2.SecurityGroup{Id: "sg-67ad940e", Name: "ignored"})
--	req := testServer.WaitRequest()
+-	err := mapstructure.Decode(page.(networks.NetworkPage).Body, &resp)
 -
--	c.Assert(req.Form["GroupName"], IsNil)
--	c.Assert(req.Form["GroupId"], DeepEquals, []string{"sg-67ad940e"})
+-	return resp.Networks, err
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/provider/results_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/provider/results_test.go
+deleted file mode 100644
+index 9801b2e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/provider/results_test.go
++++ /dev/null
+@@ -1,253 +0,0 @@
+-package provider
 -
--func (s *S) TestAuthorizeSecurityGroupExample1(c *C) {
--	testServer.Response(200, nil, AuthorizeSecurityGroupIngressExample)
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--	perms := []ec2.IPPerm{{
--		Protocol:  "tcp",
--		FromPort:  80,
--		ToPort:    80,
--		SourceIPs: []string{"205.192.0.0/16", "205.159.0.0/16"},
--	}}
--	resp, err := s.ec2.AuthorizeSecurityGroup(ec2.SecurityGroup{Name: "websrv"}, perms)
+-	fake "github.com/rackspace/gophercloud/openstack/networking/v2/common"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/networks"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--	req := testServer.WaitRequest()
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	c.Assert(req.Form["Action"], DeepEquals, []string{"AuthorizeSecurityGroupIngress"})
--	c.Assert(req.Form["GroupName"], DeepEquals, []string{"websrv"})
--	c.Assert(req.Form["IpPermissions.1.IpProtocol"], DeepEquals, []string{"tcp"})
--	c.Assert(req.Form["IpPermissions.1.FromPort"], DeepEquals, []string{"80"})
--	c.Assert(req.Form["IpPermissions.1.ToPort"], DeepEquals, []string{"80"})
--	c.Assert(req.Form["IpPermissions.1.IpRanges.1.CidrIp"], DeepEquals, []string{"205.192.0.0/16"})
--	c.Assert(req.Form["IpPermissions.1.IpRanges.2.CidrIp"], DeepEquals, []string{"205.159.0.0/16"})
+-	th.Mux.HandleFunc("/v2.0/networks", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "networks": [
+-        {
+-            "status": "ACTIVE",
+-            "subnets": [
+-                "54d6f61d-db07-451c-9ab3-b9609b6b6f0b"
+-            ],
+-            "name": "private-network",
+-            "admin_state_up": true,
+-            "tenant_id": "4fd44f30292945e481c7b8a0c8908869",
+-            "shared": true,
+-            "id": "d32019d3-bc6e-4319-9c1d-6722fc136a22",
+-            "provider:segmentation_id": null,
+-            "provider:physical_network": null,
+-            "provider:network_type": "local"
+-        },
+-        {
+-            "status": "ACTIVE",
+-            "subnets": [
+-                "08eae331-0402-425a-923c-34f7cfe39c1b"
+-            ],
+-            "name": "private",
+-            "admin_state_up": true,
+-            "tenant_id": "26a7980765d0414dbc1fc1f88cdb7e6e",
+-            "shared": true,
+-            "id": "db193ab3-96e3-4cb3-8fc5-05f4296d0324",
+-            "provider:segmentation_id": null,
+-            "provider:physical_network": null,
+-            "provider:network_type": "local"
+-        }
+-    ]
 -}
+-			`)
+-	})
 -
--func (s *S) TestAuthorizeSecurityGroupEgress(c *C) {
--	testServer.Response(200, nil, AuthorizeSecurityGroupEgressExample)
+-	count := 0
 -
--	perms := []ec2.IPPerm{{
--		Protocol:  "tcp",
--		FromPort:  80,
--		ToPort:    80,
--		SourceIPs: []string{"205.192.0.0/16", "205.159.0.0/16"},
--	}}
--	resp, err := s.ec2.AuthorizeSecurityGroupEgress(ec2.SecurityGroup{Name: "websrv"}, perms)
+-	networks.List(fake.ServiceClient(), networks.ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractList(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract networks: %v", err)
+-			return false, err
+-		}
 -
--	req := testServer.WaitRequest()
+-		expected := []NetworkExtAttrs{
+-			NetworkExtAttrs{
+-				Status:          "ACTIVE",
+-				Subnets:         []string{"54d6f61d-db07-451c-9ab3-b9609b6b6f0b"},
+-				Name:            "private-network",
+-				AdminStateUp:    true,
+-				TenantID:        "4fd44f30292945e481c7b8a0c8908869",
+-				Shared:          true,
+-				ID:              "d32019d3-bc6e-4319-9c1d-6722fc136a22",
+-				NetworkType:     "local",
+-				PhysicalNetwork: "",
+-				SegmentationID:  "",
+-			},
+-			NetworkExtAttrs{
+-				Status:          "ACTIVE",
+-				Subnets:         []string{"08eae331-0402-425a-923c-34f7cfe39c1b"},
+-				Name:            "private",
+-				AdminStateUp:    true,
+-				TenantID:        "26a7980765d0414dbc1fc1f88cdb7e6e",
+-				Shared:          true,
+-				ID:              "db193ab3-96e3-4cb3-8fc5-05f4296d0324",
+-				NetworkType:     "local",
+-				PhysicalNetwork: "",
+-				SegmentationID:  "",
+-			},
+-		}
 -
--	c.Assert(req.Form["Action"], DeepEquals, []string{"AuthorizeSecurityGroupEgress"})
--	c.Assert(req.Form["GroupName"], DeepEquals, []string{"websrv"})
--	c.Assert(req.Form["IpPermissions.1.IpProtocol"], DeepEquals, []string{"tcp"})
--	c.Assert(req.Form["IpPermissions.1.FromPort"], DeepEquals, []string{"80"})
--	c.Assert(req.Form["IpPermissions.1.ToPort"], DeepEquals, []string{"80"})
--	c.Assert(req.Form["IpPermissions.1.IpRanges.1.CidrIp"], DeepEquals, []string{"205.192.0.0/16"})
--	c.Assert(req.Form["IpPermissions.1.IpRanges.2.CidrIp"], DeepEquals, []string{"205.159.0.0/16"})
+-		th.CheckDeepEquals(t, expected, actual)
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-		return true, nil
+-	})
+-
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
+-	}
 -}
 -
--func (s *S) TestAuthorizeSecurityGroupExample1WithId(c *C) {
--	testServer.Response(200, nil, AuthorizeSecurityGroupIngressExample)
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	perms := []ec2.IPPerm{{
--		Protocol:  "tcp",
--		FromPort:  80,
--		ToPort:    80,
--		SourceIPs: []string{"205.192.0.0/16", "205.159.0.0/16"},
--	}}
--	// ignore return and error - we're only want to check the parameter handling.
--	s.ec2.AuthorizeSecurityGroup(ec2.SecurityGroup{Id: "sg-67ad940e", Name: "ignored"}, perms)
+-	th.Mux.HandleFunc("/v2.0/networks/d32019d3-bc6e-4319-9c1d-6722fc136a22", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--	req := testServer.WaitRequest()
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--	c.Assert(req.Form["GroupName"], IsNil)
--	c.Assert(req.Form["GroupId"], DeepEquals, []string{"sg-67ad940e"})
+-		fmt.Fprintf(w, `
+-{
+-    "network": {
+-        "status": "ACTIVE",
+-        "subnets": [
+-            "54d6f61d-db07-451c-9ab3-b9609b6b6f0b"
+-        ],
+-        "name": "private-network",
+-        "provider:physical_network": null,
+-        "admin_state_up": true,
+-        "tenant_id": "4fd44f30292945e481c7b8a0c8908869",
+-        "provider:network_type": "local",
+-        "shared": true,
+-        "id": "d32019d3-bc6e-4319-9c1d-6722fc136a22",
+-        "provider:segmentation_id": null
+-    }
 -}
+-			`)
+-	})
 -
--func (s *S) TestAuthorizeSecurityGroupExample2(c *C) {
--	testServer.Response(200, nil, AuthorizeSecurityGroupIngressExample)
+-	res := networks.Get(fake.ServiceClient(), "d32019d3-bc6e-4319-9c1d-6722fc136a22")
+-	n, err := ExtractGet(res)
 -
--	perms := []ec2.IPPerm{{
--		Protocol: "tcp",
--		FromPort: 80,
--		ToPort:   81,
--		SourceGroups: []ec2.UserSecurityGroup{
--			{OwnerId: "999988887777", Name: "OtherAccountGroup"},
--			{Id: "sg-67ad940e"},
--		},
--	}}
--	resp, err := s.ec2.AuthorizeSecurityGroup(ec2.SecurityGroup{Name: "websrv"}, perms)
+-	th.AssertNoErr(t, err)
 -
--	req := testServer.WaitRequest()
+-	th.AssertEquals(t, "", n.PhysicalNetwork)
+-	th.AssertEquals(t, "local", n.NetworkType)
+-	th.AssertEquals(t, "", n.SegmentationID)
+-}
 -
--	c.Assert(req.Form["Action"], DeepEquals, []string{"AuthorizeSecurityGroupIngress"})
--	c.Assert(req.Form["GroupName"], DeepEquals, []string{"websrv"})
--	c.Assert(req.Form["IpPermissions.1.IpProtocol"], DeepEquals, []string{"tcp"})
--	c.Assert(req.Form["IpPermissions.1.FromPort"], DeepEquals, []string{"80"})
--	c.Assert(req.Form["IpPermissions.1.ToPort"], DeepEquals, []string{"81"})
--	c.Assert(req.Form["IpPermissions.1.Groups.1.UserId"], DeepEquals, []string{"999988887777"})
--	c.Assert(req.Form["IpPermissions.1.Groups.1.GroupName"], DeepEquals, []string{"OtherAccountGroup"})
--	c.Assert(req.Form["IpPermissions.1.Groups.2.UserId"], IsNil)
--	c.Assert(req.Form["IpPermissions.1.Groups.2.GroupName"], IsNil)
--	c.Assert(req.Form["IpPermissions.1.Groups.2.GroupId"], DeepEquals, []string{"sg-67ad940e"})
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/networks", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "network": {
+-        "name": "sample_network",
+-        "admin_state_up": true
+-    }
+-}
+-			`)
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "network": {
+-        "status": "ACTIVE",
+-        "subnets": [
+-            "54d6f61d-db07-451c-9ab3-b9609b6b6f0b"
+-        ],
+-        "name": "private-network",
+-        "provider:physical_network": null,
+-        "admin_state_up": true,
+-        "tenant_id": "4fd44f30292945e481c7b8a0c8908869",
+-        "provider:network_type": "local",
+-        "shared": true,
+-        "id": "d32019d3-bc6e-4319-9c1d-6722fc136a22",
+-        "provider:segmentation_id": null
+-    }
 -}
+-		`)
+-	})
 -
--func (s *S) TestRevokeSecurityGroupExample(c *C) {
--	// RevokeSecurityGroup is implemented by the same code as AuthorizeSecurityGroup
--	// so there's no need to duplicate all the tests.
--	testServer.Response(200, nil, RevokeSecurityGroupIngressExample)
+-	options := networks.CreateOpts{Name: "sample_network", AdminStateUp: Up}
+-	res := networks.Create(fake.ServiceClient(), options)
+-	n, err := ExtractCreate(res)
 -
--	resp, err := s.ec2.RevokeSecurityGroup(ec2.SecurityGroup{Name: "websrv"}, nil)
+-	th.AssertNoErr(t, err)
 -
--	req := testServer.WaitRequest()
+-	th.AssertEquals(t, "", n.PhysicalNetwork)
+-	th.AssertEquals(t, "local", n.NetworkType)
+-	th.AssertEquals(t, "", n.SegmentationID)
+-}
 -
--	c.Assert(req.Form["Action"], DeepEquals, []string{"RevokeSecurityGroupIngress"})
--	c.Assert(req.Form["GroupName"], DeepEquals, []string{"websrv"})
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-func TestUpdate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/networks/4e8e5957-649f-477b-9e5b-f1f75b21c03c", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-		"network": {
+-				"name": "new_network_name",
+-				"admin_state_up": false,
+-				"shared": true
+-		}
 -}
+-			`)
 -
--func (s *S) TestCreateTags(c *C) {
--	testServer.Response(200, nil, CreateTagsExample)
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--	resp, err := s.ec2.CreateTags([]string{"ami-1a2b3c4d", "i-7f4d3a2b"}, []ec2.Tag{{"webserver", ""}, {"stack", "Production"}})
+-		fmt.Fprintf(w, `
+-{
+-    "network": {
+-        "status": "ACTIVE",
+-        "subnets": [
+-            "54d6f61d-db07-451c-9ab3-b9609b6b6f0b"
+-        ],
+-        "name": "private-network",
+-        "provider:physical_network": null,
+-        "admin_state_up": true,
+-        "tenant_id": "4fd44f30292945e481c7b8a0c8908869",
+-        "provider:network_type": "local",
+-        "shared": true,
+-        "id": "d32019d3-bc6e-4319-9c1d-6722fc136a22",
+-        "provider:segmentation_id": null
+-    }
+-}
+-		`)
+-	})
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["ResourceId.1"], DeepEquals, []string{"ami-1a2b3c4d"})
--	c.Assert(req.Form["ResourceId.2"], DeepEquals, []string{"i-7f4d3a2b"})
--	c.Assert(req.Form["Tag.1.Key"], DeepEquals, []string{"webserver"})
--	c.Assert(req.Form["Tag.1.Value"], DeepEquals, []string{""})
--	c.Assert(req.Form["Tag.2.Key"], DeepEquals, []string{"stack"})
--	c.Assert(req.Form["Tag.2.Value"], DeepEquals, []string{"Production"})
+-	iTrue := true
+-	options := networks.UpdateOpts{Name: "new_network_name", AdminStateUp: Down, Shared: &iTrue}
+-	res := networks.Update(fake.ServiceClient(), "4e8e5957-649f-477b-9e5b-f1f75b21c03c", options)
+-	n, err := ExtractUpdate(res)
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, "", n.PhysicalNetwork)
+-	th.AssertEquals(t, "local", n.NetworkType)
+-	th.AssertEquals(t, "", n.SegmentationID)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/doc.go
+deleted file mode 100644
+index 8ef455f..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/doc.go
++++ /dev/null
+@@ -1,32 +0,0 @@
+-// Package security contains functionality to work with security group and
+-// security group rules Neutron resources.
+-//
+-// Security groups and security group rules allows administrators and tenants
+-// the ability to specify the type of traffic and direction (ingress/egress)
+-// that is allowed to pass through a port. A security group is a container for
+-// security group rules.
+-//
+-// When a port is created in Networking it is associated with a security group.
+-// If a security group is not specified the port is associated with a 'default'
+-// security group. By default, this group drops all ingress traffic and allows
+-// all egress. Rules can be added to this group in order to change the behaviour.
+-//
+-// The basic characteristics of Neutron Security Groups are:
+-//
+-// For ingress traffic (to an instance)
+-//  - Only traffic matched with security group rules are allowed.
+-//  - When there is no rule defined, all traffic are dropped.
+-//
+-// For egress traffic (from an instance)
+-//  - Only traffic matched with security group rules are allowed.
+-//  - When there is no rule defined, all egress traffic are dropped.
+-//  - When a new security group is created, rules to allow all egress traffic
+-//    are automatically added.
+-//
+-// "default security group" is defined for each tenant.
+-//  - For the default security group a rule which allows intercommunication
+-//    among hosts associated with the default security group is defined by default.
+-//  - As a result, all egress traffic and intercommunication in the default
+-//    group are allowed and all ingress from outside of the default group is
+-//    dropped by default (in the default security group).
+-package security
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/groups/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/groups/requests.go
+deleted file mode 100644
+index 0c970ae..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/groups/requests.go
++++ /dev/null
+@@ -1,107 +0,0 @@
+-package groups
 -
--func (s *S) TestStartInstances(c *C) {
--	testServer.Response(200, nil, StartInstancesExample)
+-import (
+-	"fmt"
 -
--	resp, err := s.ec2.StartInstances("i-10a64379")
--	req := testServer.WaitRequest()
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	c.Assert(req.Form["Action"], DeepEquals, []string{"StartInstances"})
--	c.Assert(req.Form["InstanceId.1"], DeepEquals, []string{"i-10a64379"})
+-// ListOpts allows the filtering and sorting of paginated collections through
+-// the API. Filtering is achieved by passing in struct field values that map to
+-// the floating IP attributes you want to see returned. SortKey allows you to
+-// sort by a particular network attribute. SortDir sets the direction, and is
+-// either `asc' or `desc'. Marker and Limit are used for pagination.
+-type ListOpts struct {
+-	ID       string `q:"id"`
+-	Name     string `q:"name"`
+-	TenantID string `q:"tenant_id"`
+-	Limit    int    `q:"limit"`
+-	Marker   string `q:"marker"`
+-	SortKey  string `q:"sort_key"`
+-	SortDir  string `q:"sort_dir"`
+-}
+-
+-// List returns a Pager which allows you to iterate over a collection of
+-// security groups. It accepts a ListOpts struct, which allows you to filter
+-// and sort the returned collection for greater efficiency.
+-func List(c *gophercloud.ServiceClient, opts ListOpts) pagination.Pager {
+-	q, err := gophercloud.BuildQueryString(&opts)
+-	if err != nil {
+-		return pagination.Pager{Err: err}
+-	}
+-	u := rootURL(c) + q.String()
+-	return pagination.NewPager(c, u, func(r pagination.PageResult) pagination.Page {
+-		return SecGroupPage{pagination.LinkedPageBase{PageResult: r}}
+-	})
+-}
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-var (
+-	errNameRequired = fmt.Errorf("Name is required")
+-)
 -
--	s0 := resp.StateChanges[0]
--	c.Assert(s0.InstanceId, Equals, "i-10a64379")
--	c.Assert(s0.CurrentState.Code, Equals, 0)
--	c.Assert(s0.CurrentState.Name, Equals, "pending")
--	c.Assert(s0.PreviousState.Code, Equals, 80)
--	c.Assert(s0.PreviousState.Name, Equals, "stopped")
+-// CreateOpts contains all the values needed to create a new security group.
+-type CreateOpts struct {
+-	// Required. Human-readable name for the VIP. Does not have to be unique.
+-	Name string
+-
+-	// Optional. Describes the security group.
+-	Description string
 -}
 -
--func (s *S) TestStopInstances(c *C) {
--	testServer.Response(200, nil, StopInstancesExample)
+-// Create is an operation which provisions a new security group with default
+-// security group rules for the IPv4 and IPv6 ether types.
+-func Create(c *gophercloud.ServiceClient, opts CreateOpts) CreateResult {
+-	var res CreateResult
 -
--	resp, err := s.ec2.StopInstances("i-10a64379")
--	req := testServer.WaitRequest()
+-	// Validate required opts
+-	if opts.Name == "" {
+-		res.Err = errNameRequired
+-		return res
+-	}
 -
--	c.Assert(req.Form["Action"], DeepEquals, []string{"StopInstances"})
--	c.Assert(req.Form["InstanceId.1"], DeepEquals, []string{"i-10a64379"})
+-	type secgroup struct {
+-		Name        string `json:"name"`
+-		Description string `json:"description,omitempty"`
+-	}
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	type request struct {
+-		SecGroup secgroup `json:"security_group"`
+-	}
 -
--	s0 := resp.StateChanges[0]
--	c.Assert(s0.InstanceId, Equals, "i-10a64379")
--	c.Assert(s0.CurrentState.Code, Equals, 64)
--	c.Assert(s0.CurrentState.Name, Equals, "stopping")
--	c.Assert(s0.PreviousState.Code, Equals, 16)
--	c.Assert(s0.PreviousState.Name, Equals, "running")
--}
+-	reqBody := request{SecGroup: secgroup{
+-		Name:        opts.Name,
+-		Description: opts.Description,
+-	}}
 -
--func (s *S) TestRebootInstances(c *C) {
--	testServer.Response(200, nil, RebootInstancesExample)
+-	_, res.Err = perigee.Request("POST", rootURL(c), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{201},
+-	})
 -
--	resp, err := s.ec2.RebootInstances("i-10a64379")
--	req := testServer.WaitRequest()
+-	return res
+-}
 -
--	c.Assert(req.Form["Action"], DeepEquals, []string{"RebootInstances"})
--	c.Assert(req.Form["InstanceId.1"], DeepEquals, []string{"i-10a64379"})
+-// Get retrieves a particular security group based on its unique ID.
+-func Get(c *gophercloud.ServiceClient, id string) GetResult {
+-	var res GetResult
+-	_, res.Err = perigee.Request("GET", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return res
+-}
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-// Delete will permanently delete a particular security group based on its unique ID.
+-func Delete(c *gophercloud.ServiceClient, id string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{204},
+-	})
+-	return res
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/groups/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/groups/requests_test.go
+deleted file mode 100644
+index 5f074c7..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/groups/requests_test.go
++++ /dev/null
+@@ -1,213 +0,0 @@
+-package groups
 -
--func (s *S) TestSignatureWithEndpointPath(c *C) {
--	ec2.FakeTime(true)
--	defer ec2.FakeTime(false)
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--	testServer.Response(200, nil, RebootInstancesExample)
+-	fake "github.com/rackspace/gophercloud/openstack/networking/v2/common"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--	// https://bugs.launchpad.net/goamz/+bug/1022749
--	ec2 := ec2.NewWithClient(s.ec2.Auth, aws.Region{EC2Endpoint: testServer.URL + "/services/Cloud"}, testutil.DefaultClient)
+-func TestURLs(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	_, err := ec2.RebootInstances("i-10a64379")
--	c.Assert(err, IsNil)
+-	th.AssertEquals(t, th.Endpoint()+"v2.0/security-groups", rootURL(fake.ServiceClient()))
+-	th.AssertEquals(t, th.Endpoint()+"v2.0/security-groups/foo", resourceURL(fake.ServiceClient(), "foo"))
+-}
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Signature"], DeepEquals, []string{"QmvgkYGn19WirCuCz/jRp3RmRgFwWR5WRkKZ5AZnyXQ="})
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/security-groups", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "security_groups": [
+-        {
+-            "description": "default",
+-            "id": "85cc3048-abc3-43cc-89b3-377341426ac5",
+-            "name": "default",
+-            "security_group_rules": [],
+-            "tenant_id": "e4f50856753b4dc6afee5fa6b9b6c550"
+-        }
+-    ]
 -}
+-      `)
+-	})
 -
--func (s *S) TestAllocateAddressExample(c *C) {
--	testServer.Response(200, nil, AllocateAddressExample)
+-	count := 0
 -
--	options := &ec2.AllocateAddress{
--		Domain: "vpc",
--	}
+-	List(fake.ServiceClient(), ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractGroups(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract secgroups: %v", err)
+-			return false, err
+-		}
 -
--	resp, err := s.ec2.AllocateAddress(options)
+-		expected := []SecGroup{
+-			SecGroup{
+-				Description: "default",
+-				ID:          "85cc3048-abc3-43cc-89b3-377341426ac5",
+-				Name:        "default",
+-				Rules:       []rules.SecGroupRule{},
+-				TenantID:    "e4f50856753b4dc6afee5fa6b9b6c550",
+-			},
+-		}
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"AllocateAddress"})
--	c.Assert(req.Form["Domain"], DeepEquals, []string{"vpc"})
+-		th.CheckDeepEquals(t, expected, actual)
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
--	c.Assert(resp.PublicIp, Equals, "198.51.100.1")
--	c.Assert(resp.Domain, Equals, "vpc")
--	c.Assert(resp.AllocationId, Equals, "eipalloc-5723d13e")
--}
+-		return true, nil
+-	})
 -
--func (s *S) TestReleaseAddressExample(c *C) {
--	testServer.Response(200, nil, ReleaseAddressExample)
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
+-	}
+-}
 -
--	resp, err := s.ec2.ReleaseAddress("eipalloc-5723d13e")
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/security-groups", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "security_group": {
+-        "name": "new-webservers",
+-        "description": "security group for webservers"
+-    }
+-}
+-      `)
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"ReleaseAddress"})
--	c.Assert(req.Form["AllocationId"], DeepEquals, []string{"eipalloc-5723d13e"})
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-		fmt.Fprintf(w, `
+-{
+-    "security_group": {
+-        "description": "security group for webservers",
+-        "id": "2076db17-a522-4506-91de-c6dd8e837028",
+-        "name": "new-webservers",
+-        "security_group_rules": [
+-            {
+-                "direction": "egress",
+-                "ethertype": "IPv4",
+-                "id": "38ce2d8e-e8f1-48bd-83c2-d33cb9f50c3d",
+-                "port_range_max": null,
+-                "port_range_min": null,
+-                "protocol": null,
+-                "remote_group_id": null,
+-                "remote_ip_prefix": null,
+-                "security_group_id": "2076db17-a522-4506-91de-c6dd8e837028",
+-                "tenant_id": "e4f50856753b4dc6afee5fa6b9b6c550"
+-            },
+-            {
+-                "direction": "egress",
+-                "ethertype": "IPv6",
+-                "id": "565b9502-12de-4ffd-91e9-68885cff6ae1",
+-                "port_range_max": null,
+-                "port_range_min": null,
+-                "protocol": null,
+-                "remote_group_id": null,
+-                "remote_ip_prefix": null,
+-                "security_group_id": "2076db17-a522-4506-91de-c6dd8e837028",
+-                "tenant_id": "e4f50856753b4dc6afee5fa6b9b6c550"
+-            }
+-        ],
+-        "tenant_id": "e4f50856753b4dc6afee5fa6b9b6c550"
+-    }
 -}
+-    `)
+-	})
 -
--func (s *S) TestAssociateAddressExample(c *C) {
--	testServer.Response(200, nil, AssociateAddressExample)
+-	opts := CreateOpts{Name: "new-webservers", Description: "security group for webservers"}
+-	_, err := Create(fake.ServiceClient(), opts).Extract()
+-	th.AssertNoErr(t, err)
+-}
 -
--	options := &ec2.AssociateAddress{
--		InstanceId:         "i-4fd2431a",
--		AllocationId:       "eipalloc-5723d13e",
--		AllowReassociation: true,
--	}
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	resp, err := s.ec2.AssociateAddress(options)
+-	th.Mux.HandleFunc("/v2.0/security-groups/85cc3048-abc3-43cc-89b3-377341426ac5", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"AssociateAddress"})
--	c.Assert(req.Form["InstanceId"], DeepEquals, []string{"i-4fd2431a"})
--	c.Assert(req.Form["AllocationId"], DeepEquals, []string{"eipalloc-5723d13e"})
--	c.Assert(req.Form["AllowReassociation"], DeepEquals, []string{"true"})
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
--	c.Assert(resp.AssociationId, Equals, "eipassoc-fc5ca095")
+-		fmt.Fprintf(w, `
+-{
+-    "security_group": {
+-        "description": "default",
+-        "id": "85cc3048-abc3-43cc-89b3-377341426ac5",
+-        "name": "default",
+-        "security_group_rules": [
+-            {
+-                "direction": "egress",
+-                "ethertype": "IPv6",
+-                "id": "3c0e45ff-adaf-4124-b083-bf390e5482ff",
+-                "port_range_max": null,
+-                "port_range_min": null,
+-                "protocol": null,
+-                "remote_group_id": null,
+-                "remote_ip_prefix": null,
+-                "security_group_id": "85cc3048-abc3-43cc-89b3-377341426ac5",
+-                "tenant_id": "e4f50856753b4dc6afee5fa6b9b6c550"
+-            },
+-            {
+-                "direction": "egress",
+-                "ethertype": "IPv4",
+-                "id": "93aa42e5-80db-4581-9391-3a608bd0e448",
+-                "port_range_max": null,
+-                "port_range_min": null,
+-                "protocol": null,
+-                "remote_group_id": null,
+-                "remote_ip_prefix": null,
+-                "security_group_id": "85cc3048-abc3-43cc-89b3-377341426ac5",
+-                "tenant_id": "e4f50856753b4dc6afee5fa6b9b6c550"
+-            }
+-        ],
+-        "tenant_id": "e4f50856753b4dc6afee5fa6b9b6c550"
+-    }
 -}
+-      `)
+-	})
 -
--func (s *S) TestDisassociateAddressExample(c *C) {
--	testServer.Response(200, nil, DisassociateAddressExample)
+-	sg, err := Get(fake.ServiceClient(), "85cc3048-abc3-43cc-89b3-377341426ac5").Extract()
+-	th.AssertNoErr(t, err)
 -
--	resp, err := s.ec2.DisassociateAddress("eipassoc-aa7486c3")
+-	th.AssertEquals(t, "default", sg.Description)
+-	th.AssertEquals(t, "85cc3048-abc3-43cc-89b3-377341426ac5", sg.ID)
+-	th.AssertEquals(t, "default", sg.Name)
+-	th.AssertEquals(t, 2, len(sg.Rules))
+-	th.AssertEquals(t, "e4f50856753b4dc6afee5fa6b9b6c550", sg.TenantID)
+-}
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"DisassociateAddress"})
--	c.Assert(req.Form["AssociationId"], DeepEquals, []string{"eipassoc-aa7486c3"})
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	th.Mux.HandleFunc("/v2.0/security-groups/4ec89087-d057-4e2c-911f-60a3b47ee304", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-
+-	res := Delete(fake.ServiceClient(), "4ec89087-d057-4e2c-911f-60a3b47ee304")
+-	th.AssertNoErr(t, res.Err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/groups/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/groups/results.go
+deleted file mode 100644
+index 49db261..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/groups/results.go
++++ /dev/null
+@@ -1,108 +0,0 @@
+-package groups
 -
--func (s *S) TestModifyInstance(c *C) {
--	testServer.Response(200, nil, ModifyInstanceExample)
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	options := ec2.ModifyInstance{
--		InstanceType:          "m1.small",
--		DisableAPITermination: true,
--		EbsOptimized:          true,
--		SecurityGroups:        []ec2.SecurityGroup{{Id: "g1"}, {Id: "g2"}},
--		ShutdownBehavior:      "terminate",
--		KernelId:              "kernel-id",
--		RamdiskId:             "ramdisk-id",
--		SourceDestCheck:       true,
--		SriovNetSupport:       true,
--		UserData:              []byte("1234"),
--		BlockDevices: []ec2.BlockDeviceMapping{
--			{DeviceName: "/dev/sda1", SnapshotId: "snap-a08912c9", DeleteOnTermination: true},
--		},
--	}
+-// SecGroup represents a container for security group rules.
+-type SecGroup struct {
+-	// The UUID for the security group.
+-	ID string
 -
--	resp, err := s.ec2.ModifyInstance("i-2ba64342", &options)
--	req := testServer.WaitRequest()
+-	// Human-readable name for the security group. Might not be unique. Cannot be
+-	// named "default" as that is automatically created for a tenant.
+-	Name string
 -
--	c.Assert(req.Form["Action"], DeepEquals, []string{"ModifyInstanceAttribute"})
--	c.Assert(req.Form["InstanceId"], DeepEquals, []string{"i-2ba64342"})
--	c.Assert(req.Form["InstanceType.Value"], DeepEquals, []string{"m1.small"})
--	c.Assert(req.Form["BlockDeviceMapping.1.DeviceName"], DeepEquals, []string{"/dev/sda1"})
--	c.Assert(req.Form["BlockDeviceMapping.1.Ebs.SnapshotId"], DeepEquals, []string{"snap-a08912c9"})
--	c.Assert(req.Form["BlockDeviceMapping.1.Ebs.DeleteOnTermination"], DeepEquals, []string{"true"})
--	c.Assert(req.Form["DisableApiTermination.Value"], DeepEquals, []string{"true"})
--	c.Assert(req.Form["EbsOptimized"], DeepEquals, []string{"true"})
--	c.Assert(req.Form["GroupId.1"], DeepEquals, []string{"g1"})
--	c.Assert(req.Form["GroupId.2"], DeepEquals, []string{"g2"})
--	c.Assert(req.Form["InstanceInitiatedShutdownBehavior.Value"], DeepEquals, []string{"terminate"})
--	c.Assert(req.Form["Kernel.Value"], DeepEquals, []string{"kernel-id"})
--	c.Assert(req.Form["Ramdisk.Value"], DeepEquals, []string{"ramdisk-id"})
--	c.Assert(req.Form["SourceDestCheck.Value"], DeepEquals, []string{"true"})
--	c.Assert(req.Form["SriovNetSupport.Value"], DeepEquals, []string{"simple"})
--	c.Assert(req.Form["UserData"], DeepEquals, []string{"MTIzNA=="})
+-	// The security group description.
+-	Description string
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-	// A slice of security group rules that dictate the permitted behaviour for
+-	// traffic entering and leaving the group.
+-	Rules []rules.SecGroupRule `json:"security_group_rules" mapstructure:"security_group_rules"`
+-
+-	// Owner of the security group. Only admin users can specify a TenantID
+-	// other than their own.
+-	TenantID string `json:"tenant_id" mapstructure:"tenant_id"`
 -}
 -
--func (s *S) TestCreateVpc(c *C) {
--	testServer.Response(200, nil, CreateVpcExample)
+-// SecGroupPage is the page returned by a pager when traversing over a
+-// collection of security groups.
+-type SecGroupPage struct {
+-	pagination.LinkedPageBase
+-}
 -
--	options := &ec2.CreateVpc{
--		CidrBlock: "foo",
+-// NextPageURL is invoked when a paginated collection of security groups has
+-// reached the end of a page and the pager seeks to traverse over a new one. In
+-// order to do this, it needs to construct the next page's URL.
+-func (p SecGroupPage) NextPageURL() (string, error) {
+-	type resp struct {
+-		Links []gophercloud.Link `mapstructure:"security_groups_links"`
 -	}
 -
--	resp, err := s.ec2.CreateVpc(options)
--
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["CidrBlock"], DeepEquals, []string{"foo"})
+-	var r resp
+-	err := mapstructure.Decode(p.Body, &r)
+-	if err != nil {
+-		return "", err
+-	}
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "7a62c49f-347e-4fc4-9331-6e8eEXAMPLE")
--	c.Assert(resp.VPC.VpcId, Equals, "vpc-1a2b3c4d")
--	c.Assert(resp.VPC.State, Equals, "pending")
--	c.Assert(resp.VPC.CidrBlock, Equals, "10.0.0.0/16")
--	c.Assert(resp.VPC.DHCPOptionsID, Equals, "dopt-1a2b3c4d2")
--	c.Assert(resp.VPC.InstanceTenancy, Equals, "default")
+-	return gophercloud.ExtractNextURL(r.Links)
 -}
 -
--func (s *S) TestDescribeVpcs(c *C) {
--	testServer.Response(200, nil, DescribeVpcsExample)
+-// IsEmpty checks whether a SecGroupPage struct is empty.
+-func (p SecGroupPage) IsEmpty() (bool, error) {
+-	is, err := ExtractGroups(p)
+-	if err != nil {
+-		return true, nil
+-	}
+-	return len(is) == 0, nil
+-}
 -
--	filter := ec2.NewFilter()
--	filter.Add("key1", "value1")
--	filter.Add("key2", "value2", "value3")
+-// ExtractGroups accepts a Page struct, specifically a SecGroupPage struct,
+-// and extracts the elements into a slice of SecGroup structs. In other words,
+-// a generic collection is mapped into a relevant slice.
+-func ExtractGroups(page pagination.Page) ([]SecGroup, error) {
+-	var resp struct {
+-		SecGroups []SecGroup `mapstructure:"security_groups" json:"security_groups"`
+-	}
 -
--	resp, err := s.ec2.DescribeVpcs([]string{"id1", "id2"}, filter)
+-	err := mapstructure.Decode(page.(SecGroupPage).Body, &resp)
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"DescribeVpcs"})
--	c.Assert(req.Form["VpcId.1"], DeepEquals, []string{"id1"})
--	c.Assert(req.Form["VpcId.2"], DeepEquals, []string{"id2"})
--	c.Assert(req.Form["Filter.1.Name"], DeepEquals, []string{"key1"})
--	c.Assert(req.Form["Filter.1.Value.1"], DeepEquals, []string{"value1"})
--	c.Assert(req.Form["Filter.1.Value.2"], IsNil)
--	c.Assert(req.Form["Filter.2.Name"], DeepEquals, []string{"key2"})
--	c.Assert(req.Form["Filter.2.Value.1"], DeepEquals, []string{"value2"})
--	c.Assert(req.Form["Filter.2.Value.2"], DeepEquals, []string{"value3"})
+-	return resp.SecGroups, err
+-}
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "7a62c49f-347e-4fc4-9331-6e8eEXAMPLE")
--	c.Assert(resp.VPCs, HasLen, 1)
+-type commonResult struct {
+-	gophercloud.Result
 -}
 -
--func (s *S) TestCreateSubnet(c *C) {
--	testServer.Response(200, nil, CreateSubnetExample)
+-// Extract is a function that accepts a result and extracts a security group.
+-func (r commonResult) Extract() (*SecGroup, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
+-	}
 -
--	options := &ec2.CreateSubnet{
--		AvailabilityZone: "baz",
--		CidrBlock:        "foo",
--		VpcId:            "bar",
+-	var res struct {
+-		SecGroup *SecGroup `mapstructure:"security_group" json:"security_group"`
 -	}
 -
--	resp, err := s.ec2.CreateSubnet(options)
+-	err := mapstructure.Decode(r.Body, &res)
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["VpcId"], DeepEquals, []string{"bar"})
--	c.Assert(req.Form["CidrBlock"], DeepEquals, []string{"foo"})
--	c.Assert(req.Form["AvailabilityZone"], DeepEquals, []string{"baz"})
+-	return res.SecGroup, err
+-}
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "7a62c49f-347e-4fc4-9331-6e8eEXAMPLE")
--	c.Assert(resp.Subnet.SubnetId, Equals, "subnet-9d4a7b6c")
--	c.Assert(resp.Subnet.State, Equals, "pending")
--	c.Assert(resp.Subnet.VpcId, Equals, "vpc-1a2b3c4d")
--	c.Assert(resp.Subnet.CidrBlock, Equals, "10.0.1.0/24")
--	c.Assert(resp.Subnet.AvailableIpAddressCount, Equals, 251)
+-// CreateResult represents the result of a create operation.
+-type CreateResult struct {
+-	commonResult
 -}
 -
--func (s *S) TestResetImageAttribute(c *C) {
--	testServer.Response(200, nil, ResetImageAttributeExample)
+-// GetResult represents the result of a get operation.
+-type GetResult struct {
+-	commonResult
+-}
 -
--	options := ec2.ResetImageAttribute{Attribute: "launchPermission"}
--	resp, err := s.ec2.ResetImageAttribute("i-2ba64342", &options)
+-// DeleteResult represents the result of a delete operation.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/groups/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/groups/urls.go
+deleted file mode 100644
+index 84f7324..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/groups/urls.go
++++ /dev/null
+@@ -1,13 +0,0 @@
+-package groups
 -
--	req := testServer.WaitRequest()
--	c.Assert(req.Form["Action"], DeepEquals, []string{"ResetImageAttribute"})
+-import "github.com/rackspace/gophercloud"
 -
--	c.Assert(err, IsNil)
--	c.Assert(resp.RequestId, Equals, "59dbff89-35bd-4eac-99ed-be587EXAMPLE")
+-const rootPath = "security-groups"
+-
+-func rootURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL(rootPath)
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2i_test.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2i_test.go
+-
+-func resourceURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL(rootPath, id)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules/requests.go
 deleted file mode 100644
-index 3773041..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2i_test.go
+index edaebe8..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules/requests.go
 +++ /dev/null
-@@ -1,203 +0,0 @@
--package ec2_test
+@@ -1,183 +0,0 @@
+-package rules
 -
 -import (
--	"crypto/rand"
 -	"fmt"
--	"github.com/mitchellh/goamz/aws"
--	"github.com/mitchellh/goamz/ec2"
--	"github.com/mitchellh/goamz/testutil"
--	. "github.com/motain/gocheck"
+-
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
 -)
 -
--// AmazonServer represents an Amazon EC2 server.
--type AmazonServer struct {
--	auth aws.Auth
+-// ListOpts allows the filtering and sorting of paginated collections through
+-// the API. Filtering is achieved by passing in struct field values that map to
+-// the security group attributes you want to see returned. SortKey allows you to
+-// sort by a particular network attribute. SortDir sets the direction, and is
+-// either `asc' or `desc'. Marker and Limit are used for pagination.
+-type ListOpts struct {
+-	Direction      string `q:"direction"`
+-	EtherType      string `q:"ethertype"`
+-	ID             string `q:"id"`
+-	PortRangeMax   int    `q:"port_range_max"`
+-	PortRangeMin   int    `q:"port_range_min"`
+-	Protocol       string `q:"protocol"`
+-	RemoteGroupID  string `q:"remote_group_id"`
+-	RemoteIPPrefix string `q:"remote_ip_prefix"`
+-	SecGroupID     string `q:"security_group_id"`
+-	TenantID       string `q:"tenant_id"`
+-	Limit          int    `q:"limit"`
+-	Marker         string `q:"marker"`
+-	SortKey        string `q:"sort_key"`
+-	SortDir        string `q:"sort_dir"`
+-}
+-
+-// List returns a Pager which allows you to iterate over a collection of
+-// security group rules. It accepts a ListOpts struct, which allows you to filter
+-// and sort the returned collection for greater efficiency.
+-func List(c *gophercloud.ServiceClient, opts ListOpts) pagination.Pager {
+-	q, err := gophercloud.BuildQueryString(&opts)
+-	if err != nil {
+-		return pagination.Pager{Err: err}
+-	}
+-	u := rootURL(c) + q.String()
+-	return pagination.NewPager(c, u, func(r pagination.PageResult) pagination.Page {
+-		return SecGroupRulePage{pagination.LinkedPageBase{PageResult: r}}
+-	})
 -}
 -
--func (s *AmazonServer) SetUp(c *C) {
--	auth, err := aws.EnvAuth()
--	if err != nil {
--		c.Fatal(err.Error())
--	}
--	s.auth = auth
--}
+-// Errors
+-var (
+-	errValidDirectionRequired = fmt.Errorf("A valid Direction is required")
+-	errValidEtherTypeRequired = fmt.Errorf("A valid EtherType is required")
+-	errSecGroupIDRequired     = fmt.Errorf("A valid SecGroupID is required")
+-	errValidProtocolRequired  = fmt.Errorf("A valid Protocol is required")
+-)
 -
--// Suite cost per run: 0.02 USD
--var _ = Suite(&AmazonClientSuite{})
+-// Constants useful for CreateOpts
+-const (
+-	DirIngress   = "ingress"
+-	DirEgress    = "egress"
+-	Ether4       = "IPv4"
+-	Ether6       = "IPv6"
+-	ProtocolTCP  = "tcp"
+-	ProtocolUDP  = "udp"
+-	ProtocolICMP = "icmp"
+-)
 -
--// AmazonClientSuite tests the client against a live EC2 server.
--type AmazonClientSuite struct {
--	srv AmazonServer
--	ClientTests
--}
+-// CreateOpts contains all the values needed to create a new security group rule.
+-type CreateOpts struct {
+-	// Required. Must be either "ingress" or "egress": the direction in which the
+-	// security group rule is applied.
+-	Direction string
+-
+-	// Required. Must be "IPv4" or "IPv6", and addresses represented in CIDR must
+-	// match the ingress or egress rules.
+-	EtherType string
+-
+-	// Required. The security group ID to associate with this security group rule.
+-	SecGroupID string
+-
+-	// Optional. The maximum port number in the range that is matched by the
+-	// security group rule. The PortRangeMin attribute constrains the PortRangeMax
+-	// attribute. If the protocol is ICMP, this value must be an ICMP type.
+-	PortRangeMax int
+-
+-	// Optional. The minimum port number in the range that is matched by the
+-	// security group rule. If the protocol is TCP or UDP, this value must be
+-	// less than or equal to the value of the PortRangeMax attribute. If the
+-	// protocol is ICMP, this value must be an ICMP type.
+-	PortRangeMin int
+-
+-	// Optional. The protocol that is matched by the security group rule. Valid
+-	// values are "tcp", "udp", "icmp" or an empty string.
+-	Protocol string
+-
+-	// Optional. The remote group ID to be associated with this security group
+-	// rule. You can specify either RemoteGroupID or RemoteIPPrefix.
+-	RemoteGroupID string
+-
+-	// Optional. The remote IP prefix to be associated with this security group
+-	// rule. You can specify either RemoteGroupID or RemoteIPPrefix. This
+-	// attribute matches the specified IP prefix as the source IP address of the
+-	// IP packet.
+-	RemoteIPPrefix string
+-}
+-
+-// Create is an operation which provisions a new security group with default
+-// security group rules for the IPv4 and IPv6 ether types.
+-func Create(c *gophercloud.ServiceClient, opts CreateOpts) CreateResult {
+-	var res CreateResult
+-
+-	// Validate required opts
+-	if opts.Direction != DirIngress && opts.Direction != DirEgress {
+-		res.Err = errValidDirectionRequired
+-		return res
+-	}
+-	if opts.EtherType != Ether4 && opts.EtherType != Ether6 {
+-		res.Err = errValidEtherTypeRequired
+-		return res
+-	}
+-	if opts.SecGroupID == "" {
+-		res.Err = errSecGroupIDRequired
+-		return res
+-	}
+-	if opts.Protocol != "" && opts.Protocol != ProtocolTCP && opts.Protocol != ProtocolUDP && opts.Protocol != ProtocolICMP {
+-		res.Err = errValidProtocolRequired
+-		return res
+-	}
+-
+-	type secrule struct {
+-		Direction      string `json:"direction"`
+-		EtherType      string `json:"ethertype"`
+-		SecGroupID     string `json:"security_group_id"`
+-		PortRangeMax   int    `json:"port_range_max,omitempty"`
+-		PortRangeMin   int    `json:"port_range_min,omitempty"`
+-		Protocol       string `json:"protocol,omitempty"`
+-		RemoteGroupID  string `json:"remote_group_id,omitempty"`
+-		RemoteIPPrefix string `json:"remote_ip_prefix,omitempty"`
+-	}
+-
+-	type request struct {
+-		SecRule secrule `json:"security_group_rule"`
+-	}
+-
+-	reqBody := request{SecRule: secrule{
+-		Direction:      opts.Direction,
+-		EtherType:      opts.EtherType,
+-		SecGroupID:     opts.SecGroupID,
+-		PortRangeMax:   opts.PortRangeMax,
+-		PortRangeMin:   opts.PortRangeMin,
+-		Protocol:       opts.Protocol,
+-		RemoteGroupID:  opts.RemoteGroupID,
+-		RemoteIPPrefix: opts.RemoteIPPrefix,
+-	}}
 -
--func (s *AmazonClientSuite) SetUpSuite(c *C) {
--	if !testutil.Amazon {
--		c.Skip("AmazonClientSuite tests not enabled")
--	}
--	s.srv.SetUp(c)
--	s.ec2 = ec2.NewWithClient(s.srv.auth, aws.USEast, testutil.DefaultClient)
+-	_, res.Err = perigee.Request("POST", rootURL(c), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{201},
+-	})
+-
+-	return res
 -}
 -
--// ClientTests defines integration tests designed to test the client.
--// It is not used as a test suite in itself, but embedded within
--// another type.
--type ClientTests struct {
--	ec2 *ec2.EC2
+-// Get retrieves a particular security group based on its unique ID.
+-func Get(c *gophercloud.ServiceClient, id string) GetResult {
+-	var res GetResult
+-	_, res.Err = perigee.Request("GET", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return res
 -}
 -
--var imageId = "ami-ccf405a5" // Ubuntu Maverick, i386, EBS store
+-// Delete will permanently delete a particular security group based on its unique ID.
+-func Delete(c *gophercloud.ServiceClient, id string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", resourceURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{204},
+-	})
+-	return res
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules/requests_test.go
+deleted file mode 100644
+index b5afef3..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules/requests_test.go
++++ /dev/null
+@@ -1,243 +0,0 @@
+-package rules
 -
--// Cost: 0.00 USD
--func (s *ClientTests) TestRunInstancesError(c *C) {
--	options := ec2.RunInstances{
--		ImageId:      "ami-a6f504cf", // Ubuntu Maverick, i386, instance store
--		InstanceType: "t1.micro",     // Doesn't work with micro, results in 400.
--	}
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--	resp, err := s.ec2.RunInstances(&options)
+-	fake "github.com/rackspace/gophercloud/openstack/networking/v2/common"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--	c.Assert(resp, IsNil)
--	c.Assert(err, ErrorMatches, "AMI.*root device.*not supported.*")
+-func TestURLs(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	ec2err, ok := err.(*ec2.Error)
--	c.Assert(ok, Equals, true)
--	c.Assert(ec2err.StatusCode, Equals, 400)
--	c.Assert(ec2err.Code, Equals, "UnsupportedOperation")
--	c.Assert(ec2err.Message, Matches, "AMI.*root device.*not supported.*")
--	c.Assert(ec2err.RequestId, Matches, ".+")
+-	th.AssertEquals(t, th.Endpoint()+"v2.0/security-group-rules", rootURL(fake.ServiceClient()))
+-	th.AssertEquals(t, th.Endpoint()+"v2.0/security-group-rules/foo", resourceURL(fake.ServiceClient(), "foo"))
 -}
 -
--// Cost: 0.02 USD
--func (s *ClientTests) TestRunAndTerminate(c *C) {
--	options := ec2.RunInstances{
--		ImageId:      imageId,
--		InstanceType: "t1.micro",
--	}
--	resp1, err := s.ec2.RunInstances(&options)
--	c.Assert(err, IsNil)
--	c.Check(resp1.ReservationId, Matches, "r-[0-9a-f]*")
--	c.Check(resp1.OwnerId, Matches, "[0-9]+")
--	c.Check(resp1.Instances, HasLen, 1)
--	c.Check(resp1.Instances[0].InstanceType, Equals, "t1.micro")
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	instId := resp1.Instances[0].InstanceId
+-	th.Mux.HandleFunc("/v2.0/security-group-rules", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--	resp2, err := s.ec2.Instances([]string{instId}, nil)
--	c.Assert(err, IsNil)
--	if c.Check(resp2.Reservations, HasLen, 1) && c.Check(len(resp2.Reservations[0].Instances), Equals, 1) {
--		inst := resp2.Reservations[0].Instances[0]
--		c.Check(inst.InstanceId, Equals, instId)
--	}
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--	resp3, err := s.ec2.TerminateInstances([]string{instId})
--	c.Assert(err, IsNil)
--	c.Check(resp3.StateChanges, HasLen, 1)
--	c.Check(resp3.StateChanges[0].InstanceId, Equals, instId)
--	c.Check(resp3.StateChanges[0].CurrentState.Name, Equals, "shutting-down")
--	c.Check(resp3.StateChanges[0].CurrentState.Code, Equals, 32)
+-		fmt.Fprintf(w, `
+-{
+-    "security_group_rules": [
+-        {
+-            "direction": "egress",
+-            "ethertype": "IPv6",
+-            "id": "3c0e45ff-adaf-4124-b083-bf390e5482ff",
+-            "port_range_max": null,
+-            "port_range_min": null,
+-            "protocol": null,
+-            "remote_group_id": null,
+-            "remote_ip_prefix": null,
+-            "security_group_id": "85cc3048-abc3-43cc-89b3-377341426ac5",
+-            "tenant_id": "e4f50856753b4dc6afee5fa6b9b6c550"
+-        },
+-        {
+-            "direction": "egress",
+-            "ethertype": "IPv4",
+-            "id": "93aa42e5-80db-4581-9391-3a608bd0e448",
+-            "port_range_max": null,
+-            "port_range_min": null,
+-            "protocol": null,
+-            "remote_group_id": null,
+-            "remote_ip_prefix": null,
+-            "security_group_id": "85cc3048-abc3-43cc-89b3-377341426ac5",
+-            "tenant_id": "e4f50856753b4dc6afee5fa6b9b6c550"
+-        }
+-    ]
 -}
+-      `)
+-	})
 -
--// Cost: 0.00 USD
--func (s *ClientTests) TestSecurityGroups(c *C) {
--	name := "goamz-test"
--	descr := "goamz security group for tests"
--
--	// Clean it up, if a previous test left it around and avoid leaving it around.
--	s.ec2.DeleteSecurityGroup(ec2.SecurityGroup{Name: name})
--	defer s.ec2.DeleteSecurityGroup(ec2.SecurityGroup{Name: name})
--
--	resp1, err := s.ec2.CreateSecurityGroup(ec2.SecurityGroup{Name: name, Description: descr})
--	c.Assert(err, IsNil)
--	c.Assert(resp1.RequestId, Matches, ".+")
--	c.Assert(resp1.Name, Equals, name)
--	c.Assert(resp1.Id, Matches, ".+")
+-	count := 0
 -
--	resp1, err = s.ec2.CreateSecurityGroup(ec2.SecurityGroup{Name: name, Description: descr})
--	ec2err, _ := err.(*ec2.Error)
--	c.Assert(resp1, IsNil)
--	c.Assert(ec2err, NotNil)
--	c.Assert(ec2err.Code, Equals, "InvalidGroup.Duplicate")
+-	List(fake.ServiceClient(), ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractRules(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract secrules: %v", err)
+-			return false, err
+-		}
 -
--	perms := []ec2.IPPerm{{
--		Protocol:  "tcp",
--		FromPort:  0,
--		ToPort:    1024,
--		SourceIPs: []string{"127.0.0.1/24"},
--	}}
+-		expected := []SecGroupRule{
+-			SecGroupRule{
+-				Direction:      "egress",
+-				EtherType:      "IPv6",
+-				ID:             "3c0e45ff-adaf-4124-b083-bf390e5482ff",
+-				PortRangeMax:   0,
+-				PortRangeMin:   0,
+-				Protocol:       "",
+-				RemoteGroupID:  "",
+-				RemoteIPPrefix: "",
+-				SecGroupID:     "85cc3048-abc3-43cc-89b3-377341426ac5",
+-				TenantID:       "e4f50856753b4dc6afee5fa6b9b6c550",
+-			},
+-			SecGroupRule{
+-				Direction:      "egress",
+-				EtherType:      "IPv4",
+-				ID:             "93aa42e5-80db-4581-9391-3a608bd0e448",
+-				PortRangeMax:   0,
+-				PortRangeMin:   0,
+-				Protocol:       "",
+-				RemoteGroupID:  "",
+-				RemoteIPPrefix: "",
+-				SecGroupID:     "85cc3048-abc3-43cc-89b3-377341426ac5",
+-				TenantID:       "e4f50856753b4dc6afee5fa6b9b6c550",
+-			},
+-		}
 -
--	resp2, err := s.ec2.AuthorizeSecurityGroup(ec2.SecurityGroup{Name: name}, perms)
--	c.Assert(err, IsNil)
--	c.Assert(resp2.RequestId, Matches, ".+")
+-		th.CheckDeepEquals(t, expected, actual)
 -
--	resp3, err := s.ec2.SecurityGroups(ec2.SecurityGroupNames(name), nil)
--	c.Assert(err, IsNil)
--	c.Assert(resp3.RequestId, Matches, ".+")
--	c.Assert(resp3.Groups, HasLen, 1)
+-		return true, nil
+-	})
 -
--	g0 := resp3.Groups[0]
--	c.Assert(g0.Name, Equals, name)
--	c.Assert(g0.Description, Equals, descr)
--	c.Assert(g0.IPPerms, HasLen, 1)
--	c.Assert(g0.IPPerms[0].Protocol, Equals, "tcp")
--	c.Assert(g0.IPPerms[0].FromPort, Equals, 0)
--	c.Assert(g0.IPPerms[0].ToPort, Equals, 1024)
--	c.Assert(g0.IPPerms[0].SourceIPs, DeepEquals, []string{"127.0.0.1/24"})
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
+-	}
+-}
 -
--	resp2, err = s.ec2.DeleteSecurityGroup(ec2.SecurityGroup{Name: name})
--	c.Assert(err, IsNil)
--	c.Assert(resp2.RequestId, Matches, ".+")
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/security-group-rules", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "security_group_rule": {
+-        "direction": "ingress",
+-        "port_range_min": 80,
+-        "ethertype": "IPv4",
+-        "port_range_max": 80,
+-        "protocol": "tcp",
+-        "remote_group_id": "85cc3048-abc3-43cc-89b3-377341426ac5",
+-        "security_group_id": "a7734e61-b545-452d-a3cd-0189cbd9747a"
+-    }
 -}
+-      `)
 -
--var sessionId = func() string {
--	buf := make([]byte, 8)
--	// if we have no randomness, we'll just make do, so ignore the error.
--	rand.Read(buf)
--	return fmt.Sprintf("%x", buf)
--}()
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
 -
--// sessionName reutrns a name that is probably
--// unique to this test session.
--func sessionName(prefix string) string {
--	return prefix + "-" + sessionId
+-		fmt.Fprintf(w, `
+-{
+-    "security_group_rule": {
+-        "direction": "ingress",
+-        "ethertype": "IPv4",
+-        "id": "2bc0accf-312e-429a-956e-e4407625eb62",
+-        "port_range_max": 80,
+-        "port_range_min": 80,
+-        "protocol": "tcp",
+-        "remote_group_id": "85cc3048-abc3-43cc-89b3-377341426ac5",
+-        "remote_ip_prefix": null,
+-        "security_group_id": "a7734e61-b545-452d-a3cd-0189cbd9747a",
+-        "tenant_id": "e4f50856753b4dc6afee5fa6b9b6c550"
+-    }
 -}
+-    `)
+-	})
 -
--var allRegions = []aws.Region{
--	aws.USEast,
--	aws.USWest,
--	aws.EUWest,
--	aws.APSoutheast,
--	aws.APNortheast,
+-	opts := CreateOpts{
+-		Direction:     "ingress",
+-		PortRangeMin:  80,
+-		EtherType:     "IPv4",
+-		PortRangeMax:  80,
+-		Protocol:      "tcp",
+-		RemoteGroupID: "85cc3048-abc3-43cc-89b3-377341426ac5",
+-		SecGroupID:    "a7734e61-b545-452d-a3cd-0189cbd9747a",
+-	}
+-	_, err := Create(fake.ServiceClient(), opts).Extract()
+-	th.AssertNoErr(t, err)
 -}
 -
--// Communicate with all EC2 endpoints to see if they are alive.
--func (s *ClientTests) TestRegions(c *C) {
--	name := sessionName("goamz-region-test")
--	perms := []ec2.IPPerm{{
--		Protocol:  "tcp",
--		FromPort:  80,
--		ToPort:    80,
--		SourceIPs: []string{"127.0.0.1/32"},
--	}}
--	errs := make(chan error, len(allRegions))
--	for _, region := range allRegions {
--		go func(r aws.Region) {
--			e := ec2.NewWithClient(s.ec2.Auth, r, testutil.DefaultClient)
--			_, err := e.AuthorizeSecurityGroup(ec2.SecurityGroup{Name: name}, perms)
--			errs <- err
--		}(region)
+-func TestRequiredCreateOpts(t *testing.T) {
+-	res := Create(fake.ServiceClient(), CreateOpts{Direction: "something"})
+-	if res.Err == nil {
+-		t.Fatalf("Expected error, got none")
 -	}
--	for _ = range allRegions {
--		err := <-errs
--		if err != nil {
--			ec2_err, ok := err.(*ec2.Error)
--			if ok {
--				c.Check(ec2_err.Code, Matches, "InvalidGroup.NotFound")
--			} else {
--				c.Errorf("Non-EC2 error: %s", err)
--			}
--		} else {
--			c.Errorf("Test should have errored but it seems to have succeeded")
--		}
+-	res = Create(fake.ServiceClient(), CreateOpts{Direction: DirIngress, EtherType: "something"})
+-	if res.Err == nil {
+-		t.Fatalf("Expected error, got none")
+-	}
+-	res = Create(fake.ServiceClient(), CreateOpts{Direction: DirIngress, EtherType: Ether4})
+-	if res.Err == nil {
+-		t.Fatalf("Expected error, got none")
+-	}
+-	res = Create(fake.ServiceClient(), CreateOpts{Direction: DirIngress, EtherType: Ether4, SecGroupID: "something", Protocol: "foo"})
+-	if res.Err == nil {
+-		t.Fatalf("Expected error, got none")
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2t_test.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2t_test.go
+-
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/security-group-rules/3c0e45ff-adaf-4124-b083-bf390e5482ff", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "security_group_rule": {
+-        "direction": "egress",
+-        "ethertype": "IPv6",
+-        "id": "3c0e45ff-adaf-4124-b083-bf390e5482ff",
+-        "port_range_max": null,
+-        "port_range_min": null,
+-        "protocol": null,
+-        "remote_group_id": null,
+-        "remote_ip_prefix": null,
+-        "security_group_id": "85cc3048-abc3-43cc-89b3-377341426ac5",
+-        "tenant_id": "e4f50856753b4dc6afee5fa6b9b6c550"
+-    }
+-}
+-      `)
+-	})
+-
+-	sr, err := Get(fake.ServiceClient(), "3c0e45ff-adaf-4124-b083-bf390e5482ff").Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, "egress", sr.Direction)
+-	th.AssertEquals(t, "IPv6", sr.EtherType)
+-	th.AssertEquals(t, "3c0e45ff-adaf-4124-b083-bf390e5482ff", sr.ID)
+-	th.AssertEquals(t, 0, sr.PortRangeMax)
+-	th.AssertEquals(t, 0, sr.PortRangeMin)
+-	th.AssertEquals(t, "", sr.Protocol)
+-	th.AssertEquals(t, "", sr.RemoteGroupID)
+-	th.AssertEquals(t, "", sr.RemoteIPPrefix)
+-	th.AssertEquals(t, "85cc3048-abc3-43cc-89b3-377341426ac5", sr.SecGroupID)
+-	th.AssertEquals(t, "e4f50856753b4dc6afee5fa6b9b6c550", sr.TenantID)
+-}
+-
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/security-group-rules/4ec89087-d057-4e2c-911f-60a3b47ee304", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-
+-	res := Delete(fake.ServiceClient(), "4ec89087-d057-4e2c-911f-60a3b47ee304")
+-	th.AssertNoErr(t, res.Err)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules/results.go
 deleted file mode 100644
-index fe50356..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2t_test.go
+index 6e13857..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules/results.go
 +++ /dev/null
-@@ -1,580 +0,0 @@
--package ec2_test
+@@ -1,133 +0,0 @@
+-package rules
 -
 -import (
--	"fmt"
--	"github.com/mitchellh/goamz/aws"
--	"github.com/mitchellh/goamz/ec2"
--	"github.com/mitchellh/goamz/ec2/ec2test"
--	"github.com/mitchellh/goamz/testutil"
--	. "github.com/motain/gocheck"
--	"regexp"
--	"sort"
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
 -)
 -
--// LocalServer represents a local ec2test fake server.
--type LocalServer struct {
--	auth   aws.Auth
--	region aws.Region
--	srv    *ec2test.Server
--}
+-// SecGroupRule represents a rule to dictate the behaviour of incoming or
+-// outgoing traffic for a particular security group.
+-type SecGroupRule struct {
+-	// The UUID for this security group rule.
+-	ID string
 -
--func (s *LocalServer) SetUp(c *C) {
--	srv, err := ec2test.NewServer()
--	c.Assert(err, IsNil)
--	c.Assert(srv, NotNil)
+-	// The direction in which the security group rule is applied. The only values
+-	// allowed are "ingress" or "egress". For a compute instance, an ingress
+-	// security group rule is applied to incoming (ingress) traffic for that
+-	// instance. An egress rule is applied to traffic leaving the instance.
+-	Direction string
 -
--	s.srv = srv
--	s.region = aws.Region{EC2Endpoint: srv.URL()}
--}
+-	// Must be IPv4 or IPv6, and addresses represented in CIDR must match the
+-	// ingress or egress rules.
+-	EtherType string `json:"ethertype" mapstructure:"ethertype"`
 -
--// LocalServerSuite defines tests that will run
--// against the local ec2test server. It includes
--// selected tests from ClientTests;
--// when the ec2test functionality is sufficient, it should
--// include all of them, and ClientTests can be simply embedded.
--type LocalServerSuite struct {
--	srv LocalServer
--	ServerTests
--	clientTests ClientTests
--}
+-	// The security group ID to associate with this security group rule.
+-	SecGroupID string `json:"security_group_id" mapstructure:"security_group_id"`
 -
--var _ = Suite(&LocalServerSuite{})
+-	// The minimum port number in the range that is matched by the security group
+-	// rule. If the protocol is TCP or UDP, this value must be less than or equal
+-	// to the value of the PortRangeMax attribute. If the protocol is ICMP, this
+-	// value must be an ICMP type.
+-	PortRangeMin int `json:"port_range_min" mapstructure:"port_range_min"`
 -
--func (s *LocalServerSuite) SetUpSuite(c *C) {
--	s.srv.SetUp(c)
--	s.ServerTests.ec2 = ec2.NewWithClient(s.srv.auth, s.srv.region, testutil.DefaultClient)
--	s.clientTests.ec2 = ec2.NewWithClient(s.srv.auth, s.srv.region, testutil.DefaultClient)
+-	// The maximum port number in the range that is matched by the security group
+-	// rule. The PortRangeMin attribute constrains the PortRangeMax attribute. If
+-	// the protocol is ICMP, this value must be an ICMP type.
+-	PortRangeMax int `json:"port_range_max" mapstructure:"port_range_max"`
+-
+-	// The protocol that is matched by the security group rule. Valid values are
+-	// "tcp", "udp", "icmp" or an empty string.
+-	Protocol string
+-
+-	// The remote group ID to be associated with this security group rule. You
+-	// can specify either RemoteGroupID or RemoteIPPrefix.
+-	RemoteGroupID string `json:"remote_group_id" mapstructure:"remote_group_id"`
+-
+-	// The remote IP prefix to be associated with this security group rule. You
+-	// can specify either RemoteGroupID or RemoteIPPrefix . This attribute
+-	// matches the specified IP prefix as the source IP address of the IP packet.
+-	RemoteIPPrefix string `json:"remote_ip_prefix" mapstructure:"remote_ip_prefix"`
+-
+-	// The owner of this security group rule.
+-	TenantID string `json:"tenant_id" mapstructure:"tenant_id"`
 -}
 -
--func (s *LocalServerSuite) TestRunAndTerminate(c *C) {
--	s.clientTests.TestRunAndTerminate(c)
+-// SecGroupRulePage is the page returned by a pager when traversing over a
+-// collection of security group rules.
+-type SecGroupRulePage struct {
+-	pagination.LinkedPageBase
 -}
 -
--func (s *LocalServerSuite) TestSecurityGroups(c *C) {
--	s.clientTests.TestSecurityGroups(c)
+-// NextPageURL is invoked when a paginated collection of security group rules has
+-// reached the end of a page and the pager seeks to traverse over a new one. In
+-// order to do this, it needs to construct the next page's URL.
+-func (p SecGroupRulePage) NextPageURL() (string, error) {
+-	type resp struct {
+-		Links []gophercloud.Link `mapstructure:"security_group_rules_links"`
+-	}
+-
+-	var r resp
+-	err := mapstructure.Decode(p.Body, &r)
+-	if err != nil {
+-		return "", err
+-	}
+-
+-	return gophercloud.ExtractNextURL(r.Links)
 -}
 -
--// TestUserData is not defined on ServerTests because it
--// requires the ec2test server to function.
--func (s *LocalServerSuite) TestUserData(c *C) {
--	data := make([]byte, 256)
--	for i := range data {
--		data[i] = byte(i)
+-// IsEmpty checks whether a SecGroupRulePage struct is empty.
+-func (p SecGroupRulePage) IsEmpty() (bool, error) {
+-	is, err := ExtractRules(p)
+-	if err != nil {
+-		return true, nil
 -	}
--	inst, err := s.ec2.RunInstances(&ec2.RunInstances{
--		ImageId:      imageId,
--		InstanceType: "t1.micro",
--		UserData:     data,
--	})
--	c.Assert(err, IsNil)
--	c.Assert(inst, NotNil)
--	c.Assert(inst.Instances[0].DNSName, Equals, inst.Instances[0].InstanceId+".example.com")
+-	return len(is) == 0, nil
+-}
 -
--	id := inst.Instances[0].InstanceId
+-// ExtractRules accepts a Page struct, specifically a SecGroupRulePage struct,
+-// and extracts the elements into a slice of SecGroupRule structs. In other words,
+-// a generic collection is mapped into a relevant slice.
+-func ExtractRules(page pagination.Page) ([]SecGroupRule, error) {
+-	var resp struct {
+-		SecGroupRules []SecGroupRule `mapstructure:"security_group_rules" json:"security_group_rules"`
+-	}
 -
--	defer s.ec2.TerminateInstances([]string{id})
+-	err := mapstructure.Decode(page.(SecGroupRulePage).Body, &resp)
 -
--	tinst := s.srv.srv.Instance(id)
--	c.Assert(tinst, NotNil)
--	c.Assert(tinst.UserData, DeepEquals, data)
+-	return resp.SecGroupRules, err
 -}
 -
--// AmazonServerSuite runs the ec2test server tests against a live EC2 server.
--// It will only be activated if the -all flag is specified.
--type AmazonServerSuite struct {
--	srv AmazonServer
--	ServerTests
+-type commonResult struct {
+-	gophercloud.Result
 -}
 -
--var _ = Suite(&AmazonServerSuite{})
+-// Extract is a function that accepts a result and extracts a security rule.
+-func (r commonResult) Extract() (*SecGroupRule, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
+-	}
 -
--func (s *AmazonServerSuite) SetUpSuite(c *C) {
--	if !testutil.Amazon {
--		c.Skip("AmazonServerSuite tests not enabled")
+-	var res struct {
+-		SecGroupRule *SecGroupRule `mapstructure:"security_group_rule" json:"security_group_rule"`
 -	}
--	s.srv.SetUp(c)
--	s.ServerTests.ec2 = ec2.NewWithClient(s.srv.auth, aws.USEast, testutil.DefaultClient)
--}
 -
--// ServerTests defines a set of tests designed to test
--// the ec2test local fake ec2 server.
--// It is not used as a test suite in itself, but embedded within
--// another type.
--type ServerTests struct {
--	ec2 *ec2.EC2
+-	err := mapstructure.Decode(r.Body, &res)
+-
+-	return res.SecGroupRule, err
 -}
 -
--func terminateInstances(c *C, e *ec2.EC2, insts []*ec2.Instance) {
--	var ids []string
--	for _, inst := range insts {
--		if inst != nil {
--			ids = append(ids, inst.InstanceId)
--		}
--	}
--	_, err := e.TerminateInstances(ids)
--	c.Check(err, IsNil, Commentf("%d INSTANCES LEFT RUNNING!!!", len(ids)))
+-// CreateResult represents the result of a create operation.
+-type CreateResult struct {
+-	commonResult
 -}
 -
--func (s *ServerTests) makeTestGroup(c *C, name, descr string) ec2.SecurityGroup {
--	// Clean it up if a previous test left it around.
--	_, err := s.ec2.DeleteSecurityGroup(ec2.SecurityGroup{Name: name})
--	if err != nil && err.(*ec2.Error).Code != "InvalidGroup.NotFound" {
--		c.Fatalf("delete security group: %v", err)
--	}
+-// GetResult represents the result of a get operation.
+-type GetResult struct {
+-	commonResult
+-}
 -
--	resp, err := s.ec2.CreateSecurityGroup(ec2.SecurityGroup{Name: name, Description: descr})
--	c.Assert(err, IsNil)
--	c.Assert(resp.Name, Equals, name)
--	return resp.SecurityGroup
+-// DeleteResult represents the result of a delete operation.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules/urls.go
+deleted file mode 100644
+index 8e2b2bb..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/extensions/security/rules/urls.go
++++ /dev/null
+@@ -1,13 +0,0 @@
+-package rules
 -
--func (s *ServerTests) TestIPPerms(c *C) {
--	g0 := s.makeTestGroup(c, "goamz-test0", "ec2test group 0")
--	defer s.ec2.DeleteSecurityGroup(g0)
+-import "github.com/rackspace/gophercloud"
 -
--	g1 := s.makeTestGroup(c, "goamz-test1", "ec2test group 1")
--	defer s.ec2.DeleteSecurityGroup(g1)
+-const rootPath = "security-group-rules"
 -
--	resp, err := s.ec2.SecurityGroups([]ec2.SecurityGroup{g0, g1}, nil)
--	c.Assert(err, IsNil)
--	c.Assert(resp.Groups, HasLen, 2)
--	c.Assert(resp.Groups[0].IPPerms, HasLen, 0)
--	c.Assert(resp.Groups[1].IPPerms, HasLen, 0)
+-func rootURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL(rootPath)
+-}
 -
--	ownerId := resp.Groups[0].OwnerId
+-func resourceURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL(rootPath, id)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/doc.go
+deleted file mode 100644
+index c87a7ce..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/doc.go
++++ /dev/null
+@@ -1,9 +0,0 @@
+-// Package networks contains functionality for working with Neutron network
+-// resources. A network is an isolated virtual layer-2 broadcast domain that is
+-// typically reserved for the tenant who created it (unless you configure the
+-// network to be shared). Tenants can create multiple networks until the
+-// thresholds per-tenant quota is reached.
+-//
+-// In the v2.0 Networking API, the network is the main entity. Ports and subnets
+-// are always associated with a network.
+-package networks
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/errors.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/errors.go
+deleted file mode 100644
+index 83c4a6a..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/errors.go
++++ /dev/null
+@@ -1 +0,0 @@
+-package networks
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/requests.go
+deleted file mode 100644
+index eaa7136..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/requests.go
++++ /dev/null
+@@ -1,209 +0,0 @@
+-package networks
 -
--	// test some invalid parameters
--	// TODO more
--	_, err = s.ec2.AuthorizeSecurityGroup(g0, []ec2.IPPerm{{
--		Protocol:  "tcp",
--		FromPort:  0,
--		ToPort:    1024,
--		SourceIPs: []string{"z127.0.0.1/24"},
--	}})
--	c.Assert(err, NotNil)
--	c.Check(err.(*ec2.Error).Code, Equals, "InvalidPermission.Malformed")
+-import (
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
 -
--	// Check that AuthorizeSecurityGroup adds the correct authorizations.
--	_, err = s.ec2.AuthorizeSecurityGroup(g0, []ec2.IPPerm{{
--		Protocol:  "tcp",
--		FromPort:  2000,
--		ToPort:    2001,
--		SourceIPs: []string{"127.0.0.0/24"},
--		SourceGroups: []ec2.UserSecurityGroup{{
--			Name: g1.Name,
--		}, {
--			Id: g0.Id,
--		}},
--	}, {
--		Protocol:  "tcp",
--		FromPort:  2000,
--		ToPort:    2001,
--		SourceIPs: []string{"200.1.1.34/32"},
--	}})
--	c.Assert(err, IsNil)
+-	"github.com/racker/perigee"
+-)
 -
--	resp, err = s.ec2.SecurityGroups([]ec2.SecurityGroup{g0}, nil)
--	c.Assert(err, IsNil)
--	c.Assert(resp.Groups, HasLen, 1)
--	c.Assert(resp.Groups[0].IPPerms, HasLen, 1)
+-// AdminState gives users a solid type to work with for create and update
+-// operations. It is recommended that users use the `Up` and `Down` enums.
+-type AdminState *bool
 -
--	perm := resp.Groups[0].IPPerms[0]
--	srcg := perm.SourceGroups
--	c.Assert(srcg, HasLen, 2)
+-// Convenience vars for AdminStateUp values.
+-var (
+-	iTrue  = true
+-	iFalse = false
 -
--	// Normalize so we don't care about returned order.
--	if srcg[0].Name == g1.Name {
--		srcg[0], srcg[1] = srcg[1], srcg[0]
+-	Up   AdminState = &iTrue
+-	Down AdminState = &iFalse
+-)
+-
+-type networkOpts struct {
+-	AdminStateUp *bool
+-	Name         string
+-	Shared       *bool
+-	TenantID     string
+-}
+-
+-// ListOptsBuilder allows extensions to add additional parameters to the
+-// List request.
+-type ListOptsBuilder interface {
+-	ToNetworkListQuery() (string, error)
+-}
+-
+-// ListOpts allows the filtering and sorting of paginated collections through
+-// the API. Filtering is achieved by passing in struct field values that map to
+-// the network attributes you want to see returned. SortKey allows you to sort
+-// by a particular network attribute. SortDir sets the direction, and is either
+-// `asc' or `desc'. Marker and Limit are used for pagination.
+-type ListOpts struct {
+-	Status       string `q:"status"`
+-	Name         string `q:"name"`
+-	AdminStateUp *bool  `q:"admin_state_up"`
+-	TenantID     string `q:"tenant_id"`
+-	Shared       *bool  `q:"shared"`
+-	ID           string `q:"id"`
+-	Marker       string `q:"marker"`
+-	Limit        int    `q:"limit"`
+-	SortKey      string `q:"sort_key"`
+-	SortDir      string `q:"sort_dir"`
+-}
+-
+-// ToNetworkListQuery formats a ListOpts into a query string.
+-func (opts ListOpts) ToNetworkListQuery() (string, error) {
+-	q, err := gophercloud.BuildQueryString(opts)
+-	if err != nil {
+-		return "", err
 -	}
--	c.Check(srcg[0].Name, Equals, g0.Name)
--	c.Check(srcg[0].Id, Equals, g0.Id)
--	c.Check(srcg[0].OwnerId, Equals, ownerId)
--	c.Check(srcg[1].Name, Equals, g1.Name)
--	c.Check(srcg[1].Id, Equals, g1.Id)
--	c.Check(srcg[1].OwnerId, Equals, ownerId)
+-	return q.String(), nil
+-}
 -
--	sort.Strings(perm.SourceIPs)
--	c.Check(perm.SourceIPs, DeepEquals, []string{"127.0.0.0/24", "200.1.1.34/32"})
+-// List returns a Pager which allows you to iterate over a collection of
+-// networks. It accepts a ListOpts struct, which allows you to filter and sort
+-// the returned collection for greater efficiency.
+-func List(c *gophercloud.ServiceClient, opts ListOptsBuilder) pagination.Pager {
+-	url := listURL(c)
+-	if opts != nil {
+-		query, err := opts.ToNetworkListQuery()
+-		if err != nil {
+-			return pagination.Pager{Err: err}
+-		}
+-		url += query
+-	}
 -
--	// Check that we can't delete g1 (because g0 is using it)
--	_, err = s.ec2.DeleteSecurityGroup(g1)
--	c.Assert(err, NotNil)
--	c.Check(err.(*ec2.Error).Code, Equals, "InvalidGroup.InUse")
+-	return pagination.NewPager(c, url, func(r pagination.PageResult) pagination.Page {
+-		return NetworkPage{pagination.LinkedPageBase{PageResult: r}}
+-	})
+-}
 -
--	_, err = s.ec2.RevokeSecurityGroup(g0, []ec2.IPPerm{{
--		Protocol:     "tcp",
--		FromPort:     2000,
--		ToPort:       2001,
--		SourceGroups: []ec2.UserSecurityGroup{{Id: g1.Id}},
--	}, {
--		Protocol:  "tcp",
--		FromPort:  2000,
--		ToPort:    2001,
--		SourceIPs: []string{"200.1.1.34/32"},
--	}})
--	c.Assert(err, IsNil)
+-// Get retrieves a specific network based on its unique ID.
+-func Get(c *gophercloud.ServiceClient, id string) GetResult {
+-	var res GetResult
+-	_, res.Err = perigee.Request("GET", getURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return res
+-}
 -
--	resp, err = s.ec2.SecurityGroups([]ec2.SecurityGroup{g0}, nil)
--	c.Assert(err, IsNil)
--	c.Assert(resp.Groups, HasLen, 1)
--	c.Assert(resp.Groups[0].IPPerms, HasLen, 1)
+-// CreateOptsBuilder is the interface options structs have to satisfy in order
+-// to be used in the main Create operation in this package. Since many
+-// extensions decorate or modify the common logic, it is useful for them to
+-// satisfy a basic interface in order for them to be used.
+-type CreateOptsBuilder interface {
+-	ToNetworkCreateMap() (map[string]interface{}, error)
+-}
+-
+-// CreateOpts is the common options struct used in this package's Create
+-// operation.
+-type CreateOpts networkOpts
+-
+-// ToNetworkCreateMap casts a CreateOpts struct to a map.
+-func (opts CreateOpts) ToNetworkCreateMap() (map[string]interface{}, error) {
+-	n := make(map[string]interface{})
+-
+-	if opts.AdminStateUp != nil {
+-		n["admin_state_up"] = &opts.AdminStateUp
+-	}
+-	if opts.Name != "" {
+-		n["name"] = opts.Name
+-	}
+-	if opts.Shared != nil {
+-		n["shared"] = &opts.Shared
+-	}
+-	if opts.TenantID != "" {
+-		n["tenant_id"] = opts.TenantID
+-	}
 -
--	perm = resp.Groups[0].IPPerms[0]
--	srcg = perm.SourceGroups
--	c.Assert(srcg, HasLen, 1)
--	c.Check(srcg[0].Name, Equals, g0.Name)
--	c.Check(srcg[0].Id, Equals, g0.Id)
--	c.Check(srcg[0].OwnerId, Equals, ownerId)
+-	return map[string]interface{}{"network": n}, nil
+-}
 -
--	c.Check(perm.SourceIPs, DeepEquals, []string{"127.0.0.0/24"})
+-// Create accepts a CreateOpts struct and creates a new network using the values
+-// provided. This operation does not actually require a request body, i.e. the
+-// CreateOpts struct argument can be empty.
+-//
+-// The tenant ID that is contained in the URI is the tenant that creates the
+-// network. An admin user, however, has the option of specifying another tenant
+-// ID in the CreateOpts struct.
+-func Create(c *gophercloud.ServiceClient, opts CreateOptsBuilder) CreateResult {
+-	var res CreateResult
 -
--	// We should be able to delete g1 now because we've removed its only use.
--	_, err = s.ec2.DeleteSecurityGroup(g1)
--	c.Assert(err, IsNil)
+-	reqBody, err := opts.ToNetworkCreateMap()
+-	if err != nil {
+-		res.Err = err
+-		return res
+-	}
 -
--	_, err = s.ec2.DeleteSecurityGroup(g0)
--	c.Assert(err, IsNil)
+-	// Send request to API
+-	_, res.Err = perigee.Request("POST", createURL(c), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{201},
+-	})
+-	return res
+-}
 -
--	f := ec2.NewFilter()
--	f.Add("group-id", g0.Id, g1.Id)
--	resp, err = s.ec2.SecurityGroups(nil, f)
--	c.Assert(err, IsNil)
--	c.Assert(resp.Groups, HasLen, 0)
+-// UpdateOptsBuilder is the interface options structs have to satisfy in order
+-// to be used in the main Update operation in this package. Since many
+-// extensions decorate or modify the common logic, it is useful for them to
+-// satisfy a basic interface in order for them to be used.
+-type UpdateOptsBuilder interface {
+-	ToNetworkUpdateMap() (map[string]interface{}, error)
 -}
 -
--func (s *ServerTests) TestDuplicateIPPerm(c *C) {
--	name := "goamz-test"
--	descr := "goamz security group for tests"
+-// UpdateOpts is the common options struct used in this package's Update
+-// operation.
+-type UpdateOpts networkOpts
 -
--	// Clean it up, if a previous test left it around and avoid leaving it around.
--	s.ec2.DeleteSecurityGroup(ec2.SecurityGroup{Name: name})
--	defer s.ec2.DeleteSecurityGroup(ec2.SecurityGroup{Name: name})
+-// ToNetworkUpdateMap casts a UpdateOpts struct to a map.
+-func (opts UpdateOpts) ToNetworkUpdateMap() (map[string]interface{}, error) {
+-	n := make(map[string]interface{})
 -
--	resp1, err := s.ec2.CreateSecurityGroup(ec2.SecurityGroup{Name: name, Description: descr})
--	c.Assert(err, IsNil)
--	c.Assert(resp1.Name, Equals, name)
+-	if opts.AdminStateUp != nil {
+-		n["admin_state_up"] = &opts.AdminStateUp
+-	}
+-	if opts.Name != "" {
+-		n["name"] = opts.Name
+-	}
+-	if opts.Shared != nil {
+-		n["shared"] = &opts.Shared
+-	}
 -
--	perms := []ec2.IPPerm{{
--		Protocol:  "tcp",
--		FromPort:  200,
--		ToPort:    1024,
--		SourceIPs: []string{"127.0.0.1/24"},
--	}, {
--		Protocol:  "tcp",
--		FromPort:  0,
--		ToPort:    100,
--		SourceIPs: []string{"127.0.0.1/24"},
--	}}
+-	return map[string]interface{}{"network": n}, nil
+-}
 -
--	_, err = s.ec2.AuthorizeSecurityGroup(ec2.SecurityGroup{Name: name}, perms[0:1])
--	c.Assert(err, IsNil)
+-// Update accepts a UpdateOpts struct and updates an existing network using the
+-// values provided. For more information, see the Create function.
+-func Update(c *gophercloud.ServiceClient, networkID string, opts UpdateOptsBuilder) UpdateResult {
+-	var res UpdateResult
 -
--	_, err = s.ec2.AuthorizeSecurityGroup(ec2.SecurityGroup{Name: name}, perms[0:2])
--	c.Assert(err, ErrorMatches, `.*\(InvalidPermission.Duplicate\)`)
+-	reqBody, err := opts.ToNetworkUpdateMap()
+-	if err != nil {
+-		res.Err = err
+-		return res
+-	}
+-
+-	// Send request to API
+-	_, res.Err = perigee.Request("PUT", getURL(c, networkID), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{200, 201},
+-	})
+-
+-	return res
 -}
 -
--type filterSpec struct {
--	name   string
--	values []string
+-// Delete accepts a unique ID and deletes the network associated with it.
+-func Delete(c *gophercloud.ServiceClient, networkID string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", deleteURL(c, networkID), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{204},
+-	})
+-	return res
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/requests_test.go
+deleted file mode 100644
+index a263b7b..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/requests_test.go
++++ /dev/null
+@@ -1,275 +0,0 @@
+-package networks
 -
--func (s *ServerTests) TestInstanceFiltering(c *C) {
--	groupResp, err := s.ec2.CreateSecurityGroup(ec2.SecurityGroup{Name: sessionName("testgroup1"), Description: "testgroup one description"})
--	c.Assert(err, IsNil)
--	group1 := groupResp.SecurityGroup
--	defer s.ec2.DeleteSecurityGroup(group1)
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--	groupResp, err = s.ec2.CreateSecurityGroup(ec2.SecurityGroup{Name: sessionName("testgroup2"), Description: "testgroup two description"})
--	c.Assert(err, IsNil)
--	group2 := groupResp.SecurityGroup
--	defer s.ec2.DeleteSecurityGroup(group2)
+-	fake "github.com/rackspace/gophercloud/openstack/networking/v2/common"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--	insts := make([]*ec2.Instance, 3)
--	inst, err := s.ec2.RunInstances(&ec2.RunInstances{
--		MinCount:       2,
--		ImageId:        imageId,
--		InstanceType:   "t1.micro",
--		SecurityGroups: []ec2.SecurityGroup{group1},
--	})
--	c.Assert(err, IsNil)
--	insts[0] = &inst.Instances[0]
--	insts[1] = &inst.Instances[1]
--	defer terminateInstances(c, s.ec2, insts)
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	imageId2 := "ami-e358958a" // Natty server, i386, EBS store
--	inst, err = s.ec2.RunInstances(&ec2.RunInstances{
--		ImageId:        imageId2,
--		InstanceType:   "t1.micro",
--		SecurityGroups: []ec2.SecurityGroup{group2},
+-	th.Mux.HandleFunc("/v2.0/networks", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "networks": [
+-        {
+-            "status": "ACTIVE",
+-            "subnets": [
+-                "54d6f61d-db07-451c-9ab3-b9609b6b6f0b"
+-            ],
+-            "name": "private-network",
+-            "admin_state_up": true,
+-            "tenant_id": "4fd44f30292945e481c7b8a0c8908869",
+-            "shared": true,
+-            "id": "d32019d3-bc6e-4319-9c1d-6722fc136a22"
+-        },
+-        {
+-            "status": "ACTIVE",
+-            "subnets": [
+-                "08eae331-0402-425a-923c-34f7cfe39c1b"
+-            ],
+-            "name": "private",
+-            "admin_state_up": true,
+-            "tenant_id": "26a7980765d0414dbc1fc1f88cdb7e6e",
+-            "shared": true,
+-            "id": "db193ab3-96e3-4cb3-8fc5-05f4296d0324"
+-        }
+-    ]
+-}
+-			`)
 -	})
--	c.Assert(err, IsNil)
--	insts[2] = &inst.Instances[0]
 -
--	ids := func(indices ...int) (instIds []string) {
--		for _, index := range indices {
--			instIds = append(instIds, insts[index].InstanceId)
+-	client := fake.ServiceClient()
+-	count := 0
+-
+-	List(client, ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractNetworks(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract networks: %v", err)
+-			return false, err
 -		}
--		return
--	}
 -
--	tests := []struct {
--		about       string
--		instanceIds []string     // instanceIds argument to Instances method.
--		filters     []filterSpec // filters argument to Instances method.
--		resultIds   []string     // set of instance ids of expected results.
--		allowExtra  bool         // resultIds may be incomplete.
--		err         string       // expected error.
--	}{
--		{
--			about:      "check that Instances returns all instances",
--			resultIds:  ids(0, 1, 2),
--			allowExtra: true,
--		}, {
--			about:       "check that specifying two instance ids returns them",
--			instanceIds: ids(0, 2),
--			resultIds:   ids(0, 2),
--		}, {
--			about:       "check that specifying a non-existent instance id gives an error",
--			instanceIds: append(ids(0), "i-deadbeef"),
--			err:         `.*\(InvalidInstanceID\.NotFound\)`,
--		}, {
--			about: "check that a filter allowed both instances returns both of them",
--			filters: []filterSpec{
--				{"instance-id", ids(0, 2)},
--			},
--			resultIds: ids(0, 2),
--		}, {
--			about: "check that a filter allowing only one instance returns it",
--			filters: []filterSpec{
--				{"instance-id", ids(1)},
--			},
--			resultIds: ids(1),
--		}, {
--			about: "check that a filter allowing no instances returns none",
--			filters: []filterSpec{
--				{"instance-id", []string{"i-deadbeef12345"}},
--			},
--		}, {
--			about: "check that filtering on group id works",
--			filters: []filterSpec{
--				{"group-id", []string{group1.Id}},
--			},
--			resultIds: ids(0, 1),
--		}, {
--			about: "check that filtering on group name works",
--			filters: []filterSpec{
--				{"group-name", []string{group1.Name}},
--			},
--			resultIds: ids(0, 1),
--		}, {
--			about: "check that filtering on image id works",
--			filters: []filterSpec{
--				{"image-id", []string{imageId}},
--			},
--			resultIds:  ids(0, 1),
--			allowExtra: true,
--		}, {
--			about: "combination filters 1",
--			filters: []filterSpec{
--				{"image-id", []string{imageId, imageId2}},
--				{"group-name", []string{group1.Name}},
+-		expected := []Network{
+-			Network{
+-				Status:       "ACTIVE",
+-				Subnets:      []string{"54d6f61d-db07-451c-9ab3-b9609b6b6f0b"},
+-				Name:         "private-network",
+-				AdminStateUp: true,
+-				TenantID:     "4fd44f30292945e481c7b8a0c8908869",
+-				Shared:       true,
+-				ID:           "d32019d3-bc6e-4319-9c1d-6722fc136a22",
 -			},
--			resultIds: ids(0, 1),
--		}, {
--			about: "combination filters 2",
--			filters: []filterSpec{
--				{"image-id", []string{imageId2}},
--				{"group-name", []string{group1.Name}},
+-			Network{
+-				Status:       "ACTIVE",
+-				Subnets:      []string{"08eae331-0402-425a-923c-34f7cfe39c1b"},
+-				Name:         "private",
+-				AdminStateUp: true,
+-				TenantID:     "26a7980765d0414dbc1fc1f88cdb7e6e",
+-				Shared:       true,
+-				ID:           "db193ab3-96e3-4cb3-8fc5-05f4296d0324",
 -			},
--		},
--	}
--	for i, t := range tests {
--		c.Logf("%d. %s", i, t.about)
--		var f *ec2.Filter
--		if t.filters != nil {
--			f = ec2.NewFilter()
--			for _, spec := range t.filters {
--				f.Add(spec.name, spec.values...)
--			}
--		}
--		resp, err := s.ec2.Instances(t.instanceIds, f)
--		if t.err != "" {
--			c.Check(err, ErrorMatches, t.err)
--			continue
--		}
--		c.Assert(err, IsNil)
--		insts := make(map[string]*ec2.Instance)
--		for _, r := range resp.Reservations {
--			for j := range r.Instances {
--				inst := &r.Instances[j]
--				c.Check(insts[inst.InstanceId], IsNil, Commentf("duplicate instance id: %q", inst.InstanceId))
--				insts[inst.InstanceId] = inst
--			}
--		}
--		if !t.allowExtra {
--			c.Check(insts, HasLen, len(t.resultIds), Commentf("expected %d instances got %#v", len(t.resultIds), insts))
--		}
--		for j, id := range t.resultIds {
--			c.Check(insts[id], NotNil, Commentf("instance id %d (%q) not found; got %#v", j, id, insts))
 -		}
+-
+-		th.CheckDeepEquals(t, expected, actual)
+-
+-		return true, nil
+-	})
+-
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
 -	}
 -}
 -
--func idsOnly(gs []ec2.SecurityGroup) []ec2.SecurityGroup {
--	for i := range gs {
--		gs[i].Name = ""
--	}
--	return gs
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/networks/d32019d3-bc6e-4319-9c1d-6722fc136a22", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "network": {
+-        "status": "ACTIVE",
+-        "subnets": [
+-            "54d6f61d-db07-451c-9ab3-b9609b6b6f0b"
+-        ],
+-        "name": "private-network",
+-        "admin_state_up": true,
+-        "tenant_id": "4fd44f30292945e481c7b8a0c8908869",
+-        "shared": true,
+-        "id": "d32019d3-bc6e-4319-9c1d-6722fc136a22"
+-    }
 -}
+-			`)
+-	})
 -
--func namesOnly(gs []ec2.SecurityGroup) []ec2.SecurityGroup {
--	for i := range gs {
--		gs[i].Id = ""
--	}
--	return gs
+-	n, err := Get(fake.ServiceClient(), "d32019d3-bc6e-4319-9c1d-6722fc136a22").Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, n.Status, "ACTIVE")
+-	th.AssertDeepEquals(t, n.Subnets, []string{"54d6f61d-db07-451c-9ab3-b9609b6b6f0b"})
+-	th.AssertEquals(t, n.Name, "private-network")
+-	th.AssertEquals(t, n.AdminStateUp, true)
+-	th.AssertEquals(t, n.TenantID, "4fd44f30292945e481c7b8a0c8908869")
+-	th.AssertEquals(t, n.Shared, true)
+-	th.AssertEquals(t, n.ID, "d32019d3-bc6e-4319-9c1d-6722fc136a22")
 -}
 -
--func (s *ServerTests) TestGroupFiltering(c *C) {
--	g := make([]ec2.SecurityGroup, 4)
--	for i := range g {
--		resp, err := s.ec2.CreateSecurityGroup(ec2.SecurityGroup{Name: sessionName(fmt.Sprintf("testgroup%d", i)), Description: fmt.Sprintf("testdescription%d", i)})
--		c.Assert(err, IsNil)
--		g[i] = resp.SecurityGroup
--		c.Logf("group %d: %v", i, g[i])
--		defer s.ec2.DeleteSecurityGroup(g[i])
--	}
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/networks", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "network": {
+-        "name": "sample_network",
+-        "admin_state_up": true
+-    }
+-}
+-			`)
 -
--	perms := [][]ec2.IPPerm{
--		{{
--			Protocol:  "tcp",
--			FromPort:  100,
--			ToPort:    200,
--			SourceIPs: []string{"1.2.3.4/32"},
--		}},
--		{{
--			Protocol:     "tcp",
--			FromPort:     200,
--			ToPort:       300,
--			SourceGroups: []ec2.UserSecurityGroup{{Id: g[1].Id}},
--		}},
--		{{
--			Protocol:     "udp",
--			FromPort:     200,
--			ToPort:       400,
--			SourceGroups: []ec2.UserSecurityGroup{{Id: g[1].Id}},
--		}},
--	}
--	for i, ps := range perms {
--		_, err := s.ec2.AuthorizeSecurityGroup(g[i], ps)
--		c.Assert(err, IsNil)
--	}
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
 -
--	groups := func(indices ...int) (gs []ec2.SecurityGroup) {
--		for _, index := range indices {
--			gs = append(gs, g[index])
--		}
--		return
--	}
+-		fmt.Fprintf(w, `
+-{
+-    "network": {
+-        "status": "ACTIVE",
+-        "subnets": [],
+-        "name": "net1",
+-        "admin_state_up": true,
+-        "tenant_id": "9bacb3c5d39d41a79512987f338cf177",
+-        "shared": false,
+-        "id": "4e8e5957-649f-477b-9e5b-f1f75b21c03c"
+-    }
+-}
+-		`)
+-	})
 -
--	type groupTest struct {
--		about      string
--		groups     []ec2.SecurityGroup // groupIds argument to SecurityGroups method.
--		filters    []filterSpec        // filters argument to SecurityGroups method.
--		results    []ec2.SecurityGroup // set of expected result groups.
--		allowExtra bool                // specified results may be incomplete.
--		err        string              // expected error.
--	}
--	filterCheck := func(name, val string, gs []ec2.SecurityGroup) groupTest {
--		return groupTest{
--			about:      "filter check " + name,
--			filters:    []filterSpec{{name, []string{val}}},
--			results:    gs,
--			allowExtra: true,
--		}
--	}
--	tests := []groupTest{
--		{
--			about:      "check that SecurityGroups returns all groups",
--			results:    groups(0, 1, 2, 3),
--			allowExtra: true,
--		}, {
--			about:   "check that specifying two group ids returns them",
--			groups:  idsOnly(groups(0, 2)),
--			results: groups(0, 2),
--		}, {
--			about:   "check that specifying names only works",
--			groups:  namesOnly(groups(0, 2)),
--			results: groups(0, 2),
--		}, {
--			about:  "check that specifying a non-existent group id gives an error",
--			groups: append(groups(0), ec2.SecurityGroup{Id: "sg-eeeeeeeee"}),
--			err:    `.*\(InvalidGroup\.NotFound\)`,
--		}, {
--			about: "check that a filter allowed two groups returns both of them",
--			filters: []filterSpec{
--				{"group-id", []string{g[0].Id, g[2].Id}},
--			},
--			results: groups(0, 2),
--		},
--		{
--			about:  "check that the previous filter works when specifying a list of ids",
--			groups: groups(1, 2),
--			filters: []filterSpec{
--				{"group-id", []string{g[0].Id, g[2].Id}},
--			},
--			results: groups(2),
--		}, {
--			about: "check that a filter allowing no groups returns none",
--			filters: []filterSpec{
--				{"group-id", []string{"sg-eeeeeeeee"}},
--			},
--		},
--		filterCheck("description", "testdescription1", groups(1)),
--		filterCheck("group-name", g[2].Name, groups(2)),
--		filterCheck("ip-permission.cidr", "1.2.3.4/32", groups(0)),
--		filterCheck("ip-permission.group-name", g[1].Name, groups(1, 2)),
--		filterCheck("ip-permission.protocol", "udp", groups(2)),
--		filterCheck("ip-permission.from-port", "200", groups(1, 2)),
--		filterCheck("ip-permission.to-port", "200", groups(0)),
--		// TODO owner-id
+-	iTrue := true
+-	options := CreateOpts{Name: "sample_network", AdminStateUp: &iTrue}
+-	n, err := Create(fake.ServiceClient(), options).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, n.Status, "ACTIVE")
+-	th.AssertDeepEquals(t, n.Subnets, []string{})
+-	th.AssertEquals(t, n.Name, "net1")
+-	th.AssertEquals(t, n.AdminStateUp, true)
+-	th.AssertEquals(t, n.TenantID, "9bacb3c5d39d41a79512987f338cf177")
+-	th.AssertEquals(t, n.Shared, false)
+-	th.AssertEquals(t, n.ID, "4e8e5957-649f-477b-9e5b-f1f75b21c03c")
+-}
+-
+-func TestCreateWithOptionalFields(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/networks", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-	"network": {
+-			"name": "sample_network",
+-			"admin_state_up": true,
+-			"shared": true,
+-			"tenant_id": "12345"
 -	}
--	for i, t := range tests {
--		c.Logf("%d. %s", i, t.about)
--		var f *ec2.Filter
--		if t.filters != nil {
--			f = ec2.NewFilter()
--			for _, spec := range t.filters {
--				f.Add(spec.name, spec.values...)
--			}
--		}
--		resp, err := s.ec2.SecurityGroups(t.groups, f)
--		if t.err != "" {
--			c.Check(err, ErrorMatches, t.err)
--			continue
--		}
--		c.Assert(err, IsNil)
--		groups := make(map[string]*ec2.SecurityGroup)
--		for j := range resp.Groups {
--			group := &resp.Groups[j].SecurityGroup
--			c.Check(groups[group.Id], IsNil, Commentf("duplicate group id: %q", group.Id))
+-}
+-		`)
 -
--			groups[group.Id] = group
--		}
--		// If extra groups may be returned, eliminate all groups that
--		// we did not create in this session apart from the default group.
--		if t.allowExtra {
--			namePat := regexp.MustCompile(sessionName("testgroup[0-9]"))
--			for id, g := range groups {
--				if !namePat.MatchString(g.Name) {
--					delete(groups, id)
--				}
--			}
--		}
--		c.Check(groups, HasLen, len(t.results))
--		for j, g := range t.results {
--			rg := groups[g.Id]
--			c.Assert(rg, NotNil, Commentf("group %d (%v) not found; got %#v", j, g, groups))
--			c.Check(rg.Name, Equals, g.Name, Commentf("group %d (%v)", j, g))
+-		w.WriteHeader(http.StatusCreated)
+-	})
+-
+-	iTrue := true
+-	options := CreateOpts{Name: "sample_network", AdminStateUp: &iTrue, Shared: &iTrue, TenantID: "12345"}
+-	_, err := Create(fake.ServiceClient(), options).Extract()
+-	th.AssertNoErr(t, err)
+-}
+-
+-func TestUpdate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/networks/4e8e5957-649f-477b-9e5b-f1f75b21c03c", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-		"network": {
+-				"name": "new_network_name",
+-				"admin_state_up": false,
+-				"shared": true
 -		}
--	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2test/filter.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2test/filter.go
+-			`)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "network": {
+-        "status": "ACTIVE",
+-        "subnets": [],
+-        "name": "new_network_name",
+-        "admin_state_up": false,
+-        "tenant_id": "4fd44f30292945e481c7b8a0c8908869",
+-        "shared": true,
+-        "id": "4e8e5957-649f-477b-9e5b-f1f75b21c03c"
+-    }
+-}
+-		`)
+-	})
+-
+-	iTrue, iFalse := true, false
+-	options := UpdateOpts{Name: "new_network_name", AdminStateUp: &iFalse, Shared: &iTrue}
+-	n, err := Update(fake.ServiceClient(), "4e8e5957-649f-477b-9e5b-f1f75b21c03c", options).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, n.Name, "new_network_name")
+-	th.AssertEquals(t, n.AdminStateUp, false)
+-	th.AssertEquals(t, n.Shared, true)
+-	th.AssertEquals(t, n.ID, "4e8e5957-649f-477b-9e5b-f1f75b21c03c")
+-}
+-
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/networks/4e8e5957-649f-477b-9e5b-f1f75b21c03c", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-
+-	res := Delete(fake.ServiceClient(), "4e8e5957-649f-477b-9e5b-f1f75b21c03c")
+-	th.AssertNoErr(t, res.Err)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/results.go
 deleted file mode 100644
-index 1a0c046..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2test/filter.go
+index 3ecedde..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/results.go
 +++ /dev/null
-@@ -1,84 +0,0 @@
--package ec2test
+@@ -1,116 +0,0 @@
+-package networks
 -
 -import (
--	"fmt"
--	"net/url"
--	"strings"
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
 -)
 -
--// filter holds an ec2 filter.  A filter maps an attribute to a set of
--// possible values for that attribute. For an item to pass through the
--// filter, every attribute of the item mentioned in the filter must match
--// at least one of its given values.
--type filter map[string][]string
+-type commonResult struct {
+-	gophercloud.Result
+-}
 -
--// newFilter creates a new filter from the Filter fields in the url form.
--//
--// The filtering is specified through a map of name=>values, where the
--// name is a well-defined key identifying the data to be matched,
--// and the list of values holds the possible values the filtered
--// item can take for the key to be included in the
--// result set. For example:
--//
--//   Filter.1.Name=instance-type
--//   Filter.1.Value.1=m1.small
--//   Filter.1.Value.2=m1.large
--//
--func newFilter(form url.Values) filter {
--	// TODO return an error if the fields are not well formed?
--	names := make(map[int]string)
--	values := make(map[int][]string)
--	maxId := 0
--	for name, fvalues := range form {
--		var rest string
--		var id int
--		if x, _ := fmt.Sscanf(name, "Filter.%d.%s", &id, &rest); x != 2 {
--			continue
--		}
--		if id > maxId {
--			maxId = id
--		}
--		if rest == "Name" {
--			names[id] = fvalues[0]
--			continue
--		}
--		if !strings.HasPrefix(rest, "Value.") {
--			continue
--		}
--		values[id] = append(values[id], fvalues[0])
+-// Extract is a function that accepts a result and extracts a network resource.
+-func (r commonResult) Extract() (*Network, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
 -	}
 -
--	f := make(filter)
--	for id, name := range names {
--		f[name] = values[id]
+-	var res struct {
+-		Network *Network `json:"network"`
 -	}
--	return f
+-
+-	err := mapstructure.Decode(r.Body, &res)
+-
+-	return res.Network, err
 -}
 -
--func notDigit(r rune) bool {
--	return r < '0' || r > '9'
+-// CreateResult represents the result of a create operation.
+-type CreateResult struct {
+-	commonResult
 -}
 -
--// filterable represents an object that can be passed through a filter.
--type filterable interface {
--	// matchAttr returns true if given attribute of the
--	// object matches value. It returns an error if the
--	// attribute is not recognised or the value is malformed.
--	matchAttr(attr, value string) (bool, error)
+-// GetResult represents the result of a get operation.
+-type GetResult struct {
+-	commonResult
 -}
 -
--// ok returns true if x passes through the filter.
--func (f filter) ok(x filterable) (bool, error) {
--next:
--	for a, vs := range f {
--		for _, v := range vs {
--			if ok, err := x.matchAttr(a, v); ok {
--				continue next
--			} else if err != nil {
--				return false, fmt.Errorf("bad attribute or value %q=%q for type %T: %v", a, v, x, err)
--			}
--		}
--		return false, nil
+-// UpdateResult represents the result of an update operation.
+-type UpdateResult struct {
+-	commonResult
+-}
+-
+-// DeleteResult represents the result of a delete operation.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
+-}
+-
+-// Network represents, well, a network.
+-type Network struct {
+-	// UUID for the network
+-	ID string `mapstructure:"id" json:"id"`
+-
+-	// Human-readable name for the network. Might not be unique.
+-	Name string `mapstructure:"name" json:"name"`
+-
+-	// The administrative state of network. If false (down), the network does not forward packets.
+-	AdminStateUp bool `mapstructure:"admin_state_up" json:"admin_state_up"`
+-
+-	// Indicates whether network is currently operational. Possible values include
+-	// `ACTIVE', `DOWN', `BUILD', or `ERROR'. Plug-ins might define additional values.
+-	Status string `mapstructure:"status" json:"status"`
+-
+-	// Subnets associated with this network.
+-	Subnets []string `mapstructure:"subnets" json:"subnets"`
+-
+-	// Owner of network. Only admin users can specify a tenant_id other than its own.
+-	TenantID string `mapstructure:"tenant_id" json:"tenant_id"`
+-
+-	// Specifies whether the network resource can be accessed by any tenant or not.
+-	Shared bool `mapstructure:"shared" json:"shared"`
+-}
+-
+-// NetworkPage is the page returned by a pager when traversing over a
+-// collection of networks.
+-type NetworkPage struct {
+-	pagination.LinkedPageBase
+-}
+-
+-// NextPageURL is invoked when a paginated collection of networks has reached
+-// the end of a page and the pager seeks to traverse over a new one. In order
+-// to do this, it needs to construct the next page's URL.
+-func (p NetworkPage) NextPageURL() (string, error) {
+-	type resp struct {
+-		Links []gophercloud.Link `mapstructure:"networks_links"`
 -	}
--	return true, nil
+-
+-	var r resp
+-	err := mapstructure.Decode(p.Body, &r)
+-	if err != nil {
+-		return "", err
+-	}
+-
+-	return gophercloud.ExtractNextURL(r.Links)
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2test/server.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2test/server.go
+-
+-// IsEmpty checks whether a NetworkPage struct is empty.
+-func (p NetworkPage) IsEmpty() (bool, error) {
+-	is, err := ExtractNetworks(p)
+-	if err != nil {
+-		return true, nil
+-	}
+-	return len(is) == 0, nil
+-}
+-
+-// ExtractNetworks accepts a Page struct, specifically a NetworkPage struct,
+-// and extracts the elements into a slice of Network structs. In other words,
+-// a generic collection is mapped into a relevant slice.
+-func ExtractNetworks(page pagination.Page) ([]Network, error) {
+-	var resp struct {
+-		Networks []Network `mapstructure:"networks" json:"networks"`
+-	}
+-
+-	err := mapstructure.Decode(page.(NetworkPage).Body, &resp)
+-
+-	return resp.Networks, err
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/urls.go
 deleted file mode 100644
-index 2f24cb2..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/ec2test/server.go
+index 33c2387..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/urls.go
 +++ /dev/null
-@@ -1,993 +0,0 @@
--// The ec2test package implements a fake EC2 provider with
--// the capability of inducing errors on any given operation,
--// and retrospectively determining what operations have been
--// carried out.
--package ec2test
+@@ -1,27 +0,0 @@
+-package networks
 -
--import (
--	"encoding/base64"
--	"encoding/xml"
--	"fmt"
--	"github.com/mitchellh/goamz/ec2"
--	"io"
--	"net"
--	"net/http"
--	"net/url"
--	"regexp"
--	"strconv"
--	"strings"
--	"sync"
--)
+-import "github.com/rackspace/gophercloud"
 -
--var b64 = base64.StdEncoding
+-func resourceURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL("networks", id)
+-}
 -
--// Action represents a request that changes the ec2 state.
--type Action struct {
--	RequestId string
+-func rootURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL("networks")
+-}
 -
--	// Request holds the requested action as a url.Values instance
--	Request url.Values
+-func getURL(c *gophercloud.ServiceClient, id string) string {
+-	return resourceURL(c, id)
+-}
 -
--	// If the action succeeded, Response holds the value that
--	// was marshalled to build the XML response for the request.
--	Response interface{}
+-func listURL(c *gophercloud.ServiceClient) string {
+-	return rootURL(c)
+-}
 -
--	// If the action failed, Err holds an error giving details of the failure.
--	Err *ec2.Error
+-func createURL(c *gophercloud.ServiceClient) string {
+-	return rootURL(c)
 -}
 -
--// TODO possible other things:
--// - some virtual time stamp interface, so a client
--// can ask for all actions after a certain virtual time.
+-func deleteURL(c *gophercloud.ServiceClient, id string) string {
+-	return resourceURL(c, id)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/urls_test.go
+deleted file mode 100644
+index caf77db..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/networks/urls_test.go
++++ /dev/null
+@@ -1,38 +0,0 @@
+-package networks
 -
--// Server implements an EC2 simulator for use in testing.
--type Server struct {
--	url      string
--	listener net.Listener
--	mu       sync.Mutex
--	reqs     []*Action
+-import (
+-	"testing"
 -
--	instances            map[string]*Instance      // id -> instance
--	reservations         map[string]*reservation   // id -> reservation
--	groups               map[string]*securityGroup // id -> group
--	maxId                counter
--	reqId                counter
--	reservationId        counter
--	groupId              counter
--	initialInstanceState ec2.InstanceState
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-const endpoint = "http://localhost:57909/"
+-
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint, ResourceBase: endpoint + "v2.0/"}
 -}
 -
--// reservation holds a simulated ec2 reservation.
--type reservation struct {
--	id        string
--	instances map[string]*Instance
--	groups    []*securityGroup
+-func TestGetURL(t *testing.T) {
+-	actual := getURL(endpointClient(), "foo")
+-	expected := endpoint + "v2.0/networks/foo"
+-	th.AssertEquals(t, expected, actual)
 -}
 -
--// instance holds a simulated ec2 instance
--type Instance struct {
--	// UserData holds the data that was passed to the RunInstances request
--	// when the instance was started.
--	UserData    []byte
--	id          string
--	imageId     string
--	reservation *reservation
--	instType    string
--	state       ec2.InstanceState
+-func TestCreateURL(t *testing.T) {
+-	actual := createURL(endpointClient())
+-	expected := endpoint + "v2.0/networks"
+-	th.AssertEquals(t, expected, actual)
 -}
 -
--// permKey represents permission for a given security
--// group or IP address (but not both) to access a given range of
--// ports. Equality of permKeys is used in the implementation of
--// permission sets, relying on the uniqueness of securityGroup
--// instances.
--type permKey struct {
--	protocol string
--	fromPort int
--	toPort   int
--	group    *securityGroup
--	ipAddr   string
+-func TestListURL(t *testing.T) {
+-	actual := createURL(endpointClient())
+-	expected := endpoint + "v2.0/networks"
+-	th.AssertEquals(t, expected, actual)
 -}
 -
--// securityGroup holds a simulated ec2 security group.
--// Instances of securityGroup should only be created through
--// Server.createSecurityGroup to ensure that groups can be
--// compared by pointer value.
--type securityGroup struct {
--	id          string
--	name        string
--	description string
+-func TestDeleteURL(t *testing.T) {
+-	actual := deleteURL(endpointClient(), "foo")
+-	expected := endpoint + "v2.0/networks/foo"
+-	th.AssertEquals(t, expected, actual)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/doc.go
+deleted file mode 100644
+index f16a4bb..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/doc.go
++++ /dev/null
+@@ -1,8 +0,0 @@
+-// Package ports contains functionality for working with Neutron port resources.
+-// A port represents a virtual switch port on a logical network switch. Virtual
+-// instances attach their interfaces into ports. The logical port also defines
+-// the MAC address and the IP address(es) to be assigned to the interfaces
+-// plugged into them. When IP addresses are associated to a port, this also
+-// implies the port is associated with a subnet, as the IP address was taken
+-// from the allocation pool for a specific subnet.
+-package ports
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/errors.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/errors.go
+deleted file mode 100644
+index 111d977..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/errors.go
++++ /dev/null
+@@ -1,11 +0,0 @@
+-package ports
 -
--	perms map[permKey]bool
+-import "fmt"
+-
+-func err(str string) error {
+-	return fmt.Errorf("%s", str)
 -}
 -
--func (g *securityGroup) ec2SecurityGroup() ec2.SecurityGroup {
--	return ec2.SecurityGroup{
--		Name: g.name,
--		Id:   g.id,
+-var (
+-	errNetworkIDRequired = err("A Network ID is required")
+-)
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/requests.go
+deleted file mode 100644
+index 3399907..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/requests.go
++++ /dev/null
+@@ -1,245 +0,0 @@
+-package ports
+-
+-import (
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-
+-	"github.com/racker/perigee"
+-)
+-
+-// AdminState gives users a solid type to work with for create and update
+-// operations. It is recommended that users use the `Up` and `Down` enums.
+-type AdminState *bool
+-
+-// Convenience vars for AdminStateUp values.
+-var (
+-	iTrue  = true
+-	iFalse = false
+-
+-	Up   AdminState = &iTrue
+-	Down AdminState = &iFalse
+-)
+-
+-// ListOptsBuilder allows extensions to add additional parameters to the
+-// List request.
+-type ListOptsBuilder interface {
+-	ToPortListQuery() (string, error)
+-}
+-
+-// ListOpts allows the filtering and sorting of paginated collections through
+-// the API. Filtering is achieved by passing in struct field values that map to
+-// the port attributes you want to see returned. SortKey allows you to sort
+-// by a particular port attribute. SortDir sets the direction, and is either
+-// `asc' or `desc'. Marker and Limit are used for pagination.
+-type ListOpts struct {
+-	Status       string `q:"status"`
+-	Name         string `q:"name"`
+-	AdminStateUp *bool  `q:"admin_state_up"`
+-	NetworkID    string `q:"network_id"`
+-	TenantID     string `q:"tenant_id"`
+-	DeviceOwner  string `q:"device_owner"`
+-	MACAddress   string `q:"mac_address"`
+-	ID           string `q:"id"`
+-	DeviceID     string `q:"device_id"`
+-	Limit        int    `q:"limit"`
+-	Marker       string `q:"marker"`
+-	SortKey      string `q:"sort_key"`
+-	SortDir      string `q:"sort_dir"`
+-}
+-
+-// ToPortListQuery formats a ListOpts into a query string.
+-func (opts ListOpts) ToPortListQuery() (string, error) {
+-	q, err := gophercloud.BuildQueryString(opts)
+-	if err != nil {
+-		return "", err
 -	}
+-	return q.String(), nil
 -}
 -
--func (g *securityGroup) matchAttr(attr, value string) (ok bool, err error) {
--	switch attr {
--	case "description":
--		return g.description == value, nil
--	case "group-id":
--		return g.id == value, nil
--	case "group-name":
--		return g.name == value, nil
--	case "ip-permission.cidr":
--		return g.hasPerm(func(k permKey) bool { return k.ipAddr == value }), nil
--	case "ip-permission.group-name":
--		return g.hasPerm(func(k permKey) bool {
--			return k.group != nil && k.group.name == value
--		}), nil
--	case "ip-permission.from-port":
--		port, err := strconv.Atoi(value)
--		if err != nil {
--			return false, err
--		}
--		return g.hasPerm(func(k permKey) bool { return k.fromPort == port }), nil
--	case "ip-permission.to-port":
--		port, err := strconv.Atoi(value)
+-// List returns a Pager which allows you to iterate over a collection of
+-// ports. It accepts a ListOpts struct, which allows you to filter and sort
+-// the returned collection for greater efficiency.
+-//
+-// Default policy settings return only those ports that are owned by the tenant
+-// who submits the request, unless the request is submitted by a user with
+-// administrative rights.
+-func List(c *gophercloud.ServiceClient, opts ListOptsBuilder) pagination.Pager {
+-	url := listURL(c)
+-	if opts != nil {
+-		query, err := opts.ToPortListQuery()
 -		if err != nil {
--			return false, err
+-			return pagination.Pager{Err: err}
 -		}
--		return g.hasPerm(func(k permKey) bool { return k.toPort == port }), nil
--	case "ip-permission.protocol":
--		return g.hasPerm(func(k permKey) bool { return k.protocol == value }), nil
--	case "owner-id":
--		return value == ownerId, nil
+-		url += query
 -	}
--	return false, fmt.Errorf("unknown attribute %q", attr)
+-
+-	return pagination.NewPager(c, url, func(r pagination.PageResult) pagination.Page {
+-		return PortPage{pagination.LinkedPageBase{PageResult: r}}
+-	})
 -}
 -
--func (g *securityGroup) hasPerm(test func(k permKey) bool) bool {
--	for k := range g.perms {
--		if test(k) {
--			return true
--		}
--	}
--	return false
+-// Get retrieves a specific port based on its unique ID.
+-func Get(c *gophercloud.ServiceClient, id string) GetResult {
+-	var res GetResult
+-	_, res.Err = perigee.Request("GET", getURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return res
 -}
 -
--// ec2Perms returns the list of EC2 permissions granted
--// to g. It groups permissions by port range and protocol.
--func (g *securityGroup) ec2Perms() (perms []ec2.IPPerm) {
--	// The grouping is held in result. We use permKey for convenience,
--	// (ensuring that the group and ipAddr of each key is zero). For
--	// each protocol/port range combination, we build up the permission
--	// set in the associated value.
--	result := make(map[permKey]*ec2.IPPerm)
--	for k := range g.perms {
--		groupKey := k
--		groupKey.group = nil
--		groupKey.ipAddr = ""
+-// CreateOptsBuilder is the interface options structs have to satisfy in order
+-// to be used in the main Create operation in this package. Since many
+-// extensions decorate or modify the common logic, it is useful for them to
+-// satisfy a basic interface in order for them to be used.
+-type CreateOptsBuilder interface {
+-	ToPortCreateMap() (map[string]interface{}, error)
+-}
 -
--		ec2p := result[groupKey]
--		if ec2p == nil {
--			ec2p = &ec2.IPPerm{
--				Protocol: k.protocol,
--				FromPort: k.fromPort,
--				ToPort:   k.toPort,
--			}
--			result[groupKey] = ec2p
--		}
--		if k.group != nil {
--			ec2p.SourceGroups = append(ec2p.SourceGroups,
--				ec2.UserSecurityGroup{
--					Id:      k.group.id,
--					Name:    k.group.name,
--					OwnerId: ownerId,
--				})
--		} else {
--			ec2p.SourceIPs = append(ec2p.SourceIPs, k.ipAddr)
--		}
+-// CreateOpts represents the attributes used when creating a new port.
+-type CreateOpts struct {
+-	NetworkID      string
+-	Name           string
+-	AdminStateUp   *bool
+-	MACAddress     string
+-	FixedIPs       interface{}
+-	DeviceID       string
+-	DeviceOwner    string
+-	TenantID       string
+-	SecurityGroups []string
+-}
+-
+-// ToPortCreateMap casts a CreateOpts struct to a map.
+-func (opts CreateOpts) ToPortCreateMap() (map[string]interface{}, error) {
+-	p := make(map[string]interface{})
+-
+-	if opts.NetworkID == "" {
+-		return nil, errNetworkIDRequired
 -	}
--	for _, ec2p := range result {
--		perms = append(perms, *ec2p)
+-	p["network_id"] = opts.NetworkID
+-
+-	if opts.DeviceID != "" {
+-		p["device_id"] = opts.DeviceID
+-	}
+-	if opts.DeviceOwner != "" {
+-		p["device_owner"] = opts.DeviceOwner
+-	}
+-	if opts.FixedIPs != nil {
+-		p["fixed_ips"] = opts.FixedIPs
+-	}
+-	if opts.SecurityGroups != nil {
+-		p["security_groups"] = opts.SecurityGroups
+-	}
+-	if opts.TenantID != "" {
+-		p["tenant_id"] = opts.TenantID
+-	}
+-	if opts.AdminStateUp != nil {
+-		p["admin_state_up"] = &opts.AdminStateUp
+-	}
+-	if opts.Name != "" {
+-		p["name"] = opts.Name
+-	}
+-	if opts.MACAddress != "" {
+-		p["mac_address"] = opts.MACAddress
 -	}
--	return
--}
 -
--var actions = map[string]func(*Server, http.ResponseWriter, *http.Request, string) interface{}{
--	"RunInstances":                  (*Server).runInstances,
--	"TerminateInstances":            (*Server).terminateInstances,
--	"DescribeInstances":             (*Server).describeInstances,
--	"CreateSecurityGroup":           (*Server).createSecurityGroup,
--	"DescribeSecurityGroups":        (*Server).describeSecurityGroups,
--	"DeleteSecurityGroup":           (*Server).deleteSecurityGroup,
--	"AuthorizeSecurityGroupIngress": (*Server).authorizeSecurityGroupIngress,
--	"RevokeSecurityGroupIngress":    (*Server).revokeSecurityGroupIngress,
+-	return map[string]interface{}{"port": p}, nil
 -}
 -
--const ownerId = "9876"
+-// Create accepts a CreateOpts struct and creates a new network using the values
+-// provided. You must remember to provide a NetworkID value.
+-func Create(c *gophercloud.ServiceClient, opts CreateOptsBuilder) CreateResult {
+-	var res CreateResult
 -
--// newAction allocates a new action and adds it to the
--// recorded list of server actions.
--func (srv *Server) newAction() *Action {
--	srv.mu.Lock()
--	defer srv.mu.Unlock()
+-	reqBody, err := opts.ToPortCreateMap()
+-	if err != nil {
+-		res.Err = err
+-		return res
+-	}
 -
--	a := new(Action)
--	srv.reqs = append(srv.reqs, a)
--	return a
+-	// Response
+-	_, res.Err = perigee.Request("POST", createURL(c), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{201},
+-		DumpReqJson: true,
+-	})
+-
+-	return res
 -}
 -
--// NewServer returns a new server.
--func NewServer() (*Server, error) {
--	srv := &Server{
--		instances:            make(map[string]*Instance),
--		groups:               make(map[string]*securityGroup),
--		reservations:         make(map[string]*reservation),
--		initialInstanceState: Pending,
--	}
+-// UpdateOptsBuilder is the interface options structs have to satisfy in order
+-// to be used in the main Update operation in this package. Since many
+-// extensions decorate or modify the common logic, it is useful for them to
+-// satisfy a basic interface in order for them to be used.
+-type UpdateOptsBuilder interface {
+-	ToPortUpdateMap() (map[string]interface{}, error)
+-}
 -
--	// Add default security group.
--	g := &securityGroup{
--		name:        "default",
--		description: "default group",
--		id:          fmt.Sprintf("sg-%d", srv.groupId.next()),
+-// UpdateOpts represents the attributes used when updating an existing port.
+-type UpdateOpts struct {
+-	Name           string
+-	AdminStateUp   *bool
+-	FixedIPs       interface{}
+-	DeviceID       string
+-	DeviceOwner    string
+-	SecurityGroups []string
+-}
+-
+-// ToPortUpdateMap casts an UpdateOpts struct to a map.
+-func (opts UpdateOpts) ToPortUpdateMap() (map[string]interface{}, error) {
+-	p := make(map[string]interface{})
+-
+-	if opts.DeviceID != "" {
+-		p["device_id"] = opts.DeviceID
 -	}
--	g.perms = map[permKey]bool{
--		permKey{
--			protocol: "icmp",
--			fromPort: -1,
--			toPort:   -1,
--			group:    g,
--		}: true,
--		permKey{
--			protocol: "tcp",
--			fromPort: 0,
--			toPort:   65535,
--			group:    g,
--		}: true,
--		permKey{
--			protocol: "udp",
--			fromPort: 0,
--			toPort:   65535,
--			group:    g,
--		}: true,
+-	if opts.DeviceOwner != "" {
+-		p["device_owner"] = opts.DeviceOwner
+-	}
+-	if opts.FixedIPs != nil {
+-		p["fixed_ips"] = opts.FixedIPs
+-	}
+-	if opts.SecurityGroups != nil {
+-		p["security_groups"] = opts.SecurityGroups
+-	}
+-	if opts.AdminStateUp != nil {
+-		p["admin_state_up"] = &opts.AdminStateUp
+-	}
+-	if opts.Name != "" {
+-		p["name"] = opts.Name
 -	}
--	srv.groups[g.id] = g
 -
--	l, err := net.Listen("tcp", "localhost:0")
+-	return map[string]interface{}{"port": p}, nil
+-}
+-
+-// Update accepts a UpdateOpts struct and updates an existing port using the
+-// values provided.
+-func Update(c *gophercloud.ServiceClient, id string, opts UpdateOptsBuilder) UpdateResult {
+-	var res UpdateResult
+-
+-	reqBody, err := opts.ToPortUpdateMap()
 -	if err != nil {
--		return nil, fmt.Errorf("cannot listen on localhost: %v", err)
+-		res.Err = err
+-		return res
 -	}
--	srv.listener = l
--
--	srv.url = "http://" + l.Addr().String()
 -
--	// we use HandlerFunc rather than *Server directly so that we
--	// can avoid exporting HandlerFunc from *Server.
--	go http.Serve(l, http.HandlerFunc(func(w http.ResponseWriter, req *http.Request) {
--		srv.serveHTTP(w, req)
--	}))
--	return srv, nil
+-	_, res.Err = perigee.Request("PUT", updateURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{200, 201},
+-	})
+-	return res
 -}
 -
--// Quit closes down the server.
--func (srv *Server) Quit() {
--	srv.listener.Close()
+-// Delete accepts a unique ID and deletes the port associated with it.
+-func Delete(c *gophercloud.ServiceClient, id string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", deleteURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{204},
+-	})
+-	return res
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/requests_test.go
+deleted file mode 100644
+index 9e323ef..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/requests_test.go
++++ /dev/null
+@@ -1,321 +0,0 @@
+-package ports
 -
--// SetInitialInstanceState sets the state that any new instances will be started in.
--func (srv *Server) SetInitialInstanceState(state ec2.InstanceState) {
--	srv.mu.Lock()
--	srv.initialInstanceState = state
--	srv.mu.Unlock()
--}
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--// URL returns the URL of the server.
--func (srv *Server) URL() string {
--	return srv.url
--}
+-	fake "github.com/rackspace/gophercloud/openstack/networking/v2/common"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--// serveHTTP serves the EC2 protocol.
--func (srv *Server) serveHTTP(w http.ResponseWriter, req *http.Request) {
--	req.ParseForm()
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	a := srv.newAction()
--	a.RequestId = fmt.Sprintf("req%d", srv.reqId.next())
--	a.Request = req.Form
+-	th.Mux.HandleFunc("/v2.0/ports", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--	// Methods on Server that deal with parsing user data
--	// may fail. To save on error handling code, we allow these
--	// methods to call fatalf, which will panic with an *ec2.Error
--	// which will be caught here and returned
--	// to the client as a properly formed EC2 error.
--	defer func() {
--		switch err := recover().(type) {
--		case *ec2.Error:
--			a.Err = err
--			err.RequestId = a.RequestId
--			writeError(w, err)
--		case nil:
--		default:
--			panic(err)
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "ports": [
+-        {
+-            "status": "ACTIVE",
+-            "binding:host_id": "devstack",
+-            "name": "",
+-            "admin_state_up": true,
+-            "network_id": "70c1db1f-b701-45bd-96e0-a313ee3430b3",
+-            "tenant_id": "",
+-            "device_owner": "network:router_gateway",
+-            "mac_address": "fa:16:3e:58:42:ed",
+-            "fixed_ips": [
+-                {
+-                    "subnet_id": "008ba151-0b8c-4a67-98b5-0d2b87666062",
+-                    "ip_address": "172.24.4.2"
+-                }
+-            ],
+-            "id": "d80b1a3b-4fc1-49f3-952e-1e2ab7081d8b",
+-            "security_groups": [],
+-            "device_id": "9ae135f4-b6e0-4dad-9e91-3c223e385824"
+-        }
+-    ]
+-}
+-      `)
+-	})
+-
+-	count := 0
+-
+-	List(fake.ServiceClient(), ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractPorts(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract subnets: %v", err)
+-			return false, nil
+-		}
+-
+-		expected := []Port{
+-			Port{
+-				Status:       "ACTIVE",
+-				Name:         "",
+-				AdminStateUp: true,
+-				NetworkID:    "70c1db1f-b701-45bd-96e0-a313ee3430b3",
+-				TenantID:     "",
+-				DeviceOwner:  "network:router_gateway",
+-				MACAddress:   "fa:16:3e:58:42:ed",
+-				FixedIPs: []IP{
+-					IP{
+-						SubnetID:  "008ba151-0b8c-4a67-98b5-0d2b87666062",
+-						IPAddress: "172.24.4.2",
+-					},
+-				},
+-				ID:             "d80b1a3b-4fc1-49f3-952e-1e2ab7081d8b",
+-				SecurityGroups: []string{},
+-				DeviceID:       "9ae135f4-b6e0-4dad-9e91-3c223e385824",
+-			},
 -		}
--	}()
 -
--	f := actions[req.Form.Get("Action")]
--	if f == nil {
--		fatalf(400, "InvalidParameterValue", "Unrecognized Action")
+-		th.CheckDeepEquals(t, expected, actual)
+-
+-		return true, nil
+-	})
+-
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
 -	}
+-}
 -
--	response := f(srv, w, req, a.RequestId)
--	a.Response = response
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	w.Header().Set("Content-Type", `xml version="1.0" encoding="UTF-8"`)
--	xmlMarshal(w, response)
+-	th.Mux.HandleFunc("/v2.0/ports/46d4bfb9-b26e-41f3-bd2e-e6dcc1ccedb2", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "port": {
+-        "status": "ACTIVE",
+-        "name": "",
+-        "admin_state_up": true,
+-        "network_id": "a87cc70a-3e15-4acf-8205-9b711a3531b7",
+-        "tenant_id": "7e02058126cc4950b75f9970368ba177",
+-        "device_owner": "network:router_interface",
+-        "mac_address": "fa:16:3e:23:fd:d7",
+-        "fixed_ips": [
+-            {
+-                "subnet_id": "a0304c3a-4f08-4c43-88af-d796509c97d2",
+-                "ip_address": "10.0.0.1"
+-            }
+-        ],
+-        "id": "46d4bfb9-b26e-41f3-bd2e-e6dcc1ccedb2",
+-        "security_groups": [],
+-        "device_id": "5e3898d7-11be-483e-9732-b2f5eccd2b2e"
+-    }
 -}
+-			`)
+-	})
 -
--// Instance returns the instance for the given instance id.
--// It returns nil if there is no such instance.
--func (srv *Server) Instance(id string) *Instance {
--	srv.mu.Lock()
--	defer srv.mu.Unlock()
--	return srv.instances[id]
+-	n, err := Get(fake.ServiceClient(), "46d4bfb9-b26e-41f3-bd2e-e6dcc1ccedb2").Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, n.Status, "ACTIVE")
+-	th.AssertEquals(t, n.Name, "")
+-	th.AssertEquals(t, n.AdminStateUp, true)
+-	th.AssertEquals(t, n.NetworkID, "a87cc70a-3e15-4acf-8205-9b711a3531b7")
+-	th.AssertEquals(t, n.TenantID, "7e02058126cc4950b75f9970368ba177")
+-	th.AssertEquals(t, n.DeviceOwner, "network:router_interface")
+-	th.AssertEquals(t, n.MACAddress, "fa:16:3e:23:fd:d7")
+-	th.AssertDeepEquals(t, n.FixedIPs, []IP{
+-		IP{SubnetID: "a0304c3a-4f08-4c43-88af-d796509c97d2", IPAddress: "10.0.0.1"},
+-	})
+-	th.AssertEquals(t, n.ID, "46d4bfb9-b26e-41f3-bd2e-e6dcc1ccedb2")
+-	th.AssertDeepEquals(t, n.SecurityGroups, []string{})
+-	th.AssertEquals(t, n.Status, "ACTIVE")
+-	th.AssertEquals(t, n.DeviceID, "5e3898d7-11be-483e-9732-b2f5eccd2b2e")
 -}
 -
--// writeError writes an appropriate error response.
--// TODO how should we deal with errors when the
--// error itself is potentially generated by backend-agnostic
--// code?
--func writeError(w http.ResponseWriter, err *ec2.Error) {
--	// Error encapsulates an error returned by EC2.
--	// TODO merge with ec2.Error when xml supports ignoring a field.
--	type ec2error struct {
--		Code      string // EC2 error code ("UnsupportedOperation", ...)
--		Message   string // The human-oriented error message
--		RequestId string
--	}
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/ports", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "port": {
+-        "network_id": "a87cc70a-3e15-4acf-8205-9b711a3531b7",
+-        "name": "private-port",
+-        "admin_state_up": true,
+-				"fixed_ips": [
+-						{
+-								"subnet_id": "a0304c3a-4f08-4c43-88af-d796509c97d2",
+-								"ip_address": "10.0.0.2"
+-						}
+-				],
+-				"security_groups": ["foo"]
+-    }
+-}
+-			`)
 -
--	type Response struct {
--		RequestId string
--		Errors    []ec2error `xml:"Errors>Error"`
--	}
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
 -
--	w.Header().Set("Content-Type", `xml version="1.0" encoding="UTF-8"`)
--	w.WriteHeader(err.StatusCode)
--	xmlMarshal(w, Response{
--		RequestId: err.RequestId,
--		Errors: []ec2error{{
--			Code:    err.Code,
--			Message: err.Message,
--		}},
+-		fmt.Fprintf(w, `
+-{
+-    "port": {
+-        "status": "DOWN",
+-        "name": "private-port",
+-        "allowed_address_pairs": [],
+-        "admin_state_up": true,
+-        "network_id": "a87cc70a-3e15-4acf-8205-9b711a3531b7",
+-        "tenant_id": "d6700c0c9ffa4f1cb322cd4a1f3906fa",
+-        "device_owner": "",
+-        "mac_address": "fa:16:3e:c9:cb:f0",
+-        "fixed_ips": [
+-            {
+-                "subnet_id": "a0304c3a-4f08-4c43-88af-d796509c97d2",
+-                "ip_address": "10.0.0.2"
+-            }
+-        ],
+-        "id": "65c0ee9f-d634-4522-8954-51021b570b0d",
+-        "security_groups": [
+-            "f0ac4394-7e4a-4409-9701-ba8be283dbc3"
+-        ],
+-        "device_id": ""
+-    }
+-}
+-		`)
+-	})
+-
+-	asu := true
+-	options := CreateOpts{
+-		Name:         "private-port",
+-		AdminStateUp: &asu,
+-		NetworkID:    "a87cc70a-3e15-4acf-8205-9b711a3531b7",
+-		FixedIPs: []IP{
+-			IP{SubnetID: "a0304c3a-4f08-4c43-88af-d796509c97d2", IPAddress: "10.0.0.2"},
+-		},
+-		SecurityGroups: []string{"foo"},
+-	}
+-	n, err := Create(fake.ServiceClient(), options).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, n.Status, "DOWN")
+-	th.AssertEquals(t, n.Name, "private-port")
+-	th.AssertEquals(t, n.AdminStateUp, true)
+-	th.AssertEquals(t, n.NetworkID, "a87cc70a-3e15-4acf-8205-9b711a3531b7")
+-	th.AssertEquals(t, n.TenantID, "d6700c0c9ffa4f1cb322cd4a1f3906fa")
+-	th.AssertEquals(t, n.DeviceOwner, "")
+-	th.AssertEquals(t, n.MACAddress, "fa:16:3e:c9:cb:f0")
+-	th.AssertDeepEquals(t, n.FixedIPs, []IP{
+-		IP{SubnetID: "a0304c3a-4f08-4c43-88af-d796509c97d2", IPAddress: "10.0.0.2"},
 -	})
+-	th.AssertEquals(t, n.ID, "65c0ee9f-d634-4522-8954-51021b570b0d")
+-	th.AssertDeepEquals(t, n.SecurityGroups, []string{"f0ac4394-7e4a-4409-9701-ba8be283dbc3"})
 -}
 -
--// xmlMarshal is the same as xml.Marshal except that
--// it panics on error. The marshalling should not fail,
--// but we want to know if it does.
--func xmlMarshal(w io.Writer, x interface{}) {
--	if err := xml.NewEncoder(w).Encode(x); err != nil {
--		panic(fmt.Errorf("error marshalling %#v: %v", x, err))
+-func TestRequiredCreateOpts(t *testing.T) {
+-	res := Create(fake.ServiceClient(), CreateOpts{})
+-	if res.Err == nil {
+-		t.Fatalf("Expected error, got none")
 -	}
 -}
 -
--// formToGroups parses a set of SecurityGroup form values
--// as found in a RunInstances request, and returns the resulting
--// slice of security groups.
--// It calls fatalf if a group is not found.
--func (srv *Server) formToGroups(form url.Values) []*securityGroup {
--	var groups []*securityGroup
--	for name, values := range form {
--		switch {
--		case strings.HasPrefix(name, "SecurityGroupId."):
--			if g := srv.groups[values[0]]; g != nil {
--				groups = append(groups, g)
--			} else {
--				fatalf(400, "InvalidGroup.NotFound", "unknown group id %q", values[0])
--			}
--		case strings.HasPrefix(name, "SecurityGroup."):
--			var found *securityGroup
--			for _, g := range srv.groups {
--				if g.name == values[0] {
--					found = g
--				}
--			}
--			if found == nil {
--				fatalf(400, "InvalidGroup.NotFound", "unknown group name %q", values[0])
--			}
--			groups = append(groups, found)
+-func TestUpdate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/ports/65c0ee9f-d634-4522-8954-51021b570b0d", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-		"port": {
+-				"name": "new_port_name",
+-				"fixed_ips": [
+-            {
+-                "subnet_id": "a0304c3a-4f08-4c43-88af-d796509c97d2",
+-                "ip_address": "10.0.0.3"
+-            }
+-        ],
+-				"security_groups": [
+-            "f0ac4394-7e4a-4409-9701-ba8be283dbc3"
+-        ]
 -		}
--	}
--	return groups
 -}
+-			`)
 -
--// runInstances implements the EC2 RunInstances entry point.
--func (srv *Server) runInstances(w http.ResponseWriter, req *http.Request, reqId string) interface{} {
--	min := atoi(req.Form.Get("MinCount"))
--	max := atoi(req.Form.Get("MaxCount"))
--	if min < 0 || max < 1 {
--		fatalf(400, "InvalidParameterValue", "bad values for MinCount or MaxCount")
--	}
--	if min > max {
--		fatalf(400, "InvalidParameterCombination", "MinCount is greater than MaxCount")
--	}
--	var userData []byte
--	if data := req.Form.Get("UserData"); data != "" {
--		var err error
--		userData, err = b64.DecodeString(data)
--		if err != nil {
--			fatalf(400, "InvalidParameterValue", "bad UserData value: %v", err)
--		}
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "port": {
+-        "status": "DOWN",
+-        "name": "new_port_name",
+-        "admin_state_up": true,
+-        "network_id": "a87cc70a-3e15-4acf-8205-9b711a3531b7",
+-        "tenant_id": "d6700c0c9ffa4f1cb322cd4a1f3906fa",
+-        "device_owner": "",
+-        "mac_address": "fa:16:3e:c9:cb:f0",
+-        "fixed_ips": [
+-            {
+-                "subnet_id": "a0304c3a-4f08-4c43-88af-d796509c97d2",
+-                "ip_address": "10.0.0.3"
+-            }
+-        ],
+-        "id": "65c0ee9f-d634-4522-8954-51021b570b0d",
+-        "security_groups": [
+-            "f0ac4394-7e4a-4409-9701-ba8be283dbc3"
+-        ],
+-        "device_id": ""
+-    }
+-}
+-		`)
+-	})
+-
+-	options := UpdateOpts{
+-		Name: "new_port_name",
+-		FixedIPs: []IP{
+-			IP{SubnetID: "a0304c3a-4f08-4c43-88af-d796509c97d2", IPAddress: "10.0.0.3"},
+-		},
+-		SecurityGroups: []string{"f0ac4394-7e4a-4409-9701-ba8be283dbc3"},
 -	}
 -
--	// TODO attributes still to consider:
--	//    ImageId:                  accept anything, we can verify later
--	//    KeyName                   ?
--	//    InstanceType              ?
--	//    KernelId                  ?
--	//    RamdiskId                 ?
--	//    AvailZone                 ?
--	//    GroupName                 tag
--	//    Monitoring                ignore?
--	//    SubnetId                  ?
--	//    DisableAPITermination     bool
--	//    ShutdownBehavior          string
--	//    PrivateIPAddress          string
+-	s, err := Update(fake.ServiceClient(), "65c0ee9f-d634-4522-8954-51021b570b0d", options).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, s.Name, "new_port_name")
+-	th.AssertDeepEquals(t, s.FixedIPs, []IP{
+-		IP{SubnetID: "a0304c3a-4f08-4c43-88af-d796509c97d2", IPAddress: "10.0.0.3"},
+-	})
+-	th.AssertDeepEquals(t, s.SecurityGroups, []string{"f0ac4394-7e4a-4409-9701-ba8be283dbc3"})
+-}
 -
--	srv.mu.Lock()
--	defer srv.mu.Unlock()
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	// make sure that form fields are correct before creating the reservation.
--	instType := req.Form.Get("InstanceType")
--	imageId := req.Form.Get("ImageId")
+-	th.Mux.HandleFunc("/v2.0/ports/65c0ee9f-d634-4522-8954-51021b570b0d", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		w.WriteHeader(http.StatusNoContent)
+-	})
 -
--	r := srv.newReservation(srv.formToGroups(req.Form))
+-	res := Delete(fake.ServiceClient(), "65c0ee9f-d634-4522-8954-51021b570b0d")
+-	th.AssertNoErr(t, res.Err)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/results.go
+deleted file mode 100644
+index 2511ff5..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/results.go
++++ /dev/null
+@@ -1,126 +0,0 @@
+-package ports
 -
--	var resp ec2.RunInstancesResp
--	resp.RequestId = reqId
--	resp.ReservationId = r.id
--	resp.OwnerId = ownerId
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	for i := 0; i < max; i++ {
--		inst := srv.newInstance(r, instType, imageId, srv.initialInstanceState)
--		inst.UserData = userData
--		resp.Instances = append(resp.Instances, inst.ec2instance())
--	}
--	return &resp
+-type commonResult struct {
+-	gophercloud.Result
 -}
 -
--func (srv *Server) group(group ec2.SecurityGroup) *securityGroup {
--	if group.Id != "" {
--		return srv.groups[group.Id]
+-// Extract is a function that accepts a result and extracts a port resource.
+-func (r commonResult) Extract() (*Port, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
 -	}
--	for _, g := range srv.groups {
--		if g.name == group.Name {
--			return g
--		}
+-
+-	var res struct {
+-		Port *Port `json:"port"`
 -	}
--	return nil
+-
+-	err := mapstructure.Decode(r.Body, &res)
+-
+-	return res.Port, err
 -}
 -
--// NewInstances creates n new instances in srv with the given instance type,
--// image ID,  initial state and security groups. If any group does not already
--// exist, it will be created. NewInstances returns the ids of the new instances.
--func (srv *Server) NewInstances(n int, instType string, imageId string, state ec2.InstanceState, groups []ec2.SecurityGroup) []string {
--	srv.mu.Lock()
--	defer srv.mu.Unlock()
+-// CreateResult represents the result of a create operation.
+-type CreateResult struct {
+-	commonResult
+-}
 -
--	rgroups := make([]*securityGroup, len(groups))
--	for i, group := range groups {
--		g := srv.group(group)
--		if g == nil {
--			fatalf(400, "InvalidGroup.NotFound", "no such group %v", g)
--		}
--		rgroups[i] = g
+-// GetResult represents the result of a get operation.
+-type GetResult struct {
+-	commonResult
+-}
+-
+-// UpdateResult represents the result of an update operation.
+-type UpdateResult struct {
+-	commonResult
+-}
+-
+-// DeleteResult represents the result of a delete operation.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
+-}
+-
+-// IP is a sub-struct that represents an individual IP.
+-type IP struct {
+-	SubnetID  string `mapstructure:"subnet_id" json:"subnet_id"`
+-	IPAddress string `mapstructure:"ip_address" json:"ip_address,omitempty"`
+-}
+-
+-// Port represents a Neutron port. See package documentation for a top-level
+-// description of what this is.
+-type Port struct {
+-	// UUID for the port.
+-	ID string `mapstructure:"id" json:"id"`
+-	// Network that this port is associated with.
+-	NetworkID string `mapstructure:"network_id" json:"network_id"`
+-	// Human-readable name for the port. Might not be unique.
+-	Name string `mapstructure:"name" json:"name"`
+-	// Administrative state of port. If false (down), port does not forward packets.
+-	AdminStateUp bool `mapstructure:"admin_state_up" json:"admin_state_up"`
+-	// Indicates whether network is currently operational. Possible values include
+-	// `ACTIVE', `DOWN', `BUILD', or `ERROR'. Plug-ins might define additional values.
+-	Status string `mapstructure:"status" json:"status"`
+-	// Mac address to use on this port.
+-	MACAddress string `mapstructure:"mac_address" json:"mac_address"`
+-	// Specifies IP addresses for the port thus associating the port itself with
+-	// the subnets where the IP addresses are picked from
+-	FixedIPs []IP `mapstructure:"fixed_ips" json:"fixed_ips"`
+-	// Owner of network. Only admin users can specify a tenant_id other than its own.
+-	TenantID string `mapstructure:"tenant_id" json:"tenant_id"`
+-	// Identifies the entity (e.g.: dhcp agent) using this port.
+-	DeviceOwner string `mapstructure:"device_owner" json:"device_owner"`
+-	// Specifies the IDs of any security groups associated with a port.
+-	SecurityGroups []string `mapstructure:"security_groups" json:"security_groups"`
+-	// Identifies the device (e.g., virtual server) using this port.
+-	DeviceID string `mapstructure:"device_id" json:"device_id"`
+-}
+-
+-// PortPage is the page returned by a pager when traversing over a collection
+-// of network ports.
+-type PortPage struct {
+-	pagination.LinkedPageBase
+-}
+-
+-// NextPageURL is invoked when a paginated collection of ports has reached
+-// the end of a page and the pager seeks to traverse over a new one. In order
+-// to do this, it needs to construct the next page's URL.
+-func (p PortPage) NextPageURL() (string, error) {
+-	type resp struct {
+-		Links []gophercloud.Link `mapstructure:"ports_links"`
 -	}
--	r := srv.newReservation(rgroups)
 -
--	ids := make([]string, n)
--	for i := 0; i < n; i++ {
--		inst := srv.newInstance(r, instType, imageId, state)
--		ids[i] = inst.id
+-	var r resp
+-	err := mapstructure.Decode(p.Body, &r)
+-	if err != nil {
+-		return "", err
 -	}
--	return ids
+-
+-	return gophercloud.ExtractNextURL(r.Links)
 -}
 -
--func (srv *Server) newInstance(r *reservation, instType string, imageId string, state ec2.InstanceState) *Instance {
--	inst := &Instance{
--		id:          fmt.Sprintf("i-%d", srv.maxId.next()),
--		instType:    instType,
--		imageId:     imageId,
--		state:       state,
--		reservation: r,
+-// IsEmpty checks whether a PortPage struct is empty.
+-func (p PortPage) IsEmpty() (bool, error) {
+-	is, err := ExtractPorts(p)
+-	if err != nil {
+-		return true, nil
 -	}
--	srv.instances[inst.id] = inst
--	r.instances[inst.id] = inst
--	return inst
+-	return len(is) == 0, nil
 -}
 -
--func (srv *Server) newReservation(groups []*securityGroup) *reservation {
--	r := &reservation{
--		id:        fmt.Sprintf("r-%d", srv.reservationId.next()),
--		instances: make(map[string]*Instance),
--		groups:    groups,
+-// ExtractPorts accepts a Page struct, specifically a PortPage struct,
+-// and extracts the elements into a slice of Port structs. In other words,
+-// a generic collection is mapped into a relevant slice.
+-func ExtractPorts(page pagination.Page) ([]Port, error) {
+-	var resp struct {
+-		Ports []Port `mapstructure:"ports" json:"ports"`
 -	}
 -
--	srv.reservations[r.id] = r
--	return r
+-	err := mapstructure.Decode(page.(PortPage).Body, &resp)
+-
+-	return resp.Ports, err
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/urls.go
+deleted file mode 100644
+index 6d0572f..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/urls.go
++++ /dev/null
+@@ -1,31 +0,0 @@
+-package ports
 -
--func (srv *Server) terminateInstances(w http.ResponseWriter, req *http.Request, reqId string) interface{} {
--	srv.mu.Lock()
--	defer srv.mu.Unlock()
--	var resp ec2.TerminateInstancesResp
--	resp.RequestId = reqId
--	var insts []*Instance
--	for attr, vals := range req.Form {
--		if strings.HasPrefix(attr, "InstanceId.") {
--			id := vals[0]
--			inst := srv.instances[id]
--			if inst == nil {
--				fatalf(400, "InvalidInstanceID.NotFound", "no such instance id %q", id)
--			}
--			insts = append(insts, inst)
--		}
--	}
--	for _, inst := range insts {
--		resp.StateChanges = append(resp.StateChanges, inst.terminate())
--	}
--	return &resp
+-import "github.com/rackspace/gophercloud"
+-
+-func resourceURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL("ports", id)
 -}
 -
--func (inst *Instance) terminate() (d ec2.InstanceStateChange) {
--	d.PreviousState = inst.state
--	inst.state = ShuttingDown
--	d.CurrentState = inst.state
--	d.InstanceId = inst.id
--	return d
+-func rootURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL("ports")
 -}
 -
--func (inst *Instance) ec2instance() ec2.Instance {
--	return ec2.Instance{
--		InstanceId:   inst.id,
--		InstanceType: inst.instType,
--		ImageId:      inst.imageId,
--		DNSName:      fmt.Sprintf("%s.example.com", inst.id),
--		// TODO the rest
--	}
+-func listURL(c *gophercloud.ServiceClient) string {
+-	return rootURL(c)
 -}
 -
--func (inst *Instance) matchAttr(attr, value string) (ok bool, err error) {
--	switch attr {
--	case "architecture":
--		return value == "i386", nil
--	case "instance-id":
--		return inst.id == value, nil
--	case "group-id":
--		for _, g := range inst.reservation.groups {
--			if g.id == value {
--				return true, nil
--			}
--		}
--		return false, nil
--	case "group-name":
--		for _, g := range inst.reservation.groups {
--			if g.name == value {
--				return true, nil
--			}
--		}
--		return false, nil
--	case "image-id":
--		return value == inst.imageId, nil
--	case "instance-state-code":
--		code, err := strconv.Atoi(value)
--		if err != nil {
--			return false, err
--		}
--		return code&0xff == inst.state.Code, nil
--	case "instance-state-name":
--		return value == inst.state.Name, nil
--	}
--	return false, fmt.Errorf("unknown attribute %q", attr)
+-func getURL(c *gophercloud.ServiceClient, id string) string {
+-	return resourceURL(c, id)
 -}
 -
--var (
--	Pending      = ec2.InstanceState{0, "pending"}
--	Running      = ec2.InstanceState{16, "running"}
--	ShuttingDown = ec2.InstanceState{32, "shutting-down"}
--	Terminated   = ec2.InstanceState{16, "terminated"}
--	Stopped      = ec2.InstanceState{16, "stopped"}
+-func createURL(c *gophercloud.ServiceClient) string {
+-	return rootURL(c)
+-}
+-
+-func updateURL(c *gophercloud.ServiceClient, id string) string {
+-	return resourceURL(c, id)
+-}
+-
+-func deleteURL(c *gophercloud.ServiceClient, id string) string {
+-	return resourceURL(c, id)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/urls_test.go
+deleted file mode 100644
+index 7fadd4d..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/ports/urls_test.go
++++ /dev/null
+@@ -1,44 +0,0 @@
+-package ports
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--func (srv *Server) createSecurityGroup(w http.ResponseWriter, req *http.Request, reqId string) interface{} {
--	name := req.Form.Get("GroupName")
--	if name == "" {
--		fatalf(400, "InvalidParameterValue", "empty security group name")
--	}
--	srv.mu.Lock()
--	defer srv.mu.Unlock()
--	if srv.group(ec2.SecurityGroup{Name: name}) != nil {
--		fatalf(400, "InvalidGroup.Duplicate", "group %q already exists", name)
--	}
--	g := &securityGroup{
--		name:        name,
--		description: req.Form.Get("GroupDescription"),
--		id:          fmt.Sprintf("sg-%d", srv.groupId.next()),
--		perms:       make(map[permKey]bool),
--	}
--	srv.groups[g.id] = g
--	// we define a local type for this because ec2.CreateSecurityGroupResp
--	// contains SecurityGroup, but the response to this request
--	// should not contain the security group name.
--	type CreateSecurityGroupResponse struct {
--		RequestId string `xml:"requestId"`
--		Return    bool   `xml:"return"`
--		GroupId   string `xml:"groupId"`
--	}
--	r := &CreateSecurityGroupResponse{
--		RequestId: reqId,
--		Return:    true,
--		GroupId:   g.id,
--	}
--	return r
+-const endpoint = "http://localhost:57909/"
+-
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint, ResourceBase: endpoint + "v2.0/"}
 -}
 -
--func (srv *Server) notImplemented(w http.ResponseWriter, req *http.Request, reqId string) interface{} {
--	fatalf(500, "InternalError", "not implemented")
--	panic("not reached")
+-func TestListURL(t *testing.T) {
+-	actual := listURL(endpointClient())
+-	expected := endpoint + "v2.0/ports"
+-	th.AssertEquals(t, expected, actual)
 -}
 -
--func (srv *Server) describeInstances(w http.ResponseWriter, req *http.Request, reqId string) interface{} {
--	srv.mu.Lock()
--	defer srv.mu.Unlock()
--	insts := make(map[*Instance]bool)
--	for name, vals := range req.Form {
--		if !strings.HasPrefix(name, "InstanceId.") {
--			continue
--		}
--		inst := srv.instances[vals[0]]
--		if inst == nil {
--			fatalf(400, "InvalidInstanceID.NotFound", "instance %q not found", vals[0])
--		}
--		insts[inst] = true
--	}
+-func TestGetURL(t *testing.T) {
+-	actual := getURL(endpointClient(), "foo")
+-	expected := endpoint + "v2.0/ports/foo"
+-	th.AssertEquals(t, expected, actual)
+-}
 -
--	f := newFilter(req.Form)
+-func TestCreateURL(t *testing.T) {
+-	actual := createURL(endpointClient())
+-	expected := endpoint + "v2.0/ports"
+-	th.AssertEquals(t, expected, actual)
+-}
 -
--	var resp ec2.InstancesResp
--	resp.RequestId = reqId
--	for _, r := range srv.reservations {
--		var instances []ec2.Instance
--		for _, inst := range r.instances {
--			if len(insts) > 0 && !insts[inst] {
--				continue
--			}
--			ok, err := f.ok(inst)
--			if ok {
--				instances = append(instances, inst.ec2instance())
--			} else if err != nil {
--				fatalf(400, "InvalidParameterValue", "describe instances: %v", err)
--			}
--		}
--		if len(instances) > 0 {
--			var groups []ec2.SecurityGroup
--			for _, g := range r.groups {
--				groups = append(groups, g.ec2SecurityGroup())
--			}
--			resp.Reservations = append(resp.Reservations, ec2.Reservation{
--				ReservationId:  r.id,
--				OwnerId:        ownerId,
--				Instances:      instances,
--				SecurityGroups: groups,
--			})
--		}
--	}
--	return &resp
+-func TestUpdateURL(t *testing.T) {
+-	actual := updateURL(endpointClient(), "foo")
+-	expected := endpoint + "v2.0/ports/foo"
+-	th.AssertEquals(t, expected, actual)
 -}
 -
--func (srv *Server) describeSecurityGroups(w http.ResponseWriter, req *http.Request, reqId string) interface{} {
--	// BUG similar bug to describeInstances, but for GroupName and GroupId
--	srv.mu.Lock()
--	defer srv.mu.Unlock()
+-func TestDeleteURL(t *testing.T) {
+-	actual := deleteURL(endpointClient(), "foo")
+-	expected := endpoint + "v2.0/ports/foo"
+-	th.AssertEquals(t, expected, actual)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/doc.go
+deleted file mode 100644
+index 43e8296..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/doc.go
++++ /dev/null
+@@ -1,10 +0,0 @@
+-// Package subnets contains functionality for working with Neutron subnet
+-// resources. A subnet represents an IP address block that can be used to
+-// assign IP addresses to virtual instances. Each subnet must have a CIDR and
+-// must be associated with a network. IPs can either be selected from the whole
+-// subnet CIDR or from allocation pools specified by the user.
+-//
+-// A subnet can also have a gateway, a list of DNS name servers, and host routes.
+-// This information is pushed to instances whose interfaces are associated with
+-// the subnet.
+-package subnets
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/errors.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/errors.go
+deleted file mode 100644
+index 0db0a6e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/errors.go
++++ /dev/null
+@@ -1,13 +0,0 @@
+-package subnets
 -
--	var groups []*securityGroup
--	for name, vals := range req.Form {
--		var g ec2.SecurityGroup
--		switch {
--		case strings.HasPrefix(name, "GroupName."):
--			g.Name = vals[0]
--		case strings.HasPrefix(name, "GroupId."):
--			g.Id = vals[0]
--		default:
--			continue
--		}
--		sg := srv.group(g)
--		if sg == nil {
--			fatalf(400, "InvalidGroup.NotFound", "no such group %v", g)
--		}
--		groups = append(groups, sg)
--	}
--	if len(groups) == 0 {
--		for _, g := range srv.groups {
--			groups = append(groups, g)
--		}
--	}
+-import "fmt"
 -
--	f := newFilter(req.Form)
--	var resp ec2.SecurityGroupsResp
--	resp.RequestId = reqId
--	for _, group := range groups {
--		ok, err := f.ok(group)
--		if ok {
--			resp.Groups = append(resp.Groups, ec2.SecurityGroupInfo{
--				OwnerId:       ownerId,
--				SecurityGroup: group.ec2SecurityGroup(),
--				Description:   group.description,
--				IPPerms:       group.ec2Perms(),
--			})
--		} else if err != nil {
--			fatalf(400, "InvalidParameterValue", "describe security groups: %v", err)
--		}
--	}
--	return &resp
+-func err(str string) error {
+-	return fmt.Errorf("%s", str)
 -}
 -
--func (srv *Server) authorizeSecurityGroupIngress(w http.ResponseWriter, req *http.Request, reqId string) interface{} {
--	srv.mu.Lock()
--	defer srv.mu.Unlock()
--	g := srv.group(ec2.SecurityGroup{
--		Name: req.Form.Get("GroupName"),
--		Id:   req.Form.Get("GroupId"),
--	})
--	if g == nil {
--		fatalf(400, "InvalidGroup.NotFound", "group not found")
+-var (
+-	errNetworkIDRequired = err("A network ID is required")
+-	errCIDRRequired      = err("A valid CIDR is required")
+-	errInvalidIPType     = err("An IP type must either be 4 or 6")
+-)
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/requests.go
+deleted file mode 100644
+index cd7c663..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/requests.go
++++ /dev/null
+@@ -1,254 +0,0 @@
+-package subnets
+-
+-import (
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-
+-	"github.com/racker/perigee"
+-)
+-
+-// AdminState gives users a solid type to work with for create and update
+-// operations. It is recommended that users use the `Up` and `Down` enums.
+-type AdminState *bool
+-
+-// Convenience vars for AdminStateUp values.
+-var (
+-	iTrue  = true
+-	iFalse = false
+-
+-	Up   AdminState = &iTrue
+-	Down AdminState = &iFalse
+-)
+-
+-// ListOptsBuilder allows extensions to add additional parameters to the
+-// List request.
+-type ListOptsBuilder interface {
+-	ToSubnetListQuery() (string, error)
+-}
+-
+-// ListOpts allows the filtering and sorting of paginated collections through
+-// the API. Filtering is achieved by passing in struct field values that map to
+-// the subnet attributes you want to see returned. SortKey allows you to sort
+-// by a particular subnet attribute. SortDir sets the direction, and is either
+-// `asc' or `desc'. Marker and Limit are used for pagination.
+-type ListOpts struct {
+-	Name       string `q:"name"`
+-	EnableDHCP *bool  `q:"enable_dhcp"`
+-	NetworkID  string `q:"network_id"`
+-	TenantID   string `q:"tenant_id"`
+-	IPVersion  int    `q:"ip_version"`
+-	GatewayIP  string `q:"gateway_ip"`
+-	CIDR       string `q:"cidr"`
+-	ID         string `q:"id"`
+-	Limit      int    `q:"limit"`
+-	Marker     string `q:"marker"`
+-	SortKey    string `q:"sort_key"`
+-	SortDir    string `q:"sort_dir"`
+-}
+-
+-// ToSubnetListQuery formats a ListOpts into a query string.
+-func (opts ListOpts) ToSubnetListQuery() (string, error) {
+-	q, err := gophercloud.BuildQueryString(opts)
+-	if err != nil {
+-		return "", err
 -	}
--	perms := srv.parsePerms(req)
+-	return q.String(), nil
+-}
 -
--	for _, p := range perms {
--		if g.perms[p] {
--			fatalf(400, "InvalidPermission.Duplicate", "Permission has already been authorized on the specified group")
+-// List returns a Pager which allows you to iterate over a collection of
+-// subnets. It accepts a ListOpts struct, which allows you to filter and sort
+-// the returned collection for greater efficiency.
+-//
+-// Default policy settings return only those subnets that are owned by the tenant
+-// who submits the request, unless the request is submitted by a user with
+-// administrative rights.
+-func List(c *gophercloud.ServiceClient, opts ListOptsBuilder) pagination.Pager {
+-	url := listURL(c)
+-	if opts != nil {
+-		query, err := opts.ToSubnetListQuery()
+-		if err != nil {
+-			return pagination.Pager{Err: err}
 -		}
+-		url += query
 -	}
--	for _, p := range perms {
--		g.perms[p] = true
--	}
--	return &ec2.SimpleResp{
--		XMLName:   xml.Name{"", "AuthorizeSecurityGroupIngressResponse"},
--		RequestId: reqId,
--	}
+-
+-	return pagination.NewPager(c, url, func(r pagination.PageResult) pagination.Page {
+-		return SubnetPage{pagination.LinkedPageBase{PageResult: r}}
+-	})
 -}
 -
--func (srv *Server) revokeSecurityGroupIngress(w http.ResponseWriter, req *http.Request, reqId string) interface{} {
--	srv.mu.Lock()
--	defer srv.mu.Unlock()
--	g := srv.group(ec2.SecurityGroup{
--		Name: req.Form.Get("GroupName"),
--		Id:   req.Form.Get("GroupId"),
+-// Get retrieves a specific subnet based on its unique ID.
+-func Get(c *gophercloud.ServiceClient, id string) GetResult {
+-	var res GetResult
+-	_, res.Err = perigee.Request("GET", getURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
 -	})
--	if g == nil {
--		fatalf(400, "InvalidGroup.NotFound", "group not found")
--	}
--	perms := srv.parsePerms(req)
+-	return res
+-}
 -
--	// Note EC2 does not give an error if asked to revoke an authorization
--	// that does not exist.
--	for _, p := range perms {
--		delete(g.perms, p)
--	}
--	return &ec2.SimpleResp{
--		XMLName:   xml.Name{"", "RevokeSecurityGroupIngressResponse"},
--		RequestId: reqId,
--	}
+-// Valid IP types
+-const (
+-	IPv4 = 4
+-	IPv6 = 6
+-)
+-
+-// CreateOptsBuilder is the interface options structs have to satisfy in order
+-// to be used in the main Create operation in this package. Since many
+-// extensions decorate or modify the common logic, it is useful for them to
+-// satisfy a basic interface in order for them to be used.
+-type CreateOptsBuilder interface {
+-	ToSubnetCreateMap() (map[string]interface{}, error)
 -}
 -
--var secGroupPat = regexp.MustCompile(`^sg-[a-z0-9]+$`)
--var ipPat = regexp.MustCompile(`^[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+/[0-9]+$`)
--var ownerIdPat = regexp.MustCompile(`^[0-9]+$`)
+-// CreateOpts represents the attributes used when creating a new subnet.
+-type CreateOpts struct {
+-	// Required
+-	NetworkID string
+-	CIDR      string
+-	// Optional
+-	Name            string
+-	TenantID        string
+-	AllocationPools []AllocationPool
+-	GatewayIP       string
+-	IPVersion       int
+-	EnableDHCP      *bool
+-	DNSNameservers  []string
+-	HostRoutes      []HostRoute
+-}
 -
--// parsePerms returns a slice of permKey values extracted
--// from the permission fields in req.
--func (srv *Server) parsePerms(req *http.Request) []permKey {
--	// perms maps an index found in the form to its associated
--	// IPPerm. For instance, the form value with key
--	// "IpPermissions.3.FromPort" will be stored in perms[3].FromPort
--	perms := make(map[int]ec2.IPPerm)
+-// ToSubnetCreateMap casts a CreateOpts struct to a map.
+-func (opts CreateOpts) ToSubnetCreateMap() (map[string]interface{}, error) {
+-	s := make(map[string]interface{})
 -
--	type subgroupKey struct {
--		id1, id2 int
+-	if opts.NetworkID == "" {
+-		return nil, errNetworkIDRequired
 -	}
--	// Each IPPerm can have many source security groups.  The form key
--	// for a source security group contains two indices: the index
--	// of the IPPerm and the sub-index of the security group. The
--	// sourceGroups map maps from a subgroupKey containing these
--	// two indices to the associated security group. For instance,
--	// the form value with key "IPPermissions.3.Groups.2.GroupName"
--	// will be stored in sourceGroups[subgroupKey{3, 2}].Name.
--	sourceGroups := make(map[subgroupKey]ec2.UserSecurityGroup)
--
--	// For each value in the form we store its associated information in the
--	// above maps. The maps are necessary because the form keys may
--	// arrive in any order, and the indices are not
--	// necessarily sequential or even small.
--	for name, vals := range req.Form {
--		val := vals[0]
--		var id1 int
--		var rest string
--		if x, _ := fmt.Sscanf(name, "IpPermissions.%d.%s", &id1, &rest); x != 2 {
--			continue
--		}
--		ec2p := perms[id1]
--		switch {
--		case rest == "FromPort":
--			ec2p.FromPort = atoi(val)
--		case rest == "ToPort":
--			ec2p.ToPort = atoi(val)
--		case rest == "IpProtocol":
--			switch val {
--			case "tcp", "udp", "icmp":
--				ec2p.Protocol = val
--			default:
--				// check it's a well formed number
--				atoi(val)
--				ec2p.Protocol = val
--			}
--		case strings.HasPrefix(rest, "Groups."):
--			k := subgroupKey{id1: id1}
--			if x, _ := fmt.Sscanf(rest[len("Groups."):], "%d.%s", &k.id2, &rest); x != 2 {
--				continue
--			}
--			g := sourceGroups[k]
--			switch rest {
--			case "UserId":
--				// BUG if the user id is blank, this does not conform to the
--				// way that EC2 handles it - a specified but blank owner id
--				// can cause RevokeSecurityGroupIngress to fail with
--				// "group not found" even if the security group id has been
--				// correctly specified.
--				// By failing here, we ensure that we fail early in this case.
--				if !ownerIdPat.MatchString(val) {
--					fatalf(400, "InvalidUserID.Malformed", "Invalid user ID: %q", val)
--				}
--				g.OwnerId = val
--			case "GroupName":
--				g.Name = val
--			case "GroupId":
--				if !secGroupPat.MatchString(val) {
--					fatalf(400, "InvalidGroupId.Malformed", "Invalid group ID: %q", val)
--				}
--				g.Id = val
--			default:
--				fatalf(400, "UnknownParameter", "unknown parameter %q", name)
--			}
--			sourceGroups[k] = g
--		case strings.HasPrefix(rest, "IpRanges."):
--			var id2 int
--			if x, _ := fmt.Sscanf(rest[len("IpRanges."):], "%d.%s", &id2, &rest); x != 2 {
--				continue
--			}
--			switch rest {
--			case "CidrIp":
--				if !ipPat.MatchString(val) {
--					fatalf(400, "InvalidPermission.Malformed", "Invalid IP range: %q", val)
--				}
--				ec2p.SourceIPs = append(ec2p.SourceIPs, val)
--			default:
--				fatalf(400, "UnknownParameter", "unknown parameter %q", name)
--			}
--		default:
--			fatalf(400, "UnknownParameter", "unknown parameter %q", name)
--		}
--		perms[id1] = ec2p
+-	if opts.CIDR == "" {
+-		return nil, errCIDRRequired
 -	}
--	// Associate each set of source groups with its IPPerm.
--	for k, g := range sourceGroups {
--		p := perms[k.id1]
--		p.SourceGroups = append(p.SourceGroups, g)
--		perms[k.id1] = p
+-	if opts.IPVersion != 0 && opts.IPVersion != IPv4 && opts.IPVersion != IPv6 {
+-		return nil, errInvalidIPType
 -	}
 -
--	// Now that we have built up the IPPerms we need, we check for
--	// parameter errors and build up a permKey for each permission,
--	// looking up security groups from srv as we do so.
--	var result []permKey
--	for _, p := range perms {
--		if p.FromPort > p.ToPort {
--			fatalf(400, "InvalidParameterValue", "invalid port range")
--		}
--		k := permKey{
--			protocol: p.Protocol,
--			fromPort: p.FromPort,
--			toPort:   p.ToPort,
--		}
--		for _, g := range p.SourceGroups {
--			if g.OwnerId != "" && g.OwnerId != ownerId {
--				fatalf(400, "InvalidGroup.NotFound", "group %q not found", g.Name)
--			}
--			var ec2g ec2.SecurityGroup
--			switch {
--			case g.Id != "":
--				ec2g.Id = g.Id
--			case g.Name != "":
--				ec2g.Name = g.Name
--			}
--			k.group = srv.group(ec2g)
--			if k.group == nil {
--				fatalf(400, "InvalidGroup.NotFound", "group %v not found", g)
--			}
--			result = append(result, k)
--		}
--		k.group = nil
--		for _, ip := range p.SourceIPs {
--			k.ipAddr = ip
--			result = append(result, k)
--		}
--	}
--	return result
--}
+-	s["network_id"] = opts.NetworkID
+-	s["cidr"] = opts.CIDR
 -
--func (srv *Server) deleteSecurityGroup(w http.ResponseWriter, req *http.Request, reqId string) interface{} {
--	srv.mu.Lock()
--	defer srv.mu.Unlock()
--	g := srv.group(ec2.SecurityGroup{
--		Name: req.Form.Get("GroupName"),
--		Id:   req.Form.Get("GroupId"),
--	})
--	if g == nil {
--		fatalf(400, "InvalidGroup.NotFound", "group not found")
+-	if opts.EnableDHCP != nil {
+-		s["enable_dhcp"] = &opts.EnableDHCP
 -	}
--	for _, r := range srv.reservations {
--		for _, h := range r.groups {
--			if h == g && r.hasRunningMachine() {
--				fatalf(500, "InvalidGroup.InUse", "group is currently in use by a running instance")
--			}
--		}
+-	if opts.Name != "" {
+-		s["name"] = opts.Name
 -	}
--	for _, sg := range srv.groups {
--		// If a group refers to itself, it's ok to delete it.
--		if sg == g {
--			continue
--		}
--		for k := range sg.perms {
--			if k.group == g {
--				fatalf(500, "InvalidGroup.InUse", "group is currently in use by group %q", sg.id)
--			}
--		}
+-	if opts.GatewayIP != "" {
+-		s["gateway_ip"] = opts.GatewayIP
 -	}
--
--	delete(srv.groups, g.id)
--	return &ec2.SimpleResp{
--		XMLName:   xml.Name{"", "DeleteSecurityGroupResponse"},
--		RequestId: reqId,
+-	if opts.TenantID != "" {
+-		s["tenant_id"] = opts.TenantID
 -	}
--}
--
--func (r *reservation) hasRunningMachine() bool {
--	for _, inst := range r.instances {
--		if inst.state.Code != ShuttingDown.Code && inst.state.Code != Terminated.Code {
--			return true
--		}
+-	if opts.IPVersion != 0 {
+-		s["ip_version"] = opts.IPVersion
+-	}
+-	if len(opts.AllocationPools) != 0 {
+-		s["allocation_pools"] = opts.AllocationPools
+-	}
+-	if len(opts.DNSNameservers) != 0 {
+-		s["dns_nameservers"] = opts.DNSNameservers
+-	}
+-	if len(opts.HostRoutes) != 0 {
+-		s["host_routes"] = opts.HostRoutes
 -	}
--	return false
--}
--
--type counter int
 -
--func (c *counter) next() (i int) {
--	i = int(*c)
--	(*c)++
--	return
+-	return map[string]interface{}{"subnet": s}, nil
 -}
 -
--// atoi is like strconv.Atoi but is fatal if the
--// string is not well formed.
--func atoi(s string) int {
--	i, err := strconv.Atoi(s)
+-// Create accepts a CreateOpts struct and creates a new subnet using the values
+-// provided. You must remember to provide a valid NetworkID, CIDR and IP version.
+-func Create(c *gophercloud.ServiceClient, opts CreateOptsBuilder) CreateResult {
+-	var res CreateResult
+-
+-	reqBody, err := opts.ToSubnetCreateMap()
 -	if err != nil {
--		fatalf(400, "InvalidParameterValue", "bad number: %v", err)
+-		res.Err = err
+-		return res
 -	}
--	return i
--}
 -
--func fatalf(statusCode int, code string, f string, a ...interface{}) {
--	panic(&ec2.Error{
--		StatusCode: statusCode,
--		Code:       code,
--		Message:    fmt.Sprintf(f, a...),
+-	_, res.Err = perigee.Request("POST", createURL(c), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{201},
 -	})
--}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/export_test.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/export_test.go
-deleted file mode 100644
-index 1c24422..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/export_test.go
-+++ /dev/null
-@@ -1,22 +0,0 @@
--package ec2
--
--import (
--	"github.com/mitchellh/goamz/aws"
--	"time"
--)
 -
--func Sign(auth aws.Auth, method, path string, params map[string]string, host string) {
--	sign(auth, method, path, params, host)
+-	return res
 -}
 -
--func fixedTime() time.Time {
--	return time.Date(2012, 1, 1, 0, 0, 0, 0, time.UTC)
+-// UpdateOptsBuilder allows extensions to add additional parameters to the
+-// Update request.
+-type UpdateOptsBuilder interface {
+-	ToSubnetUpdateMap() (map[string]interface{}, error)
 -}
 -
--func FakeTime(fakeIt bool) {
--	if fakeIt {
--		timeNow = fixedTime
--	} else {
--		timeNow = time.Now
--	}
+-// UpdateOpts represents the attributes used when updating an existing subnet.
+-type UpdateOpts struct {
+-	Name           string
+-	GatewayIP      string
+-	DNSNameservers []string
+-	HostRoutes     []HostRoute
+-	EnableDHCP     *bool
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/responses_test.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/responses_test.go
-deleted file mode 100644
-index 0a4dbb3..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/responses_test.go
-+++ /dev/null
-@@ -1,854 +0,0 @@
--package ec2_test
--
--var ErrorDump = `
--<?xml version="1.0" encoding="UTF-8"?>
--<Response><Errors><Error><Code>UnsupportedOperation</Code>
--<Message>AMIs with an instance-store root device are not supported for the instance type 't1.micro'.</Message>
--</Error></Errors><RequestID>0503f4e9-bbd6-483c-b54f-c4ae9f3b30f4</RequestID></Response>
--`
--
--// http://goo.gl/Mcm3b
--var RunInstancesExample = `
--<RunInstancesResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
--  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--  <reservationId>r-47a5402e</reservationId>
--  <ownerId>999988887777</ownerId>
--  <groupSet>
--      <item>
--          <groupId>sg-67ad940e</groupId>
--          <groupName>default</groupName>
--      </item>
--  </groupSet>
--  <instancesSet>
--    <item>
--      <instanceId>i-2ba64342</instanceId>
--      <imageId>ami-60a54009</imageId>
--      <instanceState>
--        <code>0</code>
--        <name>pending</name>
--      </instanceState>
--      <privateDnsName></privateDnsName>
--      <dnsName></dnsName>
--      <keyName>example-key-name</keyName>
--      <amiLaunchIndex>0</amiLaunchIndex>
--      <instanceType>m1.small</instanceType>
--      <launchTime>2007-08-07T11:51:50.000Z</launchTime>
--      <placement>
--        <availabilityZone>us-east-1b</availabilityZone>
--      </placement>
--      <monitoring>
--        <state>enabled</state>
--      </monitoring>
--      <virtualizationType>paravirtual</virtualizationType>
--      <clientToken/>
--      <tagSet/>
--      <hypervisor>xen</hypervisor>
--    </item>
--    <item>
--      <instanceId>i-2bc64242</instanceId>
--      <imageId>ami-60a54009</imageId>
--      <instanceState>
--        <code>0</code>
--        <name>pending</name>
--      </instanceState>
--      <privateDnsName></privateDnsName>
--      <dnsName></dnsName>
--      <keyName>example-key-name</keyName>
--      <amiLaunchIndex>1</amiLaunchIndex>
--      <instanceType>m1.small</instanceType>
--      <launchTime>2007-08-07T11:51:50.000Z</launchTime>
--      <placement>
--         <availabilityZone>us-east-1b</availabilityZone>
--      </placement>
--      <monitoring>
--        <state>enabled</state>
--      </monitoring>
--      <virtualizationType>paravirtual</virtualizationType>
--      <clientToken/>
--      <tagSet/>
--      <hypervisor>xen</hypervisor>
--    </item>
--    <item>
--      <instanceId>i-2be64332</instanceId>
--      <imageId>ami-60a54009</imageId>
--      <instanceState>
--        <code>0</code>
--        <name>pending</name>
--      </instanceState>
--      <privateDnsName></privateDnsName>
--      <dnsName></dnsName>
--      <keyName>example-key-name</keyName>
--      <amiLaunchIndex>2</amiLaunchIndex>
--      <instanceType>m1.small</instanceType>
--      <launchTime>2007-08-07T11:51:50.000Z</launchTime>
--      <placement>
--         <availabilityZone>us-east-1b</availabilityZone>
--      </placement>
--      <monitoring>
--        <state>enabled</state>
--      </monitoring>
--      <virtualizationType>paravirtual</virtualizationType>
--      <clientToken/>
--      <tagSet/>
--      <hypervisor>xen</hypervisor>
--    </item>
--  </instancesSet>
--</RunInstancesResponse>
--`
 -
--// http://goo.gl/GRZgCD
--var RequestSpotInstancesExample = `
--<RequestSpotInstancesResponse xmlns="http://ec2.amazonaws.com/doc/2014-02-01/">
--  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--  <spotInstanceRequestSet>
--    <item>
--      <spotInstanceRequestId>sir-1a2b3c4d</spotInstanceRequestId>
--      <spotPrice>0.5</spotPrice>
--      <type>one-time</type>
--      <state>open</state>
--      <status>
--        <code>pending-evaluation</code>
--        <updateTime>2008-05-07T12:51:50.000Z</updateTime>
--        <message>Your Spot request has been submitted for review, and is pending evaluation.</message>
--      </status>
--      <availabilityZoneGroup>MyAzGroup</availabilityZoneGroup>
--      <launchSpecification>
--        <imageId>ami-1a2b3c4d</imageId>
--        <keyName>gsg-keypair</keyName>
--        <groupSet>
--          <item>
--            <groupId>sg-1a2b3c4d</groupId>
--            <groupName>websrv</groupName>
--          </item>
--        </groupSet>
--        <instanceType>m1.small</instanceType>
--        <blockDeviceMapping/>
--        <monitoring>
--          <enabled>false</enabled>
--        </monitoring>
--        <ebsOptimized>false</ebsOptimized>
--      </launchSpecification>
--      <createTime>YYYY-MM-DDTHH:MM:SS.000Z</createTime>
--      <productDescription>Linux/UNIX</productDescription>
--    </item>
-- </spotInstanceRequestSet>
--</RequestSpotInstancesResponse>
--`
+-// ToSubnetUpdateMap casts an UpdateOpts struct to a map.
+-func (opts UpdateOpts) ToSubnetUpdateMap() (map[string]interface{}, error) {
+-	s := make(map[string]interface{})
 -
--// http://goo.gl/KsKJJk
--var DescribeSpotRequestsExample = `
--<DescribeSpotInstanceRequestsResponse xmlns="http://ec2.amazonaws.com/doc/2014-02-01/">
--  <requestId>b1719f2a-5334-4479-b2f1-26926EXAMPLE</requestId>
--  <spotInstanceRequestSet>
--    <item>
--      <spotInstanceRequestId>sir-1a2b3c4d</spotInstanceRequestId>
--      <spotPrice>0.5</spotPrice>
--      <type>one-time</type>
--      <state>active</state>
--      <status>
--        <code>fulfilled</code>
--        <updateTime>2008-05-07T12:51:50.000Z</updateTime>
--        <message>Your Spot request is fulfilled.</message>
--      </status>
--      <launchSpecification>
--        <imageId>ami-1a2b3c4d</imageId>
--        <keyName>gsg-keypair</keyName>
--        <groupSet>
--          <item>
--            <groupId>sg-1a2b3c4d</groupId>
--            <groupName>websrv</groupName>
--          </item>
--        </groupSet>
--        <instanceType>m1.small</instanceType>
--        <monitoring>
--          <enabled>false</enabled>
--        </monitoring>
--        <ebsOptimized>false</ebsOptimized>
--      </launchSpecification>
--      <instanceId>i-1a2b3c4d</instanceId>
--      <createTime>YYYY-MM-DDTHH:MM:SS.000Z</createTime>
--      <productDescription>Linux/UNIX</productDescription>
--      <launchedAvailabilityZone>us-east-1a</launchedAvailabilityZone>
--    </item>
--  </spotInstanceRequestSet>
--</DescribeSpotInstanceRequestsResponse>
--`
+-	if opts.EnableDHCP != nil {
+-		s["enable_dhcp"] = &opts.EnableDHCP
+-	}
+-	if opts.Name != "" {
+-		s["name"] = opts.Name
+-	}
+-	if opts.GatewayIP != "" {
+-		s["gateway_ip"] = opts.GatewayIP
+-	}
+-	if len(opts.DNSNameservers) != 0 {
+-		s["dns_nameservers"] = opts.DNSNameservers
+-	}
+-	if len(opts.HostRoutes) != 0 {
+-		s["host_routes"] = opts.HostRoutes
+-	}
 -
--// http://goo.gl/DcfFgJ
--var CancelSpotRequestsExample = `
--<CancelSpotInstanceRequestsResponse xmlns="http://ec2.amazonaws.com/doc/2014-02-01/">
--  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--  <spotInstanceRequestSet>
--    <item>
--      <spotInstanceRequestId>sir-1a2b3c4d</spotInstanceRequestId>
--      <state>cancelled</state>
--    </item>
--  </spotInstanceRequestSet>
--</CancelSpotInstanceRequestsResponse>
--`
+-	return map[string]interface{}{"subnet": s}, nil
+-}
 -
--// http://goo.gl/3BKHj
--var TerminateInstancesExample = `
--<TerminateInstancesResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
--  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--  <instancesSet>
--    <item>
--      <instanceId>i-3ea74257</instanceId>
--      <currentState>
--        <code>32</code>
--        <name>shutting-down</name>
--      </currentState>
--      <previousState>
--        <code>16</code>
--        <name>running</name>
--      </previousState>
--    </item>
--  </instancesSet>
--</TerminateInstancesResponse>
--`
+-// Update accepts a UpdateOpts struct and updates an existing subnet using the
+-// values provided.
+-func Update(c *gophercloud.ServiceClient, id string, opts UpdateOptsBuilder) UpdateResult {
+-	var res UpdateResult
 -
--// http://goo.gl/mLbmw
--var DescribeInstancesExample1 = `
--<DescribeInstancesResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
--  <requestId>98e3c9a4-848c-4d6d-8e8a-b1bdEXAMPLE</requestId>
--  <reservationSet>
--    <item>
--      <reservationId>r-b27e30d9</reservationId>
--      <ownerId>999988887777</ownerId>
--      <groupSet>
--        <item>
--          <groupId>sg-67ad940e</groupId>
--          <groupName>default</groupName>
--        </item>
--      </groupSet>
--      <instancesSet>
--        <item>
--          <instanceId>i-c5cd56af</instanceId>
--          <imageId>ami-1a2b3c4d</imageId>
--          <instanceState>
--            <code>16</code>
--            <name>running</name>
--          </instanceState>
--          <privateDnsName>domU-12-31-39-10-56-34.compute-1.internal</privateDnsName>
--          <dnsName>ec2-174-129-165-232.compute-1.amazonaws.com</dnsName>
--          <reason/>
--          <keyName>GSG_Keypair</keyName>
--          <amiLaunchIndex>0</amiLaunchIndex>
--          <productCodes/>
--          <instanceType>m1.small</instanceType>
--          <launchTime>2010-08-17T01:15:18.000Z</launchTime>
--          <placement>
--            <availabilityZone>us-east-1b</availabilityZone>
--            <groupName/>
--          </placement>
--          <kernelId>aki-94c527fd</kernelId>
--          <ramdiskId>ari-96c527ff</ramdiskId>
--          <monitoring>
--            <state>disabled</state>
--          </monitoring>
--          <privateIpAddress>10.198.85.190</privateIpAddress>
--          <ipAddress>174.129.165.232</ipAddress>
--          <architecture>i386</architecture>
--          <rootDeviceType>ebs</rootDeviceType>
--          <rootDeviceName>/dev/sda1</rootDeviceName>
--          <blockDeviceMapping>
--            <item>
--              <deviceName>/dev/sda1</deviceName>
--              <ebs>
--                <volumeId>vol-a082c1c9</volumeId>
--                <status>attached</status>
--                <attachTime>2010-08-17T01:15:21.000Z</attachTime>
--                <deleteOnTermination>false</deleteOnTermination>
--              </ebs>
--            </item>
--          </blockDeviceMapping>
--          <instanceLifecycle>spot</instanceLifecycle>
--          <spotInstanceRequestId>sir-7a688402</spotInstanceRequestId>
--          <virtualizationType>paravirtual</virtualizationType>
--          <clientToken/>
--          <tagSet/>
--          <hypervisor>xen</hypervisor>
--       </item>
--      </instancesSet>
--      <requesterId>854251627541</requesterId>
--    </item>
--    <item>
--      <reservationId>r-b67e30dd</reservationId>
--      <ownerId>999988887777</ownerId>
--      <groupSet>
--        <item>
--          <groupId>sg-67ad940e</groupId>
--          <groupName>default</groupName>
--        </item>
--      </groupSet>
--      <instancesSet>
--        <item>
--          <instanceId>i-d9cd56b3</instanceId>
--          <imageId>ami-1a2b3c4d</imageId>
--          <instanceState>
--            <code>16</code>
--            <name>running</name>
--          </instanceState>
--          <privateDnsName>domU-12-31-39-10-54-E5.compute-1.internal</privateDnsName>
--          <dnsName>ec2-184-73-58-78.compute-1.amazonaws.com</dnsName>
--          <reason/>
--          <keyName>GSG_Keypair</keyName>
--          <amiLaunchIndex>0</amiLaunchIndex>
--          <productCodes/>
--          <instanceType>m1.large</instanceType>
--          <launchTime>2010-08-17T01:15:19.000Z</launchTime>
--          <placement>
--            <availabilityZone>us-east-1b</availabilityZone>
--            <groupName/>
--          </placement>
--          <kernelId>aki-94c527fd</kernelId>
--          <ramdiskId>ari-96c527ff</ramdiskId>
--          <monitoring>
--            <state>disabled</state>
--          </monitoring>
--          <privateIpAddress>10.198.87.19</privateIpAddress>
--          <ipAddress>184.73.58.78</ipAddress>
--          <architecture>i386</architecture>
--          <rootDeviceType>ebs</rootDeviceType>
--          <rootDeviceName>/dev/sda1</rootDeviceName>
--          <blockDeviceMapping>
--            <item>
--              <deviceName>/dev/sda1</deviceName>
--              <ebs>
--                <volumeId>vol-a282c1cb</volumeId>
--                <status>attached</status>
--                <attachTime>2010-08-17T01:15:23.000Z</attachTime>
--                <deleteOnTermination>false</deleteOnTermination>
--              </ebs>
--            </item>
--          </blockDeviceMapping>
--          <instanceLifecycle>spot</instanceLifecycle>
--          <spotInstanceRequestId>sir-55a3aa02</spotInstanceRequestId>
--          <virtualizationType>paravirtual</virtualizationType>
--          <clientToken/>
--          <tagSet/>
--          <hypervisor>xen</hypervisor>
--       </item>
--      </instancesSet>
--      <requesterId>854251627541</requesterId>
--    </item>
--  </reservationSet>
--</DescribeInstancesResponse>
--`
+-	reqBody, err := opts.ToSubnetUpdateMap()
+-	if err != nil {
+-		res.Err = err
+-		return res
+-	}
 -
--// http://goo.gl/mLbmw
--var DescribeInstancesExample2 = `
--<DescribeInstancesResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
--  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--  <reservationSet>
--    <item>
--      <reservationId>r-bc7e30d7</reservationId>
--      <ownerId>999988887777</ownerId>
--      <groupSet>
--        <item>
--          <groupId>sg-67ad940e</groupId>
--          <groupName>default</groupName>
--        </item>
--      </groupSet>
--      <instancesSet>
--        <item>
--          <instanceId>i-c7cd56ad</instanceId>
--          <imageId>ami-b232d0db</imageId>
--          <instanceState>
--            <code>16</code>
--            <name>running</name>
--          </instanceState>
--          <privateDnsName>domU-12-31-39-01-76-06.compute-1.internal</privateDnsName>
--          <dnsName>ec2-72-44-52-124.compute-1.amazonaws.com</dnsName>
--          <keyName>GSG_Keypair</keyName>
--          <amiLaunchIndex>0</amiLaunchIndex>
--          <productCodes/>
--          <instanceType>m1.small</instanceType>
--          <launchTime>2010-08-17T01:15:16.000Z</launchTime>
--          <placement>
--              <availabilityZone>us-east-1b</availabilityZone>
--          </placement>
--          <kernelId>aki-94c527fd</kernelId>
--          <ramdiskId>ari-96c527ff</ramdiskId>
--          <monitoring>
--              <state>disabled</state>
--          </monitoring>
--          <privateIpAddress>10.255.121.240</privateIpAddress>
--          <ipAddress>72.44.52.124</ipAddress>
--          <architecture>i386</architecture>
--          <rootDeviceType>ebs</rootDeviceType>
--          <rootDeviceName>/dev/sda1</rootDeviceName>
--          <blockDeviceMapping>
--              <item>
--                 <deviceName>/dev/sda1</deviceName>
--                 <ebs>
--                    <volumeId>vol-a482c1cd</volumeId>
--                    <status>attached</status>
--                    <attachTime>2010-08-17T01:15:26.000Z</attachTime>
--                    <deleteOnTermination>true</deleteOnTermination>
--                </ebs>
--             </item>
--          </blockDeviceMapping>
--          <virtualizationType>paravirtual</virtualizationType>
--          <clientToken/>
--          <tagSet>
--              <item>
--                    <key>webserver</key>
--                    <value></value>
--             </item>
--              <item>
--                    <key>stack</key>
--                    <value>Production</value>
--             </item>
--          </tagSet>
--          <hypervisor>xen</hypervisor>
--        </item>
--      </instancesSet>
--    </item>
--  </reservationSet>
--</DescribeInstancesResponse>
--`
+-	_, res.Err = perigee.Request("PUT", updateURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{200, 201},
+-	})
 -
--// http://goo.gl/cxU41
--var CreateImageExample = `
--<CreateImageResponse xmlns="http://ec2.amazonaws.com/doc/2013-02-01/">
--   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--   <imageId>ami-4fa54026</imageId>
--</CreateImageResponse>
--`
+-	return res
+-}
 -
--// http://goo.gl/V0U25
--var DescribeImagesExample = `
--<DescribeImagesResponse xmlns="http://ec2.amazonaws.com/doc/2012-08-15/">
--         <requestId>4a4a27a2-2e7c-475d-b35b-ca822EXAMPLE</requestId>
--    <imagesSet>
--        <item>
--            <imageId>ami-a2469acf</imageId>
--            <imageLocation>aws-marketplace/example-marketplace-amzn-ami.1</imageLocation>
--            <imageState>available</imageState>
--            <imageOwnerId>123456789999</imageOwnerId>
--            <isPublic>true</isPublic>
--            <productCodes>
--                <item>
--                    <productCode>a1b2c3d4e5f6g7h8i9j10k11</productCode>
--                    <type>marketplace</type>
--                </item>
--            </productCodes>
--            <architecture>i386</architecture>
--            <imageType>machine</imageType>
--            <kernelId>aki-805ea7e9</kernelId>
--            <imageOwnerAlias>aws-marketplace</imageOwnerAlias>
--            <name>example-marketplace-amzn-ami.1</name>
--            <description>Amazon Linux AMI i386 EBS</description>
--            <rootDeviceType>ebs</rootDeviceType>
--            <rootDeviceName>/dev/sda1</rootDeviceName>
--            <blockDeviceMapping>
--                <item>
--                    <deviceName>/dev/sda1</deviceName>
--                    <ebs>
--                        <snapshotId>snap-787e9403</snapshotId>
--                        <volumeSize>8</volumeSize>
--                        <deleteOnTermination>true</deleteOnTermination>
--                    </ebs>
--                </item>
--            </blockDeviceMapping>
--            <virtualizationType>paravirtual</virtualizationType>
--            <hypervisor>xen</hypervisor>
--        </item>
--    </imagesSet>
--</DescribeImagesResponse>
--`
+-// Delete accepts a unique ID and deletes the subnet associated with it.
+-func Delete(c *gophercloud.ServiceClient, id string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", deleteURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{204},
+-	})
+-	return res
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/requests_test.go
+deleted file mode 100644
+index 987064a..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/requests_test.go
++++ /dev/null
+@@ -1,362 +0,0 @@
+-package subnets
 -
--// http://goo.gl/bHO3z
--var ImageAttributeExample = `
--<DescribeImageAttributeResponse xmlns="http://ec2.amazonaws.com/doc/2013-07-15/">
--   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--   <imageId>ami-61a54008</imageId>
--   <launchPermission>
--      <item>
--         <group>all</group>
--      </item>
--      <item>
--         <userId>495219933132</userId>
--      </item>
--   </launchPermission>
--</DescribeImageAttributeResponse>
--`
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--// http://goo.gl/ttcda
--var CreateSnapshotExample = `
--<CreateSnapshotResponse xmlns="http://ec2.amazonaws.com/doc/2012-10-01/">
--  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--  <snapshotId>snap-78a54011</snapshotId>
--  <volumeId>vol-4d826724</volumeId>
--  <status>pending</status>
--  <startTime>2008-05-07T12:51:50.000Z</startTime>
--  <progress>60%</progress>
--  <ownerId>111122223333</ownerId>
--  <volumeSize>10</volumeSize>
--  <description>Daily Backup</description>
--</CreateSnapshotResponse>
--`
+-	fake "github.com/rackspace/gophercloud/openstack/networking/v2/common"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--// http://goo.gl/vwU1y
--var DeleteSnapshotExample = `
--<DeleteSnapshotResponse xmlns="http://ec2.amazonaws.com/doc/2012-10-01/">
--  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--  <return>true</return>
--</DeleteSnapshotResponse>
--`
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--// http://goo.gl/nkovs
--var DescribeSnapshotsExample = `
--<DescribeSnapshotsResponse xmlns="http://ec2.amazonaws.com/doc/2012-10-01/">
--   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--   <snapshotSet>
--      <item>
--         <snapshotId>snap-1a2b3c4d</snapshotId>
--         <volumeId>vol-8875daef</volumeId>
--         <status>pending</status>
--         <startTime>2010-07-29T04:12:01.000Z</startTime>
--         <progress>30%</progress>
--         <ownerId>111122223333</ownerId>
--         <volumeSize>15</volumeSize>
--         <description>Daily Backup</description>
--         <tagSet>
--            <item>
--               <key>Purpose</key>
--               <value>demo_db_14_backup</value>
--            </item>
--         </tagSet>
--      </item>
--   </snapshotSet>
--</DescribeSnapshotsResponse>
--`
+-	th.Mux.HandleFunc("/v2.0/subnets", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--// http://goo.gl/YUjO4G
--var ModifyImageAttributeExample = `
--<ModifyImageAttributeResponse xmlns="http://ec2.amazonaws.com/doc/2013-06-15/">
--  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--  <return>true</return>
--</ModifyImageAttributeResponse>
--`
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--// http://goo.gl/hQwPCK
--var CopyImageExample = `
--<CopyImageResponse xmlns="http://ec2.amazonaws.com/doc/2013-06-15/">
--   <requestId>60bc441d-fa2c-494d-b155-5d6a3EXAMPLE</requestId>
--   <imageId>ami-4d3c2b1a</imageId>
--</CopyImageResponse>
--`
+-		fmt.Fprintf(w, `
+-{
+-    "subnets": [
+-        {
+-            "name": "private-subnet",
+-            "enable_dhcp": true,
+-            "network_id": "db193ab3-96e3-4cb3-8fc5-05f4296d0324",
+-            "tenant_id": "26a7980765d0414dbc1fc1f88cdb7e6e",
+-            "dns_nameservers": [],
+-            "allocation_pools": [
+-                {
+-                    "start": "10.0.0.2",
+-                    "end": "10.0.0.254"
+-                }
+-            ],
+-            "host_routes": [],
+-            "ip_version": 4,
+-            "gateway_ip": "10.0.0.1",
+-            "cidr": "10.0.0.0/24",
+-            "id": "08eae331-0402-425a-923c-34f7cfe39c1b"
+-        },
+-        {
+-            "name": "my_subnet",
+-            "enable_dhcp": true,
+-            "network_id": "d32019d3-bc6e-4319-9c1d-6722fc136a22",
+-            "tenant_id": "4fd44f30292945e481c7b8a0c8908869",
+-            "dns_nameservers": [],
+-            "allocation_pools": [
+-                {
+-                    "start": "192.0.0.2",
+-                    "end": "192.255.255.254"
+-                }
+-            ],
+-            "host_routes": [],
+-            "ip_version": 4,
+-            "gateway_ip": "192.0.0.1",
+-            "cidr": "192.0.0.0/8",
+-            "id": "54d6f61d-db07-451c-9ab3-b9609b6b6f0b"
+-        }
+-    ]
+-}
+-      `)
+-	})
 -
--var CreateKeyPairExample = `
--<CreateKeyPairResponse xmlns="http://ec2.amazonaws.com/doc/2013-02-01/">
--  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--  <keyName>foo</keyName>
--  <keyFingerprint>
--     00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00:00
--  </keyFingerprint>
--  <keyMaterial>---- BEGIN RSA PRIVATE KEY ----
--MIICiTCCAfICCQD6m7oRw0uXOjANBgkqhkiG9w0BAQUFADCBiDELMAkGA1UEBhMC
--VVMxCzAJBgNVBAgTAldBMRAwDgYDVQQHEwdTZWF0dGxlMQ8wDQYDVQQKEwZBbWF6
--b24xFDASBgNVBAsTC0lBTSBDb25zb2xlMRIwEAYDVQQDEwlUZXN0Q2lsYWMxHzAd
--BgkqhkiG9w0BCQEWEG5vb25lQGFtYXpvbi5jb20wHhcNMTEwNDI1MjA0NTIxWhcN
--MTIwNDI0MjA0NTIxWjCBiDELMAkGA1UEBhMCVVMxCzAJBgNVBAgTAldBMRAwDgYD
--VQQHEwdTZWF0dGxlMQ8wDQYDVQQKEwZBbWF6b24xFDASBgNVBAsTC0lBTSBDb25z
--b2xlMRIwEAYDVQQDEwlUZXN0Q2lsYWMxHzAdBgkqhkiG9w0BCQEWEG5vb25lQGFt
--YXpvbi5jb20wgZ8wDQYJKoZIhvcNAQEBBQADgY0AMIGJAoGBAMaK0dn+a4GmWIWJ
--21uUSfwfEvySWtC2XADZ4nB+BLYgVIk60CpiwsZ3G93vUEIO3IyNoH/f0wYK8m9T
--rDHudUZg3qX4waLG5M43q7Wgc/MbQITxOUSQv7c7ugFFDzQGBzZswY6786m86gpE
--Ibb3OhjZnzcvQAaRHhdlQWIMm2nrAgMBAAEwDQYJKoZIhvcNAQEFBQADgYEAtCu4
--nUhVVxYUntneD9+h8Mg9q6q+auNKyExzyLwaxlAoo7TJHidbtS4J5iNmZgXL0Fkb
--FFBjvSfpJIlJ00zbhNYS5f6GuoEDmFJl0ZxBHjJnyp378OD8uTs7fLvjx79LjSTb
--NYiytVbZPQUQ5Yaxu2jXnimvw3rrszlaEXAMPLE=
-------END RSA PRIVATE KEY-----
--</keyMaterial>
--</CreateKeyPairResponse>
--`
+-	count := 0
 -
--var DeleteKeyPairExample = `
--<DeleteKeyPairResponse xmlns="http://ec2.amazonaws.com/doc/2013-02-01/">
--  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--  <return>true</return>
--</DeleteKeyPairResponse>
--`
+-	List(fake.ServiceClient(), ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractSubnets(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract subnets: %v", err)
+-			return false, nil
+-		}
+-
+-		expected := []Subnet{
+-			Subnet{
+-				Name:           "private-subnet",
+-				EnableDHCP:     true,
+-				NetworkID:      "db193ab3-96e3-4cb3-8fc5-05f4296d0324",
+-				TenantID:       "26a7980765d0414dbc1fc1f88cdb7e6e",
+-				DNSNameservers: []string{},
+-				AllocationPools: []AllocationPool{
+-					AllocationPool{
+-						Start: "10.0.0.2",
+-						End:   "10.0.0.254",
+-					},
+-				},
+-				HostRoutes: []HostRoute{},
+-				IPVersion:  4,
+-				GatewayIP:  "10.0.0.1",
+-				CIDR:       "10.0.0.0/24",
+-				ID:         "08eae331-0402-425a-923c-34f7cfe39c1b",
+-			},
+-			Subnet{
+-				Name:           "my_subnet",
+-				EnableDHCP:     true,
+-				NetworkID:      "d32019d3-bc6e-4319-9c1d-6722fc136a22",
+-				TenantID:       "4fd44f30292945e481c7b8a0c8908869",
+-				DNSNameservers: []string{},
+-				AllocationPools: []AllocationPool{
+-					AllocationPool{
+-						Start: "192.0.0.2",
+-						End:   "192.255.255.254",
+-					},
+-				},
+-				HostRoutes: []HostRoute{},
+-				IPVersion:  4,
+-				GatewayIP:  "192.0.0.1",
+-				CIDR:       "192.0.0.0/8",
+-				ID:         "54d6f61d-db07-451c-9ab3-b9609b6b6f0b",
+-			},
+-		}
 -
--// http://goo.gl/Eo7Yl
--var CreateSecurityGroupExample = `
--<CreateSecurityGroupResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
--   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--   <return>true</return>
--   <groupId>sg-67ad940e</groupId>
--</CreateSecurityGroupResponse>
--`
+-		th.CheckDeepEquals(t, expected, actual)
 -
--// http://goo.gl/k12Uy
--var DescribeSecurityGroupsExample = `
--<DescribeSecurityGroupsResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
--  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--  <securityGroupInfo>
--    <item>
--      <ownerId>999988887777</ownerId>
--      <groupName>WebServers</groupName>
--      <groupId>sg-67ad940e</groupId>
--      <groupDescription>Web Servers</groupDescription>
--      <ipPermissions>
--        <item>
--           <ipProtocol>tcp</ipProtocol>
--           <fromPort>80</fromPort>
--           <toPort>80</toPort>
--           <groups/>
--           <ipRanges>
--             <item>
--               <cidrIp>0.0.0.0/0</cidrIp>
--             </item>
--           </ipRanges>
--        </item>
--      </ipPermissions>
--    </item>
--    <item>
--      <ownerId>999988887777</ownerId>
--      <groupName>RangedPortsBySource</groupName>
--      <groupId>sg-76abc467</groupId>
--      <groupDescription>Group A</groupDescription>
--      <ipPermissions>
--        <item>
--           <ipProtocol>tcp</ipProtocol>
--           <fromPort>6000</fromPort>
--           <toPort>7000</toPort>
--           <groups/>
--           <ipRanges/>
--        </item>
--      </ipPermissions>
--    </item>
--  </securityGroupInfo>
--</DescribeSecurityGroupsResponse>
--`
+-		return true, nil
+-	})
 -
--// A dump which includes groups within ip permissions.
--var DescribeSecurityGroupsDump = `
--<?xml version="1.0" encoding="UTF-8"?>
--<DescribeSecurityGroupsResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
--    <requestId>87b92b57-cc6e-48b2-943f-f6f0e5c9f46c</requestId>
--    <securityGroupInfo>
--        <item>
--            <ownerId>12345</ownerId>
--            <groupName>default</groupName>
--            <groupDescription>default group</groupDescription>
--            <ipPermissions>
--                <item>
--                    <ipProtocol>icmp</ipProtocol>
--                    <fromPort>-1</fromPort>
--                    <toPort>-1</toPort>
--                    <groups>
--                        <item>
--                            <userId>12345</userId>
--                            <groupName>default</groupName>
--                            <groupId>sg-67ad940e</groupId>
--                        </item>
--                    </groups>
--                    <ipRanges/>
--                </item>
--                <item>
--                    <ipProtocol>tcp</ipProtocol>
--                    <fromPort>0</fromPort>
--                    <toPort>65535</toPort>
--                    <groups>
--                        <item>
--                            <userId>12345</userId>
--                            <groupName>other</groupName>
--                            <groupId>sg-76abc467</groupId>
--                        </item>
--                    </groups>
--                    <ipRanges/>
--                </item>
--            </ipPermissions>
--        </item>
--    </securityGroupInfo>
--</DescribeSecurityGroupsResponse>
--`
+-	if count != 1 {
+-		t.Errorf("Expected 1 page, got %d", count)
+-	}
+-}
 -
--// http://goo.gl/QJJDO
--var DeleteSecurityGroupExample = `
--<DeleteSecurityGroupResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
--   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--   <return>true</return>
--</DeleteSecurityGroupResponse>
--`
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--// http://goo.gl/u2sDJ
--var AuthorizeSecurityGroupIngressExample = `
--<AuthorizeSecurityGroupIngressResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
--  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--  <return>true</return>
--</AuthorizeSecurityGroupIngressResponse>
--`
+-	th.Mux.HandleFunc("/v2.0/subnets/54d6f61d-db07-451c-9ab3-b9609b6b6f0b", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--// http://goo.gl/u2sDJ
--var AuthorizeSecurityGroupEgressExample = `
--<AuthorizeSecurityGroupEgressResponse xmlns="http://ec2.amazonaws.com/doc/2014-06-15/">
--   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--   <return>true</return>
--</AuthorizeSecurityGroupEgressResponse>
--`
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--// http://goo.gl/Mz7xr
--var RevokeSecurityGroupIngressExample = `
--<RevokeSecurityGroupIngressResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
--  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--  <return>true</return>
--</RevokeSecurityGroupIngressResponse>
--`
+-		fmt.Fprintf(w, `
+-{
+-    "subnet": {
+-        "name": "my_subnet",
+-        "enable_dhcp": true,
+-        "network_id": "d32019d3-bc6e-4319-9c1d-6722fc136a22",
+-        "tenant_id": "4fd44f30292945e481c7b8a0c8908869",
+-        "dns_nameservers": [],
+-        "allocation_pools": [
+-            {
+-                "start": "192.0.0.2",
+-                "end": "192.255.255.254"
+-            }
+-        ],
+-        "host_routes": [],
+-        "ip_version": 4,
+-        "gateway_ip": "192.0.0.1",
+-        "cidr": "192.0.0.0/8",
+-        "id": "54d6f61d-db07-451c-9ab3-b9609b6b6f0b"
+-    }
+-}
+-			`)
+-	})
 -
--// http://goo.gl/Vmkqc
--var CreateTagsExample = `
--<CreateTagsResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
--   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--   <return>true</return>
--</CreateTagsResponse>
--`
+-	s, err := Get(fake.ServiceClient(), "54d6f61d-db07-451c-9ab3-b9609b6b6f0b").Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, s.Name, "my_subnet")
+-	th.AssertEquals(t, s.EnableDHCP, true)
+-	th.AssertEquals(t, s.NetworkID, "d32019d3-bc6e-4319-9c1d-6722fc136a22")
+-	th.AssertEquals(t, s.TenantID, "4fd44f30292945e481c7b8a0c8908869")
+-	th.AssertDeepEquals(t, s.DNSNameservers, []string{})
+-	th.AssertDeepEquals(t, s.AllocationPools, []AllocationPool{
+-		AllocationPool{
+-			Start: "192.0.0.2",
+-			End:   "192.255.255.254",
+-		},
+-	})
+-	th.AssertDeepEquals(t, s.HostRoutes, []HostRoute{})
+-	th.AssertEquals(t, s.IPVersion, 4)
+-	th.AssertEquals(t, s.GatewayIP, "192.0.0.1")
+-	th.AssertEquals(t, s.CIDR, "192.0.0.0/8")
+-	th.AssertEquals(t, s.ID, "54d6f61d-db07-451c-9ab3-b9609b6b6f0b")
+-}
 -
--// http://goo.gl/awKeF
--var StartInstancesExample = `
--<StartInstancesResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
--  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--  <instancesSet>
--    <item>
--      <instanceId>i-10a64379</instanceId>
--      <currentState>
--          <code>0</code>
--          <name>pending</name>
--      </currentState>
--      <previousState>
--          <code>80</code>
--          <name>stopped</name>
--      </previousState>
--    </item>
--  </instancesSet>
--</StartInstancesResponse>
--`
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/subnets", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "subnet": {
+-        "network_id": "d32019d3-bc6e-4319-9c1d-6722fc136a22",
+-        "ip_version": 4,
+-        "cidr": "192.168.199.0/24",
+-				"dns_nameservers": ["foo"],
+-				"allocation_pools": [
+-						{
+-								"start": "192.168.199.2",
+-								"end": "192.168.199.254"
+-						}
+-				],
+-				"host_routes": [{"destination":"","nexthop": "bar"}]
+-    }
+-}
+-			`)
 -
--// http://goo.gl/436dJ
--var StopInstancesExample = `
--<StopInstancesResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
--  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--  <instancesSet>
--    <item>
--      <instanceId>i-10a64379</instanceId>
--      <currentState>
--          <code>64</code>
--          <name>stopping</name>
--      </currentState>
--      <previousState>
--          <code>16</code>
--          <name>running</name>
--      </previousState>
--    </item>
--  </instancesSet>
--</StopInstancesResponse>
--`
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
 -
--// http://goo.gl/baoUf
--var RebootInstancesExample = `
--<RebootInstancesResponse xmlns="http://ec2.amazonaws.com/doc/2011-12-15/">
--  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--  <return>true</return>
--</RebootInstancesResponse>
--`
+-		fmt.Fprintf(w, `
+-{
+-    "subnet": {
+-        "name": "",
+-        "enable_dhcp": true,
+-        "network_id": "d32019d3-bc6e-4319-9c1d-6722fc136a22",
+-        "tenant_id": "4fd44f30292945e481c7b8a0c8908869",
+-        "dns_nameservers": [],
+-        "allocation_pools": [
+-            {
+-                "start": "192.168.199.2",
+-                "end": "192.168.199.254"
+-            }
+-        ],
+-        "host_routes": [],
+-        "ip_version": 4,
+-        "gateway_ip": "192.168.199.1",
+-        "cidr": "192.168.199.0/24",
+-        "id": "3b80198d-4f7b-4f77-9ef5-774d54e17126"
+-    }
+-}
+-		`)
+-	})
 -
--// http://goo.gl/9rprDN
--var AllocateAddressExample = `
--<AllocateAddressResponse xmlns="http://ec2.amazonaws.com/doc/2013-10-15/">
--   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--   <publicIp>198.51.100.1</publicIp>
--   <domain>vpc</domain>
--   <allocationId>eipalloc-5723d13e</allocationId>
--</AllocateAddressResponse>
--`
+-	opts := CreateOpts{
+-		NetworkID: "d32019d3-bc6e-4319-9c1d-6722fc136a22",
+-		IPVersion: 4,
+-		CIDR:      "192.168.199.0/24",
+-		AllocationPools: []AllocationPool{
+-			AllocationPool{
+-				Start: "192.168.199.2",
+-				End:   "192.168.199.254",
+-			},
+-		},
+-		DNSNameservers: []string{"foo"},
+-		HostRoutes: []HostRoute{
+-			HostRoute{NextHop: "bar"},
+-		},
+-	}
+-	s, err := Create(fake.ServiceClient(), opts).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, s.Name, "")
+-	th.AssertEquals(t, s.EnableDHCP, true)
+-	th.AssertEquals(t, s.NetworkID, "d32019d3-bc6e-4319-9c1d-6722fc136a22")
+-	th.AssertEquals(t, s.TenantID, "4fd44f30292945e481c7b8a0c8908869")
+-	th.AssertDeepEquals(t, s.DNSNameservers, []string{})
+-	th.AssertDeepEquals(t, s.AllocationPools, []AllocationPool{
+-		AllocationPool{
+-			Start: "192.168.199.2",
+-			End:   "192.168.199.254",
+-		},
+-	})
+-	th.AssertDeepEquals(t, s.HostRoutes, []HostRoute{})
+-	th.AssertEquals(t, s.IPVersion, 4)
+-	th.AssertEquals(t, s.GatewayIP, "192.168.199.1")
+-	th.AssertEquals(t, s.CIDR, "192.168.199.0/24")
+-	th.AssertEquals(t, s.ID, "3b80198d-4f7b-4f77-9ef5-774d54e17126")
+-}
 -
--// http://goo.gl/3Q0oCc
--var ReleaseAddressExample = `
--<ReleaseAddressResponse xmlns="http://ec2.amazonaws.com/doc/2013-10-15/">
--   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--   <return>true</return>
--</ReleaseAddressResponse>
--`
+-func TestRequiredCreateOpts(t *testing.T) {
+-	res := Create(fake.ServiceClient(), CreateOpts{})
+-	if res.Err == nil {
+-		t.Fatalf("Expected error, got none")
+-	}
 -
--// http://goo.gl/uOSQE
--var AssociateAddressExample = `
--<AssociateAddressResponse xmlns="http://ec2.amazonaws.com/doc/2013-10-15/">
--   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--   <return>true</return>
--   <associationId>eipassoc-fc5ca095</associationId>
--</AssociateAddressResponse>
--`
+-	res = Create(fake.ServiceClient(), CreateOpts{NetworkID: "foo"})
+-	if res.Err == nil {
+-		t.Fatalf("Expected error, got none")
+-	}
 -
--// http://goo.gl/LrOa0
--var DisassociateAddressExample = `
--<DisassociateAddressResponse xmlns="http://ec2.amazonaws.com/doc/2013-10-15/">
--   <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--   <return>true</return>
--</DisassociateAddressResponse>
--`
+-	res = Create(fake.ServiceClient(), CreateOpts{NetworkID: "foo", CIDR: "bar", IPVersion: 40})
+-	if res.Err == nil {
+-		t.Fatalf("Expected error, got none")
+-	}
+-}
 -
--// http://goo.gl/icuXh5
--var ModifyInstanceExample = `
--<ModifyImageAttributeResponse xmlns="http://ec2.amazonaws.com/doc/2013-06-15/">
--  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--  <return>true</return>
--</ModifyImageAttributeResponse>
--`
+-func TestUpdate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/subnets/08eae331-0402-425a-923c-34f7cfe39c1b", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "subnet": {
+-        "name": "my_new_subnet",
+-				"dns_nameservers": ["foo"],
+-				"host_routes": [{"destination":"","nexthop": "bar"}]
+-    }
+-}
+-		`)
 -
--var CreateVpcExample = `
--<CreateVpcResponse xmlns="http://ec2.amazonaws.com/doc/2014-06-15/">
--   <requestId>7a62c49f-347e-4fc4-9331-6e8eEXAMPLE</requestId>
--   <vpc>
--      <vpcId>vpc-1a2b3c4d</vpcId>
--      <state>pending</state>
--      <cidrBlock>10.0.0.0/16</cidrBlock>
--      <dhcpOptionsId>dopt-1a2b3c4d2</dhcpOptionsId>
--      <instanceTenancy>default</instanceTenancy>
--      <tagSet/>
--   </vpc>
--</CreateVpcResponse>
--`
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
 -
--var DescribeVpcsExample = `
--<DescribeVpcsResponse xmlns="http://ec2.amazonaws.com/doc/2014-06-15/">
--  <requestId>7a62c49f-347e-4fc4-9331-6e8eEXAMPLE</requestId>
--  <vpcSet>
--    <item>
--      <vpcId>vpc-1a2b3c4d</vpcId>
--      <state>available</state>
--      <cidrBlock>10.0.0.0/23</cidrBlock>
--      <dhcpOptionsId>dopt-7a8b9c2d</dhcpOptionsId>
--      <instanceTenancy>default</instanceTenancy>
--      <isDefault>false</isDefault>
--      <tagSet/>
--    </item>
--  </vpcSet>
--</DescribeVpcsResponse>
--`
+-		fmt.Fprintf(w, `
+-{
+-    "subnet": {
+-        "name": "my_new_subnet",
+-        "enable_dhcp": true,
+-        "network_id": "db193ab3-96e3-4cb3-8fc5-05f4296d0324",
+-        "tenant_id": "26a7980765d0414dbc1fc1f88cdb7e6e",
+-        "dns_nameservers": [],
+-        "allocation_pools": [
+-            {
+-                "start": "10.0.0.2",
+-                "end": "10.0.0.254"
+-            }
+-        ],
+-        "host_routes": [],
+-        "ip_version": 4,
+-        "gateway_ip": "10.0.0.1",
+-        "cidr": "10.0.0.0/24",
+-        "id": "08eae331-0402-425a-923c-34f7cfe39c1b"
+-    }
+-}
+-	`)
+-	})
 -
--var CreateSubnetExample = `
--<CreateSubnetResponse xmlns="http://ec2.amazonaws.com/doc/2014-06-15/">
--  <requestId>7a62c49f-347e-4fc4-9331-6e8eEXAMPLE</requestId>
--  <subnet>
--    <subnetId>subnet-9d4a7b6c</subnetId>
--    <state>pending</state>
--    <vpcId>vpc-1a2b3c4d</vpcId>
--    <cidrBlock>10.0.1.0/24</cidrBlock>
--    <availableIpAddressCount>251</availableIpAddressCount>
--    <availabilityZone>us-east-1a</availabilityZone>
--    <tagSet/>
--  </subnet>
--</CreateSubnetResponse>
--`
+-	opts := UpdateOpts{
+-		Name:           "my_new_subnet",
+-		DNSNameservers: []string{"foo"},
+-		HostRoutes: []HostRoute{
+-			HostRoute{NextHop: "bar"},
+-		},
+-	}
+-	s, err := Update(fake.ServiceClient(), "08eae331-0402-425a-923c-34f7cfe39c1b", opts).Extract()
+-	th.AssertNoErr(t, err)
 -
--// http://goo.gl/r6ZCPm
--var ResetImageAttributeExample = `
--<ResetImageAttributeResponse xmlns="http://ec2.amazonaws.com/doc/2014-06-15/">
--  <requestId>59dbff89-35bd-4eac-99ed-be587EXAMPLE</requestId>
--  <return>true</return>
--</ResetImageAttributeResponse>
--`
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/sign.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/sign.go
+-	th.AssertEquals(t, s.Name, "my_new_subnet")
+-	th.AssertEquals(t, s.ID, "08eae331-0402-425a-923c-34f7cfe39c1b")
+-}
+-
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/v2.0/subnets/08eae331-0402-425a-923c-34f7cfe39c1b", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-
+-	res := Delete(fake.ServiceClient(), "08eae331-0402-425a-923c-34f7cfe39c1b")
+-	th.AssertNoErr(t, res.Err)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/results.go
 deleted file mode 100644
-index bffc3c7..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/sign.go
+index 1910f17..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/results.go
 +++ /dev/null
-@@ -1,45 +0,0 @@
--package ec2
+@@ -1,132 +0,0 @@
+-package subnets
 -
 -import (
--	"crypto/hmac"
--	"crypto/sha256"
--	"encoding/base64"
--	"github.com/mitchellh/goamz/aws"
--	"sort"
--	"strings"
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
 -)
 -
--// ----------------------------------------------------------------------------
--// EC2 signing (http://goo.gl/fQmAN)
+-type commonResult struct {
+-	gophercloud.Result
+-}
 -
--var b64 = base64.StdEncoding
+-// Extract is a function that accepts a result and extracts a subnet resource.
+-func (r commonResult) Extract() (*Subnet, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
+-	}
 -
--func sign(auth aws.Auth, method, path string, params map[string]string, host string) {
--	params["AWSAccessKeyId"] = auth.AccessKey
--	params["SignatureVersion"] = "2"
--	params["SignatureMethod"] = "HmacSHA256"
--	if auth.Token != "" {
--		params["SecurityToken"] = auth.Token
+-	var res struct {
+-		Subnet *Subnet `json:"subnet"`
 -	}
 -
--	// AWS specifies that the parameters in a signed request must
--	// be provided in the natural order of the keys. This is distinct
--	// from the natural order of the encoded value of key=value.
--	// Percent and equals affect the sorting order.
--	var keys, sarray []string
--	for k, _ := range params {
--		keys = append(keys, k)
+-	err := mapstructure.Decode(r.Body, &res)
+-
+-	return res.Subnet, err
+-}
+-
+-// CreateResult represents the result of a create operation.
+-type CreateResult struct {
+-	commonResult
+-}
+-
+-// GetResult represents the result of a get operation.
+-type GetResult struct {
+-	commonResult
+-}
+-
+-// UpdateResult represents the result of an update operation.
+-type UpdateResult struct {
+-	commonResult
+-}
+-
+-// DeleteResult represents the result of a delete operation.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
+-}
+-
+-// AllocationPool represents a sub-range of cidr available for dynamic
+-// allocation to ports, e.g. {Start: "10.0.0.2", End: "10.0.0.254"}
+-type AllocationPool struct {
+-	Start string `json:"start"`
+-	End   string `json:"end"`
+-}
+-
+-// HostRoute represents a route that should be used by devices with IPs from
+-// a subnet (not including local subnet route).
+-type HostRoute struct {
+-	DestinationCIDR string `json:"destination"`
+-	NextHop         string `json:"nexthop"`
+-}
+-
+-// Subnet represents a subnet. See package documentation for a top-level
+-// description of what this is.
+-type Subnet struct {
+-	// UUID representing the subnet
+-	ID string `mapstructure:"id" json:"id"`
+-	// UUID of the parent network
+-	NetworkID string `mapstructure:"network_id" json:"network_id"`
+-	// Human-readable name for the subnet. Might not be unique.
+-	Name string `mapstructure:"name" json:"name"`
+-	// IP version, either `4' or `6'
+-	IPVersion int `mapstructure:"ip_version" json:"ip_version"`
+-	// CIDR representing IP range for this subnet, based on IP version
+-	CIDR string `mapstructure:"cidr" json:"cidr"`
+-	// Default gateway used by devices in this subnet
+-	GatewayIP string `mapstructure:"gateway_ip" json:"gateway_ip"`
+-	// DNS name servers used by hosts in this subnet.
+-	DNSNameservers []string `mapstructure:"dns_nameservers" json:"dns_nameservers"`
+-	// Sub-ranges of CIDR available for dynamic allocation to ports. See AllocationPool.
+-	AllocationPools []AllocationPool `mapstructure:"allocation_pools" json:"allocation_pools"`
+-	// Routes that should be used by devices with IPs from this subnet (not including local subnet route).
+-	HostRoutes []HostRoute `mapstructure:"host_routes" json:"host_routes"`
+-	// Specifies whether DHCP is enabled for this subnet or not.
+-	EnableDHCP bool `mapstructure:"enable_dhcp" json:"enable_dhcp"`
+-	// Owner of network. Only admin users can specify a tenant_id other than its own.
+-	TenantID string `mapstructure:"tenant_id" json:"tenant_id"`
+-}
+-
+-// SubnetPage is the page returned by a pager when traversing over a collection
+-// of subnets.
+-type SubnetPage struct {
+-	pagination.LinkedPageBase
+-}
+-
+-// NextPageURL is invoked when a paginated collection of subnets has reached
+-// the end of a page and the pager seeks to traverse over a new one. In order
+-// to do this, it needs to construct the next page's URL.
+-func (p SubnetPage) NextPageURL() (string, error) {
+-	type resp struct {
+-		Links []gophercloud.Link `mapstructure:"subnets_links"`
+-	}
+-
+-	var r resp
+-	err := mapstructure.Decode(p.Body, &r)
+-	if err != nil {
+-		return "", err
 -	}
--	sort.Strings(keys)
--	for _, k := range keys {
--		sarray = append(sarray, aws.Encode(k)+"="+aws.Encode(params[k]))
+-
+-	return gophercloud.ExtractNextURL(r.Links)
+-}
+-
+-// IsEmpty checks whether a SubnetPage struct is empty.
+-func (p SubnetPage) IsEmpty() (bool, error) {
+-	is, err := ExtractSubnets(p)
+-	if err != nil {
+-		return true, nil
 -	}
--	joined := strings.Join(sarray, "&")
--	payload := method + "\n" + host + "\n" + path + "\n" + joined
--	hash := hmac.New(sha256.New, []byte(auth.SecretKey))
--	hash.Write([]byte(payload))
--	signature := make([]byte, b64.EncodedLen(hash.Size()))
--	b64.Encode(signature, hash.Sum(nil))
+-	return len(is) == 0, nil
+-}
 -
--	params["Signature"] = string(signature)
+-// ExtractSubnets accepts a Page struct, specifically a SubnetPage struct,
+-// and extracts the elements into a slice of Subnet structs. In other words,
+-// a generic collection is mapped into a relevant slice.
+-func ExtractSubnets(page pagination.Page) ([]Subnet, error) {
+-	var resp struct {
+-		Subnets []Subnet `mapstructure:"subnets" json:"subnets"`
+-	}
+-
+-	err := mapstructure.Decode(page.(SubnetPage).Body, &resp)
+-
+-	return resp.Subnets, err
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/sign_test.go b/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/sign_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/urls.go
 deleted file mode 100644
-index 86d203e..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/goamz/ec2/sign_test.go
+index 0d02368..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/urls.go
 +++ /dev/null
-@@ -1,68 +0,0 @@
--package ec2_test
+@@ -1,31 +0,0 @@
+-package subnets
+-
+-import "github.com/rackspace/gophercloud"
+-
+-func resourceURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL("subnets", id)
+-}
+-
+-func rootURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL("subnets")
+-}
+-
+-func listURL(c *gophercloud.ServiceClient) string {
+-	return rootURL(c)
+-}
+-
+-func getURL(c *gophercloud.ServiceClient, id string) string {
+-	return resourceURL(c, id)
+-}
+-
+-func createURL(c *gophercloud.ServiceClient) string {
+-	return rootURL(c)
+-}
+-
+-func updateURL(c *gophercloud.ServiceClient, id string) string {
+-	return resourceURL(c, id)
+-}
+-
+-func deleteURL(c *gophercloud.ServiceClient, id string) string {
+-	return resourceURL(c, id)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/urls_test.go
+deleted file mode 100644
+index aeeddf3..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/networking/v2/subnets/urls_test.go
++++ /dev/null
+@@ -1,44 +0,0 @@
+-package subnets
 -
 -import (
--	"github.com/mitchellh/goamz/aws"
--	"github.com/mitchellh/goamz/ec2"
--	. "github.com/motain/gocheck"
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--// EC2 ReST authentication docs: http://goo.gl/fQmAN
+-const endpoint = "http://localhost:57909/"
 -
--var testAuth = aws.Auth{"user", "secret", ""}
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint, ResourceBase: endpoint + "v2.0/"}
+-}
 -
--func (s *S) TestBasicSignature(c *C) {
--	params := map[string]string{}
--	ec2.Sign(testAuth, "GET", "/path", params, "localhost")
--	c.Assert(params["SignatureVersion"], Equals, "2")
--	c.Assert(params["SignatureMethod"], Equals, "HmacSHA256")
--	expected := "6lSe5QyXum0jMVc7cOUz32/52ZnL7N5RyKRk/09yiK4="
--	c.Assert(params["Signature"], Equals, expected)
+-func TestListURL(t *testing.T) {
+-	actual := listURL(endpointClient())
+-	expected := endpoint + "v2.0/subnets"
+-	th.AssertEquals(t, expected, actual)
 -}
 -
--func (s *S) TestParamSignature(c *C) {
--	params := map[string]string{
--		"param1": "value1",
--		"param2": "value2",
--		"param3": "value3",
+-func TestGetURL(t *testing.T) {
+-	actual := getURL(endpointClient(), "foo")
+-	expected := endpoint + "v2.0/subnets/foo"
+-	th.AssertEquals(t, expected, actual)
+-}
+-
+-func TestCreateURL(t *testing.T) {
+-	actual := createURL(endpointClient())
+-	expected := endpoint + "v2.0/subnets"
+-	th.AssertEquals(t, expected, actual)
+-}
+-
+-func TestUpdateURL(t *testing.T) {
+-	actual := updateURL(endpointClient(), "foo")
+-	expected := endpoint + "v2.0/subnets/foo"
+-	th.AssertEquals(t, expected, actual)
+-}
+-
+-func TestDeleteURL(t *testing.T) {
+-	actual := deleteURL(endpointClient(), "foo")
+-	expected := endpoint + "v2.0/subnets/foo"
+-	th.AssertEquals(t, expected, actual)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/doc.go
+deleted file mode 100644
+index f5f894a..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/doc.go
++++ /dev/null
+@@ -1,8 +0,0 @@
+-// Package accounts contains functionality for working with Object Storage
+-// account resources. An account is the top-level resource the object storage
+-// hierarchy: containers belong to accounts, objects belong to containers.
+-//
+-// Another way of thinking of an account is like a namespace for all your
+-// resources. It is synonymous with a project or tenant in other OpenStack
+-// services.
+-package accounts
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/fixtures.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/fixtures.go
+deleted file mode 100644
+index 3dad0c5..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/fixtures.go
++++ /dev/null
+@@ -1,38 +0,0 @@
+-// +build fixtures
+-
+-package accounts
+-
+-import (
+-	"net/http"
+-	"testing"
+-
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
+-
+-// HandleGetAccountSuccessfully creates an HTTP handler at `/` on the test handler mux that
+-// responds with a `Get` response.
+-func HandleGetAccountSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "X-Account-Meta-Gophercloud-Test", "accounts")
+-
+-		w.Header().Set("X-Account-Container-Count", "2")
+-		w.Header().Set("X-Account-Bytes-Used", "14")
+-		w.Header().Set("X-Account-Meta-Subject", "books")
+-
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-}
+-
+-// HandleUpdateAccountSuccessfully creates an HTTP handler at `/` on the test handler mux that
+-// responds with a `Update` response.
+-func HandleUpdateAccountSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "HEAD")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		w.Header().Set("X-Account-Meta-Foo", "bar")
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/requests.go
+deleted file mode 100644
+index e6f5f95..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/requests.go
++++ /dev/null
+@@ -1,106 +0,0 @@
+-package accounts
+-
+-import (
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-)
+-
+-// GetOptsBuilder allows extensions to add additional headers to the Get
+-// request.
+-type GetOptsBuilder interface {
+-	ToAccountGetMap() (map[string]string, error)
+-}
+-
+-// GetOpts is a structure that contains parameters for getting an account's
+-// metadata.
+-type GetOpts struct {
+-	Newest bool `h:"X-Newest"`
+-}
+-
+-// ToAccountGetMap formats a GetOpts into a map[string]string of headers.
+-func (opts GetOpts) ToAccountGetMap() (map[string]string, error) {
+-	return gophercloud.BuildHeaders(opts)
+-}
+-
+-// Get is a function that retrieves an account's metadata. To extract just the
+-// custom metadata, call the ExtractMetadata method on the GetResult. To extract
+-// all the headers that are returned (including the metadata), call the
+-// ExtractHeader method on the GetResult.
+-func Get(c *gophercloud.ServiceClient, opts GetOptsBuilder) GetResult {
+-	var res GetResult
+-	h := c.AuthenticatedHeaders()
+-
+-	if opts != nil {
+-		headers, err := opts.ToAccountGetMap()
+-		if err != nil {
+-			res.Err = err
+-			return res
+-		}
+-
+-		for k, v := range headers {
+-			h[k] = v
+-		}
 -	}
--	ec2.Sign(testAuth, "GET", "/path", params, "localhost")
--	expected := "XWOR4+0lmK8bD8CGDGZ4kfuSPbb2JibLJiCl/OPu1oU="
--	c.Assert(params["Signature"], Equals, expected)
+-
+-	resp, err := perigee.Request("HEAD", getURL(c), perigee.Options{
+-		MoreHeaders: h,
+-		OkCodes:     []int{204},
+-	})
+-	res.Header = resp.HttpResponse.Header
+-	res.Err = err
+-	return res
 -}
 -
--func (s *S) TestManyParams(c *C) {
--	params := map[string]string{
--		"param1":  "value10",
--		"param2":  "value2",
--		"param3":  "value3",
--		"param4":  "value4",
--		"param5":  "value5",
--		"param6":  "value6",
--		"param7":  "value7",
--		"param8":  "value8",
--		"param9":  "value9",
--		"param10": "value1",
+-// UpdateOptsBuilder allows extensions to add additional headers to the Update
+-// request.
+-type UpdateOptsBuilder interface {
+-	ToAccountUpdateMap() (map[string]string, error)
+-}
+-
+-// UpdateOpts is a structure that contains parameters for updating, creating, or
+-// deleting an account's metadata.
+-type UpdateOpts struct {
+-	Metadata          map[string]string
+-	ContentType       string `h:"Content-Type"`
+-	DetectContentType bool   `h:"X-Detect-Content-Type"`
+-	TempURLKey        string `h:"X-Account-Meta-Temp-URL-Key"`
+-	TempURLKey2       string `h:"X-Account-Meta-Temp-URL-Key-2"`
+-}
+-
+-// ToAccountUpdateMap formats an UpdateOpts into a map[string]string of headers.
+-func (opts UpdateOpts) ToAccountUpdateMap() (map[string]string, error) {
+-	headers, err := gophercloud.BuildHeaders(opts)
+-	if err != nil {
+-		return nil, err
 -	}
--	ec2.Sign(testAuth, "GET", "/path", params, "localhost")
--	expected := "di0sjxIvezUgQ1SIL6i+C/H8lL+U0CQ9frLIak8jkVg="
--	c.Assert(params["Signature"], Equals, expected)
+-	for k, v := range opts.Metadata {
+-		headers["X-Account-Meta-"+k] = v
+-	}
+-	return headers, err
 -}
 -
--func (s *S) TestEscaping(c *C) {
--	params := map[string]string{"Nonce": "+ +"}
--	ec2.Sign(testAuth, "GET", "/path", params, "localhost")
--	c.Assert(params["Nonce"], Equals, "+ +")
--	expected := "bqffDELReIqwjg/W0DnsnVUmfLK4wXVLO4/LuG+1VFA="
--	c.Assert(params["Signature"], Equals, expected)
+-// Update is a function that creates, updates, or deletes an account's metadata.
+-// To extract the headers returned, call the Extract method on the UpdateResult.
+-func Update(c *gophercloud.ServiceClient, opts UpdateOptsBuilder) UpdateResult {
+-	var res UpdateResult
+-	h := c.AuthenticatedHeaders()
+-
+-	if opts != nil {
+-		headers, err := opts.ToAccountUpdateMap()
+-		if err != nil {
+-			res.Err = err
+-			return res
+-		}
+-		for k, v := range headers {
+-			h[k] = v
+-		}
+-	}
+-
+-	resp, err := perigee.Request("POST", updateURL(c), perigee.Options{
+-		MoreHeaders: h,
+-		OkCodes:     []int{204},
+-	})
+-	res.Header = resp.HttpResponse.Header
+-	res.Err = err
+-	return res
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/requests_test.go
+deleted file mode 100644
+index d6dc26b..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/requests_test.go
++++ /dev/null
+@@ -1,33 +0,0 @@
+-package accounts
 -
--func (s *S) TestSignatureExample1(c *C) {
--	params := map[string]string{
--		"Timestamp": "2009-02-01T12:53:20+00:00",
--		"Version":   "2007-11-07",
--		"Action":    "ListDomains",
+-import (
+-	"testing"
+-
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
+-
+-var metadata = map[string]string{"gophercloud-test": "accounts"}
+-
+-func TestUpdateAccount(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleGetAccountSuccessfully(t)
+-
+-	options := &UpdateOpts{Metadata: map[string]string{"gophercloud-test": "accounts"}}
+-	res := Update(fake.ServiceClient(), options)
+-	th.AssertNoErr(t, res.Err)
+-}
+-
+-func TestGetAccount(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleUpdateAccountSuccessfully(t)
+-
+-	expected := map[string]string{"Foo": "bar"}
+-	actual, err := Get(fake.ServiceClient(), &GetOpts{}).ExtractMetadata()
+-	if err != nil {
+-		t.Fatalf("Unable to get account metadata: %v", err)
 -	}
--	ec2.Sign(aws.Auth{"access", "secret", ""}, "GET", "/", params, "sdb.amazonaws.com")
--	expected := "okj96/5ucWBSc1uR2zXVfm6mDHtgfNv657rRtt/aunQ="
--	c.Assert(params["Signature"], Equals, expected)
+-	th.CheckDeepEquals(t, expected, actual)
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/LICENSE b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/LICENSE
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/results.go
 deleted file mode 100644
-index f9c841a..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/LICENSE
+index abae026..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/results.go
 +++ /dev/null
-@@ -1,21 +0,0 @@
--The MIT License (MIT)
+@@ -1,34 +0,0 @@
+-package accounts
 -
--Copyright (c) 2013 Mitchell Hashimoto
+-import (
+-	"strings"
 -
--Permission is hereby granted, free of charge, to any person obtaining a copy
--of this software and associated documentation files (the "Software"), to deal
--in the Software without restriction, including without limitation the rights
--to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
--copies of the Software, and to permit persons to whom the Software is
--furnished to do so, subject to the following conditions:
+-	"github.com/rackspace/gophercloud"
+-)
 -
--The above copyright notice and this permission notice shall be included in
--all copies or substantial portions of the Software.
+-// GetResult is returned from a call to the Get function.
+-type GetResult struct {
+-	gophercloud.HeaderResult
+-}
 -
--THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
--IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
--FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
--AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
--LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
--OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
--THE SOFTWARE.
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/README.md b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/README.md
+-// ExtractMetadata is a function that takes a GetResult (of type *http.Response)
+-// and returns the custom metatdata associated with the account.
+-func (gr GetResult) ExtractMetadata() (map[string]string, error) {
+-	if gr.Err != nil {
+-		return nil, gr.Err
+-	}
+-
+-	metadata := make(map[string]string)
+-	for k, v := range gr.Header {
+-		if strings.HasPrefix(k, "X-Account-Meta-") {
+-			key := strings.TrimPrefix(k, "X-Account-Meta-")
+-			metadata[key] = v[0]
+-		}
+-	}
+-	return metadata, nil
+-}
+-
+-// UpdateResult is returned from a call to the Update function.
+-type UpdateResult struct {
+-	gophercloud.HeaderResult
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/urls.go
 deleted file mode 100644
-index 659d688..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/README.md
+index 9952fe4..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/urls.go
 +++ /dev/null
-@@ -1,46 +0,0 @@
--# mapstructure
+@@ -1,11 +0,0 @@
+-package accounts
 -
--mapstructure is a Go library for decoding generic map values to structures
--and vice versa, while providing helpful error handling.
+-import "github.com/rackspace/gophercloud"
 -
--This library is most useful when decoding values from some data stream (JSON,
--Gob, etc.) where you don't _quite_ know the structure of the underlying data
--until you read a part of it. You can therefore read a `map[string]interface{}`
--and use this library to decode it into the proper underlying native Go
--structure.
+-func getURL(c *gophercloud.ServiceClient) string {
+-	return c.Endpoint
+-}
 -
--## Installation
+-func updateURL(c *gophercloud.ServiceClient) string {
+-	return getURL(c)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/urls_test.go
+deleted file mode 100644
+index 074d52d..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts/urls_test.go
++++ /dev/null
+@@ -1,26 +0,0 @@
+-package accounts
 -
--Standard `go get`:
+-import (
+-	"testing"
 -
--```
--$ go get github.com/mitchellh/mapstructure
--```
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--## Usage & Example
+-const endpoint = "http://localhost:57909/"
 -
--For usage and examples see the [Godoc](http://godoc.org/github.com/mitchellh/mapstructure).
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint}
+-}
 -
--The `Decode` function has examples associated with it there.
+-func TestGetURL(t *testing.T) {
+-	actual := getURL(endpointClient())
+-	expected := endpoint
+-	th.CheckEquals(t, expected, actual)
+-}
 -
--## But Why?!
+-func TestUpdateURL(t *testing.T) {
+-	actual := updateURL(endpointClient())
+-	expected := endpoint
+-	th.CheckEquals(t, expected, actual)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/doc.go
+deleted file mode 100644
+index 5fed553..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/doc.go
++++ /dev/null
+@@ -1,8 +0,0 @@
+-// Package containers contains functionality for working with Object Storage
+-// container resources. A container serves as a logical namespace for objects
+-// that are placed inside it - an object with the same name in two different
+-// containers represents two different objects.
+-//
+-// In addition to containing objects, you can also use the container to control
+-// access to objects by using an access control list (ACL).
+-package containers
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/fixtures.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/fixtures.go
+deleted file mode 100644
+index 1c0a915..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/fixtures.go
++++ /dev/null
+@@ -1,132 +0,0 @@
+-// +build fixtures
 -
--Go offers fantastic standard libraries for decoding formats such as JSON.
--The standard method is to have a struct pre-created, and populate that struct
--from the bytes of the encoded format. This is great, but the problem is if
--you have configuration or an encoding that changes slightly depending on
--specific fields. For example, consider this JSON:
+-package containers
 -
--```json
--{
--  "type": "person",
--  "name": "Mitchell"
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
+-
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
+-
+-// ExpectedListInfo is the result expected from a call to `List` when full
+-// info is requested.
+-var ExpectedListInfo = []Container{
+-	Container{
+-		Count: 0,
+-		Bytes: 0,
+-		Name:  "janeausten",
+-	},
+-	Container{
+-		Count: 1,
+-		Bytes: 14,
+-		Name:  "marktwain",
+-	},
 -}
--```
 -
--Perhaps we can't populate a specific structure without first reading
--the "type" field from the JSON. We could always do two passes over the
--decoding of the JSON (reading the "type" first, and the rest later).
--However, it is much simpler to just decode this into a `map[string]interface{}`
--structure, read the "type" key, then use something like this library
--to decode it into the proper structure.
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/decode_hooks.go b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/decode_hooks.go
+-// ExpectedListNames is the result expected from a call to `List` when just
+-// container names are requested.
+-var ExpectedListNames = []string{"janeausten", "marktwain"}
+-
+-// HandleListContainerInfoSuccessfully creates an HTTP handler at `/` on the test handler mux that
+-// responds with a `List` response when full info is requested.
+-func HandleListContainerInfoSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Accept", "application/json")
+-
+-		w.Header().Set("Content-Type", "application/json")
+-		r.ParseForm()
+-		marker := r.Form.Get("marker")
+-		switch marker {
+-		case "":
+-			fmt.Fprintf(w, `[
+-        {
+-          "count": 0,
+-          "bytes": 0,
+-          "name": "janeausten"
+-        },
+-        {
+-          "count": 1,
+-          "bytes": 14,
+-          "name": "marktwain"
+-        }
+-      ]`)
+-		case "marktwain":
+-			fmt.Fprintf(w, `[]`)
+-		default:
+-			t.Fatalf("Unexpected marker: [%s]", marker)
+-		}
+-	})
+-}
+-
+-// HandleListContainerNamesSuccessfully creates an HTTP handler at `/` on the test handler mux that
+-// responds with a `ListNames` response when only container names are requested.
+-func HandleListContainerNamesSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Accept", "text/plain")
+-
+-		w.Header().Set("Content-Type", "text/plain")
+-		r.ParseForm()
+-		marker := r.Form.Get("marker")
+-		switch marker {
+-		case "":
+-			fmt.Fprintf(w, "janeausten\nmarktwain\n")
+-		case "marktwain":
+-			fmt.Fprintf(w, ``)
+-		default:
+-			t.Fatalf("Unexpected marker: [%s]", marker)
+-		}
+-	})
+-}
+-
+-// HandleCreateContainerSuccessfully creates an HTTP handler at `/testContainer` on the test handler mux that
+-// responds with a `Create` response.
+-func HandleCreateContainerSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/testContainer", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Accept", "application/json")
+-
+-		w.Header().Add("X-Container-Meta-Foo", "bar")
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-}
+-
+-// HandleDeleteContainerSuccessfully creates an HTTP handler at `/testContainer` on the test handler mux that
+-// responds with a `Delete` response.
+-func HandleDeleteContainerSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/testContainer", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-}
+-
+-// HandleUpdateContainerSuccessfully creates an HTTP handler at `/testContainer` on the test handler mux that
+-// responds with a `Update` response.
+-func HandleUpdateContainerSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/testContainer", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-}
+-
+-// HandleGetContainerSuccessfully creates an HTTP handler at `/testContainer` on the test handler mux that
+-// responds with a `Get` response.
+-func HandleGetContainerSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/testContainer", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "HEAD")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/requests.go
 deleted file mode 100644
-index 087a392..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/decode_hooks.go
+index 9f3b2af..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/requests.go
 +++ /dev/null
-@@ -1,84 +0,0 @@
--package mapstructure
+@@ -1,204 +0,0 @@
+-package containers
 -
 -import (
--	"reflect"
--	"strconv"
--	"strings"
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
 -)
 -
--// ComposeDecodeHookFunc creates a single DecodeHookFunc that
--// automatically composes multiple DecodeHookFuncs.
--//
--// The composed funcs are called in order, with the result of the
--// previous transformation.
--func ComposeDecodeHookFunc(fs ...DecodeHookFunc) DecodeHookFunc {
--	return func(
--		f reflect.Kind,
--		t reflect.Kind,
--		data interface{}) (interface{}, error) {
--		var err error
--		for _, f1 := range fs {
--			data, err = f1(f, t, data)
--			if err != nil {
--				return nil, err
--			}
+-// ListOptsBuilder allows extensions to add additional parameters to the List
+-// request.
+-type ListOptsBuilder interface {
+-	ToContainerListParams() (bool, string, error)
+-}
 -
--			// Modify the from kind to be correct with the new data
--			f = getKind(reflect.ValueOf(data))
+-// ListOpts is a structure that holds options for listing containers.
+-type ListOpts struct {
+-	Full      bool
+-	Limit     int    `q:"limit"`
+-	Marker    string `q:"marker"`
+-	EndMarker string `q:"end_marker"`
+-	Format    string `q:"format"`
+-	Prefix    string `q:"prefix"`
+-	Delimiter string `q:"delimiter"`
+-}
+-
+-// ToContainerListParams formats a ListOpts into a query string and boolean
+-// representing whether to list complete information for each container.
+-func (opts ListOpts) ToContainerListParams() (bool, string, error) {
+-	q, err := gophercloud.BuildQueryString(opts)
+-	if err != nil {
+-		return false, "", err
+-	}
+-	return opts.Full, q.String(), nil
+-}
+-
+-// List is a function that retrieves containers associated with the account as
+-// well as account metadata. It returns a pager which can be iterated with the
+-// EachPage function.
+-func List(c *gophercloud.ServiceClient, opts ListOptsBuilder) pagination.Pager {
+-	headers := map[string]string{"Accept": "text/plain", "Content-Type": "text/plain"}
+-
+-	url := listURL(c)
+-	if opts != nil {
+-		full, query, err := opts.ToContainerListParams()
+-		if err != nil {
+-			return pagination.Pager{Err: err}
 -		}
+-		url += query
 -
--		return data, nil
+-		if full {
+-			headers = map[string]string{"Accept": "application/json", "Content-Type": "application/json"}
+-		}
+-	}
+-
+-	createPage := func(r pagination.PageResult) pagination.Page {
+-		p := ContainerPage{pagination.MarkerPageBase{PageResult: r}}
+-		p.MarkerPageBase.Owner = p
+-		return p
 -	}
+-
+-	pager := pagination.NewPager(c, url, createPage)
+-	pager.Headers = headers
+-	return pager
 -}
 -
--// StringToSliceHookFunc returns a DecodeHookFunc that converts
--// string to []string by splitting on the given sep.
--func StringToSliceHookFunc(sep string) DecodeHookFunc {
--	return func(
--		f reflect.Kind,
--		t reflect.Kind,
--		data interface{}) (interface{}, error) {
--		if f != reflect.String || t != reflect.Slice {
--			return data, nil
+-// CreateOptsBuilder allows extensions to add additional parameters to the
+-// Create request.
+-type CreateOptsBuilder interface {
+-	ToContainerCreateMap() (map[string]string, error)
+-}
+-
+-// CreateOpts is a structure that holds parameters for creating a container.
+-type CreateOpts struct {
+-	Metadata          map[string]string
+-	ContainerRead     string `h:"X-Container-Read"`
+-	ContainerSyncTo   string `h:"X-Container-Sync-To"`
+-	ContainerSyncKey  string `h:"X-Container-Sync-Key"`
+-	ContainerWrite    string `h:"X-Container-Write"`
+-	ContentType       string `h:"Content-Type"`
+-	DetectContentType bool   `h:"X-Detect-Content-Type"`
+-	IfNoneMatch       string `h:"If-None-Match"`
+-	VersionsLocation  string `h:"X-Versions-Location"`
+-}
+-
+-// ToContainerCreateMap formats a CreateOpts into a map of headers.
+-func (opts CreateOpts) ToContainerCreateMap() (map[string]string, error) {
+-	h, err := gophercloud.BuildHeaders(opts)
+-	if err != nil {
+-		return nil, err
+-	}
+-	for k, v := range opts.Metadata {
+-		h["X-Container-Meta-"+k] = v
+-	}
+-	return h, nil
+-}
+-
+-// Create is a function that creates a new container.
+-func Create(c *gophercloud.ServiceClient, containerName string, opts CreateOptsBuilder) CreateResult {
+-	var res CreateResult
+-	h := c.AuthenticatedHeaders()
+-
+-	if opts != nil {
+-		headers, err := opts.ToContainerCreateMap()
+-		if err != nil {
+-			res.Err = err
+-			return res
 -		}
 -
--		raw := data.(string)
--		if raw == "" {
--			return []string{}, nil
+-		for k, v := range headers {
+-			h[k] = v
 -		}
+-	}
 -
--		return strings.Split(raw, sep), nil
+-	resp, err := perigee.Request("PUT", createURL(c, containerName), perigee.Options{
+-		MoreHeaders: h,
+-		OkCodes:     []int{201, 202, 204},
+-	})
+-	res.Header = resp.HttpResponse.Header
+-	res.Err = err
+-	return res
+-}
+-
+-// Delete is a function that deletes a container.
+-func Delete(c *gophercloud.ServiceClient, containerName string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", deleteURL(c, containerName), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{202, 204},
+-	})
+-	return res
+-}
+-
+-// UpdateOptsBuilder allows extensions to add additional parameters to the
+-// Update request.
+-type UpdateOptsBuilder interface {
+-	ToContainerUpdateMap() (map[string]string, error)
+-}
+-
+-// UpdateOpts is a structure that holds parameters for updating, creating, or
+-// deleting a container's metadata.
+-type UpdateOpts struct {
+-	Metadata               map[string]string
+-	ContainerRead          string `h:"X-Container-Read"`
+-	ContainerSyncTo        string `h:"X-Container-Sync-To"`
+-	ContainerSyncKey       string `h:"X-Container-Sync-Key"`
+-	ContainerWrite         string `h:"X-Container-Write"`
+-	ContentType            string `h:"Content-Type"`
+-	DetectContentType      bool   `h:"X-Detect-Content-Type"`
+-	RemoveVersionsLocation string `h:"X-Remove-Versions-Location"`
+-	VersionsLocation       string `h:"X-Versions-Location"`
+-}
+-
+-// ToContainerUpdateMap formats a CreateOpts into a map of headers.
+-func (opts UpdateOpts) ToContainerUpdateMap() (map[string]string, error) {
+-	h, err := gophercloud.BuildHeaders(opts)
+-	if err != nil {
+-		return nil, err
 -	}
+-	for k, v := range opts.Metadata {
+-		h["X-Container-Meta-"+k] = v
+-	}
+-	return h, nil
 -}
 -
--func WeaklyTypedHook(
--	f reflect.Kind,
--	t reflect.Kind,
--	data interface{}) (interface{}, error) {
--	dataVal := reflect.ValueOf(data)
--	switch t {
--	case reflect.String:
--		switch f {
--		case reflect.Bool:
--			if dataVal.Bool() {
--				return "1", nil
--			} else {
--				return "0", nil
--			}
--		case reflect.Float32:
--			return strconv.FormatFloat(dataVal.Float(), 'f', -1, 64), nil
--		case reflect.Int:
--			return strconv.FormatInt(dataVal.Int(), 10), nil
--		case reflect.Slice:
--			dataType := dataVal.Type()
--			elemKind := dataType.Elem().Kind()
--			if elemKind == reflect.Uint8 {
--				return string(dataVal.Interface().([]uint8)), nil
--			}
--		case reflect.Uint:
--			return strconv.FormatUint(dataVal.Uint(), 10), nil
+-// Update is a function that creates, updates, or deletes a container's
+-// metadata.
+-func Update(c *gophercloud.ServiceClient, containerName string, opts UpdateOptsBuilder) UpdateResult {
+-	var res UpdateResult
+-	h := c.AuthenticatedHeaders()
+-
+-	if opts != nil {
+-		headers, err := opts.ToContainerUpdateMap()
+-		if err != nil {
+-			res.Err = err
+-			return res
+-		}
+-
+-		for k, v := range headers {
+-			h[k] = v
 -		}
 -	}
 -
--	return data, nil
+-	resp, err := perigee.Request("POST", updateURL(c, containerName), perigee.Options{
+-		MoreHeaders: h,
+-		OkCodes:     []int{202, 204},
+-	})
+-	res.Header = resp.HttpResponse.Header
+-	res.Err = err
+-	return res
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/decode_hooks_test.go b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/decode_hooks_test.go
+-
+-// Get is a function that retrieves the metadata of a container. To extract just
+-// the custom metadata, pass the GetResult response to the ExtractMetadata
+-// function.
+-func Get(c *gophercloud.ServiceClient, containerName string) GetResult {
+-	var res GetResult
+-	resp, err := perigee.Request("HEAD", getURL(c, containerName), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{200, 204},
+-	})
+-	res.Header = resp.HttpResponse.Header
+-	res.Err = err
+-	return res
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/requests_test.go
 deleted file mode 100644
-index b417dee..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/decode_hooks_test.go
+index d0ce7f1..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/requests_test.go
 +++ /dev/null
-@@ -1,191 +0,0 @@
--package mapstructure
+@@ -1,91 +0,0 @@
+-package containers
 -
 -import (
--	"errors"
--	"reflect"
 -	"testing"
+-
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
+-
+-var metadata = map[string]string{"gophercloud-test": "containers"}
+-
+-func TestListContainerInfo(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleListContainerInfoSuccessfully(t)
+-
+-	count := 0
+-	err := List(fake.ServiceClient(), &ListOpts{Full: true}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractInfo(page)
+-		th.AssertNoErr(t, err)
+-
+-		th.CheckDeepEquals(t, ExpectedListInfo, actual)
+-
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, count, 1)
+-}
+-
+-func TestListContainerNames(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleListContainerNamesSuccessfully(t)
+-
+-	count := 0
+-	err := List(fake.ServiceClient(), &ListOpts{Full: false}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractNames(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract container names: %v", err)
+-			return false, err
+-		}
+-
+-		th.CheckDeepEquals(t, ExpectedListNames, actual)
+-
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, count, 1)
+-}
+-
+-func TestCreateContainer(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleCreateContainerSuccessfully(t)
+-
+-	options := CreateOpts{ContentType: "application/json", Metadata: map[string]string{"foo": "bar"}}
+-	res := Create(fake.ServiceClient(), "testContainer", options)
+-	th.CheckNoErr(t, res.Err)
+-	th.CheckEquals(t, "bar", res.Header["X-Container-Meta-Foo"][0])
+-}
+-
+-func TestDeleteContainer(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleDeleteContainerSuccessfully(t)
+-
+-	res := Delete(fake.ServiceClient(), "testContainer")
+-	th.CheckNoErr(t, res.Err)
+-}
+-
+-func TestUpateContainer(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleUpdateContainerSuccessfully(t)
+-
+-	options := &UpdateOpts{Metadata: map[string]string{"foo": "bar"}}
+-	res := Update(fake.ServiceClient(), "testContainer", options)
+-	th.CheckNoErr(t, res.Err)
+-}
+-
+-func TestGetContainer(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleGetContainerSuccessfully(t)
+-
+-	_, err := Get(fake.ServiceClient(), "testContainer").ExtractMetadata()
+-	th.CheckNoErr(t, err)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/results.go
+deleted file mode 100644
+index 74f3286..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/results.go
++++ /dev/null
+@@ -1,139 +0,0 @@
+-package containers
+-
+-import (
+-	"fmt"
+-	"strings"
+-
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-
+-	"github.com/mitchellh/mapstructure"
 -)
 -
--func TestComposeDecodeHookFunc(t *testing.T) {
--	f1 := func(
--		f reflect.Kind,
--		t reflect.Kind,
--		data interface{}) (interface{}, error) {
--		return data.(string) + "foo", nil
--	}
+-// Container represents a container resource.
+-type Container struct {
+-	// The total number of bytes stored in the container.
+-	Bytes int `json:"bytes" mapstructure:"bytes"`
 -
--	f2 := func(
--		f reflect.Kind,
--		t reflect.Kind,
--		data interface{}) (interface{}, error) {
--		return data.(string) + "bar", nil
--	}
+-	// The total number of objects stored in the container.
+-	Count int `json:"count" mapstructure:"count"`
 -
--	f := ComposeDecodeHookFunc(f1, f2)
+-	// The name of the container.
+-	Name string `json:"name" mapstructure:"name"`
+-}
 -
--	result, err := f(reflect.String, reflect.Slice, "")
+-// ContainerPage is the page returned by a pager when traversing over a
+-// collection of containers.
+-type ContainerPage struct {
+-	pagination.MarkerPageBase
+-}
+-
+-// IsEmpty returns true if a ListResult contains no container names.
+-func (r ContainerPage) IsEmpty() (bool, error) {
+-	names, err := ExtractNames(r)
 -	if err != nil {
--		t.Fatalf("bad: %s", err)
--	}
--	if result.(string) != "foobar" {
--		t.Fatalf("bad: %#v", result)
+-		return true, err
 -	}
+-	return len(names) == 0, nil
 -}
 -
--func TestComposeDecodeHookFunc_err(t *testing.T) {
--	f1 := func(reflect.Kind, reflect.Kind, interface{}) (interface{}, error) {
--		return nil, errors.New("foo")
+-// LastMarker returns the last container name in a ListResult.
+-func (r ContainerPage) LastMarker() (string, error) {
+-	names, err := ExtractNames(r)
+-	if err != nil {
+-		return "", err
 -	}
--
--	f2 := func(reflect.Kind, reflect.Kind, interface{}) (interface{}, error) {
--		panic("NOPE")
+-	if len(names) == 0 {
+-		return "", nil
 -	}
+-	return names[len(names)-1], nil
+-}
 -
--	f := ComposeDecodeHookFunc(f1, f2)
--
--	_, err := f(reflect.String, reflect.Slice, 42)
--	if err.Error() != "foo" {
--		t.Fatalf("bad: %s", err)
+-// ExtractInfo is a function that takes a ListResult and returns the containers' information.
+-func ExtractInfo(page pagination.Page) ([]Container, error) {
+-	untyped := page.(ContainerPage).Body.([]interface{})
+-	results := make([]Container, len(untyped))
+-	for index, each := range untyped {
+-		container := each.(map[string]interface{})
+-		err := mapstructure.Decode(container, &results[index])
+-		if err != nil {
+-			return results, err
+-		}
 -	}
+-	return results, nil
 -}
 -
--func TestComposeDecodeHookFunc_kinds(t *testing.T) {
--	var f2From reflect.Kind
+-// ExtractNames is a function that takes a ListResult and returns the containers' names.
+-func ExtractNames(page pagination.Page) ([]string, error) {
+-	casted := page.(ContainerPage)
+-	ct := casted.Header.Get("Content-Type")
 -
--	f1 := func(
--		f reflect.Kind,
--		t reflect.Kind,
--		data interface{}) (interface{}, error) {
--		return int(42), nil
--	}
+-	switch {
+-	case strings.HasPrefix(ct, "application/json"):
+-		parsed, err := ExtractInfo(page)
+-		if err != nil {
+-			return nil, err
+-		}
 -
--	f2 := func(
--		f reflect.Kind,
--		t reflect.Kind,
--		data interface{}) (interface{}, error) {
--		f2From = f
--		return data, nil
--	}
+-		names := make([]string, 0, len(parsed))
+-		for _, container := range parsed {
+-			names = append(names, container.Name)
+-		}
+-		return names, nil
+-	case strings.HasPrefix(ct, "text/plain"):
+-		names := make([]string, 0, 50)
 -
--	f := ComposeDecodeHookFunc(f1, f2)
+-		body := string(page.(ContainerPage).Body.([]uint8))
+-		for _, name := range strings.Split(body, "\n") {
+-			if len(name) > 0 {
+-				names = append(names, name)
+-			}
+-		}
 -
--	_, err := f(reflect.String, reflect.Slice, "")
--	if err != nil {
--		t.Fatalf("bad: %s", err)
--	}
--	if f2From != reflect.Int {
--		t.Fatalf("bad: %#v", f2From)
+-		return names, nil
+-	default:
+-		return nil, fmt.Errorf("Cannot extract names from response with content-type: [%s]", ct)
 -	}
 -}
 -
--func TestStringToSliceHookFunc(t *testing.T) {
--	f := StringToSliceHookFunc(",")
+-// GetResult represents the result of a get operation.
+-type GetResult struct {
+-	gophercloud.HeaderResult
+-}
 -
--	cases := []struct {
--		f, t   reflect.Kind
--		data   interface{}
--		result interface{}
--		err    bool
--	}{
--		{reflect.Slice, reflect.Slice, 42, 42, false},
--		{reflect.String, reflect.String, 42, 42, false},
--		{
--			reflect.String,
--			reflect.Slice,
--			"foo,bar,baz",
--			[]string{"foo", "bar", "baz"},
--			false,
--		},
--		{
--			reflect.String,
--			reflect.Slice,
--			"",
--			[]string{},
--			false,
--		},
+-// ExtractMetadata is a function that takes a GetResult (of type *http.Response)
+-// and returns the custom metadata associated with the container.
+-func (gr GetResult) ExtractMetadata() (map[string]string, error) {
+-	if gr.Err != nil {
+-		return nil, gr.Err
 -	}
--
--	for i, tc := range cases {
--		actual, err := f(tc.f, tc.t, tc.data)
--		if tc.err != (err != nil) {
--			t.Fatalf("case %d: expected err %#v", i, tc.err)
--		}
--		if !reflect.DeepEqual(actual, tc.result) {
--			t.Fatalf(
--				"case %d: expected %#v, got %#v",
--				i, tc.result, actual)
+-	metadata := make(map[string]string)
+-	for k, v := range gr.Header {
+-		if strings.HasPrefix(k, "X-Container-Meta-") {
+-			key := strings.TrimPrefix(k, "X-Container-Meta-")
+-			metadata[key] = v[0]
 -		}
 -	}
+-	return metadata, nil
 -}
 -
--func TestWeaklyTypedHook(t *testing.T) {
--	var f DecodeHookFunc = WeaklyTypedHook
+-// CreateResult represents the result of a create operation. To extract the
+-// the headers from the HTTP response, you can invoke the 'ExtractHeader'
+-// method on the result struct.
+-type CreateResult struct {
+-	gophercloud.HeaderResult
+-}
 -
--	cases := []struct {
--		f, t   reflect.Kind
--		data   interface{}
--		result interface{}
--		err    bool
--	}{
--		// TO STRING
--		{
--			reflect.Bool,
--			reflect.String,
--			false,
--			"0",
--			false,
--		},
+-// UpdateResult represents the result of an update operation. To extract the
+-// the headers from the HTTP response, you can invoke the 'ExtractHeader'
+-// method on the result struct.
+-type UpdateResult struct {
+-	gophercloud.HeaderResult
+-}
 -
--		{
--			reflect.Bool,
--			reflect.String,
--			true,
--			"1",
--			false,
--		},
+-// DeleteResult represents the result of a delete operation. To extract the
+-// the headers from the HTTP response, you can invoke the 'ExtractHeader'
+-// method on the result struct.
+-type DeleteResult struct {
+-	gophercloud.HeaderResult
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/urls.go
+deleted file mode 100644
+index f864f84..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/urls.go
++++ /dev/null
+@@ -1,23 +0,0 @@
+-package containers
 -
--		{
--			reflect.Float32,
--			reflect.String,
--			float32(7),
--			"7",
--			false,
--		},
+-import "github.com/rackspace/gophercloud"
 -
--		{
--			reflect.Int,
--			reflect.String,
--			int(7),
--			"7",
--			false,
--		},
+-func listURL(c *gophercloud.ServiceClient) string {
+-	return c.Endpoint
+-}
 -
--		{
--			reflect.Slice,
--			reflect.String,
--			[]uint8("foo"),
--			"foo",
--			false,
--		},
+-func createURL(c *gophercloud.ServiceClient, container string) string {
+-	return c.ServiceURL(container)
+-}
 -
--		{
--			reflect.Uint,
--			reflect.String,
--			uint(7),
--			"7",
--			false,
--		},
--	}
+-func getURL(c *gophercloud.ServiceClient, container string) string {
+-	return createURL(c, container)
+-}
 -
--	for i, tc := range cases {
--		actual, err := f(tc.f, tc.t, tc.data)
--		if tc.err != (err != nil) {
--			t.Fatalf("case %d: expected err %#v", i, tc.err)
--		}
--		if !reflect.DeepEqual(actual, tc.result) {
--			t.Fatalf(
--				"case %d: expected %#v, got %#v",
--				i, tc.result, actual)
--		}
--	}
+-func deleteURL(c *gophercloud.ServiceClient, container string) string {
+-	return createURL(c, container)
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/error.go b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/error.go
+-
+-func updateURL(c *gophercloud.ServiceClient, container string) string {
+-	return createURL(c, container)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/urls_test.go
 deleted file mode 100644
-index 3460799..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/error.go
+index d043a2a..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers/urls_test.go
 +++ /dev/null
-@@ -1,32 +0,0 @@
--package mapstructure
+@@ -1,43 +0,0 @@
+-package containers
 -
 -import (
--	"fmt"
--	"strings"
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"testing"
 -)
 -
--// Error implements the error interface and can represents multiple
--// errors that occur in the course of a single decode.
--type Error struct {
--	Errors []string
+-const endpoint = "http://localhost:57909/"
+-
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint}
 -}
 -
--func (e *Error) Error() string {
--	points := make([]string, len(e.Errors))
--	for i, err := range e.Errors {
--		points[i] = fmt.Sprintf("* %s", err)
--	}
+-func TestListURL(t *testing.T) {
+-	actual := listURL(endpointClient())
+-	expected := endpoint
+-	th.CheckEquals(t, expected, actual)
+-}
 -
--	return fmt.Sprintf(
--		"%d error(s) decoding:\n\n%s",
--		len(e.Errors), strings.Join(points, "\n"))
+-func TestCreateURL(t *testing.T) {
+-	actual := createURL(endpointClient(), "foo")
+-	expected := endpoint + "foo"
+-	th.CheckEquals(t, expected, actual)
 -}
 -
--func appendErrors(errors []string, err error) []string {
--	switch e := err.(type) {
--	case *Error:
--		return append(errors, e.Errors...)
--	default:
--		return append(errors, e.Error())
--	}
+-func TestGetURL(t *testing.T) {
+-	actual := getURL(endpointClient(), "foo")
+-	expected := endpoint + "foo"
+-	th.CheckEquals(t, expected, actual)
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure.go b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure.go
+-
+-func TestDeleteURL(t *testing.T) {
+-	actual := deleteURL(endpointClient(), "foo")
+-	expected := endpoint + "foo"
+-	th.CheckEquals(t, expected, actual)
+-}
+-
+-func TestUpdateURL(t *testing.T) {
+-	actual := updateURL(endpointClient(), "foo")
+-	expected := endpoint + "foo"
+-	th.CheckEquals(t, expected, actual)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/doc.go
 deleted file mode 100644
-index 381ba5d..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure.go
+index 30a9add..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/doc.go
 +++ /dev/null
-@@ -1,704 +0,0 @@
--// The mapstructure package exposes functionality to convert an
--// abitrary map[string]interface{} into a native Go structure.
--//
--// The Go structure can be arbitrarily complex, containing slices,
--// other structs, etc. and the decoder will properly decode nested
--// maps and so on into the proper structures in the native Go struct.
--// See the examples to see what the decoder is capable of.
--package mapstructure
+@@ -1,5 +0,0 @@
+-// Package objects contains functionality for working with Object Storage
+-// object resources. An object is a resource that represents and contains data
+-// - such as documents, images, and so on. You can also store custom metadata
+-// with an object.
+-package objects
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/fixtures.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/fixtures.go
+deleted file mode 100644
+index d951160..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/fixtures.go
++++ /dev/null
+@@ -1,164 +0,0 @@
+-// +build fixtures
+-
+-package objects
 -
 -import (
--	"errors"
 -	"fmt"
--	"reflect"
--	"sort"
--	"strconv"
--	"strings"
+-	"net/http"
+-	"testing"
+-
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
 -)
 -
--// DecodeHookFunc is the callback function that can be used for
--// data transformations. See "DecodeHook" in the DecoderConfig
--// struct.
--type DecodeHookFunc func(
--	from reflect.Kind,
--	to reflect.Kind,
--	data interface{}) (interface{}, error)
+-// HandleDownloadObjectSuccessfully creates an HTTP handler at `/testContainer/testObject` on the test handler mux that
+-// responds with a `Download` response.
+-func HandleDownloadObjectSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/testContainer/testObject", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-		fmt.Fprintf(w, "Successful download with Gophercloud")
+-	})
+-}
 -
--// DecoderConfig is the configuration that is used to create a new decoder
--// and allows customization of various aspects of decoding.
--type DecoderConfig struct {
--	// DecodeHook, if set, will be called before any decoding and any
--	// type conversion (if WeaklyTypedInput is on). This lets you modify
--	// the values before they're set down onto the resulting struct.
--	//
--	// If an error is returned, the entire decode will fail with that
--	// error.
--	DecodeHook DecodeHookFunc
+-// ExpectedListInfo is the result expected from a call to `List` when full
+-// info is requested.
+-var ExpectedListInfo = []Object{
+-	Object{
+-		Hash:         "451e372e48e0f6b1114fa0724aa79fa1",
+-		LastModified: "2009-11-10 23:00:00 +0000 UTC",
+-		Bytes:        14,
+-		Name:         "goodbye",
+-		ContentType:  "application/octet-stream",
+-	},
+-	Object{
+-		Hash:         "451e372e48e0f6b1114fa0724aa79fa1",
+-		LastModified: "2009-11-10 23:00:00 +0000 UTC",
+-		Bytes:        14,
+-		Name:         "hello",
+-		ContentType:  "application/octet-stream",
+-	},
+-}
 -
--	// If ErrorUnused is true, then it is an error for there to exist
--	// keys in the original map that were unused in the decoding process
--	// (extra keys).
--	ErrorUnused bool
+-// ExpectedListNames is the result expected from a call to `List` when just
+-// object names are requested.
+-var ExpectedListNames = []string{"hello", "goodbye"}
+-
+-// HandleListObjectsInfoSuccessfully creates an HTTP handler at `/testContainer` on the test handler mux that
+-// responds with a `List` response when full info is requested.
+-func HandleListObjectsInfoSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/testContainer", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Accept", "application/json")
+-
+-		w.Header().Set("Content-Type", "application/json")
+-		r.ParseForm()
+-		marker := r.Form.Get("marker")
+-		switch marker {
+-		case "":
+-			fmt.Fprintf(w, `[
+-      {
+-        "hash": "451e372e48e0f6b1114fa0724aa79fa1",
+-        "last_modified": "2009-11-10 23:00:00 +0000 UTC",
+-        "bytes": 14,
+-        "name": "goodbye",
+-        "content_type": "application/octet-stream"
+-      },
+-      {
+-        "hash": "451e372e48e0f6b1114fa0724aa79fa1",
+-        "last_modified": "2009-11-10 23:00:00 +0000 UTC",
+-        "bytes": 14,
+-        "name": "hello",
+-        "content_type": "application/octet-stream"
+-      }
+-    ]`)
+-		case "hello":
+-			fmt.Fprintf(w, `[]`)
+-		default:
+-			t.Fatalf("Unexpected marker: [%s]", marker)
+-		}
+-	})
+-}
 -
--	// If WeaklyTypedInput is true, the decoder will make the following
--	// "weak" conversions:
--	//
--	//   - bools to string (true = "1", false = "0")
--	//   - numbers to string (base 10)
--	//   - bools to int/uint (true = 1, false = 0)
--	//   - strings to int/uint (base implied by prefix)
--	//   - int to bool (true if value != 0)
--	//   - string to bool (accepts: 1, t, T, TRUE, true, True, 0, f, F,
--	//     FALSE, false, False. Anything else is an error)
--	//   - empty array = empty map and vice versa
--	//
--	WeaklyTypedInput bool
+-// HandleListObjectNamesSuccessfully creates an HTTP handler at `/testContainer` on the test handler mux that
+-// responds with a `List` response when only object names are requested.
+-func HandleListObjectNamesSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/testContainer", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Accept", "text/plain")
+-
+-		w.Header().Set("Content-Type", "text/plain")
+-		r.ParseForm()
+-		marker := r.Form.Get("marker")
+-		switch marker {
+-		case "":
+-			fmt.Fprintf(w, "hello\ngoodbye\n")
+-		case "goodbye":
+-			fmt.Fprintf(w, "")
+-		default:
+-			t.Fatalf("Unexpected marker: [%s]", marker)
+-		}
+-	})
+-}
 -
--	// Metadata is the struct that will contain extra metadata about
--	// the decoding. If this is nil, then no metadata will be tracked.
--	Metadata *Metadata
+-// HandleCreateObjectSuccessfully creates an HTTP handler at `/testContainer/testObject` on the test handler mux that
+-// responds with a `Create` response.
+-func HandleCreateObjectSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/testContainer/testObject", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		w.WriteHeader(http.StatusCreated)
+-	})
+-}
 -
--	// Result is a pointer to the struct that will contain the decoded
--	// value.
--	Result interface{}
+-// HandleCopyObjectSuccessfully creates an HTTP handler at `/testContainer/testObject` on the test handler mux that
+-// responds with a `Copy` response.
+-func HandleCopyObjectSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/testContainer/testObject", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "COPY")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestHeader(t, r, "Destination", "/newTestContainer/newTestObject")
+-		w.WriteHeader(http.StatusCreated)
+-	})
+-}
 -
--	// The tag name that mapstructure reads for field names. This
--	// defaults to "mapstructure"
--	TagName string
+-// HandleDeleteObjectSuccessfully creates an HTTP handler at `/testContainer/testObject` on the test handler mux that
+-// responds with a `Delete` response.
+-func HandleDeleteObjectSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/testContainer/testObject", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		w.WriteHeader(http.StatusNoContent)
+-	})
 -}
 -
--// A Decoder takes a raw interface value and turns it into structured
--// data, keeping track of rich error information along the way in case
--// anything goes wrong. Unlike the basic top-level Decode method, you can
--// more finely control how the Decoder behaves using the DecoderConfig
--// structure. The top-level Decode method is just a convenience that sets
--// up the most basic Decoder.
--type Decoder struct {
--	config *DecoderConfig
+-// HandleUpdateObjectSuccessfully creates an HTTP handler at `/testContainer/testObject` on the test handler mux that
+-// responds with a `Update` response.
+-func HandleUpdateObjectSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/testContainer/testObject", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestHeader(t, r, "X-Object-Meta-Gophercloud-Test", "objects")
+-		w.WriteHeader(http.StatusAccepted)
+-	})
 -}
 -
--// Metadata contains information about decoding a structure that
--// is tedious or difficult to get otherwise.
--type Metadata struct {
--	// Keys are the keys of the structure which were successfully decoded
--	Keys []string
+-// HandleGetObjectSuccessfully creates an HTTP handler at `/testContainer/testObject` on the test handler mux that
+-// responds with a `Get` response.
+-func HandleGetObjectSuccessfully(t *testing.T) {
+-	th.Mux.HandleFunc("/testContainer/testObject", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "HEAD")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		w.Header().Add("X-Object-Meta-Gophercloud-Test", "objects")
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/requests.go
+deleted file mode 100644
+index 9778de3..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/requests.go
++++ /dev/null
+@@ -1,416 +0,0 @@
+-package objects
 -
--	// Unused is a slice of keys that were found in the raw value but
--	// weren't decoded since there was no matching field in the result interface
--	Unused []string
+-import (
+-	"fmt"
+-	"io"
+-	"time"
+-
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
+-
+-// ListOptsBuilder allows extensions to add additional parameters to the List
+-// request.
+-type ListOptsBuilder interface {
+-	ToObjectListParams() (bool, string, error)
 -}
 -
--// Decode takes a map and uses reflection to convert it into the
--// given Go native structure. val must be a pointer to a struct.
--func Decode(m interface{}, rawVal interface{}) error {
--	config := &DecoderConfig{
--		Metadata: nil,
--		Result:   rawVal,
--	}
+-// ListOpts is a structure that holds parameters for listing objects.
+-type ListOpts struct {
+-	Full      bool
+-	Limit     int    `q:"limit"`
+-	Marker    string `q:"marker"`
+-	EndMarker string `q:"end_marker"`
+-	Format    string `q:"format"`
+-	Prefix    string `q:"prefix"`
+-	Delimiter string `q:"delimiter"`
+-	Path      string `q:"path"`
+-}
 -
--	decoder, err := NewDecoder(config)
+-// ToObjectListParams formats a ListOpts into a query string and boolean
+-// representing whether to list complete information for each object.
+-func (opts ListOpts) ToObjectListParams() (bool, string, error) {
+-	q, err := gophercloud.BuildQueryString(opts)
 -	if err != nil {
--		return err
+-		return false, "", err
 -	}
--
--	return decoder.Decode(m)
+-	return opts.Full, q.String(), nil
 -}
 -
--// WeakDecode is the same as Decode but is shorthand to enable
--// WeaklyTypedInput. See DecoderConfig for more info.
--func WeakDecode(input, output interface{}) error {
--	config := &DecoderConfig{
--		Metadata:         nil,
--		Result:           output,
--		WeaklyTypedInput: true,
+-// List is a function that retrieves all objects in a container. It also returns the details
+-// for the container. To extract only the object information or names, pass the ListResult
+-// response to the ExtractInfo or ExtractNames function, respectively.
+-func List(c *gophercloud.ServiceClient, containerName string, opts ListOptsBuilder) pagination.Pager {
+-	headers := map[string]string{"Accept": "text/plain", "Content-Type": "text/plain"}
+-
+-	url := listURL(c, containerName)
+-	if opts != nil {
+-		full, query, err := opts.ToObjectListParams()
+-		if err != nil {
+-			return pagination.Pager{Err: err}
+-		}
+-		url += query
+-
+-		if full {
+-			headers = map[string]string{"Accept": "application/json", "Content-Type": "application/json"}
+-		}
 -	}
 -
--	decoder, err := NewDecoder(config)
--	if err != nil {
--		return err
+-	createPage := func(r pagination.PageResult) pagination.Page {
+-		p := ObjectPage{pagination.MarkerPageBase{PageResult: r}}
+-		p.MarkerPageBase.Owner = p
+-		return p
 -	}
 -
--	return decoder.Decode(input)
+-	pager := pagination.NewPager(c, url, createPage)
+-	pager.Headers = headers
+-	return pager
 -}
 -
--// NewDecoder returns a new decoder for the given configuration. Once
--// a decoder has been returned, the same configuration must not be used
--// again.
--func NewDecoder(config *DecoderConfig) (*Decoder, error) {
--	val := reflect.ValueOf(config.Result)
--	if val.Kind() != reflect.Ptr {
--		return nil, errors.New("result must be a pointer")
--	}
+-// DownloadOptsBuilder allows extensions to add additional parameters to the
+-// Download request.
+-type DownloadOptsBuilder interface {
+-	ToObjectDownloadParams() (map[string]string, string, error)
+-}
 -
--	val = val.Elem()
--	if !val.CanAddr() {
--		return nil, errors.New("result must be addressable (a pointer)")
+-// DownloadOpts is a structure that holds parameters for downloading an object.
+-type DownloadOpts struct {
+-	IfMatch           string    `h:"If-Match"`
+-	IfModifiedSince   time.Time `h:"If-Modified-Since"`
+-	IfNoneMatch       string    `h:"If-None-Match"`
+-	IfUnmodifiedSince time.Time `h:"If-Unmodified-Since"`
+-	Range             string    `h:"Range"`
+-	Expires           string    `q:"expires"`
+-	MultipartManifest string    `q:"multipart-manifest"`
+-	Signature         string    `q:"signature"`
+-}
+-
+-// ToObjectDownloadParams formats a DownloadOpts into a query string and map of
+-// headers.
+-func (opts ListOpts) ToObjectDownloadParams() (map[string]string, string, error) {
+-	q, err := gophercloud.BuildQueryString(opts)
+-	if err != nil {
+-		return nil, "", err
+-	}
+-	h, err := gophercloud.BuildHeaders(opts)
+-	if err != nil {
+-		return nil, q.String(), err
 -	}
+-	return h, q.String(), nil
+-}
 -
--	if config.Metadata != nil {
--		if config.Metadata.Keys == nil {
--			config.Metadata.Keys = make([]string, 0)
+-// Download is a function that retrieves the content and metadata for an object.
+-// To extract just the content, pass the DownloadResult response to the
+-// ExtractContent function.
+-func Download(c *gophercloud.ServiceClient, containerName, objectName string, opts DownloadOptsBuilder) DownloadResult {
+-	var res DownloadResult
+-
+-	url := downloadURL(c, containerName, objectName)
+-	h := c.AuthenticatedHeaders()
+-
+-	if opts != nil {
+-		headers, query, err := opts.ToObjectDownloadParams()
+-		if err != nil {
+-			res.Err = err
+-			return res
 -		}
 -
--		if config.Metadata.Unused == nil {
--			config.Metadata.Unused = make([]string, 0)
+-		for k, v := range headers {
+-			h[k] = v
 -		}
--	}
 -
--	if config.TagName == "" {
--		config.TagName = "mapstructure"
+-		url += query
 -	}
 -
--	result := &Decoder{
--		config: config,
--	}
+-	resp, err := perigee.Request("GET", url, perigee.Options{
+-		MoreHeaders: h,
+-		OkCodes:     []int{200},
+-	})
 -
--	return result, nil
+-	res.Body = resp.HttpResponse.Body
+-	res.Err = err
+-	res.Header = resp.HttpResponse.Header
+-
+-	return res
 -}
 -
--// Decode decodes the given raw interface to the target pointer specified
--// by the configuration.
--func (d *Decoder) Decode(raw interface{}) error {
--	return d.decode("", raw, reflect.ValueOf(d.config.Result).Elem())
+-// CreateOptsBuilder allows extensions to add additional parameters to the
+-// Create request.
+-type CreateOptsBuilder interface {
+-	ToObjectCreateParams() (map[string]string, string, error)
 -}
 -
--// Decodes an unknown data type into a specific reflection value.
--func (d *Decoder) decode(name string, data interface{}, val reflect.Value) error {
--	if data == nil {
--		// If the data is nil, then we don't set anything.
--		return nil
+-// CreateOpts is a structure that holds parameters for creating an object.
+-type CreateOpts struct {
+-	Metadata           map[string]string
+-	ContentDisposition string `h:"Content-Disposition"`
+-	ContentEncoding    string `h:"Content-Encoding"`
+-	ContentLength      int    `h:"Content-Length"`
+-	ContentType        string `h:"Content-Type"`
+-	CopyFrom           string `h:"X-Copy-From"`
+-	DeleteAfter        int    `h:"X-Delete-After"`
+-	DeleteAt           int    `h:"X-Delete-At"`
+-	DetectContentType  string `h:"X-Detect-Content-Type"`
+-	ETag               string `h:"ETag"`
+-	IfNoneMatch        string `h:"If-None-Match"`
+-	ObjectManifest     string `h:"X-Object-Manifest"`
+-	TransferEncoding   string `h:"Transfer-Encoding"`
+-	Expires            string `q:"expires"`
+-	MultipartManifest  string `q:"multiple-manifest"`
+-	Signature          string `q:"signature"`
+-}
+-
+-// ToObjectCreateParams formats a CreateOpts into a query string and map of
+-// headers.
+-func (opts CreateOpts) ToObjectCreateParams() (map[string]string, string, error) {
+-	q, err := gophercloud.BuildQueryString(opts)
+-	if err != nil {
+-		return nil, "", err
+-	}
+-	h, err := gophercloud.BuildHeaders(opts)
+-	if err != nil {
+-		return nil, q.String(), err
 -	}
 -
--	dataVal := reflect.ValueOf(data)
--	if !dataVal.IsValid() {
--		// If the data value is invalid, then we just set the value
--		// to be the zero value.
--		val.Set(reflect.Zero(val.Type()))
--		return nil
+-	for k, v := range opts.Metadata {
+-		h["X-Object-Meta-"+k] = v
 -	}
 -
--	if d.config.DecodeHook != nil {
--		// We have a DecodeHook, so let's pre-process the data.
--		var err error
--		data, err = d.config.DecodeHook(getKind(dataVal), getKind(val), data)
+-	return h, q.String(), nil
+-}
+-
+-// Create is a function that creates a new object or replaces an existing object.
+-func Create(c *gophercloud.ServiceClient, containerName, objectName string, content io.Reader, opts CreateOptsBuilder) CreateResult {
+-	var res CreateResult
+-
+-	url := createURL(c, containerName, objectName)
+-	h := c.AuthenticatedHeaders()
+-
+-	if opts != nil {
+-		headers, query, err := opts.ToObjectCreateParams()
 -		if err != nil {
--			return err
+-			res.Err = err
+-			return res
 -		}
--	}
 -
--	var err error
--	dataKind := getKind(val)
--	switch dataKind {
--	case reflect.Bool:
--		err = d.decodeBool(name, data, val)
--	case reflect.Interface:
--		err = d.decodeBasic(name, data, val)
--	case reflect.String:
--		err = d.decodeString(name, data, val)
--	case reflect.Int:
--		err = d.decodeInt(name, data, val)
--	case reflect.Uint:
--		err = d.decodeUint(name, data, val)
--	case reflect.Float32:
--		err = d.decodeFloat(name, data, val)
--	case reflect.Struct:
--		err = d.decodeStruct(name, data, val)
--	case reflect.Map:
--		err = d.decodeMap(name, data, val)
--	case reflect.Ptr:
--		err = d.decodePtr(name, data, val)
--	case reflect.Slice:
--		err = d.decodeSlice(name, data, val)
--	default:
--		// If we reached this point then we weren't able to decode it
--		return fmt.Errorf("%s: unsupported type: %s", name, dataKind)
--	}
+-		for k, v := range headers {
+-			h[k] = v
+-		}
 -
--	// If we reached here, then we successfully decoded SOMETHING, so
--	// mark the key as used if we're tracking metadata.
--	if d.config.Metadata != nil && name != "" {
--		d.config.Metadata.Keys = append(d.config.Metadata.Keys, name)
+-		url += query
 -	}
 -
--	return err
+-	contentType := h["Content-Type"]
+-
+-	resp, err := perigee.Request("PUT", url, perigee.Options{
+-		ContentType: contentType,
+-		ReqBody:     content,
+-		MoreHeaders: h,
+-		OkCodes:     []int{201, 202},
+-	})
+-	res.Header = resp.HttpResponse.Header
+-	res.Err = err
+-	return res
 -}
 -
--// This decodes a basic type (bool, int, string, etc.) and sets the
--// value to "data" of that type.
--func (d *Decoder) decodeBasic(name string, data interface{}, val reflect.Value) error {
--	dataVal := reflect.ValueOf(data)
--	dataValType := dataVal.Type()
--	if !dataValType.AssignableTo(val.Type()) {
--		return fmt.Errorf(
--			"'%s' expected type '%s', got '%s'",
--			name, val.Type(), dataValType)
--	}
+-// CopyOptsBuilder allows extensions to add additional parameters to the
+-// Copy request.
+-type CopyOptsBuilder interface {
+-	ToObjectCopyMap() (map[string]string, error)
+-}
 -
--	val.Set(dataVal)
--	return nil
+-// CopyOpts is a structure that holds parameters for copying one object to
+-// another.
+-type CopyOpts struct {
+-	Metadata           map[string]string
+-	ContentDisposition string `h:"Content-Disposition"`
+-	ContentEncoding    string `h:"Content-Encoding"`
+-	ContentType        string `h:"Content-Type"`
+-	Destination        string `h:"Destination,required"`
 -}
 -
--func (d *Decoder) decodeString(name string, data interface{}, val reflect.Value) error {
--	dataVal := reflect.ValueOf(data)
--	dataKind := getKind(dataVal)
+-// ToObjectCopyMap formats a CopyOpts into a map of headers.
+-func (opts CopyOpts) ToObjectCopyMap() (map[string]string, error) {
+-	if opts.Destination == "" {
+-		return nil, fmt.Errorf("Required CopyOpts field 'Destination' not set.")
+-	}
+-	h, err := gophercloud.BuildHeaders(opts)
+-	if err != nil {
+-		return nil, err
+-	}
+-	for k, v := range opts.Metadata {
+-		h["X-Object-Meta-"+k] = v
+-	}
+-	return h, nil
+-}
 -
--	converted := true
--	switch {
--	case dataKind == reflect.String:
--		val.SetString(dataVal.String())
--	case dataKind == reflect.Bool && d.config.WeaklyTypedInput:
--		if dataVal.Bool() {
--			val.SetString("1")
--		} else {
--			val.SetString("0")
--		}
--	case dataKind == reflect.Int && d.config.WeaklyTypedInput:
--		val.SetString(strconv.FormatInt(dataVal.Int(), 10))
--	case dataKind == reflect.Uint && d.config.WeaklyTypedInput:
--		val.SetString(strconv.FormatUint(dataVal.Uint(), 10))
--	case dataKind == reflect.Float32 && d.config.WeaklyTypedInput:
--		val.SetString(strconv.FormatFloat(dataVal.Float(), 'f', -1, 64))
--	case dataKind == reflect.Slice && d.config.WeaklyTypedInput:
--		dataType := dataVal.Type()
--		elemKind := dataType.Elem().Kind()
--		switch {
--		case elemKind == reflect.Uint8:
--			val.SetString(string(dataVal.Interface().([]uint8)))
--		default:
--			converted = false
--		}
--	default:
--		converted = false
+-// Copy is a function that copies one object to another.
+-func Copy(c *gophercloud.ServiceClient, containerName, objectName string, opts CopyOptsBuilder) CopyResult {
+-	var res CopyResult
+-	h := c.AuthenticatedHeaders()
+-
+-	headers, err := opts.ToObjectCopyMap()
+-	if err != nil {
+-		res.Err = err
+-		return res
 -	}
 -
--	if !converted {
--		return fmt.Errorf(
--			"'%s' expected type '%s', got unconvertible type '%s'",
--			name, val.Type(), dataVal.Type())
+-	for k, v := range headers {
+-		h[k] = v
 -	}
 -
--	return nil
+-	url := copyURL(c, containerName, objectName)
+-	resp, err := perigee.Request("COPY", url, perigee.Options{
+-		MoreHeaders: h,
+-		OkCodes:     []int{201},
+-	})
+-	res.Header = resp.HttpResponse.Header
+-	res.Err = err
+-	return res
 -}
 -
--func (d *Decoder) decodeInt(name string, data interface{}, val reflect.Value) error {
--	dataVal := reflect.ValueOf(data)
--	dataKind := getKind(dataVal)
+-// DeleteOptsBuilder allows extensions to add additional parameters to the
+-// Delete request.
+-type DeleteOptsBuilder interface {
+-	ToObjectDeleteQuery() (string, error)
+-}
 -
--	switch {
--	case dataKind == reflect.Int:
--		val.SetInt(dataVal.Int())
--	case dataKind == reflect.Uint:
--		val.SetInt(int64(dataVal.Uint()))
--	case dataKind == reflect.Float32:
--		val.SetInt(int64(dataVal.Float()))
--	case dataKind == reflect.Bool && d.config.WeaklyTypedInput:
--		if dataVal.Bool() {
--			val.SetInt(1)
--		} else {
--			val.SetInt(0)
--		}
--	case dataKind == reflect.String && d.config.WeaklyTypedInput:
--		i, err := strconv.ParseInt(dataVal.String(), 0, val.Type().Bits())
--		if err == nil {
--			val.SetInt(i)
--		} else {
--			return fmt.Errorf("cannot parse '%s' as int: %s", name, err)
--		}
--	default:
--		return fmt.Errorf(
--			"'%s' expected type '%s', got unconvertible type '%s'",
--			name, val.Type(), dataVal.Type())
--	}
+-// DeleteOpts is a structure that holds parameters for deleting an object.
+-type DeleteOpts struct {
+-	MultipartManifest string `q:"multipart-manifest"`
+-}
 -
--	return nil
+-// ToObjectDeleteQuery formats a DeleteOpts into a query string.
+-func (opts DeleteOpts) ToObjectDeleteQuery() (string, error) {
+-	q, err := gophercloud.BuildQueryString(opts)
+-	if err != nil {
+-		return "", err
+-	}
+-	return q.String(), nil
 -}
 -
--func (d *Decoder) decodeUint(name string, data interface{}, val reflect.Value) error {
--	dataVal := reflect.ValueOf(data)
--	dataKind := getKind(dataVal)
+-// Delete is a function that deletes an object.
+-func Delete(c *gophercloud.ServiceClient, containerName, objectName string, opts DeleteOptsBuilder) DeleteResult {
+-	var res DeleteResult
+-	url := deleteURL(c, containerName, objectName)
 -
--	switch {
--	case dataKind == reflect.Int:
--		val.SetUint(uint64(dataVal.Int()))
--	case dataKind == reflect.Uint:
--		val.SetUint(dataVal.Uint())
--	case dataKind == reflect.Float32:
--		val.SetUint(uint64(dataVal.Float()))
--	case dataKind == reflect.Bool && d.config.WeaklyTypedInput:
--		if dataVal.Bool() {
--			val.SetUint(1)
--		} else {
--			val.SetUint(0)
--		}
--	case dataKind == reflect.String && d.config.WeaklyTypedInput:
--		i, err := strconv.ParseUint(dataVal.String(), 0, val.Type().Bits())
--		if err == nil {
--			val.SetUint(i)
--		} else {
--			return fmt.Errorf("cannot parse '%s' as uint: %s", name, err)
+-	if opts != nil {
+-		query, err := opts.ToObjectDeleteQuery()
+-		if err != nil {
+-			res.Err = err
+-			return res
 -		}
--	default:
--		return fmt.Errorf(
--			"'%s' expected type '%s', got unconvertible type '%s'",
--			name, val.Type(), dataVal.Type())
+-		url += query
 -	}
 -
--	return nil
+-	resp, err := perigee.Request("DELETE", url, perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{204},
+-	})
+-	res.Header = resp.HttpResponse.Header
+-	res.Err = err
+-	return res
 -}
 -
--func (d *Decoder) decodeBool(name string, data interface{}, val reflect.Value) error {
--	dataVal := reflect.ValueOf(data)
--	dataKind := getKind(dataVal)
+-// GetOptsBuilder allows extensions to add additional parameters to the
+-// Get request.
+-type GetOptsBuilder interface {
+-	ToObjectGetQuery() (string, error)
+-}
 -
--	switch {
--	case dataKind == reflect.Bool:
--		val.SetBool(dataVal.Bool())
--	case dataKind == reflect.Int && d.config.WeaklyTypedInput:
--		val.SetBool(dataVal.Int() != 0)
--	case dataKind == reflect.Uint && d.config.WeaklyTypedInput:
--		val.SetBool(dataVal.Uint() != 0)
--	case dataKind == reflect.Float32 && d.config.WeaklyTypedInput:
--		val.SetBool(dataVal.Float() != 0)
--	case dataKind == reflect.String && d.config.WeaklyTypedInput:
--		b, err := strconv.ParseBool(dataVal.String())
--		if err == nil {
--			val.SetBool(b)
--		} else if dataVal.String() == "" {
--			val.SetBool(false)
--		} else {
--			return fmt.Errorf("cannot parse '%s' as bool: %s", name, err)
--		}
--	default:
--		return fmt.Errorf(
--			"'%s' expected type '%s', got unconvertible type '%s'",
--			name, val.Type(), dataVal.Type())
--	}
+-// GetOpts is a structure that holds parameters for getting an object's metadata.
+-type GetOpts struct {
+-	Expires   string `q:"expires"`
+-	Signature string `q:"signature"`
+-}
 -
--	return nil
+-// ToObjectGetQuery formats a GetOpts into a query string.
+-func (opts GetOpts) ToObjectGetQuery() (string, error) {
+-	q, err := gophercloud.BuildQueryString(opts)
+-	if err != nil {
+-		return "", err
+-	}
+-	return q.String(), nil
 -}
 -
--func (d *Decoder) decodeFloat(name string, data interface{}, val reflect.Value) error {
--	dataVal := reflect.ValueOf(data)
--	dataKind := getKind(dataVal)
+-// Get is a function that retrieves the metadata of an object. To extract just the custom
+-// metadata, pass the GetResult response to the ExtractMetadata function.
+-func Get(c *gophercloud.ServiceClient, containerName, objectName string, opts GetOptsBuilder) GetResult {
+-	var res GetResult
+-	url := getURL(c, containerName, objectName)
 -
--	switch {
--	case dataKind == reflect.Int:
--		val.SetFloat(float64(dataVal.Int()))
--	case dataKind == reflect.Uint:
--		val.SetFloat(float64(dataVal.Uint()))
--	case dataKind == reflect.Float32:
--		val.SetFloat(float64(dataVal.Float()))
--	case dataKind == reflect.Bool && d.config.WeaklyTypedInput:
--		if dataVal.Bool() {
--			val.SetFloat(1)
--		} else {
--			val.SetFloat(0)
--		}
--	case dataKind == reflect.String && d.config.WeaklyTypedInput:
--		f, err := strconv.ParseFloat(dataVal.String(), val.Type().Bits())
--		if err == nil {
--			val.SetFloat(f)
--		} else {
--			return fmt.Errorf("cannot parse '%s' as float: %s", name, err)
+-	if opts != nil {
+-		query, err := opts.ToObjectGetQuery()
+-		if err != nil {
+-			res.Err = err
+-			return res
 -		}
--	default:
--		return fmt.Errorf(
--			"'%s' expected type '%s', got unconvertible type '%s'",
--			name, val.Type(), dataVal.Type())
+-		url += query
 -	}
 -
--	return nil
+-	resp, err := perigee.Request("HEAD", url, perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{200, 204},
+-	})
+-	res.Header = resp.HttpResponse.Header
+-	res.Err = err
+-	return res
 -}
 -
--func (d *Decoder) decodeMap(name string, data interface{}, val reflect.Value) error {
--	valType := val.Type()
--	valKeyType := valType.Key()
--	valElemType := valType.Elem()
+-// UpdateOptsBuilder allows extensions to add additional parameters to the
+-// Update request.
+-type UpdateOptsBuilder interface {
+-	ToObjectUpdateMap() (map[string]string, error)
+-}
 -
--	// Make a new map to hold our result
--	mapType := reflect.MapOf(valKeyType, valElemType)
--	valMap := reflect.MakeMap(mapType)
+-// UpdateOpts is a structure that holds parameters for updating, creating, or deleting an
+-// object's metadata.
+-type UpdateOpts struct {
+-	Metadata           map[string]string
+-	ContentDisposition string `h:"Content-Disposition"`
+-	ContentEncoding    string `h:"Content-Encoding"`
+-	ContentType        string `h:"Content-Type"`
+-	DeleteAfter        int    `h:"X-Delete-After"`
+-	DeleteAt           int    `h:"X-Delete-At"`
+-	DetectContentType  bool   `h:"X-Detect-Content-Type"`
+-}
 -
--	// Check input type
--	dataVal := reflect.Indirect(reflect.ValueOf(data))
--	if dataVal.Kind() != reflect.Map {
--		// Accept empty array/slice instead of an empty map in weakly typed mode
--		if d.config.WeaklyTypedInput &&
--			(dataVal.Kind() == reflect.Slice || dataVal.Kind() == reflect.Array) &&
--			dataVal.Len() == 0 {
--			val.Set(valMap)
--			return nil
--		} else {
--			return fmt.Errorf("'%s' expected a map, got '%s'", name, dataVal.Kind())
--		}
+-// ToObjectUpdateMap formats a UpdateOpts into a map of headers.
+-func (opts UpdateOpts) ToObjectUpdateMap() (map[string]string, error) {
+-	h, err := gophercloud.BuildHeaders(opts)
+-	if err != nil {
+-		return nil, err
 -	}
+-	for k, v := range opts.Metadata {
+-		h["X-Object-Meta-"+k] = v
+-	}
+-	return h, nil
+-}
 -
--	// Accumulate errors
--	errors := make([]string, 0)
--
--	for _, k := range dataVal.MapKeys() {
--		fieldName := fmt.Sprintf("%s[%s]", name, k)
+-// Update is a function that creates, updates, or deletes an object's metadata.
+-func Update(c *gophercloud.ServiceClient, containerName, objectName string, opts UpdateOptsBuilder) UpdateResult {
+-	var res UpdateResult
+-	h := c.AuthenticatedHeaders()
 -
--		// First decode the key into the proper type
--		currentKey := reflect.Indirect(reflect.New(valKeyType))
--		if err := d.decode(fieldName, k.Interface(), currentKey); err != nil {
--			errors = appendErrors(errors, err)
--			continue
+-	if opts != nil {
+-		headers, err := opts.ToObjectUpdateMap()
+-		if err != nil {
+-			res.Err = err
+-			return res
 -		}
 -
--		// Next decode the data into the proper type
--		v := dataVal.MapIndex(k).Interface()
--		currentVal := reflect.Indirect(reflect.New(valElemType))
--		if err := d.decode(fieldName, v, currentVal); err != nil {
--			errors = appendErrors(errors, err)
--			continue
+-		for k, v := range headers {
+-			h[k] = v
 -		}
--
--		valMap.SetMapIndex(currentKey, currentVal)
 -	}
 -
--	// Set the built up map to the value
--	val.Set(valMap)
+-	url := updateURL(c, containerName, objectName)
+-	resp, err := perigee.Request("POST", url, perigee.Options{
+-		MoreHeaders: h,
+-		OkCodes:     []int{202},
+-	})
+-	res.Header = resp.HttpResponse.Header
+-	res.Err = err
+-	return res
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/requests_test.go
+deleted file mode 100644
+index c3c28a7..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/requests_test.go
++++ /dev/null
+@@ -1,132 +0,0 @@
+-package objects
 -
--	// If we had errors, return those
--	if len(errors) > 0 {
--		return &Error{errors}
--	}
+-import (
+-	"bytes"
+-	"io"
+-	"testing"
 -
--	return nil
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
+-
+-func TestDownloadReader(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleDownloadObjectSuccessfully(t)
+-
+-	response := Download(fake.ServiceClient(), "testContainer", "testObject", nil)
+-	defer response.Body.Close()
+-
+-	// Check reader
+-	buf := bytes.NewBuffer(make([]byte, 0))
+-	io.CopyN(buf, response.Body, 10)
+-	th.CheckEquals(t, "Successful", string(buf.Bytes()))
 -}
 -
--func (d *Decoder) decodePtr(name string, data interface{}, val reflect.Value) error {
--	// Create an element of the concrete (non pointer) type and decode
--	// into that. Then set the value of the pointer to this type.
--	valType := val.Type()
--	valElemType := valType.Elem()
--	realVal := reflect.New(valElemType)
--	if err := d.decode(name, data, reflect.Indirect(realVal)); err != nil {
--		return err
--	}
+-func TestDownloadExtraction(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleDownloadObjectSuccessfully(t)
 -
--	val.Set(realVal)
--	return nil
+-	response := Download(fake.ServiceClient(), "testContainer", "testObject", nil)
+-
+-	// Check []byte extraction
+-	bytes, err := response.ExtractContent()
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, "Successful download with Gophercloud", string(bytes))
 -}
 -
--func (d *Decoder) decodeSlice(name string, data interface{}, val reflect.Value) error {
--	dataVal := reflect.Indirect(reflect.ValueOf(data))
--	dataValKind := dataVal.Kind()
--	valType := val.Type()
--	valElemType := valType.Elem()
--	sliceType := reflect.SliceOf(valElemType)
+-func TestListObjectInfo(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleListObjectsInfoSuccessfully(t)
 -
--	// Check input type
--	if dataValKind != reflect.Array && dataValKind != reflect.Slice {
--		// Accept empty map instead of array/slice in weakly typed mode
--		if d.config.WeaklyTypedInput && dataVal.Kind() == reflect.Map && dataVal.Len() == 0 {
--			val.Set(reflect.MakeSlice(sliceType, 0, 0))
--			return nil
--		} else {
--			return fmt.Errorf(
--				"'%s': source data must be an array or slice, got %s", name, dataValKind)
--		}
--	}
+-	count := 0
+-	options := &ListOpts{Full: true}
+-	err := List(fake.ServiceClient(), "testContainer", options).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractInfo(page)
+-		th.AssertNoErr(t, err)
 -
--	// Make a new slice to hold our result, same size as the original data.
--	valSlice := reflect.MakeSlice(sliceType, dataVal.Len(), dataVal.Len())
+-		th.CheckDeepEquals(t, ExpectedListInfo, actual)
 -
--	// Accumulate any errors
--	errors := make([]string, 0)
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, count, 1)
+-}
 -
--	for i := 0; i < dataVal.Len(); i++ {
--		currentData := dataVal.Index(i).Interface()
--		currentField := valSlice.Index(i)
+-func TestListObjectNames(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleListObjectNamesSuccessfully(t)
 -
--		fieldName := fmt.Sprintf("%s[%d]", name, i)
--		if err := d.decode(fieldName, currentData, currentField); err != nil {
--			errors = appendErrors(errors, err)
+-	count := 0
+-	options := &ListOpts{Full: false}
+-	err := List(fake.ServiceClient(), "testContainer", options).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractNames(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract container names: %v", err)
+-			return false, err
 -		}
--	}
--
--	// Finally, set the value to the slice we built up
--	val.Set(valSlice)
 -
--	// If there were errors, we return those
--	if len(errors) > 0 {
--		return &Error{errors}
--	}
+-		th.CheckDeepEquals(t, ExpectedListNames, actual)
 -
--	return nil
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, count, 1)
 -}
 -
--func (d *Decoder) decodeStruct(name string, data interface{}, val reflect.Value) error {
--	dataVal := reflect.Indirect(reflect.ValueOf(data))
--	dataValKind := dataVal.Kind()
--	if dataValKind != reflect.Map {
--		return fmt.Errorf("'%s' expected a map, got '%s'", name, dataValKind)
--	}
+-func TestCreateObject(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleCreateObjectSuccessfully(t)
 -
--	dataValType := dataVal.Type()
--	if kind := dataValType.Key().Kind(); kind != reflect.String && kind != reflect.Interface {
--		return fmt.Errorf(
--			"'%s' needs a map with string keys, has '%s' keys",
--			name, dataValType.Key().Kind())
--	}
+-	content := bytes.NewBufferString("Did gyre and gimble in the wabe")
+-	options := &CreateOpts{ContentType: "application/json"}
+-	res := Create(fake.ServiceClient(), "testContainer", "testObject", content, options)
+-	th.AssertNoErr(t, res.Err)
+-}
 -
--	dataValKeys := make(map[reflect.Value]struct{})
--	dataValKeysUnused := make(map[interface{}]struct{})
--	for _, dataValKey := range dataVal.MapKeys() {
--		dataValKeys[dataValKey] = struct{}{}
--		dataValKeysUnused[dataValKey.Interface()] = struct{}{}
--	}
+-func TestCopyObject(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleCopyObjectSuccessfully(t)
 -
--	errors := make([]string, 0)
+-	options := &CopyOpts{Destination: "/newTestContainer/newTestObject"}
+-	res := Copy(fake.ServiceClient(), "testContainer", "testObject", options)
+-	th.AssertNoErr(t, res.Err)
+-}
 -
--	// This slice will keep track of all the structs we'll be decoding.
--	// There can be more than one struct if there are embedded structs
--	// that are squashed.
--	structs := make([]reflect.Value, 1, 5)
--	structs[0] = val
+-func TestDeleteObject(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleDeleteObjectSuccessfully(t)
 -
--	// Compile the list of all the fields that we're going to be decoding
--	// from all the structs.
--	fields := make(map[*reflect.StructField]reflect.Value)
--	for len(structs) > 0 {
--		structVal := structs[0]
--		structs = structs[1:]
+-	res := Delete(fake.ServiceClient(), "testContainer", "testObject", nil)
+-	th.AssertNoErr(t, res.Err)
+-}
 -
--		structType := structVal.Type()
--		for i := 0; i < structType.NumField(); i++ {
--			fieldType := structType.Field(i)
+-func TestUpateObjectMetadata(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleUpdateObjectSuccessfully(t)
 -
--			if fieldType.Anonymous {
--				fieldKind := fieldType.Type.Kind()
--				if fieldKind != reflect.Struct {
--					errors = appendErrors(errors,
--						fmt.Errorf("%s: unsupported type: %s", fieldType.Name, fieldKind))
--					continue
--				}
+-	options := &UpdateOpts{Metadata: map[string]string{"Gophercloud-Test": "objects"}}
+-	res := Update(fake.ServiceClient(), "testContainer", "testObject", options)
+-	th.AssertNoErr(t, res.Err)
+-}
 -
--				// We have an embedded field. We "squash" the fields down
--				// if specified in the tag.
--				squash := false
--				tagParts := strings.Split(fieldType.Tag.Get(d.config.TagName), ",")
--				for _, tag := range tagParts[1:] {
--					if tag == "squash" {
--						squash = true
--						break
--					}
--				}
+-func TestGetObject(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	HandleGetObjectSuccessfully(t)
 -
--				if squash {
--					structs = append(structs, val.FieldByName(fieldType.Name))
--					continue
--				}
--			}
+-	expected := map[string]string{"Gophercloud-Test": "objects"}
+-	actual, err := Get(fake.ServiceClient(), "testContainer", "testObject", nil).ExtractMetadata()
+-	th.AssertNoErr(t, err)
+-	th.CheckDeepEquals(t, expected, actual)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/results.go
+deleted file mode 100644
+index 102d94c..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/results.go
++++ /dev/null
+@@ -1,162 +0,0 @@
+-package objects
 -
--			// Normal struct field, store it away
--			fields[&fieldType] = structVal.Field(i)
--		}
--	}
+-import (
+-	"fmt"
+-	"io"
+-	"io/ioutil"
+-	"strings"
 -
--	for fieldType, field := range fields {
--		fieldName := fieldType.Name
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
 -
--		tagValue := fieldType.Tag.Get(d.config.TagName)
--		tagValue = strings.SplitN(tagValue, ",", 2)[0]
--		if tagValue != "" {
--			fieldName = tagValue
--		}
+-	"github.com/mitchellh/mapstructure"
+-)
 -
--		rawMapKey := reflect.ValueOf(fieldName)
--		rawMapVal := dataVal.MapIndex(rawMapKey)
--		if !rawMapVal.IsValid() {
--			// Do a slower search by iterating over each key and
--			// doing case-insensitive search.
--			for dataValKey, _ := range dataValKeys {
--				mK, ok := dataValKey.Interface().(string)
--				if !ok {
--					// Not a string key
--					continue
--				}
+-// Object is a structure that holds information related to a storage object.
+-type Object struct {
+-	Bytes        int    `json:"bytes" mapstructure:"bytes"`
+-	ContentType  string `json:"content_type" mapstructure:"content_type"`
+-	Hash         string `json:"hash" mapstructure:"hash"`
+-	LastModified string `json:"last_modified" mapstructure:"last_modified"`
+-	Name         string `json:"name" mapstructure:"name"`
+-}
 -
--				if strings.EqualFold(mK, fieldName) {
--					rawMapKey = dataValKey
--					rawMapVal = dataVal.MapIndex(dataValKey)
--					break
--				}
--			}
+-// ObjectPage is a single page of objects that is returned from a call to the
+-// List function.
+-type ObjectPage struct {
+-	pagination.MarkerPageBase
+-}
 -
--			if !rawMapVal.IsValid() {
--				// There was no matching key in the map for the value in
--				// the struct. Just ignore.
--				continue
--			}
--		}
+-// IsEmpty returns true if a ListResult contains no object names.
+-func (r ObjectPage) IsEmpty() (bool, error) {
+-	names, err := ExtractNames(r)
+-	if err != nil {
+-		return true, err
+-	}
+-	return len(names) == 0, nil
+-}
 -
--		// Delete the key we're using from the unused map so we stop tracking
--		delete(dataValKeysUnused, rawMapKey.Interface())
+-// LastMarker returns the last object name in a ListResult.
+-func (r ObjectPage) LastMarker() (string, error) {
+-	names, err := ExtractNames(r)
+-	if err != nil {
+-		return "", err
+-	}
+-	if len(names) == 0 {
+-		return "", nil
+-	}
+-	return names[len(names)-1], nil
+-}
 -
--		if !field.IsValid() {
--			// This should never happen
--			panic("field is not valid")
+-// ExtractInfo is a function that takes a page of objects and returns their full information.
+-func ExtractInfo(page pagination.Page) ([]Object, error) {
+-	untyped := page.(ObjectPage).Body.([]interface{})
+-	results := make([]Object, len(untyped))
+-	for index, each := range untyped {
+-		object := each.(map[string]interface{})
+-		err := mapstructure.Decode(object, &results[index])
+-		if err != nil {
+-			return results, err
 -		}
+-	}
+-	return results, nil
+-}
 -
--		// If we can't set the field, then it is unexported or something,
--		// and we just continue onwards.
--		if !field.CanSet() {
--			continue
+-// ExtractNames is a function that takes a page of objects and returns only their names.
+-func ExtractNames(page pagination.Page) ([]string, error) {
+-	casted := page.(ObjectPage)
+-	ct := casted.Header.Get("Content-Type")
+-	switch {
+-	case strings.HasPrefix(ct, "application/json"):
+-		parsed, err := ExtractInfo(page)
+-		if err != nil {
+-			return nil, err
 -		}
 -
--		// If the name is empty string, then we're at the root, and we
--		// don't dot-join the fields.
--		if name != "" {
--			fieldName = fmt.Sprintf("%s.%s", name, fieldName)
+-		names := make([]string, 0, len(parsed))
+-		for _, object := range parsed {
+-			names = append(names, object.Name)
 -		}
 -
--		if err := d.decode(fieldName, rawMapVal.Interface(), field); err != nil {
--			errors = appendErrors(errors, err)
--		}
--	}
+-		return names, nil
+-	case strings.HasPrefix(ct, "text/plain"):
+-		names := make([]string, 0, 50)
 -
--	if d.config.ErrorUnused && len(dataValKeysUnused) > 0 {
--		keys := make([]string, 0, len(dataValKeysUnused))
--		for rawKey, _ := range dataValKeysUnused {
--			keys = append(keys, rawKey.(string))
+-		body := string(page.(ObjectPage).Body.([]uint8))
+-		for _, name := range strings.Split(body, "\n") {
+-			if len(name) > 0 {
+-				names = append(names, name)
+-			}
 -		}
--		sort.Strings(keys)
 -
--		err := fmt.Errorf("'%s' has invalid keys: %s", name, strings.Join(keys, ", "))
--		errors = appendErrors(errors, err)
+-		return names, nil
+-	case strings.HasPrefix(ct, "text/html"):
+-		return []string{}, nil
+-	default:
+-		return nil, fmt.Errorf("Cannot extract names from response with content-type: [%s]", ct)
 -	}
+-}
 -
--	if len(errors) > 0 {
--		return &Error{errors}
+-// DownloadResult is a *http.Response that is returned from a call to the Download function.
+-type DownloadResult struct {
+-	gophercloud.HeaderResult
+-	Body io.ReadCloser
+-}
+-
+-// ExtractContent is a function that takes a DownloadResult's io.Reader body
+-// and reads all available data into a slice of bytes. Please be aware that due
+-// the nature of io.Reader is forward-only - meaning that it can only be read
+-// once and not rewound. You can recreate a reader from the output of this
+-// function by using bytes.NewReader(downloadBytes)
+-func (dr DownloadResult) ExtractContent() ([]byte, error) {
+-	if dr.Err != nil {
+-		return nil, dr.Err
+-	}
+-	body, err := ioutil.ReadAll(dr.Body)
+-	if err != nil {
+-		return nil, err
 -	}
+-	dr.Body.Close()
+-	return body, nil
+-}
 -
--	// Add the unused keys to the list of unused keys if we're tracking metadata
--	if d.config.Metadata != nil {
--		for rawKey, _ := range dataValKeysUnused {
--			key := rawKey.(string)
--			if name != "" {
--				key = fmt.Sprintf("%s.%s", name, key)
--			}
+-// GetResult is a *http.Response that is returned from a call to the Get function.
+-type GetResult struct {
+-	gophercloud.HeaderResult
+-}
 -
--			d.config.Metadata.Unused = append(d.config.Metadata.Unused, key)
+-// ExtractMetadata is a function that takes a GetResult (of type *http.Response)
+-// and returns the custom metadata associated with the object.
+-func (gr GetResult) ExtractMetadata() (map[string]string, error) {
+-	if gr.Err != nil {
+-		return nil, gr.Err
+-	}
+-	metadata := make(map[string]string)
+-	for k, v := range gr.Header {
+-		if strings.HasPrefix(k, "X-Object-Meta-") {
+-			key := strings.TrimPrefix(k, "X-Object-Meta-")
+-			metadata[key] = v[0]
 -		}
 -	}
+-	return metadata, nil
+-}
 -
--	return nil
+-// CreateResult represents the result of a create operation.
+-type CreateResult struct {
+-	gophercloud.HeaderResult
 -}
 -
--func getKind(val reflect.Value) reflect.Kind {
--	kind := val.Kind()
+-// UpdateResult represents the result of an update operation.
+-type UpdateResult struct {
+-	gophercloud.HeaderResult
+-}
 -
--	switch {
--	case kind >= reflect.Int && kind <= reflect.Int64:
--		return reflect.Int
--	case kind >= reflect.Uint && kind <= reflect.Uint64:
--		return reflect.Uint
--	case kind >= reflect.Float32 && kind <= reflect.Float64:
--		return reflect.Float32
--	default:
--		return kind
--	}
+-// DeleteResult represents the result of a delete operation.
+-type DeleteResult struct {
+-	gophercloud.HeaderResult
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_benchmark_test.go b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_benchmark_test.go
+-
+-// CopyResult represents the result of a copy operation.
+-type CopyResult struct {
+-	gophercloud.HeaderResult
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/urls.go
 deleted file mode 100644
-index b50ac36..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_benchmark_test.go
+index d2ec62c..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/urls.go
 +++ /dev/null
-@@ -1,243 +0,0 @@
--package mapstructure
+@@ -1,33 +0,0 @@
+-package objects
 -
 -import (
--	"testing"
+-	"github.com/rackspace/gophercloud"
 -)
 -
--func Benchmark_Decode(b *testing.B) {
--	type Person struct {
--		Name   string
--		Age    int
--		Emails []string
--		Extra  map[string]string
--	}
+-func listURL(c *gophercloud.ServiceClient, container string) string {
+-	return c.ServiceURL(container)
+-}
 -
--	input := map[string]interface{}{
--		"name":   "Mitchell",
--		"age":    91,
--		"emails": []string{"one", "two", "three"},
--		"extra": map[string]string{
--			"twitter": "mitchellh",
--		},
--	}
+-func copyURL(c *gophercloud.ServiceClient, container, object string) string {
+-	return c.ServiceURL(container, object)
+-}
 -
--	var result Person
--	for i := 0; i < b.N; i++ {
--		Decode(input, &result)
--	}
+-func createURL(c *gophercloud.ServiceClient, container, object string) string {
+-	return copyURL(c, container, object)
 -}
 -
--func Benchmark_DecodeBasic(b *testing.B) {
--	input := map[string]interface{}{
--		"vstring": "foo",
--		"vint":    42,
--		"Vuint":   42,
--		"vbool":   true,
--		"Vfloat":  42.42,
--		"vsilent": true,
--		"vdata":   42,
--	}
+-func getURL(c *gophercloud.ServiceClient, container, object string) string {
+-	return copyURL(c, container, object)
+-}
 -
--	var result Basic
--	for i := 0; i < b.N; i++ {
--		Decode(input, &result)
--	}
+-func deleteURL(c *gophercloud.ServiceClient, container, object string) string {
+-	return copyURL(c, container, object)
 -}
 -
--func Benchmark_DecodeEmbedded(b *testing.B) {
--	input := map[string]interface{}{
--		"vstring": "foo",
--		"Basic": map[string]interface{}{
--			"vstring": "innerfoo",
--		},
--		"vunique": "bar",
--	}
+-func downloadURL(c *gophercloud.ServiceClient, container, object string) string {
+-	return copyURL(c, container, object)
+-}
+-
+-func updateURL(c *gophercloud.ServiceClient, container, object string) string {
+-	return copyURL(c, container, object)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/urls_test.go
+deleted file mode 100644
+index 1dcfe35..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects/urls_test.go
++++ /dev/null
+@@ -1,56 +0,0 @@
+-package objects
+-
+-import (
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-const endpoint = "http://localhost:57909/"
 -
--	var result Embedded
--	for i := 0; i < b.N; i++ {
--		Decode(input, &result)
--	}
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint}
 -}
 -
--func Benchmark_DecodeTypeConversion(b *testing.B) {
--	input := map[string]interface{}{
--		"IntToFloat":    42,
--		"IntToUint":     42,
--		"IntToBool":     1,
--		"IntToString":   42,
--		"UintToInt":     42,
--		"UintToFloat":   42,
--		"UintToBool":    42,
--		"UintToString":  42,
--		"BoolToInt":     true,
--		"BoolToUint":    true,
--		"BoolToFloat":   true,
--		"BoolToString":  true,
--		"FloatToInt":    42.42,
--		"FloatToUint":   42.42,
--		"FloatToBool":   42.42,
--		"FloatToString": 42.42,
--		"StringToInt":   "42",
--		"StringToUint":  "42",
--		"StringToBool":  "1",
--		"StringToFloat": "42.42",
--		"SliceToMap":    []interface{}{},
--		"MapToSlice":    map[string]interface{}{},
--	}
--
--	var resultStrict TypeConversionResult
--	for i := 0; i < b.N; i++ {
--		Decode(input, &resultStrict)
--	}
+-func TestListURL(t *testing.T) {
+-	actual := listURL(endpointClient(), "foo")
+-	expected := endpoint + "foo"
+-	th.CheckEquals(t, expected, actual)
 -}
 -
--func Benchmark_DecodeMap(b *testing.B) {
--	input := map[string]interface{}{
--		"vfoo": "foo",
--		"vother": map[interface{}]interface{}{
--			"foo": "foo",
--			"bar": "bar",
--		},
--	}
+-func TestCopyURL(t *testing.T) {
+-	actual := copyURL(endpointClient(), "foo", "bar")
+-	expected := endpoint + "foo/bar"
+-	th.CheckEquals(t, expected, actual)
+-}
 -
--	var result Map
--	for i := 0; i < b.N; i++ {
--		Decode(input, &result)
--	}
+-func TestCreateURL(t *testing.T) {
+-	actual := createURL(endpointClient(), "foo", "bar")
+-	expected := endpoint + "foo/bar"
+-	th.CheckEquals(t, expected, actual)
 -}
 -
--func Benchmark_DecodeMapOfStruct(b *testing.B) {
--	input := map[string]interface{}{
--		"value": map[string]interface{}{
--			"foo": map[string]string{"vstring": "one"},
--			"bar": map[string]string{"vstring": "two"},
--		},
--	}
+-func TestGetURL(t *testing.T) {
+-	actual := getURL(endpointClient(), "foo", "bar")
+-	expected := endpoint + "foo/bar"
+-	th.CheckEquals(t, expected, actual)
+-}
 -
--	var result MapOfStruct
--	for i := 0; i < b.N; i++ {
--		Decode(input, &result)
--	}
+-func TestDeleteURL(t *testing.T) {
+-	actual := deleteURL(endpointClient(), "foo", "bar")
+-	expected := endpoint + "foo/bar"
+-	th.CheckEquals(t, expected, actual)
 -}
 -
--func Benchmark_DecodeSlice(b *testing.B) {
--	input := map[string]interface{}{
--		"vfoo": "foo",
--		"vbar": []string{"foo", "bar", "baz"},
--	}
+-func TestDownloadURL(t *testing.T) {
+-	actual := downloadURL(endpointClient(), "foo", "bar")
+-	expected := endpoint + "foo/bar"
+-	th.CheckEquals(t, expected, actual)
+-}
 -
--	var result Slice
--	for i := 0; i < b.N; i++ {
--		Decode(input, &result)
--	}
+-func TestUpdateURL(t *testing.T) {
+-	actual := updateURL(endpointClient(), "foo", "bar")
+-	expected := endpoint + "foo/bar"
+-	th.CheckEquals(t, expected, actual)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/utils/choose_version.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/utils/choose_version.go
+deleted file mode 100644
+index a0d5b26..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/utils/choose_version.go
++++ /dev/null
+@@ -1,114 +0,0 @@
+-package utils
 -
--func Benchmark_DecodeSliceOfStruct(b *testing.B) {
--	input := map[string]interface{}{
--		"value": []map[string]interface{}{
--			{"vstring": "one"},
--			{"vstring": "two"},
--		},
--	}
+-import (
+-	"fmt"
+-	"strings"
 -
--	var result SliceOfStruct
--	for i := 0; i < b.N; i++ {
--		Decode(input, &result)
--	}
+-	"github.com/racker/perigee"
+-)
+-
+-// Version is a supported API version, corresponding to a vN package within the appropriate service.
+-type Version struct {
+-	ID       string
+-	Suffix   string
+-	Priority int
 -}
 -
--func Benchmark_DecodeWeaklyTypedInput(b *testing.B) {
--	type Person struct {
--		Name   string
--		Age    int
--		Emails []string
--	}
+-var goodStatus = map[string]bool{
+-	"current":   true,
+-	"supported": true,
+-	"stable":    true,
+-}
 -
--	// This input can come from anywhere, but typically comes from
--	// something like decoding JSON, generated by a weakly typed language
--	// such as PHP.
--	input := map[string]interface{}{
--		"name":   123,                      // number => string
--		"age":    "42",                     // string => number
--		"emails": map[string]interface{}{}, // empty map => empty array
+-// ChooseVersion queries the base endpoint of an API to choose the most recent non-experimental alternative from a service's
+-// published versions.
+-// It returns the highest-Priority Version among the alternatives that are provided, as well as its corresponding endpoint.
+-func ChooseVersion(identityBase string, identityEndpoint string, recognized []*Version) (*Version, string, error) {
+-	type linkResp struct {
+-		Href string `json:"href"`
+-		Rel  string `json:"rel"`
 -	}
 -
--	var result Person
--	config := &DecoderConfig{
--		WeaklyTypedInput: true,
--		Result:           &result,
+-	type valueResp struct {
+-		ID     string     `json:"id"`
+-		Status string     `json:"status"`
+-		Links  []linkResp `json:"links"`
 -	}
 -
--	decoder, err := NewDecoder(config)
--	if err != nil {
--		panic(err)
+-	type versionsResp struct {
+-		Values []valueResp `json:"values"`
 -	}
 -
--	for i := 0; i < b.N; i++ {
--		decoder.Decode(input)
+-	type response struct {
+-		Versions versionsResp `json:"versions"`
 -	}
--}
 -
--func Benchmark_DecodeMetadata(b *testing.B) {
--	type Person struct {
--		Name string
--		Age  int
+-	normalize := func(endpoint string) string {
+-		if !strings.HasSuffix(endpoint, "/") {
+-			return endpoint + "/"
+-		}
+-		return endpoint
 -	}
+-	identityEndpoint = normalize(identityEndpoint)
 -
--	input := map[string]interface{}{
--		"name":  "Mitchell",
--		"age":   91,
--		"email": "foo at bar.com",
+-	// If a full endpoint is specified, check version suffixes for a match first.
+-	for _, v := range recognized {
+-		if strings.HasSuffix(identityEndpoint, v.Suffix) {
+-			return v, identityEndpoint, nil
+-		}
 -	}
 -
--	var md Metadata
--	var result Person
--	config := &DecoderConfig{
--		Metadata: &md,
--		Result:   &result,
--	}
+-	var resp response
+-	_, err := perigee.Request("GET", identityBase, perigee.Options{
+-		Results: &resp,
+-		OkCodes: []int{200, 300},
+-	})
 -
--	decoder, err := NewDecoder(config)
 -	if err != nil {
--		panic(err)
+-		return nil, "", err
 -	}
 -
--	for i := 0; i < b.N; i++ {
--		decoder.Decode(input)
+-	byID := make(map[string]*Version)
+-	for _, version := range recognized {
+-		byID[version.ID] = version
 -	}
--}
 -
--func Benchmark_DecodeMetadataEmbedded(b *testing.B) {
--	input := map[string]interface{}{
--		"vstring": "foo",
--		"vunique": "bar",
--	}
+-	var highest *Version
+-	var endpoint string
 -
--	var md Metadata
--	var result EmbeddedSquash
--	config := &DecoderConfig{
--		Metadata: &md,
--		Result:   &result,
--	}
+-	for _, value := range resp.Versions.Values {
+-		href := ""
+-		for _, link := range value.Links {
+-			if link.Rel == "self" {
+-				href = normalize(link.Href)
+-			}
+-		}
 -
--	decoder, err := NewDecoder(config)
--	if err != nil {
--		b.Fatalf("err: %s", err)
--	}
+-		if matching, ok := byID[value.ID]; ok {
+-			// Prefer a version that exactly matches the provided endpoint.
+-			if href == identityEndpoint {
+-				if href == "" {
+-					return nil, "", fmt.Errorf("Endpoint missing in version %s response from %s", value.ID, identityBase)
+-				}
+-				return matching, href, nil
+-			}
 -
--	for i := 0; i < b.N; i++ {
--		decoder.Decode(input)
+-			// Otherwise, find the highest-priority version with a whitelisted status.
+-			if goodStatus[strings.ToLower(value.Status)] {
+-				if highest == nil || matching.Priority > highest.Priority {
+-					highest = matching
+-					endpoint = href
+-				}
+-			}
+-		}
 -	}
--}
 -
--func Benchmark_DecodeTagged(b *testing.B) {
--	input := map[string]interface{}{
--		"foo": "bar",
--		"bar": "value",
+-	if highest == nil {
+-		return nil, "", fmt.Errorf("No supported version available from endpoint %s", identityBase)
 -	}
--
--	var result Tagged
--	for i := 0; i < b.N; i++ {
--		Decode(input, &result)
+-	if endpoint == "" {
+-		return nil, "", fmt.Errorf("Endpoint missing in version %s response from %s", highest.ID, identityBase)
 -	}
+-
+-	return highest, endpoint, nil
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_bugs_test.go b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_bugs_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/utils/choose_version_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/utils/choose_version_test.go
 deleted file mode 100644
-index 7054f1a..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_bugs_test.go
+index 9552696..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/openstack/utils/choose_version_test.go
 +++ /dev/null
-@@ -1,47 +0,0 @@
--package mapstructure
+@@ -1,105 +0,0 @@
+-package utils
 -
--import "testing"
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--// GH-1
--func TestDecode_NilValue(t *testing.T) {
--	input := map[string]interface{}{
--		"vfoo":   nil,
--		"vother": nil,
--	}
+-	"github.com/rackspace/gophercloud/testhelper"
+-)
+-
+-func setupVersionHandler() {
+-	testhelper.Mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
+-		fmt.Fprintf(w, `
+-			{
+-				"versions": {
+-					"values": [
+-						{
+-							"status": "stable",
+-							"id": "v3.0",
+-							"links": [
+-								{ "href": "%s/v3.0", "rel": "self" }
+-							]
+-						},
+-						{
+-							"status": "stable",
+-							"id": "v2.0",
+-							"links": [
+-								{ "href": "%s/v2.0", "rel": "self" }
+-							]
+-						}
+-					]
+-				}
+-			}
+-		`, testhelper.Server.URL, testhelper.Server.URL)
+-	})
+-}
+-
+-func TestChooseVersion(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
+-	setupVersionHandler()
+-
+-	v2 := &Version{ID: "v2.0", Priority: 2, Suffix: "blarg"}
+-	v3 := &Version{ID: "v3.0", Priority: 3, Suffix: "hargl"}
+-
+-	v, endpoint, err := ChooseVersion(testhelper.Endpoint(), "", []*Version{v2, v3})
 -
--	var result Map
--	err := Decode(input, &result)
 -	if err != nil {
--		t.Fatalf("should not error: %s", err)
+-		t.Fatalf("Unexpected error from ChooseVersion: %v", err)
 -	}
 -
--	if result.Vfoo != "" {
--		t.Fatalf("value should be default: %s", result.Vfoo)
+-	if v != v3 {
+-		t.Errorf("Expected %#v to win, but %#v did instead", v3, v)
 -	}
 -
--	if result.Vother != nil {
--		t.Fatalf("Vother should be nil: %s", result.Vother)
+-	expected := testhelper.Endpoint() + "v3.0/"
+-	if endpoint != expected {
+-		t.Errorf("Expected endpoint [%s], but was [%s] instead", expected, endpoint)
 -	}
 -}
 -
--// GH-10
--func TestDecode_mapInterfaceInterface(t *testing.T) {
--	input := map[interface{}]interface{}{
--		"vfoo":   nil,
--		"vother": nil,
--	}
+-func TestChooseVersionOpinionatedLink(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
+-	setupVersionHandler()
 -
--	var result Map
--	err := Decode(input, &result)
+-	v2 := &Version{ID: "v2.0", Priority: 2, Suffix: "nope"}
+-	v3 := &Version{ID: "v3.0", Priority: 3, Suffix: "northis"}
+-
+-	v, endpoint, err := ChooseVersion(testhelper.Endpoint(), testhelper.Endpoint()+"v2.0/", []*Version{v2, v3})
 -	if err != nil {
--		t.Fatalf("should not error: %s", err)
+-		t.Fatalf("Unexpected error from ChooseVersion: %v", err)
 -	}
 -
--	if result.Vfoo != "" {
--		t.Fatalf("value should be default: %s", result.Vfoo)
+-	if v != v2 {
+-		t.Errorf("Expected %#v to win, but %#v did instead", v2, v)
 -	}
 -
--	if result.Vother != nil {
--		t.Fatalf("Vother should be nil: %s", result.Vother)
+-	expected := testhelper.Endpoint() + "v2.0/"
+-	if endpoint != expected {
+-		t.Errorf("Expected endpoint [%s], but was [%s] instead", expected, endpoint)
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_examples_test.go b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_examples_test.go
-deleted file mode 100644
-index aa393cc..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_examples_test.go
-+++ /dev/null
-@@ -1,169 +0,0 @@
--package mapstructure
 -
--import (
--	"fmt"
--)
+-func TestChooseVersionFromSuffix(t *testing.T) {
+-	testhelper.SetupHTTP()
+-	defer testhelper.TeardownHTTP()
 -
--func ExampleDecode() {
--	type Person struct {
--		Name   string
--		Age    int
--		Emails []string
--		Extra  map[string]string
--	}
+-	v2 := &Version{ID: "v2.0", Priority: 2, Suffix: "/v2.0/"}
+-	v3 := &Version{ID: "v3.0", Priority: 3, Suffix: "/v3.0/"}
 -
--	// This input can come from anywhere, but typically comes from
--	// something like decoding JSON where we're not quite sure of the
--	// struct initially.
--	input := map[string]interface{}{
--		"name":   "Mitchell",
--		"age":    91,
--		"emails": []string{"one", "two", "three"},
--		"extra": map[string]string{
--			"twitter": "mitchellh",
--		},
+-	v, endpoint, err := ChooseVersion(testhelper.Endpoint(), testhelper.Endpoint()+"v2.0/", []*Version{v2, v3})
+-	if err != nil {
+-		t.Fatalf("Unexpected error from ChooseVersion: %v", err)
 -	}
 -
--	var result Person
--	err := Decode(input, &result)
--	if err != nil {
--		panic(err)
+-	if v != v2 {
+-		t.Errorf("Expected %#v to win, but %#v did instead", v2, v)
 -	}
 -
--	fmt.Printf("%#v", result)
--	// Output:
--	// mapstructure.Person{Name:"Mitchell", Age:91, Emails:[]string{"one", "two", "three"}, Extra:map[string]string{"twitter":"mitchellh"}}
+-	expected := testhelper.Endpoint() + "v2.0/"
+-	if endpoint != expected {
+-		t.Errorf("Expected endpoint [%s], but was [%s] instead", expected, endpoint)
+-	}
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/package.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/package.go
+deleted file mode 100644
+index e8c2e82..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/package.go
++++ /dev/null
+@@ -1,38 +0,0 @@
+-/*
+-Package gophercloud provides a multi-vendor interface to OpenStack-compatible
+-clouds. The library has a three-level hierarchy: providers, services, and
+-resources.
+-
+-Provider structs represent the service providers that offer and manage a
+-collection of services. Examples of providers include: OpenStack, Rackspace,
+-HP. These are defined like so:
+-
+-  opts := gophercloud.AuthOptions{
+-    IdentityEndpoint: "https://my-openstack.com:5000/v2.0",
+-    Username: "{username}",
+-    Password: "{password}",
+-    TenantID: "{tenant_id}",
+-  }
 -
--func ExampleDecode_errors() {
--	type Person struct {
--		Name   string
--		Age    int
--		Emails []string
--		Extra  map[string]string
--	}
+-  provider, err := openstack.AuthenticatedClient(opts)
 -
--	// This input can come from anywhere, but typically comes from
--	// something like decoding JSON where we're not quite sure of the
--	// struct initially.
--	input := map[string]interface{}{
--		"name":   123,
--		"age":    "bad value",
--		"emails": []int{1, 2, 3},
--	}
+-Service structs are specific to a provider and handle all of the logic and
+-operations for a particular OpenStack service. Examples of services include:
+-Compute, Object Storage, Block Storage. In order to define one, you need to
+-pass in the parent provider, like so:
 -
--	var result Person
--	err := Decode(input, &result)
--	if err == nil {
--		panic("should have an error")
--	}
+-  opts := gophercloud.EndpointOpts{Region: "RegionOne"}
 -
--	fmt.Println(err.Error())
--	// Output:
--	// 5 error(s) decoding:
--	//
--	// * 'Name' expected type 'string', got unconvertible type 'int'
--	// * 'Age' expected type 'int', got unconvertible type 'string'
--	// * 'Emails[0]' expected type 'string', got unconvertible type 'int'
--	// * 'Emails[1]' expected type 'string', got unconvertible type 'int'
--	// * 'Emails[2]' expected type 'string', got unconvertible type 'int'
--}
+-  client := openstack.NewComputeV2(provider, opts)
 -
--func ExampleDecode_metadata() {
--	type Person struct {
--		Name string
--		Age  int
--	}
+-Resource structs are the domain models that services make use of in order
+-to work with and represent the state of API resources:
 -
--	// This input can come from anywhere, but typically comes from
--	// something like decoding JSON where we're not quite sure of the
--	// struct initially.
--	input := map[string]interface{}{
--		"name":  "Mitchell",
--		"age":   91,
--		"email": "foo at bar.com",
--	}
+-  server, err := servers.Get(client, "{serverId}").Extract()
 -
--	// For metadata, we make a more advanced DecoderConfig so we can
--	// more finely configure the decoder that is used. In this case, we
--	// just tell the decoder we want to track metadata.
--	var md Metadata
--	var result Person
--	config := &DecoderConfig{
--		Metadata: &md,
--		Result:   &result,
--	}
+-Another convention is to return Result structs for API operations, which allow
+-you to access the HTTP headers, response body, and associated errors with the
+-network transaction. To get a resource struct, you then call the Extract
+-method which is chained to the response.
+-*/
+-package gophercloud
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/http.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/http.go
+deleted file mode 100644
+index 1e108c8..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/http.go
++++ /dev/null
+@@ -1,64 +0,0 @@
+-package pagination
 -
--	decoder, err := NewDecoder(config)
--	if err != nil {
--		panic(err)
--	}
+-import (
+-	"encoding/json"
+-	"io/ioutil"
+-	"net/http"
+-	"net/url"
+-	"strings"
 -
--	if err := decoder.Decode(input); err != nil {
--		panic(err)
--	}
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-)
 -
--	fmt.Printf("Unused keys: %#v", md.Unused)
--	// Output:
--	// Unused keys: []string{"email"}
+-// PageResult stores the HTTP response that returned the current page of results.
+-type PageResult struct {
+-	gophercloud.Result
+-	url.URL
 -}
 -
--func ExampleDecode_weaklyTypedInput() {
--	type Person struct {
--		Name   string
--		Age    int
--		Emails []string
--	}
+-// PageResultFrom parses an HTTP response as JSON and returns a PageResult containing the
+-// results, interpreting it as JSON if the content type indicates.
+-func PageResultFrom(resp http.Response) (PageResult, error) {
+-	var parsedBody interface{}
 -
--	// This input can come from anywhere, but typically comes from
--	// something like decoding JSON, generated by a weakly typed language
--	// such as PHP.
--	input := map[string]interface{}{
--		"name":   123,                      // number => string
--		"age":    "42",                     // string => number
--		"emails": map[string]interface{}{}, // empty map => empty array
+-	defer resp.Body.Close()
+-	rawBody, err := ioutil.ReadAll(resp.Body)
+-	if err != nil {
+-		return PageResult{}, err
 -	}
 -
--	var result Person
--	config := &DecoderConfig{
--		WeaklyTypedInput: true,
--		Result:           &result,
+-	if strings.HasPrefix(resp.Header.Get("Content-Type"), "application/json") {
+-		err = json.Unmarshal(rawBody, &parsedBody)
+-		if err != nil {
+-			return PageResult{}, err
+-		}
+-	} else {
+-		parsedBody = rawBody
 -	}
 -
--	decoder, err := NewDecoder(config)
--	if err != nil {
--		panic(err)
+-	return PageResult{
+-		Result: gophercloud.Result{
+-			Body:   parsedBody,
+-			Header: resp.Header,
+-		},
+-		URL: *resp.Request.URL,
+-	}, err
+-}
+-
+-// Request performs a Perigee request and extracts the http.Response from the result.
+-func Request(client *gophercloud.ServiceClient, headers map[string]string, url string) (http.Response, error) {
+-	h := client.AuthenticatedHeaders()
+-	for key, value := range headers {
+-		h[key] = value
 -	}
 -
--	err = decoder.Decode(input)
+-	resp, err := perigee.Request("GET", url, perigee.Options{
+-		MoreHeaders: h,
+-		OkCodes:     []int{200, 204},
+-	})
 -	if err != nil {
--		panic(err)
+-		return http.Response{}, err
 -	}
+-	return resp.HttpResponse, nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/linked.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/linked.go
+deleted file mode 100644
+index 461fa49..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/linked.go
++++ /dev/null
+@@ -1,61 +0,0 @@
+-package pagination
 -
--	fmt.Printf("%#v", result)
--	// Output: mapstructure.Person{Name:"123", Age:42, Emails:[]string{}}
+-import "fmt"
+-
+-// LinkedPageBase may be embedded to implement a page that provides navigational "Next" and "Previous" links within its result.
+-type LinkedPageBase struct {
+-	PageResult
+-
+-	// LinkPath lists the keys that should be traversed within a response to arrive at the "next" pointer.
+-	// If any link along the path is missing, an empty URL will be returned.
+-	// If any link results in an unexpected value type, an error will be returned.
+-	// When left as "nil", []string{"links", "next"} will be used as a default.
+-	LinkPath []string
 -}
 -
--func ExampleDecode_tags() {
--	// Note that the mapstructure tags defined in the struct type
--	// can indicate which fields the values are mapped to.
--	type Person struct {
--		Name string `mapstructure:"person_name"`
--		Age  int    `mapstructure:"person_age"`
--	}
+-// NextPageURL extracts the pagination structure from a JSON response and returns the "next" link, if one is present.
+-// It assumes that the links are available in a "links" element of the top-level response object.
+-// If this is not the case, override NextPageURL on your result type.
+-func (current LinkedPageBase) NextPageURL() (string, error) {
+-	var path []string
+-	var key string
 -
--	input := map[string]interface{}{
--		"person_name": "Mitchell",
--		"person_age":  91,
+-	if current.LinkPath == nil {
+-		path = []string{"links", "next"}
+-	} else {
+-		path = current.LinkPath
 -	}
 -
--	var result Person
--	err := Decode(input, &result)
--	if err != nil {
--		panic(err)
+-	submap, ok := current.Body.(map[string]interface{})
+-	if !ok {
+-		return "", fmt.Errorf("Expected an object, but was %#v", current.Body)
 -	}
 -
--	fmt.Printf("%#v", result)
--	// Output:
--	// mapstructure.Person{Name:"Mitchell", Age:91}
+-	for {
+-		key, path = path[0], path[1:len(path)]
+-
+-		value, ok := submap[key]
+-		if !ok {
+-			return "", nil
+-		}
+-
+-		if len(path) > 0 {
+-			submap, ok = value.(map[string]interface{})
+-			if !ok {
+-				return "", fmt.Errorf("Expected an object, but was %#v", value)
+-			}
+-		} else {
+-			if value == nil {
+-				// Actual null element.
+-				return "", nil
+-			}
+-
+-			url, ok := value.(string)
+-			if !ok {
+-				return "", fmt.Errorf("Expected a string, but was %#v", value)
+-			}
+-
+-			return url, nil
+-		}
+-	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_test.go b/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/linked_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/linked_test.go
 deleted file mode 100644
-index 23029c7..0000000
---- a/Godeps/_workspace/src/github.com/mitchellh/mapstructure/mapstructure_test.go
+index 4d3248e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/linked_test.go
 +++ /dev/null
-@@ -1,828 +0,0 @@
--package mapstructure
+@@ -1,107 +0,0 @@
+-package pagination
 -
 -import (
+-	"fmt"
+-	"net/http"
 -	"reflect"
--	"sort"
 -	"testing"
+-
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud/testhelper"
 -)
 -
--type Basic struct {
--	Vstring string
--	Vint    int
--	Vuint   uint
--	Vbool   bool
--	Vfloat  float64
--	Vextra  string
--	vsilent bool
--	Vdata   interface{}
--}
+-// LinkedPager sample and test cases.
 -
--type Embedded struct {
--	Basic
--	Vunique string
+-type LinkedPageResult struct {
+-	LinkedPageBase
 -}
 -
--type EmbeddedPointer struct {
--	*Basic
--	Vunique string
+-func (r LinkedPageResult) IsEmpty() (bool, error) {
+-	is, err := ExtractLinkedInts(r)
+-	if err != nil {
+-		return true, nil
+-	}
+-	return len(is) == 0, nil
 -}
 -
--type EmbeddedSquash struct {
--	Basic   `mapstructure:",squash"`
--	Vunique string
--}
+-func ExtractLinkedInts(page Page) ([]int, error) {
+-	var response struct {
+-		Ints []int `mapstructure:"ints"`
+-	}
 -
--type Map struct {
--	Vfoo   string
--	Vother map[string]string
--}
+-	err := mapstructure.Decode(page.(LinkedPageResult).Body, &response)
+-	if err != nil {
+-		return nil, err
+-	}
 -
--type MapOfStruct struct {
--	Value map[string]Basic
+-	return response.Ints, nil
 -}
 -
--type Nested struct {
--	Vfoo string
--	Vbar Basic
--}
+-func createLinked(t *testing.T) Pager {
+-	testhelper.SetupHTTP()
 -
--type NestedPointer struct {
--	Vfoo string
--	Vbar *Basic
--}
+-	testhelper.Mux.HandleFunc("/page1", func(w http.ResponseWriter, r *http.Request) {
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, `{ "ints": [1, 2, 3], "links": { "next": "%s/page2" } }`, testhelper.Server.URL)
+-	})
 -
--type Slice struct {
--	Vfoo string
--	Vbar []string
--}
+-	testhelper.Mux.HandleFunc("/page2", func(w http.ResponseWriter, r *http.Request) {
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, `{ "ints": [4, 5, 6], "links": { "next": "%s/page3" } }`, testhelper.Server.URL)
+-	})
 -
--type SliceOfStruct struct {
--	Value []Basic
--}
+-	testhelper.Mux.HandleFunc("/page3", func(w http.ResponseWriter, r *http.Request) {
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, `{ "ints": [7, 8, 9], "links": { "next": null } }`)
+-	})
 -
--type Tagged struct {
--	Extra string `mapstructure:"bar,what,what"`
--	Value string `mapstructure:"foo"`
--}
+-	client := createClient()
 -
--type TypeConversionResult struct {
--	IntToFloat         float32
--	IntToUint          uint
--	IntToBool          bool
--	IntToString        string
--	UintToInt          int
--	UintToFloat        float32
--	UintToBool         bool
--	UintToString       string
--	BoolToInt          int
--	BoolToUint         uint
--	BoolToFloat        float32
--	BoolToString       string
--	FloatToInt         int
--	FloatToUint        uint
--	FloatToBool        bool
--	FloatToString      string
--	SliceUint8ToString string
--	StringToInt        int
--	StringToUint       uint
--	StringToBool       bool
--	StringToFloat      float32
--	SliceToMap         map[string]interface{}
--	MapToSlice         []interface{}
+-	createPage := func(r PageResult) Page {
+-		return LinkedPageResult{LinkedPageBase{PageResult: r}}
+-	}
+-
+-	return NewPager(client, testhelper.Server.URL+"/page1", createPage)
 -}
 -
--func TestBasicTypes(t *testing.T) {
--	t.Parallel()
+-func TestEnumerateLinked(t *testing.T) {
+-	pager := createLinked(t)
+-	defer testhelper.TeardownHTTP()
 -
--	input := map[string]interface{}{
--		"vstring": "foo",
--		"vint":    42,
--		"Vuint":   42,
--		"vbool":   true,
--		"Vfloat":  42.42,
--		"vsilent": true,
--		"vdata":   42,
--	}
+-	callCount := 0
+-	err := pager.EachPage(func(page Page) (bool, error) {
+-		actual, err := ExtractLinkedInts(page)
+-		if err != nil {
+-			return false, err
+-		}
 -
--	var result Basic
--	err := Decode(input, &result)
--	if err != nil {
--		t.Errorf("got an err: %s", err.Error())
--		t.FailNow()
--	}
+-		t.Logf("Handler invoked with %v", actual)
 -
--	if result.Vstring != "foo" {
--		t.Errorf("vstring value should be 'foo': %#v", result.Vstring)
--	}
+-		var expected []int
+-		switch callCount {
+-		case 0:
+-			expected = []int{1, 2, 3}
+-		case 1:
+-			expected = []int{4, 5, 6}
+-		case 2:
+-			expected = []int{7, 8, 9}
+-		default:
+-			t.Fatalf("Unexpected call count: %d", callCount)
+-			return false, nil
+-		}
 -
--	if result.Vint != 42 {
--		t.Errorf("vint value should be 42: %#v", result.Vint)
--	}
+-		if !reflect.DeepEqual(expected, actual) {
+-			t.Errorf("Call %d: Expected %#v, but was %#v", callCount, expected, actual)
+-		}
 -
--	if result.Vuint != 42 {
--		t.Errorf("vuint value should be 42: %#v", result.Vuint)
+-		callCount++
+-		return true, nil
+-	})
+-	if err != nil {
+-		t.Errorf("Unexpected error for page iteration: %v", err)
 -	}
 -
--	if result.Vbool != true {
--		t.Errorf("vbool value should be true: %#v", result.Vbool)
+-	if callCount != 3 {
+-		t.Errorf("Expected 3 calls, but was %d", callCount)
 -	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/marker.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/marker.go
+deleted file mode 100644
+index e7688c2..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/marker.go
++++ /dev/null
+@@ -1,34 +0,0 @@
+-package pagination
 -
--	if result.Vfloat != 42.42 {
--		t.Errorf("vfloat value should be 42.42: %#v", result.Vfloat)
--	}
+-// MarkerPage is a stricter Page interface that describes additional functionality required for use with NewMarkerPager.
+-// For convenience, embed the MarkedPageBase struct.
+-type MarkerPage interface {
+-	Page
 -
--	if result.Vextra != "" {
--		t.Errorf("vextra value should be empty: %#v", result.Vextra)
--	}
+-	// LastMarker returns the last "marker" value on this page.
+-	LastMarker() (string, error)
+-}
 -
--	if result.vsilent != false {
--		t.Error("vsilent should not be set, it is unexported")
--	}
+-// MarkerPageBase is a page in a collection that's paginated by "limit" and "marker" query parameters.
+-type MarkerPageBase struct {
+-	PageResult
 -
--	if result.Vdata != 42 {
--		t.Error("vdata should be valid")
--	}
+-	// Owner is a reference to the embedding struct.
+-	Owner MarkerPage
 -}
 -
--func TestBasic_IntWithFloat(t *testing.T) {
--	t.Parallel()
--
--	input := map[string]interface{}{
--		"vint": float64(42),
--	}
+-// NextPageURL generates the URL for the page of results after this one.
+-func (current MarkerPageBase) NextPageURL() (string, error) {
+-	currentURL := current.URL
 -
--	var result Basic
--	err := Decode(input, &result)
+-	mark, err := current.Owner.LastMarker()
 -	if err != nil {
--		t.Fatalf("got an err: %s", err)
+-		return "", err
 -	}
+-
+-	q := currentURL.Query()
+-	q.Set("marker", mark)
+-	currentURL.RawQuery = q.Encode()
+-
+-	return currentURL.String(), nil
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/marker_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/marker_test.go
+deleted file mode 100644
+index 3b1df1d..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/marker_test.go
++++ /dev/null
+@@ -1,113 +0,0 @@
+-package pagination
 -
--func TestDecode_Embedded(t *testing.T) {
--	t.Parallel()
+-import (
+-	"fmt"
+-	"net/http"
+-	"strings"
+-	"testing"
 -
--	input := map[string]interface{}{
--		"vstring": "foo",
--		"Basic": map[string]interface{}{
--			"vstring": "innerfoo",
--		},
--		"vunique": "bar",
--	}
+-	"github.com/rackspace/gophercloud/testhelper"
+-)
 -
--	var result Embedded
--	err := Decode(input, &result)
--	if err != nil {
--		t.Fatalf("got an err: %s", err.Error())
--	}
+-// MarkerPager sample and test cases.
 -
--	if result.Vstring != "innerfoo" {
--		t.Errorf("vstring value should be 'innerfoo': %#v", result.Vstring)
--	}
+-type MarkerPageResult struct {
+-	MarkerPageBase
+-}
 -
--	if result.Vunique != "bar" {
--		t.Errorf("vunique value should be 'bar': %#v", result.Vunique)
+-func (r MarkerPageResult) IsEmpty() (bool, error) {
+-	results, err := ExtractMarkerStrings(r)
+-	if err != nil {
+-		return true, err
 -	}
+-	return len(results) == 0, err
 -}
 -
--func TestDecode_EmbeddedPointer(t *testing.T) {
--	t.Parallel()
--
--	input := map[string]interface{}{
--		"vstring": "foo",
--		"Basic": map[string]interface{}{
--			"vstring": "innerfoo",
--		},
--		"vunique": "bar",
+-func (r MarkerPageResult) LastMarker() (string, error) {
+-	results, err := ExtractMarkerStrings(r)
+-	if err != nil {
+-		return "", err
 -	}
--
--	var result EmbeddedPointer
--	err := Decode(input, &result)
--	if err == nil {
--		t.Fatal("should get error")
+-	if len(results) == 0 {
+-		return "", nil
 -	}
+-	return results[len(results)-1], nil
 -}
 -
--func TestDecode_EmbeddedSquash(t *testing.T) {
--	t.Parallel()
+-func createMarkerPaged(t *testing.T) Pager {
+-	testhelper.SetupHTTP()
 -
--	input := map[string]interface{}{
--		"vstring": "foo",
--		"vunique": "bar",
--	}
+-	testhelper.Mux.HandleFunc("/page", func(w http.ResponseWriter, r *http.Request) {
+-		r.ParseForm()
+-		ms := r.Form["marker"]
+-		switch {
+-		case len(ms) == 0:
+-			fmt.Fprintf(w, "aaa\nbbb\nccc")
+-		case len(ms) == 1 && ms[0] == "ccc":
+-			fmt.Fprintf(w, "ddd\neee\nfff")
+-		case len(ms) == 1 && ms[0] == "fff":
+-			fmt.Fprintf(w, "ggg\nhhh\niii")
+-		case len(ms) == 1 && ms[0] == "iii":
+-			w.WriteHeader(http.StatusNoContent)
+-		default:
+-			t.Errorf("Request with unexpected marker: [%v]", ms)
+-		}
+-	})
 -
--	var result EmbeddedSquash
--	err := Decode(input, &result)
--	if err != nil {
--		t.Fatalf("got an err: %s", err.Error())
--	}
+-	client := createClient()
 -
--	if result.Vstring != "foo" {
--		t.Errorf("vstring value should be 'foo': %#v", result.Vstring)
+-	createPage := func(r PageResult) Page {
+-		p := MarkerPageResult{MarkerPageBase{PageResult: r}}
+-		p.MarkerPageBase.Owner = p
+-		return p
 -	}
 -
--	if result.Vunique != "bar" {
--		t.Errorf("vunique value should be 'bar': %#v", result.Vunique)
+-	return NewPager(client, testhelper.Server.URL+"/page", createPage)
+-}
+-
+-func ExtractMarkerStrings(page Page) ([]string, error) {
+-	content := page.(MarkerPageResult).Body.([]uint8)
+-	parts := strings.Split(string(content), "\n")
+-	results := make([]string, 0, len(parts))
+-	for _, part := range parts {
+-		if len(part) > 0 {
+-			results = append(results, part)
+-		}
 -	}
+-	return results, nil
 -}
 -
--func TestDecode_DecodeHook(t *testing.T) {
--	t.Parallel()
+-func TestEnumerateMarker(t *testing.T) {
+-	pager := createMarkerPaged(t)
+-	defer testhelper.TeardownHTTP()
 -
--	input := map[string]interface{}{
--		"vint": "WHAT",
--	}
+-	callCount := 0
+-	err := pager.EachPage(func(page Page) (bool, error) {
+-		actual, err := ExtractMarkerStrings(page)
+-		if err != nil {
+-			return false, err
+-		}
 -
--	decodeHook := func(from reflect.Kind, to reflect.Kind, v interface{}) (interface{}, error) {
--		if from == reflect.String && to != reflect.String {
--			return 5, nil
+-		t.Logf("Handler invoked with %v", actual)
+-
+-		var expected []string
+-		switch callCount {
+-		case 0:
+-			expected = []string{"aaa", "bbb", "ccc"}
+-		case 1:
+-			expected = []string{"ddd", "eee", "fff"}
+-		case 2:
+-			expected = []string{"ggg", "hhh", "iii"}
+-		default:
+-			t.Fatalf("Unexpected call count: %d", callCount)
+-			return false, nil
 -		}
 -
--		return v, nil
--	}
+-		testhelper.CheckDeepEquals(t, expected, actual)
 -
--	var result Basic
--	config := &DecoderConfig{
--		DecodeHook: decodeHook,
--		Result:     &result,
--	}
+-		callCount++
+-		return true, nil
+-	})
+-	testhelper.AssertNoErr(t, err)
+-	testhelper.AssertEquals(t, callCount, 3)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/null.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/null.go
+deleted file mode 100644
+index ae57e18..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/null.go
++++ /dev/null
+@@ -1,20 +0,0 @@
+-package pagination
 -
--	decoder, err := NewDecoder(config)
--	if err != nil {
--		t.Fatalf("err: %s", err)
--	}
+-// nullPage is an always-empty page that trivially satisfies all Page interfacts.
+-// It's useful to be returned along with an error.
+-type nullPage struct{}
 -
--	err = decoder.Decode(input)
--	if err != nil {
--		t.Fatalf("got an err: %s", err)
--	}
+-// NextPageURL always returns "" to indicate that there are no more pages to return.
+-func (p nullPage) NextPageURL() (string, error) {
+-	return "", nil
+-}
 -
--	if result.Vint != 5 {
--		t.Errorf("vint should be 5: %#v", result.Vint)
--	}
+-// IsEmpty always returns true to prevent iteration over nullPages.
+-func (p nullPage) IsEmpty() (bool, error) {
+-	return true, nil
 -}
 -
--func TestDecode_Nil(t *testing.T) {
--	t.Parallel()
+-// LastMark always returns "" because the nullPage contains no items to have a mark.
+-func (p nullPage) LastMark() (string, error) {
+-	return "", nil
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/pager.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/pager.go
+deleted file mode 100644
+index 5c20e16..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/pager.go
++++ /dev/null
+@@ -1,115 +0,0 @@
+-package pagination
 -
--	var input interface{} = nil
--	result := Basic{
--		Vstring: "foo",
--	}
+-import (
+-	"errors"
 -
--	err := Decode(input, &result)
--	if err != nil {
--		t.Fatalf("err: %s", err)
--	}
+-	"github.com/rackspace/gophercloud"
+-)
 -
--	if result.Vstring != "foo" {
--		t.Fatalf("bad: %#v", result.Vstring)
--	}
+-var (
+-	// ErrPageNotAvailable is returned from a Pager when a next or previous page is requested, but does not exist.
+-	ErrPageNotAvailable = errors.New("The requested page does not exist.")
+-)
+-
+-// Page must be satisfied by the result type of any resource collection.
+-// It allows clients to interact with the resource uniformly, regardless of whether or not or how it's paginated.
+-// Generally, rather than implementing this interface directly, implementors should embed one of the concrete PageBase structs,
+-// instead.
+-// Depending on the pagination strategy of a particular resource, there may be an additional subinterface that the result type
+-// will need to implement.
+-type Page interface {
+-
+-	// NextPageURL generates the URL for the page of data that follows this collection.
+-	// Return "" if no such page exists.
+-	NextPageURL() (string, error)
+-
+-	// IsEmpty returns true if this Page has no items in it.
+-	IsEmpty() (bool, error)
 -}
 -
--func TestDecode_NonStruct(t *testing.T) {
--	t.Parallel()
+-// Pager knows how to advance through a specific resource collection, one page at a time.
+-type Pager struct {
+-	client *gophercloud.ServiceClient
 -
--	input := map[string]interface{}{
--		"foo": "bar",
--		"bar": "baz",
--	}
+-	initialURL string
 -
--	var result map[string]string
--	err := Decode(input, &result)
--	if err != nil {
--		t.Fatalf("err: %s", err)
--	}
+-	createPage func(r PageResult) Page
 -
--	if result["foo"] != "bar" {
--		t.Fatal("foo is not bar")
--	}
+-	Err error
+-
+-	// Headers supplies additional HTTP headers to populate on each paged request.
+-	Headers map[string]string
 -}
 -
--func TestDecode_TypeConversion(t *testing.T) {
--	input := map[string]interface{}{
--		"IntToFloat":         42,
--		"IntToUint":          42,
--		"IntToBool":          1,
--		"IntToString":        42,
--		"UintToInt":          42,
--		"UintToFloat":        42,
--		"UintToBool":         42,
--		"UintToString":       42,
--		"BoolToInt":          true,
--		"BoolToUint":         true,
--		"BoolToFloat":        true,
--		"BoolToString":       true,
--		"FloatToInt":         42.42,
--		"FloatToUint":        42.42,
--		"FloatToBool":        42.42,
--		"FloatToString":      42.42,
--		"SliceUint8ToString": []uint8("foo"),
--		"StringToInt":        "42",
--		"StringToUint":       "42",
--		"StringToBool":       "1",
--		"StringToFloat":      "42.42",
--		"SliceToMap":         []interface{}{},
--		"MapToSlice":         map[string]interface{}{},
+-// NewPager constructs a manually-configured pager.
+-// Supply the URL for the first page, a function that requests a specific page given a URL, and a function that counts a page.
+-func NewPager(client *gophercloud.ServiceClient, initialURL string, createPage func(r PageResult) Page) Pager {
+-	return Pager{
+-		client:     client,
+-		initialURL: initialURL,
+-		createPage: createPage,
 -	}
+-}
 -
--	expectedResultStrict := TypeConversionResult{
--		IntToFloat:  42.0,
--		IntToUint:   42,
--		UintToInt:   42,
--		UintToFloat: 42,
--		BoolToInt:   0,
--		BoolToUint:  0,
--		BoolToFloat: 0,
--		FloatToInt:  42,
--		FloatToUint: 42,
+-// WithPageCreator returns a new Pager that substitutes a different page creation function. This is
+-// useful for overriding List functions in delegation.
+-func (p Pager) WithPageCreator(createPage func(r PageResult) Page) Pager {
+-	return Pager{
+-		client:     p.client,
+-		initialURL: p.initialURL,
+-		createPage: createPage,
 -	}
+-}
 -
--	expectedResultWeak := TypeConversionResult{
--		IntToFloat:         42.0,
--		IntToUint:          42,
--		IntToBool:          true,
--		IntToString:        "42",
--		UintToInt:          42,
--		UintToFloat:        42,
--		UintToBool:         true,
--		UintToString:       "42",
--		BoolToInt:          1,
--		BoolToUint:         1,
--		BoolToFloat:        1,
--		BoolToString:       "1",
--		FloatToInt:         42,
--		FloatToUint:        42,
--		FloatToBool:        true,
--		FloatToString:      "42.42",
--		SliceUint8ToString: "foo",
--		StringToInt:        42,
--		StringToUint:       42,
--		StringToBool:       true,
--		StringToFloat:      42.42,
--		SliceToMap:         map[string]interface{}{},
--		MapToSlice:         []interface{}{},
+-func (p Pager) fetchNextPage(url string) (Page, error) {
+-	resp, err := Request(p.client, p.Headers, url)
+-	if err != nil {
+-		return nil, err
 -	}
 -
--	// Test strict type conversion
--	var resultStrict TypeConversionResult
--	err := Decode(input, &resultStrict)
--	if err == nil {
--		t.Errorf("should return an error")
--	}
--	if !reflect.DeepEqual(resultStrict, expectedResultStrict) {
--		t.Errorf("expected %v, got: %v", expectedResultStrict, resultStrict)
+-	remembered, err := PageResultFrom(resp)
+-	if err != nil {
+-		return nil, err
 -	}
 -
--	// Test weak type conversion
--	var decoder *Decoder
--	var resultWeak TypeConversionResult
+-	return p.createPage(remembered), nil
+-}
 -
--	config := &DecoderConfig{
--		WeaklyTypedInput: true,
--		Result:           &resultWeak,
+-// EachPage iterates over each page returned by a Pager, yielding one at a time to a handler function.
+-// Return "false" from the handler to prematurely stop iterating.
+-func (p Pager) EachPage(handler func(Page) (bool, error)) error {
+-	if p.Err != nil {
+-		return p.Err
 -	}
+-	currentURL := p.initialURL
+-	for {
+-		currentPage, err := p.fetchNextPage(currentURL)
+-		if err != nil {
+-			return err
+-		}
 -
--	decoder, err = NewDecoder(config)
--	if err != nil {
--		t.Fatalf("err: %s", err)
--	}
+-		empty, err := currentPage.IsEmpty()
+-		if err != nil {
+-			return err
+-		}
+-		if empty {
+-			return nil
+-		}
 -
--	err = decoder.Decode(input)
--	if err != nil {
--		t.Fatalf("got an err: %s", err)
--	}
+-		ok, err := handler(currentPage)
+-		if err != nil {
+-			return err
+-		}
+-		if !ok {
+-			return nil
+-		}
 -
--	if !reflect.DeepEqual(resultWeak, expectedResultWeak) {
--		t.Errorf("expected \n%#v, got: \n%#v", expectedResultWeak, resultWeak)
+-		currentURL, err = currentPage.NextPageURL()
+-		if err != nil {
+-			return err
+-		}
+-		if currentURL == "" {
+-			return nil
+-		}
 -	}
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/pagination_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/pagination_test.go
+deleted file mode 100644
+index f3e4de1..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/pagination_test.go
++++ /dev/null
+@@ -1,13 +0,0 @@
+-package pagination
 -
--func TestDecoder_ErrorUnused(t *testing.T) {
--	t.Parallel()
--
--	input := map[string]interface{}{
--		"vstring": "hello",
--		"foo":     "bar",
--	}
+-import (
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/testhelper"
+-)
 -
--	var result Basic
--	config := &DecoderConfig{
--		ErrorUnused: true,
--		Result:      &result,
+-func createClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{
+-		ProviderClient: &gophercloud.ProviderClient{TokenID: "abc123"},
+-		Endpoint:       testhelper.Endpoint(),
 -	}
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/pkg.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/pkg.go
+deleted file mode 100644
+index 912daea..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/pkg.go
++++ /dev/null
+@@ -1,4 +0,0 @@
+-/*
+-Package pagination contains utilities and convenience structs that implement common pagination idioms within OpenStack APIs.
+-*/
+-package pagination
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/single.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/single.go
+deleted file mode 100644
+index 4dd3c5c..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/single.go
++++ /dev/null
+@@ -1,9 +0,0 @@
+-package pagination
 -
--	decoder, err := NewDecoder(config)
--	if err != nil {
--		t.Fatalf("err: %s", err)
--	}
+-// SinglePageBase may be embedded in a Page that contains all of the results from an operation at once.
+-type SinglePageBase PageResult
 -
--	err = decoder.Decode(input)
--	if err == nil {
--		t.Fatal("expected error")
--	}
+-// NextPageURL always returns "" to indicate that there are no more pages to return.
+-func (current SinglePageBase) NextPageURL() (string, error) {
+-	return "", nil
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/single_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/single_test.go
+deleted file mode 100644
+index 8817d57..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/pagination/single_test.go
++++ /dev/null
+@@ -1,71 +0,0 @@
+-package pagination
 -
--func TestMap(t *testing.T) {
--	t.Parallel()
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--	input := map[string]interface{}{
--		"vfoo": "foo",
--		"vother": map[interface{}]interface{}{
--			"foo": "foo",
--			"bar": "bar",
--		},
--	}
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud/testhelper"
+-)
 -
--	var result Map
--	err := Decode(input, &result)
+-// SinglePage sample and test cases.
+-
+-type SinglePageResult struct {
+-	SinglePageBase
+-}
+-
+-func (r SinglePageResult) IsEmpty() (bool, error) {
+-	is, err := ExtractSingleInts(r)
 -	if err != nil {
--		t.Fatalf("got an error: %s", err)
+-		return true, err
 -	}
+-	return len(is) == 0, nil
+-}
 -
--	if result.Vfoo != "foo" {
--		t.Errorf("vfoo value should be 'foo': %#v", result.Vfoo)
+-func ExtractSingleInts(page Page) ([]int, error) {
+-	var response struct {
+-		Ints []int `mapstructure:"ints"`
 -	}
 -
--	if result.Vother == nil {
--		t.Fatal("vother should not be nil")
+-	err := mapstructure.Decode(page.(SinglePageResult).Body, &response)
+-	if err != nil {
+-		return nil, err
 -	}
 -
--	if len(result.Vother) != 2 {
--		t.Error("vother should have two items")
--	}
+-	return response.Ints, nil
+-}
 -
--	if result.Vother["foo"] != "foo" {
--		t.Errorf("'foo' key should be foo, got: %#v", result.Vother["foo"])
--	}
+-func setupSinglePaged() Pager {
+-	testhelper.SetupHTTP()
+-	client := createClient()
 -
--	if result.Vother["bar"] != "bar" {
--		t.Errorf("'bar' key should be bar, got: %#v", result.Vother["bar"])
+-	testhelper.Mux.HandleFunc("/only", func(w http.ResponseWriter, r *http.Request) {
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, `{ "ints": [1, 2, 3] }`)
+-	})
+-
+-	createPage := func(r PageResult) Page {
+-		return SinglePageResult{SinglePageBase(r)}
 -	}
+-
+-	return NewPager(client, testhelper.Server.URL+"/only", createPage)
 -}
 -
--func TestMapOfStruct(t *testing.T) {
--	t.Parallel()
+-func TestEnumerateSinglePaged(t *testing.T) {
+-	callCount := 0
+-	pager := setupSinglePaged()
+-	defer testhelper.TeardownHTTP()
 -
--	input := map[string]interface{}{
--		"value": map[string]interface{}{
--			"foo": map[string]string{"vstring": "one"},
--			"bar": map[string]string{"vstring": "two"},
--		},
--	}
+-	err := pager.EachPage(func(page Page) (bool, error) {
+-		callCount++
 -
--	var result MapOfStruct
--	err := Decode(input, &result)
--	if err != nil {
--		t.Fatalf("got an err: %s", err)
--	}
+-		expected := []int{1, 2, 3}
+-		actual, err := ExtractSingleInts(page)
+-		testhelper.AssertNoErr(t, err)
+-		testhelper.CheckDeepEquals(t, expected, actual)
+-		return true, nil
+-	})
+-	testhelper.CheckNoErr(t, err)
+-	testhelper.CheckEquals(t, 1, callCount)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/params.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/params.go
+deleted file mode 100644
+index 5fe3c2c..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/params.go
++++ /dev/null
+@@ -1,184 +0,0 @@
+-package gophercloud
 -
--	if result.Value == nil {
--		t.Fatal("value should not be nil")
--	}
+-import (
+-	"fmt"
+-	"net/url"
+-	"reflect"
+-	"strconv"
+-	"strings"
+-	"time"
+-)
 -
--	if len(result.Value) != 2 {
--		t.Error("value should have two items")
+-// MaybeString takes a string that might be a zero-value, and either returns a
+-// pointer to its address or a nil value (i.e. empty pointer). This is useful
+-// for converting zero values in options structs when the end-user hasn't
+-// defined values. Those zero values need to be nil in order for the JSON
+-// serialization to ignore them.
+-func MaybeString(original string) *string {
+-	if original != "" {
+-		return &original
 -	}
+-	return nil
+-}
 -
--	if result.Value["foo"].Vstring != "one" {
--		t.Errorf("foo value should be 'one', got: %s", result.Value["foo"].Vstring)
+-// MaybeInt takes an int that might be a zero-value, and either returns a
+-// pointer to its address or a nil value (i.e. empty pointer).
+-func MaybeInt(original int) *int {
+-	if original != 0 {
+-		return &original
 -	}
+-	return nil
+-}
 -
--	if result.Value["bar"].Vstring != "two" {
--		t.Errorf("bar value should be 'two', got: %s", result.Value["bar"].Vstring)
+-var t time.Time
+-
+-func isZero(v reflect.Value) bool {
+-	switch v.Kind() {
+-	case reflect.Func, reflect.Map, reflect.Slice:
+-		return v.IsNil()
+-	case reflect.Array:
+-		z := true
+-		for i := 0; i < v.Len(); i++ {
+-			z = z && isZero(v.Index(i))
+-		}
+-		return z
+-	case reflect.Struct:
+-		if v.Type() == reflect.TypeOf(t) {
+-			if v.Interface().(time.Time).IsZero() {
+-				return true
+-			}
+-			return false
+-		}
+-		z := true
+-		for i := 0; i < v.NumField(); i++ {
+-			z = z && isZero(v.Field(i))
+-		}
+-		return z
 -	}
+-	// Compare other types directly:
+-	z := reflect.Zero(v.Type())
+-	return v.Interface() == z.Interface()
 -}
 -
--func TestNestedType(t *testing.T) {
--	t.Parallel()
+-/*
+-BuildQueryString accepts a generic structure and parses it URL struct. It
+-converts field names into query names based on "q" tags. So for example, this
+-type:
 -
--	input := map[string]interface{}{
--		"vfoo": "foo",
--		"vbar": map[string]interface{}{
--			"vstring": "foo",
--			"vint":    42,
--			"vbool":   true,
--		},
+-	struct {
+-	   Bar string `q:"x_bar"`
+-	   Baz int    `q:"lorem_ipsum"`
+-	}{
+-	   Bar: "XXX",
+-	   Baz: "YYY",
 -	}
 -
--	var result Nested
--	err := Decode(input, &result)
--	if err != nil {
--		t.Fatalf("got an err: %s", err.Error())
--	}
+-will be converted into ?x_bar=XXX&lorem_ipsum=YYYY
+-*/
+-func BuildQueryString(opts interface{}) (*url.URL, error) {
+-	optsValue := reflect.ValueOf(opts)
+-	if optsValue.Kind() == reflect.Ptr {
+-		optsValue = optsValue.Elem()
+-	}
+-
+-	optsType := reflect.TypeOf(opts)
+-	if optsType.Kind() == reflect.Ptr {
+-		optsType = optsType.Elem()
+-	}
+-
+-	var optsSlice []string
+-	if optsValue.Kind() == reflect.Struct {
+-		for i := 0; i < optsValue.NumField(); i++ {
+-			v := optsValue.Field(i)
+-			f := optsType.Field(i)
+-			qTag := f.Tag.Get("q")
+-
+-			// if the field has a 'q' tag, it goes in the query string
+-			if qTag != "" {
+-				tags := strings.Split(qTag, ",")
+-
+-				// if the field is set, add it to the slice of query pieces
+-				if !isZero(v) {
+-					switch v.Kind() {
+-					case reflect.String:
+-						optsSlice = append(optsSlice, tags[0]+"="+v.String())
+-					case reflect.Int:
+-						optsSlice = append(optsSlice, tags[0]+"="+strconv.FormatInt(v.Int(), 10))
+-					case reflect.Bool:
+-						optsSlice = append(optsSlice, tags[0]+"="+strconv.FormatBool(v.Bool()))
+-					}
+-				} else {
+-					// Otherwise, the field is not set.
+-					if len(tags) == 2 && tags[1] == "required" {
+-						// And the field is required. Return an error.
+-						return nil, fmt.Errorf("Required query parameter [%s] not set.", f.Name)
+-					}
+-				}
+-			}
 -
--	if result.Vfoo != "foo" {
--		t.Errorf("vfoo value should be 'foo': %#v", result.Vfoo)
+-		}
+-		// URL encode the string for safety.
+-		s := strings.Join(optsSlice, "&")
+-		if s != "" {
+-			s = "?" + s
+-		}
+-		u, err := url.Parse(s)
+-		if err != nil {
+-			return nil, err
+-		}
+-		return u, nil
 -	}
+-	// Return an error if the underlying type of 'opts' isn't a struct.
+-	return nil, fmt.Errorf("Options type is not a struct.")
+-}
 -
--	if result.Vbar.Vstring != "foo" {
--		t.Errorf("vstring value should be 'foo': %#v", result.Vbar.Vstring)
+-// BuildHeaders accepts a generic structure and parses it into a string map. It
+-// converts field names into header names based on "h" tags, and field values
+-// into header values by a simple one-to-one mapping.
+-func BuildHeaders(opts interface{}) (map[string]string, error) {
+-	optsValue := reflect.ValueOf(opts)
+-	if optsValue.Kind() == reflect.Ptr {
+-		optsValue = optsValue.Elem()
 -	}
 -
--	if result.Vbar.Vint != 42 {
--		t.Errorf("vint value should be 42: %#v", result.Vbar.Vint)
+-	optsType := reflect.TypeOf(opts)
+-	if optsType.Kind() == reflect.Ptr {
+-		optsType = optsType.Elem()
 -	}
 -
--	if result.Vbar.Vbool != true {
--		t.Errorf("vbool value should be true: %#v", result.Vbar.Vbool)
+-	optsMap := make(map[string]string)
+-	if optsValue.Kind() == reflect.Struct {
+-		for i := 0; i < optsValue.NumField(); i++ {
+-			v := optsValue.Field(i)
+-			f := optsType.Field(i)
+-			hTag := f.Tag.Get("h")
+-
+-			// if the field has a 'h' tag, it goes in the header
+-			if hTag != "" {
+-				tags := strings.Split(hTag, ",")
+-
+-				// if the field is set, add it to the slice of query pieces
+-				if !isZero(v) {
+-					switch v.Kind() {
+-					case reflect.String:
+-						optsMap[tags[0]] = v.String()
+-					case reflect.Int:
+-						optsMap[tags[0]] = strconv.FormatInt(v.Int(), 10)
+-					case reflect.Bool:
+-						optsMap[tags[0]] = strconv.FormatBool(v.Bool())
+-					}
+-				} else {
+-					// Otherwise, the field is not set.
+-					if len(tags) == 2 && tags[1] == "required" {
+-						// And the field is required. Return an error.
+-						return optsMap, fmt.Errorf("Required header not set.")
+-					}
+-				}
+-			}
+-
+-		}
+-		return optsMap, nil
 -	}
+-	// Return an error if the underlying type of 'opts' isn't a struct.
+-	return optsMap, fmt.Errorf("Options type is not a struct.")
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/params_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/params_test.go
+deleted file mode 100644
+index 9f1d3bd..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/params_test.go
++++ /dev/null
+@@ -1,142 +0,0 @@
+-package gophercloud
+-
+-import (
+-	"net/url"
+-	"reflect"
+-	"testing"
+-	"time"
+-
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--	if result.Vbar.Vextra != "" {
--		t.Errorf("vextra value should be empty: %#v", result.Vbar.Vextra)
--	}
+-func TestMaybeString(t *testing.T) {
+-	testString := ""
+-	var expected *string
+-	actual := MaybeString(testString)
+-	th.CheckDeepEquals(t, expected, actual)
+-
+-	testString = "carol"
+-	expected = &testString
+-	actual = MaybeString(testString)
+-	th.CheckDeepEquals(t, expected, actual)
 -}
 -
--func TestNestedTypePointer(t *testing.T) {
--	t.Parallel()
+-func TestMaybeInt(t *testing.T) {
+-	testInt := 0
+-	var expected *int
+-	actual := MaybeInt(testInt)
+-	th.CheckDeepEquals(t, expected, actual)
 -
--	input := map[string]interface{}{
--		"vfoo": "foo",
--		"vbar": &map[string]interface{}{
--			"vstring": "foo",
--			"vint":    42,
--			"vbool":   true,
--		},
--	}
+-	testInt = 4
+-	expected = &testInt
+-	actual = MaybeInt(testInt)
+-	th.CheckDeepEquals(t, expected, actual)
+-}
 -
--	var result NestedPointer
--	err := Decode(input, &result)
+-func TestBuildQueryString(t *testing.T) {
+-	opts := struct {
+-		J int    `q:"j"`
+-		R string `q:"r,required"`
+-		C bool   `q:"c"`
+-	}{
+-		J: 2,
+-		R: "red",
+-		C: true,
+-	}
+-	expected := &url.URL{RawQuery: "j=2&r=red&c=true"}
+-	actual, err := BuildQueryString(&opts)
 -	if err != nil {
--		t.Fatalf("got an err: %s", err.Error())
+-		t.Errorf("Error building query string: %v", err)
 -	}
+-	th.CheckDeepEquals(t, expected, actual)
 -
--	if result.Vfoo != "foo" {
--		t.Errorf("vfoo value should be 'foo': %#v", result.Vfoo)
+-	opts = struct {
+-		J int    `q:"j"`
+-		R string `q:"r,required"`
+-		C bool   `q:"c"`
+-	}{
+-		J: 2,
+-		C: true,
+-	}
+-	_, err = BuildQueryString(&opts)
+-	if err == nil {
+-		t.Errorf("Expected error: 'Required field not set'")
 -	}
+-	th.CheckDeepEquals(t, expected, actual)
 -
--	if result.Vbar.Vstring != "foo" {
--		t.Errorf("vstring value should be 'foo': %#v", result.Vbar.Vstring)
+-	_, err = BuildQueryString(map[string]interface{}{"Number": 4})
+-	if err == nil {
+-		t.Errorf("Expected error: 'Options type is not a struct'")
 -	}
+-}
 -
--	if result.Vbar.Vint != 42 {
--		t.Errorf("vint value should be 42: %#v", result.Vbar.Vint)
+-func TestBuildHeaders(t *testing.T) {
+-	testStruct := struct {
+-		Accept string `h:"Accept"`
+-		Num    int    `h:"Number,required"`
+-		Style  bool   `h:"Style"`
+-	}{
+-		Accept: "application/json",
+-		Num:    4,
+-		Style:  true,
 -	}
+-	expected := map[string]string{"Accept": "application/json", "Number": "4", "Style": "true"}
+-	actual, err := BuildHeaders(&testStruct)
+-	th.CheckNoErr(t, err)
+-	th.CheckDeepEquals(t, expected, actual)
 -
--	if result.Vbar.Vbool != true {
--		t.Errorf("vbool value should be true: %#v", result.Vbar.Vbool)
+-	testStruct.Num = 0
+-	_, err = BuildHeaders(&testStruct)
+-	if err == nil {
+-		t.Errorf("Expected error: 'Required header not set'")
 -	}
 -
--	if result.Vbar.Vextra != "" {
--		t.Errorf("vextra value should be empty: %#v", result.Vbar.Vextra)
+-	_, err = BuildHeaders(map[string]interface{}{"Number": 4})
+-	if err == nil {
+-		t.Errorf("Expected error: 'Options type is not a struct'")
+-	}
+-}
+-
+-func TestIsZero(t *testing.T) {
+-	var testMap map[string]interface{}
+-	testMapValue := reflect.ValueOf(testMap)
+-	expected := true
+-	actual := isZero(testMapValue)
+-	th.CheckEquals(t, expected, actual)
+-	testMap = map[string]interface{}{"empty": false}
+-	testMapValue = reflect.ValueOf(testMap)
+-	expected = false
+-	actual = isZero(testMapValue)
+-	th.CheckEquals(t, expected, actual)
+-
+-	var testArray [2]string
+-	testArrayValue := reflect.ValueOf(testArray)
+-	expected = true
+-	actual = isZero(testArrayValue)
+-	th.CheckEquals(t, expected, actual)
+-	testArray = [2]string{"one", "two"}
+-	testArrayValue = reflect.ValueOf(testArray)
+-	expected = false
+-	actual = isZero(testArrayValue)
+-	th.CheckEquals(t, expected, actual)
+-
+-	var testStruct struct {
+-		A string
+-		B time.Time
+-	}
+-	testStructValue := reflect.ValueOf(testStruct)
+-	expected = true
+-	actual = isZero(testStructValue)
+-	th.CheckEquals(t, expected, actual)
+-	testStruct = struct {
+-		A string
+-		B time.Time
+-	}{
+-		B: time.Date(2009, time.November, 10, 23, 0, 0, 0, time.UTC),
 -	}
+-	testStructValue = reflect.ValueOf(testStruct)
+-	expected = false
+-	actual = isZero(testStructValue)
+-	th.CheckEquals(t, expected, actual)
+-
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/provider_client.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/provider_client.go
+deleted file mode 100644
+index 7754c20..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/provider_client.go
++++ /dev/null
+@@ -1,33 +0,0 @@
+-package gophercloud
 -
--func TestSlice(t *testing.T) {
--	t.Parallel()
+-// ProviderClient stores details that are required to interact with any
+-// services within a specific provider's API.
+-//
+-// Generally, you acquire a ProviderClient by calling the NewClient method in
+-// the appropriate provider's child package, providing whatever authentication
+-// credentials are required.
+-type ProviderClient struct {
+-	// IdentityBase is the base URL used for a particular provider's identity
+-	// service - it will be used when issuing authenticatation requests. It
+-	// should point to the root resource of the identity service, not a specific
+-	// identity version.
+-	IdentityBase string
 -
--	inputStringSlice := map[string]interface{}{
--		"vfoo": "foo",
--		"vbar": []string{"foo", "bar", "baz"},
--	}
+-	// IdentityEndpoint is the identity endpoint. This may be a specific version
+-	// of the identity service. If this is the case, this endpoint is used rather
+-	// than querying versions first.
+-	IdentityEndpoint string
 -
--	inputStringSlicePointer := map[string]interface{}{
--		"vfoo": "foo",
--		"vbar": &[]string{"foo", "bar", "baz"},
--	}
+-	// TokenID is the ID of the most recently issued valid token.
+-	TokenID string
 -
--	outputStringSlice := &Slice{
--		"foo",
--		[]string{"foo", "bar", "baz"},
--	}
+-	// EndpointLocator describes how this provider discovers the endpoints for
+-	// its constituent services.
+-	EndpointLocator EndpointLocator
+-}
 -
--	testSliceInput(t, inputStringSlice, outputStringSlice)
--	testSliceInput(t, inputStringSlicePointer, outputStringSlice)
+-// AuthenticatedHeaders returns a map of HTTP headers that are common for all
+-// authenticated service requests.
+-func (client *ProviderClient) AuthenticatedHeaders() map[string]string {
+-	return map[string]string{"X-Auth-Token": client.TokenID}
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/provider_client_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/provider_client_test.go
+deleted file mode 100644
+index b260246..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/provider_client_test.go
++++ /dev/null
+@@ -1,16 +0,0 @@
+-package gophercloud
 -
--func TestInvalidSlice(t *testing.T) {
--	t.Parallel()
+-import (
+-	"testing"
 -
--	input := map[string]interface{}{
--		"vfoo": "foo",
--		"vbar": 42,
--	}
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--	result := Slice{}
--	err := Decode(input, &result)
--	if err == nil {
--		t.Errorf("expected failure")
+-func TestAuthenticatedHeaders(t *testing.T) {
+-	p := &ProviderClient{
+-		TokenID: "1234",
 -	}
+-	expected := map[string]string{"X-Auth-Token": "1234"}
+-	actual := p.AuthenticatedHeaders()
+-	th.CheckDeepEquals(t, expected, actual)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/auth_env.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/auth_env.go
+deleted file mode 100644
+index 5852c3c..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/auth_env.go
++++ /dev/null
+@@ -1,57 +0,0 @@
+-package rackspace
 -
--func TestSliceOfStruct(t *testing.T) {
--	t.Parallel()
--
--	input := map[string]interface{}{
--		"value": []map[string]interface{}{
--			{"vstring": "one"},
--			{"vstring": "two"},
--		},
--	}
+-import (
+-	"fmt"
+-	"os"
 -
--	var result SliceOfStruct
--	err := Decode(input, &result)
--	if err != nil {
--		t.Fatalf("got unexpected error: %s", err)
--	}
+-	"github.com/rackspace/gophercloud"
+-)
 -
--	if len(result.Value) != 2 {
--		t.Fatalf("expected two values, got %d", len(result.Value))
--	}
+-var nilOptions = gophercloud.AuthOptions{}
 -
--	if result.Value[0].Vstring != "one" {
--		t.Errorf("first value should be 'one', got: %s", result.Value[0].Vstring)
--	}
+-// ErrNoAuthUrl, ErrNoUsername, and ErrNoPassword errors indicate of the
+-// required RS_AUTH_URL, RS_USERNAME, or RS_PASSWORD environment variables,
+-// respectively, remain undefined.  See the AuthOptions() function for more details.
+-var (
+-	ErrNoAuthURL  = fmt.Errorf("Environment variable RS_AUTH_URL or OS_AUTH_URL need to be set.")
+-	ErrNoUsername = fmt.Errorf("Environment variable RS_USERNAME or OS_USERNAME need to be set.")
+-	ErrNoPassword = fmt.Errorf("Environment variable RS_API_KEY or RS_PASSWORD needs to be set.")
+-)
 -
--	if result.Value[1].Vstring != "two" {
--		t.Errorf("second value should be 'two', got: %s", result.Value[1].Vstring)
+-func prefixedEnv(base string) string {
+-	value := os.Getenv("RS_" + base)
+-	if value == "" {
+-		value = os.Getenv("OS_" + base)
 -	}
+-	return value
 -}
 -
--func TestInvalidType(t *testing.T) {
--	t.Parallel()
+-// AuthOptionsFromEnv fills out an identity.AuthOptions structure with the
+-// settings found on the various Rackspace RS_* environment variables.
+-func AuthOptionsFromEnv() (gophercloud.AuthOptions, error) {
+-	authURL := prefixedEnv("AUTH_URL")
+-	username := prefixedEnv("USERNAME")
+-	password := prefixedEnv("PASSWORD")
+-	apiKey := prefixedEnv("API_KEY")
 -
--	input := map[string]interface{}{
--		"vstring": 42,
+-	if authURL == "" {
+-		return nilOptions, ErrNoAuthURL
 -	}
 -
--	var result Basic
--	err := Decode(input, &result)
--	if err == nil {
--		t.Fatal("error should exist")
+-	if username == "" {
+-		return nilOptions, ErrNoUsername
 -	}
 -
--	derr, ok := err.(*Error)
--	if !ok {
--		t.Fatalf("error should be kind of Error, instead: %#v", err)
+-	if password == "" && apiKey == "" {
+-		return nilOptions, ErrNoPassword
 -	}
 -
--	if derr.Errors[0] != "'Vstring' expected type 'string', got unconvertible type 'int'" {
--		t.Errorf("got unexpected error: %s", err)
+-	ao := gophercloud.AuthOptions{
+-		IdentityEndpoint: authURL,
+-		Username:         username,
+-		Password:         password,
+-		APIKey:           apiKey,
 -	}
+-
+-	return ao, nil
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/snapshots/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/snapshots/delegate.go
+deleted file mode 100644
+index b338c36..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/snapshots/delegate.go
++++ /dev/null
+@@ -1,134 +0,0 @@
+-package snapshots
 -
--func TestMetadata(t *testing.T) {
--	t.Parallel()
+-import (
+-	"errors"
 -
--	input := map[string]interface{}{
--		"vfoo": "foo",
--		"vbar": map[string]interface{}{
--			"vstring": "foo",
--			"Vuint":   42,
--			"foo":     "bar",
--		},
--		"bar": "nil",
--	}
+-	"github.com/racker/perigee"
 -
--	var md Metadata
--	var result Nested
--	config := &DecoderConfig{
--		Metadata: &md,
--		Result:   &result,
--	}
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
 -
--	decoder, err := NewDecoder(config)
--	if err != nil {
--		t.Fatalf("err: %s", err)
--	}
+-	os "github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots"
+-)
 -
--	err = decoder.Decode(input)
--	if err != nil {
--		t.Fatalf("err: %s", err.Error())
--	}
+-func updateURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL("snapshots", id)
+-}
 -
--	expectedKeys := []string{"Vfoo", "Vbar.Vstring", "Vbar.Vuint", "Vbar"}
--	if !reflect.DeepEqual(md.Keys, expectedKeys) {
--		t.Fatalf("bad keys: %#v", md.Keys)
--	}
+-// CreateOptsBuilder allows extensions to add additional parameters to the
+-// Create request.
+-type CreateOptsBuilder interface {
+-	ToSnapshotCreateMap() (map[string]interface{}, error)
+-}
 -
--	expectedUnused := []string{"Vbar.foo", "bar"}
--	if !reflect.DeepEqual(md.Unused, expectedUnused) {
--		t.Fatalf("bad unused: %#v", md.Unused)
--	}
+-// CreateOpts contains options for creating a Snapshot. This object is passed to
+-// the snapshots.Create function. For more information about these parameters,
+-// see the Snapshot object.
+-type CreateOpts struct {
+-	// REQUIRED
+-	VolumeID string
+-	// OPTIONAL
+-	Description string
+-	// OPTIONAL
+-	Force bool
+-	// OPTIONAL
+-	Name string
 -}
 -
--func TestMetadata_Embedded(t *testing.T) {
--	t.Parallel()
+-// ToSnapshotCreateMap assembles a request body based on the contents of a
+-// CreateOpts.
+-func (opts CreateOpts) ToSnapshotCreateMap() (map[string]interface{}, error) {
+-	s := make(map[string]interface{})
 -
--	input := map[string]interface{}{
--		"vstring": "foo",
--		"vunique": "bar",
+-	if opts.VolumeID == "" {
+-		return nil, errors.New("Required CreateOpts field 'VolumeID' not set.")
 -	}
 -
--	var md Metadata
--	var result EmbeddedSquash
--	config := &DecoderConfig{
--		Metadata: &md,
--		Result:   &result,
--	}
+-	s["volume_id"] = opts.VolumeID
 -
--	decoder, err := NewDecoder(config)
--	if err != nil {
--		t.Fatalf("err: %s", err)
+-	if opts.Description != "" {
+-		s["display_description"] = opts.Description
 -	}
--
--	err = decoder.Decode(input)
--	if err != nil {
--		t.Fatalf("err: %s", err.Error())
+-	if opts.Name != "" {
+-		s["display_name"] = opts.Name
+-	}
+-	if opts.Force {
+-		s["force"] = opts.Force
 -	}
 -
--	expectedKeys := []string{"Vstring", "Vunique"}
+-	return map[string]interface{}{"snapshot": s}, nil
+-}
 -
--	sort.Strings(md.Keys)
--	if !reflect.DeepEqual(md.Keys, expectedKeys) {
--		t.Fatalf("bad keys: %#v", md.Keys)
--	}
+-// Create will create a new Snapshot based on the values in CreateOpts. To
+-// extract the Snapshot object from the response, call the Extract method on the
+-// CreateResult.
+-func Create(client *gophercloud.ServiceClient, opts CreateOptsBuilder) CreateResult {
+-	return CreateResult{os.Create(client, opts)}
+-}
 -
--	expectedUnused := []string{}
--	if !reflect.DeepEqual(md.Unused, expectedUnused) {
--		t.Fatalf("bad unused: %#v", md.Unused)
--	}
+-// Delete will delete the existing Snapshot with the provided ID.
+-func Delete(client *gophercloud.ServiceClient, id string) os.DeleteResult {
+-	return os.Delete(client, id)
 -}
 -
--func TestNonPtrValue(t *testing.T) {
--	t.Parallel()
+-// Get retrieves the Snapshot with the provided ID. To extract the Snapshot
+-// object from the response, call the Extract method on the GetResult.
+-func Get(client *gophercloud.ServiceClient, id string) GetResult {
+-	return GetResult{os.Get(client, id)}
+-}
 -
--	err := Decode(map[string]interface{}{}, Basic{})
--	if err == nil {
--		t.Fatal("error should exist")
--	}
+-// List returns Snapshots.
+-func List(client *gophercloud.ServiceClient) pagination.Pager {
+-	return os.List(client, os.ListOpts{})
+-}
 -
--	if err.Error() != "result must be a pointer" {
--		t.Errorf("got unexpected error: %s", err)
--	}
+-// UpdateOptsBuilder is the interface options structs have to satisfy in order
+-// to be used in the main Update operation in this package. Since many
+-// extensions decorate or modify the common logic, it is useful for them to
+-// satisfy a basic interface in order for them to be used.
+-type UpdateOptsBuilder interface {
+-	ToSnapshotUpdateMap() (map[string]interface{}, error)
 -}
 -
--func TestTagged(t *testing.T) {
--	t.Parallel()
+-// UpdateOpts is the common options struct used in this package's Update
+-// operation.
+-type UpdateOpts struct {
+-	Name        string
+-	Description string
+-}
 -
--	input := map[string]interface{}{
--		"foo": "bar",
--		"bar": "value",
+-// ToSnapshotUpdateMap casts a UpdateOpts struct to a map.
+-func (opts UpdateOpts) ToSnapshotUpdateMap() (map[string]interface{}, error) {
+-	s := make(map[string]interface{})
+-
+-	if opts.Name != "" {
+-		s["display_name"] = opts.Name
+-	}
+-	if opts.Description != "" {
+-		s["display_description"] = opts.Description
 -	}
 -
--	var result Tagged
--	err := Decode(input, &result)
+-	return map[string]interface{}{"snapshot": s}, nil
+-}
+-
+-// Update accepts a UpdateOpts struct and updates an existing snapshot using the
+-// values provided.
+-func Update(c *gophercloud.ServiceClient, snapshotID string, opts UpdateOptsBuilder) UpdateResult {
+-	var res UpdateResult
+-
+-	reqBody, err := opts.ToSnapshotUpdateMap()
 -	if err != nil {
--		t.Fatalf("unexpected error: %s", err)
+-		res.Err = err
+-		return res
 -	}
 -
--	if result.Value != "bar" {
--		t.Errorf("value should be 'bar', got: %#v", result.Value)
--	}
+-	// Send request to API
+-	_, res.Err = perigee.Request("PUT", updateURL(c, snapshotID), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{200, 201},
+-	})
 -
--	if result.Extra != "value" {
--		t.Errorf("extra should be 'value', got: %#v", result.Extra)
--	}
+-	return res
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/snapshots/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/snapshots/delegate_test.go
+deleted file mode 100644
+index 1a02b46..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/snapshots/delegate_test.go
++++ /dev/null
+@@ -1,97 +0,0 @@
+-package snapshots
 -
--func TestWeakDecode(t *testing.T) {
--	t.Parallel()
+-import (
+-	"testing"
 -
--	input := map[string]interface{}{
--		"foo": "4",
--		"bar": "value",
--	}
+-	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--	var result struct {
--		Foo int
--		Bar string
--	}
+-const endpoint = "http://localhost:57909/v1/12345"
 -
--	if err := WeakDecode(input, &result); err != nil {
--		t.Fatalf("err: %s", err)
--	}
--	if result.Foo != 4 {
--		t.Fatalf("bad: %#v", result)
--	}
--	if result.Bar != "value" {
--		t.Fatalf("bad: %#v", result)
--	}
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint}
 -}
 -
--func testSliceInput(t *testing.T, input map[string]interface{}, expected *Slice) {
--	var result Slice
--	err := Decode(input, &result)
--	if err != nil {
--		t.Fatalf("got error: %s", err)
--	}
+-func TestUpdateURL(t *testing.T) {
+-	actual := updateURL(endpointClient(), "foo")
+-	expected := endpoint + "snapshots/foo"
+-	th.AssertEquals(t, expected, actual)
+-}
 -
--	if result.Vfoo != expected.Vfoo {
--		t.Errorf("Vfoo expected '%s', got '%s'", expected.Vfoo, result.Vfoo)
--	}
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	if result.Vbar == nil {
--		t.Fatalf("Vbar a slice, got '%#v'", result.Vbar)
--	}
+-	os.MockListResponse(t)
 -
--	if len(result.Vbar) != len(expected.Vbar) {
--		t.Errorf("Vbar length should be %d, got %d", len(expected.Vbar), len(result.Vbar))
--	}
+-	count := 0
 -
--	for i, v := range result.Vbar {
--		if v != expected.Vbar[i] {
--			t.Errorf(
--				"Vbar[%d] should be '%#v', got '%#v'",
--				i, expected.Vbar[i], v)
+-	err := List(fake.ServiceClient()).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractSnapshots(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract snapshots: %v", err)
+-			return false, err
 -		}
--	}
+-
+-		expected := []Snapshot{
+-			Snapshot{
+-				ID:   "289da7f8-6440-407c-9fb4-7db01ec49164",
+-				Name: "snapshot-001",
+-			},
+-			Snapshot{
+-				ID:   "96c3bda7-c82a-4f50-be73-ca7621794835",
+-				Name: "snapshot-002",
+-			},
+-		}
+-
+-		th.CheckDeepEquals(t, expected, actual)
+-
+-		return true, nil
+-	})
+-
+-	th.AssertEquals(t, 1, count)
+-	th.AssertNoErr(t, err)
 -}
-diff --git a/Godeps/_workspace/src/github.com/racker/perigee/.gitignore b/Godeps/_workspace/src/github.com/racker/perigee/.gitignore
+-
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	os.MockGetResponse(t)
+-
+-	v, err := Get(fake.ServiceClient(), "d32019d3-bc6e-4319-9c1d-6722fc136a22").Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, v.Name, "snapshot-001")
+-	th.AssertEquals(t, v.ID, "d32019d3-bc6e-4319-9c1d-6722fc136a22")
+-}
+-
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	os.MockCreateResponse(t)
+-
+-	options := &CreateOpts{VolumeID: "1234", Name: "snapshot-001"}
+-	n, err := Create(fake.ServiceClient(), options).Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertEquals(t, n.VolumeID, "1234")
+-	th.AssertEquals(t, n.Name, "snapshot-001")
+-	th.AssertEquals(t, n.ID, "d32019d3-bc6e-4319-9c1d-6722fc136a22")
+-}
+-
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	os.MockDeleteResponse(t)
+-
+-	res := Delete(fake.ServiceClient(), "d32019d3-bc6e-4319-9c1d-6722fc136a22")
+-	th.AssertNoErr(t, res.Err)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/snapshots/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/snapshots/doc.go
 deleted file mode 100644
-index 49ca32a..0000000
---- a/Godeps/_workspace/src/github.com/racker/perigee/.gitignore
+index ad6064f..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/snapshots/doc.go
 +++ /dev/null
-@@ -1,2 +0,0 @@
--bin/*
--pkg/*
-diff --git a/Godeps/_workspace/src/github.com/racker/perigee/LICENSE b/Godeps/_workspace/src/github.com/racker/perigee/LICENSE
+@@ -1,3 +0,0 @@
+-// Package snapshots provides information and interaction with the snapshot
+-// API resource for the Rackspace Block Storage service.
+-package snapshots
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/snapshots/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/snapshots/results.go
 deleted file mode 100644
-index d645695..0000000
---- a/Godeps/_workspace/src/github.com/racker/perigee/LICENSE
+index 0fab282..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/snapshots/results.go
 +++ /dev/null
-@@ -1,202 +0,0 @@
+@@ -1,149 +0,0 @@
+-package snapshots
 -
--                                 Apache License
--                           Version 2.0, January 2004
--                        http://www.apache.org/licenses/
+-import (
+-	"github.com/racker/perigee"
 -
--   TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+-	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack/blockstorage/v1/snapshots"
+-	"github.com/rackspace/gophercloud/pagination"
 -
--   1. Definitions.
+-	"github.com/mitchellh/mapstructure"
+-)
 -
--      "License" shall mean the terms and conditions for use, reproduction,
--      and distribution as defined by Sections 1 through 9 of this document.
+-// Status is the type used to represent a snapshot's status
+-type Status string
 -
--      "Licensor" shall mean the copyright owner or entity authorized by
--      the copyright owner that is granting the License.
+-// Constants to use for supported statuses
+-const (
+-	Creating    Status = "CREATING"
+-	Available   Status = "AVAILABLE"
+-	Deleting    Status = "DELETING"
+-	Error       Status = "ERROR"
+-	DeleteError Status = "ERROR_DELETING"
+-)
 -
--      "Legal Entity" shall mean the union of the acting entity and all
--      other entities that control, are controlled by, or are under common
--      control with that entity. For the purposes of this definition,
--      "control" means (i) the power, direct or indirect, to cause the
--      direction or management of such entity, whether by contract or
--      otherwise, or (ii) ownership of fifty percent (50%) or more of the
--      outstanding shares, or (iii) beneficial ownership of such entity.
+-// Snapshot is the Rackspace representation of an external block storage device.
+-type Snapshot struct {
+-	// The timestamp when this snapshot was created.
+-	CreatedAt string `mapstructure:"created_at"`
 -
--      "You" (or "Your") shall mean an individual or Legal Entity
--      exercising permissions granted by this License.
+-	// The human-readable description for this snapshot.
+-	Description string `mapstructure:"display_description"`
 -
--      "Source" form shall mean the preferred form for making modifications,
--      including but not limited to software source code, documentation
--      source, and configuration files.
+-	// The human-readable name for this snapshot.
+-	Name string `mapstructure:"display_name"`
 -
--      "Object" form shall mean any form resulting from mechanical
--      transformation or translation of a Source form, including but
--      not limited to compiled object code, generated documentation,
--      and conversions to other media types.
+-	// The UUID for this snapshot.
+-	ID string `mapstructure:"id"`
 -
--      "Work" shall mean the work of authorship, whether in Source or
--      Object form, made available under the License, as indicated by a
--      copyright notice that is included in or attached to the work
--      (an example is provided in the Appendix below).
+-	// The random metadata associated with this snapshot. Note: unlike standard
+-	// OpenStack snapshots, this cannot actually be set.
+-	Metadata map[string]string `mapstructure:"metadata"`
 -
--      "Derivative Works" shall mean any work, whether in Source or Object
--      form, that is based on (or derived from) the Work and for which the
--      editorial revisions, annotations, elaborations, or other modifications
--      represent, as a whole, an original work of authorship. For the purposes
--      of this License, Derivative Works shall not include works that remain
--      separable from, or merely link (or bind by name) to the interfaces of,
--      the Work and Derivative Works thereof.
+-	// Indicates the current progress of the snapshot's backup procedure.
+-	Progress string `mapstructure:"os-extended-snapshot-attributes:progress"`
 -
--      "Contribution" shall mean any work of authorship, including
--      the original version of the Work and any modifications or additions
--      to that Work or Derivative Works thereof, that is intentionally
--      submitted to Licensor for inclusion in the Work by the copyright owner
--      or by an individual or Legal Entity authorized to submit on behalf of
--      the copyright owner. For the purposes of this definition, "submitted"
--      means any form of electronic, verbal, or written communication sent
--      to the Licensor or its representatives, including but not limited to
--      communication on electronic mailing lists, source code control systems,
--      and issue tracking systems that are managed by, or on behalf of, the
--      Licensor for the purpose of discussing and improving the Work, but
--      excluding communication that is conspicuously marked or otherwise
--      designated in writing by the copyright owner as "Not a Contribution."
+-	// The project ID.
+-	ProjectID string `mapstructure:"os-extended-snapshot-attributes:project_id"`
 -
--      "Contributor" shall mean Licensor and any individual or Legal Entity
--      on behalf of whom a Contribution has been received by Licensor and
--      subsequently incorporated within the Work.
+-	// The size of the volume which this snapshot backs up.
+-	Size int `mapstructure:"size"`
 -
--   2. Grant of Copyright License. Subject to the terms and conditions of
--      this License, each Contributor hereby grants to You a perpetual,
--      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
--      copyright license to reproduce, prepare Derivative Works of,
--      publicly display, publicly perform, sublicense, and distribute the
--      Work and such Derivative Works in Source or Object form.
+-	// The status of the snapshot.
+-	Status Status `mapstructure:"status"`
 -
--   3. Grant of Patent License. Subject to the terms and conditions of
--      this License, each Contributor hereby grants to You a perpetual,
--      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
--      (except as stated in this section) patent license to make, have made,
--      use, offer to sell, sell, import, and otherwise transfer the Work,
--      where such license applies only to those patent claims licensable
--      by such Contributor that are necessarily infringed by their
--      Contribution(s) alone or by combination of their Contribution(s)
--      with the Work to which such Contribution(s) was submitted. If You
--      institute patent litigation against any entity (including a
--      cross-claim or counterclaim in a lawsuit) alleging that the Work
--      or a Contribution incorporated within the Work constitutes direct
--      or contributory patent infringement, then any patent licenses
--      granted to You under this License for that Work shall terminate
--      as of the date such litigation is filed.
+-	// The ID of the volume which this snapshot seeks to back up.
+-	VolumeID string `mapstructure:"volume_id"`
+-}
 -
--   4. Redistribution. You may reproduce and distribute copies of the
--      Work or Derivative Works thereof in any medium, with or without
--      modifications, and in Source or Object form, provided that You
--      meet the following conditions:
+-// CreateResult represents the result of a create operation
+-type CreateResult struct {
+-	os.CreateResult
+-}
 -
--      (a) You must give any other recipients of the Work or
--          Derivative Works a copy of this License; and
+-// GetResult represents the result of a get operation
+-type GetResult struct {
+-	os.GetResult
+-}
 -
--      (b) You must cause any modified files to carry prominent notices
--          stating that You changed the files; and
+-// UpdateResult represents the result of an update operation
+-type UpdateResult struct {
+-	gophercloud.Result
+-}
 -
--      (c) You must retain, in the Source form of any Derivative Works
--          that You distribute, all copyright, patent, trademark, and
--          attribution notices from the Source form of the Work,
--          excluding those notices that do not pertain to any part of
--          the Derivative Works; and
+-func commonExtract(resp interface{}, err error) (*Snapshot, error) {
+-	if err != nil {
+-		return nil, err
+-	}
 -
--      (d) If the Work includes a "NOTICE" text file as part of its
--          distribution, then any Derivative Works that You distribute must
--          include a readable copy of the attribution notices contained
--          within such NOTICE file, excluding those notices that do not
--          pertain to any part of the Derivative Works, in at least one
--          of the following places: within a NOTICE text file distributed
--          as part of the Derivative Works; within the Source form or
--          documentation, if provided along with the Derivative Works; or,
--          within a display generated by the Derivative Works, if and
--          wherever such third-party notices normally appear. The contents
--          of the NOTICE file are for informational purposes only and
--          do not modify the License. You may add Your own attribution
--          notices within Derivative Works that You distribute, alongside
--          or as an addendum to the NOTICE text from the Work, provided
--          that such additional attribution notices cannot be construed
--          as modifying the License.
+-	var respStruct struct {
+-		Snapshot *Snapshot `json:"snapshot"`
+-	}
 -
--      You may add Your own copyright statement to Your modifications and
--      may provide additional or different license terms and conditions
--      for use, reproduction, or distribution of Your modifications, or
--      for any such Derivative Works as a whole, provided Your use,
--      reproduction, and distribution of the Work otherwise complies with
--      the conditions stated in this License.
+-	err = mapstructure.Decode(resp, &respStruct)
 -
--   5. Submission of Contributions. Unless You explicitly state otherwise,
--      any Contribution intentionally submitted for inclusion in the Work
--      by You to the Licensor shall be under the terms and conditions of
--      this License, without any additional terms or conditions.
--      Notwithstanding the above, nothing herein shall supersede or modify
--      the terms of any separate license agreement you may have executed
--      with Licensor regarding such Contributions.
+-	return respStruct.Snapshot, err
+-}
 -
--   6. Trademarks. This License does not grant permission to use the trade
--      names, trademarks, service marks, or product names of the Licensor,
--      except as required for reasonable and customary use in describing the
--      origin of the Work and reproducing the content of the NOTICE file.
+-// Extract will get the Snapshot object out of the GetResult object.
+-func (r GetResult) Extract() (*Snapshot, error) {
+-	return commonExtract(r.Body, r.Err)
+-}
 -
--   7. Disclaimer of Warranty. Unless required by applicable law or
--      agreed to in writing, Licensor provides the Work (and each
--      Contributor provides its Contributions) on an "AS IS" BASIS,
--      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
--      implied, including, without limitation, any warranties or conditions
--      of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
--      PARTICULAR PURPOSE. You are solely responsible for determining the
--      appropriateness of using or redistributing the Work and assume any
--      risks associated with Your exercise of permissions under this License.
+-// Extract will get the Snapshot object out of the CreateResult object.
+-func (r CreateResult) Extract() (*Snapshot, error) {
+-	return commonExtract(r.Body, r.Err)
+-}
 -
--   8. Limitation of Liability. In no event and under no legal theory,
--      whether in tort (including negligence), contract, or otherwise,
--      unless required by applicable law (such as deliberate and grossly
--      negligent acts) or agreed to in writing, shall any Contributor be
--      liable to You for damages, including any direct, indirect, special,
--      incidental, or consequential damages of any character arising as a
--      result of this License or out of the use or inability to use the
--      Work (including but not limited to damages for loss of goodwill,
--      work stoppage, computer failure or malfunction, or any and all
--      other commercial damages or losses), even if such Contributor
--      has been advised of the possibility of such damages.
+-// Extract will get the Snapshot object out of the UpdateResult object.
+-func (r UpdateResult) Extract() (*Snapshot, error) {
+-	return commonExtract(r.Body, r.Err)
+-}
 -
--   9. Accepting Warranty or Additional Liability. While redistributing
--      the Work or Derivative Works thereof, You may choose to offer,
--      and charge a fee for, acceptance of support, warranty, indemnity,
--      or other liability obligations and/or rights consistent with this
--      License. However, in accepting such obligations, You may act only
--      on Your own behalf and on Your sole responsibility, not on behalf
--      of any other Contributor, and only if You agree to indemnify,
--      defend, and hold each Contributor harmless for any liability
--      incurred by, or claims asserted against, such Contributor by reason
--      of your accepting any such warranty or additional liability.
+-// ExtractSnapshots extracts and returns Snapshots. It is used while iterating over a snapshots.List call.
+-func ExtractSnapshots(page pagination.Page) ([]Snapshot, error) {
+-	var response struct {
+-		Snapshots []Snapshot `json:"snapshots"`
+-	}
 -
--   END OF TERMS AND CONDITIONS
+-	err := mapstructure.Decode(page.(os.ListResult).Body, &response)
+-	return response.Snapshots, err
+-}
 -
--   APPENDIX: How to apply the Apache License to your work.
+-// WaitUntilComplete will continually poll a snapshot until it successfully
+-// transitions to a specified state. It will do this for at most the number of
+-// seconds specified.
+-func (snapshot Snapshot) WaitUntilComplete(c *gophercloud.ServiceClient, timeout int) error {
+-	return gophercloud.WaitFor(timeout, func() (bool, error) {
+-		// Poll resource
+-		current, err := Get(c, snapshot.ID).Extract()
+-		if err != nil {
+-			return false, err
+-		}
 -
--      To apply the Apache License to your work, attach the following
--      boilerplate notice, with the fields enclosed by brackets "[]"
--      replaced with your own identifying information. (Don't include
--      the brackets!)  The text should be enclosed in the appropriate
--      comment syntax for the file format. We also recommend that a
--      file or class name and description of purpose be included on the
--      same "printed page" as the copyright notice for easier
--      identification within third-party archives.
+-		// Has it been built yet?
+-		if current.Progress == "100%" {
+-			return true, nil
+-		}
 -
--   Copyright [yyyy] [name of copyright owner]
+-		return false, nil
+-	})
+-}
 -
--   Licensed under the Apache License, Version 2.0 (the "License");
--   you may not use this file except in compliance with the License.
--   You may obtain a copy of the License at
+-// WaitUntilDeleted will continually poll a snapshot until it has been
+-// successfully deleted, i.e. returns a 404 status.
+-func (snapshot Snapshot) WaitUntilDeleted(c *gophercloud.ServiceClient, timeout int) error {
+-	return gophercloud.WaitFor(timeout, func() (bool, error) {
+-		// Poll resource
+-		_, err := Get(c, snapshot.ID).Extract()
 -
--       http://www.apache.org/licenses/LICENSE-2.0
+-		// Check for a 404
+-		if casted, ok := err.(*perigee.UnexpectedResponseCodeError); ok && casted.Actual == 404 {
+-			return true, nil
+-		} else if err != nil {
+-			return false, err
+-		}
 -
--   Unless required by applicable law or agreed to in writing, software
--   distributed under the License is distributed on an "AS IS" BASIS,
--   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
--   See the License for the specific language governing permissions and
--   limitations under the License.
-diff --git a/Godeps/_workspace/src/github.com/racker/perigee/README.md b/Godeps/_workspace/src/github.com/racker/perigee/README.md
+-		return false, nil
+-	})
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumes/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumes/delegate.go
 deleted file mode 100644
-index 81cbf4a..0000000
---- a/Godeps/_workspace/src/github.com/racker/perigee/README.md
+index 4383494..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumes/delegate.go
 +++ /dev/null
-@@ -1,120 +0,0 @@
--# perigee
+@@ -1,75 +0,0 @@
+-package volumes
 -
--Perigee provides a REST client that, while it should be generic enough to use with most any RESTful API, is nonetheless optimized to the needs of the OpenStack APIs.
--Perigee grew out of the need to refactor out common API access code from the [gorax](http://github.com/racker/gorax) project.
+-import (
+-	"fmt"
 -
--Several things influenced the name of the project.
--Numerous elements of the OpenStack ecosystem are named after astronomical artifacts.
--Additionally, perigee occurs when two orbiting bodies are closest to each other.
--Perigee seemed appropriate for something aiming to bring OpenStack and other RESTful services closer to the end-user.
+-	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--**This library is still in the very early stages of development. Unless you want to contribute, it probably isn't what you want**
+-type CreateOpts struct {
+-	os.CreateOpts
+-}
 -
--## Installation and Testing
+-func (opts CreateOpts) ToVolumeCreateMap() (map[string]interface{}, error) {
+-	if opts.Size < 75 || opts.Size > 1024 {
+-		return nil, fmt.Errorf("Size field must be between 75 and 1024")
+-	}
 -
--To install:
+-	return opts.CreateOpts.ToVolumeCreateMap()
+-}
 -
--```bash
--go get github.com/racker/perigee
--```
+-// Create will create a new Volume based on the values in CreateOpts. To extract
+-// the Volume object from the response, call the Extract method on the
+-// CreateResult.
+-func Create(client *gophercloud.ServiceClient, opts os.CreateOptsBuilder) CreateResult {
+-	return CreateResult{os.Create(client, opts)}
+-}
 -
--To run unit tests:
+-// Delete will delete the existing Volume with the provided ID.
+-func Delete(client *gophercloud.ServiceClient, id string) os.DeleteResult {
+-	return os.Delete(client, id)
+-}
 -
--```bash
--go test github.com/racker/perigee
--```
+-// Get retrieves the Volume with the provided ID. To extract the Volume object
+-// from the response, call the Extract method on the GetResult.
+-func Get(client *gophercloud.ServiceClient, id string) GetResult {
+-	return GetResult{os.Get(client, id)}
+-}
 -
--## Contributing
+-// List returns volumes optionally limited by the conditions provided in ListOpts.
+-func List(client *gophercloud.ServiceClient) pagination.Pager {
+-	return os.List(client, os.ListOpts{})
+-}
 -
--The following guidelines are preliminary, as this project is just starting out.
--However, this should serve as a working first-draft.
+-// UpdateOpts contain options for updating an existing Volume. This object is passed
+-// to the volumes.Update function. For more information about the parameters, see
+-// the Volume object.
+-type UpdateOpts struct {
+-	// OPTIONAL
+-	Name string
+-	// OPTIONAL
+-	Description string
+-}
 -
--### Branching
+-// ToVolumeUpdateMap assembles a request body based on the contents of an
+-// UpdateOpts.
+-func (opts UpdateOpts) ToVolumeUpdateMap() (map[string]interface{}, error) {
+-	v := make(map[string]interface{})
 -
--The master branch must always be a valid build.
--The `go get` command will not work otherwise.
--Therefore, development must occur on a different branch.
+-	if opts.Description != "" {
+-		v["display_description"] = opts.Description
+-	}
+-	if opts.Name != "" {
+-		v["display_name"] = opts.Name
+-	}
 -
--When creating a feature branch, do so off the master branch:
+-	return map[string]interface{}{"volume": v}, nil
+-}
 -
--```bash
--git checkout master
--git pull
--git checkout -b featureBranch
--git checkout -b featureBranch-wip   # optional
--```
+-// Update will update the Volume with provided information. To extract the updated
+-// Volume from the response, call the Extract method on the UpdateResult.
+-func Update(client *gophercloud.ServiceClient, id string, opts os.UpdateOptsBuilder) UpdateResult {
+-	return UpdateResult{os.Update(client, id, opts)}
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumes/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumes/delegate_test.go
+deleted file mode 100644
+index b44564c..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumes/delegate_test.go
++++ /dev/null
+@@ -1,106 +0,0 @@
+-package volumes
 -
--Perform all your editing and testing in the WIP-branch.
--Feel free to make as many commits as you see fit.
--You may even open "WIP" pull requests from your feature branch to seek feedback.
--WIP pull requests will **never** be merged, however.
+-import (
+-	"testing"
 -
--To get code merged, you'll need to "squash" your changes into one or more clean commits in the feature branch.
--These steps should be followed:
+-	os "github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--```bash
--git checkout featureBranch
--git merge --squash featureBranch-wip
--git commit -a
--git push origin featureBranch
--```
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--You may now open a nice, clean, self-contained pull request from featureBranch to master.
+-	os.MockListResponse(t)
 -
--The `git commit -a` command above will open a text editor so that
--you may provide a comprehensive description of the changes.
+-	count := 0
 -
--In general, when submitting a pull request against master,
--be sure to answer the following questions:
+-	err := List(fake.ServiceClient()).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractVolumes(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract volumes: %v", err)
+-			return false, err
+-		}
 -
--- What is the problem?
--- Why is it a problem?
--- What is your solution?
--- How does your solution work?  (Recommended for non-trivial changes.)
--- Why should we use your solution over someone elses?  (Recommended especially if multiple solutions being discussed.)
+-		expected := []Volume{
+-			Volume{
+-				ID:   "289da7f8-6440-407c-9fb4-7db01ec49164",
+-				Name: "vol-001",
+-			},
+-			Volume{
+-				ID:   "96c3bda7-c82a-4f50-be73-ca7621794835",
+-				Name: "vol-002",
+-			},
+-		}
 -
--Remember that monster-sized pull requests are a bear to code-review,
--so having helpful commit logs are an absolute must to review changes as quickly as possible.
+-		th.CheckDeepEquals(t, expected, actual)
 -
--Finally, (s)he who breaks master is ultimately responsible for fixing master.
+-		return true, nil
+-	})
 -
--### Source Representation
+-	th.AssertEquals(t, 1, count)
+-	th.AssertNoErr(t, err)
+-}
 -
--The Go community firmly believes in a consistent representation for all Go source code.
--We do too.
--Make sure all source code is passed through "go fmt" *before* you create your pull request.
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--Please note, however, that we fully acknowledge and recognize that we no longer rely upon punch-cards for representing source files.
--Therefore, no 80-column limit exists.
--However, if a line exceeds 132 columns, you may want to consider splitting the line.
+-	os.MockGetResponse(t)
 -
--### Unit and Integration Tests
+-	v, err := Get(fake.ServiceClient(), "d32019d3-bc6e-4319-9c1d-6722fc136a22").Extract()
+-	th.AssertNoErr(t, err)
 -
--Pull requests that include non-trivial code changes without accompanying unit tests will be flatly rejected.
--While we have no way of enforcing this practice,
--you can ensure your code is thoroughly tested by always [writing tests first by intention.](http://en.wikipedia.org/wiki/Test-driven_development)
+-	th.AssertEquals(t, v.Name, "vol-001")
+-	th.AssertEquals(t, v.ID, "d32019d3-bc6e-4319-9c1d-6722fc136a22")
+-}
 -
--When creating a pull request, if even one test fails, the PR will be rejected.
--Make sure all unit tests pass.
--Make sure all integration tests pass.
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--### Documentation
+-	os.MockCreateResponse(t)
 -
--Private functions and methods which are obvious to anyone unfamiliar with gorax needn't be accompanied by documentation.
--However, this is a code-smell; if submitting a PR, expect to justify your decision.
+-	n, err := Create(fake.ServiceClient(), CreateOpts{os.CreateOpts{Size: 75}}).Extract()
+-	th.AssertNoErr(t, err)
 -
--Public functions, regardless of how obvious, **must** have accompanying godoc-style documentation.
--This is not to suggest you should provide a tome for each function, however.
--Sometimes a link to more information is more appropriate, provided the link is stable, reliable, and pertinent.
+-	th.AssertEquals(t, n.Size, 4)
+-	th.AssertEquals(t, n.ID, "d32019d3-bc6e-4319-9c1d-6722fc136a22")
+-}
 -
--Changing documentation often results in bizarre diffs in pull requests, due to text often spanning multiple lines.
--To work around this, put [one logical thought or sentence on a single line.](http://rhodesmill.org/brandon/2012/one-sentence-per-line/)
--While this looks weird in a plain-text editor,
--remember that both godoc and HTML viewers will reflow text.
--The source code and its comments should be easy to edit with minimal diff pollution.
--Let software dedicated to presenting the documentation to human readers deal with its presentation.
+-func TestSizeRange(t *testing.T) {
+-	_, err := Create(fake.ServiceClient(), CreateOpts{os.CreateOpts{Size: 1}}).Extract()
+-	if err == nil {
+-		t.Fatalf("Expected error, got none")
+-	}
 -
--## Examples
+-	_, err = Create(fake.ServiceClient(), CreateOpts{os.CreateOpts{Size: 2000}}).Extract()
+-	if err == nil {
+-		t.Fatalf("Expected error, got none")
+-	}
+-}
 -
--t.b.d.
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
-diff --git a/Godeps/_workspace/src/github.com/racker/perigee/api.go b/Godeps/_workspace/src/github.com/racker/perigee/api.go
-deleted file mode 100644
-index 0fcbadb..0000000
---- a/Godeps/_workspace/src/github.com/racker/perigee/api.go
-+++ /dev/null
-@@ -1,269 +0,0 @@
--// vim: ts=8 sw=8 noet ai
+-	os.MockDeleteResponse(t)
 -
--package perigee
+-	res := Delete(fake.ServiceClient(), "d32019d3-bc6e-4319-9c1d-6722fc136a22")
+-	th.AssertNoErr(t, res.Err)
+-}
 -
--import (
--	"encoding/json"
--	"fmt"
--	"io"
--	"io/ioutil"
--	"log"
--	"net/http"
--	"strings"
--)
+-func TestUpdate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--// The UnexpectedResponseCodeError structure represents a mismatch in understanding between server and client in terms of response codes.
--// Most often, this is due to an actual error condition (e.g., getting a 404 for a resource when you expect a 200).
--// However, it needn't always be the case (e.g., getting a 204 (No Content) response back when a 200 is expected).
--type UnexpectedResponseCodeError struct {
--	Url      string
--	Expected []int
--	Actual   int
--	Body     []byte
--}
+-	os.MockUpdateResponse(t)
 -
--func (err *UnexpectedResponseCodeError) Error() string {
--	return fmt.Sprintf("Expected HTTP response code %d when accessing URL(%s); got %d instead with the following body:\n%s", err.Expected, err.Url, err.Actual, string(err.Body))
+-	options := &UpdateOpts{Name: "vol-002"}
+-	v, err := Update(fake.ServiceClient(), "d32019d3-bc6e-4319-9c1d-6722fc136a22", options).Extract()
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, "vol-002", v.Name)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumes/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumes/doc.go
+deleted file mode 100644
+index b2be25c..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumes/doc.go
++++ /dev/null
+@@ -1,3 +0,0 @@
+-// Package volumes provides information and interaction with the volume
+-// API resource for the Rackspace Block Storage service.
+-package volumes
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumes/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumes/results.go
+deleted file mode 100644
+index c7c2cc4..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumes/results.go
++++ /dev/null
+@@ -1,66 +0,0 @@
+-package volumes
 -
--// Request issues an HTTP request, marshaling parameters, and unmarshaling results, as configured in the provided Options parameter.
--// The Response structure returned, if any, will include accumulated results recovered from the HTTP server.
--// See the Response structure for more details.
--func Request(method string, url string, opts Options) (*Response, error) {
--	var body io.Reader
--	var response Response
+-import (
+-	os "github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumes"
+-	"github.com/rackspace/gophercloud/pagination"
 -
--	client := opts.CustomClient
--	if client == nil {
--		client = new(http.Client)
--	}
+-	"github.com/mitchellh/mapstructure"
+-)
 -
--	contentType := opts.ContentType
+-// Volume wraps an Openstack volume
+-type Volume os.Volume
 -
--	body = nil
--	if opts.ReqBody != nil {
--		if contentType == "" {
--			contentType = "application/json"
--		}
+-// CreateResult represents the result of a create operation
+-type CreateResult struct {
+-	os.CreateResult
+-}
 -
--		if contentType == "application/json" {
--			bodyText, err := json.Marshal(opts.ReqBody)
--			if err != nil {
--				return nil, err
--			}
--			body = strings.NewReader(string(bodyText))
--			if opts.DumpReqJson {
--				log.Printf("Making request:\n%#v\n", string(bodyText))
--			}
--		} else {
--			// assume opts.ReqBody implements the correct interface
--			body = opts.ReqBody.(io.Reader)
--		}
--	}
+-// GetResult represents the result of a get operation
+-type GetResult struct {
+-	os.GetResult
+-}
 -
--	req, err := http.NewRequest(method, url, body)
+-// UpdateResult represents the result of an update operation
+-type UpdateResult struct {
+-	os.UpdateResult
+-}
+-
+-func commonExtract(resp interface{}, err error) (*Volume, error) {
 -	if err != nil {
 -		return nil, err
 -	}
 -
--	if contentType != "" {
--		req.Header.Add("Content-Type", contentType)
+-	var respStruct struct {
+-		Volume *Volume `json:"volume"`
 -	}
 -
--	if opts.ContentLength > 0 {
--		req.ContentLength = opts.ContentLength
--		req.Header.Add("Content-Length", string(opts.ContentLength))
--	}
+-	err = mapstructure.Decode(resp, &respStruct)
 -
--	if opts.MoreHeaders != nil {
--		for k, v := range opts.MoreHeaders {
--			req.Header.Add(k, v)
--		}
--	}
+-	return respStruct.Volume, err
+-}
 -
--	if accept := req.Header.Get("Accept"); accept == "" {
--		accept = opts.Accept
--		if accept == "" {
--			accept = "application/json"
--		}
--		req.Header.Add("Accept", accept)
--	}
+-// Extract will get the Volume object out of the GetResult object.
+-func (r GetResult) Extract() (*Volume, error) {
+-	return commonExtract(r.Body, r.Err)
+-}
 -
--	if opts.SetHeaders != nil {
--		err = opts.SetHeaders(req)
--		if err != nil {
--			return &response, err
--		}
--	}
+-// Extract will get the Volume object out of the CreateResult object.
+-func (r CreateResult) Extract() (*Volume, error) {
+-	return commonExtract(r.Body, r.Err)
+-}
 -
--	httpResponse, err := client.Do(req)
--	if httpResponse != nil {
--		response.HttpResponse = *httpResponse
--		response.StatusCode = httpResponse.StatusCode
--	}
+-// Extract will get the Volume object out of the UpdateResult object.
+-func (r UpdateResult) Extract() (*Volume, error) {
+-	return commonExtract(r.Body, r.Err)
+-}
 -
--	if err != nil {
--		return &response, err
--	}
--	// This if-statement is legacy code, preserved for backward compatibility.
--	if opts.StatusCode != nil {
--		*opts.StatusCode = httpResponse.StatusCode
+-// ExtractVolumes extracts and returns Volumes. It is used while iterating over a volumes.List call.
+-func ExtractVolumes(page pagination.Page) ([]Volume, error) {
+-	var response struct {
+-		Volumes []Volume `json:"volumes"`
 -	}
 -
--	acceptableResponseCodes := opts.OkCodes
--	if len(acceptableResponseCodes) != 0 {
--		if not_in(httpResponse.StatusCode, acceptableResponseCodes) {
--			b, _ := ioutil.ReadAll(httpResponse.Body)
--			httpResponse.Body.Close()
--			return &response, &UnexpectedResponseCodeError{
--				Url:      url,
--				Expected: acceptableResponseCodes,
--				Actual:   httpResponse.StatusCode,
--				Body:     b,
--			}
--		}
--	}
--	if opts.Results != nil {
--		defer httpResponse.Body.Close()
--		jsonResult, err := ioutil.ReadAll(httpResponse.Body)
--		response.JsonResult = jsonResult
--		if err != nil {
--			return &response, err
--		}
+-	err := mapstructure.Decode(page.(os.ListResult).Body, &response)
 -
--		err = json.Unmarshal(jsonResult, opts.Results)
--		// This if-statement is legacy code, preserved for backward compatibility.
--		if opts.ResponseJson != nil {
--			*opts.ResponseJson = jsonResult
--		}
--	}
--	return &response, err
+-	return response.Volumes, err
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumetypes/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumetypes/delegate.go
+deleted file mode 100644
+index c96b3e4..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumetypes/delegate.go
++++ /dev/null
+@@ -1,18 +0,0 @@
+-package volumetypes
 -
--// not_in returns false if, and only if, the provided needle is _not_
--// in the given set of integers.
--func not_in(needle int, haystack []int) bool {
--	for _, straw := range haystack {
--		if needle == straw {
--			return false
--		}
--	}
--	return true
--}
+-import (
+-	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--// Post makes a POST request against a server using the provided HTTP client.
--// The url must be a fully-formed URL string.
--// DEPRECATED.  Use Request() instead.
--func Post(url string, opts Options) error {
--	r, err := Request("POST", url, opts)
--	if opts.Response != nil {
--		*opts.Response = r
--	}
--	return err
+-// List returns all volume types.
+-func List(client *gophercloud.ServiceClient) pagination.Pager {
+-	return os.List(client)
 -}
 -
--// Get makes a GET request against a server using the provided HTTP client.
--// The url must be a fully-formed URL string.
--// DEPRECATED.  Use Request() instead.
--func Get(url string, opts Options) error {
--	r, err := Request("GET", url, opts)
--	if opts.Response != nil {
--		*opts.Response = r
--	}
--	return err
+-// Get will retrieve the volume type with the provided ID. To extract the volume
+-// type from the result, call the Extract method on the GetResult.
+-func Get(client *gophercloud.ServiceClient, id string) GetResult {
+-	return GetResult{os.Get(client, id)}
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumetypes/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumetypes/delegate_test.go
+deleted file mode 100644
+index 6e65c90..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumetypes/delegate_test.go
++++ /dev/null
+@@ -1,64 +0,0 @@
+-package volumetypes
 -
--// Delete makes a DELETE request against a server using the provided HTTP client.
--// The url must be a fully-formed URL string.
--// DEPRECATED.  Use Request() instead.
--func Delete(url string, opts Options) error {
--	r, err := Request("DELETE", url, opts)
--	if opts.Response != nil {
--		*opts.Response = r
--	}
--	return err
--}
+-import (
+-	"testing"
 -
--// Put makes a PUT request against a server using the provided HTTP client.
--// The url must be a fully-formed URL string.
--// DEPRECATED.  Use Request() instead.
--func Put(url string, opts Options) error {
--	r, err := Request("PUT", url, opts)
--	if opts.Response != nil {
--		*opts.Response = r
--	}
--	return err
--}
+-	os "github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--// Options describes a set of optional parameters to the various request calls.
--//
--// The custom client can be used for a variety of purposes beyond selecting encrypted versus unencrypted channels.
--// Transports can be defined to provide augmented logging, header manipulation, et. al.
--//
--// If the ReqBody field is provided, it will be embedded as a JSON object.
--// Otherwise, provide nil.
--//
--// If JSON output is to be expected from the response,
--// provide either a pointer to the container structure in Results,
--// or a pointer to a nil-initialized pointer variable.
--// The latter method will cause the unmarshaller to allocate the container type for you.
--// If no response is expected, provide a nil Results value.
--//
--// The MoreHeaders map, if non-nil or empty, provides a set of headers to add to those
--// already present in the request.  At present, only Accepted and Content-Type are set
--// by default.
--//
--// OkCodes provides a set of acceptable, positive responses.
--//
--// If provided, StatusCode specifies a pointer to an integer, which will receive the
--// returned HTTP status code, successful or not.  DEPRECATED; use the Response.StatusCode field instead for new software.
--//
--// ResponseJson, if specified, provides a means for returning the raw JSON.  This is
--// most useful for diagnostics.  DEPRECATED; use the Response.JsonResult field instead for new software.
--//
--// DumpReqJson, if set to true, will cause the request to appear to stdout for debugging purposes.
--// This attribute may be removed at any time in the future; DO NOT use this attribute in production software.
--//
--// Response, if set, provides a way to communicate the complete set of HTTP response, raw JSON, status code, and
--// other useful attributes back to the caller.  Note that the Request() method returns a Response structure as part
--// of its public interface; you don't need to set the Response field here to use this structure.  The Response field
--// exists primarily for legacy or deprecated functions.
--//
--// SetHeaders allows the caller to provide code to set any custom headers programmatically.  Typically, this
--// facility can invoke, e.g., SetBasicAuth() on the request to easily set up authentication.
--// Any error generated will terminate the request and will propegate back to the caller.
--type Options struct {
--	CustomClient  *http.Client
--	ReqBody       interface{}
--	Results       interface{}
--	MoreHeaders   map[string]string
--	OkCodes       []int
--	StatusCode    *int    `DEPRECATED`
--	DumpReqJson   bool    `UNSUPPORTED`
--	ResponseJson  *[]byte `DEPRECATED`
--	Response      **Response
--	ContentType   string `json:"Content-Type,omitempty"`
--	ContentLength int64  `json:"Content-Length,omitempty"`
--	Accept        string `json:"Accept,omitempty"`
--	SetHeaders    func(r *http.Request) error
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	os.MockListResponse(t)
+-
+-	count := 0
+-
+-	err := List(fake.ServiceClient()).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractVolumeTypes(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract volume types: %v", err)
+-			return false, err
+-		}
+-
+-		expected := []VolumeType{
+-			VolumeType{
+-				ID:   "289da7f8-6440-407c-9fb4-7db01ec49164",
+-				Name: "vol-type-001",
+-				ExtraSpecs: map[string]interface{}{
+-					"capabilities": "gpu",
+-				},
+-			},
+-			VolumeType{
+-				ID:         "96c3bda7-c82a-4f50-be73-ca7621794835",
+-				Name:       "vol-type-002",
+-				ExtraSpecs: map[string]interface{}{},
+-			},
+-		}
+-
+-		th.CheckDeepEquals(t, expected, actual)
+-
+-		return true, nil
+-	})
+-
+-	th.AssertEquals(t, 1, count)
+-	th.AssertNoErr(t, err)
 -}
 -
--// Response contains return values from the various request calls.
--//
--// HttpResponse will return the http response from the request call.
--// Note: HttpResponse.Body is always closed and will not be available from this return value.
--//
--// StatusCode specifies the returned HTTP status code, successful or not.
--//
--// If Results is specified in the Options:
--// - JsonResult will contain the raw return from the request call
--//   This is most useful for diagnostics.
--// - Result will contain the unmarshalled json either in the Result passed in
--//   or the unmarshaller will allocate the container type for you.
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--type Response struct {
--	HttpResponse http.Response
--	JsonResult   []byte
--	Results      interface{}
--	StatusCode   int
+-	os.MockGetResponse(t)
+-
+-	vt, err := Get(fake.ServiceClient(), "d32019d3-bc6e-4319-9c1d-6722fc136a22").Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.AssertDeepEquals(t, vt.ExtraSpecs, map[string]interface{}{"serverNumber": "2"})
+-	th.AssertEquals(t, vt.Name, "vol-type-001")
+-	th.AssertEquals(t, vt.ID, "d32019d3-bc6e-4319-9c1d-6722fc136a22")
 -}
-diff --git a/Godeps/_workspace/src/github.com/racker/perigee/api_test.go b/Godeps/_workspace/src/github.com/racker/perigee/api_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumetypes/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumetypes/doc.go
 deleted file mode 100644
-index da943b2..0000000
---- a/Godeps/_workspace/src/github.com/racker/perigee/api_test.go
+index 70122b7..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumetypes/doc.go
 +++ /dev/null
-@@ -1,226 +0,0 @@
--package perigee
+@@ -1,3 +0,0 @@
+-// Package volumetypes provides information and interaction with the volume type
+-// API resource for the Rackspace Block Storage service.
+-package volumetypes
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumetypes/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumetypes/results.go
+deleted file mode 100644
+index 39c8d6f..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/blockstorage/v1/volumetypes/results.go
++++ /dev/null
+@@ -1,37 +0,0 @@
+-package volumetypes
 -
 -import (
--	"bytes"
--	"fmt"
--	"net/http"
--	"net/http/httptest"
--	"strings"
--	"testing"
+-	"github.com/mitchellh/mapstructure"
+-	os "github.com/rackspace/gophercloud/openstack/blockstorage/v1/volumetypes"
+-	"github.com/rackspace/gophercloud/pagination"
 -)
 -
--func TestNormal(t *testing.T) {
--	handler := http.HandlerFunc(
--		func(w http.ResponseWriter, r *http.Request) {
--			w.Write([]byte("testing"))
--		})
--	ts := httptest.NewServer(handler)
--	defer ts.Close()
+-type VolumeType os.VolumeType
 -
--	response, err := Request("GET", ts.URL, Options{})
--	if err != nil {
--		t.Fatalf("should not have error: %s", err)
--	}
--	if response.StatusCode != 200 {
--		t.Fatalf("response code %d is not 200", response.StatusCode)
--	}
+-type GetResult struct {
+-	os.GetResult
 -}
 -
--func TestOKCodes(t *testing.T) {
--	expectCode := 201
--	handler := http.HandlerFunc(
--		func(w http.ResponseWriter, r *http.Request) {
--			w.WriteHeader(expectCode)
--			w.Write([]byte("testing"))
--		})
--	ts := httptest.NewServer(handler)
--	defer ts.Close()
--
--	options := Options{
--		OkCodes: []int{expectCode},
+-// Extract will get the Volume Type struct out of the response.
+-func (r GetResult) Extract() (*VolumeType, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
 -	}
--	results, err := Request("GET", ts.URL, options)
--	if err != nil {
--		t.Fatalf("should not have error: %s", err)
+-
+-	var res struct {
+-		VolumeType *VolumeType `json:"volume_type" mapstructure:"volume_type"`
 -	}
--	if results.StatusCode != expectCode {
--		t.Fatalf("response code %d is not %d", results.StatusCode, expectCode)
+-
+-	err := mapstructure.Decode(r.Body, &res)
+-
+-	return res.VolumeType, err
+-}
+-
+-func ExtractVolumeTypes(page pagination.Page) ([]VolumeType, error) {
+-	var response struct {
+-		VolumeTypes []VolumeType `mapstructure:"volume_types"`
 -	}
+-
+-	err := mapstructure.Decode(page.(os.ListResult).Body, &response)
+-	return response.VolumeTypes, err
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/client.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/client.go
+deleted file mode 100644
+index 5f739a8..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/client.go
++++ /dev/null
+@@ -1,156 +0,0 @@
+-package rackspace
 -
--func TestLocation(t *testing.T) {
--	newLocation := "http://www.example.com"
--	handler := http.HandlerFunc(
--		func(w http.ResponseWriter, r *http.Request) {
--			w.Header().Set("Location", newLocation)
--			w.Write([]byte("testing"))
--		})
--	ts := httptest.NewServer(handler)
--	defer ts.Close()
+-import (
+-	"fmt"
+-
+-	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack"
+-	"github.com/rackspace/gophercloud/openstack/utils"
+-	tokens2 "github.com/rackspace/gophercloud/rackspace/identity/v2/tokens"
+-)
 -
--	response, err := Request("GET", ts.URL, Options{})
--	if err != nil {
--		t.Fatalf("should not have error: %s", err)
+-const (
+-	// RackspaceUSIdentity is an identity endpoint located in the United States.
+-	RackspaceUSIdentity = "https://identity.api.rackspacecloud.com/v2.0/"
+-
+-	// RackspaceUKIdentity is an identity endpoint located in the UK.
+-	RackspaceUKIdentity = "https://lon.identity.api.rackspacecloud.com/v2.0/"
+-)
+-
+-const (
+-	v20 = "v2.0"
+-)
+-
+-// NewClient creates a client that's prepared to communicate with the Rackspace API, but is not
+-// yet authenticated. Most users will probably prefer using the AuthenticatedClient function
+-// instead.
+-//
+-// Provide the base URL of the identity endpoint you wish to authenticate against as "endpoint".
+-// Often, this will be either RackspaceUSIdentity or RackspaceUKIdentity.
+-func NewClient(endpoint string) (*gophercloud.ProviderClient, error) {
+-	if endpoint == "" {
+-		return os.NewClient(RackspaceUSIdentity)
 -	}
+-	return os.NewClient(endpoint)
+-}
 -
--	location, err := response.HttpResponse.Location()
+-// AuthenticatedClient logs in to Rackspace with the provided credentials and constructs a
+-// ProviderClient that's ready to operate.
+-//
+-// If the provided AuthOptions does not specify an explicit IdentityEndpoint, it will default to
+-// the canonical, production Rackspace US identity endpoint.
+-func AuthenticatedClient(options gophercloud.AuthOptions) (*gophercloud.ProviderClient, error) {
+-	client, err := NewClient(options.IdentityEndpoint)
 -	if err != nil {
--		t.Fatalf("should not have error: %s", err)
+-		return nil, err
 -	}
 -
--	if location.String() != newLocation {
--		t.Fatalf("location returned \"%s\" is not \"%s\"", location.String(), newLocation)
+-	err = Authenticate(client, options)
+-	if err != nil {
+-		return nil, err
 -	}
+-	return client, nil
 -}
 -
--func TestHeaders(t *testing.T) {
--	newLocation := "http://www.example.com"
--	handler := http.HandlerFunc(
--		func(w http.ResponseWriter, r *http.Request) {
--			w.Header().Set("Location", newLocation)
--			w.Write([]byte("testing"))
--		})
--	ts := httptest.NewServer(handler)
--	defer ts.Close()
+-// Authenticate or re-authenticate against the most recent identity service supported at the
+-// provided endpoint.
+-func Authenticate(client *gophercloud.ProviderClient, options gophercloud.AuthOptions) error {
+-	versions := []*utils.Version{
+-		&utils.Version{ID: v20, Priority: 20, Suffix: "/v2.0/"},
+-	}
 -
--	response, err := Request("GET", ts.URL, Options{})
+-	chosen, endpoint, err := utils.ChooseVersion(client.IdentityBase, client.IdentityEndpoint, versions)
 -	if err != nil {
--		t.Fatalf("should not have error: %s", err)
+-		return err
 -	}
 -
--	location := response.HttpResponse.Header.Get("Location")
--	if location == "" {
--		t.Fatalf("Location should not empty")
+-	switch chosen.ID {
+-	case v20:
+-		return v2auth(client, endpoint, options)
+-	default:
+-		// The switch statement must be out of date from the versions list.
+-		return fmt.Errorf("Unrecognized identity version: %s", chosen.ID)
 -	}
+-}
 -
--	if location != newLocation {
--		t.Fatalf("location returned \"%s\" is not \"%s\"", location, newLocation)
--	}
+-// AuthenticateV2 explicitly authenticates with v2 of the identity service.
+-func AuthenticateV2(client *gophercloud.ProviderClient, options gophercloud.AuthOptions) error {
+-	return v2auth(client, "", options)
 -}
 -
--func TestCustomHeaders(t *testing.T) {
--	var contentType, accept, contentLength string
+-func v2auth(client *gophercloud.ProviderClient, endpoint string, options gophercloud.AuthOptions) error {
+-	v2Client := NewIdentityV2(client)
+-	if endpoint != "" {
+-		v2Client.Endpoint = endpoint
+-	}
 -
--	handler := http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
--		m := map[string][]string(r.Header)
--		contentType = m["Content-Type"][0]
--		accept = m["Accept"][0]
--		contentLength = m["Content-Length"][0]
--	})
--	ts := httptest.NewServer(handler)
--	defer ts.Close()
+-	result := tokens2.Create(v2Client, tokens2.WrapOptions(options))
 -
--	_, err := Request("GET", ts.URL, Options{
--		ContentLength: 5,
--		ContentType:   "x-application/vb",
--		Accept:        "x-application/c",
--		ReqBody:       strings.NewReader("Hello"),
--	})
+-	token, err := result.ExtractToken()
 -	if err != nil {
--		t.Fatalf(err.Error())
+-		return err
 -	}
 -
--	if contentType != "x-application/vb" {
--		t.Fatalf("I expected x-application/vb; got ", contentType)
+-	catalog, err := result.ExtractServiceCatalog()
+-	if err != nil {
+-		return err
 -	}
 -
--	if contentLength != "5" {
--		t.Fatalf("I expected 5 byte content length; got ", contentLength)
+-	client.TokenID = token.ID
+-	client.EndpointLocator = func(opts gophercloud.EndpointOpts) (string, error) {
+-		return os.V2EndpointURL(catalog, opts)
 -	}
 -
--	if accept != "x-application/c" {
--		t.Fatalf("I expected x-application/c; got ", accept)
--	}
+-	return nil
 -}
 -
--func TestJson(t *testing.T) {
--	newLocation := "http://www.example.com"
--	jsonBytes := []byte(`{"foo": {"bar": "baz"}}`)
--	handler := http.HandlerFunc(
--		func(w http.ResponseWriter, r *http.Request) {
--			w.Header().Set("Location", newLocation)
--			w.Write(jsonBytes)
--		})
--	ts := httptest.NewServer(handler)
--	defer ts.Close()
+-// NewIdentityV2 creates a ServiceClient that may be used to access the v2 identity service.
+-func NewIdentityV2(client *gophercloud.ProviderClient) *gophercloud.ServiceClient {
+-	v2Endpoint := client.IdentityBase + "v2.0/"
 -
--	type Data struct {
--		Foo struct {
--			Bar string `json:"bar"`
--		} `json:"foo"`
+-	return &gophercloud.ServiceClient{
+-		ProviderClient: client,
+-		Endpoint:       v2Endpoint,
 -	}
--	var data Data
+-}
 -
--	response, err := Request("GET", ts.URL, Options{Results: &data})
+-// NewComputeV2 creates a ServiceClient that may be used to access the v2 compute service.
+-func NewComputeV2(client *gophercloud.ProviderClient, eo gophercloud.EndpointOpts) (*gophercloud.ServiceClient, error) {
+-	eo.ApplyDefaults("compute")
+-	url, err := client.EndpointLocator(eo)
 -	if err != nil {
--		t.Fatalf("should not have error: %s", err)
+-		return nil, err
 -	}
 -
--	if bytes.Compare(jsonBytes, response.JsonResult) != 0 {
--		t.Fatalf("json returned \"%s\" is not \"%s\"", response.JsonResult, jsonBytes)
--	}
+-	return &gophercloud.ServiceClient{
+-		ProviderClient: client,
+-		Endpoint:       url,
+-	}, nil
+-}
 -
--	if data.Foo.Bar != "baz" {
--		t.Fatalf("Results returned %v", data)
+-// NewObjectCDNV1 creates a ServiceClient that may be used with the Rackspace v1 CDN.
+-func NewObjectCDNV1(client *gophercloud.ProviderClient, eo gophercloud.EndpointOpts) (*gophercloud.ServiceClient, error) {
+-	eo.ApplyDefaults("rax:object-cdn")
+-	url, err := client.EndpointLocator(eo)
+-	if err != nil {
+-		return nil, err
 -	}
+-	return &gophercloud.ServiceClient{ProviderClient: client, Endpoint: url}, nil
 -}
 -
--func TestSetHeaders(t *testing.T) {
--	var wasCalled bool
--	handler := http.HandlerFunc(
--		func(w http.ResponseWriter, r *http.Request) {
--			w.Write([]byte("Hi"))
--		})
--	ts := httptest.NewServer(handler)
--	defer ts.Close()
--
--	_, err := Request("GET", ts.URL, Options{
--		SetHeaders: func(r *http.Request) error {
--			wasCalled = true
--			return nil
--		},
--	})
+-// NewObjectStorageV1 creates a ServiceClient that may be used with the Rackspace v1 object storage package.
+-func NewObjectStorageV1(client *gophercloud.ProviderClient, eo gophercloud.EndpointOpts) (*gophercloud.ServiceClient, error) {
+-	return os.NewObjectStorageV1(client, eo)
+-}
 -
+-// NewBlockStorageV1 creates a ServiceClient that can be used to access the
+-// Rackspace Cloud Block Storage v1 API.
+-func NewBlockStorageV1(client *gophercloud.ProviderClient, eo gophercloud.EndpointOpts) (*gophercloud.ServiceClient, error) {
+-	eo.ApplyDefaults("volume")
+-	url, err := client.EndpointLocator(eo)
 -	if err != nil {
--		t.Fatal(err)
--	}
--
--	if !wasCalled {
--		t.Fatal("I expected header setter callback to be called, but it wasn't")
+-		return nil, err
 -	}
 -
--	myError := fmt.Errorf("boo")
--
--	_, err = Request("GET", ts.URL, Options{
--		SetHeaders: func(r *http.Request) error {
--			return myError
--		},
--	})
--
--	if err != myError {
--		t.Fatal("I expected errors to propegate back to the caller.")
--	}
+-	return &gophercloud.ServiceClient{ProviderClient: client, Endpoint: url}, nil
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/client_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/client_test.go
+deleted file mode 100644
+index 73b1c88..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/client_test.go
++++ /dev/null
+@@ -1,38 +0,0 @@
+-package rackspace
 -
--func TestBodilessMethodsAreSentWithoutContentHeaders(t *testing.T) {
--	var h map[string][]string
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--	handler := http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
--		h = r.Header
--	})
--	ts := httptest.NewServer(handler)
--	defer ts.Close()
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--	_, err := Request("GET", ts.URL, Options{})
--	if err != nil {
--		t.Fatalf(err.Error())
--	}
+-func TestAuthenticatedClientV2(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	if len(h["Content-Type"]) != 0 {
--		t.Fatalf("I expected nothing for Content-Type but got ", h["Content-Type"])
--	}
+-	th.Mux.HandleFunc("/v2.0/tokens", func(w http.ResponseWriter, r *http.Request) {
+-		fmt.Fprintf(w, `
+-      {
+-        "access": {
+-          "token": {
+-            "id": "01234567890",
+-            "expires": "2014-10-01T10:00:00.000000Z"
+-          },
+-          "serviceCatalog": []
+-        }
+-      }
+-    `)
+-	})
 -
--	if len(h["Content-Length"]) != 0 {
--		t.Fatalf("I expected nothing for Content-Length but got ", h["Content-Length"])
+-	options := gophercloud.AuthOptions{
+-		Username:         "me",
+-		APIKey:           "09876543210",
+-		IdentityEndpoint: th.Endpoint() + "v2.0/",
 -	}
+-	client, err := AuthenticatedClient(options)
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, "01234567890", client.TokenID)
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/.editorconfig b/Godeps/_workspace/src/github.com/rackspace/gophercloud/.editorconfig
-deleted file mode 100644
-index 2655ebc..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/.editorconfig
-+++ /dev/null
-@@ -1,16 +0,0 @@
--# EditorConfig is awesome: http://EditorConfig.org
--
--# top-most EditorConfig file
--root = true
--
--# All files
--[*]
--end_of_line = lf
--insert_final_newline = true
--charset = utf-8
--trim_trailing_whitespace = true
--
--# Golang
--[*.go]
--indent_style = tab
--indent_size = 2
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/.travis.yml b/Godeps/_workspace/src/github.com/rackspace/gophercloud/.travis.yml
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/bootfromvolume/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/bootfromvolume/delegate.go
 deleted file mode 100644
-index 6e1dbd0..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/.travis.yml
+index 2580459..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/bootfromvolume/delegate.go
 +++ /dev/null
-@@ -1,14 +0,0 @@
--language: go
--install:
--  - go get -v .
--go:
--  - 1.1
--  - 1.2
--  - tip
--after_success:
--  - go get code.google.com/p/go.tools/cmd/cover
--  - go get github.com/axw/gocov/gocov
--  - go get github.com/mattn/goveralls
--  - export PATH=$PATH:$HOME/gopath/bin/
--  - goveralls 2k7PTU3xa474Hymwgdj6XjqenNfGTNkO8
+@@ -1,12 +0,0 @@
+-package bootfromvolume
 -
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/CONTRIBUTORS.md b/Godeps/_workspace/src/github.com/rackspace/gophercloud/CONTRIBUTORS.md
-deleted file mode 100644
-index 9076695..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/CONTRIBUTORS.md
-+++ /dev/null
-@@ -1,6 +0,0 @@
--Contributors
--============
+-import (
+-	"github.com/rackspace/gophercloud"
+-	osBFV "github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume"
+-	osServers "github.com/rackspace/gophercloud/openstack/compute/v2/servers"
+-)
 -
--Samuel A. Falvo II <sam.falvo at rackspace.com>
--Glen Campbell <glen.campbell at rackspace.com>
--Jesse Noller <jesse.noller at rackspace.com>
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/LICENSE b/Godeps/_workspace/src/github.com/rackspace/gophercloud/LICENSE
+-// Create requests the creation of a server from the given block device mapping.
+-func Create(client *gophercloud.ServiceClient, opts osServers.CreateOptsBuilder) osServers.CreateResult {
+-	return osBFV.Create(client, opts)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/bootfromvolume/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/bootfromvolume/delegate_test.go
 deleted file mode 100644
-index fbbbc9e..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/LICENSE
+index 0b53527..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/bootfromvolume/delegate_test.go
 +++ /dev/null
-@@ -1,191 +0,0 @@
--Copyright 2012-2013 Rackspace, Inc.
+@@ -1,52 +0,0 @@
+-package bootfromvolume
 -
--Licensed under the Apache License, Version 2.0 (the "License"); you may not use
--this file except in compliance with the License.  You may obtain a copy of the
--License at
+-import (
+-	"testing"
 -
--  http://www.apache.org/licenses/LICENSE-2.0
+-	osBFV "github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume"
+-	"github.com/rackspace/gophercloud/openstack/compute/v2/servers"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--Unless required by applicable law or agreed to in writing, software distributed
--under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
--CONDITIONS OF ANY KIND, either express or implied.  See the License for the
--specific language governing permissions and limitations under the License.                                
+-func TestCreateOpts(t *testing.T) {
+-	base := servers.CreateOpts{
+-		Name:      "createdserver",
+-		ImageRef:  "asdfasdfasdf",
+-		FlavorRef: "performance1-1",
+-	}
+-
+-	ext := osBFV.CreateOptsExt{
+-		CreateOptsBuilder: base,
+-		BlockDevice: []osBFV.BlockDevice{
+-			osBFV.BlockDevice{
+-				UUID:            "123456",
+-				SourceType:      osBFV.Image,
+-				DestinationType: "volume",
+-				VolumeSize:      10,
+-			},
+-		},
+-	}
 -
--------
-- 
--				Apache License
--                           Version 2.0, January 2004
--                        http://www.apache.org/licenses/
+-	expected := `
+-    {
+-      "server": {
+-        "name": "createdserver",
+-        "imageRef": "asdfasdfasdf",
+-        "flavorRef": "performance1-1",
+-        "block_device_mapping_v2":[
+-          {
+-            "uuid":"123456",
+-            "source_type":"image",
+-            "destination_type":"volume",
+-            "boot_index": "0",
+-            "delete_on_termination": "false",
+-            "volume_size": "10"
+-          }
+-        ]
+-      }
+-    }
+-  `
+-	actual, err := ext.ToServerCreateMap()
+-	th.AssertNoErr(t, err)
+-	th.CheckJSONEquals(t, expected, actual)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/flavors/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/flavors/delegate.go
+deleted file mode 100644
+index 6bfc20c..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/flavors/delegate.go
++++ /dev/null
+@@ -1,46 +0,0 @@
+-package flavors
 -
--   TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+-import (
+-	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack/compute/v2/flavors"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--   1. Definitions.
+-// ListOpts helps control the results returned by the List() function. For example, a flavor with a
+-// minDisk field of 10 will not be returned if you specify MinDisk set to 20.
+-type ListOpts struct {
 -
--      "License" shall mean the terms and conditions for use, reproduction,
--      and distribution as defined by Sections 1 through 9 of this document.
+-	// MinDisk and MinRAM, if provided, elide flavors that do not meet your criteria.
+-	MinDisk int `q:"minDisk"`
+-	MinRAM  int `q:"minRam"`
 -
--      "Licensor" shall mean the copyright owner or entity authorized by
--      the copyright owner that is granting the License.
+-	// Marker specifies the ID of the last flavor in the previous page.
+-	Marker string `q:"marker"`
 -
--      "Legal Entity" shall mean the union of the acting entity and all
--      other entities that control, are controlled by, or are under common
--      control with that entity. For the purposes of this definition,
--      "control" means (i) the power, direct or indirect, to cause the
--      direction or management of such entity, whether by contract or
--      otherwise, or (ii) ownership of fifty percent (50%) or more of the
--      outstanding shares, or (iii) beneficial ownership of such entity.
+-	// Limit instructs List to refrain from sending excessively large lists of flavors.
+-	Limit int `q:"limit"`
+-}
 -
--      "You" (or "Your") shall mean an individual or Legal Entity
--      exercising permissions granted by this License.
+-// ToFlavorListQuery formats a ListOpts into a query string.
+-func (opts ListOpts) ToFlavorListQuery() (string, error) {
+-	q, err := gophercloud.BuildQueryString(opts)
+-	if err != nil {
+-		return "", err
+-	}
+-	return q.String(), nil
+-}
 -
--      "Source" form shall mean the preferred form for making modifications,
--      including but not limited to software source code, documentation
--      source, and configuration files.
+-// ListDetail enumerates the server images available to your account.
+-func ListDetail(client *gophercloud.ServiceClient, opts os.ListOptsBuilder) pagination.Pager {
+-	return os.ListDetail(client, opts)
+-}
 -
--      "Object" form shall mean any form resulting from mechanical
--      transformation or translation of a Source form, including but
--      not limited to compiled object code, generated documentation,
--      and conversions to other media types.
+-// Get returns details about a single flavor, identity by ID.
+-func Get(client *gophercloud.ServiceClient, id string) os.GetResult {
+-	return os.Get(client, id)
+-}
 -
--      "Work" shall mean the work of authorship, whether in Source or
--      Object form, made available under the License, as indicated by a
--      copyright notice that is included in or attached to the work
--      (an example is provided in the Appendix below).
+-// ExtractFlavors interprets a page of List results as Flavors.
+-func ExtractFlavors(page pagination.Page) ([]os.Flavor, error) {
+-	return os.ExtractFlavors(page)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/flavors/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/flavors/delegate_test.go
+deleted file mode 100644
+index 204081d..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/flavors/delegate_test.go
++++ /dev/null
+@@ -1,62 +0,0 @@
+-package flavors
 -
--      "Derivative Works" shall mean any work, whether in Source or Object
--      form, that is based on (or derived from) the Work and for which the
--      editorial revisions, annotations, elaborations, or other modifications
--      represent, as a whole, an original work of authorship. For the purposes
--      of this License, Derivative Works shall not include works that remain
--      separable from, or merely link (or bind by name) to the interfaces of,
--      the Work and Derivative Works thereof.
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--      "Contribution" shall mean any work of authorship, including
--      the original version of the Work and any modifications or additions
--      to that Work or Derivative Works thereof, that is intentionally
--      submitted to Licensor for inclusion in the Work by the copyright owner
--      or by an individual or Legal Entity authorized to submit on behalf of
--      the copyright owner. For the purposes of this definition, "submitted"
--      means any form of electronic, verbal, or written communication sent
--      to the Licensor or its representatives, including but not limited to
--      communication on electronic mailing lists, source code control systems,
--      and issue tracking systems that are managed by, or on behalf of, the
--      Licensor for the purpose of discussing and improving the Work, but
--      excluding communication that is conspicuously marked or otherwise
--      designated in writing by the copyright owner as "Not a Contribution."
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--      "Contributor" shall mean Licensor and any individual or Legal Entity
--      on behalf of whom a Contribution has been received by Licensor and
--      subsequently incorporated within the Work.
+-func TestListFlavors(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/flavors/detail", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		r.ParseForm()
+-		marker := r.Form.Get("marker")
+-		switch marker {
+-		case "":
+-			fmt.Fprintf(w, ListOutput)
+-		case "performance1-2":
+-			fmt.Fprintf(w, `{ "flavors": [] }`)
+-		default:
+-			t.Fatalf("Unexpected marker: [%s]", marker)
+-		}
+-	})
 -
--   2. Grant of Copyright License. Subject to the terms and conditions of
--      this License, each Contributor hereby grants to You a perpetual,
--      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
--      copyright license to reproduce, prepare Derivative Works of,
--      publicly display, publicly perform, sublicense, and distribute the
--      Work and such Derivative Works in Source or Object form.
+-	count := 0
+-	err := ListDetail(client.ServiceClient(), nil).EachPage(func(page pagination.Page) (bool, error) {
+-		actual, err := ExtractFlavors(page)
+-		th.AssertNoErr(t, err)
+-		th.CheckDeepEquals(t, ExpectedFlavorSlice, actual)
 -
--   3. Grant of Patent License. Subject to the terms and conditions of
--      this License, each Contributor hereby grants to You a perpetual,
--      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
--      (except as stated in this section) patent license to make, have made,
--      use, offer to sell, sell, import, and otherwise transfer the Work,
--      where such license applies only to those patent claims licensable
--      by such Contributor that are necessarily infringed by their
--      Contribution(s) alone or by combination of their Contribution(s)
--      with the Work to which such Contribution(s) was submitted. If You
--      institute patent litigation against any entity (including a
--      cross-claim or counterclaim in a lawsuit) alleging that the Work
--      or a Contribution incorporated within the Work constitutes direct
--      or contributory patent infringement, then any patent licenses
--      granted to You under this License for that Work shall terminate
--      as of the date such litigation is filed.
+-		count++
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, 1, count)
+-}
 -
--   4. Redistribution. You may reproduce and distribute copies of the
--      Work or Derivative Works thereof in any medium, with or without
--      modifications, and in Source or Object form, provided that You
--      meet the following conditions:
+-func TestGetFlavor(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--      (a) You must give any other recipients of the Work or
--          Derivative Works a copy of this License; and
+-	th.Mux.HandleFunc("/flavors/performance1-1", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
 -
--      (b) You must cause any modified files to carry prominent notices
--          stating that You changed the files; and
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, GetOutput)
+-	})
 -
--      (c) You must retain, in the Source form of any Derivative Works
--          that You distribute, all copyright, patent, trademark, and
--          attribution notices from the Source form of the Work,
--          excluding those notices that do not pertain to any part of
--          the Derivative Works; and
+-	actual, err := Get(client.ServiceClient(), "performance1-1").Extract()
+-	th.AssertNoErr(t, err)
+-	th.CheckDeepEquals(t, &Performance1Flavor, actual)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/flavors/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/flavors/doc.go
+deleted file mode 100644
+index 278229a..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/flavors/doc.go
++++ /dev/null
+@@ -1,3 +0,0 @@
+-// Package flavors provides information and interaction with the flavor
+-// API resource for the Rackspace Cloud Servers service.
+-package flavors
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/flavors/fixtures.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/flavors/fixtures.go
+deleted file mode 100644
+index b6dca93..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/flavors/fixtures.go
++++ /dev/null
+@@ -1,128 +0,0 @@
+-// +build fixtures
+-package flavors
 -
--      (d) If the Work includes a "NOTICE" text file as part of its
--          distribution, then any Derivative Works that You distribute must
--          include a readable copy of the attribution notices contained
--          within such NOTICE file, excluding those notices that do not
--          pertain to any part of the Derivative Works, in at least one
--          of the following places: within a NOTICE text file distributed
--          as part of the Derivative Works; within the Source form or
--          documentation, if provided along with the Derivative Works; or,
--          within a display generated by the Derivative Works, if and
--          wherever such third-party notices normally appear. The contents
--          of the NOTICE file are for informational purposes only and
--          do not modify the License. You may add Your own attribution
--          notices within Derivative Works that You distribute, alongside
--          or as an addendum to the NOTICE text from the Work, provided
--          that such additional attribution notices cannot be construed
--          as modifying the License.
+-import (
+-	os "github.com/rackspace/gophercloud/openstack/compute/v2/flavors"
+-)
 -
--      You may add Your own copyright statement to Your modifications and
--      may provide additional or different license terms and conditions
--      for use, reproduction, or distribution of Your modifications, or
--      for any such Derivative Works as a whole, provided Your use,
--      reproduction, and distribution of the Work otherwise complies with
--      the conditions stated in this License.
+-// ListOutput is a sample response of a flavor List request.
+-const ListOutput = `
+-{
+-  "flavors": [
+-    {
+-      "OS-FLV-EXT-DATA:ephemeral": 0,
+-      "OS-FLV-WITH-EXT-SPECS:extra_specs": {
+-        "class": "performance1",
+-        "disk_io_index": "40",
+-        "number_of_data_disks": "0",
+-        "policy_class": "performance_flavor",
+-        "resize_policy_class": "performance_flavor"
+-      },
+-      "disk": 20,
+-      "id": "performance1-1",
+-      "links": [
+-        {
+-          "href": "https://iad.servers.api.rackspacecloud.com/v2/864477/flavors/performance1-1",
+-          "rel": "self"
+-        },
+-        {
+-          "href": "https://iad.servers.api.rackspacecloud.com/864477/flavors/performance1-1",
+-          "rel": "bookmark"
+-        }
+-      ],
+-      "name": "1 GB Performance",
+-      "ram": 1024,
+-      "rxtx_factor": 200,
+-      "swap": "",
+-      "vcpus": 1
+-    },
+-    {
+-      "OS-FLV-EXT-DATA:ephemeral": 20,
+-      "OS-FLV-WITH-EXT-SPECS:extra_specs": {
+-        "class": "performance1",
+-        "disk_io_index": "40",
+-        "number_of_data_disks": "1",
+-        "policy_class": "performance_flavor",
+-        "resize_policy_class": "performance_flavor"
+-      },
+-      "disk": 40,
+-      "id": "performance1-2",
+-      "links": [
+-        {
+-          "href": "https://iad.servers.api.rackspacecloud.com/v2/864477/flavors/performance1-2",
+-          "rel": "self"
+-        },
+-        {
+-          "href": "https://iad.servers.api.rackspacecloud.com/864477/flavors/performance1-2",
+-          "rel": "bookmark"
+-        }
+-      ],
+-      "name": "2 GB Performance",
+-      "ram": 2048,
+-      "rxtx_factor": 400,
+-      "swap": "",
+-      "vcpus": 2
+-    }
+-  ]
+-}`
 -
--   5. Submission of Contributions. Unless You explicitly state otherwise,
--      any Contribution intentionally submitted for inclusion in the Work
--      by You to the Licensor shall be under the terms and conditions of
--      this License, without any additional terms or conditions.
--      Notwithstanding the above, nothing herein shall supersede or modify
--      the terms of any separate license agreement you may have executed
--      with Licensor regarding such Contributions.
+-// GetOutput is a sample response from a flavor Get request. Its contents correspond to the
+-// Performance1Flavor struct.
+-const GetOutput = `
+-{
+-  "flavor": {
+-    "OS-FLV-EXT-DATA:ephemeral": 0,
+-    "OS-FLV-WITH-EXT-SPECS:extra_specs": {
+-      "class": "performance1",
+-      "disk_io_index": "40",
+-      "number_of_data_disks": "0",
+-      "policy_class": "performance_flavor",
+-      "resize_policy_class": "performance_flavor"
+-    },
+-    "disk": 20,
+-    "id": "performance1-1",
+-    "links": [
+-      {
+-        "href": "https://iad.servers.api.rackspacecloud.com/v2/864477/flavors/performance1-1",
+-        "rel": "self"
+-      },
+-      {
+-        "href": "https://iad.servers.api.rackspacecloud.com/864477/flavors/performance1-1",
+-        "rel": "bookmark"
+-      }
+-    ],
+-    "name": "1 GB Performance",
+-    "ram": 1024,
+-    "rxtx_factor": 200,
+-    "swap": "",
+-    "vcpus": 1
+-  }
+-}
+-`
 -
--   6. Trademarks. This License does not grant permission to use the trade
--      names, trademarks, service marks, or product names of the Licensor,
--      except as required for reasonable and customary use in describing the
--      origin of the Work and reproducing the content of the NOTICE file.
+-// Performance1Flavor is the expected result of parsing GetOutput, or the first element of
+-// ListOutput.
+-var Performance1Flavor = os.Flavor{
+-	ID:         "performance1-1",
+-	Disk:       20,
+-	RAM:        1024,
+-	Name:       "1 GB Performance",
+-	RxTxFactor: 200.0,
+-	Swap:       0,
+-	VCPUs:      1,
+-}
+-
+-// Performance2Flavor is the second result expected from parsing ListOutput.
+-var Performance2Flavor = os.Flavor{
+-	ID:         "performance1-2",
+-	Disk:       40,
+-	RAM:        2048,
+-	Name:       "2 GB Performance",
+-	RxTxFactor: 400.0,
+-	Swap:       0,
+-	VCPUs:      2,
+-}
+-
+-// ExpectedFlavorSlice is the slice of Flavor structs that are expected to be parsed from
+-// ListOutput.
+-var ExpectedFlavorSlice = []os.Flavor{Performance1Flavor, Performance2Flavor}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/images/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/images/delegate.go
+deleted file mode 100644
+index 18e1f31..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/images/delegate.go
++++ /dev/null
+@@ -1,22 +0,0 @@
+-package images
 -
--   7. Disclaimer of Warranty. Unless required by applicable law or
--      agreed to in writing, Licensor provides the Work (and each
--      Contributor provides its Contributions) on an "AS IS" BASIS,
--      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
--      implied, including, without limitation, any warranties or conditions
--      of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
--      PARTICULAR PURPOSE. You are solely responsible for determining the
--      appropriateness of using or redistributing the Work and assume any
--      risks associated with Your exercise of permissions under this License.
+-import (
+-	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack/compute/v2/images"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--   8. Limitation of Liability. In no event and under no legal theory,
--      whether in tort (including negligence), contract, or otherwise,
--      unless required by applicable law (such as deliberate and grossly
--      negligent acts) or agreed to in writing, shall any Contributor be
--      liable to You for damages, including any direct, indirect, special,
--      incidental, or consequential damages of any character arising as a
--      result of this License or out of the use or inability to use the
--      Work (including but not limited to damages for loss of goodwill,
--      work stoppage, computer failure or malfunction, or any and all
--      other commercial damages or losses), even if such Contributor
--      has been advised of the possibility of such damages.
+-// ListDetail enumerates the available server images.
+-func ListDetail(client *gophercloud.ServiceClient, opts os.ListOptsBuilder) pagination.Pager {
+-	return os.ListDetail(client, opts)
+-}
 -
--   9. Accepting Warranty or Additional Liability. While redistributing
--      the Work or Derivative Works thereof, You may choose to offer,
--      and charge a fee for, acceptance of support, warranty, indemnity,
--      or other liability obligations and/or rights consistent with this
--      License. However, in accepting such obligations, You may act only
--      on Your own behalf and on Your sole responsibility, not on behalf
--      of any other Contributor, and only if You agree to indemnify,
--      defend, and hold each Contributor harmless for any liability
--      incurred by, or claims asserted against, such Contributor by reason
--      of your accepting any such warranty or additional liability.
+-// Get acquires additional detail about a specific image by ID.
+-func Get(client *gophercloud.ServiceClient, id string) os.GetResult {
+-	return os.Get(client, id)
+-}
 -
--   END OF TERMS AND CONDITIONS
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/README.asciidoc b/Godeps/_workspace/src/github.com/rackspace/gophercloud/README.asciidoc
+-// ExtractImages interprets a page as a collection of server images.
+-func ExtractImages(page pagination.Page) ([]os.Image, error) {
+-	return os.ExtractImages(page)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/images/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/images/delegate_test.go
 deleted file mode 100644
-index b7a7c01..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/README.asciidoc
+index db0a6e3..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/images/delegate_test.go
 +++ /dev/null
-@@ -1,44 +0,0 @@
--== Gophercloud -- V0.1.0 image:https://secure.travis-ci.org/rackspace/gophercloud.png?branch=master["build status",link="https://travis-ci.org/rackspace/gophercloud"]
--
--Gophercloud currently lets you authenticate with OpenStack providers to create and manage servers.
--We are working on extending the API to further include cloud files, block storage, DNS, databases, security groups, and other features.
--
--WARNING: This library is still in the very early stages of development. Unless you want to contribute, it probably isn't what you want.  Yet.
--
--=== Outstanding Features
--
--1.  Apache 2.0 License, making Gophercloud friendly to commercial and open-source enterprises alike.
--2.  Gophercloud is one of the most actively maintained Go SDKs for OpenStack.
--3.  Gophercloud supports Identity V2 and Nova V2 APIs.  More coming soon!
--4.  The up-coming Gophercloud 0.2.0 release supports API extensions, and makes writing support for new extensions easy.
--5.  Gophercloud supports automatic reauthentication upon auth token timeout, if enabled by your software.
--6.  Gophercloud is the only SDK implementation with actual acceptance-level integration tests.
--
--=== What Does it Look Like?
+@@ -1,62 +0,0 @@
+-package images
 -
--The Gophercloud 0.1.0 and earlier APIs are now deprecated and obsolete.
--No new feature development will occur for 0.1.0 or 0.0.0.
--However, we will accept and provide bug fixes for these APIs.
--Please refer to the acceptance tests in the master brach for code examples using the v0.1.0 API.
--The most up to date documentation for version 0.1.x can be found at link:http://godoc.org/github.com/rackspace/gophercloud[our Godoc.org documentation].
+-import (
+-	"fmt"
+-	"net/http"
+-	"testing"
 -
--We are working on a new API that provides much better support for extensions, pagination, and other features that proved difficult to implement before.
--This new API will be substantially more Go-idiomatic as well; one of the complaints received about 0.1.x and earlier is that it didn't "feel" right.
--To see what this new API is going to look like, you can look at the code examples up on the link:http://gophercloud.io/docs.html[Gophercloud website].
--If you're interested in tracking progress, note that features for version 0.2.0 will appear in the `v0.2.0` branch until merged to master.
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--=== How can I Contribute?
+-func TestListImageDetails(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/images/detail", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		r.ParseForm()
+-		marker := r.Form.Get("marker")
+-		switch marker {
+-		case "":
+-			fmt.Fprintf(w, ListOutput)
+-		case "e19a734c-c7e6-443a-830c-242209c4d65d":
+-			fmt.Fprintf(w, `{ "images": [] }`)
+-		default:
+-			t.Fatalf("Unexpected marker: [%s]", marker)
+-		}
+-	})
 -
--After using Gophercloud for a while, you might find that it lacks some useful feature, or that existing behavior seems buggy.  We welcome contributions
--from our users for both missing functionality as well as for bug fixes.  We encourage contributors to collaborate with the
--link:http://gophercloud.io/community.html[Gophercloud community.]
+-	count := 0
+-	err := ListDetail(client.ServiceClient(), nil).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractImages(page)
+-		th.AssertNoErr(t, err)
+-		th.CheckDeepEquals(t, ExpectedImageSlice, actual)
 -
--Finally, Gophercloud maintains its own link:http://gophercloud.io[announcements and updates blog.]
--Feel free to check back now and again to see what's new.
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, 1, count)
+-}
 -
--== License
+-func TestGetImageDetails(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--Copyright (C) 2013, 2014 Rackspace, Inc.
+-	th.Mux.HandleFunc("/images/e19a734c-c7e6-443a-830c-242209c4d65d", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
 -
--Licensed under the Apache License, Version 2.0
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, GetOutput)
+-	})
 -
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/00-authentication.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/00-authentication.go
+-	actual, err := Get(client.ServiceClient(), "e19a734c-c7e6-443a-830c-242209c4d65d").Extract()
+-	th.AssertNoErr(t, err)
+-	th.CheckDeepEquals(t, &UbuntuImage, actual)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/images/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/images/doc.go
 deleted file mode 100644
-index 6467203..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/00-authentication.go
+index cfae806..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/images/doc.go
 +++ /dev/null
-@@ -1,30 +0,0 @@
--// +build acceptance,old
--
--package main
+@@ -1,3 +0,0 @@
+-// Package images provides information and interaction with the image
+-// API resource for the Rackspace Cloud Servers service.
+-package images
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/images/fixtures.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/images/fixtures.go
+deleted file mode 100644
+index c46d196..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/images/fixtures.go
++++ /dev/null
+@@ -1,199 +0,0 @@
+-// +build fixtures
+-package images
 -
 -import (
--	"fmt"
--	"github.com/rackspace/gophercloud"
--	"os"
--	"strings"
+-	os "github.com/rackspace/gophercloud/openstack/compute/v2/images"
 -)
 -
--func main() {
--	provider, username, _, apiKey := getCredentials()
--
--	if !strings.Contains(provider, "rackspace") {
--		fmt.Fprintf(os.Stdout, "Skipping test because provider doesn't support API_KEYs\n")
--		return
--	}
+-// ListOutput is an example response from an /images/detail request.
+-const ListOutput = `
+-{
+-	"images": [
+-		{
+-			"OS-DCF:diskConfig": "MANUAL",
+-			"OS-EXT-IMG-SIZE:size": 1.017415075e+09,
+-			"created": "2014-10-01T15:49:02Z",
+-			"id": "30aa010e-080e-4d4b-a7f9-09fc55b07d69",
+-			"links": [
+-				{
+-					"href": "https://iad.servers.api.rackspacecloud.com/v2/111222/images/30aa010e-080e-4d4b-a7f9-09fc55b07d69",
+-					"rel": "self"
+-				},
+-				{
+-					"href": "https://iad.servers.api.rackspacecloud.com/111222/images/30aa010e-080e-4d4b-a7f9-09fc55b07d69",
+-					"rel": "bookmark"
+-				},
+-				{
+-					"href": "https://iad.servers.api.rackspacecloud.com/111222/images/30aa010e-080e-4d4b-a7f9-09fc55b07d69",
+-					"rel": "alternate",
+-					"type": "application/vnd.openstack.image"
+-				}
+-			],
+-			"metadata": {
+-				"auto_disk_config": "disabled",
+-				"cache_in_nova": "True",
+-				"com.rackspace__1__build_core": "1",
+-				"com.rackspace__1__build_managed": "1",
+-				"com.rackspace__1__build_rackconnect": "1",
+-				"com.rackspace__1__options": "0",
+-				"com.rackspace__1__platform_target": "PublicCloud",
+-				"com.rackspace__1__release_build_date": "2014-10-01_15-46-08",
+-				"com.rackspace__1__release_id": "100",
+-				"com.rackspace__1__release_version": "10",
+-				"com.rackspace__1__source": "kickstart",
+-				"com.rackspace__1__visible_core": "1",
+-				"com.rackspace__1__visible_managed": "0",
+-				"com.rackspace__1__visible_rackconnect": "0",
+-				"image_type": "base",
+-				"org.openstack__1__architecture": "x64",
+-				"org.openstack__1__os_distro": "org.archlinux",
+-				"org.openstack__1__os_version": "2014.8",
+-				"os_distro": "arch",
+-				"os_type": "linux",
+-				"vm_mode": "hvm"
+-			},
+-			"minDisk": 20,
+-			"minRam": 512,
+-			"name": "Arch 2014.10 (PVHVM)",
+-			"progress": 100,
+-			"status": "ACTIVE",
+-			"updated": "2014-10-01T19:37:58Z"
+-		},
+-		{
+-			"OS-DCF:diskConfig": "AUTO",
+-			"OS-EXT-IMG-SIZE:size": 1.060306463e+09,
+-			"created": "2014-10-01T12:58:11Z",
+-			"id": "e19a734c-c7e6-443a-830c-242209c4d65d",
+-			"links": [
+-				{
+-					"href": "https://iad.servers.api.rackspacecloud.com/v2/111222/images/e19a734c-c7e6-443a-830c-242209c4d65d",
+-					"rel": "self"
+-				},
+-				{
+-					"href": "https://iad.servers.api.rackspacecloud.com/111222/images/e19a734c-c7e6-443a-830c-242209c4d65d",
+-					"rel": "bookmark"
+-				},
+-				{
+-					"href": "https://iad.servers.api.rackspacecloud.com/111222/images/e19a734c-c7e6-443a-830c-242209c4d65d",
+-					"rel": "alternate",
+-					"type": "application/vnd.openstack.image"
+-				}
+-			],
+-			"metadata": {
+-				"auto_disk_config": "True",
+-				"cache_in_nova": "True",
+-				"com.rackspace__1__build_core": "1",
+-				"com.rackspace__1__build_managed": "1",
+-				"com.rackspace__1__build_rackconnect": "1",
+-				"com.rackspace__1__options": "0",
+-				"com.rackspace__1__platform_target": "PublicCloud",
+-				"com.rackspace__1__release_build_date": "2014-10-01_12-31-03",
+-				"com.rackspace__1__release_id": "1007",
+-				"com.rackspace__1__release_version": "6",
+-				"com.rackspace__1__source": "kickstart",
+-				"com.rackspace__1__visible_core": "1",
+-				"com.rackspace__1__visible_managed": "1",
+-				"com.rackspace__1__visible_rackconnect": "1",
+-				"image_type": "base",
+-				"org.openstack__1__architecture": "x64",
+-				"org.openstack__1__os_distro": "com.ubuntu",
+-				"org.openstack__1__os_version": "14.04",
+-				"os_distro": "ubuntu",
+-				"os_type": "linux",
+-				"vm_mode": "xen"
+-			},
+-			"minDisk": 20,
+-			"minRam": 512,
+-			"name": "Ubuntu 14.04 LTS (Trusty Tahr)",
+-			"progress": 100,
+-			"status": "ACTIVE",
+-			"updated": "2014-10-01T15:51:44Z"
+-		}
+-	]
+-}
+-`
 -
--	_, err := gophercloud.Authenticate(
--		provider,
--		gophercloud.AuthOptions{
--			Username: username,
--			ApiKey:   apiKey,
+-// GetOutput is an example response from an /images request.
+-const GetOutput = `
+-{
+-	"image": {
+-		"OS-DCF:diskConfig": "AUTO",
+-		"OS-EXT-IMG-SIZE:size": 1060306463,
+-		"created": "2014-10-01T12:58:11Z",
+-		"id": "e19a734c-c7e6-443a-830c-242209c4d65d",
+-		"links": [
+-			{
+-				"href": "https://iad.servers.api.rackspacecloud.com/v2/111222/images/e19a734c-c7e6-443a-830c-242209c4d65d",
+-				"rel": "self"
+-			},
+-			{
+-				"href": "https://iad.servers.api.rackspacecloud.com/111222/images/e19a734c-c7e6-443a-830c-242209c4d65d",
+-				"rel": "bookmark"
+-			},
+-			{
+-				"href": "https://iad.servers.api.rackspacecloud.com/111222/images/e19a734c-c7e6-443a-830c-242209c4d65d",
+-				"rel": "alternate",
+-				"type": "application/vnd.openstack.image"
+-			}
+-		],
+-		"metadata": {
+-			"auto_disk_config": "True",
+-			"cache_in_nova": "True",
+-			"com.rackspace__1__build_core": "1",
+-			"com.rackspace__1__build_managed": "1",
+-			"com.rackspace__1__build_rackconnect": "1",
+-			"com.rackspace__1__options": "0",
+-			"com.rackspace__1__platform_target": "PublicCloud",
+-			"com.rackspace__1__release_build_date": "2014-10-01_12-31-03",
+-			"com.rackspace__1__release_id": "1007",
+-			"com.rackspace__1__release_version": "6",
+-			"com.rackspace__1__source": "kickstart",
+-			"com.rackspace__1__visible_core": "1",
+-			"com.rackspace__1__visible_managed": "1",
+-			"com.rackspace__1__visible_rackconnect": "1",
+-			"image_type": "base",
+-			"org.openstack__1__architecture": "x64",
+-			"org.openstack__1__os_distro": "com.ubuntu",
+-			"org.openstack__1__os_version": "14.04",
+-			"os_distro": "ubuntu",
+-			"os_type": "linux",
+-			"vm_mode": "xen"
 -		},
--	)
--	if err != nil {
--		panic(err)
+-		"minDisk": 20,
+-		"minRam": 512,
+-		"name": "Ubuntu 14.04 LTS (Trusty Tahr)",
+-		"progress": 100,
+-		"status": "ACTIVE",
+-		"updated": "2014-10-01T15:51:44Z"
 -	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/01-authentication.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/01-authentication.go
-deleted file mode 100644
-index 5cc9d38..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/01-authentication.go
-+++ /dev/null
-@@ -1,22 +0,0 @@
--// +build acceptance,old
+-`
 -
--package main
+-// ArchImage is the first Image structure that should be parsed from ListOutput.
+-var ArchImage = os.Image{
+-	ID:       "30aa010e-080e-4d4b-a7f9-09fc55b07d69",
+-	Name:     "Arch 2014.10 (PVHVM)",
+-	Created:  "2014-10-01T15:49:02Z",
+-	Updated:  "2014-10-01T19:37:58Z",
+-	MinDisk:  20,
+-	MinRAM:   512,
+-	Progress: 100,
+-	Status:   "ACTIVE",
+-}
+-
+-// UbuntuImage is the second Image structure that should be parsed from ListOutput and
+-// the only image that should be extracted from GetOutput.
+-var UbuntuImage = os.Image{
+-	ID:       "e19a734c-c7e6-443a-830c-242209c4d65d",
+-	Name:     "Ubuntu 14.04 LTS (Trusty Tahr)",
+-	Created:  "2014-10-01T12:58:11Z",
+-	Updated:  "2014-10-01T15:51:44Z",
+-	MinDisk:  20,
+-	MinRAM:   512,
+-	Progress: 100,
+-	Status:   "ACTIVE",
+-}
+-
+-// ExpectedImageSlice is the collection of images that should be parsed from ListOutput,
+-// in order.
+-var ExpectedImageSlice = []os.Image{ArchImage, UbuntuImage}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/keypairs/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/keypairs/delegate.go
+deleted file mode 100644
+index 3e53525..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/keypairs/delegate.go
++++ /dev/null
+@@ -1,33 +0,0 @@
+-package keypairs
 -
 -import (
 -	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs"
+-	"github.com/rackspace/gophercloud/pagination"
 -)
 -
--func main() {
--	provider, username, password, _ := getCredentials()
+-// List returns a Pager that allows you to iterate over a collection of KeyPairs.
+-func List(client *gophercloud.ServiceClient) pagination.Pager {
+-	return os.List(client)
+-}
 -
--	_, err := gophercloud.Authenticate(
--		provider,
--		gophercloud.AuthOptions{
--			Username: username,
--			Password: password,
--		},
--	)
--	if err != nil {
--		panic(err)
--	}
+-// Create requests the creation of a new keypair on the server, or to import a pre-existing
+-// keypair.
+-func Create(client *gophercloud.ServiceClient, opts os.CreateOptsBuilder) os.CreateResult {
+-	return os.Create(client, opts)
+-}
+-
+-// Get returns public data about a previously uploaded KeyPair.
+-func Get(client *gophercloud.ServiceClient, name string) os.GetResult {
+-	return os.Get(client, name)
+-}
+-
+-// Delete requests the deletion of a previous stored KeyPair from the server.
+-func Delete(client *gophercloud.ServiceClient, name string) os.DeleteResult {
+-	return os.Delete(client, name)
+-}
+-
+-// ExtractKeyPairs interprets a page of results as a slice of KeyPairs.
+-func ExtractKeyPairs(page pagination.Page) ([]os.KeyPair, error) {
+-	return os.ExtractKeyPairs(page)
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/02-list-servers.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/02-list-servers.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/keypairs/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/keypairs/delegate_test.go
 deleted file mode 100644
-index 772852e..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/02-list-servers.go
+index 62e5df9..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/keypairs/delegate_test.go
 +++ /dev/null
-@@ -1,62 +0,0 @@
--// +build acceptance,old
--
--package main
+@@ -1,72 +0,0 @@
+-package keypairs
 -
 -import (
--	"flag"
--	"fmt"
--	"github.com/rackspace/gophercloud"
+-	"testing"
+-
+-	os "github.com/rackspace/gophercloud/openstack/compute/v2/extensions/keypairs"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
 -)
 -
--var quiet = flag.Bool("quiet", false, "Quiet mode, for acceptance testing.  $? still indicates errors though.")
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleListSuccessfully(t)
 -
--func main() {
--	flag.Parse()
+-	count := 0
+-	err := List(client.ServiceClient()).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractKeyPairs(page)
+-		th.AssertNoErr(t, err)
+-		th.CheckDeepEquals(t, os.ExpectedKeyPairSlice, actual)
 -
--	withIdentity(false, func(acc gophercloud.AccessProvider) {
--		withServerApi(acc, func(api gophercloud.CloudServersProvider) {
--			tryFullDetails(api)
--			tryLinksOnly(api)
--		})
+-		return true, nil
 -	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, 1, count)
 -}
 -
--func tryLinksOnly(api gophercloud.CloudServersProvider) {
--	servers, err := api.ListServersLinksOnly()
--	if err != nil {
--		panic(err)
--	}
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleCreateSuccessfully(t)
 -
--	if !*quiet {
--		fmt.Println("Id,Name")
--		for _, s := range servers {
--			if s.AccessIPv4 != "" {
--				panic("IPv4 not expected")
--			}
+-	actual, err := Create(client.ServiceClient(), os.CreateOpts{
+-		Name: "createdkey",
+-	}).Extract()
+-	th.AssertNoErr(t, err)
+-	th.CheckDeepEquals(t, &os.CreatedKeyPair, actual)
+-}
 -
--			if s.Status != "" {
--				panic("Status not expected")
--			}
+-func TestImport(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleImportSuccessfully(t)
 -
--			if s.Progress != 0 {
--				panic("Progress not expected")
--			}
+-	actual, err := Create(client.ServiceClient(), os.CreateOpts{
+-		Name:      "importedkey",
+-		PublicKey: "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAAgQDx8nkQv/zgGgB4rMYmIf+6A4l6Rr+o/6lHBQdW5aYd44bd8JttDCE/F/pNRr0lRE+PiqSPO8nDPHw0010JeMH9gYgnnFlyY3/OcJ02RhIPyyxYpv9FhY+2YiUkpwFOcLImyrxEsYXpD/0d3ac30bNH6Sw9JD9UZHYcpSxsIbECHw== Generated by Nova",
+-	}).Extract()
+-	th.AssertNoErr(t, err)
+-	th.CheckDeepEquals(t, &os.ImportedKeyPair, actual)
+-}
 -
--			fmt.Printf("%s,\"%s\"\n", s.Id, s.Name)
--		}
--	}
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleGetSuccessfully(t)
+-
+-	actual, err := Get(client.ServiceClient(), "firstkey").Extract()
+-	th.AssertNoErr(t, err)
+-	th.CheckDeepEquals(t, &os.FirstKeyPair, actual)
 -}
 -
--func tryFullDetails(api gophercloud.CloudServersProvider) {
--	servers, err := api.ListServers()
--	if err != nil {
--		panic(err)
--	}
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleDeleteSuccessfully(t)
 -
--	if !*quiet {
--		fmt.Println("Id,Name,AccessIPv4,Status,Progress")
--		for _, s := range servers {
--			fmt.Printf("%s,\"%s\",%s,%s,%d\n", s.Id, s.Name, s.AccessIPv4, s.Status, s.Progress)
--		}
--	}
+-	err := Delete(client.ServiceClient(), "deletedkey").ExtractErr()
+-	th.AssertNoErr(t, err)
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/03-get-server-details.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/03-get-server-details.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/keypairs/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/keypairs/doc.go
 deleted file mode 100644
-index 01140a9..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/03-get-server-details.go
+index 3171375..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/keypairs/doc.go
 +++ /dev/null
-@@ -1,134 +0,0 @@
--// +build acceptance,old
--
--package main
+@@ -1,3 +0,0 @@
+-// Package keypairs provides information and interaction with the keypair
+-// API resource for the Rackspace Cloud Servers service.
+-package keypairs
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/doc.go
+deleted file mode 100644
+index 8e5c773..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/doc.go
++++ /dev/null
+@@ -1,3 +0,0 @@
+-// Package networks provides information and interaction with the network
+-// API resource for the Rackspace Cloud Servers service.
+-package networks
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/requests.go
+deleted file mode 100644
+index d3c973e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/requests.go
++++ /dev/null
+@@ -1,101 +0,0 @@
+-package networks
 -
 -import (
--	"flag"
--	"fmt"
+-	"errors"
+-
 -	"github.com/rackspace/gophercloud"
--	"os"
+-	"github.com/rackspace/gophercloud/pagination"
+-
 -	"github.com/racker/perigee"
 -)
 -
--var id = flag.String("i", "", "Server ID to get info on.  Defaults to first server in your account if unspecified.")
--var rgn = flag.String("r", "", "Datacenter region.  Leave blank for default region.")
--var quiet = flag.Bool("quiet", false, "Run quietly, for acceptance testing.  $? non-zero if issue.")
+-// List returns a Pager which allows you to iterate over a collection of
+-// networks. It accepts a ListOpts struct, which allows you to filter and sort
+-// the returned collection for greater efficiency.
+-func List(c *gophercloud.ServiceClient) pagination.Pager {
+-	createPage := func(r pagination.PageResult) pagination.Page {
+-		return NetworkPage{pagination.SinglePageBase(r)}
+-	}
 -
--func main() {
--	flag.Parse()
+-	return pagination.NewPager(c, listURL(c), createPage)
+-}
 -
--	resultCode := 0
--	withIdentity(false, func(auth gophercloud.AccessProvider) {
--		withServerApi(auth, func(servers gophercloud.CloudServersProvider) {
--			var (
--				err              error
--				serverId         string
--				deleteAfterwards bool
--			)
+-// Get retrieves a specific network based on its unique ID.
+-func Get(c *gophercloud.ServiceClient, id string) GetResult {
+-	var res GetResult
+-	_, res.Err = perigee.Request("GET", getURL(c, id), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		Results:     &res.Body,
+-		OkCodes:     []int{200},
+-	})
+-	return res
+-}
 -
--			// Figure out which server to provide server details for.
--			if *id == "" {
--				deleteAfterwards, serverId, err = locateAServer(servers)
--				if err != nil {
--					panic(err)
--				}
--				if deleteAfterwards {
--					defer servers.DeleteServerById(serverId)
--				}
--			} else {
--				serverId = *id
--			}
+-// CreateOptsBuilder is the interface options structs have to satisfy in order
+-// to be used in the main Create operation in this package. Since many
+-// extensions decorate or modify the common logic, it is useful for them to
+-// satisfy a basic interface in order for them to be used.
+-type CreateOptsBuilder interface {
+-	ToNetworkCreateMap() (map[string]interface{}, error)
+-}
 -
--			// Grab server details by ID, and provide a report.
--			s, err := servers.ServerById(serverId)
--			if err != nil {
--				panic(err)
--			}
--
--			configs := []string{
--				"Access IPv4: %s\n",
--				"Access IPv6: %s\n",
--				"    Created: %s\n",
--				"     Flavor: %s\n",
--				"    Host ID: %s\n",
--				"         ID: %s\n",
--				"      Image: %s\n",
--				"       Name: %s\n",
--				"   Progress: %s\n",
--				"     Status: %s\n",
--				"  Tenant ID: %s\n",
--				"    Updated: %s\n",
--				"    User ID: %s\n",
--			}
--
--			values := []string{
--				s.AccessIPv4,
--				s.AccessIPv6,
--				s.Created,
--				s.Flavor.Id,
--				s.HostId,
--				s.Id,
--				s.Image.Id,
--				s.Name,
--				fmt.Sprintf("%d", s.Progress),
--				s.Status,
--				s.TenantId,
--				s.Updated,
--				s.UserId,
--			}
--
--			if !*quiet {
--				fmt.Println("Server info:")
--				for i, _ := range configs {
--					fmt.Printf(configs[i], values[i])
--				}
--			}
--		})
+-// CreateOpts is the common options struct used in this package's Create
+-// operation.
+-type CreateOpts struct {
+-	// REQUIRED. See Network object for more info.
+-	CIDR string
+-	// REQUIRED. See Network object for more info.
+-	Label string
+-}
 -
--		// Negative test -- We should absolutely never panic for a server that doesn't exist.
--		withServerApi(auth, func(servers gophercloud.CloudServersProvider) {
--			_, err := servers.ServerById(randomString("garbage", 32))
--			if err == nil {
--				fmt.Printf("Expected a 404 response when looking for a server known not to exist\n")
--				resultCode = 1
--			}
--			perigeeError, ok := err.(*perigee.UnexpectedResponseCodeError)
--			if !ok {
--				fmt.Printf("Unexpected error type\n")
--				resultCode = 1
--			} else {
--				if perigeeError.Actual != 404 {
--					fmt.Printf("Expected a 404 error code\n")
--				}
--			}
--		})
--	})
--	os.Exit(resultCode)
+-// ToNetworkCreateMap casts a CreateOpts struct to a map.
+-func (opts CreateOpts) ToNetworkCreateMap() (map[string]interface{}, error) {
+-	n := make(map[string]interface{})
+-
+-	if opts.CIDR == "" {
+-		return nil, errors.New("Required field CIDR not set.")
+-	}
+-	if opts.Label == "" {
+-		return nil, errors.New("Required field Label not set.")
+-	}
+-
+-	n["label"] = opts.Label
+-	n["cidr"] = opts.CIDR
+-	return map[string]interface{}{"network": n}, nil
 -}
 -
--// locateAServer queries the set of servers owned by the user.  If at least one
--// exists, the first found is picked, and its ID is returned.  Otherwise, a new
--// server will be created, and its ID returned.
+-// Create accepts a CreateOpts struct and creates a new network using the values
+-// provided. This operation does not actually require a request body, i.e. the
+-// CreateOpts struct argument can be empty.
 -//
--// deleteAfter will be true if the caller should schedule a call to DeleteServerById()
--// to clean up.
--func locateAServer(servers gophercloud.CloudServersProvider) (deleteAfter bool, id string, err error) {
--	ss, err := servers.ListServers()
+-// The tenant ID that is contained in the URI is the tenant that creates the
+-// network. An admin user, however, has the option of specifying another tenant
+-// ID in the CreateOpts struct.
+-func Create(c *gophercloud.ServiceClient, opts CreateOptsBuilder) CreateResult {
+-	var res CreateResult
+-
+-	reqBody, err := opts.ToNetworkCreateMap()
 -	if err != nil {
--		return false, "", err
+-		res.Err = err
+-		return res
 -	}
 -
--	if len(ss) > 0 {
--		// We could just cheat and dump the server details from ss[0].
--		// But, that tests ListServers(), and not ServerById().  So, we
--		// elect not to cheat.
--		return false, ss[0].Id, nil
--	}
+-	// Send request to API
+-	_, res.Err = perigee.Request("POST", createURL(c), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{200, 201, 202},
+-	})
+-	return res
+-}
 -
--	serverId, err := createServer(servers, "", "", "", "")
--	if err != nil {
--		return false, "", err
--	}
--	err = waitForServerState(servers, serverId, "ACTIVE")
--	return true, serverId, err
+-// Delete accepts a unique ID and deletes the network associated with it.
+-func Delete(c *gophercloud.ServiceClient, networkID string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", deleteURL(c, networkID), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{204},
+-	})
+-	return res
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/04-create-server.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/04-create-server.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/requests_test.go
 deleted file mode 100644
-index 03fd606..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/04-create-server.go
+index 6f44c1c..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/requests_test.go
 +++ /dev/null
-@@ -1,47 +0,0 @@
--// +build acceptance,old
--
--package main
+@@ -1,156 +0,0 @@
+-package networks
 -
 -import (
--	"flag"
 -	"fmt"
--	"github.com/rackspace/gophercloud"
+-	"net/http"
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
 -)
 -
--var region, serverName, imageRef, flavorRef *string
--var adminPass = flag.String("a", "", "Administrator password (auto-assigned if none)")
--var quiet = flag.Bool("quiet", false, "Quiet mode for acceptance tests.  $? non-zero if error.")
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--func configure() {
--	region = flag.String("r", "", "Region in which to create the server.  Leave blank for provider-default region.")
--	serverName = flag.String("n", randomString("ACPTTEST--", 16), "Server name (what you see in the control panel)")
--	imageRef = flag.String("i", "", "ID of image to deploy onto the server")
--	flavorRef = flag.String("f", "", "Flavor of server to deploy image upon")
+-	th.Mux.HandleFunc("/os-networksv2", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--	flag.Parse()
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
+-
+-		fmt.Fprintf(w, `
+-{
+-    "networks": [
+-        {
+-            "label": "test-network-1",
+-            "cidr": "192.168.100.0/24",
+-            "id": "d32019d3-bc6e-4319-9c1d-6722fc136a22"
+-        },
+-        {
+-            "label": "test-network-2",
+-            "cidr": "192.30.250.00/18",
+-            "id": "db193ab3-96e3-4cb3-8fc5-05f4296d0324"
+-        }
+-    ]
 -}
+-      `)
+-	})
 -
--func main() {
--	configure()
+-	client := fake.ServiceClient()
+-	count := 0
 -
--	withIdentity(false, func(auth gophercloud.AccessProvider) {
--		withServerApi(auth, func(servers gophercloud.CloudServersProvider) {
--			_, err := createServer(servers, *imageRef, *flavorRef, *serverName, *adminPass)
--			if err != nil {
--				panic(err)
--			}
+-	err := List(client).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractNetworks(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract networks: %v", err)
+-			return false, err
+-		}
 -
--			allServers, err := servers.ListServers()
--			if err != nil {
--				panic(err)
--			}
+-		expected := []Network{
+-			Network{
+-				Label: "test-network-1",
+-				CIDR:  "192.168.100.0/24",
+-				ID:    "d32019d3-bc6e-4319-9c1d-6722fc136a22",
+-			},
+-			Network{
+-				Label: "test-network-2",
+-				CIDR:  "192.30.250.00/18",
+-				ID:    "db193ab3-96e3-4cb3-8fc5-05f4296d0324",
+-			},
+-		}
 -
--			if !*quiet {
--				fmt.Printf("ID,Name,Status,Progress\n")
--				for _, i := range allServers {
--					fmt.Printf("%s,\"%s\",%s,%d\n", i.Id, i.Name, i.Status, i.Progress)
--				}
--			}
--		})
+-		th.CheckDeepEquals(t, expected, actual)
+-
+-		return true, nil
 -	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, 1, count)
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/05-list-images.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/05-list-images.go
-deleted file mode 100644
-index 5ead18b..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/05-list-images.go
-+++ /dev/null
-@@ -1,32 +0,0 @@
--// +build acceptance,old
 -
--package main
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--import (
--	"flag"
--	"fmt"
--	"github.com/rackspace/gophercloud"
--)
+-	th.Mux.HandleFunc("/os-networksv2/d32019d3-bc6e-4319-9c1d-6722fc136a22", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--var quiet = flag.Bool("quiet", false, "Quiet mode for acceptance testing.  $? non-zero on error though.")
--var rgn = flag.String("r", "", "Datacenter region to interrogate.  Leave blank for provider-default region.")
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--func main() {
--	flag.Parse()
+-		fmt.Fprintf(w, `
+-{
+-    "network": {
+-        "label": "test-network-1",
+-        "cidr": "192.168.100.0/24",
+-        "id": "d32019d3-bc6e-4319-9c1d-6722fc136a22"
+-    }
+-}
+-      `)
+-	})
 -
--	withIdentity(false, func(auth gophercloud.AccessProvider) {
--		withServerApi(auth, func(servers gophercloud.CloudServersProvider) {
--			images, err := servers.ListImages()
--			if err != nil {
--				panic(err)
--			}
+-	n, err := Get(fake.ServiceClient(), "d32019d3-bc6e-4319-9c1d-6722fc136a22").Extract()
+-	th.AssertNoErr(t, err)
 -
--			if !*quiet {
--				fmt.Println("ID,Name,MinRam,MinDisk")
--				for _, image := range images {
--					fmt.Printf("%s,\"%s\",%d,%d\n", image.Id, image.Name, image.MinRam, image.MinDisk)
--				}
--			}
--		})
--	})
+-	th.AssertEquals(t, n.CIDR, "192.168.100.0/24")
+-	th.AssertEquals(t, n.Label, "test-network-1")
+-	th.AssertEquals(t, n.ID, "d32019d3-bc6e-4319-9c1d-6722fc136a22")
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/06-list-flavors.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/06-list-flavors.go
-deleted file mode 100644
-index 65db7da..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/06-list-flavors.go
-+++ /dev/null
-@@ -1,32 +0,0 @@
--// +build acceptance,old
 -
--package main
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/os-networksv2", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "network": {
+-        "label": "test-network-1",
+-        "cidr": "192.168.100.0/24"
+-    }
+-}
+-      `)
 -
--import (
--	"flag"
--	"fmt"
--	"github.com/rackspace/gophercloud"
--)
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
 -
--var quiet = flag.Bool("quiet", false, "Quiet mode for acceptance testing.  $? non-zero on error though.")
--var rgn = flag.String("r", "", "Datacenter region to interrogate.  Leave blank for provider-default region.")
+-		fmt.Fprintf(w, `
+-{
+-    "network": {
+-        "label": "test-network-1",
+-        "cidr": "192.168.100.0/24",
+-        "id": "4e8e5957-649f-477b-9e5b-f1f75b21c03c"
+-    }
+-}
+-    `)
+-	})
 -
--func main() {
--	flag.Parse()
+-	options := CreateOpts{Label: "test-network-1", CIDR: "192.168.100.0/24"}
+-	n, err := Create(fake.ServiceClient(), options).Extract()
+-	th.AssertNoErr(t, err)
 -
--	withIdentity(false, func(auth gophercloud.AccessProvider) {
--		withServerApi(auth, func(servers gophercloud.CloudServersProvider) {
--			flavors, err := servers.ListFlavors()
--			if err != nil {
--				panic(err)
--			}
+-	th.AssertEquals(t, n.Label, "test-network-1")
+-	th.AssertEquals(t, n.ID, "4e8e5957-649f-477b-9e5b-f1f75b21c03c")
+-}
 -
--			if !*quiet {
--				fmt.Println("ID,Name,MinRam,MinDisk")
--				for _, f := range flavors {
--					fmt.Printf("%s,\"%s\",%d,%d\n", f.Id, f.Name, f.Ram, f.Disk)
--				}
--			}
--		})
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/os-networksv2/4e8e5957-649f-477b-9e5b-f1f75b21c03c", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		w.WriteHeader(http.StatusNoContent)
 -	})
+-
+-	res := Delete(fake.ServiceClient(), "4e8e5957-649f-477b-9e5b-f1f75b21c03c")
+-	th.AssertNoErr(t, res.Err)
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/07-change-admin-password.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/07-change-admin-password.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/results.go
 deleted file mode 100644
-index 880fbe8..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/07-change-admin-password.go
+index eb6a76c..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/results.go
 +++ /dev/null
-@@ -1,49 +0,0 @@
--// +build acceptance,old
--
--package main
+@@ -1,81 +0,0 @@
+-package networks
 -
 -import (
--	"flag"
--	"fmt"
+-	"github.com/mitchellh/mapstructure"
 -	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
 -)
 -
--var quiet = flag.Bool("quiet", false, "Quiet mode, for acceptance testing.  $? still indicates errors though.")
--var serverId = flag.String("i", "", "ID of server whose admin password is to be changed.")
--var newPass = flag.String("p", "", "New password for the server.")
--
--func main() {
--	flag.Parse()
+-type commonResult struct {
+-	gophercloud.Result
+-}
 -
--	withIdentity(false, func(acc gophercloud.AccessProvider) {
--		withServerApi(acc, func(api gophercloud.CloudServersProvider) {
--			// If user doesn't explicitly provide a server ID, create one dynamically.
--			if *serverId == "" {
--				var err error
--				*serverId, err = createServer(api, "", "", "", "")
--				if err != nil {
--					panic(err)
--				}
--				waitForServerState(api, *serverId, "ACTIVE")
--			}
+-// Extract is a function that accepts a result and extracts a network resource.
+-func (r commonResult) Extract() (*Network, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
+-	}
 -
--			// If no password is provided, create one dynamically.
--			if *newPass == "" {
--				*newPass = randomString("", 16)
--			}
+-	var res struct {
+-		Network *Network `json:"network"`
+-	}
 -
--			// Submit the request for changing the admin password.
--			// Note that we don't verify this actually completes;
--			// doing so is beyond the scope of the SDK, and should be
--			// the responsibility of your specific OpenStack provider.
--			err := api.SetAdminPassword(*serverId, *newPass)
--			if err != nil {
--				panic(err)
--			}
+-	err := mapstructure.Decode(r.Body, &res)
 -
--			if !*quiet {
--				fmt.Println("Password change request submitted.")
--			}
--		})
--	})
+-	return res.Network, err
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/08-reauthentication.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/08-reauthentication.go
-deleted file mode 100644
-index c46f5bb..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/08-reauthentication.go
-+++ /dev/null
-@@ -1,50 +0,0 @@
--// +build acceptance,old
 -
--package main
+-// CreateResult represents the result of a create operation.
+-type CreateResult struct {
+-	commonResult
+-}
 -
--import (
--	"flag"
--	"fmt"
--	"github.com/rackspace/gophercloud"
--)
+-// GetResult represents the result of a get operation.
+-type GetResult struct {
+-	commonResult
+-}
 -
--var quiet = flag.Bool("quiet", false, "Quiet mode for acceptance testing.  $? non-zero on error though.")
--var rgn = flag.String("r", "", "Datacenter region to interrogate.  Leave blank for provider-default region.")
+-// DeleteResult represents the result of a delete operation.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
+-}
 -
--func main() {
--	flag.Parse()
+-// Network represents, well, a network.
+-type Network struct {
+-	// UUID for the network
+-	ID string `mapstructure:"id" json:"id"`
 -
--	// Invoke withIdentity such that re-auth is enabled.
--	withIdentity(true, func(auth gophercloud.AccessProvider) {
--		token1 := auth.AuthToken()
+-	// Human-readable name for the network. Might not be unique.
+-	Label string `mapstructure:"label" json:"label"`
 -
--		withServerApi(auth, func(servers gophercloud.CloudServersProvider) {
--			// Just to confirm everything works, we should be able to list images without error.
--			_, err := servers.ListImages()
--			if err != nil {
--				panic(err)
--			}
+-	// Classless Inter-Domain Routing
+-	CIDR string `mapstructure:"cidr" json:"cidr"`
+-}
 -
--			// Revoke our current authentication token.
--			auth.Revoke(auth.AuthToken())
+-// NetworkPage is the page returned by a pager when traversing over a
+-// collection of networks.
+-type NetworkPage struct {
+-	pagination.SinglePageBase
+-}
 -
--			// Attempt to list images again.  This should _succeed_, because we enabled re-authentication.
--			_, err = servers.ListImages()
--			if err != nil {
--				panic(err)
--			}
+-// IsEmpty returns true if the NetworkPage contains no Networks.
+-func (r NetworkPage) IsEmpty() (bool, error) {
+-	networks, err := ExtractNetworks(r)
+-	if err != nil {
+-		return true, err
+-	}
+-	return len(networks) == 0, nil
+-}
 -
--			// However, our new authentication token should differ.
--			token2 := auth.AuthToken()
+-// ExtractNetworks accepts a Page struct, specifically a NetworkPage struct,
+-// and extracts the elements into a slice of Network structs. In other words,
+-// a generic collection is mapped into a relevant slice.
+-func ExtractNetworks(page pagination.Page) ([]Network, error) {
+-	var resp struct {
+-		Networks []Network `mapstructure:"networks" json:"networks"`
+-	}
 -
--			if !*quiet {
--				fmt.Println("Old authentication token: ", token1)
--				fmt.Println("New authentication token: ", token2)
--			}
+-	err := mapstructure.Decode(page.(NetworkPage).Body, &resp)
 -
--			if token1 == token2 {
--				panic("Tokens should differ")
--			}
--		})
--	})
+-	return resp.Networks, err
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/09-resize-server.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/09-resize-server.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/urls.go
 deleted file mode 100644
-index a2ef3c8..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/09-resize-server.go
+index 19a21aa..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/urls.go
 +++ /dev/null
-@@ -1,102 +0,0 @@
--// +build acceptance,old
--
--package main
--
--import (
--	"flag"
--	"fmt"
--	"github.com/rackspace/gophercloud"
--	"time"
--)
+@@ -1,27 +0,0 @@
+-package networks
 -
--var quiet = flag.Bool("quiet", false, "Quiet mode, for acceptance testing.  $? still indicates errors though.")
+-import "github.com/rackspace/gophercloud"
 -
--func main() {
--	flag.Parse()
+-func resourceURL(c *gophercloud.ServiceClient, id string) string {
+-	return c.ServiceURL("os-networksv2", id)
+-}
 -
--	withIdentity(false, func(acc gophercloud.AccessProvider) {
--		withServerApi(acc, func(api gophercloud.CloudServersProvider) {
--			// These tests are going to take some time to complete.
--			// So, we'll do two tests at the same time to help amortize test time.
--			done := make(chan bool)
--			go resizeRejectTest(api, done)
--			go resizeAcceptTest(api, done)
--			_ = <-done
--			_ = <-done
+-func rootURL(c *gophercloud.ServiceClient) string {
+-	return c.ServiceURL("os-networksv2")
+-}
 -
--			if !*quiet {
--				fmt.Println("Done.")
--			}
--		})
--	})
+-func getURL(c *gophercloud.ServiceClient, id string) string {
+-	return resourceURL(c, id)
 -}
 -
--// Perform the resize test, but reject the resize request.
--func resizeRejectTest(api gophercloud.CloudServersProvider, done chan bool) {
--	withServer(api, func(id string) {
--		newFlavorId := findAlternativeFlavor()
--		err := api.ResizeServer(id, randomString("ACPTTEST", 24), newFlavorId, "")
--		if err != nil {
--			panic(err)
--		}
+-func listURL(c *gophercloud.ServiceClient) string {
+-	return rootURL(c)
+-}
 -
--		waitForServerState(api, id, "VERIFY_RESIZE")
+-func createURL(c *gophercloud.ServiceClient) string {
+-	return rootURL(c)
+-}
 -
--		err = api.RevertResize(id)
--		if err != nil {
--			panic(err)
--		}
--	})
--	done <- true
+-func deleteURL(c *gophercloud.ServiceClient, id string) string {
+-	return resourceURL(c, id)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/urls_test.go
+deleted file mode 100644
+index 983992e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/networks/urls_test.go
++++ /dev/null
+@@ -1,38 +0,0 @@
+-package networks
 -
--// Perform the resize test, but accept the resize request.
--func resizeAcceptTest(api gophercloud.CloudServersProvider, done chan bool) {
--	withServer(api, func(id string) {
--		newFlavorId := findAlternativeFlavor()
--		err := api.ResizeServer(id, randomString("ACPTTEST", 24), newFlavorId, "")
--		if err != nil {
--			panic(err)
--		}
+-import (
+-	"testing"
 -
--		waitForServerState(api, id, "VERIFY_RESIZE")
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--		err = api.ConfirmResize(id)
--		if err != nil {
--			panic(err)
--		}
--	})
--	done <- true
+-const endpoint = "http://localhost:57909/"
+-
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint}
 -}
 -
--func withServer(api gophercloud.CloudServersProvider, f func(string)) {
--	id, err := createServer(api, "", "", "", "")
--	if err != nil {
--		panic(err)
--	}
+-func TestGetURL(t *testing.T) {
+-	actual := getURL(endpointClient(), "foo")
+-	expected := endpoint + "os-networksv2/foo"
+-	th.AssertEquals(t, expected, actual)
+-}
 -
--	for {
--		s, err := api.ServerById(id)
--		if err != nil {
--			panic(err)
--		}
--		if s.Status == "ACTIVE" {
--			break
--		}
--		time.Sleep(10 * time.Second)
--	}
+-func TestCreateURL(t *testing.T) {
+-	actual := createURL(endpointClient())
+-	expected := endpoint + "os-networksv2"
+-	th.AssertEquals(t, expected, actual)
+-}
 -
--	f(id)
+-func TestListURL(t *testing.T) {
+-	actual := createURL(endpointClient())
+-	expected := endpoint + "os-networksv2"
+-	th.AssertEquals(t, expected, actual)
+-}
 -
--	// I've learned that resizing an instance can fail if a delete request
--	// comes in prior to its completion.  This ends up leaving the server
--	// in an error state, and neither the resize NOR the delete complete.
--	// This is a bug in OpenStack, as far as I'm concerned, but thankfully,
--	// there's an easy work-around -- just wait for your server to return to
--	// active state first!
--	waitForServerState(api, id, "ACTIVE")
--	err = api.DeleteServerById(id)
--	if err != nil {
--		panic(err)
--	}
+-func TestDeleteURL(t *testing.T) {
+-	actual := deleteURL(endpointClient(), "foo")
+-	expected := endpoint + "os-networksv2/foo"
+-	th.AssertEquals(t, expected, actual)
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/10-reboot-server.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/10-reboot-server.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/delegate.go
 deleted file mode 100644
-index ba6215a..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/10-reboot-server.go
+index 4c7b249..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/delegate.go
 +++ /dev/null
-@@ -1,45 +0,0 @@
--// +build acceptance,old
--
--package main
+@@ -1,61 +0,0 @@
+-package servers
 -
 -import (
--	"flag"
--	"fmt"
 -	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack/compute/v2/servers"
+-	"github.com/rackspace/gophercloud/pagination"
 -)
 -
--var quiet = flag.Bool("quiet", false, "Quiet mode, for acceptance testing.  $? still indicates errors though.")
+-// List makes a request against the API to list servers accessible to you.
+-func List(client *gophercloud.ServiceClient, opts os.ListOptsBuilder) pagination.Pager {
+-	return os.List(client, opts)
+-}
+-
+-// Create requests a server to be provisioned to the user in the current tenant.
+-func Create(client *gophercloud.ServiceClient, opts os.CreateOptsBuilder) os.CreateResult {
+-	return os.Create(client, opts)
+-}
 -
--func main() {
--	flag.Parse()
+-// Delete requests that a server previously provisioned be removed from your account.
+-func Delete(client *gophercloud.ServiceClient, id string) os.DeleteResult {
+-	return os.Delete(client, id)
+-}
 -
--	withIdentity(false, func(acc gophercloud.AccessProvider) {
--		withServerApi(acc, func(servers gophercloud.CloudServersProvider) {
--			log("Creating server")
--			serverId, err := createServer(servers, "", "", "", "")
--			if err != nil {
--				panic(err)
--			}
--			waitForServerState(servers, serverId, "ACTIVE")
+-// Get requests details on a single server, by ID.
+-func Get(client *gophercloud.ServiceClient, id string) os.GetResult {
+-	return os.Get(client, id)
+-}
 -
--			log("Soft-rebooting server")
--			servers.RebootServer(serverId, false)
--			waitForServerState(servers, serverId, "REBOOT")
--			waitForServerState(servers, serverId, "ACTIVE")
+-// ChangeAdminPassword alters the administrator or root password for a specified server.
+-func ChangeAdminPassword(client *gophercloud.ServiceClient, id, newPassword string) os.ActionResult {
+-	return os.ChangeAdminPassword(client, id, newPassword)
+-}
 -
--			log("Hard-rebooting server")
--			servers.RebootServer(serverId, true)
--			waitForServerState(servers, serverId, "HARD_REBOOT")
--			waitForServerState(servers, serverId, "ACTIVE")
+-// Reboot requests that a given server reboot. Two methods exist for rebooting a server:
+-//
+-// os.HardReboot (aka PowerCycle) restarts the server instance by physically cutting power to the
+-// machine, or if a VM, terminating it at the hypervisor level. It's done. Caput. Full stop. Then,
+-// after a brief wait, power is restored or the VM instance restarted.
+-//
+-// os.SoftReboot (aka OSReboot) simply tells the OS to restart under its own procedures. E.g., in
+-// Linux, asking it to enter runlevel 6, or executing "sudo shutdown -r now", or by asking Windows to restart the machine.
+-func Reboot(client *gophercloud.ServiceClient, id string, how os.RebootMethod) os.ActionResult {
+-	return os.Reboot(client, id, how)
+-}
 -
--			log("Done")
--			servers.DeleteServerById(serverId)
--		})
--	})
+-// Rebuild will reprovision the server according to the configuration options provided in the
+-// RebuildOpts struct.
+-func Rebuild(client *gophercloud.ServiceClient, id string, opts os.RebuildOptsBuilder) os.RebuildResult {
+-	return os.Rebuild(client, id, opts)
 -}
 -
--func log(s string) {
--	if !*quiet {
--		fmt.Println(s)
--	}
+-// WaitForStatus will continually poll a server until it successfully transitions to a specified
+-// status. It will do this for at most the number of seconds specified.
+-func WaitForStatus(c *gophercloud.ServiceClient, id, status string, secs int) error {
+-	return os.WaitForStatus(c, id, status, secs)
+-}
+-
+-// ExtractServers interprets the results of a single page from a List() call, producing a slice of Server entities.
+-func ExtractServers(page pagination.Page) ([]os.Server, error) {
+-	return os.ExtractServers(page)
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/11-rescue-unrescue-server.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/11-rescue-unrescue-server.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/delegate_test.go
 deleted file mode 100644
-index 008ad9d..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/11-rescue-unrescue-server.go
+index 7f41404..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/delegate_test.go
 +++ /dev/null
-@@ -1,52 +0,0 @@
--// +build acceptance,old
--
--package main
+@@ -1,112 +0,0 @@
+-package servers
 -
 -import (
--	"flag"
 -	"fmt"
--	"github.com/rackspace/gophercloud"
+-	"net/http"
+-	"testing"
+-
+-	os "github.com/rackspace/gophercloud/openstack/compute/v2/servers"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
 -)
 -
--var quiet = flag.Bool("quiet", false, "Quiet mode, for acceptance testing.  $? still indicates errors though.")
+-func TestListServers(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--func main() {
--	flag.Parse()
--	withIdentity(false, func(acc gophercloud.AccessProvider) {
--		withServerApi(acc, func(servers gophercloud.CloudServersProvider) {
--			log("Creating server")
--			id, err := createServer(servers, "", "", "", "")
--			if err != nil {
--				panic(err)
--			}
--			waitForServerState(servers, id, "ACTIVE")
--			defer servers.DeleteServerById(id)
+-	th.Mux.HandleFunc("/servers/detail", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
 -
--			log("Rescuing server")
--			adminPass, err := servers.RescueServer(id)
--			if err != nil {
--				panic(err)
--			}
--			log("  Admin password = " + adminPass)
--			if len(adminPass) < 1 {
--				panic("Empty admin password")
--			}
--			waitForServerState(servers, id, "RESCUE")
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, ListOutput)
+-	})
 -
--			log("Unrescuing server")
--			err = servers.UnrescueServer(id)
--			if err != nil {
--				panic(err)
--			}
--			waitForServerState(servers, id, "ACTIVE")
+-	count := 0
+-	err := List(client.ServiceClient(), nil).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractServers(page)
+-		th.AssertNoErr(t, err)
+-		th.CheckDeepEquals(t, ExpectedServerSlice, actual)
 -
--			log("Done")
--		})
+-		return true, nil
 -	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, 1, count)
 -}
 -
--func log(s string) {
--	if !*quiet {
--		fmt.Println(s)
--	}
--}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/12-update-server.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/12-update-server.go
-deleted file mode 100644
-index c0191f1..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/12-update-server.go
-+++ /dev/null
-@@ -1,46 +0,0 @@
--// +build acceptance,old
+-func TestCreateServer(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleServerCreationSuccessfully(t, CreateOutput)
 -
--package main
+-	actual, err := Create(client.ServiceClient(), os.CreateOpts{
+-		Name:      "derp",
+-		ImageRef:  "f90f6034-2570-4974-8351-6b49732ef2eb",
+-		FlavorRef: "1",
+-	}).Extract()
+-	th.AssertNoErr(t, err)
 -
--import (
--	"flag"
--	"fmt"
--	"github.com/rackspace/gophercloud"
--)
+-	th.CheckDeepEquals(t, &CreatedServer, actual)
+-}
 -
--var quiet = flag.Bool("quiet", false, "Quiet mode, for acceptance testing.  $? still indicates errors though.")
+-func TestDeleteServer(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleServerDeletionSuccessfully(t)
 -
--func main() {
--	flag.Parse()
--	withIdentity(false, func(acc gophercloud.AccessProvider) {
--		withServerApi(acc, func(servers gophercloud.CloudServersProvider) {
--			log("Creating server")
--			id, err := createServer(servers, "", "", "", "")
--			if err != nil {
--				panic(err)
--			}
--			waitForServerState(servers, id, "ACTIVE")
--			defer servers.DeleteServerById(id)
+-	res := Delete(client.ServiceClient(), "asdfasdfasdf")
+-	th.AssertNoErr(t, res.Err)
+-}
 -
--			log("Updating name of server")
--			newName := randomString("ACPTTEST", 32)
--			newDetails, err := servers.UpdateServer(id, gophercloud.NewServerSettings{
--				Name: newName,
--			})
--			if err != nil {
--				panic(err)
--			}
--			if newDetails.Name != newName {
--				panic("Name change didn't appear to take")
--			}
+-func TestGetServer(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--			log("Done")
--		})
+-	th.Mux.HandleFunc("/servers/8c65cb68-0681-4c30-bc88-6b83a8a26aee", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
+-
+-		w.Header().Add("Content-Type", "application/json")
+-		fmt.Fprintf(w, GetOutput)
 -	})
+-
+-	actual, err := Get(client.ServiceClient(), "8c65cb68-0681-4c30-bc88-6b83a8a26aee").Extract()
+-	th.AssertNoErr(t, err)
+-	th.CheckDeepEquals(t, &GophercloudServer, actual)
+-}
+-
+-func TestChangeAdminPassword(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleAdminPasswordChangeSuccessfully(t)
+-
+-	res := ChangeAdminPassword(client.ServiceClient(), "1234asdf", "new-password")
+-	th.AssertNoErr(t, res.Err)
+-}
+-
+-func TestReboot(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleRebootSuccessfully(t)
+-
+-	res := Reboot(client.ServiceClient(), "1234asdf", os.SoftReboot)
+-	th.AssertNoErr(t, res.Err)
 -}
 -
--func log(s string) {
--	if !*quiet {
--		fmt.Println(s)
+-func TestRebuildServer(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleRebuildSuccessfully(t, GetOutput)
+-
+-	opts := os.RebuildOpts{
+-		Name:       "new-name",
+-		AdminPass:  "swordfish",
+-		ImageID:    "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/images/f90f6034-2570-4974-8351-6b49732ef2eb",
+-		AccessIPv4: "1.2.3.4",
 -	}
+-	actual, err := Rebuild(client.ServiceClient(), "1234asdf", opts).Extract()
+-	th.AssertNoErr(t, err)
+-	th.CheckDeepEquals(t, &GophercloudServer, actual)
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/13-rebuild-server.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/13-rebuild-server.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/doc.go
 deleted file mode 100644
-index ae7e19f..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/13-rebuild-server.go
+index c9f77f6..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/doc.go
 +++ /dev/null
-@@ -1,46 +0,0 @@
--// +build acceptance,old
+@@ -1,3 +0,0 @@
+-// Package servers provides information and interaction with the server
+-// API resource for the Rackspace Cloud Servers service.
+-package servers
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/fixtures.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/fixtures.go
+deleted file mode 100644
+index b22a289..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/fixtures.go
++++ /dev/null
+@@ -1,439 +0,0 @@
+-// +build fixtures
 -
--package main
+-package servers
 -
 -import (
--	"flag"
--	"fmt"
--	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack/compute/v2/servers"
 -)
 -
--var quiet = flag.Bool("quiet", false, "Quiet mode, for acceptance testing.  $? still indicates errors though.")
+-// ListOutput is the recorded output of a Rackspace servers.List request.
+-const ListOutput = `
+-{
+-	"servers": [
+-		{
+-			"OS-DCF:diskConfig": "MANUAL",
+-			"OS-EXT-STS:power_state": 1,
+-			"OS-EXT-STS:task_state": null,
+-			"OS-EXT-STS:vm_state": "active",
+-			"accessIPv4": "1.2.3.4",
+-			"accessIPv6": "1111:4822:7818:121:2000:9b5e:7438:a2d0",
+-			"addresses": {
+-				"private": [
+-					{
+-						"addr": "10.208.230.113",
+-						"version": 4
+-					}
+-				],
+-				"public": [
+-					{
+-						"addr": "2001:4800:7818:101:2000:9b5e:7428:a2d0",
+-						"version": 6
+-					},
+-					{
+-						"addr": "104.130.131.164",
+-						"version": 4
+-					}
+-				]
+-			},
+-			"created": "2014-09-23T12:34:58Z",
+-			"flavor": {
+-				"id": "performance1-8",
+-				"links": [
+-					{
+-						"href": "https://dfw.servers.api.rackspacecloud.com/111111/flavors/performance1-8",
+-						"rel": "bookmark"
+-					}
+-				]
+-			},
+-			"hostId": "e8951a524bc465b0898aeac7674da6fe1495e253ae1ea17ddb2c2475",
+-			"id": "59818cee-bc8c-44eb-8073-673ee65105f7",
+-			"image": {
+-				"id": "255df5fb-e3d4-45a3-9a07-c976debf7c14",
+-				"links": [
+-					{
+-						"href": "https://dfw.servers.api.rackspacecloud.com/111111/images/255df5fb-e3d4-45a3-9a07-c976debf7c14",
+-						"rel": "bookmark"
+-					}
+-				]
+-			},
+-			"key_name": "mykey",
+-			"links": [
+-				{
+-					"href": "https://dfw.servers.api.rackspacecloud.com/v2/111111/servers/59818cee-bc8c-44eb-8073-673ee65105f7",
+-					"rel": "self"
+-				},
+-				{
+-					"href": "https://dfw.servers.api.rackspacecloud.com/111111/servers/59818cee-bc8c-44eb-8073-673ee65105f7",
+-					"rel": "bookmark"
+-				}
+-			],
+-			"metadata": {},
+-			"name": "devstack",
+-			"progress": 100,
+-			"status": "ACTIVE",
+-			"tenant_id": "111111",
+-			"updated": "2014-09-23T12:38:19Z",
+-			"user_id": "14ae7bb21d81422694655f3cc30f2930"
+-		},
+-		{
+-			"OS-DCF:diskConfig": "MANUAL",
+-			"OS-EXT-STS:power_state": 1,
+-			"OS-EXT-STS:task_state": null,
+-			"OS-EXT-STS:vm_state": "active",
+-			"accessIPv4": "1.1.2.3",
+-			"accessIPv6": "2222:4444:7817:101:be76:4eff:f0e5:9e02",
+-			"addresses": {
+-				"private": [
+-					{
+-						"addr": "10.10.20.30",
+-						"version": 4
+-					}
+-				],
+-				"public": [
+-					{
+-						"addr": "1.1.2.3",
+-						"version": 4
+-					},
+-					{
+-						"addr": "2222:4444:7817:101:be76:4eff:f0e5:9e02",
+-						"version": 6
+-					}
+-				]
+-			},
+-			"created": "2014-07-21T19:32:55Z",
+-			"flavor": {
+-				"id": "performance1-2",
+-				"links": [
+-					{
+-						"href": "https://dfw.servers.api.rackspacecloud.com/111111/flavors/performance1-2",
+-						"rel": "bookmark"
+-					}
+-				]
+-			},
+-			"hostId": "f859679906d6b1a38c1bd516b78f4dcc7d5fcf012578fa3ce460716c",
+-			"id": "25f1c7f5-e00a-4715-b354-16e24b2f4630",
+-			"image": {
+-				"id": "bb02b1a3-bc77-4d17-ab5b-421d89850fca",
+-				"links": [
+-					{
+-						"href": "https://dfw.servers.api.rackspacecloud.com/111111/images/bb02b1a3-bc77-4d17-ab5b-421d89850fca",
+-						"rel": "bookmark"
+-					}
+-				]
+-			},
+-			"key_name": "otherkey",
+-			"links": [
+-				{
+-					"href": "https://dfw.servers.api.rackspacecloud.com/v2/111111/servers/25f1c7f5-e00a-4715-b355-16e24b2f4630",
+-					"rel": "self"
+-				},
+-				{
+-					"href": "https://dfw.servers.api.rackspacecloud.com/111111/servers/25f1c7f5-e00a-4715-b355-16e24b2f4630",
+-					"rel": "bookmark"
+-				}
+-			],
+-			"metadata": {},
+-			"name": "peril-dfw",
+-			"progress": 100,
+-			"status": "ACTIVE",
+-			"tenant_id": "111111",
+-			"updated": "2014-07-21T19:34:24Z",
+-			"user_id": "14ae7bb21d81422694655f3cc30f2930"
+-		}
+-	]
+-}
+-`
 -
--func main() {
--	flag.Parse()
--	withIdentity(false, func(acc gophercloud.AccessProvider) {
--		withServerApi(acc, func(servers gophercloud.CloudServersProvider) {
--			log("Creating server")
--			id, err := createServer(servers, "", "", "", "")
--			if err != nil {
--				panic(err)
+-// GetOutput is the recorded output of a Rackspace servers.Get request.
+-const GetOutput = `
+-{
+-	"server": {
+-		"OS-DCF:diskConfig": "AUTO",
+-		"OS-EXT-STS:power_state": 1,
+-		"OS-EXT-STS:task_state": null,
+-		"OS-EXT-STS:vm_state": "active",
+-		"accessIPv4": "1.2.4.8",
+-		"accessIPv6": "2001:4800:6666:105:2a0f:c056:f594:7777",
+-		"addresses": {
+-			"private": [
+-				{
+-					"addr": "10.20.40.80",
+-					"version": 4
+-				}
+-			],
+-			"public": [
+-				{
+-					"addr": "1.2.4.8",
+-					"version": 4
+-				},
+-				{
+-					"addr": "2001:4800:6666:105:2a0f:c056:f594:7777",
+-					"version": 6
+-				}
+-			]
+-		},
+-		"created": "2014-10-21T14:42:16Z",
+-		"flavor": {
+-			"id": "performance1-1",
+-			"links": [
+-				{
+-					"href": "https://dfw.servers.api.rackspacecloud.com/111111/flavors/performance1-1",
+-					"rel": "bookmark"
+-				}
+-			]
+-		},
+-		"hostId": "430d2ae02de0a7af77012c94778145eccf67e75b1fac0528aa10d4a7",
+-		"id": "8c65cb68-0681-4c30-bc88-6b83a8a26aee",
+-		"image": {
+-			"id": "e19a734c-c7e6-443a-830c-242209c4d65d",
+-			"links": [
+-				{
+-					"href": "https://dfw.servers.api.rackspacecloud.com/111111/images/e19a734c-c7e6-443a-830c-242209c4d65d",
+-					"rel": "bookmark"
+-				}
+-			]
+-		},
+-		"key_name": null,
+-		"links": [
+-			{
+-				"href": "https://dfw.servers.api.rackspacecloud.com/v2/111111/servers/8c65cb68-0681-4c30-bc88-6b83a8a26aee",
+-				"rel": "self"
+-			},
+-			{
+-				"href": "https://dfw.servers.api.rackspacecloud.com/111111/servers/8c65cb68-0681-4c30-bc88-6b83a8a26aee",
+-				"rel": "bookmark"
 -			}
--			waitForServerState(servers, id, "ACTIVE")
--			defer servers.DeleteServerById(id)
+-		],
+-		"metadata": {},
+-		"name": "Gophercloud-pxpGGuey",
+-		"progress": 100,
+-		"status": "ACTIVE",
+-		"tenant_id": "111111",
+-		"updated": "2014-10-21T14:42:57Z",
+-		"user_id": "14ae7bb21d81423694655f4dd30f2930"
+-	}
+-}
+-`
 -
--			log("Rebuilding server")
--			newDetails, err := servers.RebuildServer(id, gophercloud.NewServer{
--				Name:      randomString("ACPTTEST", 32),
--				ImageRef:  findAlternativeImage(),
--				FlavorRef: findAlternativeFlavor(),
--				AdminPass: randomString("", 16),
--			})
--			if err != nil {
--				panic(err)
+-// CreateOutput contains a sample of Rackspace's response to a Create call.
+-const CreateOutput = `
+-{
+-	"server": {
+-		"OS-DCF:diskConfig": "AUTO",
+-		"adminPass": "v7tADqbE5pr9",
+-		"id": "bb63327b-6a2f-34bc-b0ef-4b6d97ea637e",
+-		"links": [
+-			{
+-				"href": "https://dfw.servers.api.rackspacecloud.com/v2/111111/servers/bb63327b-6a2f-34bc-b0ef-4b6d97ea637e",
+-				"rel": "self"
+-			},
+-			{
+-				"href": "https://dfw.servers.api.rackspacecloud.com/111111/servers/bb63327b-6a2f-34bc-b0ef-4b6d97ea637e",
+-				"rel": "bookmark"
 -			}
--			waitForServerState(servers, newDetails.Id, "ACTIVE")
+-		]
+-	}
+-}
+-`
 -
--			log("Done")
--		})
--	})
+-// DevstackServer is the expected first result from parsing ListOutput.
+-var DevstackServer = os.Server{
+-	ID:         "59818cee-bc8c-44eb-8073-673ee65105f7",
+-	Name:       "devstack",
+-	TenantID:   "111111",
+-	UserID:     "14ae7bb21d81422694655f3cc30f2930",
+-	HostID:     "e8951a524bc465b0898aeac7674da6fe1495e253ae1ea17ddb2c2475",
+-	Updated:    "2014-09-23T12:38:19Z",
+-	Created:    "2014-09-23T12:34:58Z",
+-	AccessIPv4: "1.2.3.4",
+-	AccessIPv6: "1111:4822:7818:121:2000:9b5e:7438:a2d0",
+-	Progress:   100,
+-	Status:     "ACTIVE",
+-	Image: map[string]interface{}{
+-		"id": "255df5fb-e3d4-45a3-9a07-c976debf7c14",
+-		"links": []interface{}{
+-			map[string]interface{}{
+-				"href": "https://dfw.servers.api.rackspacecloud.com/111111/images/255df5fb-e3d4-45a3-9a07-c976debf7c14",
+-				"rel":  "bookmark",
+-			},
+-		},
+-	},
+-	Flavor: map[string]interface{}{
+-		"id": "performance1-8",
+-		"links": []interface{}{
+-			map[string]interface{}{
+-				"href": "https://dfw.servers.api.rackspacecloud.com/111111/flavors/performance1-8",
+-				"rel":  "bookmark",
+-			},
+-		},
+-	},
+-	Addresses: map[string]interface{}{
+-		"private": []interface{}{
+-			map[string]interface{}{
+-				"addr":    "10.20.30.40",
+-				"version": float64(4.0),
+-			},
+-		},
+-		"public": []interface{}{
+-			map[string]interface{}{
+-				"addr":    "1111:4822:7818:121:2000:9b5e:7438:a2d0",
+-				"version": float64(6.0),
+-			},
+-			map[string]interface{}{
+-				"addr":    "1.2.3.4",
+-				"version": float64(4.0),
+-			},
+-		},
+-	},
+-	Metadata: map[string]interface{}{},
+-	Links: []interface{}{
+-		map[string]interface{}{
+-			"href": "https://dfw.servers.api.rackspacecloud.com/v2/111111/servers/59918cee-bd9d-44eb-8173-673ee75105f7",
+-			"rel":  "self",
+-		},
+-		map[string]interface{}{
+-			"href": "https://dfw.servers.api.rackspacecloud.com/v2/111111/servers/59818cee-bc8c-44eb-8073-673ee65105f7",
+-			"rel":  "bookmark",
+-		},
+-	},
+-	KeyName:   "mykey",
+-	AdminPass: "",
+-}
+-
+-// PerilServer is the expected second result from parsing ListOutput.
+-var PerilServer = os.Server{
+-	ID:         "25f1c7f5-e00a-4715-b354-16e24b2f4630",
+-	Name:       "peril-dfw",
+-	TenantID:   "111111",
+-	UserID:     "14ae7bb21d81422694655f3cc30f2930",
+-	HostID:     "f859679906d6b1a38c1bd516b78f4dcc7d5fcf012578fa3ce460716c",
+-	Updated:    "2014-07-21T19:34:24Z",
+-	Created:    "2014-07-21T19:32:55Z",
+-	AccessIPv4: "1.1.2.3",
+-	AccessIPv6: "2222:4444:7817:101:be76:4eff:f0e5:9e02",
+-	Progress:   100,
+-	Status:     "ACTIVE",
+-	Image: map[string]interface{}{
+-		"id": "bb02b1a3-bc77-4d17-ab5b-421d89850fca",
+-		"links": []interface{}{
+-			map[string]interface{}{
+-				"href": "https://dfw.servers.api.rackspacecloud.com/111111/images/bb02b1a3-bc77-4d17-ab5b-421d89850fca",
+-				"rel":  "bookmark",
+-			},
+-		},
+-	},
+-	Flavor: map[string]interface{}{
+-		"id": "performance1-2",
+-		"links": []interface{}{
+-			map[string]interface{}{
+-				"href": "https://dfw.servers.api.rackspacecloud.com/111111/flavors/performance1-2",
+-				"rel":  "bookmark",
+-			},
+-		},
+-	},
+-	Addresses: map[string]interface{}{
+-		"private": []interface{}{
+-			map[string]interface{}{
+-				"addr":    "10.10.20.30",
+-				"version": float64(4.0),
+-			},
+-		},
+-		"public": []interface{}{
+-			map[string]interface{}{
+-				"addr":    "2222:4444:7817:101:be76:4eff:f0e5:9e02",
+-				"version": float64(6.0),
+-			},
+-			map[string]interface{}{
+-				"addr":    "1.1.2.3",
+-				"version": float64(4.0),
+-			},
+-		},
+-	},
+-	Metadata: map[string]interface{}{},
+-	Links: []interface{}{
+-		map[string]interface{}{
+-			"href": "https://dfw.servers.api.rackspacecloud.com/v2/111111/servers/25f1c7f5-e00a-4715-b355-16e24b2f4630",
+-			"rel":  "self",
+-		},
+-		map[string]interface{}{
+-			"href": "https://dfw.servers.api.rackspacecloud.com/v2/111111/servers/25f1c7f5-e00a-4715-b355-16e24b2f4630",
+-			"rel":  "bookmark",
+-		},
+-	},
+-	KeyName:   "otherkey",
+-	AdminPass: "",
+-}
+-
+-// GophercloudServer is the expected result from parsing GetOutput.
+-var GophercloudServer = os.Server{
+-	ID:         "8c65cb68-0681-4c30-bc88-6b83a8a26aee",
+-	Name:       "Gophercloud-pxpGGuey",
+-	TenantID:   "111111",
+-	UserID:     "14ae7bb21d81423694655f4dd30f2930",
+-	HostID:     "430d2ae02de0a7af77012c94778145eccf67e75b1fac0528aa10d4a7",
+-	Updated:    "2014-10-21T14:42:57Z",
+-	Created:    "2014-10-21T14:42:16Z",
+-	AccessIPv4: "1.2.4.8",
+-	AccessIPv6: "2001:4800:6666:105:2a0f:c056:f594:7777",
+-	Progress:   100,
+-	Status:     "ACTIVE",
+-	Image: map[string]interface{}{
+-		"id": "e19a734c-c7e6-443a-830c-242209c4d65d",
+-		"links": []interface{}{
+-			map[string]interface{}{
+-				"href": "https://dfw.servers.api.rackspacecloud.com/111111/images/e19a734c-c7e6-443a-830c-242209c4d65d",
+-				"rel":  "bookmark",
+-			},
+-		},
+-	},
+-	Flavor: map[string]interface{}{
+-		"id": "performance1-1",
+-		"links": []interface{}{
+-			map[string]interface{}{
+-				"href": "https://dfw.servers.api.rackspacecloud.com/111111/flavors/performance1-1",
+-				"rel":  "bookmark",
+-			},
+-		},
+-	},
+-	Addresses: map[string]interface{}{
+-		"private": []interface{}{
+-			map[string]interface{}{
+-				"addr":    "10.20.40.80",
+-				"version": float64(4.0),
+-			},
+-		},
+-		"public": []interface{}{
+-			map[string]interface{}{
+-				"addr":    "2001:4800:6666:105:2a0f:c056:f594:7777",
+-				"version": float64(6.0),
+-			},
+-			map[string]interface{}{
+-				"addr":    "1.2.4.8",
+-				"version": float64(4.0),
+-			},
+-		},
+-	},
+-	Metadata: map[string]interface{}{},
+-	Links: []interface{}{
+-		map[string]interface{}{
+-			"href": "https://dfw.servers.api.rackspacecloud.com/v2/111111/servers/8c65cb68-0681-4c30-bc88-6b83a8a26aee",
+-			"rel":  "self",
+-		},
+-		map[string]interface{}{
+-			"href": "https://dfw.servers.api.rackspacecloud.com/111111/servers/8c65cb68-0681-4c30-bc88-6b83a8a26aee",
+-			"rel":  "bookmark",
+-		},
+-	},
+-	KeyName:   "",
+-	AdminPass: "",
 -}
 -
--func log(s string) {
--	if !*quiet {
--		fmt.Println(s)
--	}
+-// CreatedServer is the partial Server struct that can be parsed from CreateOutput.
+-var CreatedServer = os.Server{
+-	ID:        "bb63327b-6a2f-34bc-b0ef-4b6d97ea637e",
+-	AdminPass: "v7tADqbE5pr9",
+-	Links:     []interface{}{},
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/14-list-addresses.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/14-list-addresses.go
+-
+-// ExpectedServerSlice is the collection of servers, in order, that should be parsed from ListOutput.
+-var ExpectedServerSlice = []os.Server{DevstackServer, PerilServer}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/requests.go
 deleted file mode 100644
-index 1d7d26b..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/14-list-addresses.go
+index 884b9cb..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/requests.go
 +++ /dev/null
-@@ -1,66 +0,0 @@
--// +build acceptance,old
--
--package main
+@@ -1,158 +0,0 @@
+-package servers
 -
 -import (
--	"flag"
--	"fmt"
--	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/openstack/compute/v2/extensions/bootfromvolume"
+-	"github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig"
+-	os "github.com/rackspace/gophercloud/openstack/compute/v2/servers"
 -)
 -
--var quiet = flag.Bool("quiet", false, "Quiet mode, for acceptance testing.  $? still indicates errors though.")
+-// CreateOpts specifies all of the options that Rackspace accepts in its Create request, including
+-// the union of all extensions that Rackspace supports.
+-type CreateOpts struct {
+-	// Name [required] is the name to assign to the newly launched server.
+-	Name string
 -
--func main() {
--	flag.Parse()
--	withIdentity(false, func(acc gophercloud.AccessProvider) {
--		withServerApi(acc, func(api gophercloud.CloudServersProvider) {
--			log("Creating server")
--			id, err := createServer(api, "", "", "", "")
--			if err != nil {
--				panic(err)
--			}
--			waitForServerState(api, id, "ACTIVE")
--			defer api.DeleteServerById(id)
+-	// ImageRef [required] is the ID or full URL to the image that contains the server's OS and initial state.
+-	// Optional if using the boot-from-volume extension.
+-	ImageRef string
 -
--			tryAllAddresses(id, api)
--			tryAddressesByNetwork("private", id, api)
+-	// FlavorRef [required] is the ID or full URL to the flavor that describes the server's specs.
+-	FlavorRef string
 -
--			log("Done")
--		})
--	})
--}
+-	// SecurityGroups [optional] lists the names of the security groups to which this server should belong.
+-	SecurityGroups []string
 -
--func tryAllAddresses(id string, api gophercloud.CloudServersProvider) {
--	log("Getting list of all addresses...")
--	addresses, err := api.ListAddresses(id)
--	if (err != nil) && (err != gophercloud.WarnUnauthoritative) {
--		panic(err)
--	}
--	if err == gophercloud.WarnUnauthoritative {
--		log("Uh oh -- got a response back, but it's not authoritative for some reason.")
--	}
--	if !*quiet {
--		fmt.Println("Addresses:")
--		fmt.Printf("%+v\n", addresses)
--	}
--}
+-	// UserData [optional] contains configuration information or scripts to use upon launch.
+-	// Create will base64-encode it for you.
+-	UserData []byte
 -
--func tryAddressesByNetwork(networkLabel string, id string, api gophercloud.CloudServersProvider) {
--	log("Getting list of addresses on", networkLabel, "network...")
--	network, err := api.ListAddressesByNetwork(id, networkLabel)
--	if (err != nil) && (err != gophercloud.WarnUnauthoritative) {
--		panic(err)
--	}
--	if err == gophercloud.WarnUnauthoritative {
--		log("Uh oh -- got a response back, but it's not authoritative for some reason.")
--	}
--	for _, addr := range network[networkLabel] {
--		log("Address:", addr.Addr, "  IPv", addr.Version)
--	}
--}
+-	// AvailabilityZone [optional] in which to launch the server.
+-	AvailabilityZone string
 -
--func log(s ...interface{}) {
--	if !*quiet {
--		fmt.Println(s...)
--	}
--}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/15-list-keypairs.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/15-list-keypairs.go
-deleted file mode 100644
-index 1a617ed..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/15-list-keypairs.go
-+++ /dev/null
-@@ -1,32 +0,0 @@
--// +build acceptance,old
+-	// Networks [optional] dictates how this server will be attached to available networks.
+-	// By default, the server will be attached to all isolated networks for the tenant.
+-	Networks []os.Network
 -
--package main
+-	// Metadata [optional] contains key-value pairs (up to 255 bytes each) to attach to the server.
+-	Metadata map[string]string
 -
--import (
--	"flag"
--	"fmt"
--	"github.com/rackspace/gophercloud"
--)
+-	// Personality [optional] includes the path and contents of a file to inject into the server at launch.
+-	// The maximum size of the file is 255 bytes (decoded).
+-	Personality []byte
 -
--var quiet = flag.Bool("quiet", false, "Quiet mode for acceptance testing.  $? non-zero on error though.")
--var rgn = flag.String("r", "", "Datacenter region to interrogate.  Leave blank for provider-default region.")
+-	// ConfigDrive [optional] enables metadata injection through a configuration drive.
+-	ConfigDrive bool
 -
--func main() {
--	flag.Parse()
+-	// Rackspace-specific extensions begin here.
 -
--	withIdentity(false, func(auth gophercloud.AccessProvider) {
--		withServerApi(auth, func(servers gophercloud.CloudServersProvider) {
--			keypairs, err := servers.ListKeyPairs()
--			if err != nil {
--				panic(err)
--			}
+-	// KeyPair [optional] specifies the name of the SSH KeyPair to be injected into the newly launched
+-	// server. See the "keypairs" extension in OpenStack compute v2.
+-	KeyPair string
 -
--			if !*quiet {
--				fmt.Println("name,fingerprint,publickey")
--				for _, key := range keypairs {
--					fmt.Printf("%s,%s,%s\n", key.Name, key.FingerPrint, key.PublicKey)
--				}
--			}
--		})
--	})
+-	// DiskConfig [optional] controls how the created server's disk is partitioned. See the "diskconfig"
+-	// extension in OpenStack compute v2.
+-	DiskConfig diskconfig.DiskConfig
+-
+-	// BlockDevice [optional] will create the server from a volume, which is created from an image,
+-	// a snapshot, or an another volume.
+-	BlockDevice []bootfromvolume.BlockDevice
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/16-create-delete-keypair.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/16-create-delete-keypair.go
-deleted file mode 100644
-index f59e51c..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/16-create-delete-keypair.go
-+++ /dev/null
-@@ -1,45 +0,0 @@
--// +build acceptance,old
 -
--package main
+-// ToServerCreateMap constructs a request body using all of the OpenStack extensions that are
+-// active on Rackspace.
+-func (opts CreateOpts) ToServerCreateMap() (map[string]interface{}, error) {
+-	base := os.CreateOpts{
+-		Name:             opts.Name,
+-		ImageRef:         opts.ImageRef,
+-		FlavorRef:        opts.FlavorRef,
+-		SecurityGroups:   opts.SecurityGroups,
+-		UserData:         opts.UserData,
+-		AvailabilityZone: opts.AvailabilityZone,
+-		Networks:         opts.Networks,
+-		Metadata:         opts.Metadata,
+-		Personality:      opts.Personality,
+-		ConfigDrive:      opts.ConfigDrive,
+-	}
 -
--import (
--	"flag"
--	"fmt"
--	"github.com/rackspace/gophercloud"
--)
+-	drive := diskconfig.CreateOptsExt{
+-		CreateOptsBuilder: base,
+-		DiskConfig:        opts.DiskConfig,
+-	}
 -
--var quiet = flag.Bool("quiet", false, "Quiet mode for acceptance testing.  $? non-zero on error though.")
--var rgn = flag.String("r", "", "Datacenter region to interrogate.  Leave blank for provider-default region.")
+-	res, err := drive.ToServerCreateMap()
+-	if err != nil {
+-		return nil, err
+-	}
 -
--func main() {
--	flag.Parse()
+-	if len(opts.BlockDevice) != 0 {
+-		bfv := bootfromvolume.CreateOptsExt{
+-			CreateOptsBuilder: drive,
+-			BlockDevice:       opts.BlockDevice,
+-		}
 -
--	withIdentity(false, func(auth gophercloud.AccessProvider) {
--		withServerApi(auth, func(servers gophercloud.CloudServersProvider) {
--			name := randomString("ACPTTEST", 16)
--			kp := gophercloud.NewKeyPair{
--				Name: name,
--			}
--			keypair, err := servers.CreateKeyPair(kp)
--			if err != nil {
--				panic(err)
--			}
--			if !*quiet {
--				fmt.Printf("%s,%s,%s\n", keypair.Name, keypair.FingerPrint, keypair.PublicKey)
--			}
+-		res, err = bfv.ToServerCreateMap()
+-		if err != nil {
+-			return nil, err
+-		}
+-	}
 -
--			keypair, err = servers.ShowKeyPair(name)
--			if err != nil {
--				panic(err)
--			}
--			if !*quiet {
--				fmt.Printf("%s,%s,%s\n", keypair.Name, keypair.FingerPrint, keypair.PublicKey)
--			}
+-	// key_name doesn't actually come from the extension (or at least isn't documented there) so
+-	// we need to add it manually.
+-	serverMap := res["server"].(map[string]interface{})
+-	serverMap["key_name"] = opts.KeyPair
 -
--			err = servers.DeleteKeyPair(name)
--			if err != nil {
--				panic(err)
--			}
--		})
--	})
+-	return res, nil
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/17-create-delete-image.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/17-create-delete-image.go
-deleted file mode 100644
-index b3d80a3..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/17-create-delete-image.go
-+++ /dev/null
-@@ -1,52 +0,0 @@
--// +build acceptance,old
 -
--package main
+-// RebuildOpts represents all of the configuration options used in a server rebuild operation that
+-// are supported by Rackspace.
+-type RebuildOpts struct {
+-	// Required. The ID of the image you want your server to be provisioned on
+-	ImageID string
 -
--import (
--	"flag"
--	"fmt"
--	"github.com/rackspace/gophercloud"
--)
+-	// Name to set the server to
+-	Name string
 -
--var quiet = flag.Bool("quiet", false, "Quiet mode for acceptance testing.  $? non-zero on error though.")
--var rgn = flag.String("r", "", "Datacenter region to interrogate.  Leave blank for provider-default region.")
+-	// Required. The server's admin password
+-	AdminPass string
 -
--func main() {
--	flag.Parse()
+-	// AccessIPv4 [optional] provides a new IPv4 address for the instance.
+-	AccessIPv4 string
 -
--	withIdentity(false, func(auth gophercloud.AccessProvider) {
--		withServerApi(auth, func(servers gophercloud.CloudServersProvider) {
--			log("Creating server")
--			serverId, err := createServer(servers, "", "", "", "")
--			if err != nil {
--				panic(err)
--			}
--			waitForServerState(servers, serverId, "ACTIVE")
+-	// AccessIPv6 [optional] provides a new IPv6 address for the instance.
+-	AccessIPv6 string
 -
--			log("Creating image")
--			name := randomString("ACPTTEST", 16)
--			createImage := gophercloud.CreateImage{
--				Name: name,
--			}
--			imageId, err := servers.CreateImage(serverId, createImage)
--			if err != nil {
--				panic(err)
--			}
--			waitForImageState(servers, imageId, "ACTIVE")
+-	// Metadata [optional] contains key-value pairs (up to 255 bytes each) to attach to the server.
+-	Metadata map[string]string
 -
--			log("Deleting server")
--			servers.DeleteServerById(serverId)
+-	// Personality [optional] includes the path and contents of a file to inject into the server at launch.
+-	// The maximum size of the file is 255 bytes (decoded).
+-	Personality []byte
 -
--			log("Deleting image")
--			servers.DeleteImageById(imageId)
+-	// Rackspace-specific stuff begins here.
 -
--			log("Done")
--		})
--	})
+-	// DiskConfig [optional] controls how the created server's disk is partitioned. See the "diskconfig"
+-	// extension in OpenStack compute v2.
+-	DiskConfig diskconfig.DiskConfig
 -}
 -
--func log(s string) {
--	if !*quiet {
--		fmt.Println(s)
+-// ToServerRebuildMap constructs a request body using all of the OpenStack extensions that are
+-// active on Rackspace.
+-func (opts RebuildOpts) ToServerRebuildMap() (map[string]interface{}, error) {
+-	base := os.RebuildOpts{
+-		ImageID:     opts.ImageID,
+-		Name:        opts.Name,
+-		AdminPass:   opts.AdminPass,
+-		AccessIPv4:  opts.AccessIPv4,
+-		AccessIPv6:  opts.AccessIPv6,
+-		Metadata:    opts.Metadata,
+-		Personality: opts.Personality,
+-	}
+-
+-	drive := diskconfig.RebuildOptsExt{
+-		RebuildOptsBuilder: base,
+-		DiskConfig:         opts.DiskConfig,
 -	}
+-
+-	return drive.ToServerRebuildMap()
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/18-osutil-authentication.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/18-osutil-authentication.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/requests_test.go
 deleted file mode 100644
-index 01ff4e9..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/18-osutil-authentication.go
+index 3c0f806..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/servers/requests_test.go
 +++ /dev/null
-@@ -1,19 +0,0 @@
--// +build acceptance,old
--
--package main
+@@ -1,57 +0,0 @@
+-package servers
 -
 -import (
--	"github.com/rackspace/gophercloud"
--	"github.com/rackspace/gophercloud/osutil"
+-	"testing"
+-
+-	"github.com/rackspace/gophercloud/openstack/compute/v2/extensions/diskconfig"
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--func main() {
--	provider, authOptions, err := osutil.AuthOptions()
--	if err != nil {
--		panic(err)
+-func TestCreateOpts(t *testing.T) {
+-	opts := CreateOpts{
+-		Name:       "createdserver",
+-		ImageRef:   "image-id",
+-		FlavorRef:  "flavor-id",
+-		KeyPair:    "mykey",
+-		DiskConfig: diskconfig.Manual,
 -	}
--	_, err = gophercloud.Authenticate(provider, authOptions)
--	if err != nil {
--		panic(err)
+-
+-	expected := `
+-	{
+-		"server": {
+-			"name": "createdserver",
+-			"imageRef": "image-id",
+-			"flavorRef": "flavor-id",
+-			"key_name": "mykey",
+-			"OS-DCF:diskConfig": "MANUAL"
+-		}
+-	}
+-	`
+-	actual, err := opts.ToServerCreateMap()
+-	th.AssertNoErr(t, err)
+-	th.CheckJSONEquals(t, expected, actual)
+-}
+-
+-func TestRebuildOpts(t *testing.T) {
+-	opts := RebuildOpts{
+-		Name:       "rebuiltserver",
+-		AdminPass:  "swordfish",
+-		ImageID:    "asdfasdfasdf",
+-		DiskConfig: diskconfig.Auto,
+-	}
+-
+-	actual, err := opts.ToServerRebuildMap()
+-	th.AssertNoErr(t, err)
+-
+-	expected := `
+-	{
+-		"rebuild": {
+-			"name": "rebuiltserver",
+-			"imageRef": "asdfasdfasdf",
+-			"adminPass": "swordfish",
+-			"OS-DCF:diskConfig": "AUTO"
+-		}
 -	}
+-	`
+-	th.CheckJSONEquals(t, expected, actual)
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/19-list-addresses-0.1.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/19-list-addresses-0.1.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/requests.go
 deleted file mode 100644
-index d60557b..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/19-list-addresses-0.1.go
+index bfe3487..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/requests.go
 +++ /dev/null
-@@ -1,58 +0,0 @@
--// +build acceptance,old
--
--package main
+@@ -1,51 +0,0 @@
+-package virtualinterfaces
 -
 -import (
--	"flag"
--	"fmt"
 -	"github.com/rackspace/gophercloud"
--)
--
--var quiet = flag.Bool("quiet", false, "Quiet mode, for acceptance testing.  $? still indicates errors though.")
+-	"github.com/rackspace/gophercloud/pagination"
 -
--func main() {
--	flag.Parse()
--	withIdentity(false, func(acc gophercloud.AccessProvider) {
--		withServerApi(acc, func(api gophercloud.CloudServersProvider) {
--			log("Creating server")
--			id, err := createServer(api, "", "", "", "")
--			if err != nil {
--				panic(err)
--			}
--			waitForServerState(api, id, "ACTIVE")
--			defer api.DeleteServerById(id)
+-	"github.com/racker/perigee"
+-)
 -
--			tryAllAddresses(id, api)
+-// List returns a Pager which allows you to iterate over a collection of
+-// networks. It accepts a ListOpts struct, which allows you to filter and sort
+-// the returned collection for greater efficiency.
+-func List(c *gophercloud.ServiceClient, instanceID string) pagination.Pager {
+-	createPage := func(r pagination.PageResult) pagination.Page {
+-		return VirtualInterfacePage{pagination.SinglePageBase(r)}
+-	}
 -
--			log("Done")
--		})
--	})
+-	return pagination.NewPager(c, listURL(c, instanceID), createPage)
 -}
 -
--func tryAllAddresses(id string, api gophercloud.CloudServersProvider) {
--	log("Getting the server instance")
--	s, err := api.ServerById(id)
--	if err != nil {
--		panic(err)
--	}
+-// Create creates a new virtual interface for a network and attaches the network
+-// to the server instance.
+-func Create(c *gophercloud.ServiceClient, instanceID, networkID string) CreateResult {
+-	var res CreateResult
 -
--	log("Getting the complete set of pools")
--	ps, err := s.AllAddressPools()
--	if err != nil {
--		panic(err)
+-	reqBody := map[string]map[string]string{
+-		"virtual_interface": {
+-			"network_id": networkID,
+-		},
 -	}
 -
--	log("Listing IPs for each pool")
--	for k, v := range ps {
--		log(fmt.Sprintf("  Pool %s", k))
--		for _, a := range v {
--			log(fmt.Sprintf("    IP: %s, Version: %d", a.Addr, a.Version))
--		}
--	}
+-	// Send request to API
+-	_, res.Err = perigee.Request("POST", createURL(c, instanceID), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		ReqBody:     &reqBody,
+-		Results:     &res.Body,
+-		OkCodes:     []int{200, 201, 202},
+-	})
+-	return res
 -}
 -
--func log(s ...interface{}) {
--	if !*quiet {
--		fmt.Println(s...)
--	}
+-// Delete deletes the interface with interfaceID attached to the instance with
+-// instanceID.
+-func Delete(c *gophercloud.ServiceClient, instanceID, interfaceID string) DeleteResult {
+-	var res DeleteResult
+-	_, res.Err = perigee.Request("DELETE", deleteURL(c, instanceID, interfaceID), perigee.Options{
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{200, 204},
+-	})
+-	return res
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/99-delete-server.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/99-delete-server.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/requests_test.go
 deleted file mode 100644
-index 3e38ba4..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/99-delete-server.go
+index d40af9c..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/requests_test.go
 +++ /dev/null
-@@ -1,48 +0,0 @@
--// +build acceptance,old
--
--package main
+@@ -1,165 +0,0 @@
+-package virtualinterfaces
 -
 -import (
--	"flag"
 -	"fmt"
--	"github.com/rackspace/gophercloud"
--)
+-	"net/http"
+-	"testing"
 -
--var quiet = flag.Bool("quiet", false, "Quiet operation for acceptance tests.  $? non-zero if problem.")
--var region = flag.String("r", "", "Datacenter region.  Leave blank for provider-default region.")
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--func main() {
--	flag.Parse()
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	withIdentity(false, func(auth gophercloud.AccessProvider) {
--		withServerApi(auth, func(servers gophercloud.CloudServersProvider) {
--			// Grab a listing of all servers.
--			ss, err := servers.ListServers()
--			if err != nil {
--				panic(err)
--			}
+-	th.Mux.HandleFunc("/servers/12345/os-virtual-interfacesv2", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "GET")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
 -
--			// And for each one that starts with the ACPTTEST prefix, delete it.
--			// These are likely left-overs from previously running acceptance tests.
--			// Note that 04-create-servers.go is intended to leak servers by intention,
--			// so as to test this code.  :)
--			n := 0
--			for _, s := range ss {
--				if len(s.Name) < 8 {
--					continue
--				}
--				if s.Name[0:8] == "ACPTTEST" {
--					err := servers.DeleteServerById(s.Id)
--					if err != nil {
--						panic(err)
--					}
--					n++
--				}
--			}
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusOK)
 -
--			if !*quiet {
--				fmt.Printf("%d servers removed.\n", n)
--			}
--		})
--	})
+-		fmt.Fprintf(w, `
+-{
+-    "virtual_interfaces": [
+-        {
+-            "id": "de7c6d53-b895-4b4a-963c-517ccb0f0775",
+-            "ip_addresses": [
+-                {
+-                    "address": "192.168.0.2",
+-                    "network_id": "f212726e-6321-4210-9bae-a13f5a33f83f",
+-                    "network_label": "superprivate_xml"
+-                }
+-            ],
+-            "mac_address": "BC:76:4E:04:85:20"
+-        },
+-        {
+-            "id": "e14e789d-3b98-44a6-9c2d-c23eb1d1465c",
+-            "ip_addresses": [
+-                {
+-                    "address": "10.181.1.30",
+-                    "network_id": "3b324a1b-31b8-4db5-9fe5-4a2067f60297",
+-                    "network_label": "private"
+-                }
+-            ],
+-            "mac_address": "BC:76:4E:04:81:55"
+-        }
+-    ]
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/libargs.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/libargs.go
-deleted file mode 100644
-index cf234e7..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/acceptance/libargs.go
-+++ /dev/null
-@@ -1,239 +0,0 @@
--// +build acceptance,old
+-      `)
+-	})
 -
--package main
+-	client := fake.ServiceClient()
+-	count := 0
 -
--import (
--	"crypto/rand"
--	"fmt"
--	"github.com/rackspace/gophercloud"
--	"os"
--	"strings"
--	"time"
--)
+-	err := List(client, "12345").EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractVirtualInterfaces(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract networks: %v", err)
+-			return false, err
+-		}
 -
--// getCredentials will verify existence of needed credential information
--// provided through environment variables.  This function will not return
--// if at least one piece of required information is missing.
--func getCredentials() (provider, username, password, apiKey string) {
--	provider = os.Getenv("SDK_PROVIDER")
--	username = os.Getenv("SDK_USERNAME")
--	password = os.Getenv("SDK_PASSWORD")
--	apiKey = os.Getenv("SDK_API_KEY")
--	var authURL = os.Getenv("OS_AUTH_URL")
--
--	if (provider == "") || (username == "") || (password == "") {
--		fmt.Fprintf(os.Stderr, "One or more of the following environment variables aren't set:\n")
--		fmt.Fprintf(os.Stderr, "  SDK_PROVIDER=\"%s\"\n", provider)
--		fmt.Fprintf(os.Stderr, "  SDK_USERNAME=\"%s\"\n", username)
--		fmt.Fprintf(os.Stderr, "  SDK_PASSWORD=\"%s\"\n", password)
--		os.Exit(1)
--	}
+-		expected := []VirtualInterface{
+-			VirtualInterface{
+-				MACAddress: "BC:76:4E:04:85:20",
+-				IPAddresses: []IPAddress{
+-					IPAddress{
+-						Address:      "192.168.0.2",
+-						NetworkID:    "f212726e-6321-4210-9bae-a13f5a33f83f",
+-						NetworkLabel: "superprivate_xml",
+-					},
+-				},
+-				ID: "de7c6d53-b895-4b4a-963c-517ccb0f0775",
+-			},
+-			VirtualInterface{
+-				MACAddress: "BC:76:4E:04:81:55",
+-				IPAddresses: []IPAddress{
+-					IPAddress{
+-						Address:      "10.181.1.30",
+-						NetworkID:    "3b324a1b-31b8-4db5-9fe5-4a2067f60297",
+-						NetworkLabel: "private",
+-					},
+-				},
+-				ID: "e14e789d-3b98-44a6-9c2d-c23eb1d1465c",
+-			},
+-		}
 -
--	if strings.Contains(provider, "rackspace") && (authURL != "") {
--		provider = authURL + "/v2.0/tokens"
--	}
+-		th.CheckDeepEquals(t, expected, actual)
 -
--	return
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, 1, count)
 -}
 -
--// 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)
+-func TestCreate(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-
+-	th.Mux.HandleFunc("/servers/12345/os-virtual-interfacesv2", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "POST")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Content-Type", "application/json")
+-		th.TestHeader(t, r, "Accept", "application/json")
+-		th.TestJSONRequest(t, r, `
+-{
+-    "virtual_interface": {
+-        "network_id": "6789"
+-    }
 -}
+-      `)
 -
--// aSuitableImage finds a minimal image for use in dynamically creating servers.
--// If none can be found, this function will panic.
--func aSuitableImage(api gophercloud.CloudServersProvider) string {
--	images, err := api.ListImages()
--	if err != nil {
--		panic(err)
--	}
+-		w.Header().Add("Content-Type", "application/json")
+-		w.WriteHeader(http.StatusCreated)
 -
--	// TODO(sfalvo):
--	// Works for Rackspace, might not work for your provider!
--	// Need to figure out why ListImages() provides 0 values for
--	// Ram and Disk fields.
--	//
--	// Until then, just return Ubuntu 12.04 LTS.
--	for i := 0; i < len(images); i++ {
--		if strings.Contains(images[i].Name, "Ubuntu 12.04 LTS") {
--			return images[i].Id
--		}
+-		fmt.Fprintf(w, `{
+-      "virtual_interfaces": [
+-        {
+-          "id": "de7c6d53-b895-4b4a-963c-517ccb0f0775",
+-          "ip_addresses": [
+-            {
+-              "address": "192.168.0.2",
+-              "network_id": "f212726e-6321-4210-9bae-a13f5a33f83f",
+-              "network_label": "superprivate_xml"
+-            }
+-          ],
+-          "mac_address": "BC:76:4E:04:85:20"
+-        }
+-      ]
+-    }`)
+-	})
+-
+-	expected := &VirtualInterface{
+-		MACAddress: "BC:76:4E:04:85:20",
+-		IPAddresses: []IPAddress{
+-			IPAddress{
+-				Address:      "192.168.0.2",
+-				NetworkID:    "f212726e-6321-4210-9bae-a13f5a33f83f",
+-				NetworkLabel: "superprivate_xml",
+-			},
+-		},
+-		ID: "de7c6d53-b895-4b4a-963c-517ccb0f0775",
 -	}
--	panic("Image for Ubuntu 12.04 LTS not found.")
+-
+-	actual, err := Create(fake.ServiceClient(), "12345", "6789").Extract()
+-	th.AssertNoErr(t, err)
+-
+-	th.CheckDeepEquals(t, expected, actual)
 -}
 -
--// aSuitableFlavor finds the minimum flavor capable of running the test image
--// chosen by aSuitableImage.  If none can be found, this function will panic.
--func aSuitableFlavor(api gophercloud.CloudServersProvider) string {
--	flavors, err := api.ListFlavors()
--	if err != nil {
--		panic(err)
--	}
+-func TestDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
 -
--	// TODO(sfalvo):
--	// Works for Rackspace, might not work for your provider!
--	// Need to figure out why ListFlavors() provides 0 values for
--	// Ram and Disk fields.
--	//
--	// Until then, just return Ubuntu 12.04 LTS.
--	for i := 0; i < len(flavors); i++ {
--		if flavors[i].Id == "2" {
--			return flavors[i].Id
--		}
--	}
--	panic("Flavor 2 (512MB 1-core 20GB machine) not found.")
+-	th.Mux.HandleFunc("/servers/12345/os-virtual-interfacesv2/6789", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		w.WriteHeader(http.StatusNoContent)
+-	})
+-
+-	res := Delete(fake.ServiceClient(), "12345", "6789")
+-	th.AssertNoErr(t, res.Err)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/results.go
+deleted file mode 100644
+index 26fa7f3..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/results.go
++++ /dev/null
+@@ -1,81 +0,0 @@
+-package virtualinterfaces
 -
--// createServer creates a new server in a manner compatible with acceptance testing.
--// In particular, it ensures that the name of the server always starts with "ACPTTEST--",
--// which the delete servers acceptance test relies on to identify servers to delete.
--// Passing in empty image and flavor references will force the use of reasonable defaults.
--// An empty name string will result in a dynamically created name prefixed with "ACPTTEST--".
--// A blank admin password will cause a password to be automatically generated; however,
--// at present no means of recovering this password exists, as no acceptance tests yet require
--// this data.
--func createServer(servers gophercloud.CloudServersProvider, imageRef, flavorRef, name, adminPass string) (string, error) {
--	if imageRef == "" {
--		imageRef = aSuitableImage(servers)
--	}
+-import (
+-	"github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	if flavorRef == "" {
--		flavorRef = aSuitableFlavor(servers)
--	}
+-type commonResult struct {
+-	gophercloud.Result
+-}
 -
--	if len(name) < 1 {
--		name = randomString("ACPTTEST", 16)
+-// Extract is a function that accepts a result and extracts a network resource.
+-func (r commonResult) Extract() (*VirtualInterface, error) {
+-	if r.Err != nil {
+-		return nil, r.Err
 -	}
 -
--	if (len(name) < 8) || (name[0:8] != "ACPTTEST") {
--		name = fmt.Sprintf("ACPTTEST--%s", name)
+-	var res struct {
+-		VirtualInterfaces []VirtualInterface `mapstructure:"virtual_interfaces" json:"virtual_interfaces"`
 -	}
 -
--	newServer, err := servers.CreateServer(gophercloud.NewServer{
--		Name:      name,
--		ImageRef:  imageRef,
--		FlavorRef: flavorRef,
--		AdminPass: adminPass,
--	})
+-	err := mapstructure.Decode(r.Body, &res)
 -
--	if err != nil {
--		return "", err
--	}
+-	return &res.VirtualInterfaces[0], err
+-}
 -
--	return newServer.Id, nil
+-// CreateResult represents the result of a create operation.
+-type CreateResult struct {
+-	commonResult
 -}
 -
--// findAlternativeFlavor locates a flavor to resize a server to.  It is guaranteed to be different
--// than what aSuitableFlavor() returns.  If none could be found, this function will panic.
--func findAlternativeFlavor() string {
--	return "3" // 1GB image, up from 512MB image
+-// DeleteResult represents the result of a delete operation.
+-type DeleteResult struct {
+-	gophercloud.ErrResult
 -}
 -
--// findAlternativeImage locates an image to resize or rebuild a server with.  It is guaranteed to be
--// different than what aSuitableImage() returns.  If none could be found, this function will panic.
--func findAlternativeImage() string {
--	return "c6f9c411-e708-4952-91e5-62ded5ea4d3e"
+-// IPAddress represents a vitual address attached to a VirtualInterface.
+-type IPAddress struct {
+-	Address      string `mapstructure:"address" json:"address"`
+-	NetworkID    string `mapstructure:"network_id" json:"network_id"`
+-	NetworkLabel string `mapstructure:"network_label" json:"network_label"`
 -}
 -
--// withIdentity authenticates the user against the provider's identity service, and provides an
--// accessor for additional services.
--func withIdentity(ar bool, f func(gophercloud.AccessProvider)) {
--	_, _, _, apiKey := getCredentials()
--	if len(apiKey) == 0 {
--		withPasswordIdentity(ar, f)
--	} else {
--		withAPIKeyIdentity(ar, f)
--	}
+-// VirtualInterface represents a virtual interface.
+-type VirtualInterface struct {
+-	// UUID for the virtual interface
+-	ID string `mapstructure:"id" json:"id"`
+-
+-	MACAddress string `mapstructure:"mac_address" json:"mac_address"`
+-
+-	IPAddresses []IPAddress `mapstructure:"ip_addresses" json:"ip_addresses"`
 -}
 -
--func withPasswordIdentity(ar bool, f func(gophercloud.AccessProvider)) {
--	provider, username, password, _ := getCredentials()
--	acc, err := gophercloud.Authenticate(
--		provider,
--		gophercloud.AuthOptions{
--			Username:    username,
--			Password:    password,
--			AllowReauth: ar,
--		},
--	)
+-// VirtualInterfacePage is the page returned by a pager when traversing over a
+-// collection of virtual interfaces.
+-type VirtualInterfacePage struct {
+-	pagination.SinglePageBase
+-}
+-
+-// IsEmpty returns true if the NetworkPage contains no Networks.
+-func (r VirtualInterfacePage) IsEmpty() (bool, error) {
+-	networks, err := ExtractVirtualInterfaces(r)
 -	if err != nil {
--		panic(err)
+-		return true, err
 -	}
--
--	f(acc)
+-	return len(networks) == 0, nil
 -}
 -
--func withAPIKeyIdentity(ar bool, f func(gophercloud.AccessProvider)) {
--	provider, username, _, apiKey := getCredentials()
--	acc, err := gophercloud.Authenticate(
--		provider,
--		gophercloud.AuthOptions{
--			Username:    username,
--			ApiKey:      apiKey,
--			AllowReauth: ar,
--		},
--	)
--	if err != nil {
--		panic(err)
+-// ExtractVirtualInterfaces accepts a Page struct, specifically a VirtualInterfacePage struct,
+-// and extracts the elements into a slice of VirtualInterface structs. In other words,
+-// a generic collection is mapped into a relevant slice.
+-func ExtractVirtualInterfaces(page pagination.Page) ([]VirtualInterface, error) {
+-	var resp struct {
+-		VirtualInterfaces []VirtualInterface `mapstructure:"virtual_interfaces" json:"virtual_interfaces"`
 -	}
 -
--	f(acc)
+-	err := mapstructure.Decode(page.(VirtualInterfacePage).Body, &resp)
+-
+-	return resp.VirtualInterfaces, err
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/urls.go
+deleted file mode 100644
+index 9e5693e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/urls.go
++++ /dev/null
+@@ -1,15 +0,0 @@
+-package virtualinterfaces
 -
--// withServerApi acquires the cloud servers API.
--func withServerApi(acc gophercloud.AccessProvider, f func(gophercloud.CloudServersProvider)) {
--	api, err := gophercloud.ServersApi(acc, gophercloud.ApiCriteria{
--		Name:      "cloudServersOpenStack",
--		VersionId: "2",
--		UrlChoice: gophercloud.PublicURL,
--	})
--	if err != nil {
--		panic(err)
--	}
+-import "github.com/rackspace/gophercloud"
 -
--	f(api)
+-func listURL(c *gophercloud.ServiceClient, instanceID string) string {
+-	return c.ServiceURL("servers", instanceID, "os-virtual-interfacesv2")
 -}
 -
--// waitForServerState polls, every 10 seconds, for a given server to appear in the indicated state.
--// This call will block forever if it never appears in the desired state, so if a timeout is required,
--// make sure to call this function in a goroutine.
--func waitForServerState(api gophercloud.CloudServersProvider, id, state string) error {
--	for {
--		s, err := api.ServerById(id)
--		if err != nil {
--			return err
--		}
--		if s.Status == state {
--			return nil
--		}
--		time.Sleep(10 * time.Second)
--	}
--	panic("Impossible")
+-func createURL(c *gophercloud.ServiceClient, instanceID string) string {
+-	return c.ServiceURL("servers", instanceID, "os-virtual-interfacesv2")
 -}
 -
--// waitForImageState polls, every 10 seconds, for a given image to appear in the indicated state.
--// This call will block forever if it never appears in the desired state, so if a timeout is required,
--// make sure to call this function in a goroutine.
--func waitForImageState(api gophercloud.CloudServersProvider, id, state string) error {
--	for {
--		s, err := api.ImageById(id)
--		if err != nil {
--			return err
--		}
--		if s.Status == state {
--			return nil
--		}
--		time.Sleep(10 * time.Second)
--	}
--	panic("Impossible")
+-func deleteURL(c *gophercloud.ServiceClient, instanceID, interfaceID string) string {
+-	return c.ServiceURL("servers", instanceID, "os-virtual-interfacesv2", interfaceID)
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/api_fetch.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/api_fetch.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/urls_test.go
 deleted file mode 100644
-index 196047e..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/api_fetch.go
+index 6732e4e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/compute/v2/virtualinterfaces/urls_test.go
 +++ /dev/null
-@@ -1,49 +0,0 @@
--package gophercloud
+@@ -1,32 +0,0 @@
+-package virtualinterfaces
+-
+-import (
+-	"testing"
 -
--import(
-- "fmt"
-- "github.com/mitchellh/mapstructure"
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--//The default generic openstack api
--var OpenstackApi = map[string]interface{}{
--	"Type": "compute",
--	"UrlChoice": PublicURL,
--}
+-const endpoint = "http://localhost:57909/"
 -
--// Api for use with rackspace
--var RackspaceApi = map[string]interface{}{
--	"Name":      "cloudServersOpenStack",
--	"VersionId": "2",
--	"UrlChoice": PublicURL,
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint}
 -}
 -
+-func TestCreateURL(t *testing.T) {
+-	actual := createURL(endpointClient(), "12345")
+-	expected := endpoint + "servers/12345/os-virtual-interfacesv2"
+-	th.AssertEquals(t, expected, actual)
+-}
 -
--//Populates an ApiCriteria struct with the api values
--//from one of the api maps 
--func PopulateApi(variant string) (ApiCriteria, error){
--	var Api ApiCriteria
--	var variantMap map[string]interface{}
+-func TestListURL(t *testing.T) {
+-	actual := createURL(endpointClient(), "12345")
+-	expected := endpoint + "servers/12345/os-virtual-interfacesv2"
+-	th.AssertEquals(t, expected, actual)
+-}
 -
--	switch variant {
--	case "":
--		variantMap = OpenstackApi
+-func TestDeleteURL(t *testing.T) {
+-	actual := deleteURL(endpointClient(), "12345", "6789")
+-	expected := endpoint + "servers/12345/os-virtual-interfacesv2/6789"
+-	th.AssertEquals(t, expected, actual)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/extensions/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/extensions/delegate.go
+deleted file mode 100644
+index fc547cd..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/extensions/delegate.go
++++ /dev/null
+@@ -1,24 +0,0 @@
+-package extensions
 -
--	case "openstack":
--		variantMap = OpenstackApi
+-import (
+-	"github.com/rackspace/gophercloud"
+-	common "github.com/rackspace/gophercloud/openstack/common/extensions"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	case "rackspace": 
--		variantMap = RackspaceApi
+-// ExtractExtensions accepts a Page struct, specifically an ExtensionPage struct, and extracts the
+-// elements into a slice of os.Extension structs.
+-func ExtractExtensions(page pagination.Page) ([]common.Extension, error) {
+-	return common.ExtractExtensions(page)
+-}
 -
--	default:
--		var err = fmt.Errorf(
--			"PopulateApi: Unknown variant %# v; legal values: \"openstack\", \"rackspace\"", variant)
--		return Api, err
--	}
+-// Get retrieves information for a specific extension using its alias.
+-func Get(c *gophercloud.ServiceClient, alias string) common.GetResult {
+-	return common.Get(c, alias)
+-}
 -
--	err := mapstructure.Decode(variantMap,&Api)
--		if err != nil{
--			return Api,err
--		}
--	return Api, err 
+-// List returns a Pager which allows you to iterate over the full collection of extensions.
+-// It does not accept query parameters.
+-func List(c *gophercloud.ServiceClient) pagination.Pager {
+-	return common.List(c)
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/authenticate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/authenticate.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/extensions/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/extensions/delegate_test.go
 deleted file mode 100644
-index ff609aa..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/authenticate.go
+index e30f794..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/extensions/delegate_test.go
 +++ /dev/null
-@@ -1,257 +0,0 @@
--package gophercloud
+@@ -1,39 +0,0 @@
+-package extensions
 -
 -import (
--	"fmt"
--	"github.com/racker/perigee"
--)
+-	"testing"
 -
--// AuthOptions lets anyone calling Authenticate() supply the required access credentials.
--// At present, only Identity V2 API support exists; therefore, only Username, Password,
--// and optionally, TenantId are provided.  If future Identity API versions become available,
--// alternative fields unique to those versions may appear here.
--type AuthOptions struct {
--	// Username and Password are required if using Identity V2 API.
--	// Consult with your provider's control panel to discover your
--	// account's username and password.
--	Username, Password string
+-	common "github.com/rackspace/gophercloud/openstack/common/extensions"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--	// ApiKey used for providers that support Api Key authentication
--	ApiKey string
+-func TestList(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	common.HandleListExtensionsSuccessfully(t)
 -
--	// The TenantId field is optional for the Identity V2 API.
--	TenantId string
+-	count := 0
 -
--	// The TenantName can be specified instead of the TenantId
--	TenantName string
+-	err := List(fake.ServiceClient()).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractExtensions(page)
+-		th.AssertNoErr(t, err)
+-		th.AssertDeepEquals(t, common.ExpectedExtensions, actual)
 -
--	// AllowReauth should be set to true if you grant permission for Gophercloud to cache
--	// your credentials in memory, and to allow Gophercloud to attempt to re-authenticate
--	// automatically if/when your token expires.  If you set it to false, it will not cache
--	// these settings, but re-authentication will not be possible.  This setting defaults
--	// to false.
--	AllowReauth bool
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, 1, count)
 -}
 -
--// AuthContainer provides a JSON encoding wrapper for passing credentials to the Identity
--// service.  You will not work with this structure directly.
--type AuthContainer struct {
--	Auth Auth `json:"auth"`
--}
+-func TestGet(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	common.HandleGetExtensionSuccessfully(t)
 -
--// Auth provides a JSON encoding wrapper for passing credentials to the Identity
--// service.  You will not work with this structure directly.
--type Auth struct {
--	PasswordCredentials *PasswordCredentials `json:"passwordCredentials,omitempty"`
--	ApiKeyCredentials   *ApiKeyCredentials   `json:"RAX-KSKEY:apiKeyCredentials,omitempty"`
--	TenantId            string               `json:"tenantId,omitempty"`
--	TenantName          string               `json:"tenantName,omitempty"`
+-	actual, err := Get(fake.ServiceClient(), "agent").Extract()
+-	th.AssertNoErr(t, err)
+-	th.CheckDeepEquals(t, common.SingleExtension, actual)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/extensions/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/extensions/doc.go
+deleted file mode 100644
+index b02a95b..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/extensions/doc.go
++++ /dev/null
+@@ -1,3 +0,0 @@
+-// Package extensions provides information and interaction with the all the
+-// extensions available for the Rackspace Identity service.
+-package extensions
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tenants/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tenants/delegate.go
+deleted file mode 100644
+index 6cdd0cf..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tenants/delegate.go
++++ /dev/null
+@@ -1,17 +0,0 @@
+-package tenants
 -
--// PasswordCredentials provides a JSON encoding wrapper for passing credentials to the Identity
--// service.  You will not work with this structure directly.
--type PasswordCredentials struct {
--	Username string `json:"username"`
--	Password string `json:"password"`
--}
+-import (
+-	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack/identity/v2/tenants"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--type ApiKeyCredentials struct {
--	Username string `json:"username"`
--	ApiKey   string `json:"apiKey"`
+-// ExtractTenants interprets a page of List results as a more usable slice of Tenant structs.
+-func ExtractTenants(page pagination.Page) ([]os.Tenant, error) {
+-	return os.ExtractTenants(page)
 -}
 -
--// Access encapsulates the API token and its relevant fields, as well as the
--// services catalog that Identity API returns once authenticated.
--type Access struct {
--	Token          Token
--	ServiceCatalog []CatalogEntry
--	User           User
--	provider       Provider    `json:"-"`
--	options        AuthOptions `json:"-"`
--	context        *Context    `json:"-"`
+-// List enumerates the tenants to which the current token grants access.
+-func List(client *gophercloud.ServiceClient, opts *os.ListOpts) pagination.Pager {
+-	return os.List(client, opts)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tenants/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tenants/delegate_test.go
+deleted file mode 100644
+index eccbfe2..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tenants/delegate_test.go
++++ /dev/null
+@@ -1,28 +0,0 @@
+-package tenants
 -
--// Token encapsulates an authentication token and when it expires.  It also includes
--// tenant information if available.
--type Token struct {
--	Id, Expires string
--	Tenant      Tenant
--}
+-import (
+-	"testing"
 -
--// Tenant encapsulates tenant authentication information.  If, after authentication,
--// no tenant information is supplied, both Id and Name will be "".
--type Tenant struct {
--	Id, Name string
--}
+-	os "github.com/rackspace/gophercloud/openstack/identity/v2/tenants"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--// User encapsulates the user credentials, and provides visibility in what
--// the user can do through its role assignments.
--type User struct {
--	Id, Name          string
--	XRaxDefaultRegion string `json:"RAX-AUTH:defaultRegion"`
--	Roles             []Role
--}
+-func TestListTenants(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleListTenantsSuccessfully(t)
 -
--// Role encapsulates a permission that a user can rely on.
--type Role struct {
--	Description, Id, Name string
--}
+-	count := 0
+-	err := List(fake.ServiceClient(), nil).EachPage(func(page pagination.Page) (bool, error) {
+-		actual, err := ExtractTenants(page)
+-		th.AssertNoErr(t, err)
+-		th.CheckDeepEquals(t, os.ExpectedTenantSlice, actual)
 -
--// CatalogEntry encapsulates a service catalog record.
--type CatalogEntry struct {
--	Name, Type string
--	Endpoints  []EntryEndpoint
+-		count++
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, 1, count)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tenants/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tenants/doc.go
+deleted file mode 100644
+index c1825c2..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tenants/doc.go
++++ /dev/null
+@@ -1,3 +0,0 @@
+-// Package tenants provides information and interaction with the tenant
+-// API resource for the Rackspace Identity service.
+-package tenants
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tokens/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tokens/delegate.go
+deleted file mode 100644
+index 4f9885a..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tokens/delegate.go
++++ /dev/null
+@@ -1,60 +0,0 @@
+-package tokens
 -
--// EntryEndpoint encapsulates how to get to the API of some service.
--type EntryEndpoint struct {
--	Region, TenantId                    string
--	PublicURL, InternalURL              string
--	VersionId, VersionInfo, VersionList string
--}
+-import (
+-	"errors"
 -
--type AuthError struct {
--	StatusCode int
--}
+-	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack/identity/v2/tokens"
+-)
 -
--func (ae *AuthError) Error() string {
--	switch ae.StatusCode {
--	case 401:
--		return "Auth failed. Bad credentials."
+-var (
+-	// ErrPasswordProvided is returned if both a password and an API key are provided to Create.
+-	ErrPasswordProvided = errors.New("Please provide either a password or an API key.")
+-)
 -
--	default:
--		return fmt.Sprintf("Auth failed. Status code is: %s.", ae.StatusCode)
--	}
+-// AuthOptions wraps the OpenStack AuthOptions struct to be able to customize the request body
+-// when API key authentication is used.
+-type AuthOptions struct {
+-	os.AuthOptions
 -}
 -
--//
--func getAuthCredentials(options AuthOptions) Auth {
--	if options.ApiKey == "" {
--		return Auth{
--			PasswordCredentials: &PasswordCredentials{
--				Username: options.Username,
--				Password: options.Password,
--			},
--			TenantId:   options.TenantId,
--			TenantName: options.TenantName,
--		}
--	} else {
--		return Auth{
--			ApiKeyCredentials: &ApiKeyCredentials{
--				Username: options.Username,
--				ApiKey:   options.ApiKey,
--			},
--			TenantId:   options.TenantId,
--			TenantName: options.TenantName,
--		}
--	}
+-// WrapOptions embeds a root AuthOptions struct in a package-specific one.
+-func WrapOptions(original gophercloud.AuthOptions) AuthOptions {
+-	return AuthOptions{AuthOptions: os.WrapOptions(original)}
 -}
 -
--// papersPlease contains the common logic between authentication and re-authentication.
--// The name, obviously a joke on the process of authentication, was chosen because
--// of how many other entities exist in the program containing the word Auth or Authorization.
--// I didn't need another one.
--func (c *Context) papersPlease(p Provider, options AuthOptions) (*Access, error) {
--	var access *Access
--	access = new(Access)
+-// ToTokenCreateMap serializes an AuthOptions into a request body. If an API key is provided, it
+-// will be used, otherwise
+-func (auth AuthOptions) ToTokenCreateMap() (map[string]interface{}, error) {
+-	if auth.APIKey == "" {
+-		return auth.AuthOptions.ToTokenCreateMap()
+-	}
 -
--	if (options.Username == "") || (options.Password == "" && options.ApiKey == "") {
--		return nil, ErrCredentials
+-	// Verify that other required attributes are present.
+-	if auth.Username == "" {
+-		return nil, os.ErrUsernameRequired
 -	}
 -
--	resp, err := perigee.Request("POST", p.AuthEndpoint, perigee.Options{
--		CustomClient: c.httpClient,
--		ReqBody: &AuthContainer{
--			Auth: getAuthCredentials(options),
--		},
--		Results: &struct {
--			Access **Access `json:"access"`
--		}{
--			&access,
--		},
--	})
+-	authMap := make(map[string]interface{})
 -
--	if err == nil {
--		switch resp.StatusCode {
--		case 200:
--			access.options = options
--			access.provider = p
--			access.context = c
+-	authMap["RAX-KSKEY:apiKeyCredentials"] = map[string]interface{}{
+-		"username": auth.Username,
+-		"apiKey":   auth.APIKey,
+-	}
 -
--		default:
--			err = &AuthError {
--				StatusCode: resp.StatusCode,
--			}
--		}
+-	if auth.TenantID != "" {
+-		authMap["tenantId"] = auth.TenantID
+-	}
+-	if auth.TenantName != "" {
+-		authMap["tenantName"] = auth.TenantName
 -	}
 -
--	return access, err
+-	return map[string]interface{}{"auth": authMap}, nil
 -}
 -
--// Authenticate() grants access to the OpenStack-compatible provider API.
--//
--// Providers are identified through a unique key string.
--// See the RegisterProvider() method for more details.
--//
--// The supplied AuthOptions instance allows the client to specify only those credentials
--// relevant for the authentication request.  At present, support exists for OpenStack
--// Identity V2 API only; support for V3 will become available as soon as documentation for it
--// becomes readily available.
--//
--// For Identity V2 API requirements, you must provide at least the Username and Password
--// options.  The TenantId field is optional, and defaults to "".
--func (c *Context) Authenticate(provider string, options AuthOptions) (*Access, error) {
--	p, err := c.ProviderByName(provider)
--	if err != nil {
--		return nil, err
--	}
--	return c.papersPlease(p, options)
+-// Create authenticates to Rackspace's identity service and attempts to acquire a Token. Rather
+-// than interact with this service directly, users should generally call
+-// rackspace.AuthenticatedClient().
+-func Create(client *gophercloud.ServiceClient, auth AuthOptions) os.CreateResult {
+-	return os.Create(client, auth)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tokens/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tokens/delegate_test.go
+deleted file mode 100644
+index 6678ff4..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tokens/delegate_test.go
++++ /dev/null
+@@ -1,36 +0,0 @@
+-package tokens
 -
--// Reauthenticate attempts to reauthenticate using the configured access credentials, if
--// allowed.  This method takes no action unless your AuthOptions has the AllowReauth flag
--// set to true.
--func (a *Access) Reauthenticate() error {
--	var other *Access
--	var err error
+-import (
+-	"testing"
 -
--	if a.options.AllowReauth {
--		other, err = a.context.papersPlease(a.provider, a.options)
--		if err == nil {
--			*a = *other
--		}
--	}
--	return err
--}
+-	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack/identity/v2/tokens"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	"github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--// See AccessProvider interface definition for details.
--func (a *Access) FirstEndpointUrlByCriteria(ac ApiCriteria) string {
--	ep := FindFirstEndpointByCriteria(a.ServiceCatalog, ac)
--	urls := []string{ep.PublicURL, ep.InternalURL}
--	return urls[ac.UrlChoice]
--}
+-func tokenPost(t *testing.T, options gophercloud.AuthOptions, requestJSON string) os.CreateResult {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleTokenPost(t, requestJSON)
 -
--// See AccessProvider interface definition for details.
--func (a *Access) AuthToken() string {
--	return a.Token.Id
+-	return Create(client.ServiceClient(), WrapOptions(options))
 -}
 -
--// See AccessProvider interface definition for details.
--func (a *Access) Revoke(tok string) error {
--	url := a.provider.AuthEndpoint + "/" + tok
--	err := perigee.Delete(url, perigee.Options{
--		MoreHeaders: map[string]string{
--			"X-Auth-Token": a.AuthToken(),
--		},
--		OkCodes: []int{204},
--	})
--	return err
--}
+-func TestCreateTokenWithAPIKey(t *testing.T) {
+-	options := gophercloud.AuthOptions{
+-		Username: "me",
+-		APIKey:   "1234567890abcdef",
+-	}
 -
--// See ServiceCatalogerForIdentityV2 interface definition for details.
--// Note that the raw slice is returend; be careful not to alter the fields of any members,
--// for other components of Gophercloud may depend upon them.
--// If this becomes a problem in the future,
--// a future revision may return a deep-copy of the service catalog instead.
--func (a *Access) V2ServiceCatalog() []CatalogEntry {
--	return a.ServiceCatalog
+-	os.IsSuccessful(t, tokenPost(t, options, `
+-    {
+-      "auth": {
+-        "RAX-KSKEY:apiKeyCredentials": {
+-          "username": "me",
+-          "apiKey": "1234567890abcdef"
+-        }
+-      }
+-    }
+-  `))
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/authenticate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/authenticate_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tokens/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tokens/doc.go
 deleted file mode 100644
-index b05c780..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/authenticate_test.go
+index 44043e5..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/identity/v2/tokens/doc.go
 +++ /dev/null
-@@ -1,264 +0,0 @@
--package gophercloud
+@@ -1,3 +0,0 @@
+-// Package tokens provides information and interaction with the token
+-// API resource for the Rackspace Identity service.
+-package tokens
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/accounts/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/accounts/delegate.go
+deleted file mode 100644
+index 9473930..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/accounts/delegate.go
++++ /dev/null
+@@ -1,39 +0,0 @@
+-package accounts
 -
 -import (
--	"net/http"
--	"testing"
+-	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts"
 -)
 -
--const SUCCESSFUL_RESPONSE = `{
--	"access": {
--		"serviceCatalog": [{
--			"endpoints": [{
--				"publicURL": "https://ord.servers.api.rackspacecloud.com/v2/12345",
--				"region": "ORD",
--				"tenantId": "12345",
--				"versionId": "2",
--				"versionInfo": "https://ord.servers.api.rackspacecloud.com/v2",
--				"versionList": "https://ord.servers.api.rackspacecloud.com/"
--			},{
--				"publicURL": "https://dfw.servers.api.rackspacecloud.com/v2/12345",
--				"region": "DFW",
--				"tenantId": "12345",
--				"versionId": "2",
--				"versionInfo": "https://dfw.servers.api.rackspacecloud.com/v2",
--				"versionList": "https://dfw.servers.api.rackspacecloud.com/"
--			}],
--			"name": "cloudServersOpenStack",
--			"type": "compute"
--		},{
--			"endpoints": [{
--				"publicURL": "https://ord.databases.api.rackspacecloud.com/v1.0/12345",
--				"region": "ORD",
--				"tenantId": "12345"
--			}],
--			"name": "cloudDatabases",
--			"type": "rax:database"
--		}],
--		"token": {
--			"expires": "2012-04-13T13:15:00.000-05:00",
--			"id": "aaaaa-bbbbb-ccccc-dddd"
--		},
--		"user": {
--			"RAX-AUTH:defaultRegion": "DFW",
--			"id": "161418",
--			"name": "demoauthor",
--			"roles": [{
--				"description": "User Admin Role.",
--				"id": "3",
--				"name": "identity:user-admin"
--			}]
--		}
--	}
+-// Get is a function that retrieves an account's metadata. To extract just the
+-// custom metadata, call the ExtractMetadata method on the GetResult. To extract
+-// all the headers that are returned (including the metadata), call the
+-// ExtractHeader method on the GetResult.
+-func Get(c *gophercloud.ServiceClient) os.GetResult {
+-	return os.Get(c, nil)
 -}
--`
--
--func TestAuthProvider(t *testing.T) {
--	tt := newTransport().WithResponse(SUCCESSFUL_RESPONSE)
--	c := TestContext().UseCustomClient(&http.Client{
--		Transport: tt,
--	})
--
--	_, err := c.Authenticate("", AuthOptions{})
--	if err == nil {
--		t.Error("Expected error for empty provider string")
--		return
--	}
--	_, err = c.Authenticate("unknown-provider", AuthOptions{Username: "u", Password: "p"})
--	if err == nil {
--		t.Error("Expected error for unknown service provider")
--		return
--	}
 -
--	err = c.RegisterProvider("provider", Provider{AuthEndpoint: "/"})
--	if err != nil {
--		t.Error(err)
--		return
--	}
--	_, err = c.Authenticate("provider", AuthOptions{Username: "u", Password: "p"})
--	if err != nil {
--		t.Error(err)
--		return
--	}
--	if tt.called != 1 {
--		t.Error("Expected transport to be called once.")
--		return
--	}
+-// UpdateOpts is a structure that contains parameters for updating, creating, or
+-// deleting an account's metadata.
+-type UpdateOpts struct {
+-	Metadata    map[string]string
+-	TempURLKey  string `h:"X-Account-Meta-Temp-URL-Key"`
+-	TempURLKey2 string `h:"X-Account-Meta-Temp-URL-Key-2"`
 -}
 -
--func TestTenantIdEncoding(t *testing.T) {
--	tt := newTransport().WithResponse(SUCCESSFUL_RESPONSE)
--	c := TestContext().
--		UseCustomClient(&http.Client{
--		Transport: tt,
--	}).
--		WithProvider("provider", Provider{AuthEndpoint: "/"})
--
--	tt.IgnoreTenantId()
--	_, err := c.Authenticate("provider", AuthOptions{
--		Username: "u",
--		Password: "p",
--	})
--	if err != nil {
--		t.Error(err)
--		return
--	}
--	if tt.tenantIdFound {
--		t.Error("Tenant ID should not have been encoded")
--		return
--	}
--
--	tt.ExpectTenantId()
--	_, err = c.Authenticate("provider", AuthOptions{
--		Username: "u",
--		Password: "p",
--		TenantId: "t",
--	})
+-// ToAccountUpdateMap formats an UpdateOpts into a map[string]string of headers.
+-func (opts UpdateOpts) ToAccountUpdateMap() (map[string]string, error) {
+-	headers, err := gophercloud.BuildHeaders(opts)
 -	if err != nil {
--		t.Error(err)
--		return
+-		return nil, err
 -	}
--	if !tt.tenantIdFound {
--		t.Error("Tenant ID should have been encoded")
--		return
+-	for k, v := range opts.Metadata {
+-		headers["X-Account-Meta-"+k] = v
 -	}
+-	return headers, err
 -}
 -
--func TestUserNameAndPassword(t *testing.T) {
--	c := TestContext().
--		WithProvider("provider", Provider{AuthEndpoint: "http://localhost/"}).
--		UseCustomClient(&http.Client{Transport: newTransport().WithResponse(SUCCESSFUL_RESPONSE)})
--
--	credentials := []AuthOptions{
--		{},
--		{Username: "u"},
--		{Password: "p"},
--	}
--	for i, auth := range credentials {
--		_, err := c.Authenticate("provider", auth)
--		if err == nil {
--			t.Error("Expected error from missing credentials (%d)", i)
--			return
--		}
--	}
--
--	_, err := c.Authenticate("provider", AuthOptions{Username: "u", Password: "p"})
--	if err != nil {
--		t.Error(err)
--		return
--	}
+-// Update will update an account's metadata with the Metadata in the UpdateOptsBuilder.
+-func Update(c *gophercloud.ServiceClient, opts os.UpdateOptsBuilder) os.UpdateResult {
+-	return os.Update(c, opts)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/accounts/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/accounts/delegate_test.go
+deleted file mode 100644
+index c568bd6..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/accounts/delegate_test.go
++++ /dev/null
+@@ -1,30 +0,0 @@
+-package accounts
 -
--func TestUserNameAndApiKey(t *testing.T) {
--	c := TestContext().
--		WithProvider("provider", Provider{AuthEndpoint: "http://localhost/"}).
--		UseCustomClient(&http.Client{Transport: newTransport().WithResponse(SUCCESSFUL_RESPONSE)})
+-import (
+-	"testing"
 -
--	credentials := []AuthOptions{
--		{},
--		{Username: "u"},
--		{ApiKey: "a"},
--	}
--	for i, auth := range credentials {
--		_, err := c.Authenticate("provider", auth)
--		if err == nil {
--			t.Error("Expected error from missing credentials (%d)", i)
--			return
--		}
--	}
+-	os "github.com/rackspace/gophercloud/openstack/objectstorage/v1/accounts"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--	_, err := c.Authenticate("provider", AuthOptions{Username: "u", ApiKey: "a"})
--	if err != nil {
--		t.Error(err)
--		return
--	}
--}
+-func TestGetAccounts(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleGetAccountSuccessfully(t)
 -
--func TestTokenAcquisition(t *testing.T) {
--	c := TestContext().
--		UseCustomClient(&http.Client{Transport: newTransport().WithResponse(SUCCESSFUL_RESPONSE)}).
--		WithProvider("provider", Provider{AuthEndpoint: "http://localhost/"})
+-	options := &UpdateOpts{Metadata: map[string]string{"gophercloud-test": "accounts"}}
+-	res := Update(fake.ServiceClient(), options)
+-	th.CheckNoErr(t, res.Err)
+-}
 -
--	acc, err := c.Authenticate("provider", AuthOptions{Username: "u", Password: "p"})
--	if err != nil {
--		t.Error(err)
--		return
--	}
+-func TestUpdateAccounts(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleUpdateAccountSuccessfully(t)
 -
--	tok := acc.Token
--	if (tok.Id == "") || (tok.Expires == "") {
--		t.Error("Expected a valid token for successful login; got %s, %s", tok.Id, tok.Expires)
--		return
--	}
+-	expected := map[string]string{"Foo": "bar"}
+-	actual, err := Get(fake.ServiceClient()).ExtractMetadata()
+-	th.CheckNoErr(t, err)
+-	th.CheckDeepEquals(t, expected, actual)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/accounts/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/accounts/doc.go
+deleted file mode 100644
+index 293a930..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/accounts/doc.go
++++ /dev/null
+@@ -1,3 +0,0 @@
+-// Package accounts provides information and interaction with the account
+-// API resource for the Rackspace Cloud Files service.
+-package accounts
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/doc.go
+deleted file mode 100644
+index 9c89e22..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/doc.go
++++ /dev/null
+@@ -1,3 +0,0 @@
+-// Package bulk provides functionality for working with bulk operations in the
+-// Rackspace Cloud Files service.
+-package bulk
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/requests.go
+deleted file mode 100644
+index d252609..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/requests.go
++++ /dev/null
+@@ -1,51 +0,0 @@
+-package bulk
 -
--func TestServiceCatalogAcquisition(t *testing.T) {
--	c := TestContext().
--		UseCustomClient(&http.Client{Transport: newTransport().WithResponse(SUCCESSFUL_RESPONSE)}).
--		WithProvider("provider", Provider{AuthEndpoint: "http://localhost/"})
--
--	acc, err := c.Authenticate("provider", AuthOptions{Username: "u", Password: "p"})
--	if err != nil {
--		t.Error(err)
--		return
--	}
+-import (
+-	"net/url"
+-	"strings"
 -
--	svcs := acc.ServiceCatalog
--	if len(svcs) < 2 {
--		t.Error("Expected 2 service catalog entries; got %d", len(svcs))
--		return
--	}
+-	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
+-)
 -
--	types := map[string]bool{
--		"compute":      true,
--		"rax:database": true,
--	}
--	for _, entry := range svcs {
--		if !types[entry.Type] {
--			t.Error("Expected to find type %s.", entry.Type)
--			return
--		}
--	}
+-// DeleteOptsBuilder allows extensions to add additional parameters to the
+-// Delete request.
+-type DeleteOptsBuilder interface {
+-	ToBulkDeleteBody() (string, error)
 -}
 -
--func TestUserAcquisition(t *testing.T) {
--	c := TestContext().
--		UseCustomClient(&http.Client{Transport: newTransport().WithResponse(SUCCESSFUL_RESPONSE)}).
--		WithProvider("provider", Provider{AuthEndpoint: "http://localhost/"})
--
--	acc, err := c.Authenticate("provider", AuthOptions{Username: "u", Password: "p"})
--	if err != nil {
--		t.Error(err)
--		return
--	}
+-// DeleteOpts is a structure that holds parameters for deleting an object.
+-type DeleteOpts []string
 -
--	u := acc.User
--	if u.Id != "161418" {
--		t.Error("Expected user ID of 16148; got", u.Id)
--		return
--	}
+-// ToBulkDeleteBody formats a DeleteOpts into a request body.
+-func (opts DeleteOpts) ToBulkDeleteBody() (string, error) {
+-	return url.QueryEscape(strings.Join(opts, "\n")), nil
 -}
 -
--func TestAuthenticationNeverReauths(t *testing.T) {
--	tt := newTransport().WithError(401)
--	c := TestContext().
--		UseCustomClient(&http.Client{Transport: tt}).
--		WithProvider("provider", Provider{AuthEndpoint: "http://localhost"})
--
--	_, err := c.Authenticate("provider", AuthOptions{Username: "u", Password: "p"})
--	if err == nil {
--		t.Error("Expected an error from a 401 Unauthorized response")
--		return
--	}
+-// Delete will delete objects or containers in bulk.
+-func Delete(c *gophercloud.ServiceClient, opts DeleteOptsBuilder) DeleteResult {
+-	var res DeleteResult
 -
--	rc, _ := ActualResponseCode(err)
--	if rc != 401 {
--		t.Error("Expected a 401 error code")
--		return
+-	if opts == nil {
+-		return res
 -	}
 -
--	err = tt.VerifyCalls(t, 1)
+-	reqString, err := opts.ToBulkDeleteBody()
 -	if err != nil {
--		// Test object already flagged.
--		return
+-		res.Err = err
+-		return res
 -	}
--}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/common_types.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/common_types.go
-deleted file mode 100644
-index 044b308..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/common_types.go
-+++ /dev/null
-@@ -1,24 +0,0 @@
--package gophercloud
--
--// Link is used for JSON (un)marshalling.
--// It provides RESTful links to a resource.
--type Link struct {
--	Href string `json:"href"`
--	Rel  string `json:"rel"`
--	Type string `json:"type"`
--}
 -
--// FileConfig structures represent a blob of data which must appear at a
--// a specific location in a server's filesystem.  The file contents are
--// base-64 encoded.
--type FileConfig struct {
--	Path     string `json:"path"`
--	Contents string `json:"contents"`
--}
+-	reqBody := strings.NewReader(reqString)
 -
--// NetworkConfig structures represent an affinity between a server and a
--// specific, uniquely identified network.  Networks are identified through
--// universally unique IDs.
--type NetworkConfig struct {
--	Uuid string `json:"uuid"`
+-	resp, err := perigee.Request("DELETE", deleteURL(c), perigee.Options{
+-		ContentType: "text/plain",
+-		MoreHeaders: c.AuthenticatedHeaders(),
+-		OkCodes:     []int{200},
+-		ReqBody:     reqBody,
+-		Results:     &res.Body,
+-	})
+-	res.Header = resp.HttpResponse.Header
+-	res.Err = err
+-	return res
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/context.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/context.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/requests_test.go
 deleted file mode 100644
-index e753c8b..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/context.go
+index 8b5578e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/requests_test.go
 +++ /dev/null
-@@ -1,150 +0,0 @@
--package gophercloud
+@@ -1,36 +0,0 @@
+-package bulk
 -
 -import (
--	"net/http"
--	"strings"
 -	"fmt"
--	"github.com/tonnerre/golang-pretty"
--)
--
--// Provider structures exist for each tangible provider of OpenStack service.
--// For example, Rackspace, Hewlett-Packard, and NASA might have their own instance of this structure.
--//
--// At a minimum, a provider must expose an authentication endpoint.
--type Provider struct {
--	AuthEndpoint string
--}
--
--// ReauthHandlerFunc functions are responsible for somehow performing the task of
--// reauthentication.
--type ReauthHandlerFunc func(AccessProvider) error
+-	"net/http"
+-	"testing"
 -
--// Context structures encapsulate Gophercloud-global state in a manner which
--// facilitates easier unit testing.  As a user of this SDK, you'll never
--// have to use this structure, except when contributing new code to the SDK.
--type Context struct {
--	// providerMap serves as a directory of supported providers.
--	providerMap map[string]Provider
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--	// httpClient refers to the current HTTP client interface to use.
--	httpClient *http.Client
+-func TestBulkDelete(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	th.Mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "DELETE")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.AssertEquals(t, r.URL.RawQuery, "bulk-delete")
 -
--	// reauthHandler provides the functionality needed to re-authenticate
--	// if that feature is enabled.  Note: in order to allow for automatic
--	// re-authentication, the Context object will need to remember your
--	// username, password, and tenant ID as provided in the initial call
--	// to Authenticate().  If you do not desire this, you'll need to handle
--	// reauthentication yourself through other means.  Two methods exist:
--	// the first approach is to just handle errors yourself at the application
--	// layer, and the other is through a custom reauthentication handler
--	// set through the WithReauthHandler() method.
--	reauthHandler ReauthHandlerFunc
--}
--
--// TestContext yields a new Context instance, pre-initialized with a barren
--// state suitable for per-unit-test customization.  This configuration consists
--// of:
--//
--// * An empty provider map.
--//
--// * An HTTP client built by the net/http package (see http://godoc.org/net/http#Client).
--func TestContext() *Context {
--	return &Context{
--		providerMap: make(map[string]Provider),
--		httpClient:  &http.Client{},
--		reauthHandler: func(acc AccessProvider) error {
--			return acc.Reauthenticate()
--		},
--	}
--}
+-		w.WriteHeader(http.StatusOK)
+-		fmt.Fprintf(w, `
+-      {
+-        "Number Not Found": 1,
+-        "Response Status": "200 OK",
+-        "Errors": [],
+-        "Number Deleted": 1,
+-        "Response Body": ""
+-      }
+-    `)
+-	})
 -
--// UseCustomClient configures the context to use a customized HTTP client
--// instance.  By default, TestContext() will return a Context which uses
--// the net/http package's default client instance.
--func (c *Context) UseCustomClient(hc *http.Client) *Context {
--	c.httpClient = hc
--	return c
+-	options := DeleteOpts{"gophercloud-testcontainer1", "gophercloud-testcontainer2"}
+-	actual, err := Delete(fake.ServiceClient(), options).ExtractBody()
+-	th.AssertNoErr(t, err)
+-	th.AssertEquals(t, actual.NumberDeleted, 1)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/results.go
+deleted file mode 100644
+index fddc125..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/results.go
++++ /dev/null
+@@ -1,28 +0,0 @@
+-package bulk
 -
--// RegisterProvider allows a unit test to register a mythical provider convenient for testing.
--// If the provider structure lacks adequate configuration, or the configuration given has some
--// detectable error, an ErrConfiguration error will result.
--func (c *Context) RegisterProvider(name string, p Provider) error {
--	if p.AuthEndpoint == "" {
--		return ErrConfiguration
--	}
+-import (
+-	"github.com/rackspace/gophercloud"
 -
--	c.providerMap[name] = p
--	return nil
--}
+-	"github.com/mitchellh/mapstructure"
+-)
 -
--// WithProvider offers convenience for unit tests.
--func (c *Context) WithProvider(name string, p Provider) *Context {
--	err := c.RegisterProvider(name, p)
--	if err != nil {
--		panic(err)
--	}
--	return c
+-// DeleteResult represents the result of a bulk delete operation.
+-type DeleteResult struct {
+-	gophercloud.Result
 -}
 -
--// ProviderByName will locate a provider amongst those previously registered, if it exists.
--// If the named provider has not been registered, an ErrProvider error will result.
--//
--// You may also specify a custom Identity API URL.
--// Any provider name that contains the characters "://", in that order, will be treated as a custom Identity API URL.
--// Custom URLs, important for private cloud deployments, overrides all provider configurations.
--func (c *Context) ProviderByName(name string) (p Provider, err error) {
--	for provider, descriptor := range c.providerMap {
--		if name == provider {
--			return descriptor, nil
--		}
--	}
--	if strings.Contains(name, "://") {
--		p = Provider{
--			AuthEndpoint: name,
--		}
--		return p, nil
--	}
--	return Provider{}, ErrProvider
+-// DeleteRespBody is the form of the response body returned by a bulk delete request.
+-type DeleteRespBody struct {
+-	NumberNotFound int      `mapstructure:"Number Not Found"`
+-	ResponseStatus string   `mapstructure:"Response Status"`
+-	Errors         []string `mapstructure:"Errors"`
+-	NumberDeleted  int      `mapstructure:"Number Deleted"`
+-	ResponseBody   string   `mapstructure:"Response Body"`
 -}
 -
--func getServiceCatalogFromAccessProvider(provider AccessProvider) ([]CatalogEntry) {
--	access, found := provider.(*Access)
--	if found {
--		return access.ServiceCatalog
--	} else {
--		return nil
--	}
+-// ExtractBody will extract the body returned by the bulk extract request.
+-func (dr DeleteResult) ExtractBody() (DeleteRespBody, error) {
+-	var resp DeleteRespBody
+-	err := mapstructure.Decode(dr.Body, &resp)
+-	return resp, err
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/urls.go
+deleted file mode 100644
+index 2e11203..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/urls.go
++++ /dev/null
+@@ -1,11 +0,0 @@
+-package bulk
 -
--// Instantiates a Cloud Servers API for the provider given.
--func (c *Context) ServersApi(provider AccessProvider, criteria ApiCriteria) (CloudServersProvider, error) {
--	url := provider.FirstEndpointUrlByCriteria(criteria)
--	if url == "" {
--		var err = fmt.Errorf(
--			"Missing endpoint, or insufficient privileges to access endpoint; criteria = %# v; serviceCatalog = %# v",
--			pretty.Formatter(criteria),
--			pretty.Formatter(getServiceCatalogFromAccessProvider(provider)))
--		return nil, err
--	}
--
--	gcp := &genericServersProvider{
--		endpoint: url,
--		context:  c,
--		access:   provider,
--	}
+-import "github.com/rackspace/gophercloud"
 -
--	return gcp, nil
+-func deleteURL(c *gophercloud.ServiceClient) string {
+-	return c.Endpoint + "?bulk-delete"
 -}
 -
--// WithReauthHandler configures the context to handle reauthentication attempts using the supplied
--// funtion.  By default, reauthentication happens by invoking Authenticate(), which is unlikely to be
--// useful in a unit test.
--//
--// Do not confuse this function with WithReauth()!  Although they work together to support reauthentication,
--// WithReauth() actually contains the decision-making logic to determine when to perform a reauth,
--// while WithReauthHandler() is used to configure what a reauth actually entails.
--func (c *Context) WithReauthHandler(f ReauthHandlerFunc) *Context {
--	c.reauthHandler = f
--	return c
+-func extractURL(c *gophercloud.ServiceClient, ext string) string {
+-	return c.Endpoint + "?extract-archive=" + ext
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/context_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/context_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/urls_test.go
 deleted file mode 100644
-index 2936526..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/context_test.go
+index 9169e52..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/bulk/urls_test.go
 +++ /dev/null
-@@ -1,28 +0,0 @@
--package gophercloud
+@@ -1,26 +0,0 @@
+-package bulk
 -
 -import (
 -	"testing"
+-
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
 -)
 -
--func TestProviderRegistry(t *testing.T) {
--	c := TestContext()
+-const endpoint = "http://localhost:57909/"
 -
--	_, err := c.ProviderByName("aProvider")
--	if err == nil {
--		t.Error("Expected error when looking for a provider by non-existant name")
--		return
--	}
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint}
+-}
 -
--	err = c.RegisterProvider("aProvider", Provider{})
--	if err != ErrConfiguration {
--		t.Error("Unexpected error/nil when registering a provider w/out an auth endpoint\n  %s", err)
--		return
--	}
+-func TestDeleteURL(t *testing.T) {
+-	actual := deleteURL(endpointClient())
+-	expected := endpoint + "?bulk-delete"
+-	th.CheckEquals(t, expected, actual)
+-}
 -
--	_ = c.RegisterProvider("aProvider", Provider{AuthEndpoint: "http://localhost/auth"})
--	_, err = c.ProviderByName("aProvider")
--	if err != nil {
--		t.Error(err)
--		return
--	}
+-func TestExtractURL(t *testing.T) {
+-	actual := extractURL(endpointClient(), "tar")
+-	expected := endpoint + "?extract-archive=tar"
+-	th.CheckEquals(t, expected, actual)
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/errors.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/errors.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/delegate.go
 deleted file mode 100644
-index 726ba7e..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/errors.go
+index d7eef20..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/delegate.go
 +++ /dev/null
-@@ -1,39 +0,0 @@
--package gophercloud
+@@ -1,71 +0,0 @@
+-package cdncontainers
 -
 -import (
--	"fmt"
+-	"strconv"
+-
+-	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers"
+-	"github.com/rackspace/gophercloud/pagination"
 -)
 -
--// ErrNotImplemented should be used only while developing new SDK features.
--// No established function or method will ever produce this error.
--var ErrNotImplemented = fmt.Errorf("Not implemented")
--
--// ErrProvider errors occur when attempting to reference an unsupported
--// provider.  More often than not, this error happens due to a typo in
--// the name.
--var ErrProvider = fmt.Errorf("Missing or incorrect provider")
--
--// ErrCredentials errors happen when attempting to authenticate using a
--// set of credentials not recognized by the Authenticate() method.
--// For example, not providing a username or password when attempting to
--// authenticate against an Identity V2 API.
--var ErrCredentials = fmt.Errorf("Missing or incomplete credentials")
--
--// ErrConfiguration errors happen when attempting to add a new provider, and
--// the provider added lacks a correct or consistent configuration.
--// For example, all providers must expose at least an Identity V2 API
--// for authentication; if this endpoint isn't specified, you may receive
--// this error when attempting to register it against a context.
--var ErrConfiguration = fmt.Errorf("Missing or incomplete configuration")
--
--// ErrError errors happen when you attempt to discover the response code
--// responsible for a previous request bombing with an error, but pass in an
--// error interface which doesn't belong to the web client.
--var ErrError = fmt.Errorf("Attempt to solicit actual HTTP response code from error entity which doesn't know")
--
--// WarnUnauthoritative warnings happen when a service believes its response
--// to be correct, but is not in a position of knowing for sure at the moment.
--// For example, the service could be responding with cached data that has
--// exceeded its time-to-live setting, but which has not yet received an official
--// update from an authoritative source.
--var WarnUnauthoritative = fmt.Errorf("Unauthoritative data")
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/flavors.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/flavors.go
-deleted file mode 100644
-index eb864d5..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/flavors.go
-+++ /dev/null
-@@ -1,55 +0,0 @@
--package gophercloud
+-// ExtractNames interprets a page of List results when just the container
+-// names are requested.
+-func ExtractNames(page pagination.Page) ([]string, error) {
+-	return os.ExtractNames(page)
+-}
 -
--import (
--	"github.com/racker/perigee"
--)
+-// ListOpts are options for listing Rackspace CDN containers.
+-type ListOpts struct {
+-	EndMarker string `q:"end_marker"`
+-	Format    string `q:"format"`
+-	Limit     int    `q:"limit"`
+-	Marker    string `q:"marker"`
+-}
+-
+-// ToContainerListParams formats a ListOpts into a query string and boolean
+-// representing whether to list complete information for each container.
+-func (opts ListOpts) ToContainerListParams() (bool, string, error) {
+-	q, err := gophercloud.BuildQueryString(opts)
+-	if err != nil {
+-		return false, "", err
+-	}
+-	return false, q.String(), nil
+-}
 -
--// See CloudServersProvider interface for details.
--func (gsp *genericServersProvider) ListFlavors() ([]Flavor, error) {
--	var fs []Flavor
+-// List is a function that retrieves containers associated with the account as
+-// well as account metadata. It returns a pager which can be iterated with the
+-// EachPage function.
+-func List(c *gophercloud.ServiceClient, opts os.ListOptsBuilder) pagination.Pager {
+-	return os.List(c, opts)
+-}
 -
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		url := gsp.endpoint + "/flavors/detail"
--		return perigee.Get(url, perigee.Options{
--			CustomClient: gsp.context.httpClient,
--			Results:      &struct{ Flavors *[]Flavor }{&fs},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--		})
--	})
--	return fs, err
+-// Get is a function that retrieves the metadata of a container. To extract just
+-// the custom metadata, pass the GetResult response to the ExtractMetadata
+-// function.
+-func Get(c *gophercloud.ServiceClient, containerName string) os.GetResult {
+-	return os.Get(c, containerName)
 -}
 -
--// FlavorLink provides a reference to a flavor by either ID or by direct URL.
--// Some services use just the ID, others use just the URL.
--// This structure provides a common means of expressing both in a single field.
--type FlavorLink struct {
--	Id    string `json:"id"`
--	Links []Link `json:"links"`
+-// UpdateOpts is a structure that holds parameters for updating, creating, or
+-// deleting a container's metadata.
+-type UpdateOpts struct {
+-	CDNEnabled   bool `h:"X-Cdn-Enabled"`
+-	LogRetention bool `h:"X-Log-Retention"`
+-	TTL          int  `h:"X-Ttl"`
 -}
 -
--// Flavor records represent (virtual) hardware configurations for server resources in a region.
--//
--// The Id field contains the flavor's unique identifier.
--// For example, this identifier will be useful when specifying which hardware configuration to use for a new server instance.
--//
--// The Disk and Ram fields provide a measure of storage space offered by the flavor, in GB and MB, respectively.
--//
--// The Name field provides a human-readable moniker for the flavor.
--//
--// Swap indicates how much space is reserved for swap.
--// If not provided, this field will be set to 0.
--//
--// VCpus indicates how many (virtual) CPUs are available for this flavor.
--type Flavor struct {
--	OsFlvDisabled bool    `json:"OS-FLV-DISABLED:disabled"`
--	Disk          int     `json:"disk"`
--	Id            string  `json:"id"`
--	Links         []Link  `json:"links"`
--	Name          string  `json:"name"`
--	Ram           int     `json:"ram"`
--	RxTxFactor    float64 `json:"rxtx_factor"`
--	Swap          int     `json:"swap"`
--	VCpus         int     `json:"vcpus"`
+-// ToContainerUpdateMap formats a CreateOpts into a map of headers.
+-func (opts UpdateOpts) ToContainerUpdateMap() (map[string]string, error) {
+-	h, err := gophercloud.BuildHeaders(opts)
+-	if err != nil {
+-		return nil, err
+-	}
+-	h["X-Cdn-Enabled"] = strconv.FormatBool(opts.CDNEnabled)
+-	return h, nil
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/floating_ips.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/floating_ips.go
+-
+-// Update is a function that creates, updates, or deletes a container's
+-// metadata.
+-func Update(c *gophercloud.ServiceClient, containerName string, opts os.UpdateOptsBuilder) os.UpdateResult {
+-	return os.Update(c, containerName, opts)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/delegate_test.go
 deleted file mode 100644
-index 1163667..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/floating_ips.go
+index 02c3c5e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/delegate_test.go
 +++ /dev/null
-@@ -1,88 +0,0 @@
--package gophercloud
+@@ -1,50 +0,0 @@
+-package cdncontainers
 -
 -import (
--	"errors"
--	"fmt"
--	"github.com/racker/perigee"
+-	"testing"
+-
+-	os "github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
 -)
 -
--func (gsp *genericServersProvider) ListFloatingIps() ([]FloatingIp, error) {
--	var fips []FloatingIp
+-func TestListCDNContainers(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleListContainerNamesSuccessfully(t)
 -
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		url := gsp.endpoint + "/os-floating-ips"
--		return perigee.Get(url, perigee.Options{
--			CustomClient: gsp.context.httpClient,
--			Results: &struct {
--				FloatingIps *[]FloatingIp `json:"floating_ips"`
--			}{&fips},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--		})
--	})
--	return fips, err
--}
+-	count := 0
+-	err := List(fake.ServiceClient(), nil).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractNames(page)
+-		th.AssertNoErr(t, err)
 -
--func (gsp *genericServersProvider) CreateFloatingIp(pool string) (FloatingIp, error) {
--	fip := new(FloatingIp)
+-		th.CheckDeepEquals(t, os.ExpectedListNames, actual)
 -
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		url := gsp.endpoint + "/os-floating-ips"
--		return perigee.Post(url, perigee.Options{
--			CustomClient: gsp.context.httpClient,
--			ReqBody: map[string]string{
--				"pool": pool,
--			},
--			Results: &struct {
--				FloatingIp **FloatingIp `json:"floating_ip"`
--			}{&fip},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--		})
+-		return true, nil
 -	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, count, 1)
+-}
 -
--	if fip.Ip == "" {
--		return *fip, errors.New("Error creating floating IP")
--	}
+-func TestGetCDNContainer(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleGetContainerSuccessfully(t)
 -
--	return *fip, err
--}
+-	_, err := Get(fake.ServiceClient(), "testContainer").ExtractMetadata()
+-	th.CheckNoErr(t, err)
 -
--func (gsp *genericServersProvider) AssociateFloatingIp(serverId string, ip FloatingIp) error {
--	return gsp.context.WithReauth(gsp.access, func() error {
--		ep := fmt.Sprintf("%s/servers/%s/action", gsp.endpoint, serverId)
--		return perigee.Post(ep, perigee.Options{
--			CustomClient: gsp.context.httpClient,
--			ReqBody: map[string](map[string]string){
--				"addFloatingIp": map[string]string{"address": ip.Ip},
--			},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			OkCodes: []int{202},
--		})
--	})
 -}
 -
--func (gsp *genericServersProvider) DeleteFloatingIp(ip FloatingIp) error {
--	return gsp.context.WithReauth(gsp.access, func() error {
--		ep := fmt.Sprintf("%s/os-floating-ips/%d", gsp.endpoint, ip.Id)
--		return perigee.Delete(ep, perigee.Options{
--			CustomClient: gsp.context.httpClient,
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			OkCodes: []int{202},
--		})
--	})
--}
+-func TestUpdateCDNContainer(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleUpdateContainerSuccessfully(t)
+-
+-	options := &UpdateOpts{TTL: 3600}
+-	res := Update(fake.ServiceClient(), "testContainer", options)
+-	th.CheckNoErr(t, res.Err)
 -
--type FloatingIp struct {
--	Id         int    `json:"id"`
--	Pool       string `json:"pool"`
--	Ip         string `json:"ip"`
--	FixedIp    string `json:"fixed_ip"`
--	InstanceId string `json:"instance_id"`
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/global_context.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/global_context.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/doc.go
 deleted file mode 100644
-index 89d283b..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/global_context.go
+index 7b0930e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/doc.go
 +++ /dev/null
-@@ -1,67 +0,0 @@
--package gophercloud
+@@ -1,3 +0,0 @@
+-// Package cdncontainers provides information and interaction with the CDN
+-// Container API resource for the Rackspace Cloud Files service.
+-package cdncontainers
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/requests.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/requests.go
+deleted file mode 100644
+index 0567833..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/requests.go
++++ /dev/null
+@@ -1,58 +0,0 @@
+-package cdncontainers
 -
 -import (
 -	"github.com/racker/perigee"
+-	"github.com/rackspace/gophercloud"
 -)
 -
--// globalContext is the, well, "global context."
--// Most of this SDK is written in a manner to facilitate easier testing,
--// which doesn't require all the configuration a real-world application would require.
--// However, for real-world deployments, applications should be able to rely on a consistent configuration of providers, etc.
--var globalContext *Context
+-// EnableOptsBuilder allows extensions to add additional parameters to the Enable
+-// request.
+-type EnableOptsBuilder interface {
+-	ToCDNContainerEnableMap() (map[string]string, error)
+-}
 -
--// providers is the set of supported providers.
--var providers = map[string]Provider{
--	"rackspace-us": {
--		AuthEndpoint: "https://identity.api.rackspacecloud.com/v2.0/tokens",
--	},
--	"rackspace-uk": {
--		AuthEndpoint: "https://lon.identity.api.rackspacecloud.com/v2.0/tokens",
--	},
+-// EnableOpts is a structure that holds options for enabling a CDN container.
+-type EnableOpts struct {
+-	// CDNEnabled indicates whether or not the container is CDN enabled. Set to
+-	// `true` to enable the container. Note that changing this setting from true
+-	// to false will disable the container in the CDN but only after the TTL has
+-	// expired.
+-	CDNEnabled bool `h:"X-Cdn-Enabled"`
+-	// TTL is the time-to-live for the container (in seconds).
+-	TTL int `h:"X-Ttl"`
 -}
 -
--// Initialize the global context to sane configuration.
--// The Go runtime ensures this function is called before main(),
--// thus guaranteeing proper configuration before your application ever runs.
--func init() {
--	globalContext = TestContext()
--	for name, descriptor := range providers {
--		globalContext.RegisterProvider(name, descriptor)
+-// ToCDNContainerEnableMap formats an EnableOpts into a map of headers.
+-func (opts EnableOpts) ToCDNContainerEnableMap() (map[string]string, error) {
+-	h, err := gophercloud.BuildHeaders(opts)
+-	if err != nil {
+-		return nil, err
 -	}
+-	return h, nil
 -}
 -
--// Authenticate() grants access to the OpenStack-compatible provider API.
--//
--// Providers are identified through a unique key string.
--// Specifying an unsupported provider will result in an ErrProvider error.
--// However, you may also specify a custom Identity API URL.
--// Any provider name that contains the characters "://", in that order, will be treated as a custom Identity API URL.
--// Custom URLs, important for private cloud deployments, overrides all provider configurations.
--//
--// The supplied AuthOptions instance allows the client to specify only those credentials
--// relevant for the authentication request.  At present, support exists for OpenStack
--// Identity V2 API only; support for V3 will become available as soon as documentation for it
--// becomes readily available.
--//
--// For Identity V2 API requirements, you must provide at least the Username and Password
--// options.  The TenantId field is optional, and defaults to "".
--func Authenticate(provider string, options AuthOptions) (*Access, error) {
--	return globalContext.Authenticate(provider, options)
--}
+-// Enable is a function that enables/disables a CDN container.
+-func Enable(c *gophercloud.ServiceClient, containerName string, opts EnableOptsBuilder) EnableResult {
+-	var res EnableResult
+-	h := c.AuthenticatedHeaders()
 -
--// Instantiates a Cloud Servers object for the provider given.
--func ServersApi(acc AccessProvider, criteria ApiCriteria) (CloudServersProvider, error) {
--	return globalContext.ServersApi(acc, criteria)
--}
+-	if opts != nil {
+-		headers, err := opts.ToCDNContainerEnableMap()
+-		if err != nil {
+-			res.Err = err
+-			return res
+-		}
 -
--// ActualResponseCode inspects a returned error, and discovers the actual response actual
--// response code that caused the error to be raised.
--func ActualResponseCode(e error) (int, error) {
--	if err, typeOk := e.(*perigee.UnexpectedResponseCodeError); typeOk {
--		return err.Actual, nil
--	} else if err, typeOk := e.(*AuthError); typeOk{
--		return err.StatusCode, nil
+-		for k, v := range headers {
+-			h[k] = v
+-		}
 -	}
 -
--	return 0, ErrError
+-	resp, err := perigee.Request("PUT", enableURL(c, containerName), perigee.Options{
+-		MoreHeaders: h,
+-		OkCodes:     []int{201, 202, 204},
+-	})
+-	res.Header = resp.HttpResponse.Header
+-	res.Err = err
+-	return res
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/images.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/images.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/requests_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/requests_test.go
 deleted file mode 100644
-index a23e0bb..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/images.go
+index 28b963d..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/requests_test.go
 +++ /dev/null
-@@ -1,106 +0,0 @@
--package gophercloud
+@@ -1,29 +0,0 @@
+-package cdncontainers
 -
 -import (
--	"github.com/racker/perigee"
--)
+-	"net/http"
+-	"testing"
 -
--// See the CloudImagesProvider interface for details.
--func (gsp *genericServersProvider) ListImages() ([]Image, error) {
--	var is []Image
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		url := gsp.endpoint + "/images/detail"
--		return perigee.Get(url, perigee.Options{
--			CustomClient: gsp.context.httpClient,
--			Results:      &struct{ Images *[]Image }{&is},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--		})
+-func TestEnableCDNContainer(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	th.Mux.HandleFunc("/testContainer", func(w http.ResponseWriter, r *http.Request) {
+-		th.TestMethod(t, r, "PUT")
+-		th.TestHeader(t, r, "X-Auth-Token", fake.TokenID)
+-		th.TestHeader(t, r, "Accept", "application/json")
+-
+-		w.Header().Add("X-Ttl", "259200")
+-		w.Header().Add("X-Cdn-Enabled", "True")
+-		w.WriteHeader(http.StatusNoContent)
 -	})
--	return is, err
+-
+-	options := &EnableOpts{CDNEnabled: true, TTL: 259200}
+-	actual := Enable(fake.ServiceClient(), "testContainer", options)
+-	th.AssertNoErr(t, actual.Err)
+-	th.CheckEquals(t, actual.Header["X-Ttl"][0], "259200")
+-	th.CheckEquals(t, actual.Header["X-Cdn-Enabled"][0], "True")
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/results.go
+deleted file mode 100644
+index a5097ca..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/results.go
++++ /dev/null
+@@ -1,8 +0,0 @@
+-package cdncontainers
 -
--func (gsp *genericServersProvider) ImageById(id string) (*Image, error) {
--	var is *Image
+-import "github.com/rackspace/gophercloud"
 -
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		url := gsp.endpoint + "/images/" + id
--		return perigee.Get(url, perigee.Options{
--			CustomClient: gsp.context.httpClient,
--			Results:      &struct{ Image **Image }{&is},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--		})
--	})
--	return is, err
+-// EnableResult represents the result of a get operation.
+-type EnableResult struct {
+-	gophercloud.HeaderResult
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/urls.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/urls.go
+deleted file mode 100644
+index 80653f2..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/urls.go
++++ /dev/null
+@@ -1,7 +0,0 @@
+-package cdncontainers
 -
--func (gsp *genericServersProvider) DeleteImageById(id string) error {
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		url := gsp.endpoint + "/images/" + id
--		_, err := perigee.Request("DELETE", url, perigee.Options{
--			CustomClient: gsp.context.httpClient,
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--		})
--		return err
--	})
--	return err
--}
+-import "github.com/rackspace/gophercloud"
 -
--// ImageLink provides a reference to a image by either ID or by direct URL.
--// Some services use just the ID, others use just the URL.
--// This structure provides a common means of expressing both in a single field.
--type ImageLink struct {
--	Id    string `json:"id"`
--	Links []Link `json:"links"`
+-func enableURL(c *gophercloud.ServiceClient, containerName string) string {
+-	return c.ServiceURL(containerName)
 -}
--
--// Image is used for JSON (un)marshalling.
--// It provides a description of an OS image.
--//
--// The Id field contains the image's unique identifier.
--// For example, this identifier will be useful for specifying which operating system to install on a new server instance.
--//
--// The MinDisk and MinRam fields specify the minimum resources a server must provide to be able to install the image.
--//
--// The Name field provides a human-readable moniker for the OS image.
--//
--// The Progress and Status fields indicate image-creation status.
--// Any usable image will have 100% progress.
--//
--// The Updated field indicates the last time this image was changed.
--//
--// OsDcfDiskConfig indicates the server's boot volume configuration.
--// Valid values are:
--//     AUTO
--//     ----
--//     The server is built with a single partition the size of the target flavor disk.
--//     The file system is automatically adjusted to fit the entire partition.
--//     This keeps things simple and automated.
--//     AUTO is valid only for images and servers with a single partition that use the EXT3 file system.
--//     This is the default setting for applicable Rackspace base images.
--//
--//     MANUAL
--//     ------
--//     The server is built using whatever partition scheme and file system is in the source image.
--//     If the target flavor disk is larger,
--//     the remaining disk space is left unpartitioned.
--//     This enables images to have non-EXT3 file systems, multiple partitions, and so on,
--//     and enables you to manage the disk configuration.
--//
--type Image struct {
--	Created         string `json:"created"`
--	Id              string `json:"id"`
--	Links           []Link `json:"links"`
--	MinDisk         int    `json:"minDisk"`
--	MinRam          int    `json:"minRam"`
--	Name            string `json:"name"`
--	Progress        int    `json:"progress"`
--	Status          string `json:"status"`
--	Updated         string `json:"updated"`
--	OsDcfDiskConfig string `json:"OS-DCF:diskConfig"`
--}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/interfaces.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/interfaces.go
-deleted file mode 100644
-index 4c7dbee..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/interfaces.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/urls_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/urls_test.go
+deleted file mode 100644
+index aa5bfe6..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdncontainers/urls_test.go
 +++ /dev/null
-@@ -1,247 +0,0 @@
--package gophercloud
+@@ -1,20 +0,0 @@
+-package cdncontainers
 -
--import "net/url"
+-import (
+-	"testing"
 -
--// AccessProvider instances encapsulate a Keystone authentication interface.
--type AccessProvider interface {
--	// FirstEndpointUrlByCriteria searches through the service catalog for the first
--	// matching entry endpoint fulfilling the provided criteria.  If nothing found,
--	// return "".  Otherwise, return either the public or internal URL for the
--	// endpoint, depending on both its existence and the setting of the ApiCriteria.UrlChoice
--	// field.
--	FirstEndpointUrlByCriteria(ApiCriteria) string
+-	"github.com/rackspace/gophercloud"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--	// AuthToken provides a copy of the current authentication token for the user's credentials.
--	// Note that AuthToken() will not automatically refresh an expired token.
--	AuthToken() string
+-const endpoint = "http://localhost:57909/"
 -
--	// Revoke allows you to terminate any program's access to the OpenStack API by token ID.
--	Revoke(string) error
+-func endpointClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{Endpoint: endpoint}
+-}
 -
--	// Reauthenticate attempts to acquire a new authentication token, if the feature is enabled by
--	// AuthOptions.AllowReauth.
--	Reauthenticate() error
+-func TestEnableURL(t *testing.T) {
+-	actual := enableURL(endpointClient(), "foo")
+-	expected := endpoint + "foo"
+-	th.CheckEquals(t, expected, actual)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdnobjects/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdnobjects/delegate.go
+deleted file mode 100644
+index e9d2ff1..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdnobjects/delegate.go
++++ /dev/null
+@@ -1,11 +0,0 @@
+-package cdnobjects
+-
+-import (
+-	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects"
+-)
 -
--// ServiceCatalogerIdentityV2 interface provides direct access to the service catalog as offered by the Identity V2 API.
--// We regret we need to fracture the namespace of what should otherwise be a simple concept; however,
--// the OpenStack community saw fit to render V3's service catalog completely incompatible with V2.
--type ServiceCatalogerForIdentityV2 interface {
--	V2ServiceCatalog() []CatalogEntry
+-// Delete is a function that deletes an object from the CDN.
+-func Delete(c *gophercloud.ServiceClient, containerName, objectName string, opts os.DeleteOptsBuilder) os.DeleteResult {
+-	return os.Delete(c, containerName, objectName, nil)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdnobjects/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdnobjects/delegate_test.go
+deleted file mode 100644
+index b5e04a9..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdnobjects/delegate_test.go
++++ /dev/null
+@@ -1,19 +0,0 @@
+-package cdnobjects
 -
--// CloudServersProvider instances encapsulate a Cloud Servers API, should one exist in the service catalog
--// for your provider.
--type CloudServersProvider interface {
--	// Servers
+-import (
+-	"testing"
 -
--	// ListServers provides a complete list of servers hosted by the user
--	// in a given region.  This function differs from ListServersLinksOnly()
--	// in that it returns all available details for each server returned.
--	ListServers() ([]Server, error)
+-	os "github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--	// ListServersByFilters provides a list of servers hosted by the user in a
--	// given region. This function let you requests servers by certain URI
--	// paramaters defined by the API endpoint.  This is sometimes more suitable
--	// if you have many servers and you only want to pick servers on certain
--	// criterias. An example usage could be :
--	//
--	//	   filter := url.Values{}
--	//	   filter.Set("name", "MyServer")
--	//	   filter.Set("status", "ACTIVE")
--	//
--	//	   filteredServers, err := c.ListServersByFilters(filter)
--	//
--	// Here, filteredServers only contains servers whose name started with
--	// "MyServer" and are in "ACTIVE" status.
--	ListServersByFilter(filter url.Values) ([]Server, error)
+-func TestDeleteCDNObject(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleDeleteObjectSuccessfully(t)
 -
--	// ListServers provides a complete list of servers hosted by the user
--	// in a given region.  This function differs from ListServers() in that
--	// it returns only IDs and links to each server returned.
--	//
--	// This function should be used only under certain circumstances.
--	// It's most useful for checking to see if a server with a given ID exists,
--	// or that you have permission to work with that server.  It's also useful
--	// when the cost of retrieving the server link list plus the overhead of manually
--	// invoking ServerById() for each of the servers you're interested in is less than
--	// just calling ListServers() to begin with.  This may be a consideration, for
--	// example, with mobile applications.
--	//
--	// In other cases, you probably should just call ListServers() and cache the
--	// results to conserve overall bandwidth and reduce your access rate on the API.
--	ListServersLinksOnly() ([]Server, error)
+-	res := Delete(fake.ServiceClient(), "testContainer", "testObject", nil)
+-	th.AssertNoErr(t, res.Err)
 -
--	// ServerById will retrieve a detailed server description given the unique ID
--	// of a server.  The ID can be returned by either ListServers() or by ListServersLinksOnly().
--	ServerById(id string) (*Server, error)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdnobjects/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdnobjects/doc.go
+deleted file mode 100644
+index 90cd5c9..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/cdnobjects/doc.go
++++ /dev/null
+@@ -1,3 +0,0 @@
+-// Package cdnobjects provides information and interaction with the CDN
+-// Object API resource for the Rackspace Cloud Files service.
+-package cdnobjects
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/containers/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/containers/delegate.go
+deleted file mode 100644
+index 77ed002..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/containers/delegate.go
++++ /dev/null
+@@ -1,93 +0,0 @@
+-package containers
 -
--	// CreateServer requests a new server to be created by the cloud server provider.
--	// The user must pass in a pointer to an initialized NewServerContainer structure.
--	// Please refer to the NewServerContainer documentation for more details.
--	//
--	// If the NewServer structure's AdminPass is empty (""), a password will be
--	// automatically generated by your OpenStack provider, and returned through the
--	// AdminPass field of the result.  Take care, however; this will be the only time
--	// this happens.  No other means exists in the public API to acquire a password
--	// for a pre-existing server.  If you lose it, you'll need to call SetAdminPassword()
--	// to set a new one.
--	CreateServer(ns NewServer) (*NewServer, error)
--
--	// DeleteServerById requests that the server with the assigned ID be removed
--	// from your account.  The delete happens asynchronously.
--	DeleteServerById(id string) error
--
--	// SetAdminPassword requests that the server with the specified ID have its
--	// administrative password changed.  For Linux, BSD, or other POSIX-like
--	// system, this password corresponds to the root user.  For Windows machines,
--	// the Administrator password will be affected instead.
--	SetAdminPassword(id string, pw string) error
--
--	// ResizeServer can be a short-hand for RebuildServer where only the size of the server
--	// changes.  Note that after the resize operation is requested, you will need to confirm
--	// the resize has completed for changes to take effect permanently.  Changes will assume
--	// to be confirmed even without an explicit confirmation after 24 hours from the initial
--	// request.
--	ResizeServer(id, newName, newFlavor, newDiskConfig string) error
--
--	// RevertResize will reject a server's resized configuration, thus
--	// rolling back to the original server.
--	RevertResize(id string) error
--
--	// ConfirmResizeServer will acknowledge a server's resized configuration.
--	ConfirmResize(id string) error
--
--	// RebootServer requests that the server with the specified ID be rebooted.
--	// Two reboot mechanisms exist.
--	//
--	// - Hard.  This will physically power-cycle the unit.
--	// - Soft.  This will attempt to use the server's software-based mechanisms to restart
--	//           the machine.  E.g., "shutdown -r now" on Linux.
--	RebootServer(id string, hard bool) error
--
--	// RescueServer requests that the server with the specified ID be placed into
--	// a state of maintenance.  The server instance is replaced with a new instance,
--	// of the same flavor and image.  This new image will have the boot volume of the
--	// original machine mounted as a secondary device, so that repair and administration
--	// may occur.  Use UnrescueServer() to restore the server to its previous state.
--	// Note also that many providers will impose a time limit for how long a server may
--	// exist in rescue mode!  Consult the API documentation for your provider for
--	// details.
--	RescueServer(id string) (string, error)
--
--	// UnrescueServer requests that a server in rescue state be placed into its nominal
--	// operating state.
--	UnrescueServer(id string) error
--
--	// UpdateServer alters one or more fields of the identified server's Server record.
--	// However, not all fields may be altered.  Presently, only Name, AccessIPv4, and
--	// AccessIPv6 fields may be altered.   If unspecified, or set to an empty or zero
--	// value, the corresponding field remains unaltered.
--	//
--	// This function returns the new set of server details if successful.
--	UpdateServer(id string, newValues NewServerSettings) (*Server, error)
+-import (
+-	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers"
+-	"github.com/rackspace/gophercloud/pagination"
+-)
 -
--	// RebuildServer reprovisions a server to the specifications given by the
--	// NewServer structure.  The following fields are guaranteed to be recognized:
--	//
--	//		Name (required)				AccessIPv4
--	//		imageRef (required)			AccessIPv6
--	//		AdminPass (required)		Metadata
--	//		Personality
--	//
--	// Other providers may reserve the right to act on additional fields.
--	RebuildServer(id string, ns NewServer) (*Server, error)
+-// ExtractInfo interprets a page of List results when full container info
+-// is requested.
+-func ExtractInfo(page pagination.Page) ([]os.Container, error) {
+-	return os.ExtractInfo(page)
+-}
 -
--	// CreateImage will create a new image from the specified server id returning the id of the new image.
--	CreateImage(id string, ci CreateImage) (string, error)
+-// ExtractNames interprets a page of List results when just the container
+-// names are requested.
+-func ExtractNames(page pagination.Page) ([]string, error) {
+-	return os.ExtractNames(page)
+-}
+-
+-// List is a function that retrieves containers associated with the account as
+-// well as account metadata. It returns a pager which can be iterated with the
+-// EachPage function.
+-func List(c *gophercloud.ServiceClient, opts os.ListOptsBuilder) pagination.Pager {
+-	return os.List(c, opts)
+-}
+-
+-// CreateOpts is a structure that holds parameters for creating a container.
+-type CreateOpts struct {
+-	Metadata         map[string]string
+-	ContainerRead    string `h:"X-Container-Read"`
+-	ContainerWrite   string `h:"X-Container-Write"`
+-	VersionsLocation string `h:"X-Versions-Location"`
+-}
 -
--	// Addresses
+-// ToContainerCreateMap formats a CreateOpts into a map of headers.
+-func (opts CreateOpts) ToContainerCreateMap() (map[string]string, error) {
+-	h, err := gophercloud.BuildHeaders(opts)
+-	if err != nil {
+-		return nil, err
+-	}
+-	for k, v := range opts.Metadata {
+-		h["X-Container-Meta-"+k] = v
+-	}
+-	return h, nil
+-}
 -
--	// ListAddresses yields the list of available addresses for the server.
--	// This information is also returned by ServerById() in the Server.Addresses
--	// field.  However, if you have a lot of servers and all you need are addresses,
--	// this function might be more efficient.
--	ListAddresses(id string) (AddressSet, error)
+-// Create is a function that creates a new container.
+-func Create(c *gophercloud.ServiceClient, containerName string, opts os.CreateOptsBuilder) os.CreateResult {
+-	return os.Create(c, containerName, opts)
+-}
 -
--	// ListAddressesByNetwork yields the list of available addresses for a given server id and networkLabel.
--	// Example: ListAddressesByNetwork("234-4353-4jfrj-43j2s", "private")
--	ListAddressesByNetwork(id, networkLabel string) (NetworkAddress, error)
+-// Delete is a function that deletes a container.
+-func Delete(c *gophercloud.ServiceClient, containerName string) os.DeleteResult {
+-	return os.Delete(c, containerName)
+-}
 -
--	// ListFloatingIps yields the list of all floating IP addresses allocated to the current project.
--	ListFloatingIps() ([]FloatingIp, error)
+-// UpdateOpts is a structure that holds parameters for updating or creating a
+-// container's metadata.
+-type UpdateOpts struct {
+-	Metadata               map[string]string
+-	ContainerRead          string `h:"X-Container-Read"`
+-	ContainerWrite         string `h:"X-Container-Write"`
+-	ContentType            string `h:"Content-Type"`
+-	DetectContentType      bool   `h:"X-Detect-Content-Type"`
+-	RemoveVersionsLocation string `h:"X-Remove-Versions-Location"`
+-	VersionsLocation       string `h:"X-Versions-Location"`
+-}
 -
--	// CreateFloatingIp allocates a new IP from the named pool to the current project.
--	CreateFloatingIp(pool string) (FloatingIp, error)
+-// ToContainerUpdateMap formats a CreateOpts into a map of headers.
+-func (opts UpdateOpts) ToContainerUpdateMap() (map[string]string, error) {
+-	h, err := gophercloud.BuildHeaders(opts)
+-	if err != nil {
+-		return nil, err
+-	}
+-	for k, v := range opts.Metadata {
+-		h["X-Container-Meta-"+k] = v
+-	}
+-	return h, nil
+-}
 -
--	// DeleteFloatingIp returns the specified IP from the current project to the pool.
--	DeleteFloatingIp(ip FloatingIp) error
+-// Update is a function that creates, updates, or deletes a container's
+-// metadata.
+-func Update(c *gophercloud.ServiceClient, containerName string, opts os.UpdateOptsBuilder) os.UpdateResult {
+-	return os.Update(c, containerName, opts)
+-}
 -
--	// AssociateFloatingIp associates the given floating IP to the given server id.
--	AssociateFloatingIp(serverId string, ip FloatingIp) error
+-// Get is a function that retrieves the metadata of a container. To extract just
+-// the custom metadata, pass the GetResult response to the ExtractMetadata
+-// function.
+-func Get(c *gophercloud.ServiceClient, containerName string) os.GetResult {
+-	return os.Get(c, containerName)
+-}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/containers/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/containers/delegate_test.go
+deleted file mode 100644
+index 7ba4eb2..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/containers/delegate_test.go
++++ /dev/null
+@@ -1,91 +0,0 @@
+-package containers
 -
--	// Images
+-import (
+-	"testing"
 -
--	// ListImages yields the list of available operating system images.  This function
--	// returns full details for each image, if available.
--	ListImages() ([]Image, error)
+-	os "github.com/rackspace/gophercloud/openstack/objectstorage/v1/containers"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
+-)
 -
--	// ImageById yields details about a specific image.
--	ImageById(id string) (*Image, error)
+-func TestListContainerInfo(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleListContainerInfoSuccessfully(t)
 -
--	// DeleteImageById will delete the specific image.
--	DeleteImageById(id string) error
+-	count := 0
+-	err := List(fake.ServiceClient(), &os.ListOpts{Full: true}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractInfo(page)
+-		th.AssertNoErr(t, err)
 -
--	// Flavors
+-		th.CheckDeepEquals(t, os.ExpectedListInfo, actual)
 -
--	// ListFlavors yields the list of available system flavors.  This function
--	// returns full details for each flavor, if available.
--	ListFlavors() ([]Flavor, error)
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, count, 1)
+-}
 -
--	// KeyPairs
+-func TestListContainerNames(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleListContainerNamesSuccessfully(t)
 -
--	// ListKeyPairs yields the list of available keypairs.
--	ListKeyPairs() ([]KeyPair, error)
+-	count := 0
+-	err := List(fake.ServiceClient(), &os.ListOpts{Full: false}).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractNames(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract container names: %v", err)
+-			return false, err
+-		}
 -
--	// CreateKeyPairs will create or generate a new keypair.
--	CreateKeyPair(nkp NewKeyPair) (KeyPair, error)
+-		th.CheckDeepEquals(t, os.ExpectedListNames, actual)
 -
--	// DeleteKeyPair wil delete a keypair.
--	DeleteKeyPair(name string) error
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, count, 1)
+-}
 -
--	// ShowKeyPair will yield the named keypair.
--	ShowKeyPair(name string) (KeyPair, error)
+-func TestCreateContainers(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleCreateContainerSuccessfully(t)
 -
--	// ListSecurityGroups provides a listing of security groups for the tenant.
--	// This method works only if the provider supports the os-security-groups extension.
--	ListSecurityGroups() ([]SecurityGroup, error)
+-	options := os.CreateOpts{ContentType: "application/json", Metadata: map[string]string{"foo": "bar"}}
+-	res := Create(fake.ServiceClient(), "testContainer", options)
+-	th.CheckNoErr(t, res.Err)
+-	th.CheckEquals(t, "bar", res.Header["X-Container-Meta-Foo"][0])
 -
--	// CreateSecurityGroup lets a tenant create a new security group.
--	// Only the SecurityGroup fields which are specified will be marshalled to the API.
--	// This method works only if the provider supports the os-security-groups extension.
--	CreateSecurityGroup(desired SecurityGroup) (*SecurityGroup, error)
+-}
 -
--	// ListSecurityGroupsByServerId provides a list of security groups which apply to the indicated server.
--	// This method works only if the provider supports the os-security-groups extension.
--	ListSecurityGroupsByServerId(id string) ([]SecurityGroup, error)
+-func TestDeleteContainers(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleDeleteContainerSuccessfully(t)
 -
--	// SecurityGroupById returns a security group corresponding to the provided ID number.
--	// This method works only if the provider supports the os-security-groups extension.
--	SecurityGroupById(id int) (*SecurityGroup, error)
+-	res := Delete(fake.ServiceClient(), "testContainer")
+-	th.CheckNoErr(t, res.Err)
+-}
 -
--	// DeleteSecurityGroupById disposes of a security group corresponding to the provided ID number.
--	// This method works only if the provider supports the os-security-groups extension.
--	DeleteSecurityGroupById(id int) error
+-func TestUpdateContainers(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleUpdateContainerSuccessfully(t)
 -
--	// ListDefaultSGRules lists default security group rules.
--	// This method only works if the provider supports the os-security-groups-default-rules extension.
--	ListDefaultSGRules() ([]SGRule, error)
+-	options := &os.UpdateOpts{Metadata: map[string]string{"foo": "bar"}}
+-	res := Update(fake.ServiceClient(), "testContainer", options)
+-	th.CheckNoErr(t, res.Err)
+-}
 -
--	// CreateDefaultSGRule creates a default security group rule.
--	// This method only works if the provider supports the os-security-groups-default-rules extension.
--	CreateDefaultSGRule(SGRule) (*SGRule, error)
+-func TestGetContainers(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleGetContainerSuccessfully(t)
 -
--	// GetSGRule obtains information for a specified security group rule.
--	// This method only works if the provider supports the os-security-groups-default-rules extension.
--	GetSGRule(string) (*SGRule, error)
+-	_, err := Get(fake.ServiceClient(), "testContainer").ExtractMetadata()
+-	th.CheckNoErr(t, err)
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/keypairs.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/keypairs.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/containers/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/containers/doc.go
 deleted file mode 100644
-index 8ae8cd3..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/keypairs.go
+index d132a07..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/containers/doc.go
 +++ /dev/null
-@@ -1,98 +0,0 @@
--package gophercloud
+@@ -1,3 +0,0 @@
+-// Package containers provides information and interaction with the Container
+-// API resource for the Rackspace Cloud Files service.
+-package containers
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/objects/delegate.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/objects/delegate.go
+deleted file mode 100644
+index bd4a4f0..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/objects/delegate.go
++++ /dev/null
+@@ -1,90 +0,0 @@
+-package objects
 -
 -import (
--	"github.com/racker/perigee"
+-	"io"
+-
+-	"github.com/rackspace/gophercloud"
+-	os "github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects"
+-	"github.com/rackspace/gophercloud/pagination"
 -)
 -
--// See the CloudImagesProvider interface for details.
--func (gsp *genericServersProvider) ListKeyPairs() ([]KeyPair, error) {
--	type KeyPairs struct {
--		KeyPairs []struct {
--			KeyPair KeyPair `json:"keypair"`
--		} `json:"keypairs"`
--	}
+-// ExtractInfo is a function that takes a page of objects and returns their full information.
+-func ExtractInfo(page pagination.Page) ([]os.Object, error) {
+-	return os.ExtractInfo(page)
+-}
 -
--	var kp KeyPairs
+-// ExtractNames is a function that takes a page of objects and returns only their names.
+-func ExtractNames(page pagination.Page) ([]string, error) {
+-	return os.ExtractNames(page)
+-}
 -
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		url := gsp.endpoint + "/os-keypairs"
--		return perigee.Get(url, perigee.Options{
--			CustomClient: gsp.context.httpClient,
--			Results:      &kp,
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--		})
--	})
+-// List is a function that retrieves objects in the container as
+-// well as container metadata. It returns a pager which can be iterated with the
+-// EachPage function.
+-func List(c *gophercloud.ServiceClient, containerName string, opts os.ListOptsBuilder) pagination.Pager {
+-	return os.List(c, containerName, opts)
+-}
 -
--	// Flatten out the list of keypairs
--	var keypairs []KeyPair
--	for _, k := range kp.KeyPairs {
--		keypairs = append(keypairs, k.KeyPair)
--	}
--	return keypairs, err
+-// Download is a function that retrieves the content and metadata for an object.
+-// To extract just the content, pass the DownloadResult response to the
+-// ExtractContent function.
+-func Download(c *gophercloud.ServiceClient, containerName, objectName string, opts os.DownloadOptsBuilder) os.DownloadResult {
+-	return os.Download(c, containerName, objectName, opts)
 -}
 -
--func (gsp *genericServersProvider) CreateKeyPair(nkp NewKeyPair) (KeyPair, error) {
--	var kp KeyPair
+-// Create is a function that creates a new object or replaces an existing object.
+-func Create(c *gophercloud.ServiceClient, containerName, objectName string, content io.Reader, opts os.CreateOptsBuilder) os.CreateResult {
+-	return os.Create(c, containerName, objectName, content, opts)
+-}
 -
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		url := gsp.endpoint + "/os-keypairs"
--		return perigee.Post(url, perigee.Options{
--			ReqBody: &struct {
--				KeyPair *NewKeyPair `json:"keypair"`
--			}{&nkp},
--			CustomClient: gsp.context.httpClient,
--			Results:      &struct{ KeyPair *KeyPair }{&kp},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			OkCodes: []int{200},
--		})
--	})
--	return kp, err
+-// CopyOpts is a structure that holds parameters for copying one object to
+-// another.
+-type CopyOpts struct {
+-	Metadata           map[string]string
+-	ContentDisposition string `h:"Content-Disposition"`
+-	ContentEncoding    string `h:"Content-Encoding"`
+-	ContentLength      int    `h:"Content-Length"`
+-	ContentType        string `h:"Content-Type"`
+-	CopyFrom           string `h:"X-Copy_From"`
+-	Destination        string `h:"Destination"`
+-	DetectContentType  bool   `h:"X-Detect-Content-Type"`
 -}
 -
--// See the CloudImagesProvider interface for details.
--func (gsp *genericServersProvider) DeleteKeyPair(name string) error {
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		url := gsp.endpoint + "/os-keypairs/" + name
--		return perigee.Delete(url, perigee.Options{
--			CustomClient: gsp.context.httpClient,
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			OkCodes: []int{202},
--		})
--	})
--	return err
+-// ToObjectCopyMap formats a CopyOpts into a map of headers.
+-func (opts CopyOpts) ToObjectCopyMap() (map[string]string, error) {
+-	h, err := gophercloud.BuildHeaders(opts)
+-	if err != nil {
+-		return nil, err
+-	}
+-	for k, v := range opts.Metadata {
+-		h["X-Object-Meta-"+k] = v
+-	}
+-	// `Content-Length` is required and a value of "0" is acceptable, but calling `gophercloud.BuildHeaders`
+-	// will remove the `Content-Length` header if it's set to 0 (or equivalently not set). This will add
+-	// the header if it's not already set.
+-	if _, ok := h["Content-Length"]; !ok {
+-		h["Content-Length"] = "0"
+-	}
+-	return h, nil
 -}
 -
--func (gsp *genericServersProvider) ShowKeyPair(name string) (KeyPair, error) {
--	var kp KeyPair
+-// Copy is a function that copies one object to another.
+-func Copy(c *gophercloud.ServiceClient, containerName, objectName string, opts os.CopyOptsBuilder) os.CopyResult {
+-	return os.Copy(c, containerName, objectName, opts)
+-}
 -
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		url := gsp.endpoint + "/os-keypairs/" + name
--		return perigee.Get(url, perigee.Options{
--			CustomClient: gsp.context.httpClient,
--			Results:      &struct{ KeyPair *KeyPair }{&kp},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--		})
--	})
--	return kp, err
+-// Delete is a function that deletes an object.
+-func Delete(c *gophercloud.ServiceClient, containerName, objectName string, opts os.DeleteOptsBuilder) os.DeleteResult {
+-	return os.Delete(c, containerName, objectName, opts)
 -}
 -
--type KeyPair struct {
--	FingerPrint string `json:"fingerprint"`
--	Name        string `json:"name"`
--	PrivateKey  string `json:"private_key,omitempty"`
--	PublicKey   string `json:"public_key"`
--	UserID      string `json:"user_id,omitempty"`
+-// Get is a function that retrieves the metadata of an object. To extract just the custom
+-// metadata, pass the GetResult response to the ExtractMetadata function.
+-func Get(c *gophercloud.ServiceClient, containerName, objectName string, opts os.GetOptsBuilder) os.GetResult {
+-	return os.Get(c, containerName, objectName, opts)
 -}
 -
--type NewKeyPair struct {
--	Name      string `json:"name"`
--	PublicKey string `json:"public_key,omitempty"`
+-// Update is a function that creates, updates, or deletes an object's metadata.
+-func Update(c *gophercloud.ServiceClient, containerName, objectName string, opts os.UpdateOptsBuilder) os.UpdateResult {
+-	return os.Update(c, containerName, objectName, opts)
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/osutil/auth.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/osutil/auth.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/objects/delegate_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/objects/delegate_test.go
 deleted file mode 100644
-index a411b63..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/osutil/auth.go
+index 08831ec..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/objects/delegate_test.go
 +++ /dev/null
-@@ -1,64 +0,0 @@
--package osutil
+@@ -1,115 +0,0 @@
+-package objects
 -
 -import (
--	"fmt"
--	"github.com/rackspace/gophercloud"
--	"os"
--	"strings"
+-	"bytes"
+-	"testing"
+-
+-	os "github.com/rackspace/gophercloud/openstack/objectstorage/v1/objects"
+-	"github.com/rackspace/gophercloud/pagination"
+-	th "github.com/rackspace/gophercloud/testhelper"
+-	fake "github.com/rackspace/gophercloud/testhelper/client"
 -)
 -
--var (
--	nilOptions = gophercloud.AuthOptions{}
+-func TestDownloadObject(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleDownloadObjectSuccessfully(t)
 -
--	// ErrNoAuthUrl errors occur when the value of the OS_AUTH_URL environment variable cannot be determined.
--	ErrNoAuthUrl = fmt.Errorf("Environment variable OS_AUTH_URL needs to be set.")
+-	content, err := Download(fake.ServiceClient(), "testContainer", "testObject", nil).ExtractContent()
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, string(content), "Successful download with Gophercloud")
+-}
 -
--	// ErrNoUsername errors occur when the value of the OS_USERNAME environment variable cannot be determined.
--	ErrNoUsername = fmt.Errorf("Environment variable OS_USERNAME needs to be set.")
+-func TestListObjectsInfo(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleListObjectsInfoSuccessfully(t)
 -
--	// ErrNoPassword errors occur when the value of the OS_PASSWORD environment variable cannot be determined.
--	ErrNoPassword = fmt.Errorf("Environment variable OS_PASSWORD or OS_API_KEY needs to be set.")
--)
+-	count := 0
+-	options := &os.ListOpts{Full: true}
+-	err := List(fake.ServiceClient(), "testContainer", options).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractInfo(page)
+-		th.AssertNoErr(t, err)
 -
--// AuthOptions fills out a gophercloud.AuthOptions structure with the settings found on the various OpenStack
--// OS_* environment variables.  The following variables provide sources of truth: OS_AUTH_URL, OS_USERNAME,
--// OS_PASSWORD, OS_TENANT_ID, and OS_TENANT_NAME.  Of these, OS_USERNAME, OS_PASSWORD, and OS_AUTH_URL must
--// have settings, or an error will result.  OS_TENANT_ID and OS_TENANT_NAME are optional.
--//
--// The value of OS_AUTH_URL will be returned directly to the caller, for subsequent use in
--// gophercloud.Authenticate()'s Provider parameter.  This function will not interpret the value of OS_AUTH_URL,
--// so as a convenient extention, you may set OS_AUTH_URL to, e.g., "rackspace-uk", or any other Gophercloud-recognized
--// provider shortcuts.  For broad compatibility, especially with local installations, you should probably
--// avoid the temptation to do this.
--func AuthOptions() (string, gophercloud.AuthOptions, error) {
--	provider := os.Getenv("OS_AUTH_URL")
--	username := os.Getenv("OS_USERNAME")
--	password := os.Getenv("OS_PASSWORD")
--	tenantId := os.Getenv("OS_TENANT_ID")
--	tenantName := os.Getenv("OS_TENANT_NAME")
+-		th.CheckDeepEquals(t, os.ExpectedListInfo, actual)
 -
--	if provider == "" {
--		return "", nilOptions, ErrNoAuthUrl
--	}
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, count, 1)
+-}
 -
--	if username == "" {
--		return "", nilOptions, ErrNoUsername
--	}
+-func TestListObjectNames(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleListObjectNamesSuccessfully(t)
 -
--	if password == "" {
--		return "", nilOptions, ErrNoPassword
--	}
+-	count := 0
+-	options := &os.ListOpts{Full: false}
+-	err := List(fake.ServiceClient(), "testContainer", options).EachPage(func(page pagination.Page) (bool, error) {
+-		count++
+-		actual, err := ExtractNames(page)
+-		if err != nil {
+-			t.Errorf("Failed to extract container names: %v", err)
+-			return false, err
+-		}
 -
--	ao := gophercloud.AuthOptions{
--		Username:   username,
--		Password:   password,
--		TenantId:   tenantId,
--		TenantName: tenantName,
--	}
+-		th.CheckDeepEquals(t, os.ExpectedListNames, actual)
 -
--	if !strings.HasSuffix(provider, "/tokens") {
--		provider += "/tokens"
--	}
+-		return true, nil
+-	})
+-	th.AssertNoErr(t, err)
+-	th.CheckEquals(t, count, 1)
+-}
+-
+-func TestCreateObject(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleCreateObjectSuccessfully(t)
 -
--	return provider, ao, nil
+-	content := bytes.NewBufferString("Did gyre and gimble in the wabe")
+-	options := &os.CreateOpts{ContentType: "application/json"}
+-	res := Create(fake.ServiceClient(), "testContainer", "testObject", content, options)
+-	th.AssertNoErr(t, res.Err)
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/osutil/region.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/osutil/region.go
-deleted file mode 100644
-index f7df507..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/osutil/region.go
-+++ /dev/null
-@@ -1,9 +0,0 @@
--package osutil
 -
--import "os"
+-func TestCopyObject(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleCopyObjectSuccessfully(t)
 -
--// Region provides a means of querying the OS_REGION_NAME environment variable.
--// At present, you may also use os.Getenv("OS_REGION_NAME") as well.
--func Region() string {
--	return os.Getenv("OS_REGION_NAME")
+-	options := &CopyOpts{Destination: "/newTestContainer/newTestObject"}
+-	res := Copy(fake.ServiceClient(), "testContainer", "testObject", options)
+-	th.AssertNoErr(t, res.Err)
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/package.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/package.go
-deleted file mode 100644
-index 396e523..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/package.go
-+++ /dev/null
-@@ -1,7 +0,0 @@
--// Gophercloud provides a multi-vendor interface to OpenStack-compatible clouds which attempts to follow
--// established Go community coding standards and social norms.
--//
--// Unless you intend on contributing code to the SDK, you will almost certainly never have to use any
--// Context structures or any of its methods.  Contextual methods exist for easier unit testing only.
--// Stick with the global functions unless you know exactly what you're doing, and why.
--package gophercloud
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/reauth.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/reauth.go
-deleted file mode 100644
-index 342aca4..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/reauth.go
-+++ /dev/null
-@@ -1,36 +0,0 @@
--package gophercloud
 -
--import (
--	"github.com/racker/perigee"
--)
+-func TestDeleteObject(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleDeleteObjectSuccessfully(t)
 -
--// WithReauth wraps a Perigee request fragment with logic to perform re-authentication
--// if it's deemed necessary.
--//
--// Do not confuse this function with WithReauth()!  Although they work together to support reauthentication,
--// WithReauth() actually contains the decision-making logic to determine when to perform a reauth,
--// while WithReauthHandler() is used to configure what a reauth actually entails.
--func (c *Context) WithReauth(ap AccessProvider, f func() error) error {
--	err := f()
--	cause, ok := err.(*perigee.UnexpectedResponseCodeError)
--	if ok && cause.Actual == 401 {
--		err = c.reauthHandler(ap)
--		if err == nil {
--			err = f()
--		}
--	}
--	return err
+-	res := Delete(fake.ServiceClient(), "testContainer", "testObject", nil)
+-	th.AssertNoErr(t, res.Err)
 -}
 -
--// This is like WithReauth above but returns a perigee Response object
--func (c *Context) ResponseWithReauth(ap AccessProvider, f func() (*perigee.Response, error)) (*perigee.Response, error) {
--	response, err := f()
--	cause, ok := err.(*perigee.UnexpectedResponseCodeError)
--	if ok && cause.Actual == 401 {
--		err = c.reauthHandler(ap)
--		if err == nil {
--			response, err = f()
--		}
--	}
--	return response, err
+-func TestUpdateObject(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleUpdateObjectSuccessfully(t)
+-
+-	options := &os.UpdateOpts{Metadata: map[string]string{"Gophercloud-Test": "objects"}}
+-	res := Update(fake.ServiceClient(), "testContainer", "testObject", options)
+-	th.AssertNoErr(t, res.Err)
+-}
+-
+-func TestGetObject(t *testing.T) {
+-	th.SetupHTTP()
+-	defer th.TeardownHTTP()
+-	os.HandleGetObjectSuccessfully(t)
+-
+-	expected := map[string]string{"Gophercloud-Test": "objects"}
+-	actual, err := Get(fake.ServiceClient(), "testContainer", "testObject", nil).ExtractMetadata()
+-	th.AssertNoErr(t, err)
+-	th.CheckDeepEquals(t, expected, actual)
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/reauth_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/reauth_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/objects/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/objects/doc.go
 deleted file mode 100644
-index e3501b8..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/reauth_test.go
+index 781984b..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/rackspace/objectstorage/v1/objects/doc.go
 +++ /dev/null
-@@ -1,133 +0,0 @@
+@@ -1,3 +0,0 @@
+-// Package objects provides information and interaction with the Object
+-// API resource for the Rackspace Cloud Files service.
+-package objects
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/results.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/results.go
+deleted file mode 100644
+index f480bc7..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/results.go
++++ /dev/null
+@@ -1,83 +0,0 @@
 -package gophercloud
 -
 -import (
--	"github.com/racker/perigee"
--	"testing"
+-	"encoding/json"
+-	"net/http"
 -)
 -
--// This reauth-handler does nothing, and returns no error.
--func doNothing(_ AccessProvider) error {
--	return nil
--}
+-// Result acts as a base struct that other results can embed.
+-type Result struct {
+-	// Body is the payload of the HTTP response from the server. In most cases, this will be the
+-	// deserialized JSON structure.
+-	Body interface{}
 -
--func TestOtherErrorsPropegate(t *testing.T) {
--	calls := 0
--	c := TestContext().WithReauthHandler(doNothing)
+-	// Header contains the HTTP header structure from the original response.
+-	Header http.Header
 -
--	err := c.WithReauth(nil, func() error {
--		calls++
--		return &perigee.UnexpectedResponseCodeError{
--			Expected: []int{204},
--			Actual:   404,
--		}
--	})
+-	// Err is an error that occurred during the operation. It's deferred until extraction to make
+-	// it easier to chain operations.
+-	Err error
+-}
 -
--	if err == nil {
--		t.Error("Expected MyError to be returned; got nil instead.")
--		return
--	}
--	if _, ok := err.(*perigee.UnexpectedResponseCodeError); !ok {
--		t.Error("Expected UnexpectedResponseCodeError; got %#v", err)
--		return
--	}
--	if calls != 1 {
--		t.Errorf("Expected the body to be invoked once; found %d calls instead", calls)
--		return
+-// PrettyPrintJSON creates a string containing the full response body as pretty-printed JSON.
+-func (r Result) PrettyPrintJSON() string {
+-	pretty, err := json.MarshalIndent(r.Body, "", "  ")
+-	if err != nil {
+-		panic(err.Error())
 -	}
+-	return string(pretty)
 -}
 -
--func Test401ErrorCausesBodyInvokation2ndTime(t *testing.T) {
--	calls := 0
--	c := TestContext().WithReauthHandler(doNothing)
--
--	err := c.WithReauth(nil, func() error {
--		calls++
--		return &perigee.UnexpectedResponseCodeError{
--			Expected: []int{204},
--			Actual:   401,
--		}
--	})
+-// ErrResult represents results that only contain a potential error and
+-// nothing else. Usually if the operation executed successfully, the Err field
+-// will be nil; otherwise it will be stocked with a relevant error.
+-type ErrResult struct {
+-	Result
+-}
 -
--	if err == nil {
--		t.Error("Expected MyError to be returned; got nil instead.")
--		return
--	}
--	if calls != 2 {
--		t.Errorf("Expected the body to be invoked once; found %d calls instead", calls)
--		return
--	}
+-// ExtractErr is a function that extracts error information from a result.
+-func (r ErrResult) ExtractErr() error {
+-	return r.Err
 -}
 -
--func TestReauthAttemptShouldHappen(t *testing.T) {
--	calls := 0
--	c := TestContext().WithReauthHandler(func(_ AccessProvider) error {
--		calls++
--		return nil
--	})
--	c.WithReauth(nil, func() error {
--		return &perigee.UnexpectedResponseCodeError{
--			Expected: []int{204},
--			Actual:   401,
--		}
--	})
+-// HeaderResult represents a result that only contains an `error` (possibly nil)
+-// and an http.Header. This is used, for example, by the `objectstorage` packages
+-// in `openstack`, because most of the operations don't return response bodies.
+-type HeaderResult struct {
+-	Result
+-}
 -
--	if calls != 1 {
--		t.Errorf("Expected Reauthenticator to be called once; found %d instead", calls)
--		return
--	}
+-// ExtractHeader will return the http.Header and error from the HeaderResult.
+-// Usage: header, err := objects.Create(client, "my_container", objects.CreateOpts{}).ExtractHeader()
+-func (hr HeaderResult) ExtractHeader() (http.Header, error) {
+-	return hr.Header, hr.Err
 -}
 -
--type MyError struct{}
+-// RFC3339Milli describes a time format used by API responses.
+-const RFC3339Milli = "2006-01-02T15:04:05.999999Z"
 -
--func (*MyError) Error() string {
--	return "MyError instance"
+-// Link represents a structure that enables paginated collections how to
+-// traverse backward or forward. The "Rel" field is usually either "next".
+-type Link struct {
+-	Href string `mapstructure:"href"`
+-	Rel  string `mapstructure:"rel"`
 -}
 -
--func TestReauthErrorShouldPropegate(t *testing.T) {
--	c := TestContext().WithReauthHandler(func(_ AccessProvider) error {
--		return &MyError{}
--	})
+-// ExtractNextURL attempts to extract the next URL from a JSON structure. It
+-// follows the common convention of nesting back and next URLs in a "links"
+-// JSON array.
+-func ExtractNextURL(links []Link) (string, error) {
+-	var url string
 -
--	err := c.WithReauth(nil, func() error {
--		return &perigee.UnexpectedResponseCodeError{
--			Expected: []int{204},
--			Actual:   401,
+-	for _, l := range links {
+-		if l.Rel == "next" {
+-			url = l.Href
 -		}
--	})
--
--	if _, ok := err.(*MyError); !ok {
--		t.Errorf("Expected a MyError; got %#v", err)
--		return
 -	}
--}
 -
--type MyAccess struct{}
+-	if url == "" {
+-		return "", nil
+-	}
 -
--func (my *MyAccess) FirstEndpointUrlByCriteria(ApiCriteria) string {
--	return ""
--}
--func (my *MyAccess) AuthToken() string {
--	return ""
--}
--func (my *MyAccess) Revoke(string) error {
--	return nil
--}
--func (my *MyAccess) Reauthenticate() error {
--	return nil
+-	return url, nil
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/script/acceptancetest b/Godeps/_workspace/src/github.com/rackspace/gophercloud/script/acceptancetest
+deleted file mode 100644
+index f9c89f4..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/script/acceptancetest
++++ /dev/null
+@@ -1,5 +0,0 @@
+-#!/bin/bash
+-#
+-# Run the acceptance tests.
 -
--func TestReauthHandlerUsesSameAccessProvider(t *testing.T) {
--	fakeAccess := &MyAccess{}
--	c := TestContext().WithReauthHandler(func(acc AccessProvider) error {
--		if acc != fakeAccess {
--			t.Errorf("Expected acc = fakeAccess")
--		}
--		return nil
--	})
--	c.WithReauth(fakeAccess, func() error {
--		return &perigee.UnexpectedResponseCodeError{
--			Expected: []int{204},
--			Actual:   401,
--		}
--	})
--}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/scripts/create-environment.sh b/Godeps/_workspace/src/github.com/rackspace/gophercloud/scripts/create-environment.sh
+-exec go test -p=1 -tags 'acceptance fixtures' github.com/rackspace/gophercloud/acceptance/... $@
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/script/bootstrap b/Godeps/_workspace/src/github.com/rackspace/gophercloud/script/bootstrap
 deleted file mode 100644
 index 6bae6e8..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/scripts/create-environment.sh
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/script/bootstrap
 +++ /dev/null
 @@ -1,26 +0,0 @@
 -#!/bin/bash
@@ -83877,1307 +143597,626 @@ index 6bae6e8..0000000
 -# Make changes immediately available as a convenience.
 -. ./env.sh
 -
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/scripts/test-all.sh b/Godeps/_workspace/src/github.com/rackspace/gophercloud/scripts/test-all.sh
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/script/cibuild b/Godeps/_workspace/src/github.com/rackspace/gophercloud/script/cibuild
 deleted file mode 100644
-index 096736f..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/scripts/test-all.sh
+index 1cb389e..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/script/cibuild
 +++ /dev/null
-@@ -1,37 +0,0 @@
+@@ -1,5 +0,0 @@
 -#!/bin/bash
 -#
--# This script is responsible for executing all the acceptance tests found in
--# the acceptance/ directory.
--
--# Find where _this_ script is running from.
--SCRIPTS=$(dirname $0)
--SCRIPTS=$(cd $SCRIPTS; pwd)
--
--# Locate the acceptance test / examples directory.
--ACCEPTANCE=$(cd $SCRIPTS/../acceptance; pwd)
--
--# Go workspace path
--WS=$(cd $SCRIPTS/..; pwd)
--
--# In order to run Go code interactively, we need the GOPATH environment
--# to be set.
--if [ "x$GOPATH" == "x" ]; then
--  export GOPATH=$WS
--  echo "WARNING: You didn't have your GOPATH environment variable set."
--  echo "         I'm assuming $GOPATH as its value."
--fi
--
--# Run all acceptance tests sequentially.
--# If any test fails, we fail fast.
--LIBS=$(ls $ACCEPTANCE/lib*.go)
--for T in $(ls -1 $ACCEPTANCE/[0-9][0-9]*.go); do
--  if ! [ -x $T ]; then
--    CMD="go run $T $LIBS -quiet"
--    echo "$CMD ..."
--    if ! $CMD ; then
--      echo "- FAILED.  Try re-running w/out the -quiet option to see output."
--      exit 1
--    fi
--  fi
--done
+-# Test script to be invoked by Travis.
 -
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/servers.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/servers.go
+-exec script/unittest -v
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/script/test b/Godeps/_workspace/src/github.com/rackspace/gophercloud/script/test
 deleted file mode 100644
-index 1f6a7a4..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/servers.go
+index 1e03dff..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/script/test
 +++ /dev/null
-@@ -1,807 +0,0 @@
--// TODO(sfalvo): Remove Rackspace-specific Server structure fields and refactor them into a provider-specific access method.
--// Be sure to update godocs accordingly.
+@@ -1,5 +0,0 @@
+-#!/bin/bash
+-#
+-# Run all the tests.
 -
--package gophercloud
+-exec go test -tags 'acceptance fixtures' ./... $@
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/script/unittest b/Godeps/_workspace/src/github.com/rackspace/gophercloud/script/unittest
+deleted file mode 100644
+index d3440a9..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/script/unittest
++++ /dev/null
+@@ -1,5 +0,0 @@
+-#!/bin/bash
+-#
+-# Run the unit tests.
 -
--import (
--	"fmt"
--	"net/url"
--	"strings"
+-exec go test -tags fixtures ./... $@
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/service_client.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/service_client.go
+deleted file mode 100644
+index 3490da0..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/service_client.go
++++ /dev/null
+@@ -1,32 +0,0 @@
+-package gophercloud
 -
--	"github.com/mitchellh/mapstructure"
--	"github.com/racker/perigee"
--)
+-import "strings"
 -
--// genericServersProvider structures provide the implementation for generic OpenStack-compatible
--// CloudServersProvider interfaces.
--type genericServersProvider struct {
--	// endpoint refers to the provider's API endpoint base URL.  This will be used to construct
--	// and issue queries.
--	endpoint string
+-// ServiceClient stores details required to interact with a specific service API implemented by a provider.
+-// Generally, you'll acquire these by calling the appropriate `New` method on a ProviderClient.
+-type ServiceClient struct {
+-	// ProviderClient is a reference to the provider that implements this service.
+-	*ProviderClient
 -
--	// Test context (if any) in which to issue requests.
--	context *Context
+-	// Endpoint is the base URL of the service's API, acquired from a service catalog.
+-	// It MUST end with a /.
+-	Endpoint string
 -
--	// access associates this API provider with a set of credentials,
--	// which may be automatically renewed if they near expiration.
--	access AccessProvider
+-	// ResourceBase is the base URL shared by the resources within a service's API. It should include
+-	// the API version and, like Endpoint, MUST end with a / if set. If not set, the Endpoint is used
+-	// as-is, instead.
+-	ResourceBase string
 -}
 -
--// See the CloudServersProvider interface for details.
--func (gcp *genericServersProvider) ListServersByFilter(filter url.Values) ([]Server, error) {
--	var ss []Server
--
--	err := gcp.context.WithReauth(gcp.access, func() error {
--		url := gcp.endpoint + "/servers/detail?" + filter.Encode()
--		return perigee.Get(url, perigee.Options{
--			CustomClient: gcp.context.httpClient,
--			Results:      &struct{ Servers *[]Server }{&ss},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gcp.access.AuthToken(),
--			},
--		})
--	})
--	return ss, err
+-// ResourceBaseURL returns the base URL of any resources used by this service. It MUST end with a /.
+-func (client *ServiceClient) ResourceBaseURL() string {
+-	if client.ResourceBase != "" {
+-		return client.ResourceBase
+-	}
+-	return client.Endpoint
 -}
 -
--// See the CloudServersProvider interface for details.
--func (gcp *genericServersProvider) ListServersLinksOnly() ([]Server, error) {
--	var ss []Server
--
--	err := gcp.context.WithReauth(gcp.access, func() error {
--		url := gcp.endpoint + "/servers"
--		return perigee.Get(url, perigee.Options{
--			CustomClient: gcp.context.httpClient,
--			Results:      &struct{ Servers *[]Server }{&ss},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gcp.access.AuthToken(),
--			},
--		})
--	})
--	return ss, err
+-// ServiceURL constructs a URL for a resource belonging to this provider.
+-func (client *ServiceClient) ServiceURL(parts ...string) string {
+-	return client.ResourceBaseURL() + strings.Join(parts, "/")
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/service_client_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/service_client_test.go
+deleted file mode 100644
+index 84beb3f..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/service_client_test.go
++++ /dev/null
+@@ -1,14 +0,0 @@
+-package gophercloud
 -
--// See the CloudServersProvider interface for details.
--func (gcp *genericServersProvider) ListServers() ([]Server, error) {
--	var ss []Server
--
--	err := gcp.context.WithReauth(gcp.access, func() error {
--		url := gcp.endpoint + "/servers/detail"
--		return perigee.Get(url, perigee.Options{
--			CustomClient: gcp.context.httpClient,
--			Results:      &struct{ Servers *[]Server }{&ss},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gcp.access.AuthToken(),
--			},
--		})
--	})
--
--	// Compatibility with v0.0.x -- we "map" our public and private
--	// addresses into a legacy structure field for the benefit of
--	// earlier software.
--
--	if err != nil {
--		return ss, err
--	}
+-import (
+-	"testing"
 -
--	for _, s := range ss {
--		err = mapstructure.Decode(s.RawAddresses, &s.Addresses)
--		if err != nil {
--			return ss, err
--		}
--	}
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--	return ss, err
+-func TestServiceURL(t *testing.T) {
+-	c := &ServiceClient{Endpoint: "http://123.45.67.8/"}
+-	expected := "http://123.45.67.8/more/parts/here"
+-	actual := c.ServiceURL("more", "parts", "here")
+-	th.CheckEquals(t, expected, actual)
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/testhelper/client/fake.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/testhelper/client/fake.go
+deleted file mode 100644
+index 5b69b05..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/testhelper/client/fake.go
++++ /dev/null
+@@ -1,17 +0,0 @@
+-package client
 -
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) ServerById(id string) (*Server, error) {
--	var s *Server
--
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		url := gsp.endpoint + "/servers/" + id
--		return perigee.Get(url, perigee.Options{
--			Results: &struct{ Server **Server }{&s},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			OkCodes: []int{200},
--		})
--	})
+-import (
+-	"github.com/rackspace/gophercloud"
+-	"github.com/rackspace/gophercloud/testhelper"
+-)
 -
--	// Compatibility with v0.0.x -- we "map" our public and private
--	// addresses into a legacy structure field for the benefit of
--	// earlier software.
+-// Fake token to use.
+-const TokenID = "cbc36478b0bd8e67e89469c7749d4127"
 -
--	if err != nil {
--		return s, err
+-// ServiceClient returns a generic service client for use in tests.
+-func ServiceClient() *gophercloud.ServiceClient {
+-	return &gophercloud.ServiceClient{
+-		ProviderClient: &gophercloud.ProviderClient{TokenID: TokenID},
+-		Endpoint:       testhelper.Endpoint(),
 -	}
--
--	err = mapstructure.Decode(s.RawAddresses, &s.Addresses)
--
--	return s, err
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/testhelper/convenience.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/testhelper/convenience.go
+deleted file mode 100644
+index cf33e1a..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/testhelper/convenience.go
++++ /dev/null
+@@ -1,329 +0,0 @@
+-package testhelper
 -
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) CreateServer(ns NewServer) (*NewServer, error) {
--	var s *NewServer
+-import (
+-	"encoding/json"
+-	"fmt"
+-	"path/filepath"
+-	"reflect"
+-	"runtime"
+-	"strings"
+-	"testing"
+-)
 -
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		ep := gsp.endpoint + "/servers"
--		return perigee.Post(ep, perigee.Options{
--			ReqBody: &struct {
--				Server *NewServer `json:"server"`
--			}{&ns},
--			Results: &struct{ Server **NewServer }{&s},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			OkCodes: []int{202},
--		})
--	})
+-const (
+-	logBodyFmt = "\033[1;31m%s %s\033[0m"
+-	greenCode  = "\033[0m\033[1;32m"
+-	yellowCode = "\033[0m\033[1;33m"
+-	resetCode  = "\033[0m\033[1;31m"
+-)
 -
--	return s, err
+-func prefix(depth int) string {
+-	_, file, line, _ := runtime.Caller(depth)
+-	return fmt.Sprintf("Failure in %s, line %d:", filepath.Base(file), line)
 -}
 -
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) DeleteServerById(id string) error {
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		url := gsp.endpoint + "/servers/" + id
--		return perigee.Delete(url, perigee.Options{
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			OkCodes: []int{204},
--		})
--	})
--	return err
+-func green(str interface{}) string {
+-	return fmt.Sprintf("%s%#v%s", greenCode, str, resetCode)
 -}
 -
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) SetAdminPassword(id, pw string) error {
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		url := fmt.Sprintf("%s/servers/%s/action", gsp.endpoint, id)
--		return perigee.Post(url, perigee.Options{
--			ReqBody: &struct {
--				ChangePassword struct {
--					AdminPass string `json:"adminPass"`
--				} `json:"changePassword"`
--			}{
--				struct {
--					AdminPass string `json:"adminPass"`
--				}{pw},
--			},
--			OkCodes: []int{202},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--		})
--	})
--	return err
+-func yellow(str interface{}) string {
+-	return fmt.Sprintf("%s%#v%s", yellowCode, str, resetCode)
 -}
 -
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) ResizeServer(id, newName, newFlavor, newDiskConfig string) error {
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		url := fmt.Sprintf("%s/servers/%s/action", gsp.endpoint, id)
--		rr := ResizeRequest{
--			Name:       newName,
--			FlavorRef:  newFlavor,
--			DiskConfig: newDiskConfig,
--		}
--		return perigee.Post(url, perigee.Options{
--			ReqBody: &struct {
--				Resize ResizeRequest `json:"resize"`
--			}{rr},
--			OkCodes: []int{202},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--		})
--	})
--	return err
+-func logFatal(t *testing.T, str string) {
+-	t.Fatalf(logBodyFmt, prefix(3), str)
 -}
 -
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) RevertResize(id string) error {
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		url := fmt.Sprintf("%s/servers/%s/action", gsp.endpoint, id)
--		return perigee.Post(url, perigee.Options{
--			ReqBody: &struct {
--				RevertResize *int `json:"revertResize"`
--			}{nil},
--			OkCodes: []int{202},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--		})
--	})
--	return err
+-func logError(t *testing.T, str string) {
+-	t.Errorf(logBodyFmt, prefix(3), str)
 -}
 -
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) ConfirmResize(id string) error {
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		url := fmt.Sprintf("%s/servers/%s/action", gsp.endpoint, id)
--		return perigee.Post(url, perigee.Options{
--			ReqBody: &struct {
--				ConfirmResize *int `json:"confirmResize"`
--			}{nil},
--			OkCodes: []int{204},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--		})
--	})
--	return err
--}
+-type diffLogger func([]string, interface{}, interface{})
 -
--// See the CloudServersProvider interface for details
--func (gsp *genericServersProvider) RebootServer(id string, hard bool) error {
--	return gsp.context.WithReauth(gsp.access, func() error {
--		url := fmt.Sprintf("%s/servers/%s/action", gsp.endpoint, id)
--		types := map[bool]string{false: "SOFT", true: "HARD"}
--		return perigee.Post(url, perigee.Options{
--			ReqBody: &struct {
--				Reboot struct {
--					Type string `json:"type"`
--				} `json:"reboot"`
--			}{
--				struct {
--					Type string `json:"type"`
--				}{types[hard]},
--			},
--			OkCodes: []int{202},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--		})
--	})
+-type visit struct {
+-	a1  uintptr
+-	a2  uintptr
+-	typ reflect.Type
 -}
 -
--// See the CloudServersProvider interface for details
--func (gsp *genericServersProvider) RescueServer(id string) (string, error) {
--	var pw *string
+-// Recursively visits the structures of "expected" and "actual". The diffLogger function will be
+-// invoked with each different value encountered, including the reference path that was followed
+-// to get there.
+-func deepDiffEqual(expected, actual reflect.Value, visited map[visit]bool, path []string, logDifference diffLogger) {
+-	defer func() {
+-		// Fall back to the regular reflect.DeepEquals function.
+-		if r := recover(); r != nil {
+-			var e, a interface{}
+-			if expected.IsValid() {
+-				e = expected.Interface()
+-			}
+-			if actual.IsValid() {
+-				a = actual.Interface()
+-			}
 -
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		url := fmt.Sprintf("%s/servers/%s/action", gsp.endpoint, id)
--		return perigee.Post(url, perigee.Options{
--			ReqBody: &struct {
--				Rescue string `json:"rescue"`
--			}{"none"},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			Results: &struct {
--				AdminPass **string `json:"adminPass"`
--			}{&pw},
--		})
--	})
--	return *pw, err
--}
+-			if !reflect.DeepEqual(e, a) {
+-				logDifference(path, e, a)
+-			}
+-		}
+-	}()
 -
--// See the CloudServersProvider interface for details
--func (gsp *genericServersProvider) UnrescueServer(id string) error {
--	return gsp.context.WithReauth(gsp.access, func() error {
--		url := fmt.Sprintf("%s/servers/%s/action", gsp.endpoint, id)
--		return perigee.Post(url, perigee.Options{
--			ReqBody: &struct {
--				Unrescue *int `json:"unrescue"`
--			}{nil},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			OkCodes: []int{202},
--		})
--	})
--}
+-	if !expected.IsValid() && actual.IsValid() {
+-		logDifference(path, nil, actual.Interface())
+-		return
+-	}
+-	if expected.IsValid() && !actual.IsValid() {
+-		logDifference(path, expected.Interface(), nil)
+-		return
+-	}
+-	if !expected.IsValid() && !actual.IsValid() {
+-		return
+-	}
 -
--// See the CloudServersProvider interface for details
--func (gsp *genericServersProvider) UpdateServer(id string, changes NewServerSettings) (*Server, error) {
--	var svr *Server
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		url := fmt.Sprintf("%s/servers/%s", gsp.endpoint, id)
--		return perigee.Put(url, perigee.Options{
--			ReqBody: &struct {
--				Server NewServerSettings `json:"server"`
--			}{changes},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			Results: &struct {
--				Server **Server `json:"server"`
--			}{&svr},
--		})
--	})
--	return svr, err
--}
+-	hard := func(k reflect.Kind) bool {
+-		switch k {
+-		case reflect.Array, reflect.Map, reflect.Slice, reflect.Struct:
+-			return true
+-		}
+-		return false
+-	}
 -
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) RebuildServer(id string, ns NewServer) (*Server, error) {
--	var s *Server
+-	if expected.CanAddr() && actual.CanAddr() && hard(expected.Kind()) {
+-		addr1 := expected.UnsafeAddr()
+-		addr2 := actual.UnsafeAddr()
 -
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		ep := fmt.Sprintf("%s/servers/%s/action", gsp.endpoint, id)
--		return perigee.Post(ep, perigee.Options{
--			ReqBody: &struct {
--				Rebuild *NewServer `json:"rebuild"`
--			}{&ns},
--			Results: &struct{ Server **Server }{&s},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			OkCodes: []int{202},
--		})
--	})
+-		if addr1 > addr2 {
+-			addr1, addr2 = addr2, addr1
+-		}
 -
--	return s, err
--}
+-		if addr1 == addr2 {
+-			// References are identical. We can short-circuit
+-			return
+-		}
 -
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) ListAddresses(id string) (AddressSet, error) {
--	var pas *AddressSet
--	var statusCode int
+-		typ := expected.Type()
+-		v := visit{addr1, addr2, typ}
+-		if visited[v] {
+-			// Already visited.
+-			return
+-		}
 -
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		ep := fmt.Sprintf("%s/servers/%s/ips", gsp.endpoint, id)
--		return perigee.Get(ep, perigee.Options{
--			Results: &struct{ Addresses **AddressSet }{&pas},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			OkCodes:    []int{200, 203},
--			StatusCode: &statusCode,
--		})
--	})
+-		// Remember this visit for later.
+-		visited[v] = true
+-	}
 -
--	if err != nil {
--		if statusCode == 203 {
--			err = WarnUnauthoritative
+-	switch expected.Kind() {
+-	case reflect.Array:
+-		for i := 0; i < expected.Len(); i++ {
+-			hop := append(path, fmt.Sprintf("[%d]", i))
+-			deepDiffEqual(expected.Index(i), actual.Index(i), visited, hop, logDifference)
+-		}
+-		return
+-	case reflect.Slice:
+-		if expected.IsNil() != actual.IsNil() {
+-			logDifference(path, expected.Interface(), actual.Interface())
+-			return
+-		}
+-		if expected.Len() == actual.Len() && expected.Pointer() == actual.Pointer() {
+-			return
+-		}
+-		for i := 0; i < expected.Len(); i++ {
+-			hop := append(path, fmt.Sprintf("[%d]", i))
+-			deepDiffEqual(expected.Index(i), actual.Index(i), visited, hop, logDifference)
+-		}
+-		return
+-	case reflect.Interface:
+-		if expected.IsNil() != actual.IsNil() {
+-			logDifference(path, expected.Interface(), actual.Interface())
+-			return
+-		}
+-		deepDiffEqual(expected.Elem(), actual.Elem(), visited, path, logDifference)
+-		return
+-	case reflect.Ptr:
+-		deepDiffEqual(expected.Elem(), actual.Elem(), visited, path, logDifference)
+-		return
+-	case reflect.Struct:
+-		for i, n := 0, expected.NumField(); i < n; i++ {
+-			field := expected.Type().Field(i)
+-			hop := append(path, "."+field.Name)
+-			deepDiffEqual(expected.Field(i), actual.Field(i), visited, hop, logDifference)
+-		}
+-		return
+-	case reflect.Map:
+-		if expected.IsNil() != actual.IsNil() {
+-			logDifference(path, expected.Interface(), actual.Interface())
+-			return
+-		}
+-		if expected.Len() == actual.Len() && expected.Pointer() == actual.Pointer() {
+-			return
 -		}
--	}
 -
--	return *pas, err
--}
+-		var keys []reflect.Value
+-		if expected.Len() >= actual.Len() {
+-			keys = expected.MapKeys()
+-		} else {
+-			keys = actual.MapKeys()
+-		}
 -
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) ListAddressesByNetwork(id, networkLabel string) (NetworkAddress, error) {
--	pas := make(NetworkAddress)
--	var statusCode int
+-		for _, k := range keys {
+-			expectedValue := expected.MapIndex(k)
+-			actualValue := expected.MapIndex(k)
 -
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		ep := fmt.Sprintf("%s/servers/%s/ips/%s", gsp.endpoint, id, networkLabel)
--		return perigee.Get(ep, perigee.Options{
--			Results: &pas,
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			OkCodes:    []int{200, 203},
--			StatusCode: &statusCode,
--		})
--	})
+-			if !expectedValue.IsValid() {
+-				logDifference(path, nil, actual.Interface())
+-				return
+-			}
+-			if !actualValue.IsValid() {
+-				logDifference(path, expected.Interface(), nil)
+-				return
+-			}
 -
--	if err != nil {
--		if statusCode == 203 {
--			err = WarnUnauthoritative
+-			hop := append(path, fmt.Sprintf("[%v]", k))
+-			deepDiffEqual(expectedValue, actualValue, visited, hop, logDifference)
+-		}
+-		return
+-	case reflect.Func:
+-		if expected.IsNil() != actual.IsNil() {
+-			logDifference(path, expected.Interface(), actual.Interface())
+-		}
+-		return
+-	default:
+-		if expected.Interface() != actual.Interface() {
+-			logDifference(path, expected.Interface(), actual.Interface())
 -		}
 -	}
--
--	return pas, err
 -}
 -
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) CreateImage(id string, ci CreateImage) (string, error) {
--	response, err := gsp.context.ResponseWithReauth(gsp.access, func() (*perigee.Response, error) {
--		ep := fmt.Sprintf("%s/servers/%s/action", gsp.endpoint, id)
--		return perigee.Request("POST", ep, perigee.Options{
--			ReqBody: &struct {
--				CreateImage *CreateImage `json:"createImage"`
--			}{&ci},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			OkCodes: []int{200, 202},
--		})
--	})
--
--	if err != nil {
--		return "", err
--	}
--	location, err := response.HttpResponse.Location()
--	if err != nil {
--		return "", err
+-func deepDiff(expected, actual interface{}, logDifference diffLogger) {
+-	if expected == nil || actual == nil {
+-		logDifference([]string{}, expected, actual)
+-		return
 -	}
 -
--	// Return the last element of the location which is the image id
--	locationArr := strings.Split(location.Path, "/")
--	return locationArr[len(locationArr)-1], err
--}
--
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) ListSecurityGroups() ([]SecurityGroup, error) {
--	var sgs []SecurityGroup
--
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		ep := fmt.Sprintf("%s/os-security-groups", gsp.endpoint)
--		return perigee.Get(ep, perigee.Options{
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			Results: &struct {
--				SecurityGroups *[]SecurityGroup `json:"security_groups"`
--			}{&sgs},
--		})
--	})
--	return sgs, err
--}
--
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) CreateSecurityGroup(desired SecurityGroup) (*SecurityGroup, error) {
--	var actual *SecurityGroup
+-	expectedValue := reflect.ValueOf(expected)
+-	actualValue := reflect.ValueOf(actual)
 -
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		ep := fmt.Sprintf("%s/os-security-groups", gsp.endpoint)
--		return perigee.Post(ep, perigee.Options{
--			ReqBody: struct {
--				AddSecurityGroup SecurityGroup `json:"security_group"`
--			}{desired},
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			Results: &struct {
--				SecurityGroup **SecurityGroup `json:"security_group"`
--			}{&actual},
--		})
--	})
--	return actual, err
+-	if expectedValue.Type() != actualValue.Type() {
+-		logDifference([]string{}, expected, actual)
+-		return
+-	}
+-	deepDiffEqual(expectedValue, actualValue, map[visit]bool{}, []string{}, logDifference)
 -}
 -
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) ListSecurityGroupsByServerId(id string) ([]SecurityGroup, error) {
--	var sgs []SecurityGroup
--
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		ep := fmt.Sprintf("%s/servers/%s/os-security-groups", gsp.endpoint, id)
--		return perigee.Get(ep, perigee.Options{
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			Results: &struct {
--				SecurityGroups *[]SecurityGroup `json:"security_groups"`
--			}{&sgs},
--		})
--	})
--	return sgs, err
+-// AssertEquals compares two arbitrary values and performs a comparison. If the
+-// comparison fails, a fatal error is raised that will fail the test
+-func AssertEquals(t *testing.T, expected, actual interface{}) {
+-	if expected != actual {
+-		logFatal(t, fmt.Sprintf("expected %s but got %s", green(expected), yellow(actual)))
+-	}
 -}
 -
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) SecurityGroupById(id int) (*SecurityGroup, error) {
--	var actual *SecurityGroup
--
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		ep := fmt.Sprintf("%s/os-security-groups/%d", gsp.endpoint, id)
--		return perigee.Get(ep, perigee.Options{
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			Results: &struct {
--				SecurityGroup **SecurityGroup `json:"security_group"`
--			}{&actual},
--		})
--	})
--	return actual, err
+-// CheckEquals is similar to AssertEquals, except with a non-fatal error
+-func CheckEquals(t *testing.T, expected, actual interface{}) {
+-	if expected != actual {
+-		logError(t, fmt.Sprintf("expected %s but got %s", green(expected), yellow(actual)))
+-	}
 -}
 -
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) DeleteSecurityGroupById(id int) error {
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		ep := fmt.Sprintf("%s/os-security-groups/%d", gsp.endpoint, id)
--		return perigee.Delete(ep, perigee.Options{
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			OkCodes: []int{202},
--		})
--	})
--	return err
--}
+-// AssertDeepEquals - like Equals - performs a comparison - but on more complex
+-// structures that requires deeper inspection
+-func AssertDeepEquals(t *testing.T, expected, actual interface{}) {
+-	pre := prefix(2)
 -
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) ListDefaultSGRules() ([]SGRule, error) {
--	var sgrs []SGRule
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		ep := fmt.Sprintf("%s/os-security-group-default-rules", gsp.endpoint)
--		return perigee.Get(ep, perigee.Options{
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			Results: &struct{ Security_group_default_rules *[]SGRule }{&sgrs},
--		})
+-	differed := false
+-	deepDiff(expected, actual, func(path []string, expected, actual interface{}) {
+-		differed = true
+-		t.Errorf("\033[1;31m%sat %s expected %s, but got %s\033[0m",
+-			pre,
+-			strings.Join(path, ""),
+-			green(expected),
+-			yellow(actual))
 -	})
--	return sgrs, err
+-	if differed {
+-		logFatal(t, "The structures were different.")
+-	}
 -}
 -
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) CreateDefaultSGRule(r SGRule) (*SGRule, error) {
--	var sgr *SGRule
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		ep := fmt.Sprintf("%s/os-security-group-default-rules", gsp.endpoint)
--		return perigee.Post(ep, perigee.Options{
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			Results: &struct{ Security_group_default_rule **SGRule }{&sgr},
--			ReqBody: struct {
--				Security_group_default_rule SGRule `json:"security_group_default_rule"`
--			}{r},
--		})
--	})
--	return sgr, err
--}
+-// CheckDeepEquals is similar to AssertDeepEquals, except with a non-fatal error
+-func CheckDeepEquals(t *testing.T, expected, actual interface{}) {
+-	pre := prefix(2)
 -
--// See the CloudServersProvider interface for details.
--func (gsp *genericServersProvider) GetSGRule(id string) (*SGRule, error) {
--	var sgr *SGRule
--	err := gsp.context.WithReauth(gsp.access, func() error {
--		ep := fmt.Sprintf("%s/os-security-group-default-rules/%s", gsp.endpoint, id)
--		return perigee.Get(ep, perigee.Options{
--			MoreHeaders: map[string]string{
--				"X-Auth-Token": gsp.access.AuthToken(),
--			},
--			Results: &struct{ Security_group_default_rule **SGRule }{&sgr},
--		})
+-	deepDiff(expected, actual, func(path []string, expected, actual interface{}) {
+-		t.Errorf("\033[1;31m%s at %s expected %s, but got %s\033[0m",
+-			pre,
+-			strings.Join(path, ""),
+-			green(expected),
+-			yellow(actual))
 -	})
--	return sgr, err
--}
--
--// SecurityGroup provides a description of a security group, including all its rules.
--type SecurityGroup struct {
--	Description string   `json:"description,omitempty"`
--	Id          int      `json:"id,omitempty"`
--	Name        string   `json:"name,omitempty"`
--	Rules       []SGRule `json:"rules,omitempty"`
--	TenantId    string   `json:"tenant_id,omitempty"`
--}
--
--// SGRule encapsulates a single rule which applies to a security group.
--// This definition is just a guess, based on the documentation found in another extension here: http://docs.openstack.org/api/openstack-compute/2/content/GET_os-security-group-default-rules-v2_listSecGroupDefaultRules_v2__tenant_id__os-security-group-rules_ext-os-security-group-default-rules.html
--type SGRule struct {
--	FromPort   int                    `json:"from_port,omitempty"`
--	Id         int                    `json:"id,omitempty"`
--	IpProtocol string                 `json:"ip_protocol,omitempty"`
--	IpRange    map[string]interface{} `json:"ip_range,omitempty"`
--	ToPort     int                    `json:"to_port,omitempty"`
--}
--
--// RaxBandwidth provides measurement of server bandwidth consumed over a given audit interval.
--type RaxBandwidth struct {
--	AuditPeriodEnd    string `json:"audit_period_end"`
--	AuditPeriodStart  string `json:"audit_period_start"`
--	BandwidthInbound  int64  `json:"bandwidth_inbound"`
--	BandwidthOutbound int64  `json:"bandwidth_outbound"`
--	Interface         string `json:"interface"`
 -}
 -
--// A VersionedAddress denotes either an IPv4 or IPv6 (depending on version indicated)
--// address.
--type VersionedAddress struct {
--	Addr    string `json:"addr"`
--	Version int    `json:"version"`
--}
+-// isJSONEquals is a utility function that implements JSON comparison for AssertJSONEquals and
+-// CheckJSONEquals.
+-func isJSONEquals(t *testing.T, expectedJSON string, actual interface{}) bool {
+-	var parsedExpected, parsedActual interface{}
+-	err := json.Unmarshal([]byte(expectedJSON), &parsedExpected)
+-	if err != nil {
+-		t.Errorf("Unable to parse expected value as JSON: %v", err)
+-		return false
+-	}
 -
--// An AddressSet provides a set of public and private IP addresses for a resource.
--// Each address has a version to identify if IPv4 or IPv6.
--type AddressSet struct {
--	Public  []VersionedAddress `json:"public"`
--	Private []VersionedAddress `json:"private"`
--}
+-	jsonActual, err := json.Marshal(actual)
+-	AssertNoErr(t, err)
+-	err = json.Unmarshal(jsonActual, &parsedActual)
+-	AssertNoErr(t, err)
 -
--type NetworkAddress map[string][]VersionedAddress
+-	if !reflect.DeepEqual(parsedExpected, parsedActual) {
+-		prettyExpected, err := json.MarshalIndent(parsedExpected, "", "  ")
+-		if err != nil {
+-			t.Logf("Unable to pretty-print expected JSON: %v\n%s", err, expectedJSON)
+-		} else {
+-			// We can't use green() here because %#v prints prettyExpected as a byte array literal, which
+-			// is... unhelpful. Converting it to a string first leaves "\n" uninterpreted for some reason.
+-			t.Logf("Expected JSON:\n%s%s%s", greenCode, prettyExpected, resetCode)
+-		}
 -
--// Server records represent (virtual) hardware instances (not configurations) accessible by the user.
--//
--// The AccessIPv4 / AccessIPv6 fields provides IP addresses for the server in the IPv4 or IPv6 format, respectively.
--//
--// Addresses provides addresses for any attached isolated networks.
--// The version field indicates whether the IP address is version 4 or 6.
--// Note: only public and private pools appear here.
--// To get the complete set, use the AllAddressPools() method instead.
--//
--// Created tells when the server entity was created.
--//
--// The Flavor field includes the flavor ID and flavor links.
--//
--// The compute provisioning algorithm has an anti-affinity property that
--// attempts to spread customer VMs across hosts.
--// Under certain situations,
--// VMs from the same customer might be placed on the same host.
--// The HostId field represents the host your server runs on and
--// can be used to determine this scenario if it is relevant to your application.
--// Note that HostId is unique only per account; it is not globally unique.
--//
--// Id provides the server's unique identifier.
--// This field must be treated opaquely.
--//
--// Image indicates which image is installed on the server.
--//
--// Links provides one or more means of accessing the server.
--//
--// Metadata provides a small key-value store for application-specific information.
--//
--// Name provides a human-readable name for the server.
--//
--// Progress indicates how far along it is towards being provisioned.
--// 100 represents complete, while 0 represents just beginning.
--//
--// Status provides an indication of what the server's doing at the moment.
--// A server will be in ACTIVE state if it's ready for use.
--//
--// OsDcfDiskConfig indicates the server's boot volume configuration.
--// Valid values are:
--//     AUTO
--//     ----
--//     The server is built with a single partition the size of the target flavor disk.
--//     The file system is automatically adjusted to fit the entire partition.
--//     This keeps things simple and automated.
--//     AUTO is valid only for images and servers with a single partition that use the EXT3 file system.
--//     This is the default setting for applicable Rackspace base images.
--//
--//     MANUAL
--//     ------
--//     The server is built using whatever partition scheme and file system is in the source image.
--//     If the target flavor disk is larger,
--//     the remaining disk space is left unpartitioned.
--//     This enables images to have non-EXT3 file systems, multiple partitions, and so on,
--//     and enables you to manage the disk configuration.
--//
--// RaxBandwidth provides measures of the server's inbound and outbound bandwidth per interface.
--//
--// OsExtStsPowerState provides an indication of the server's power.
--// This field appears to be a set of flag bits:
--//
--//           ... 4  3   2   1   0
--//         +--//--+---+---+---+---+
--//         | .... | 0 | S | 0 | I |
--//         +--//--+---+---+---+---+
--//                      |       |
--//                      |       +---  0=Instance is down.
--//                      |             1=Instance is up.
--//                      |
--//                      +-----------  0=Server is switched ON.
--//                                    1=Server is switched OFF.
--//                                    (note reverse logic.)
--//
--// Unused bits should be ignored when read, and written as 0 for future compatibility.
--//
--// OsExtStsTaskState and OsExtStsVmState work together
--// to provide visibility in the provisioning process for the instance.
--// Consult Rackspace documentation at
--// http://docs.rackspace.com/servers/api/v2/cs-devguide/content/ch_extensions.html#ext_status
--// for more details.  It's too lengthy to include here.
--type Server struct {
--	AccessIPv4         string `json:"accessIPv4"`
--	AccessIPv6         string `json:"accessIPv6"`
--	Addresses          AddressSet
--	Created            string            `json:"created"`
--	Flavor             FlavorLink        `json:"flavor"`
--	HostId             string            `json:"hostId"`
--	Id                 string            `json:"id"`
--	Image              ImageLink         `json:"image"`
--	Links              []Link            `json:"links"`
--	Metadata           map[string]string `json:"metadata"`
--	Name               string            `json:"name"`
--	Progress           int               `json:"progress"`
--	Status             string            `json:"status"`
--	TenantId           string            `json:"tenant_id"`
--	Updated            string            `json:"updated"`
--	UserId             string            `json:"user_id"`
--	OsDcfDiskConfig    string            `json:"OS-DCF:diskConfig"`
--	RaxBandwidth       []RaxBandwidth    `json:"rax-bandwidth:bandwidth"`
--	OsExtStsPowerState int               `json:"OS-EXT-STS:power_state"`
--	OsExtStsTaskState  string            `json:"OS-EXT-STS:task_state"`
--	OsExtStsVmState    string            `json:"OS-EXT-STS:vm_state"`
--
--	RawAddresses map[string]interface{} `json:"addresses"`
--}
--
--// AllAddressPools returns a complete set of address pools available on the server.
--// The name of each pool supported keys the map.
--// The value of the map contains the addresses provided in the corresponding pool.
--func (s *Server) AllAddressPools() (map[string][]VersionedAddress, error) {
--	pools := make(map[string][]VersionedAddress, 0)
--	for pool, subtree := range s.RawAddresses {
--		addresses := make([]VersionedAddress, 0)
--		err := mapstructure.Decode(subtree, &addresses)
+-		prettyActual, err := json.MarshalIndent(actual, "", "  ")
 -		if err != nil {
--			return nil, err
+-			t.Logf("Unable to pretty-print actual JSON: %v\n%#v", err, actual)
+-		} else {
+-			// We can't use yellow() for the same reason.
+-			t.Logf("Actual JSON:\n%s%s%s", yellowCode, prettyActual, resetCode)
 -		}
--		pools[pool] = addresses
+-
+-		return false
 -	}
--	return pools, nil
+-	return true
 -}
 -
--// NewServerSettings structures record those fields of the Server structure to change
--// when updating a server (see UpdateServer method).
--type NewServerSettings struct {
--	Name       string `json:"name,omitempty"`
--	AccessIPv4 string `json:"accessIPv4,omitempty"`
--	AccessIPv6 string `json:"accessIPv6,omitempty"`
+-// AssertJSONEquals serializes a value as JSON, parses an expected string as JSON, and ensures that
+-// both are consistent. If they aren't, the expected and actual structures are pretty-printed and
+-// shown for comparison.
+-//
+-// This is useful for comparing structures that are built as nested map[string]interface{} values,
+-// which are a pain to construct as literals.
+-func AssertJSONEquals(t *testing.T, expectedJSON string, actual interface{}) {
+-	if !isJSONEquals(t, expectedJSON, actual) {
+-		logFatal(t, "The generated JSON structure differed.")
+-	}
 -}
 -
--// NewServer structures are used for both requests and responses.
--// The fields discussed below are relevent for server-creation purposes.
--//
--// The Name field contains the desired name of the server.
--// Note that (at present) Rackspace permits more than one server with the same name;
--// however, software should not depend on this.
--// Not only will Rackspace support thank you, so will your own devops engineers.
--// A name is required.
--//
--// The ImageRef field contains the ID of the desired software image to place on the server.
--// This ID must be found in the image slice returned by the Images() function.
--// This field is required.
--//
--// The FlavorRef field contains the ID of the server configuration desired for deployment.
--// This ID must be found in the flavor slice returned by the Flavors() function.
--// This field is required.
--//
--// For OsDcfDiskConfig, refer to the Image or Server structure documentation.
--// This field defaults to "AUTO" if not explicitly provided.
--//
--// Metadata contains a small key/value association of arbitrary data.
--// Neither Rackspace nor OpenStack places significance on this field in any way.
--// This field defaults to an empty map if not provided.
--//
--// Personality specifies the contents of certain files in the server's filesystem.
--// The files and their contents are mapped through a slice of FileConfig structures.
--// If not provided, all filesystem entities retain their image-specific configuration.
--//
--// Networks specifies an affinity for the server's various networks and interfaces.
--// Networks are identified through UUIDs; see NetworkConfig structure documentation for more details.
--// If not provided, network affinity is determined automatically.
--//
--// The AdminPass field may be used to provide a root- or administrator-password
--// during the server provisioning process.
--// If not provided, a random password will be automatically generated and returned in this field.
--//
--// The following fields are intended to be used to communicate certain results about the server being provisioned.
--// When attempting to create a new server, these fields MUST not be provided.
--// They'll be filled in by the response received from the Rackspace APIs.
--//
--// The Id field contains the server's unique identifier.
--// The identifier's scope is best assumed to be bound by the user's account, unless other arrangements have been made with Rackspace.
--//
--// The SecurityGroup field allows the user to specify a security group at launch.
--//
--// Any Links provided are used to refer to the server specifically by URL.
--// These links are useful for making additional REST calls not explicitly supported by Gorax.
--type NewServer struct {
--	Name            string                   `json:"name,omitempty"`
--	ImageRef        string                   `json:"imageRef,omitempty"`
--	FlavorRef       string                   `json:"flavorRef,omitempty"`
--	Metadata        map[string]string        `json:"metadata,omitempty"`
--	Personality     []FileConfig             `json:"personality,omitempty"`
--	Networks        []NetworkConfig          `json:"networks,omitempty"`
--	AdminPass       string                   `json:"adminPass,omitempty"`
--	KeyPairName     string                   `json:"key_name,omitempty"`
--	Id              string                   `json:"id,omitempty"`
--	Links           []Link                   `json:"links,omitempty"`
--	OsDcfDiskConfig string                   `json:"OS-DCF:diskConfig,omitempty"`
--	SecurityGroup   []map[string]interface{} `json:"security_groups,omitempty"`
--	ConfigDrive     bool                     `json:"config_drive"`
--	UserData        string                   `json:"user_data"`
+-// CheckJSONEquals is similar to AssertJSONEquals, but nonfatal.
+-func CheckJSONEquals(t *testing.T, expectedJSON string, actual interface{}) {
+-	if !isJSONEquals(t, expectedJSON, actual) {
+-		logError(t, "The generated JSON structure differed.")
+-	}
 -}
 -
--// ResizeRequest structures are used internally to encode to JSON the parameters required to resize a server instance.
--// Client applications will not use this structure (no API accepts an instance of this structure).
--// See the Region method ResizeServer() for more details on how to resize a server.
--type ResizeRequest struct {
--	Name       string `json:"name,omitempty"`
--	FlavorRef  string `json:"flavorRef"`
--	DiskConfig string `json:"OS-DCF:diskConfig,omitempty"`
+-// AssertNoErr is a convenience function for checking whether an error value is
+-// an actual error
+-func AssertNoErr(t *testing.T, e error) {
+-	if e != nil {
+-		logFatal(t, fmt.Sprintf("unexpected error %s", yellow(e.Error())))
+-	}
 -}
 -
--type CreateImage struct {
--	Name     string            `json:"name"`
--	Metadata map[string]string `json:"metadata,omitempty"`
+-// CheckNoErr is similar to AssertNoErr, except with a non-fatal error
+-func CheckNoErr(t *testing.T, e error) {
+-	if e != nil {
+-		logError(t, fmt.Sprintf("unexpected error %s", yellow(e.Error())))
+-	}
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/servers_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/servers_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/testhelper/doc.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/testhelper/doc.go
 deleted file mode 100644
-index 60c71c8..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/servers_test.go
+index 25b4dfe..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/testhelper/doc.go
 +++ /dev/null
-@@ -1,54 +0,0 @@
--package gophercloud
+@@ -1,4 +0,0 @@
+-/*
+-Package testhelper container methods that are useful for writing unit tests.
+-*/
+-package testhelper
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/testhelper/http_responses.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/testhelper/http_responses.go
+deleted file mode 100644
+index e1f1f9a..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/testhelper/http_responses.go
++++ /dev/null
+@@ -1,91 +0,0 @@
+-package testhelper
 -
 -import (
+-	"encoding/json"
+-	"io/ioutil"
 -	"net/http"
+-	"net/http/httptest"
+-	"net/url"
+-	"reflect"
 -	"testing"
 -)
 -
--type testAccess struct {
--	public, internal              string
--	calledFirstEndpointByCriteria int
--}
--
--func (ta *testAccess) FirstEndpointUrlByCriteria(ac ApiCriteria) string {
--	ta.calledFirstEndpointByCriteria++
--	urls := []string{ta.public, ta.internal}
--	return urls[ac.UrlChoice]
--}
--
--func (ta *testAccess) AuthToken() string {
--	return ""
--}
+-var (
+-	// Mux is a multiplexer that can be used to register handlers.
+-	Mux *http.ServeMux
 -
--func (ta *testAccess) Revoke(string) error {
--	return nil
--}
+-	// Server is an in-memory HTTP server for testing.
+-	Server *httptest.Server
+-)
 -
--func (ta *testAccess) Reauthenticate() error {
--	return nil
+-// SetupHTTP prepares the Mux and Server.
+-func SetupHTTP() {
+-	Mux = http.NewServeMux()
+-	Server = httptest.NewServer(Mux)
 -}
 -
--func TestGetServersApi(t *testing.T) {
--	c := TestContext().UseCustomClient(&http.Client{Transport: newTransport().WithResponse("Hello")})
--
--	acc := &testAccess{
--		public:   "http://localhost:8080",
--		internal: "http://localhost:8086",
--	}
--
--	_, err := c.ServersApi(acc, ApiCriteria{
--		Name:      "cloudComputeOpenStack",
--		Region:    "dfw",
--		VersionId: "2",
--	})
--
--	if err != nil {
--		t.Error(err)
--		return
--	}
--
--	if acc.calledFirstEndpointByCriteria != 1 {
--		t.Error("Expected FirstEndpointByCriteria to be called")
--		return
--	}
+-// TeardownHTTP releases HTTP-related resources.
+-func TeardownHTTP() {
+-	Server.Close()
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/service_catalog.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/service_catalog.go
-deleted file mode 100644
-index e6cf4a0..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/service_catalog.go
-+++ /dev/null
-@@ -1,75 +0,0 @@
--package gophercloud
 -
--import (
--	"os"
--	"strings"
--)
--
--// ApiCriteria provides one or more criteria for the SDK to look for appropriate endpoints.
--// Fields left unspecified or otherwise set to their zero-values are assumed to not be
--// relevant, and do not participate in the endpoint search.
--//
--// Name specifies the desired service catalog entry name.
--// Type specifies the desired service catalog entry type.
--// Region specifies the desired endpoint region.
--// If unset, Gophercloud will try to use the region set in the
--// OS_REGION_NAME environment variable.  If that's not set,
--// region comparison will not occur.  If OS_REGION_NAME is set
--// and IgnoreEnvVars is also set, OS_REGION_NAME will be ignored.
--// VersionId specifies the desired version of the endpoint.
--// Note that this field is matched exactly, and is (at present)
--// opaque to Gophercloud.  Thus, requesting a version 2
--// endpoint will _not_ match a version 3 endpoint.
--// The UrlChoice field inidicates whether or not gophercloud
--// should use the public or internal endpoint URL if a
--// candidate endpoint is found.
--// IgnoreEnvVars instructs Gophercloud to ignore helpful environment variables.
--type ApiCriteria struct {
--	Name          string
--	Type          string
--	Region        string
--	VersionId     string
--	UrlChoice     int
--	IgnoreEnvVars bool
+-// Endpoint returns a fake endpoint that will actually target the Mux.
+-func Endpoint() string {
+-	return Server.URL + "/"
 -}
 -
--// The choices available for UrlChoice.  See the ApiCriteria structure for details.
--const (
--	PublicURL = iota
--	InternalURL
--)
--
--// Given a set of criteria to match on, locate the first candidate endpoint
--// in the provided service catalog.
--//
--// If nothing found, the result will be a zero-valued EntryEndpoint (all URLs
--// set to "").
--func FindFirstEndpointByCriteria(entries []CatalogEntry, ac ApiCriteria) EntryEndpoint {
--	rgn := strings.ToUpper(ac.Region)
--	if (rgn == "") && !ac.IgnoreEnvVars {
--		rgn = os.Getenv("OS_REGION_NAME")
+-// TestFormValues ensures that all the URL parameters given to the http.Request are the same as values.
+-func TestFormValues(t *testing.T, r *http.Request, values map[string]string) {
+-	want := url.Values{}
+-	for k, v := range values {
+-		want.Add(k, v)
 -	}
 -
--	for _, entry := range entries {
--		if (ac.Name != "") && (ac.Name != entry.Name) {
--			continue
--		}
--
--		if (ac.Type != "") && (ac.Type != entry.Type) {
--			continue
--		}
--
--		for _, endpoint := range entry.Endpoints {
--			if (rgn != "") && (rgn != strings.ToUpper(endpoint.Region)) {
--				continue
--			}
--
--			if (ac.VersionId != "") && (ac.VersionId != endpoint.VersionId) {
--				continue
--			}
--
--			return endpoint
--		}
+-	r.ParseForm()
+-	if !reflect.DeepEqual(want, r.Form) {
+-		t.Errorf("Request parameters = %v, want %v", r.Form, want)
 -	}
--	return EntryEndpoint{}
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/service_catalog_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/service_catalog_test.go
-deleted file mode 100644
-index b78f01f..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/service_catalog_test.go
-+++ /dev/null
-@@ -1,190 +0,0 @@
--package gophercloud
--
--import (
--	"os"
--	"testing"
--)
--
--// TestFFEBCViaEnvVariable exercises only those calls where a region
--// parameter is required, but is provided by an environment variable.
--func TestFFEBCViaEnvVariable(t *testing.T) {
--	changeRegion("RGN")
 -
--	endpoint := FindFirstEndpointByCriteria(
--		catalog("test", "compute", "http://localhost", "", ""),
--		ApiCriteria{Name: "test"},
--	)
--	if endpoint.PublicURL != "" {
--		t.Error("If provided, the Region qualifier must exclude endpoints with missing or mismatching regions.")
--		return
--	}
--
--	endpoint = FindFirstEndpointByCriteria(
--		catalog("test", "compute", "http://localhost", "rgn", ""),
--		ApiCriteria{Name: "test"},
--	)
--	if endpoint.PublicURL != "http://localhost" {
--		t.Error("Regions are case insensitive.")
--		return
--	}
--
--	endpoint = FindFirstEndpointByCriteria(
--		catalog("test", "compute", "http://localhost", "rgn", ""),
--		ApiCriteria{Name: "test", VersionId: "2"},
--	)
--	if endpoint.PublicURL != "" {
--		t.Error("Missing version ID means no match.")
--		return
--	}
--
--	endpoint = FindFirstEndpointByCriteria(
--		catalog("test", "compute", "http://localhost", "rgn", "3"),
--		ApiCriteria{Name: "test", VersionId: "2"},
--	)
--	if endpoint.PublicURL != "" {
--		t.Error("Mismatched version ID means no match.")
--		return
--	}
--
--	endpoint = FindFirstEndpointByCriteria(
--		catalog("test", "compute", "http://localhost", "rgn", "2"),
--		ApiCriteria{Name: "test", VersionId: "2"},
--	)
--	if endpoint.PublicURL != "http://localhost" {
--		t.Error("All search criteria met; endpoint expected.")
--		return
+-// TestMethod checks that the Request has the expected method (e.g. GET, POST).
+-func TestMethod(t *testing.T, r *http.Request, expected string) {
+-	if expected != r.Method {
+-		t.Errorf("Request method = %v, expected %v", r.Method, expected)
 -	}
 -}
 -
--// TestFFEBCViaRegionOption exercises only those calls where a region
--// parameter is specified explicitly.  The region option overrides
--// any defined OS_REGION_NAME environment setting.
--func TestFFEBCViaRegionOption(t *testing.T) {
--	changeRegion("Starfleet Command")
--
--	endpoint := FindFirstEndpointByCriteria(
--		catalog("test", "compute", "http://localhost", "", ""),
--		ApiCriteria{Name: "test", Region: "RGN"},
--	)
--	if endpoint.PublicURL != "" {
--		t.Error("If provided, the Region qualifier must exclude endpoints with missing or mismatching regions.")
--		return
--	}
--
--	endpoint = FindFirstEndpointByCriteria(
--		catalog("test", "compute", "http://localhost", "rgn", ""),
--		ApiCriteria{Name: "test", Region: "RGN"},
--	)
--	if endpoint.PublicURL != "http://localhost" {
--		t.Error("Regions are case insensitive.")
--		return
--	}
--
--	endpoint = FindFirstEndpointByCriteria(
--		catalog("test", "compute", "http://localhost", "rgn", ""),
--		ApiCriteria{Name: "test", Region: "RGN", VersionId: "2"},
--	)
--	if endpoint.PublicURL != "" {
--		t.Error("Missing version ID means no match.")
--		return
--	}
--
--	endpoint = FindFirstEndpointByCriteria(
--		catalog("test", "compute", "http://localhost", "rgn", "3"),
--		ApiCriteria{Name: "test", Region: "RGN", VersionId: "2"},
--	)
--	if endpoint.PublicURL != "" {
--		t.Error("Mismatched version ID means no match.")
--		return
--	}
--
--	endpoint = FindFirstEndpointByCriteria(
--		catalog("test", "compute", "http://localhost", "rgn", "2"),
--		ApiCriteria{Name: "test", Region: "RGN", VersionId: "2"},
--	)
--	if endpoint.PublicURL != "http://localhost" {
--		t.Error("All search criteria met; endpoint expected.")
--		return
+-// TestHeader checks that the header on the http.Request matches the expected value.
+-func TestHeader(t *testing.T, r *http.Request, header string, expected string) {
+-	if actual := r.Header.Get(header); expected != actual {
+-		t.Errorf("Header %s = %s, expected %s", header, actual, expected)
 -	}
 -}
 -
--// TestFFEBCWithoutRegion exercises only those calls where a region
--// is irrelevant.  Just to make sure, though, we enforce Gophercloud
--// from paying any attention to OS_REGION_NAME if it happens to be set.
--func TestFindFirstEndpointByCriteria(t *testing.T) {
--	endpoint := FindFirstEndpointByCriteria([]CatalogEntry{}, ApiCriteria{Name: "test", IgnoreEnvVars: true})
--	if endpoint.PublicURL != "" {
--		t.Error("Not expecting to find anything in an empty service catalog.")
--		return
--	}
--
--	endpoint = FindFirstEndpointByCriteria(
--		[]CatalogEntry{
--			{Name: "test"},
--		},
--		ApiCriteria{Name: "test", IgnoreEnvVars: true},
--	)
--	if endpoint.PublicURL != "" {
--		t.Error("Even though we have a matching entry, no endpoints exist")
--		return
--	}
--
--	endpoint = FindFirstEndpointByCriteria(
--		catalog("test", "compute", "http://localhost", "", ""),
--		ApiCriteria{Name: "test", IgnoreEnvVars: true},
--	)
--	if endpoint.PublicURL != "http://localhost" {
--		t.Error("Looking for an endpoint by name but without region or version ID should match first entry endpoint.")
--		return
--	}
--
--	endpoint = FindFirstEndpointByCriteria(
--		catalog("test", "compute", "http://localhost", "", ""),
--		ApiCriteria{Type: "compute", IgnoreEnvVars: true},
--	)
--	if endpoint.PublicURL != "http://localhost" {
--		t.Error("Looking for an endpoint by type but without region or version ID should match first entry endpoint.")
--		return
--	}
--
--	endpoint = FindFirstEndpointByCriteria(
--		catalog("test", "compute", "http://localhost", "", ""),
--		ApiCriteria{Type: "identity", IgnoreEnvVars: true},
--	)
--	if endpoint.PublicURL != "" {
--		t.Error("Returned mismatched type.")
--		return
+-// TestBody verifies that the request body matches an expected body.
+-func TestBody(t *testing.T, r *http.Request, expected string) {
+-	b, err := ioutil.ReadAll(r.Body)
+-	if err != nil {
+-		t.Errorf("Unable to read body: %v", err)
 -	}
--
--	endpoint = FindFirstEndpointByCriteria(
--		catalog("test", "compute", "http://localhost", "ord", "2"),
--		ApiCriteria{Name: "test", VersionId: "2", IgnoreEnvVars: true},
--	)
--	if endpoint.PublicURL != "http://localhost" {
--		t.Error("Sometimes, you might not care what region your stuff is in.")
--		return
+-	str := string(b)
+-	if expected != str {
+-		t.Errorf("Body = %s, expected %s", str, expected)
 -	}
 -}
 -
--func catalog(name, entry_type, url, region, version string) []CatalogEntry {
--	return []CatalogEntry{
--		{
--			Name: name,
--			Type: entry_type,
--			Endpoints: []EntryEndpoint{
--				{
--					PublicURL: url,
--					Region:    region,
--					VersionId: version,
--				},
--			},
--		},
+-// TestJSONRequest verifies that the JSON payload of a request matches an expected structure, without asserting things about
+-// whitespace or ordering.
+-func TestJSONRequest(t *testing.T, r *http.Request, expected string) {
+-	b, err := ioutil.ReadAll(r.Body)
+-	if err != nil {
+-		t.Errorf("Unable to read request body: %v", err)
 -	}
--}
 -
--func changeRegion(r string) {
--	err := os.Setenv("OS_REGION_NAME", r)
+-	var actualJSON interface{}
+-	err = json.Unmarshal(b, &actualJSON)
 -	if err != nil {
--		panic(err)
+-		t.Errorf("Unable to parse request body as JSON: %v", err)
 -	}
+-
+-	CheckJSONEquals(t, expected, actualJSON)
 -}
-diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/transport_double_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/transport_double_test.go
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/util.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/util.go
 deleted file mode 100644
-index ef7f19a..0000000
---- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/transport_double_test.go
+index 101fd39..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/util.go
 +++ /dev/null
-@@ -1,103 +0,0 @@
+@@ -1,39 +0,0 @@
 -package gophercloud
 -
 -import (
--	"encoding/json"
--	"fmt"
--	"io/ioutil"
--	"net/http"
+-	"errors"
 -	"strings"
--	"testing"
+-	"time"
 -)
 -
--type transport struct {
--	called         int
--	response       string
--	expectTenantId bool
--	tenantIdFound  bool
--	status         int
--}
--
--func (t *transport) RoundTrip(req *http.Request) (rsp *http.Response, err error) {
--	var authContainer *AuthContainer
--
--	t.called++
--
--	headers := make(http.Header)
--	headers.Add("Content-Type", "application/xml; charset=UTF-8")
--
--	body := ioutil.NopCloser(strings.NewReader(t.response))
--
--	if t.status == 0 {
--		t.status = 200
--	}
--	statusMsg := "OK"
--	if (t.status < 200) || (299 < t.status) {
--		statusMsg = "Error"
--	}
--
--	rsp = &http.Response{
--		Status:           fmt.Sprintf("%d %s", t.status, statusMsg),
--		StatusCode:       t.status,
--		Proto:            "HTTP/1.1",
--		ProtoMajor:       1,
--		ProtoMinor:       1,
--		Header:           headers,
--		Body:             body,
--		ContentLength:    -1,
--		TransferEncoding: nil,
--		Close:            true,
--		Trailer:          nil,
--		Request:          req,
--	}
+-// WaitFor polls a predicate function, once per second, up to a timeout limit.
+-// It usually does this to wait for the resource to transition to a certain state.
+-func WaitFor(timeout int, predicate func() (bool, error)) error {
+-	start := time.Now().Second()
+-	for {
+-		// Force a 1s sleep
+-		time.Sleep(1 * time.Second)
 -
--	bytes, err := ioutil.ReadAll(req.Body)
--	if err != nil {
--		return nil, err
--	}
--	err = json.Unmarshal(bytes, &authContainer)
--	if err != nil {
--		return nil, err
--	}
--	t.tenantIdFound = (authContainer.Auth.TenantId != "")
+-		// If a timeout is set, and that's been exceeded, shut it down
+-		if timeout >= 0 && time.Now().Second()-start >= timeout {
+-			return errors.New("A timeout occurred")
+-		}
 -
--	if t.tenantIdFound != t.expectTenantId {
--		rsp.Status = "500 Internal Server Error"
--		rsp.StatusCode = 500
+-		// Execute the function
+-		satisfied, err := predicate()
+-		if err != nil {
+-			return err
+-		}
+-		if satisfied {
+-			return nil
+-		}
 -	}
--	return
--}
--
--func newTransport() *transport {
--	return &transport{}
--}
--
--func (t *transport) IgnoreTenantId() *transport {
--	t.expectTenantId = false
--	return t
 -}
 -
--func (t *transport) ExpectTenantId() *transport {
--	t.expectTenantId = true
--	return t
+-// NormalizeURL ensures that each endpoint URL has a closing `/`, as expected by ServiceClient.
+-func NormalizeURL(url string) string {
+-	if !strings.HasSuffix(url, "/") {
+-		return url + "/"
+-	}
+-	return url
 -}
+diff --git a/Godeps/_workspace/src/github.com/rackspace/gophercloud/util_test.go b/Godeps/_workspace/src/github.com/rackspace/gophercloud/util_test.go
+deleted file mode 100644
+index 5a15a00..0000000
+--- a/Godeps/_workspace/src/github.com/rackspace/gophercloud/util_test.go
++++ /dev/null
+@@ -1,14 +0,0 @@
+-package gophercloud
 -
--func (t *transport) WithResponse(r string) *transport {
--	t.response = r
--	t.status = 200
--	return t
--}
+-import (
+-	"testing"
 -
--func (t *transport) WithError(code int) *transport {
--	t.response = fmt.Sprintf("Error %d", code)
--	t.status = code
--	return t
--}
+-	th "github.com/rackspace/gophercloud/testhelper"
+-)
 -
--func (t *transport) VerifyCalls(test *testing.T, n int) error {
--	if t.called != n {
--		err := fmt.Errorf("Expected Transport to be called %d times; found %d instead", n, t.called)
--		test.Error(err)
--		return err
--	}
--	return nil
+-func TestWaitFor(t *testing.T) {
+-	err := WaitFor(5, func() (bool, error) {
+-		return true, nil
+-	})
+-	th.CheckNoErr(t, err)
 -}
 diff --git a/Godeps/_workspace/src/github.com/skratchdot/LICENSE-MIT b/Godeps/_workspace/src/github.com/skratchdot/LICENSE-MIT
 deleted file mode 100644
@@ -85408,6 +144447,107 @@ index 5db2da2..0000000
 -	}
 -
 -}
+diff --git a/Godeps/_workspace/src/github.com/skynetservices/skydns/msg/service.go b/Godeps/_workspace/src/github.com/skynetservices/skydns/msg/service.go
+deleted file mode 100644
+index 564363a..0000000
+--- a/Godeps/_workspace/src/github.com/skynetservices/skydns/msg/service.go
++++ /dev/null
+@@ -1,95 +0,0 @@
+-// Copyright (c) 2014 The SkyDNS Authors. All rights reserved.
+-// Use of this source code is governed by The MIT License (MIT) that can be
+-// found in the LICENSE file.
+-
+-package msg
+-
+-import (
+-	"net"
+-	"path"
+-	"strings"
+-
+-	"github.com/miekg/dns"
+-)
+-
+-// This *is* the rdata from a SRV record, but with a twist.
+-// Host (Target in SRV) must be a domain name, but if it looks like an IP
+-// address (4/6), we will treat it like an IP address.
+-type Service struct {
+-	Host     string `json:"host,omitempty"`
+-	Port     int    `json:"port,omitempty"`
+-	Priority int    `json:"priority,omitempty"`
+-	Weight   int    `json:"weight,omitempty"`
+-	Ttl      uint32 `json:"ttl,omitempty"`
+-	// etcd key where we found this service and ignore from json un-/marshalling
+-	Key string `json:"-"`
+-}
+-
+-// NewSRV returns a new SRV record based on the Service.
+-func (s *Service) NewSRV(name string, weight uint16) *dns.SRV {
+-	return &dns.SRV{Hdr: dns.RR_Header{Name: name, Rrtype: dns.TypeSRV, Class: dns.ClassINET, Ttl: s.Ttl},
+-		Priority: uint16(s.Priority), Weight: weight, Port: uint16(s.Port), Target: dns.Fqdn(s.Host)}
+-}
+-
+-// NewA returns a new A record based on the Service.
+-func (s *Service) NewA(name string, ip net.IP) *dns.A {
+-	return &dns.A{Hdr: dns.RR_Header{Name: name, Rrtype: dns.TypeA, Class: dns.ClassINET, Ttl: s.Ttl}, A: ip}
+-}
+-
+-// NewAAAA returns a new AAAA record based on the Service.
+-func (s *Service) NewAAAA(name string, ip net.IP) *dns.AAAA {
+-	return &dns.AAAA{Hdr: dns.RR_Header{Name: name, Rrtype: dns.TypeAAAA, Class: dns.ClassINET, Ttl: s.Ttl}, AAAA: ip}
+-}
+-
+-// NewCNAME returns a new CNAME record based on the Service.
+-func (s *Service) NewCNAME(name string, target string) *dns.CNAME {
+-	return &dns.CNAME{Hdr: dns.RR_Header{Name: name, Rrtype: dns.TypeCNAME, Class: dns.ClassINET, Ttl: s.Ttl}, Target: target}
+-}
+-
+-// NewNS returns a new NS record based on the Service.
+-func (s *Service) NewNS(name string, target string) *dns.NS {
+-	return &dns.NS{Hdr: dns.RR_Header{Name: name, Rrtype: dns.TypeNS, Class: dns.ClassINET, Ttl: s.Ttl}, Ns: target}
+-}
+-
+-// NewPTR returns a new PTR record based on the Service.
+-func (s *Service) NewPTR(name string, ttl uint32) *dns.PTR {
+-	return &dns.PTR{Hdr: dns.RR_Header{Name: name, Rrtype: dns.TypePTR, Class: dns.ClassINET, Ttl: ttl}, Ptr: dns.Fqdn(s.Host)}
+-}
+-
+-// As Path, but
+-// if a name contains wildcards (*), the name will be chopped of before the (first) wildcard, and
+-// we do a highler evel search and later find the matching names.
+-// So service.*.skydns.local, will look for all services under skydns.local and will later check
+-// for names that match service.*.skydns.local.  If a wildcard is found the returned bool is true.
+-func PathWithWildcard(s string) (string, bool) {
+-	l := dns.SplitDomainName(s)
+-	for i, j := 0, len(l)-1; i < j; i, j = i+1, j-1 {
+-		l[i], l[j] = l[j], l[i]
+-	}
+-	for i, k := range l {
+-		if k == "*" {
+-			return path.Join(append([]string{"/skydns/"}, l[:i]...)...), true
+-		}
+-	}
+-	return path.Join(append([]string{"/skydns/"}, l...)...), false
+-}
+-
+-// Path converts a domainname to an etcd path. If s looks like service.staging.skydns.local.,
+-// the resulting key will be /skydns/local/skydns/staging/service .
+-func Path(s string) string {
+-	l := dns.SplitDomainName(s)
+-	for i, j := 0, len(l)-1; i < j; i, j = i+1, j-1 {
+-		l[i], l[j] = l[j], l[i]
+-	}
+-	return path.Join(append([]string{"/skydns/"}, l...)...)
+-}
+-
+-// Domain is the opposite of Path.
+-func Domain(s string) string {
+-	l := strings.Split(s, "/")
+-	// start with 1, to strip /skydns
+-	for i, j := 1, len(l)-1; i < j; i, j = i+1, j-1 {
+-		l[i], l[j] = l[j], l[i]
+-	}
+-	return dns.Fqdn(strings.Join(l[1:len(l)-1], "."))
+-}
 diff --git a/Godeps/_workspace/src/github.com/spf13/cobra/.gitignore b/Godeps/_workspace/src/github.com/spf13/cobra/.gitignore
 deleted file mode 100644
 index 36d1a84..0000000
@@ -85632,10 +144772,10 @@ index 298f0e2..0000000
 -      of your accepting any such warranty or additional liability.
 diff --git a/Godeps/_workspace/src/github.com/spf13/cobra/README.md b/Godeps/_workspace/src/github.com/spf13/cobra/README.md
 deleted file mode 100644
-index 67c4eff..0000000
+index 528233d..0000000
 --- a/Godeps/_workspace/src/github.com/spf13/cobra/README.md
 +++ /dev/null
-@@ -1,397 +0,0 @@
+@@ -1,399 +0,0 @@
 -# Cobra
 -
 -A Commander for modern go CLI interactions
@@ -85758,7 +144898,9 @@ index 67c4eff..0000000
 -
 -### Assign flags to a command
 -
--Since the flags are defined and used in different locations, we need to define a variable outside with the correct scope to assign the flag to work with.
+-Since the flags are defined and used in different locations, we need to
+-define a variable outside with the correct scope to assign the flag to
+-work with.
 -
 -    var Verbose bool
 -    var Source string
@@ -86035,10 +145177,10 @@ index 67c4eff..0000000
 -
 diff --git a/Godeps/_workspace/src/github.com/spf13/cobra/cobra.go b/Godeps/_workspace/src/github.com/spf13/cobra/cobra.go
 deleted file mode 100644
-index e03b496..0000000
+index 1b5ca36..0000000
 --- a/Godeps/_workspace/src/github.com/spf13/cobra/cobra.go
 +++ /dev/null
-@@ -1,98 +0,0 @@
+@@ -1,104 +0,0 @@
 -// Copyright © 2013 Steve Francia <spf at spf13.com>.
 -//
 -// Licensed under the Apache License, Version 2.0 (the "License");
@@ -86072,12 +145214,16 @@ index e03b496..0000000
 -// Set this to true to enable it
 -var EnablePrefixMatching bool = false
 -
+-//OnInitialize takes a series of func() arguments and appends them to a slice of func().
 -func OnInitialize(y ...func()) {
 -	for _, x := range y {
 -		initializers = append(initializers, x)
 -	}
 -}
 -
+-//Gt takes two types and checks whether the first type is greater than the second. In case of types Arrays, Chans,
+-//Maps and Slices, Gt will compare their lengths. Ints are compared directly while strings are first parsed as
+-//ints and then compared.
 -func Gt(a interface{}, b interface{}) bool {
 -	var left, right int64
 -	av := reflect.ValueOf(a)
@@ -86105,6 +145251,7 @@ index e03b496..0000000
 -	return left > right
 -}
 -
+-//Eq takes two types and checks whether they are equal. Supported types are int and string. Unsupported types will panic.
 -func Eq(a interface{}, b interface{}) bool {
 -	av := reflect.ValueOf(a)
 -	bv := reflect.ValueOf(b)
@@ -86120,6 +145267,7 @@ index e03b496..0000000
 -	return false
 -}
 -
+-//rpad adds padding to the right of a string
 -func rpad(s string, padding int) string {
 -	template := fmt.Sprintf("%%-%ds", padding)
 -	return fmt.Sprintf(template, s)
@@ -86139,10 +145287,10 @@ index e03b496..0000000
 -}
 diff --git a/Godeps/_workspace/src/github.com/spf13/cobra/cobra_test.go b/Godeps/_workspace/src/github.com/spf13/cobra/cobra_test.go
 deleted file mode 100644
-index 05d18d0..0000000
+index dd44812..0000000
 --- a/Godeps/_workspace/src/github.com/spf13/cobra/cobra_test.go
 +++ /dev/null
-@@ -1,507 +0,0 @@
+@@ -1,553 +0,0 @@
 -package cobra
 -
 -import (
@@ -86281,6 +145429,24 @@ index 05d18d0..0000000
 -	return fullTester(c, input)
 -}
 -
+-func rootOnlySetupTest(input string) resulter {
+-	c := initializeWithRootCmd()
+-
+-	return simpleTester(c, input)
+-}
+-
+-func simpleTester(c *Command, input string) resulter {
+-	buf := new(bytes.Buffer)
+-	// Testing flag with invalid input
+-	c.SetOutput(buf)
+-	c.SetArgs(strings.Split(input, " "))
+-
+-	err := c.Execute()
+-	output := buf.String()
+-
+-	return resulter{err, output, c}
+-}
+-
 -func fullTester(c *Command, input string) resulter {
 -	buf := new(bytes.Buffer)
 -	// Testing flag with invalid input
@@ -86301,6 +145467,12 @@ index 05d18d0..0000000
 -	}
 -}
 -
+-func checkResultOmits(t *testing.T, x resulter, check string) {
+-	if strings.Contains(x.Output, check) {
+-		t.Errorf("Unexpected response.\nExpecting to omit: \n %q\nGot:\n %q\n", check, x.Output)
+-	}
+-}
+-
 -func checkOutputContains(t *testing.T, c *Command, check string) {
 -	buf := new(bytes.Buffer)
 -	c.SetOutput(buf)
@@ -86582,6 +145754,7 @@ index 05d18d0..0000000
 -	x := fullSetupTest("--help")
 -
 -	checkResultContains(t, x, "Available Commands:")
+-	checkResultContains(t, x, "for more information about that command")
 -
 -	if strings.Contains(x.Output, "unknown flag: --help") {
 -		t.Errorf("--help shouldn't trigger an error, Got: \n %s", x.Output)
@@ -86590,11 +145763,32 @@ index 05d18d0..0000000
 -	x = fullSetupTest("echo --help")
 -
 -	checkResultContains(t, x, "Available Commands:")
+-	checkResultContains(t, x, "for more information about that command")
+-
+-	if strings.Contains(x.Output, "unknown flag: --help") {
+-		t.Errorf("--help shouldn't trigger an error, Got: \n %s", x.Output)
+-	}
+-
+-}
+-
+-func TestRootNoCommandHelp(t *testing.T) {
+-	x := rootOnlySetupTest("--help")
+-
+-	checkResultOmits(t, x, "Available Commands:")
+-	checkResultOmits(t, x, "for more information about that command")
 -
 -	if strings.Contains(x.Output, "unknown flag: --help") {
 -		t.Errorf("--help shouldn't trigger an error, Got: \n %s", x.Output)
 -	}
 -
+-	x = rootOnlySetupTest("echo --help")
+-
+-	checkResultOmits(t, x, "Available Commands:")
+-	checkResultOmits(t, x, "for more information about that command")
+-
+-	if strings.Contains(x.Output, "unknown flag: --help") {
+-		t.Errorf("--help shouldn't trigger an error, Got: \n %s", x.Output)
+-	}
 -}
 -
 -func TestFlagsBeforeCommand(t *testing.T) {
@@ -86652,10 +145846,10 @@ index 05d18d0..0000000
 -}
 diff --git a/Godeps/_workspace/src/github.com/spf13/cobra/command.go b/Godeps/_workspace/src/github.com/spf13/cobra/command.go
 deleted file mode 100644
-index 1337065..0000000
+index a3a01ad..0000000
 --- a/Godeps/_workspace/src/github.com/spf13/cobra/command.go
 +++ /dev/null
-@@ -1,764 +0,0 @@
+@@ -1,790 +0,0 @@
 -// Copyright © 2013 Steve Francia <spf at spf13.com>.
 -//
 -// Licensed under the Apache License, Version 2.0 (the "License");
@@ -86669,9 +145863,8 @@ index 1337065..0000000
 -// See the License for the specific language governing permissions and
 -// limitations under the License.
 -
--// Commands similar to git, go tools and other modern CLI tools
--// inspired by go, go-Commander, gh and subcommand
--
+-//Package cobra is a commander providing a simple interface to create powerful modern CLI interfaces.
+-//In addition to providing an interface, Cobra simultaneously provides a controller to organize your application code.
 -package cobra
 -
 -import (
@@ -86715,8 +145908,9 @@ index 1337065..0000000
 -	commandsMaxCommandPathLen int
 -
 -	flagErrorBuf *bytes.Buffer
+-	cmdErrorBuf  *bytes.Buffer
 -
--	args          []string
+-	args          []string                 // actual args parsed from flags
 -	output        *io.Writer               // nil means stderr; use Out() method instead
 -	usageFunc     func(*Command) error     // Usage can be defined by application
 -	usageTemplate string                   // Can be defined by Application
@@ -86830,6 +146024,7 @@ index 1337065..0000000
 -
 -var minCommandPathPadding int = 11
 -
+-//
 -func (c *Command) CommandPathPadding() int {
 -	if c.parent == nil || minCommandPathPadding > c.parent.commandsMaxCommandPathLen {
 -		return minCommandPathPadding
@@ -86861,9 +146056,9 @@ index 1337065..0000000
 -{{.Flags.FlagUsages}}{{end}}{{if .HasParent}}{{if and (gt .Commands 0) (gt .Parent.Commands 1) }}
 -Additional help topics: {{if gt .Commands 0 }}{{range .Commands}}{{if not .Runnable}} {{rpad .CommandPath .CommandPathPadding}} {{.Short}}{{end}}{{end}}{{end}}{{if gt .Parent.Commands 1 }}{{range .Parent.Commands}}{{if .Runnable}}{{if not (eq .Name $cmd.Name) }}{{end}}
 -  {{rpad .CommandPath .CommandPathPadding}} {{.Short}}{{end}}{{end}}{{end}}{{end}}
--{{end}}
+-{{end}}{{ if .HasSubCommands }}
 -Use "{{.Root.Name}} help [command]" for more information about that command.
--`
+-{{end}}`
 -	}
 -}
 -
@@ -87013,10 +146208,22 @@ index 1337065..0000000
 -	err = c.ParseFlags(a)
 -
 -	if err != nil {
+-		// We're writing subcommand usage to root command's error buffer to have it displayed to the user
+-		r := c.Root()
+-		if r.cmdErrorBuf == nil {
+-			r.cmdErrorBuf = new(bytes.Buffer)
+-		}
+-		// for writing the usage to the buffer we need to switch the output temporarily
+-		// since Out() returns root output, you also need to revert that on root
+-		out := r.Out()
+-		r.SetOutput(r.cmdErrorBuf)
+-		c.Usage()
+-		r.SetOutput(out)
 -		return err
 -	} else {
--		// If help is called, regardless of other flags, we print that
--		if c.helpFlagVal {
+-		// If help is called, regardless of other flags, we print that.
+-		// Print help also if c.Run is nil.
+-		if c.helpFlagVal || !c.Runnable() {
 -			c.Help()
 -			return nil
 -		}
@@ -87088,7 +146295,12 @@ index 1337065..0000000
 -			// Flags parsing had an error.
 -			// If an error happens here, we have to report it to the user
 -			c.Println(c.errorMsgFromParse())
--			c.Usage()
+-			// If an error happens search also for subcommand info about that
+-			if c.cmdErrorBuf != nil && c.cmdErrorBuf.Len() > 0 {
+-				c.Println(c.cmdErrorBuf.String())
+-			} else {
+-				c.Usage()
+-			}
 -			return e
 -		} else {
 -			// If help is called, regardless of other flags, we print that
@@ -87123,6 +146335,10 @@ index 1337065..0000000
 -
 -func (c *Command) initHelp() {
 -	if c.helpCommand == nil {
+-		if !c.HasSubCommands() {
+-			return
+-		}
+-
 -		c.helpCommand = &Command{
 -			Use:   "help [command]",
 -			Short: "Help about any command",
@@ -87137,13 +146353,17 @@ index 1337065..0000000
 -// Used for testing
 -func (c *Command) ResetCommands() {
 -	c.commands = nil
+-	c.helpCommand = nil
+-	c.cmdErrorBuf = new(bytes.Buffer)
+-	c.cmdErrorBuf.Reset()
 -}
 -
+-//Commands returns a slice of child commands.
 -func (c *Command) Commands() []*Command {
 -	return c.commands
 -}
 -
--// Add one or many commands as children of this
+-// AddCommand adds one or more commands to this parent command.
 -func (c *Command) AddCommand(cmds ...*Command) {
 -	for i, x := range cmds {
 -		if cmds[i] == c {
@@ -87207,7 +146427,7 @@ index 1337065..0000000
 -	return bb.String()
 -}
 -
--// The full path to this command
+-// CommandPath returns the full path to this command.
 -func (c *Command) CommandPath() string {
 -	str := c.Name()
 -	x := c
@@ -99951,1037 +159171,6 @@ index cd06451..0000000
 -	assert.Equal(t, true, args.Bool(2))
 -
 -}
-diff --git a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/.gitignore b/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/.gitignore
-deleted file mode 100644
-index 1f0a99f..0000000
---- a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/.gitignore
-+++ /dev/null
-@@ -1,4 +0,0 @@
--[568].out
--_go*
--_test*
--_obj
-diff --git a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/License b/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/License
-deleted file mode 100644
-index 480a328..0000000
---- a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/License
-+++ /dev/null
-@@ -1,19 +0,0 @@
--Copyright 2012 Keith Rarick
--
--Permission is hereby granted, free of charge, to any person obtaining a copy
--of this software and associated documentation files (the "Software"), to deal
--in the Software without restriction, including without limitation the rights
--to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
--copies of the Software, and to permit persons to whom the Software is
--furnished to do so, subject to the following conditions:
--
--The above copyright notice and this permission notice shall be included in
--all copies or substantial portions of the Software.
--
--THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
--IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
--FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
--AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
--LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
--OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
--THE SOFTWARE.
-diff --git a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/Readme b/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/Readme
-deleted file mode 100644
-index c589fc6..0000000
---- a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/Readme
-+++ /dev/null
-@@ -1,9 +0,0 @@
--package pretty
--
--    import "github.com/kr/pretty"
--
--    Package pretty provides pretty-printing for Go values.
--
--Documentation
--
--    http://godoc.org/github.com/kr/pretty
-diff --git a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/changelog b/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/changelog
-deleted file mode 100644
-index 9350c05..0000000
---- a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/changelog
-+++ /dev/null
-@@ -1,5 +0,0 @@
--golang-pretty (0.0~git20130613-1) unstable; urgency=low
--
--  * Initial release. Closes: #722983
--
-- -- Tonnerre Lombard <tonnerre at ancient-solutions.com>  Wed, 11 Sep 2013 02:36:12 +0200
-diff --git a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/compat b/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/compat
-deleted file mode 100644
-index ec63514..0000000
---- a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/compat
-+++ /dev/null
-@@ -1 +0,0 @@
--9
-diff --git a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/control b/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/control
-deleted file mode 100644
-index a852fe7..0000000
---- a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/control
-+++ /dev/null
-@@ -1,22 +0,0 @@
--Source: golang-pretty
--Section: devel
--Priority: extra
--Maintainer: Tonnerre Lombard <tonnerre at ancient-solutions.com>
--Build-Depends: debhelper (>= 9), golang-go, dh-golang,
--	       golang-text-dev
--Standards-Version: 3.9.4
--Homepage: https://github.com/kr/pretty/
--Vcs-Git: git://anonscm.debian.org/pkg-go/packages/golang-pretty.git
--Vcs-Browser: http://anonscm.debian.org/gitweb/?p=pkg-go/packages/golang-pretty.git;a=summary
--
--Package: golang-pretty-dev
--Architecture: all
--Depends: ${shlibs:Depends}, ${misc:Depends}, golang-text-dev
--Description: Pretty printing for go values
-- Package pretty provides pretty-printing for Go values. This is useful
-- during debugging, to avoid wrapping long output lines in the
-- terminal.
-- .
-- It provides a function, Formatter, that can be used with any function
-- that accepts a format string. It also provides convenience wrappers
-- for functions in packages fmt and log.
-diff --git a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/copyright b/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/copyright
-deleted file mode 100644
-index 80b0807..0000000
---- a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/copyright
-+++ /dev/null
-@@ -1,30 +0,0 @@
--Format: http://www.debian.org/doc/packaging-manuals/copyright-format/1.0/
--Upstream-Name: golang-pretty
--Source: https://github.com/kr/pretty/
--
--Files: *
--Copyright: 2011, 2012, 2013 Keith Rarick <kr at xph.us>
--License: Expat
--
--Files: debian/*
--Copyright: 2013 Tonnerre Lombard <tonnerre at ancient-solutions.com>
--License: Expat
--
--License: Expat
-- Permission is hereby granted, free of charge, to any person obtaining a copy
-- of this software and associated documentation files (the "Software"), to deal
-- in the Software without restriction, including without limitation the rights
-- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
-- copies of the Software, and to permit persons to whom the Software is
-- furnished to do so, subject to the following conditions:
-- .
-- The above copyright notice and this permission notice shall be included in
-- all copies or substantial portions of the Software.
-- .
-- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
-- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
-- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
-- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
-- THE SOFTWARE.
-diff --git a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/docs b/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/docs
-deleted file mode 100644
-index 304360c..0000000
---- a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/docs
-+++ /dev/null
-@@ -1 +0,0 @@
--Readme
-diff --git a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/rules b/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/rules
-deleted file mode 100644
-index c48a3ad..0000000
---- a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/rules
-+++ /dev/null
-@@ -1,11 +0,0 @@
--#!/usr/bin/make -f
--
--# Uncomment this to turn on verbose mode.
--export DH_VERBOSE=1
--
--# DH_GOPKG is the upstream path which you would normally “go get”.
--# Using it allows us to build applications without patching locations.
--export DH_GOPKG := github.com/kr/pretty
--
--%:
--	dh $@ --buildsystem=golang --with=golang
-diff --git a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/source/format b/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/source/format
-deleted file mode 100644
-index 163aaf8..0000000
---- a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/debian/source/format
-+++ /dev/null
-@@ -1 +0,0 @@
--3.0 (quilt)
-diff --git a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/diff.go b/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/diff.go
-deleted file mode 100644
-index 64fac64..0000000
---- a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/diff.go
-+++ /dev/null
-@@ -1,148 +0,0 @@
--package pretty
--
--import (
--	"fmt"
--	"io"
--	"reflect"
--)
--
--type sbuf []string
--
--func (s *sbuf) Write(b []byte) (int, error) {
--	*s = append(*s, string(b))
--	return len(b), nil
--}
--
--// Diff returns a slice where each element describes
--// a difference between a and b.
--func Diff(a, b interface{}) (desc []string) {
--	Fdiff((*sbuf)(&desc), a, b)
--	return desc
--}
--
--// Fdiff writes to w a description of the differences between a and b.
--func Fdiff(w io.Writer, a, b interface{}) {
--	diffWriter{w: w}.diff(reflect.ValueOf(a), reflect.ValueOf(b))
--}
--
--type diffWriter struct {
--	w io.Writer
--	l string // label
--}
--
--func (w diffWriter) printf(f string, a ...interface{}) {
--	var l string
--	if w.l != "" {
--		l = w.l + ": "
--	}
--	fmt.Fprintf(w.w, l+f, a...)
--}
--
--func (w diffWriter) diff(av, bv reflect.Value) {
--	if !av.IsValid() && bv.IsValid() {
--		w.printf("nil != %#v", bv.Interface())
--		return
--	}
--	if av.IsValid() && !bv.IsValid() {
--		w.printf("%#v != nil", av.Interface())
--		return
--	}
--	if !av.IsValid() && !bv.IsValid() {
--		return
--	}
--
--	at := av.Type()
--	bt := bv.Type()
--	if at != bt {
--		w.printf("%v != %v", at, bt)
--		return
--	}
--
--	// numeric types, including bool
--	if at.Kind() < reflect.Array {
--		a, b := av.Interface(), bv.Interface()
--		if a != b {
--			w.printf("%#v != %#v", a, b)
--		}
--		return
--	}
--
--	switch at.Kind() {
--	case reflect.String:
--		a, b := av.Interface(), bv.Interface()
--		if a != b {
--			w.printf("%q != %q", a, b)
--		}
--	case reflect.Ptr:
--		switch {
--		case av.IsNil() && !bv.IsNil():
--			w.printf("nil != %v", bv.Interface())
--		case !av.IsNil() && bv.IsNil():
--			w.printf("%v != nil", av.Interface())
--		case !av.IsNil() && !bv.IsNil():
--			w.diff(av.Elem(), bv.Elem())
--		}
--	case reflect.Struct:
--		for i := 0; i < av.NumField(); i++ {
--			w.relabel(at.Field(i).Name).diff(av.Field(i), bv.Field(i))
--		}
--	case reflect.Map:
--		ak, both, bk := keyDiff(av.MapKeys(), bv.MapKeys())
--		for _, k := range ak {
--			w := w.relabel(fmt.Sprintf("[%#v]", k.Interface()))
--			w.printf("%q != (missing)", av.MapIndex(k))
--		}
--		for _, k := range both {
--			w := w.relabel(fmt.Sprintf("[%#v]", k.Interface()))
--			w.diff(av.MapIndex(k), bv.MapIndex(k))
--		}
--		for _, k := range bk {
--			w := w.relabel(fmt.Sprintf("[%#v]", k.Interface()))
--			w.printf("(missing) != %q", bv.MapIndex(k))
--		}
--	case reflect.Interface:
--		w.diff(reflect.ValueOf(av.Interface()), reflect.ValueOf(bv.Interface()))
--	default:
--		if !reflect.DeepEqual(av.Interface(), bv.Interface()) {
--			w.printf("%# v != %# v", Formatter(av.Interface()), Formatter(bv.Interface()))
--		}
--	}
--}
--
--func (d diffWriter) relabel(name string) (d1 diffWriter) {
--	d1 = d
--	if d.l != "" && name[0] != '[' {
--		d1.l += "."
--	}
--	d1.l += name
--	return d1
--}
--
--func keyDiff(a, b []reflect.Value) (ak, both, bk []reflect.Value) {
--	for _, av := range a {
--		inBoth := false
--		for _, bv := range b {
--			if reflect.DeepEqual(av.Interface(), bv.Interface()) {
--				inBoth = true
--				both = append(both, av)
--				break
--			}
--		}
--		if !inBoth {
--			ak = append(ak, av)
--		}
--	}
--	for _, bv := range b {
--		inBoth := false
--		for _, av := range a {
--			if reflect.DeepEqual(av.Interface(), bv.Interface()) {
--				inBoth = true
--				break
--			}
--		}
--		if !inBoth {
--			bk = append(bk, bv)
--		}
--	}
--	return
--}
-diff --git a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/diff_test.go b/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/diff_test.go
-deleted file mode 100644
-index 02d1953..0000000
---- a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/diff_test.go
-+++ /dev/null
-@@ -1,73 +0,0 @@
--package pretty
--
--import (
--	"testing"
--)
--
--type difftest struct {
--	a   interface{}
--	b   interface{}
--	exp []string
--}
--
--type S struct {
--	A int
--	S *S
--	I interface{}
--	C []int
--}
--
--var diffs = []difftest{
--	{a: nil, b: nil},
--	{a: S{A: 1}, b: S{A: 1}},
--
--	{0, "", []string{`int != string`}},
--	{0, 1, []string{`0 != 1`}},
--	{S{}, new(S), []string{`pretty.S != *pretty.S`}},
--	{"a", "b", []string{`"a" != "b"`}},
--	{S{}, S{A: 1}, []string{`A: 0 != 1`}},
--	{new(S), &S{A: 1}, []string{`A: 0 != 1`}},
--	{S{S: new(S)}, S{S: &S{A: 1}}, []string{`S.A: 0 != 1`}},
--	{S{}, S{I: 0}, []string{`I: nil != 0`}},
--	{S{I: 1}, S{I: "x"}, []string{`I: int != string`}},
--	{S{}, S{C: []int{1}}, []string{`C: []int(nil) != []int{1}`}},
--	{S{C: []int{}}, S{C: []int{1}}, []string{`C: []int{} != []int{1}`}},
--	{S{}, S{A: 1, S: new(S)}, []string{`A: 0 != 1`, `S: nil != &{0 <nil> <nil> []}`}},
--}
--
--func TestDiff(t *testing.T) {
--	for _, tt := range diffs {
--		got := Diff(tt.a, tt.b)
--		eq := len(got) == len(tt.exp)
--		if eq {
--			for i := range got {
--				eq = eq && got[i] == tt.exp[i]
--			}
--		}
--		if !eq {
--			t.Errorf("diffing % #v", tt.a)
--			t.Errorf("with    % #v", tt.b)
--			diffdiff(t, got, tt.exp)
--			continue
--		}
--	}
--}
--
--func diffdiff(t *testing.T, got, exp []string) {
--	minus(t, "unexpected:", got, exp)
--	minus(t, "missing:", exp, got)
--}
--
--func minus(t *testing.T, s string, a, b []string) {
--	var i, j int
--	for i = 0; i < len(a); i++ {
--		for j = 0; j < len(b); j++ {
--			if a[i] == b[j] {
--				break
--			}
--		}
--		if j == len(b) {
--			t.Error(s, a[i])
--		}
--	}
--}
-diff --git a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/example_test.go b/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/example_test.go
-deleted file mode 100644
-index ecf40f3..0000000
---- a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/example_test.go
-+++ /dev/null
-@@ -1,20 +0,0 @@
--package pretty_test
--
--import (
--	"fmt"
--	"github.com/kr/pretty"
--)
--
--func Example() {
--	type myType struct {
--		a, b int
--	}
--	var x = []myType{{1, 2}, {3, 4}, {5, 6}}
--	fmt.Printf("%# v", pretty.Formatter(x))
--	// output:
--	// []pretty_test.myType{
--	//     {a:1, b:2},
--	//     {a:3, b:4},
--	//     {a:5, b:6},
--	// }
--}
-diff --git a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/formatter.go b/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/formatter.go
-deleted file mode 100644
-index 1161de7..0000000
---- a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/formatter.go
-+++ /dev/null
-@@ -1,300 +0,0 @@
--package pretty
--
--import (
--	"fmt"
--	"github.com/kr/text"
--	"io"
--	"reflect"
--	"strconv"
--	"text/tabwriter"
--)
--
--const (
--	limit = 50
--)
--
--type formatter struct {
--	x     interface{}
--	force bool
--	quote bool
--}
--
--// Formatter makes a wrapper, f, that will format x as go source with line
--// breaks and tabs. Object f responds to the "%v" formatting verb when both the
--// "#" and " " (space) flags are set, for example:
--//
--//     fmt.Sprintf("%# v", Formatter(x))
--//
--// If one of these two flags is not set, or any other verb is used, f will
--// format x according to the usual rules of package fmt.
--// In particular, if x satisfies fmt.Formatter, then x.Format will be called.
--func Formatter(x interface{}) (f fmt.Formatter) {
--	return formatter{x: x, quote: true}
--}
--
--func (fo formatter) String() string {
--	return fmt.Sprint(fo.x) // unwrap it
--}
--
--func (fo formatter) passThrough(f fmt.State, c rune) {
--	s := "%"
--	for i := 0; i < 128; i++ {
--		if f.Flag(i) {
--			s += string(i)
--		}
--	}
--	if w, ok := f.Width(); ok {
--		s += fmt.Sprintf("%d", w)
--	}
--	if p, ok := f.Precision(); ok {
--		s += fmt.Sprintf(".%d", p)
--	}
--	s += string(c)
--	fmt.Fprintf(f, s, fo.x)
--}
--
--func (fo formatter) Format(f fmt.State, c rune) {
--	if fo.force || c == 'v' && f.Flag('#') && f.Flag(' ') {
--		w := tabwriter.NewWriter(f, 4, 4, 1, ' ', 0)
--		p := &printer{tw: w, Writer: w}
--		p.printValue(reflect.ValueOf(fo.x), true, fo.quote)
--		w.Flush()
--		return
--	}
--	fo.passThrough(f, c)
--}
--
--type printer struct {
--	io.Writer
--	tw *tabwriter.Writer
--}
--
--func (p *printer) indent() *printer {
--	q := *p
--	q.tw = tabwriter.NewWriter(p.Writer, 4, 4, 1, ' ', 0)
--	q.Writer = text.NewIndentWriter(q.tw, []byte{'\t'})
--	return &q
--}
--
--func (p *printer) printInline(v reflect.Value, x interface{}, showType bool) {
--	if showType {
--		io.WriteString(p, v.Type().String())
--		fmt.Fprintf(p, "(%#v)", x)
--	} else {
--		fmt.Fprintf(p, "%#v", x)
--	}
--}
--
--func (p *printer) printValue(v reflect.Value, showType, quote bool) {
--	switch v.Kind() {
--	case reflect.Bool:
--		p.printInline(v, v.Bool(), showType)
--	case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
--		p.printInline(v, v.Int(), showType)
--	case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
--		p.printInline(v, v.Uint(), showType)
--	case reflect.Float32, reflect.Float64:
--		p.printInline(v, v.Float(), showType)
--	case reflect.Complex64, reflect.Complex128:
--		fmt.Fprintf(p, "%#v", v.Complex())
--	case reflect.String:
--		p.fmtString(v.String(), quote)
--	case reflect.Map:
--		t := v.Type()
--		if showType {
--			io.WriteString(p, t.String())
--		}
--		writeByte(p, '{')
--		if nonzero(v) {
--			expand := !canInline(v.Type())
--			pp := p
--			if expand {
--				writeByte(p, '\n')
--				pp = p.indent()
--			}
--			keys := v.MapKeys()
--			for i := 0; i < v.Len(); i++ {
--				showTypeInStruct := true
--				k := keys[i]
--				mv := v.MapIndex(k)
--				pp.printValue(k, false, true)
--				writeByte(pp, ':')
--				if expand {
--					writeByte(pp, '\t')
--				}
--				showTypeInStruct = t.Elem().Kind() == reflect.Interface
--				pp.printValue(mv, showTypeInStruct, true)
--				if expand {
--					io.WriteString(pp, ",\n")
--				} else if i < v.Len()-1 {
--					io.WriteString(pp, ", ")
--				}
--			}
--			if expand {
--				pp.tw.Flush()
--			}
--		}
--		writeByte(p, '}')
--	case reflect.Struct:
--		t := v.Type()
--		if showType {
--			io.WriteString(p, t.String())
--		}
--		writeByte(p, '{')
--		if nonzero(v) {
--			expand := !canInline(v.Type())
--			pp := p
--			if expand {
--				writeByte(p, '\n')
--				pp = p.indent()
--			}
--			for i := 0; i < v.NumField(); i++ {
--				showTypeInStruct := true
--				if f := t.Field(i); f.Name != "" {
--					io.WriteString(pp, f.Name)
--					writeByte(pp, ':')
--					if expand {
--						writeByte(pp, '\t')
--					}
--					showTypeInStruct = f.Type.Kind() == reflect.Interface
--				}
--				pp.printValue(getField(v, i), showTypeInStruct, true)
--				if expand {
--					io.WriteString(pp, ",\n")
--				} else if i < v.NumField()-1 {
--					io.WriteString(pp, ", ")
--				}
--			}
--			if expand {
--				pp.tw.Flush()
--			}
--		}
--		writeByte(p, '}')
--	case reflect.Interface:
--		switch e := v.Elem(); {
--		case e.Kind() == reflect.Invalid:
--			io.WriteString(p, "nil")
--		case e.IsValid():
--			p.printValue(e, showType, true)
--		default:
--			io.WriteString(p, v.Type().String())
--			io.WriteString(p, "(nil)")
--		}
--	case reflect.Array, reflect.Slice:
--		t := v.Type()
--		if showType {
--			io.WriteString(p, t.String())
--		}
--		if v.Kind() == reflect.Slice && v.IsNil() && showType {
--			io.WriteString(p, "(nil)")
--			break
--		}
--		if v.Kind() == reflect.Slice && v.IsNil() {
--			io.WriteString(p, "nil")
--			break
--		}
--		writeByte(p, '{')
--		expand := !canInline(v.Type())
--		pp := p
--		if expand {
--			writeByte(p, '\n')
--			pp = p.indent()
--		}
--		for i := 0; i < v.Len(); i++ {
--			showTypeInSlice := t.Elem().Kind() == reflect.Interface
--			pp.printValue(v.Index(i), showTypeInSlice, true)
--			if expand {
--				io.WriteString(pp, ",\n")
--			} else if i < v.Len()-1 {
--				io.WriteString(pp, ", ")
--			}
--		}
--		if expand {
--			pp.tw.Flush()
--		}
--		writeByte(p, '}')
--	case reflect.Ptr:
--		e := v.Elem()
--		if !e.IsValid() {
--			writeByte(p, '(')
--			io.WriteString(p, v.Type().String())
--			io.WriteString(p, ")(nil)")
--		} else {
--			writeByte(p, '&')
--			p.printValue(e, true, true)
--		}
--	case reflect.Chan:
--		x := v.Pointer()
--		if showType {
--			writeByte(p, '(')
--			io.WriteString(p, v.Type().String())
--			fmt.Fprintf(p, ")(%#v)", x)
--		} else {
--			fmt.Fprintf(p, "%#v", x)
--		}
--	case reflect.Func:
--		io.WriteString(p, v.Type().String())
--		io.WriteString(p, " {...}")
--	case reflect.UnsafePointer:
--		p.printInline(v, v.Pointer(), showType)
--	case reflect.Invalid:
--		io.WriteString(p, "nil")
--	}
--}
--
--func canInline(t reflect.Type) bool {
--	switch t.Kind() {
--	case reflect.Map:
--		return !canExpand(t.Elem())
--	case reflect.Struct:
--		for i := 0; i < t.NumField(); i++ {
--			if canExpand(t.Field(i).Type) {
--				return false
--			}
--		}
--		return true
--	case reflect.Interface:
--		return false
--	case reflect.Array, reflect.Slice:
--		return !canExpand(t.Elem())
--	case reflect.Ptr:
--		return false
--	case reflect.Chan, reflect.Func, reflect.UnsafePointer:
--		return false
--	}
--	return true
--}
--
--func canExpand(t reflect.Type) bool {
--	switch t.Kind() {
--	case reflect.Map, reflect.Struct,
--		reflect.Interface, reflect.Array, reflect.Slice,
--		reflect.Ptr:
--		return true
--	}
--	return false
--}
--
--func (p *printer) fmtString(s string, quote bool) {
--	if quote {
--		s = strconv.Quote(s)
--	}
--	io.WriteString(p, s)
--}
--
--func tryDeepEqual(a, b interface{}) bool {
--	defer func() { recover() }()
--	return reflect.DeepEqual(a, b)
--}
--
--func writeByte(w io.Writer, b byte) {
--	w.Write([]byte{b})
--}
--
--func getField(v reflect.Value, i int) reflect.Value {
--	val := v.Field(i)
--	if val.Kind() == reflect.Interface && !val.IsNil() {
--		val = val.Elem()
--	}
--	return val
--}
-diff --git a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/formatter_test.go b/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/formatter_test.go
-deleted file mode 100644
-index 303f033..0000000
---- a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/formatter_test.go
-+++ /dev/null
-@@ -1,146 +0,0 @@
--package pretty
--
--import (
--	"fmt"
--	"io"
--	"testing"
--	"unsafe"
--)
--
--type test struct {
--	v interface{}
--	s string
--}
--
--type LongStructTypeName struct {
--	longFieldName      interface{}
--	otherLongFieldName interface{}
--}
--
--type SA struct {
--	t *T
--}
--
--type T struct {
--	x, y int
--}
--
--type F int
--
--func (f F) Format(s fmt.State, c rune) {
--	fmt.Fprintf(s, "F(%d)", int(f))
--}
--
--var long = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"
--
--var gosyntax = []test{
--	{nil, `nil`},
--	{"", `""`},
--	{"a", `"a"`},
--	{1, "int(1)"},
--	{1.0, "float64(1)"},
--	{[]int(nil), "[]int(nil)"},
--	{[0]int{}, "[0]int{}"},
--	{complex(1, 0), "(1+0i)"},
--	//{make(chan int), "(chan int)(0x1234)"},
--	{unsafe.Pointer(uintptr(1)), "unsafe.Pointer(0x1)"},
--	{func(int) {}, "func(int) {...}"},
--	{map[int]int{1: 1}, "map[int]int{1:1}"},
--	{int32(1), "int32(1)"},
--	{io.EOF, `&errors.errorString{s:"EOF"}`},
--	{[]string{"a"}, `[]string{"a"}`},
--	{
--		[]string{long},
--		`[]string{"abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"}`,
--	},
--	{F(5), "pretty.F(5)"},
--	{
--		SA{&T{1, 2}},
--		`pretty.SA{
--    t:  &pretty.T{x:1, y:2},
--}`,
--	},
--	{
--		map[int][]byte{1: []byte{}},
--		`map[int][]uint8{
--    1:  {},
--}`,
--	},
--	{
--		map[int]T{1: T{}},
--		`map[int]pretty.T{
--    1:  {},
--}`,
--	},
--	{
--		long,
--		`"abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"`,
--	},
--	{
--		LongStructTypeName{
--			longFieldName:      LongStructTypeName{},
--			otherLongFieldName: long,
--		},
--		`pretty.LongStructTypeName{
--    longFieldName:      pretty.LongStructTypeName{},
--    otherLongFieldName: "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789",
--}`,
--	},
--	{
--		&LongStructTypeName{
--			longFieldName:      &LongStructTypeName{},
--			otherLongFieldName: (*LongStructTypeName)(nil),
--		},
--		`&pretty.LongStructTypeName{
--    longFieldName:      &pretty.LongStructTypeName{},
--    otherLongFieldName: (*pretty.LongStructTypeName)(nil),
--}`,
--	},
--	{
--		[]LongStructTypeName{
--			{nil, nil},
--			{3, 3},
--			{long, nil},
--		},
--		`[]pretty.LongStructTypeName{
--    {},
--    {
--        longFieldName:      int(3),
--        otherLongFieldName: int(3),
--    },
--    {
--        longFieldName:      "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789",
--        otherLongFieldName: nil,
--    },
--}`,
--	},
--	{
--		[]interface{}{
--			LongStructTypeName{nil, nil},
--			[]byte{1, 2, 3},
--			T{3, 4},
--			LongStructTypeName{long, nil},
--		},
--		`[]interface {}{
--    pretty.LongStructTypeName{},
--    []uint8{0x1, 0x2, 0x3},
--    pretty.T{x:3, y:4},
--    pretty.LongStructTypeName{
--        longFieldName:      "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789",
--        otherLongFieldName: nil,
--    },
--}`,
--	},
--}
--
--func TestGoSyntax(t *testing.T) {
--	for _, tt := range gosyntax {
--		s := fmt.Sprintf("%# v", Formatter(tt.v))
--		if tt.s != s {
--			t.Errorf("expected %q", tt.s)
--			t.Errorf("got      %q", s)
--			t.Errorf("expraw\n%s", tt.s)
--			t.Errorf("gotraw\n%s", s)
--		}
--	}
--}
-diff --git a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/pretty.go b/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/pretty.go
-deleted file mode 100644
-index d3df868..0000000
---- a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/pretty.go
-+++ /dev/null
-@@ -1,98 +0,0 @@
--// Package pretty provides pretty-printing for Go values. This is
--// useful during debugging, to avoid wrapping long output lines in
--// the terminal.
--//
--// It provides a function, Formatter, that can be used with any
--// function that accepts a format string. It also provides
--// convenience wrappers for functions in packages fmt and log.
--package pretty
--
--import (
--	"fmt"
--	"io"
--	"log"
--)
--
--// Errorf is a convenience wrapper for fmt.Errorf.
--//
--// Calling Errorf(f, x, y) is equivalent to
--// fmt.Errorf(f, Formatter(x), Formatter(y)).
--func Errorf(format string, a ...interface{}) error {
--	return fmt.Errorf(format, wrap(a, false)...)
--}
--
--// Fprintf is a convenience wrapper for fmt.Fprintf.
--//
--// Calling Fprintf(w, f, x, y) is equivalent to
--// fmt.Fprintf(w, f, Formatter(x), Formatter(y)).
--func Fprintf(w io.Writer, format string, a ...interface{}) (n int, error error) {
--	return fmt.Fprintf(w, format, wrap(a, false)...)
--}
--
--// Log is a convenience wrapper for log.Printf.
--//
--// Calling Log(x, y) is equivalent to
--// log.Print(Formatter(x), Formatter(y)), but each operand is
--// formatted with "%# v".
--func Log(a ...interface{}) {
--	log.Print(wrap(a, true)...)
--}
--
--// Logf is a convenience wrapper for log.Printf.
--//
--// Calling Logf(f, x, y) is equivalent to
--// log.Printf(f, Formatter(x), Formatter(y)).
--func Logf(format string, a ...interface{}) {
--	log.Printf(format, wrap(a, false)...)
--}
--
--// Logln is a convenience wrapper for log.Printf.
--//
--// Calling Logln(x, y) is equivalent to
--// log.Println(Formatter(x), Formatter(y)), but each operand is
--// formatted with "%# v".
--func Logln(a ...interface{}) {
--	log.Println(wrap(a, true)...)
--}
--
--// Print pretty-prints its operands and writes to standard output.
--//
--// Calling Print(x, y) is equivalent to
--// fmt.Print(Formatter(x), Formatter(y)), but each operand is
--// formatted with "%# v".
--func Print(a ...interface{}) (n int, errno error) {
--	return fmt.Print(wrap(a, true)...)
--}
--
--// Printf is a convenience wrapper for fmt.Printf.
--//
--// Calling Printf(f, x, y) is equivalent to
--// fmt.Printf(f, Formatter(x), Formatter(y)).
--func Printf(format string, a ...interface{}) (n int, errno error) {
--	return fmt.Printf(format, wrap(a, false)...)
--}
--
--// Println pretty-prints its operands and writes to standard output.
--//
--// Calling Print(x, y) is equivalent to
--// fmt.Println(Formatter(x), Formatter(y)), but each operand is
--// formatted with "%# v".
--func Println(a ...interface{}) (n int, errno error) {
--	return fmt.Println(wrap(a, true)...)
--}
--
--// Sprintf is a convenience wrapper for fmt.Sprintf.
--//
--// Calling Sprintf(f, x, y) is equivalent to
--// fmt.Sprintf(f, Formatter(x), Formatter(y)).
--func Sprintf(format string, a ...interface{}) string {
--	return fmt.Sprintf(format, wrap(a, false)...)
--}
--
--func wrap(a []interface{}, force bool) []interface{} {
--	w := make([]interface{}, len(a))
--	for i, x := range a {
--		w[i] = formatter{x: x, force: force}
--	}
--	return w
--}
-diff --git a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/zero.go b/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/zero.go
-deleted file mode 100644
-index abb5b6f..0000000
---- a/Godeps/_workspace/src/github.com/tonnerre/golang-pretty/zero.go
-+++ /dev/null
-@@ -1,41 +0,0 @@
--package pretty
--
--import (
--	"reflect"
--)
--
--func nonzero(v reflect.Value) bool {
--	switch v.Kind() {
--	case reflect.Bool:
--		return v.Bool()
--	case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
--		return v.Int() != 0
--	case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
--		return v.Uint() != 0
--	case reflect.Float32, reflect.Float64:
--		return v.Float() != 0
--	case reflect.Complex64, reflect.Complex128:
--		return v.Complex() != complex(0, 0)
--	case reflect.String:
--		return v.String() != ""
--	case reflect.Struct:
--		for i := 0; i < v.NumField(); i++ {
--			if nonzero(getField(v, i)) {
--				return true
--			}
--		}
--		return false
--	case reflect.Array:
--		for i := 0; i < v.Len(); i++ {
--			if nonzero(v.Index(i)) {
--				return true
--			}
--		}
--		return false
--	case reflect.Map, reflect.Interface, reflect.Slice, reflect.Ptr, reflect.Chan, reflect.Func:
--		return !v.IsNil()
--	case reflect.UnsafePointer:
--		return v.Pointer() != 0
--	}
--	return true
--}
 diff --git a/Godeps/_workspace/src/github.com/vaughan0/go-ini/LICENSE b/Godeps/_workspace/src/github.com/vaughan0/go-ini/LICENSE
 deleted file mode 100644
 index 968b453..0000000
@@ -101361,7 +159550,7 @@ index d13c999..0000000
 -stuff = things
 diff --git a/Godeps/_workspace/src/golang.org/x/net/context/context.go b/Godeps/_workspace/src/golang.org/x/net/context/context.go
 deleted file mode 100644
-index 66aff7c..0000000
+index 490245d..0000000
 --- a/Godeps/_workspace/src/golang.org/x/net/context/context.go
 +++ /dev/null
 @@ -1,432 +0,0 @@
@@ -101401,7 +159590,7 @@ index 66aff7c..0000000
 -//
 -// See http://blog.golang.org/context for example code for a server that uses
 -// Contexts.
--package context
+-package context // import "golang.org/x/net/context"
 -
 -import (
 -	"errors"
@@ -102390,7 +160579,7 @@ index a6754dc..0000000
 -}
 diff --git a/Godeps/_workspace/src/golang.org/x/net/html/atom/atom.go b/Godeps/_workspace/src/golang.org/x/net/html/atom/atom.go
 deleted file mode 100644
-index 227404b..0000000
+index cd0a8ac..0000000
 --- a/Godeps/_workspace/src/golang.org/x/net/html/atom/atom.go
 +++ /dev/null
 @@ -1,78 +0,0 @@
@@ -102411,7 +160600,7 @@ index 227404b..0000000
 -// whether atom.H1 < atom.H2 may also change. The codes are not guaranteed to
 -// be dense. The only guarantees are that e.g. looking up "div" will yield
 -// atom.Div, calling atom.Div.String will return "div", and atom.Div != 0.
--package atom
+-package atom // import "golang.org/x/net/html/atom"
 -
 -// Atom is an integer code for a string. The zero value maps to "".
 -type Atom uint32
@@ -104278,7 +162467,7 @@ index db016a1..0000000
 -}
 diff --git a/Godeps/_workspace/src/golang.org/x/net/html/charset/charset.go b/Godeps/_workspace/src/golang.org/x/net/html/charset/charset.go
 deleted file mode 100644
-index b19f83b..0000000
+index 2e5f9ba..0000000
 --- a/Godeps/_workspace/src/golang.org/x/net/html/charset/charset.go
 +++ /dev/null
 @@ -1,231 +0,0 @@
@@ -104290,7 +162479,7 @@ index b19f83b..0000000
 -//
 -// The mapping from encoding labels to encodings is defined at
 -// http://encoding.spec.whatwg.org.
--package charset
+-package charset // import "golang.org/x/net/html/charset"
 -
 -import (
 -	"bytes"
@@ -105753,7 +163942,7 @@ index d7cc8bb..0000000
 -}
 diff --git a/Godeps/_workspace/src/golang.org/x/net/html/doc.go b/Godeps/_workspace/src/golang.org/x/net/html/doc.go
 deleted file mode 100644
-index fac0f54..0000000
+index 32379a3..0000000
 --- a/Godeps/_workspace/src/golang.org/x/net/html/doc.go
 +++ /dev/null
 @@ -1,106 +0,0 @@
@@ -105852,7 +164041,7 @@ index fac0f54..0000000
 -http://www.whatwg.org/specs/web-apps/current-work/multipage/syntax.html and
 -http://www.whatwg.org/specs/web-apps/current-work/multipage/tokenization.html
 -*/
--package html
+-package html // import "golang.org/x/net/html"
 -
 -// The tokenization algorithm implemented by this package is not a line-by-line
 -// transliteration of the relatively verbose state-machine in the WHATWG
@@ -134661,7 +192850,7 @@ index 7032213..0000000
 -}
 diff --git a/Godeps/_workspace/src/golang.org/x/net/websocket/websocket.go b/Godeps/_workspace/src/golang.org/x/net/websocket/websocket.go
 deleted file mode 100644
-index 0f4917b..0000000
+index b8d2e6d..0000000
 --- a/Godeps/_workspace/src/golang.org/x/net/websocket/websocket.go
 +++ /dev/null
 @@ -1,411 +0,0 @@
@@ -134671,7 +192860,7 @@ index 0f4917b..0000000
 -
 -// Package websocket implements a client and server for the WebSocket protocol
 -// as specified in RFC 6455.
--package websocket
+-package websocket // import "golang.org/x/net/websocket"
 -
 -import (
 -	"bufio"
@@ -146430,6 +204619,1788 @@ index 8110ce3..0000000
 -	return 0
 -
 -}
+diff --git a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/LICENSE b/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/LICENSE
+deleted file mode 100644
+index efa1aa1..0000000
+--- a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/LICENSE
++++ /dev/null
+@@ -1,57 +0,0 @@
+-Copyright (c) 2012 Péter Surányi. All rights reserved.
+-
+-Redistribution and use in source and binary forms, with or without
+-modification, are permitted provided that the following conditions are
+-met:
+-
+-   * Redistributions of source code must retain the above copyright
+-notice, this list of conditions and the following disclaimer.
+-   * Redistributions in binary form must reproduce the above
+-copyright notice, this list of conditions and the following disclaimer
+-in the documentation and/or other materials provided with the
+-distribution.
+-
+-THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+-"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+-LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+-A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+-OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+-SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+-LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+-DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+-THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+-(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+-OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+-
+-----------------------------------------------------------------------
+-Portions of inf.Dec's source code have been derived from Go and are
+-covered by the following license:
+-----------------------------------------------------------------------
+-
+-Copyright (c) 2009 The Go Authors. All rights reserved.
+-
+-Redistribution and use in source and binary forms, with or without
+-modification, are permitted provided that the following conditions are
+-met:
+-
+-   * Redistributions of source code must retain the above copyright
+-notice, this list of conditions and the following disclaimer.
+-   * Redistributions in binary form must reproduce the above
+-copyright notice, this list of conditions and the following disclaimer
+-in the documentation and/or other materials provided with the
+-distribution.
+-   * Neither the name of Google Inc. nor the names of its
+-contributors may be used to endorse or promote products derived from
+-this software without specific prior written permission.
+-
+-THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+-"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+-LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+-A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+-OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+-SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+-LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+-DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+-THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+-(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+-OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+diff --git a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/benchmark_test.go b/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/benchmark_test.go
+deleted file mode 100644
+index 27071da..0000000
+--- a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/benchmark_test.go
++++ /dev/null
+@@ -1,210 +0,0 @@
+-package inf
+-
+-import (
+-	"fmt"
+-	"math/big"
+-	"math/rand"
+-	"sync"
+-	"testing"
+-)
+-
+-const maxcap = 1024 * 1024
+-const bits = 256
+-const maxscale = 32
+-
+-var once sync.Once
+-
+-var decInput [][2]Dec
+-var intInput [][2]big.Int
+-
+-var initBench = func() {
+-	decInput = make([][2]Dec, maxcap)
+-	intInput = make([][2]big.Int, maxcap)
+-	max := new(big.Int).Lsh(big.NewInt(1), bits)
+-	r := rand.New(rand.NewSource(0))
+-	for i := 0; i < cap(decInput); i++ {
+-		decInput[i][0].SetUnscaledBig(new(big.Int).Rand(r, max)).
+-			SetScale(Scale(r.Int31n(int32(2*maxscale-1)) - int32(maxscale)))
+-		decInput[i][1].SetUnscaledBig(new(big.Int).Rand(r, max)).
+-			SetScale(Scale(r.Int31n(int32(2*maxscale-1)) - int32(maxscale)))
+-	}
+-	for i := 0; i < cap(intInput); i++ {
+-		intInput[i][0].Rand(r, max)
+-		intInput[i][1].Rand(r, max)
+-	}
+-}
+-
+-func doBenchmarkDec1(b *testing.B, f func(z *Dec)) {
+-	once.Do(initBench)
+-	b.ResetTimer()
+-	b.StartTimer()
+-	for i := 0; i < b.N; i++ {
+-		f(&decInput[i%maxcap][0])
+-	}
+-}
+-
+-func doBenchmarkDec2(b *testing.B, f func(x, y *Dec)) {
+-	once.Do(initBench)
+-	b.ResetTimer()
+-	b.StartTimer()
+-	for i := 0; i < b.N; i++ {
+-		f(&decInput[i%maxcap][0], &decInput[i%maxcap][1])
+-	}
+-}
+-
+-func doBenchmarkInt1(b *testing.B, f func(z *big.Int)) {
+-	once.Do(initBench)
+-	b.ResetTimer()
+-	b.StartTimer()
+-	for i := 0; i < b.N; i++ {
+-		f(&intInput[i%maxcap][0])
+-	}
+-}
+-
+-func doBenchmarkInt2(b *testing.B, f func(x, y *big.Int)) {
+-	once.Do(initBench)
+-	b.ResetTimer()
+-	b.StartTimer()
+-	for i := 0; i < b.N; i++ {
+-		f(&intInput[i%maxcap][0], &intInput[i%maxcap][1])
+-	}
+-}
+-
+-func Benchmark_Dec_String(b *testing.B) {
+-	doBenchmarkDec1(b, func(x *Dec) {
+-		x.String()
+-	})
+-}
+-
+-func Benchmark_Dec_StringScan(b *testing.B) {
+-	doBenchmarkDec1(b, func(x *Dec) {
+-		s := x.String()
+-		d := new(Dec)
+-		fmt.Sscan(s, d)
+-	})
+-}
+-
+-func Benchmark_Dec_GobEncode(b *testing.B) {
+-	doBenchmarkDec1(b, func(x *Dec) {
+-		x.GobEncode()
+-	})
+-}
+-
+-func Benchmark_Dec_GobEnDecode(b *testing.B) {
+-	doBenchmarkDec1(b, func(x *Dec) {
+-		g, _ := x.GobEncode()
+-		new(Dec).GobDecode(g)
+-	})
+-}
+-
+-func Benchmark_Dec_Add(b *testing.B) {
+-	doBenchmarkDec2(b, func(x, y *Dec) {
+-		ys := y.Scale()
+-		y.SetScale(x.Scale())
+-		_ = new(Dec).Add(x, y)
+-		y.SetScale(ys)
+-	})
+-}
+-
+-func Benchmark_Dec_AddMixed(b *testing.B) {
+-	doBenchmarkDec2(b, func(x, y *Dec) {
+-		_ = new(Dec).Add(x, y)
+-	})
+-}
+-
+-func Benchmark_Dec_Sub(b *testing.B) {
+-	doBenchmarkDec2(b, func(x, y *Dec) {
+-		ys := y.Scale()
+-		y.SetScale(x.Scale())
+-		_ = new(Dec).Sub(x, y)
+-		y.SetScale(ys)
+-	})
+-}
+-
+-func Benchmark_Dec_SubMixed(b *testing.B) {
+-	doBenchmarkDec2(b, func(x, y *Dec) {
+-		_ = new(Dec).Sub(x, y)
+-	})
+-}
+-
+-func Benchmark_Dec_Mul(b *testing.B) {
+-	doBenchmarkDec2(b, func(x, y *Dec) {
+-		_ = new(Dec).Mul(x, y)
+-	})
+-}
+-
+-func Benchmark_Dec_Mul_QuoExact(b *testing.B) {
+-	doBenchmarkDec2(b, func(x, y *Dec) {
+-		v := new(Dec).Mul(x, y)
+-		_ = new(Dec).QuoExact(v, y)
+-	})
+-}
+-
+-func Benchmark_Dec_QuoRound_Fixed_Down(b *testing.B) {
+-	doBenchmarkDec2(b, func(x, y *Dec) {
+-		_ = new(Dec).QuoRound(x, y, 0, RoundDown)
+-	})
+-}
+-
+-func Benchmark_Dec_QuoRound_Fixed_HalfUp(b *testing.B) {
+-	doBenchmarkDec2(b, func(x, y *Dec) {
+-		_ = new(Dec).QuoRound(x, y, 0, RoundHalfUp)
+-	})
+-}
+-
+-func Benchmark_Int_String(b *testing.B) {
+-	doBenchmarkInt1(b, func(x *big.Int) {
+-		x.String()
+-	})
+-}
+-
+-func Benchmark_Int_StringScan(b *testing.B) {
+-	doBenchmarkInt1(b, func(x *big.Int) {
+-		s := x.String()
+-		d := new(big.Int)
+-		fmt.Sscan(s, d)
+-	})
+-}
+-
+-func Benchmark_Int_GobEncode(b *testing.B) {
+-	doBenchmarkInt1(b, func(x *big.Int) {
+-		x.GobEncode()
+-	})
+-}
+-
+-func Benchmark_Int_GobEnDecode(b *testing.B) {
+-	doBenchmarkInt1(b, func(x *big.Int) {
+-		g, _ := x.GobEncode()
+-		new(big.Int).GobDecode(g)
+-	})
+-}
+-
+-func Benchmark_Int_Add(b *testing.B) {
+-	doBenchmarkInt2(b, func(x, y *big.Int) {
+-		_ = new(big.Int).Add(x, y)
+-	})
+-}
+-
+-func Benchmark_Int_Sub(b *testing.B) {
+-	doBenchmarkInt2(b, func(x, y *big.Int) {
+-		_ = new(big.Int).Sub(x, y)
+-	})
+-}
+-
+-func Benchmark_Int_Mul(b *testing.B) {
+-	doBenchmarkInt2(b, func(x, y *big.Int) {
+-		_ = new(big.Int).Mul(x, y)
+-	})
+-}
+-
+-func Benchmark_Int_Quo(b *testing.B) {
+-	doBenchmarkInt2(b, func(x, y *big.Int) {
+-		_ = new(big.Int).Quo(x, y)
+-	})
+-}
+-
+-func Benchmark_Int_QuoRem(b *testing.B) {
+-	doBenchmarkInt2(b, func(x, y *big.Int) {
+-		_, _ = new(big.Int).QuoRem(x, y, new(big.Int))
+-	})
+-}
+diff --git a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/dec.go b/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/dec.go
+deleted file mode 100644
+index d17ad94..0000000
+--- a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/dec.go
++++ /dev/null
+@@ -1,615 +0,0 @@
+-// Package inf (type inf.Dec) implements "infinite-precision" decimal
+-// arithmetic.
+-// "Infinite precision" describes two characteristics: practically unlimited
+-// precision for decimal number representation and no support for calculating
+-// with any specific fixed precision.
+-// (Although there is no practical limit on precision, inf.Dec can only
+-// represent finite decimals.)
+-//
+-// This package is currently in experimental stage and the API may change.
+-//
+-// This package does NOT support:
+-//  - rounding to specific precisions (as opposed to specific decimal positions)
+-//  - the notion of context (each rounding must be explicit)
+-//  - NaN and Inf values, and distinguishing between positive and negative zero
+-//  - conversions to and from float32/64 types
+-//
+-// Features considered for possible addition:
+-//  + formatting options
+-//  + Exp method
+-//  + combined operations such as AddRound/MulAdd etc
+-//  + exchanging data in decimal32/64/128 formats
+-//
+-package inf
+-
+-// TODO:
+-//  - avoid excessive deep copying (quo and rounders)
+-
+-import (
+-	"fmt"
+-	"io"
+-	"math/big"
+-	"strings"
+-)
+-
+-// A Dec represents a signed arbitrary-precision decimal.
+-// It is a combination of a sign, an arbitrary-precision integer coefficient
+-// value, and a signed fixed-precision exponent value.
+-// The sign and the coefficient value are handled together as a signed value
+-// and referred to as the unscaled value.
+-// (Positive and negative zero values are not distinguished.)
+-// Since the exponent is most commonly non-positive, it is handled in negated
+-// form and referred to as scale.
+-//
+-// The mathematical value of a Dec equals:
+-//
+-//  unscaled * 10**(-scale)
+-//
+-// Note that different Dec representations may have equal mathematical values.
+-//
+-//  unscaled  scale  String()
+-//  -------------------------
+-//         0      0    "0"
+-//         0      2    "0.00"
+-//         0     -2    "0"
+-//         1      0    "1"
+-//       100      2    "1.00"
+-//        10      0   "10"
+-//         1     -1   "10"
+-//
+-// The zero value for a Dec represents the value 0 with scale 0.
+-//
+-// Operations are typically performed through the *Dec type.
+-// The semantics of the assignment operation "=" for "bare" Dec values is
+-// undefined and should not be relied on.
+-//
+-// Methods are typically of the form:
+-//
+-//	func (z *Dec) Op(x, y *Dec) *Dec
+-//
+-// and implement operations z = x Op y with the result as receiver; if it
+-// is one of the operands it may be overwritten (and its memory reused).
+-// To enable chaining of operations, the result is also returned. Methods
+-// returning a result other than *Dec take one of the operands as the receiver.
+-//
+-// A "bare" Quo method (quotient / division operation) is not provided, as the
+-// result is not always a finite decimal and thus in general cannot be
+-// represented as a Dec.
+-// Instead, in the common case when rounding is (potentially) necessary,
+-// QuoRound should be used with a Scale and a Rounder.
+-// QuoExact or QuoRound with RoundExact can be used in the special cases when it
+-// is known that the result is always a finite decimal.
+-//
+-type Dec struct {
+-	unscaled big.Int
+-	scale    Scale
+-}
+-
+-// Scale represents the type used for the scale of a Dec.
+-type Scale int32
+-
+-const scaleSize = 4 // bytes in a Scale value
+-
+-// Scaler represents a method for obtaining the scale to use for the result of
+-// an operation on x and y.
+-type scaler interface {
+-	Scale(x *Dec, y *Dec) Scale
+-}
+-
+-var bigInt = [...]*big.Int{
+-	big.NewInt(0), big.NewInt(1), big.NewInt(2), big.NewInt(3), big.NewInt(4),
+-	big.NewInt(5), big.NewInt(6), big.NewInt(7), big.NewInt(8), big.NewInt(9),
+-	big.NewInt(10),
+-}
+-
+-var exp10cache [64]big.Int = func() [64]big.Int {
+-	e10, e10i := [64]big.Int{}, bigInt[1]
+-	for i, _ := range e10 {
+-		e10[i].Set(e10i)
+-		e10i = new(big.Int).Mul(e10i, bigInt[10])
+-	}
+-	return e10
+-}()
+-
+-// NewDec allocates and returns a new Dec set to the given int64 unscaled value
+-// and scale.
+-func NewDec(unscaled int64, scale Scale) *Dec {
+-	return new(Dec).SetUnscaled(unscaled).SetScale(scale)
+-}
+-
+-// NewDecBig allocates and returns a new Dec set to the given *big.Int unscaled
+-// value and scale.
+-func NewDecBig(unscaled *big.Int, scale Scale) *Dec {
+-	return new(Dec).SetUnscaledBig(unscaled).SetScale(scale)
+-}
+-
+-// Scale returns the scale of x.
+-func (x *Dec) Scale() Scale {
+-	return x.scale
+-}
+-
+-// Unscaled returns the unscaled value of x for u and true for ok when the
+-// unscaled value can be represented as int64; otherwise it returns an undefined
+-// int64 value for u and false for ok. Use x.UnscaledBig().Int64() to avoid
+-// checking the validity of the value when the check is known to be redundant.
+-func (x *Dec) Unscaled() (u int64, ok bool) {
+-	u = x.unscaled.Int64()
+-	var i big.Int
+-	ok = i.SetInt64(u).Cmp(&x.unscaled) == 0
+-	return
+-}
+-
+-// UnscaledBig returns the unscaled value of x as *big.Int.
+-func (x *Dec) UnscaledBig() *big.Int {
+-	return &x.unscaled
+-}
+-
+-// SetScale sets the scale of z, with the unscaled value unchanged, and returns
+-// z.
+-// The mathematical value of the Dec changes as if it was multiplied by
+-// 10**(oldscale-scale).
+-func (z *Dec) SetScale(scale Scale) *Dec {
+-	z.scale = scale
+-	return z
+-}
+-
+-// SetUnscaled sets the unscaled value of z, with the scale unchanged, and
+-// returns z.
+-func (z *Dec) SetUnscaled(unscaled int64) *Dec {
+-	z.unscaled.SetInt64(unscaled)
+-	return z
+-}
+-
+-// SetUnscaledBig sets the unscaled value of z, with the scale unchanged, and
+-// returns z.
+-func (z *Dec) SetUnscaledBig(unscaled *big.Int) *Dec {
+-	z.unscaled.Set(unscaled)
+-	return z
+-}
+-
+-// Set sets z to the value of x and returns z.
+-// It does nothing if z == x.
+-func (z *Dec) Set(x *Dec) *Dec {
+-	if z != x {
+-		z.SetUnscaledBig(x.UnscaledBig())
+-		z.SetScale(x.Scale())
+-	}
+-	return z
+-}
+-
+-// Sign returns:
+-//
+-//	-1 if x <  0
+-//	 0 if x == 0
+-//	+1 if x >  0
+-//
+-func (x *Dec) Sign() int {
+-	return x.UnscaledBig().Sign()
+-}
+-
+-// Neg sets z to -x and returns z.
+-func (z *Dec) Neg(x *Dec) *Dec {
+-	z.SetScale(x.Scale())
+-	z.UnscaledBig().Neg(x.UnscaledBig())
+-	return z
+-}
+-
+-// Cmp compares x and y and returns:
+-//
+-//   -1 if x <  y
+-//    0 if x == y
+-//   +1 if x >  y
+-//
+-func (x *Dec) Cmp(y *Dec) int {
+-	xx, yy := upscale(x, y)
+-	return xx.UnscaledBig().Cmp(yy.UnscaledBig())
+-}
+-
+-// Abs sets z to |x| (the absolute value of x) and returns z.
+-func (z *Dec) Abs(x *Dec) *Dec {
+-	z.SetScale(x.Scale())
+-	z.UnscaledBig().Abs(x.UnscaledBig())
+-	return z
+-}
+-
+-// Add sets z to the sum x+y and returns z.
+-// The scale of z is the greater of the scales of x and y.
+-func (z *Dec) Add(x, y *Dec) *Dec {
+-	xx, yy := upscale(x, y)
+-	z.SetScale(xx.Scale())
+-	z.UnscaledBig().Add(xx.UnscaledBig(), yy.UnscaledBig())
+-	return z
+-}
+-
+-// Sub sets z to the difference x-y and returns z.
+-// The scale of z is the greater of the scales of x and y.
+-func (z *Dec) Sub(x, y *Dec) *Dec {
+-	xx, yy := upscale(x, y)
+-	z.SetScale(xx.Scale())
+-	z.UnscaledBig().Sub(xx.UnscaledBig(), yy.UnscaledBig())
+-	return z
+-}
+-
+-// Mul sets z to the product x*y and returns z.
+-// The scale of z is the sum of the scales of x and y.
+-func (z *Dec) Mul(x, y *Dec) *Dec {
+-	z.SetScale(x.Scale() + y.Scale())
+-	z.UnscaledBig().Mul(x.UnscaledBig(), y.UnscaledBig())
+-	return z
+-}
+-
+-// Round sets z to the value of x rounded to Scale s using Rounder r, and
+-// returns z.
+-func (z *Dec) Round(x *Dec, s Scale, r Rounder) *Dec {
+-	return z.QuoRound(x, NewDec(1, 0), s, r)
+-}
+-
+-// QuoRound sets z to the quotient x/y, rounded using the given Rounder to the
+-// specified scale.
+-//
+-// If the rounder is RoundExact but the result can not be expressed exactly at
+-// the specified scale, QuoRound returns nil, and the value of z is undefined.
+-//
+-// There is no corresponding Div method; the equivalent can be achieved through
+-// the choice of Rounder used.
+-//
+-func (z *Dec) QuoRound(x, y *Dec, s Scale, r Rounder) *Dec {
+-	return z.quo(x, y, sclr{s}, r)
+-}
+-
+-func (z *Dec) quo(x, y *Dec, s scaler, r Rounder) *Dec {
+-	scl := s.Scale(x, y)
+-	var zzz *Dec
+-	if r.UseRemainder() {
+-		zz, rA, rB := new(Dec).quoRem(x, y, scl, true, new(big.Int), new(big.Int))
+-		zzz = r.Round(new(Dec), zz, rA, rB)
+-	} else {
+-		zz, _, _ := new(Dec).quoRem(x, y, scl, false, nil, nil)
+-		zzz = r.Round(new(Dec), zz, nil, nil)
+-	}
+-	if zzz == nil {
+-		return nil
+-	}
+-	return z.Set(zzz)
+-}
+-
+-// QuoExact sets z to the quotient x/y and returns z when x/y is a finite
+-// decimal. Otherwise it returns nil and the value of z is undefined.
+-//
+-// The scale of a non-nil result is "x.Scale() - y.Scale()" or greater; it is
+-// calculated so that the remainder will be zero whenever x/y is a finite
+-// decimal.
+-func (z *Dec) QuoExact(x, y *Dec) *Dec {
+-	return z.quo(x, y, scaleQuoExact{}, RoundExact)
+-}
+-
+-// quoRem sets z to the quotient x/y with the scale s, and if useRem is true,
+-// it sets remNum and remDen to the numerator and denominator of the remainder.
+-// It returns z, remNum and remDen.
+-//
+-// The remainder is normalized to the range -1 < r < 1 to simplify rounding;
+-// that is, the results satisfy the following equation:
+-//
+-//  x / y = z + (remNum/remDen) * 10**(-z.Scale())
+-//
+-// See Rounder for more details about rounding.
+-//
+-func (z *Dec) quoRem(x, y *Dec, s Scale, useRem bool,
+-	remNum, remDen *big.Int) (*Dec, *big.Int, *big.Int) {
+-	// difference (required adjustment) compared to "canonical" result scale
+-	shift := s - (x.Scale() - y.Scale())
+-	// pointers to adjusted unscaled dividend and divisor
+-	var ix, iy *big.Int
+-	switch {
+-	case shift > 0:
+-		// increased scale: decimal-shift dividend left
+-		ix = new(big.Int).Mul(x.UnscaledBig(), exp10(shift))
+-		iy = y.UnscaledBig()
+-	case shift < 0:
+-		// decreased scale: decimal-shift divisor left
+-		ix = x.UnscaledBig()
+-		iy = new(big.Int).Mul(y.UnscaledBig(), exp10(-shift))
+-	default:
+-		ix = x.UnscaledBig()
+-		iy = y.UnscaledBig()
+-	}
+-	// save a copy of iy in case it to be overwritten with the result
+-	iy2 := iy
+-	if iy == z.UnscaledBig() {
+-		iy2 = new(big.Int).Set(iy)
+-	}
+-	// set scale
+-	z.SetScale(s)
+-	// set unscaled
+-	if useRem {
+-		// Int division
+-		_, intr := z.UnscaledBig().QuoRem(ix, iy, new(big.Int))
+-		// set remainder
+-		remNum.Set(intr)
+-		remDen.Set(iy2)
+-	} else {
+-		z.UnscaledBig().Quo(ix, iy)
+-	}
+-	return z, remNum, remDen
+-}
+-
+-type sclr struct{ s Scale }
+-
+-func (s sclr) Scale(x, y *Dec) Scale {
+-	return s.s
+-}
+-
+-type scaleQuoExact struct{}
+-
+-func (sqe scaleQuoExact) Scale(x, y *Dec) Scale {
+-	rem := new(big.Rat).SetFrac(x.UnscaledBig(), y.UnscaledBig())
+-	f2, f5 := factor2(rem.Denom()), factor(rem.Denom(), bigInt[5])
+-	var f10 Scale
+-	if f2 > f5 {
+-		f10 = Scale(f2)
+-	} else {
+-		f10 = Scale(f5)
+-	}
+-	return x.Scale() - y.Scale() + f10
+-}
+-
+-func factor(n *big.Int, p *big.Int) int {
+-	// could be improved for large factors
+-	d, f := n, 0
+-	for {
+-		dd, dm := new(big.Int).DivMod(d, p, new(big.Int))
+-		if dm.Sign() == 0 {
+-			f++
+-			d = dd
+-		} else {
+-			break
+-		}
+-	}
+-	return f
+-}
+-
+-func factor2(n *big.Int) int {
+-	// could be improved for large factors
+-	f := 0
+-	for ; n.Bit(f) == 0; f++ {
+-	}
+-	return f
+-}
+-
+-func upscale(a, b *Dec) (*Dec, *Dec) {
+-	if a.Scale() == b.Scale() {
+-		return a, b
+-	}
+-	if a.Scale() > b.Scale() {
+-		bb := b.rescale(a.Scale())
+-		return a, bb
+-	}
+-	aa := a.rescale(b.Scale())
+-	return aa, b
+-}
+-
+-func exp10(x Scale) *big.Int {
+-	if int(x) < len(exp10cache) {
+-		return &exp10cache[int(x)]
+-	}
+-	return new(big.Int).Exp(bigInt[10], big.NewInt(int64(x)), nil)
+-}
+-
+-func (x *Dec) rescale(newScale Scale) *Dec {
+-	shift := newScale - x.Scale()
+-	switch {
+-	case shift < 0:
+-		e := exp10(-shift)
+-		return NewDecBig(new(big.Int).Quo(x.UnscaledBig(), e), newScale)
+-	case shift > 0:
+-		e := exp10(shift)
+-		return NewDecBig(new(big.Int).Mul(x.UnscaledBig(), e), newScale)
+-	}
+-	return x
+-}
+-
+-var zeros = []byte("00000000000000000000000000000000" +
+-	"00000000000000000000000000000000")
+-var lzeros = Scale(len(zeros))
+-
+-func appendZeros(s []byte, n Scale) []byte {
+-	for i := Scale(0); i < n; i += lzeros {
+-		if n > i+lzeros {
+-			s = append(s, zeros...)
+-		} else {
+-			s = append(s, zeros[0:n-i]...)
+-		}
+-	}
+-	return s
+-}
+-
+-func (x *Dec) String() string {
+-	if x == nil {
+-		return "<nil>"
+-	}
+-	scale := x.Scale()
+-	s := []byte(x.UnscaledBig().String())
+-	if scale <= 0 {
+-		if scale != 0 && x.unscaled.Sign() != 0 {
+-			s = appendZeros(s, -scale)
+-		}
+-		return string(s)
+-	}
+-	negbit := Scale(-((x.Sign() - 1) / 2))
+-	// scale > 0
+-	lens := Scale(len(s))
+-	if lens-negbit <= scale {
+-		ss := make([]byte, 0, scale+2)
+-		if negbit == 1 {
+-			ss = append(ss, '-')
+-		}
+-		ss = append(ss, '0', '.')
+-		ss = appendZeros(ss, scale-lens+negbit)
+-		ss = append(ss, s[negbit:]...)
+-		return string(ss)
+-	}
+-	// lens > scale
+-	ss := make([]byte, 0, lens+1)
+-	ss = append(ss, s[:lens-scale]...)
+-	ss = append(ss, '.')
+-	ss = append(ss, s[lens-scale:]...)
+-	return string(ss)
+-}
+-
+-// Format is a support routine for fmt.Formatter. It accepts the decimal
+-// formats 'd' and 'f', and handles both equivalently.
+-// Width, precision, flags and bases 2, 8, 16 are not supported.
+-func (x *Dec) Format(s fmt.State, ch rune) {
+-	if ch != 'd' && ch != 'f' && ch != 'v' && ch != 's' {
+-		fmt.Fprintf(s, "%%!%c(dec.Dec=%s)", ch, x.String())
+-		return
+-	}
+-	fmt.Fprintf(s, x.String())
+-}
+-
+-func (z *Dec) scan(r io.RuneScanner) (*Dec, error) {
+-	unscaled := make([]byte, 0, 256) // collects chars of unscaled as bytes
+-	dp, dg := -1, -1                 // indexes of decimal point, first digit
+-loop:
+-	for {
+-		ch, _, err := r.ReadRune()
+-		if err == io.EOF {
+-			break loop
+-		}
+-		if err != nil {
+-			return nil, err
+-		}
+-		switch {
+-		case ch == '+' || ch == '-':
+-			if len(unscaled) > 0 || dp >= 0 { // must be first character
+-				r.UnreadRune()
+-				break loop
+-			}
+-		case ch == '.':
+-			if dp >= 0 {
+-				r.UnreadRune()
+-				break loop
+-			}
+-			dp = len(unscaled)
+-			continue // don't add to unscaled
+-		case ch >= '0' && ch <= '9':
+-			if dg == -1 {
+-				dg = len(unscaled)
+-			}
+-		default:
+-			r.UnreadRune()
+-			break loop
+-		}
+-		unscaled = append(unscaled, byte(ch))
+-	}
+-	if dg == -1 {
+-		return nil, fmt.Errorf("no digits read")
+-	}
+-	if dp >= 0 {
+-		z.SetScale(Scale(len(unscaled) - dp))
+-	} else {
+-		z.SetScale(0)
+-	}
+-	_, ok := z.UnscaledBig().SetString(string(unscaled), 10)
+-	if !ok {
+-		return nil, fmt.Errorf("invalid decimal: %s", string(unscaled))
+-	}
+-	return z, nil
+-}
+-
+-// SetString sets z to the value of s, interpreted as a decimal (base 10),
+-// and returns z and a boolean indicating success. The scale of z is the
+-// number of digits after the decimal point (including any trailing 0s),
+-// or 0 if there is no decimal point. If SetString fails, the value of z
+-// is undefined but the returned value is nil.
+-func (z *Dec) SetString(s string) (*Dec, bool) {
+-	r := strings.NewReader(s)
+-	_, err := z.scan(r)
+-	if err != nil {
+-		return nil, false
+-	}
+-	_, _, err = r.ReadRune()
+-	if err != io.EOF {
+-		return nil, false
+-	}
+-	// err == io.EOF => scan consumed all of s
+-	return z, true
+-}
+-
+-// Scan is a support routine for fmt.Scanner; it sets z to the value of
+-// the scanned number. It accepts the decimal formats 'd' and 'f', and
+-// handles both equivalently. Bases 2, 8, 16 are not supported.
+-// The scale of z is the number of digits after the decimal point
+-// (including any trailing 0s), or 0 if there is no decimal point.
+-func (z *Dec) Scan(s fmt.ScanState, ch rune) error {
+-	if ch != 'd' && ch != 'f' && ch != 's' && ch != 'v' {
+-		return fmt.Errorf("Dec.Scan: invalid verb '%c'", ch)
+-	}
+-	s.SkipSpace()
+-	_, err := z.scan(s)
+-	return err
+-}
+-
+-// Gob encoding version
+-const decGobVersion byte = 1
+-
+-func scaleBytes(s Scale) []byte {
+-	buf := make([]byte, scaleSize)
+-	i := scaleSize
+-	for j := 0; j < scaleSize; j++ {
+-		i--
+-		buf[i] = byte(s)
+-		s >>= 8
+-	}
+-	return buf
+-}
+-
+-func scale(b []byte) (s Scale) {
+-	for j := 0; j < scaleSize; j++ {
+-		s <<= 8
+-		s |= Scale(b[j])
+-	}
+-	return
+-}
+-
+-// GobEncode implements the gob.GobEncoder interface.
+-func (x *Dec) GobEncode() ([]byte, error) {
+-	buf, err := x.UnscaledBig().GobEncode()
+-	if err != nil {
+-		return nil, err
+-	}
+-	buf = append(append(buf, scaleBytes(x.Scale())...), decGobVersion)
+-	return buf, nil
+-}
+-
+-// GobDecode implements the gob.GobDecoder interface.
+-func (z *Dec) GobDecode(buf []byte) error {
+-	if len(buf) == 0 {
+-		return fmt.Errorf("Dec.GobDecode: no data")
+-	}
+-	b := buf[len(buf)-1]
+-	if b != decGobVersion {
+-		return fmt.Errorf("Dec.GobDecode: encoding version %d not supported", b)
+-	}
+-	l := len(buf) - scaleSize - 1
+-	err := z.UnscaledBig().GobDecode(buf[:l])
+-	if err != nil {
+-		return err
+-	}
+-	z.SetScale(scale(buf[l : l+scaleSize]))
+-	return nil
+-}
+-
+-// MarshalText implements the encoding.TextMarshaler interface.
+-func (x *Dec) MarshalText() ([]byte, error) {
+-	return []byte(x.String()), nil
+-}
+-
+-// UnmarshalText implements the encoding.TextUnmarshaler interface.
+-func (z *Dec) UnmarshalText(data []byte) error {
+-	_, ok := z.SetString(string(data))
+-	if !ok {
+-		return fmt.Errorf("invalid inf.Dec")
+-	}
+-	return nil
+-}
+diff --git a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/dec_go1_2_test.go b/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/dec_go1_2_test.go
+deleted file mode 100644
+index 5df0f7b..0000000
+--- a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/dec_go1_2_test.go
++++ /dev/null
+@@ -1,33 +0,0 @@
+-// +build go1.2
+-
+-package inf
+-
+-import (
+-	"encoding"
+-	"encoding/json"
+-	"testing"
+-)
+-
+-var _ encoding.TextMarshaler = new(Dec)
+-var _ encoding.TextUnmarshaler = new(Dec)
+-
+-type Obj struct {
+-	Val *Dec
+-}
+-
+-func TestDecJsonMarshalUnmarshal(t *testing.T) {
+-	o := Obj{Val: NewDec(123, 2)}
+-	js, err := json.Marshal(o)
+-	if err != nil {
+-		t.Fatalf("json.Marshal(%v): got %v, want ok", o, err)
+-	}
+-	o2 := &Obj{}
+-	err = json.Unmarshal(js, o2)
+-	if err != nil {
+-		t.Fatalf("json.Unmarshal(%#q): got %v, want ok", js, err)
+-	}
+-	if o.Val.Scale() != o2.Val.Scale() ||
+-		o.Val.UnscaledBig().Cmp(o2.Val.UnscaledBig()) != 0 {
+-		t.Fatalf("json.Unmarshal(json.Marshal(%v)): want %v, got %v", o, o, o2)
+-	}
+-}
+diff --git a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/dec_internal_test.go b/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/dec_internal_test.go
+deleted file mode 100644
+index d4fbe3e..0000000
+--- a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/dec_internal_test.go
++++ /dev/null
+@@ -1,40 +0,0 @@
+-package inf
+-
+-import (
+-	"math/big"
+-	"testing"
+-)
+-
+-var decQuoRemZZZ = []struct {
+-	z, x, y  *Dec
+-	r        *big.Rat
+-	srA, srB int
+-}{
+-	// basic examples
+-	{NewDec(1, 0), NewDec(2, 0), NewDec(2, 0), big.NewRat(0, 1), 0, 1},
+-	{NewDec(15, 1), NewDec(3, 0), NewDec(2, 0), big.NewRat(0, 1), 0, 1},
+-	{NewDec(1, 1), NewDec(1, 0), NewDec(10, 0), big.NewRat(0, 1), 0, 1},
+-	{NewDec(0, 0), NewDec(2, 0), NewDec(3, 0), big.NewRat(2, 3), 1, 1},
+-	{NewDec(0, 0), NewDec(2, 0), NewDec(6, 0), big.NewRat(1, 3), 1, 1},
+-	{NewDec(1, 1), NewDec(2, 0), NewDec(12, 0), big.NewRat(2, 3), 1, 1},
+-
+-	// examples from the Go Language Specification
+-	{NewDec(1, 0), NewDec(5, 0), NewDec(3, 0), big.NewRat(2, 3), 1, 1},
+-	{NewDec(-1, 0), NewDec(-5, 0), NewDec(3, 0), big.NewRat(-2, 3), -1, 1},
+-	{NewDec(-1, 0), NewDec(5, 0), NewDec(-3, 0), big.NewRat(-2, 3), 1, -1},
+-	{NewDec(1, 0), NewDec(-5, 0), NewDec(-3, 0), big.NewRat(2, 3), -1, -1},
+-}
+-
+-func TestDecQuoRem(t *testing.T) {
+-	for i, a := range decQuoRemZZZ {
+-		z, rA, rB := new(Dec), new(big.Int), new(big.Int)
+-		s := scaleQuoExact{}.Scale(a.x, a.y)
+-		z.quoRem(a.x, a.y, s, true, rA, rB)
+-		if a.z.Cmp(z) != 0 || a.r.Cmp(new(big.Rat).SetFrac(rA, rB)) != 0 {
+-			t.Errorf("#%d QuoRemZZZ got %v, %v, %v; expected %v, %v", i, z, rA, rB, a.z, a.r)
+-		}
+-		if a.srA != rA.Sign() || a.srB != rB.Sign() {
+-			t.Errorf("#%d QuoRemZZZ wrong signs, got %v, %v; expected %v, %v", i, rA.Sign(), rB.Sign(), a.srA, a.srB)
+-		}
+-	}
+-}
+diff --git a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/dec_test.go b/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/dec_test.go
+deleted file mode 100644
+index 01ac771..0000000
+--- a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/dec_test.go
++++ /dev/null
+@@ -1,379 +0,0 @@
+-package inf_test
+-
+-import (
+-	"bytes"
+-	"encoding/gob"
+-	"fmt"
+-	"math/big"
+-	"strings"
+-	"testing"
+-
+-	"speter.net/go/exp/math/dec/inf"
+-)
+-
+-type decFunZZ func(z, x, y *inf.Dec) *inf.Dec
+-type decArgZZ struct {
+-	z, x, y *inf.Dec
+-}
+-
+-var decSumZZ = []decArgZZ{
+-	{inf.NewDec(0, 0), inf.NewDec(0, 0), inf.NewDec(0, 0)},
+-	{inf.NewDec(1, 0), inf.NewDec(1, 0), inf.NewDec(0, 0)},
+-	{inf.NewDec(1111111110, 0), inf.NewDec(123456789, 0), inf.NewDec(987654321, 0)},
+-	{inf.NewDec(-1, 0), inf.NewDec(-1, 0), inf.NewDec(0, 0)},
+-	{inf.NewDec(864197532, 0), inf.NewDec(-123456789, 0), inf.NewDec(987654321, 0)},
+-	{inf.NewDec(-1111111110, 0), inf.NewDec(-123456789, 0), inf.NewDec(-987654321, 0)},
+-	{inf.NewDec(12, 2), inf.NewDec(1, 1), inf.NewDec(2, 2)},
+-}
+-
+-var decProdZZ = []decArgZZ{
+-	{inf.NewDec(0, 0), inf.NewDec(0, 0), inf.NewDec(0, 0)},
+-	{inf.NewDec(0, 0), inf.NewDec(1, 0), inf.NewDec(0, 0)},
+-	{inf.NewDec(1, 0), inf.NewDec(1, 0), inf.NewDec(1, 0)},
+-	{inf.NewDec(-991*991, 0), inf.NewDec(991, 0), inf.NewDec(-991, 0)},
+-	{inf.NewDec(2, 3), inf.NewDec(1, 1), inf.NewDec(2, 2)},
+-	{inf.NewDec(2, -3), inf.NewDec(1, -1), inf.NewDec(2, -2)},
+-	{inf.NewDec(2, 3), inf.NewDec(1, 1), inf.NewDec(2, 2)},
+-}
+-
+-func TestDecSignZ(t *testing.T) {
+-	var zero inf.Dec
+-	for _, a := range decSumZZ {
+-		s := a.z.Sign()
+-		e := a.z.Cmp(&zero)
+-		if s != e {
+-			t.Errorf("got %d; want %d for z = %v", s, e, a.z)
+-		}
+-	}
+-}
+-
+-func TestDecAbsZ(t *testing.T) {
+-	var zero inf.Dec
+-	for _, a := range decSumZZ {
+-		var z inf.Dec
+-		z.Abs(a.z)
+-		var e inf.Dec
+-		e.Set(a.z)
+-		if e.Cmp(&zero) < 0 {
+-			e.Sub(&zero, &e)
+-		}
+-		if z.Cmp(&e) != 0 {
+-			t.Errorf("got z = %v; want %v", z, e)
+-		}
+-	}
+-}
+-
+-func testDecFunZZ(t *testing.T, msg string, f decFunZZ, a decArgZZ) {
+-	var z inf.Dec
+-	f(&z, a.x, a.y)
+-	if (&z).Cmp(a.z) != 0 {
+-		t.Errorf("%s%+v\n\tgot z = %v; want %v", msg, a, &z, a.z)
+-	}
+-}
+-
+-func TestDecSumZZ(t *testing.T) {
+-	AddZZ := func(z, x, y *inf.Dec) *inf.Dec { return z.Add(x, y) }
+-	SubZZ := func(z, x, y *inf.Dec) *inf.Dec { return z.Sub(x, y) }
+-	for _, a := range decSumZZ {
+-		arg := a
+-		testDecFunZZ(t, "AddZZ", AddZZ, arg)
+-
+-		arg = decArgZZ{a.z, a.y, a.x}
+-		testDecFunZZ(t, "AddZZ symmetric", AddZZ, arg)
+-
+-		arg = decArgZZ{a.x, a.z, a.y}
+-		testDecFunZZ(t, "SubZZ", SubZZ, arg)
+-
+-		arg = decArgZZ{a.y, a.z, a.x}
+-		testDecFunZZ(t, "SubZZ symmetric", SubZZ, arg)
+-	}
+-}
+-
+-func TestDecProdZZ(t *testing.T) {
+-	MulZZ := func(z, x, y *inf.Dec) *inf.Dec { return z.Mul(x, y) }
+-	for _, a := range decProdZZ {
+-		arg := a
+-		testDecFunZZ(t, "MulZZ", MulZZ, arg)
+-
+-		arg = decArgZZ{a.z, a.y, a.x}
+-		testDecFunZZ(t, "MulZZ symmetric", MulZZ, arg)
+-	}
+-}
+-
+-var decUnscaledTests = []struct {
+-	d  *inf.Dec
+-	u  int64 // ignored when ok == false
+-	ok bool
+-}{
+-	{new(inf.Dec), 0, true},
+-	{inf.NewDec(-1<<63, 0), -1 << 63, true},
+-	{inf.NewDec(-(-1<<63 + 1), 0), -(-1<<63 + 1), true},
+-	{new(inf.Dec).Neg(inf.NewDec(-1<<63, 0)), 0, false},
+-	{new(inf.Dec).Sub(inf.NewDec(-1<<63, 0), inf.NewDec(1, 0)), 0, false},
+-	{inf.NewDecBig(new(big.Int).Lsh(big.NewInt(1), 64), 0), 0, false},
+-}
+-
+-func TestDecUnscaled(t *testing.T) {
+-	for i, tt := range decUnscaledTests {
+-		u, ok := tt.d.Unscaled()
+-		if ok != tt.ok {
+-			t.Errorf("#%d Unscaled: got %v, expected %v", i, ok, tt.ok)
+-		} else if ok && u != tt.u {
+-			t.Errorf("#%d Unscaled: got %v, expected %v", i, u, tt.u)
+-		}
+-	}
+-}
+-
+-var decRoundTests = [...]struct {
+-	in  *inf.Dec
+-	s   inf.Scale
+-	r   inf.Rounder
+-	exp *inf.Dec
+-}{
+-	{inf.NewDec(123424999999999993, 15), 2, inf.RoundHalfUp, inf.NewDec(12342, 2)},
+-	{inf.NewDec(123425000000000001, 15), 2, inf.RoundHalfUp, inf.NewDec(12343, 2)},
+-	{inf.NewDec(123424999999999993, 15), 15, inf.RoundHalfUp, inf.NewDec(123424999999999993, 15)},
+-	{inf.NewDec(123424999999999993, 15), 16, inf.RoundHalfUp, inf.NewDec(1234249999999999930, 16)},
+-	{inf.NewDecBig(new(big.Int).Lsh(big.NewInt(1), 64), 0), -1, inf.RoundHalfUp, inf.NewDec(1844674407370955162, -1)},
+-	{inf.NewDecBig(new(big.Int).Lsh(big.NewInt(1), 64), 0), -2, inf.RoundHalfUp, inf.NewDec(184467440737095516, -2)},
+-	{inf.NewDecBig(new(big.Int).Lsh(big.NewInt(1), 64), 0), -3, inf.RoundHalfUp, inf.NewDec(18446744073709552, -3)},
+-	{inf.NewDecBig(new(big.Int).Lsh(big.NewInt(1), 64), 0), -4, inf.RoundHalfUp, inf.NewDec(1844674407370955, -4)},
+-	{inf.NewDecBig(new(big.Int).Lsh(big.NewInt(1), 64), 0), -5, inf.RoundHalfUp, inf.NewDec(184467440737096, -5)},
+-	{inf.NewDecBig(new(big.Int).Lsh(big.NewInt(1), 64), 0), -6, inf.RoundHalfUp, inf.NewDec(18446744073710, -6)},
+-}
+-
+-func TestDecRound(t *testing.T) {
+-	for i, tt := range decRoundTests {
+-		z := new(inf.Dec).Round(tt.in, tt.s, tt.r)
+-		if tt.exp.Cmp(z) != 0 {
+-			t.Errorf("#%d Round got %v; expected %v", i, z, tt.exp)
+-		}
+-	}
+-}
+-
+-var decStringTests = []struct {
+-	in     string
+-	out    string
+-	val    int64
+-	scale  inf.Scale // skip SetString if negative
+-	ok     bool
+-	scanOk bool
+-}{
+-	{in: "", ok: false, scanOk: false},
+-	{in: "a", ok: false, scanOk: false},
+-	{in: "z", ok: false, scanOk: false},
+-	{in: "+", ok: false, scanOk: false},
+-	{in: "-", ok: false, scanOk: false},
+-	{in: "g", ok: false, scanOk: false},
+-	{in: ".", ok: false, scanOk: false},
+-	{in: ".-0", ok: false, scanOk: false},
+-	{in: ".+0", ok: false, scanOk: false},
+-	// Scannable but not SetStringable
+-	{"0b", "ignored", 0, 0, false, true},
+-	{"0x", "ignored", 0, 0, false, true},
+-	{"0xg", "ignored", 0, 0, false, true},
+-	{"0.0g", "ignored", 0, 1, false, true},
+-	// examples from godoc for Dec
+-	{"0", "0", 0, 0, true, true},
+-	{"0.00", "0.00", 0, 2, true, true},
+-	{"ignored", "0", 0, -2, true, false},
+-	{"1", "1", 1, 0, true, true},
+-	{"1.00", "1.00", 100, 2, true, true},
+-	{"10", "10", 10, 0, true, true},
+-	{"ignored", "10", 1, -1, true, false},
+-	// other tests
+-	{"+0", "0", 0, 0, true, true},
+-	{"-0", "0", 0, 0, true, true},
+-	{"0.0", "0.0", 0, 1, true, true},
+-	{"0.1", "0.1", 1, 1, true, true},
+-	{"0.", "0", 0, 0, true, true},
+-	{"-10", "-10", -1, -1, true, true},
+-	{"-1", "-1", -1, 0, true, true},
+-	{"-0.1", "-0.1", -1, 1, true, true},
+-	{"-0.01", "-0.01", -1, 2, true, true},
+-	{"+0.", "0", 0, 0, true, true},
+-	{"-0.", "0", 0, 0, true, true},
+-	{".0", "0.0", 0, 1, true, true},
+-	{"+.0", "0.0", 0, 1, true, true},
+-	{"-.0", "0.0", 0, 1, true, true},
+-	{"0.0000000000", "0.0000000000", 0, 10, true, true},
+-	{"0.0000000001", "0.0000000001", 1, 10, true, true},
+-	{"-0.0000000000", "0.0000000000", 0, 10, true, true},
+-	{"-0.0000000001", "-0.0000000001", -1, 10, true, true},
+-	{"-10", "-10", -10, 0, true, true},
+-	{"+10", "10", 10, 0, true, true},
+-	{"00", "0", 0, 0, true, true},
+-	{"023", "23", 23, 0, true, true},      // decimal, not octal
+-	{"-02.3", "-2.3", -23, 1, true, true}, // decimal, not octal
+-}
+-
+-func TestDecGetString(t *testing.T) {
+-	z := new(inf.Dec)
+-	for i, test := range decStringTests {
+-		if !test.ok {
+-			continue
+-		}
+-		z.SetUnscaled(test.val)
+-		z.SetScale(test.scale)
+-
+-		s := z.String()
+-		if s != test.out {
+-			t.Errorf("#%da got %s; want %s", i, s, test.out)
+-		}
+-
+-		s = fmt.Sprintf("%d", z)
+-		if s != test.out {
+-			t.Errorf("#%db got %s; want %s", i, s, test.out)
+-		}
+-	}
+-}
+-
+-func TestDecSetString(t *testing.T) {
+-	tmp := new(inf.Dec)
+-	for i, test := range decStringTests {
+-		if test.scale < 0 {
+-			// SetString only supports scale >= 0
+-			continue
+-		}
+-		// initialize to a non-zero value so that issues with parsing
+-		// 0 are detected
+-		tmp.Set(inf.NewDec(1234567890, 123))
+-		n1, ok1 := new(inf.Dec).SetString(test.in)
+-		n2, ok2 := tmp.SetString(test.in)
+-		expected := inf.NewDec(test.val, test.scale)
+-		if ok1 != test.ok || ok2 != test.ok {
+-			t.Errorf("#%d (input '%s') ok incorrect (should be %t)", i, test.in, test.ok)
+-			continue
+-		}
+-		if !ok1 {
+-			if n1 != nil {
+-				t.Errorf("#%d (input '%s') n1 != nil", i, test.in)
+-			}
+-			continue
+-		}
+-		if !ok2 {
+-			if n2 != nil {
+-				t.Errorf("#%d (input '%s') n2 != nil", i, test.in)
+-			}
+-			continue
+-		}
+-
+-		if n1.Cmp(expected) != 0 {
+-			t.Errorf("#%d (input '%s') got: %s want: %d", i, test.in, n1, test.val)
+-		}
+-		if n2.Cmp(expected) != 0 {
+-			t.Errorf("#%d (input '%s') got: %s want: %d", i, test.in, n2, test.val)
+-		}
+-	}
+-}
+-
+-func TestDecScan(t *testing.T) {
+-	tmp := new(inf.Dec)
+-	for i, test := range decStringTests {
+-		if test.scale < 0 {
+-			// SetString only supports scale >= 0
+-			continue
+-		}
+-		// initialize to a non-zero value so that issues with parsing
+-		// 0 are detected
+-		tmp.Set(inf.NewDec(1234567890, 123))
+-		n1, n2 := new(inf.Dec), tmp
+-		nn1, err1 := fmt.Sscan(test.in, n1)
+-		nn2, err2 := fmt.Sscan(test.in, n2)
+-		if !test.scanOk {
+-			if err1 == nil || err2 == nil {
+-				t.Errorf("#%d (input '%s') ok incorrect, should be %t", i, test.in, test.scanOk)
+-			}
+-			continue
+-		}
+-		expected := inf.NewDec(test.val, test.scale)
+-		if nn1 != 1 || err1 != nil || nn2 != 1 || err2 != nil {
+-			t.Errorf("#%d (input '%s') error %d %v, %d %v", i, test.in, nn1, err1, nn2, err2)
+-			continue
+-		}
+-		if n1.Cmp(expected) != 0 {
+-			t.Errorf("#%d (input '%s') got: %s want: %d", i, test.in, n1, test.val)
+-		}
+-		if n2.Cmp(expected) != 0 {
+-			t.Errorf("#%d (input '%s') got: %s want: %d", i, test.in, n2, test.val)
+-		}
+-	}
+-}
+-
+-var decScanNextTests = []struct {
+-	in   string
+-	ok   bool
+-	next rune
+-}{
+-	{"", false, 0},
+-	{"a", false, 'a'},
+-	{"z", false, 'z'},
+-	{"+", false, 0},
+-	{"-", false, 0},
+-	{"g", false, 'g'},
+-	{".", false, 0},
+-	{".-0", false, '-'},
+-	{".+0", false, '+'},
+-	{"0b", true, 'b'},
+-	{"0x", true, 'x'},
+-	{"0xg", true, 'x'},
+-	{"0.0g", true, 'g'},
+-}
+-
+-func TestDecScanNext(t *testing.T) {
+-	for i, test := range decScanNextTests {
+-		rdr := strings.NewReader(test.in)
+-		n1 := new(inf.Dec)
+-		nn1, _ := fmt.Fscan(rdr, n1)
+-		if (test.ok && nn1 == 0) || (!test.ok && nn1 > 0) {
+-			t.Errorf("#%d (input '%s') ok incorrect should be %t", i, test.in, test.ok)
+-			continue
+-		}
+-		r := rune(0)
+-		nn2, err := fmt.Fscanf(rdr, "%c", &r)
+-		if test.next != r {
+-			t.Errorf("#%d (input '%s') next incorrect, got %c should be %c, %d, %v", i, test.in, r, test.next, nn2, err)
+-		}
+-	}
+-}
+-
+-var decGobEncodingTests = []string{
+-	"0",
+-	"1",
+-	"2",
+-	"10",
+-	"42",
+-	"1234567890",
+-	"298472983472983471903246121093472394872319615612417471234712061",
+-}
+-
+-func TestDecGobEncoding(t *testing.T) {
+-	var medium bytes.Buffer
+-	enc := gob.NewEncoder(&medium)
+-	dec := gob.NewDecoder(&medium)
+-	for i, test := range decGobEncodingTests {
+-		for j := 0; j < 2; j++ {
+-			for k := inf.Scale(-5); k <= 5; k++ {
+-				medium.Reset() // empty buffer for each test case (in case of failures)
+-				stest := test
+-				if j != 0 {
+-					// negative numbers
+-					stest = "-" + test
+-				}
+-				var tx inf.Dec
+-				tx.SetString(stest)
+-				tx.SetScale(k) // test with positive, negative, and zero scale
+-				if err := enc.Encode(&tx); err != nil {
+-					t.Errorf("#%d%c: encoding failed: %s", i, 'a'+j, err)
+-				}
+-				var rx inf.Dec
+-				if err := dec.Decode(&rx); err != nil {
+-					t.Errorf("#%d%c: decoding failed: %s", i, 'a'+j, err)
+-				}
+-				if rx.Cmp(&tx) != 0 {
+-					t.Errorf("#%d%c: transmission failed: got %s want %s", i, 'a'+j, &rx, &tx)
+-				}
+-			}
+-		}
+-	}
+-}
+diff --git a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/example_test.go b/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/example_test.go
+deleted file mode 100644
+index 52029e0..0000000
+--- a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/example_test.go
++++ /dev/null
+@@ -1,62 +0,0 @@
+-package inf_test
+-
+-import (
+-	"fmt"
+-	"log"
+-)
+-
+-import "speter.net/go/exp/math/dec/inf"
+-
+-func ExampleDec_SetString() {
+-	d := new(inf.Dec)
+-	d.SetString("012345.67890") // decimal; leading 0 ignored; trailing 0 kept
+-	fmt.Println(d)
+-	// Output: 12345.67890
+-}
+-
+-func ExampleDec_Scan() {
+-	// The Scan function is rarely used directly;
+-	// the fmt package recognizes it as an implementation of fmt.Scanner.
+-	d := new(inf.Dec)
+-	_, err := fmt.Sscan("184467440.73709551617", d)
+-	if err != nil {
+-		log.Println("error scanning value:", err)
+-	} else {
+-		fmt.Println(d)
+-	}
+-	// Output: 184467440.73709551617
+-}
+-
+-func ExampleDec_QuoRound_scale2RoundDown() {
+-	// 10 / 3 is an infinite decimal; it has no exact Dec representation
+-	x, y := inf.NewDec(10, 0), inf.NewDec(3, 0)
+-	// use 2 digits beyond the decimal point, round towards 0
+-	z := new(inf.Dec).QuoRound(x, y, 2, inf.RoundDown)
+-	fmt.Println(z)
+-	// Output: 3.33
+-}
+-
+-func ExampleDec_QuoRound_scale2RoundCeil() {
+-	// -42 / 400 is an finite decimal with 3 digits beyond the decimal point
+-	x, y := inf.NewDec(-42, 0), inf.NewDec(400, 0)
+-	// use 2 digits beyond decimal point, round towards positive infinity
+-	z := new(inf.Dec).QuoRound(x, y, 2, inf.RoundCeil)
+-	fmt.Println(z)
+-	// Output: -0.10
+-}
+-
+-func ExampleDec_QuoExact_ok() {
+-	// 1 / 25 is a finite decimal; it has exact Dec representation
+-	x, y := inf.NewDec(1, 0), inf.NewDec(25, 0)
+-	z := new(inf.Dec).QuoExact(x, y)
+-	fmt.Println(z)
+-	// Output: 0.04
+-}
+-
+-func ExampleDec_QuoExact_fail() {
+-	// 1 / 3 is an infinite decimal; it has no exact Dec representation
+-	x, y := inf.NewDec(1, 0), inf.NewDec(3, 0)
+-	z := new(inf.Dec).QuoExact(x, y)
+-	fmt.Println(z)
+-	// Output: <nil>
+-}
+diff --git a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/rounder.go b/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/rounder.go
+deleted file mode 100644
+index 3a97ef5..0000000
+--- a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/rounder.go
++++ /dev/null
+@@ -1,145 +0,0 @@
+-package inf
+-
+-import (
+-	"math/big"
+-)
+-
+-// Rounder represents a method for rounding the (possibly infinite decimal)
+-// result of a division to a finite Dec. It is used by Dec.Round() and
+-// Dec.Quo().
+-//
+-// See the Example for results of using each Rounder with some sample values.
+-//
+-type Rounder rounder
+-
+-// See http://speleotrove.com/decimal/damodel.html#refround for more detailed
+-// definitions of these rounding modes.
+-var (
+-	RoundDown     Rounder // towards 0
+-	RoundUp       Rounder // away from 0
+-	RoundFloor    Rounder // towards -infinity
+-	RoundCeil     Rounder // towards +infinity
+-	RoundHalfDown Rounder // to nearest; towards 0 if same distance
+-	RoundHalfUp   Rounder // to nearest; away from 0 if same distance
+-	RoundHalfEven Rounder // to nearest; even last digit if same distance
+-)
+-
+-// RoundExact is to be used in the case when rounding is not necessary.
+-// When used with Quo or Round, it returns the result verbatim when it can be
+-// expressed exactly with the given precision, and it returns nil otherwise.
+-// QuoExact is a shorthand for using Quo with RoundExact.
+-var RoundExact Rounder
+-
+-type rounder interface {
+-
+-	// When UseRemainder() returns true, the Round() method is passed the
+-	// remainder of the division, expressed as the numerator and denominator of
+-	// a rational.
+-	UseRemainder() bool
+-
+-	// Round sets the rounded value of a quotient to z, and returns z.
+-	// quo is rounded down (truncated towards zero) to the scale obtained from
+-	// the Scaler in Quo().
+-	//
+-	// When the remainder is not used, remNum and remDen are nil.
+-	// When used, the remainder is normalized between -1 and 1; that is:
+-	//
+-	//  -|remDen| < remNum < |remDen|
+-	//
+-	// remDen has the same sign as y, and remNum is zero or has the same sign
+-	// as x.
+-	Round(z, quo *Dec, remNum, remDen *big.Int) *Dec
+-}
+-
+-type rndr struct {
+-	useRem bool
+-	round  func(z, quo *Dec, remNum, remDen *big.Int) *Dec
+-}
+-
+-func (r rndr) UseRemainder() bool {
+-	return r.useRem
+-}
+-
+-func (r rndr) Round(z, quo *Dec, remNum, remDen *big.Int) *Dec {
+-	return r.round(z, quo, remNum, remDen)
+-}
+-
+-var intSign = []*big.Int{big.NewInt(-1), big.NewInt(0), big.NewInt(1)}
+-
+-func roundHalf(f func(c int, odd uint) (roundUp bool)) func(z, q *Dec, rA, rB *big.Int) *Dec {
+-	return func(z, q *Dec, rA, rB *big.Int) *Dec {
+-		z.Set(q)
+-		brA, brB := rA.BitLen(), rB.BitLen()
+-		if brA < brB-1 {
+-			// brA < brB-1 => |rA| < |rB/2|
+-			return z
+-		}
+-		roundUp := false
+-		srA, srB := rA.Sign(), rB.Sign()
+-		s := srA * srB
+-		if brA == brB-1 {
+-			rA2 := new(big.Int).Lsh(rA, 1)
+-			if s < 0 {
+-				rA2.Neg(rA2)
+-			}
+-			roundUp = f(rA2.Cmp(rB)*srB, z.UnscaledBig().Bit(0))
+-		} else {
+-			// brA > brB-1 => |rA| > |rB/2|
+-			roundUp = true
+-		}
+-		if roundUp {
+-			z.UnscaledBig().Add(z.UnscaledBig(), intSign[s+1])
+-		}
+-		return z
+-	}
+-}
+-
+-func init() {
+-	RoundExact = rndr{true,
+-		func(z, q *Dec, rA, rB *big.Int) *Dec {
+-			if rA.Sign() != 0 {
+-				return nil
+-			}
+-			return z.Set(q)
+-		}}
+-	RoundDown = rndr{false,
+-		func(z, q *Dec, rA, rB *big.Int) *Dec {
+-			return z.Set(q)
+-		}}
+-	RoundUp = rndr{true,
+-		func(z, q *Dec, rA, rB *big.Int) *Dec {
+-			z.Set(q)
+-			if rA.Sign() != 0 {
+-				z.UnscaledBig().Add(z.UnscaledBig(), intSign[rA.Sign()*rB.Sign()+1])
+-			}
+-			return z
+-		}}
+-	RoundFloor = rndr{true,
+-		func(z, q *Dec, rA, rB *big.Int) *Dec {
+-			z.Set(q)
+-			if rA.Sign()*rB.Sign() < 0 {
+-				z.UnscaledBig().Add(z.UnscaledBig(), intSign[0])
+-			}
+-			return z
+-		}}
+-	RoundCeil = rndr{true,
+-		func(z, q *Dec, rA, rB *big.Int) *Dec {
+-			z.Set(q)
+-			if rA.Sign()*rB.Sign() > 0 {
+-				z.UnscaledBig().Add(z.UnscaledBig(), intSign[2])
+-			}
+-			return z
+-		}}
+-	RoundHalfDown = rndr{true, roundHalf(
+-		func(c int, odd uint) bool {
+-			return c > 0
+-		})}
+-	RoundHalfUp = rndr{true, roundHalf(
+-		func(c int, odd uint) bool {
+-			return c >= 0
+-		})}
+-	RoundHalfEven = rndr{true, roundHalf(
+-		func(c int, odd uint) bool {
+-			return c > 0 || c == 0 && odd == 1
+-		})}
+-}
+diff --git a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/rounder_example_test.go b/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/rounder_example_test.go
+deleted file mode 100644
+index 5c5e4df..0000000
+--- a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/rounder_example_test.go
++++ /dev/null
+@@ -1,72 +0,0 @@
+-package inf_test
+-
+-import (
+-	"fmt"
+-	"os"
+-	"text/tabwriter"
+-
+-	"speter.net/go/exp/math/dec/inf"
+-)
+-
+-// This example displays the results of Dec.Round with each of the Rounders.
+-//
+-func ExampleRounder() {
+-	var vals = []struct {
+-		x string
+-		s inf.Scale
+-	}{
+-		{"-0.18", 1}, {"-0.15", 1}, {"-0.12", 1}, {"-0.10", 1},
+-		{"-0.08", 1}, {"-0.05", 1}, {"-0.02", 1}, {"0.00", 1},
+-		{"0.02", 1}, {"0.05", 1}, {"0.08", 1}, {"0.10", 1},
+-		{"0.12", 1}, {"0.15", 1}, {"0.18", 1},
+-	}
+-
+-	var rounders = []struct {
+-		name    string
+-		rounder inf.Rounder
+-	}{
+-		{"RoundDown", inf.RoundDown}, {"RoundUp", inf.RoundUp},
+-		{"RoundCeil", inf.RoundCeil}, {"RoundFloor", inf.RoundFloor},
+-		{"RoundHalfDown", inf.RoundHalfDown}, {"RoundHalfUp", inf.RoundHalfUp},
+-		{"RoundHalfEven", inf.RoundHalfEven}, {"RoundExact", inf.RoundExact},
+-	}
+-
+-	fmt.Println("The results of new(inf.Dec).Round(x, s, inf.RoundXXX):\n")
+-	w := tabwriter.NewWriter(os.Stdout, 0, 0, 1, ' ', tabwriter.AlignRight)
+-	fmt.Fprint(w, "x\ts\t|\t")
+-	for _, r := range rounders {
+-		fmt.Fprintf(w, "%s\t", r.name[5:])
+-	}
+-	fmt.Fprintln(w)
+-	for _, v := range vals {
+-		fmt.Fprintf(w, "%s\t%d\t|\t", v.x, v.s)
+-		for _, r := range rounders {
+-			x, _ := new(inf.Dec).SetString(v.x)
+-			z := new(inf.Dec).Round(x, v.s, r.rounder)
+-			fmt.Fprintf(w, "%d\t", z)
+-		}
+-		fmt.Fprintln(w)
+-	}
+-	w.Flush()
+-
+-	// Output:
+-	// The results of new(inf.Dec).Round(x, s, inf.RoundXXX):
+-	//
+-	//      x s | Down   Up Ceil Floor HalfDown HalfUp HalfEven Exact
+-	//  -0.18 1 | -0.1 -0.2 -0.1  -0.2     -0.2   -0.2     -0.2 <nil>
+-	//  -0.15 1 | -0.1 -0.2 -0.1  -0.2     -0.1   -0.2     -0.2 <nil>
+-	//  -0.12 1 | -0.1 -0.2 -0.1  -0.2     -0.1   -0.1     -0.1 <nil>
+-	//  -0.10 1 | -0.1 -0.1 -0.1  -0.1     -0.1   -0.1     -0.1  -0.1
+-	//  -0.08 1 |  0.0 -0.1  0.0  -0.1     -0.1   -0.1     -0.1 <nil>
+-	//  -0.05 1 |  0.0 -0.1  0.0  -0.1      0.0   -0.1      0.0 <nil>
+-	//  -0.02 1 |  0.0 -0.1  0.0  -0.1      0.0    0.0      0.0 <nil>
+-	//   0.00 1 |  0.0  0.0  0.0   0.0      0.0    0.0      0.0   0.0
+-	//   0.02 1 |  0.0  0.1  0.1   0.0      0.0    0.0      0.0 <nil>
+-	//   0.05 1 |  0.0  0.1  0.1   0.0      0.0    0.1      0.0 <nil>
+-	//   0.08 1 |  0.0  0.1  0.1   0.0      0.1    0.1      0.1 <nil>
+-	//   0.10 1 |  0.1  0.1  0.1   0.1      0.1    0.1      0.1   0.1
+-	//   0.12 1 |  0.1  0.2  0.2   0.1      0.1    0.1      0.1 <nil>
+-	//   0.15 1 |  0.1  0.2  0.2   0.1      0.1    0.2      0.2 <nil>
+-	//   0.18 1 |  0.1  0.2  0.2   0.1      0.2    0.2      0.2 <nil>
+-
+-}
+diff --git a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/rounder_test.go b/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/rounder_test.go
+deleted file mode 100644
+index 757ab97..0000000
+--- a/Godeps/_workspace/src/speter.net/go/exp/math/dec/inf/rounder_test.go
++++ /dev/null
+@@ -1,109 +0,0 @@
+-package inf_test
+-
+-import (
+-	"math/big"
+-	"testing"
+-
+-	"speter.net/go/exp/math/dec/inf"
+-)
+-
+-var decRounderInputs = [...]struct {
+-	quo    *inf.Dec
+-	rA, rB *big.Int
+-}{
+-	// examples from go language spec
+-	{inf.NewDec(1, 0), big.NewInt(2), big.NewInt(3)},   //  5 /  3
+-	{inf.NewDec(-1, 0), big.NewInt(-2), big.NewInt(3)}, // -5 /  3
+-	{inf.NewDec(-1, 0), big.NewInt(2), big.NewInt(-3)}, //  5 / -3
+-	{inf.NewDec(1, 0), big.NewInt(-2), big.NewInt(-3)}, // -5 / -3
+-	// examples from godoc
+-	{inf.NewDec(-1, 1), big.NewInt(-8), big.NewInt(10)},
+-	{inf.NewDec(-1, 1), big.NewInt(-5), big.NewInt(10)},
+-	{inf.NewDec(-1, 1), big.NewInt(-2), big.NewInt(10)},
+-	{inf.NewDec(0, 1), big.NewInt(-8), big.NewInt(10)},
+-	{inf.NewDec(0, 1), big.NewInt(-5), big.NewInt(10)},
+-	{inf.NewDec(0, 1), big.NewInt(-2), big.NewInt(10)},
+-	{inf.NewDec(0, 1), big.NewInt(0), big.NewInt(1)},
+-	{inf.NewDec(0, 1), big.NewInt(2), big.NewInt(10)},
+-	{inf.NewDec(0, 1), big.NewInt(5), big.NewInt(10)},
+-	{inf.NewDec(0, 1), big.NewInt(8), big.NewInt(10)},
+-	{inf.NewDec(1, 1), big.NewInt(2), big.NewInt(10)},
+-	{inf.NewDec(1, 1), big.NewInt(5), big.NewInt(10)},
+-	{inf.NewDec(1, 1), big.NewInt(8), big.NewInt(10)},
+-}
+-
+-var decRounderResults = [...]struct {
+-	rounder inf.Rounder
+-	results [len(decRounderInputs)]*inf.Dec
+-}{
+-	{inf.RoundExact, [...]*inf.Dec{nil, nil, nil, nil,
+-		nil, nil, nil, nil, nil, nil,
+-		inf.NewDec(0, 1), nil, nil, nil, nil, nil, nil}},
+-	{inf.RoundDown, [...]*inf.Dec{
+-		inf.NewDec(1, 0), inf.NewDec(-1, 0), inf.NewDec(-1, 0), inf.NewDec(1, 0),
+-		inf.NewDec(-1, 1), inf.NewDec(-1, 1), inf.NewDec(-1, 1),
+-		inf.NewDec(0, 1), inf.NewDec(0, 1), inf.NewDec(0, 1),
+-		inf.NewDec(0, 1),
+-		inf.NewDec(0, 1), inf.NewDec(0, 1), inf.NewDec(0, 1),
+-		inf.NewDec(1, 1), inf.NewDec(1, 1), inf.NewDec(1, 1)}},
+-	{inf.RoundUp, [...]*inf.Dec{
+-		inf.NewDec(2, 0), inf.NewDec(-2, 0), inf.NewDec(-2, 0), inf.NewDec(2, 0),
+-		inf.NewDec(-2, 1), inf.NewDec(-2, 1), inf.NewDec(-2, 1),
+-		inf.NewDec(-1, 1), inf.NewDec(-1, 1), inf.NewDec(-1, 1),
+-		inf.NewDec(0, 1),
+-		inf.NewDec(1, 1), inf.NewDec(1, 1), inf.NewDec(1, 1),
+-		inf.NewDec(2, 1), inf.NewDec(2, 1), inf.NewDec(2, 1)}},
+-	{inf.RoundHalfDown, [...]*inf.Dec{
+-		inf.NewDec(2, 0), inf.NewDec(-2, 0), inf.NewDec(-2, 0), inf.NewDec(2, 0),
+-		inf.NewDec(-2, 1), inf.NewDec(-1, 1), inf.NewDec(-1, 1),
+-		inf.NewDec(-1, 1), inf.NewDec(0, 1), inf.NewDec(0, 1),
+-		inf.NewDec(0, 1),
+-		inf.NewDec(0, 1), inf.NewDec(0, 1), inf.NewDec(1, 1),
+-		inf.NewDec(1, 1), inf.NewDec(1, 1), inf.NewDec(2, 1)}},
+-	{inf.RoundHalfUp, [...]*inf.Dec{
+-		inf.NewDec(2, 0), inf.NewDec(-2, 0), inf.NewDec(-2, 0), inf.NewDec(2, 0),
+-		inf.NewDec(-2, 1), inf.NewDec(-2, 1), inf.NewDec(-1, 1),
+-		inf.NewDec(-1, 1), inf.NewDec(-1, 1), inf.NewDec(0, 1),
+-		inf.NewDec(0, 1),
+-		inf.NewDec(0, 1), inf.NewDec(1, 1), inf.NewDec(1, 1),
+-		inf.NewDec(1, 1), inf.NewDec(2, 1), inf.NewDec(2, 1)}},
+-	{inf.RoundHalfEven, [...]*inf.Dec{
+-		inf.NewDec(2, 0), inf.NewDec(-2, 0), inf.NewDec(-2, 0), inf.NewDec(2, 0),
+-		inf.NewDec(-2, 1), inf.NewDec(-2, 1), inf.NewDec(-1, 1),
+-		inf.NewDec(-1, 1), inf.NewDec(0, 1), inf.NewDec(0, 1),
+-		inf.NewDec(0, 1),
+-		inf.NewDec(0, 1), inf.NewDec(0, 1), inf.NewDec(1, 1),
+-		inf.NewDec(1, 1), inf.NewDec(2, 1), inf.NewDec(2, 1)}},
+-	{inf.RoundFloor, [...]*inf.Dec{
+-		inf.NewDec(1, 0), inf.NewDec(-2, 0), inf.NewDec(-2, 0), inf.NewDec(1, 0),
+-		inf.NewDec(-2, 1), inf.NewDec(-2, 1), inf.NewDec(-2, 1),
+-		inf.NewDec(-1, 1), inf.NewDec(-1, 1), inf.NewDec(-1, 1),
+-		inf.NewDec(0, 1),
+-		inf.NewDec(0, 1), inf.NewDec(0, 1), inf.NewDec(0, 1),
+-		inf.NewDec(1, 1), inf.NewDec(1, 1), inf.NewDec(1, 1)}},
+-	{inf.RoundCeil, [...]*inf.Dec{
+-		inf.NewDec(2, 0), inf.NewDec(-1, 0), inf.NewDec(-1, 0), inf.NewDec(2, 0),
+-		inf.NewDec(-1, 1), inf.NewDec(-1, 1), inf.NewDec(-1, 1),
+-		inf.NewDec(0, 1), inf.NewDec(0, 1), inf.NewDec(0, 1),
+-		inf.NewDec(0, 1),
+-		inf.NewDec(1, 1), inf.NewDec(1, 1), inf.NewDec(1, 1),
+-		inf.NewDec(2, 1), inf.NewDec(2, 1), inf.NewDec(2, 1)}},
+-}
+-
+-func TestDecRounders(t *testing.T) {
+-	for i, a := range decRounderResults {
+-		for j, input := range decRounderInputs {
+-			q := new(inf.Dec).Set(input.quo)
+-			rA, rB := new(big.Int).Set(input.rA), new(big.Int).Set(input.rB)
+-			res := a.rounder.Round(new(inf.Dec), q, rA, rB)
+-			if a.results[j] == nil && res == nil {
+-				continue
+-			}
+-			if (a.results[j] == nil && res != nil) ||
+-				(a.results[j] != nil && res == nil) ||
+-				a.results[j].Cmp(res) != 0 {
+-				t.Errorf("#%d,%d Rounder got %v; expected %v", i, j, res, a.results[j])
+-			}
+-		}
+-	}
+-}
 -- 
-1.9.3
+2.1.0
 
diff --git a/kubernetes.spec b/kubernetes.spec
index d3fe276..985a0b9 100644
--- a/kubernetes.spec
+++ b/kubernetes.spec
@@ -1,7 +1,7 @@
 #debuginfo not supported with Go
 %global debug_package	%{nil}
 %global import_path	github.com/GoogleCloudPlatform/kubernetes
-%global commit		52e165a4fd720d1703ebc31bd6660e01334227b8
+%global commit		68298f08a4980f95dfbf7b9f58bfec1808fb2670
 %global shortcommit	%(c=%{commit}; echo ${c:0:7})
 
 #I really need this, otherwise "version_ldflags=$(kube::version_ldflags)"
@@ -10,8 +10,8 @@
 %global _checkshell	/bin/bash
 
 Name:		kubernetes
-Version:	0.7.0
-Release:	18.0.git%{shortcommit}%{?dist}
+Version:	0.8.0
+Release:	125.0.git%{shortcommit}%{?dist}
 Summary:	Container cluster management
 License:	ASL 2.0
 URL:		https://github.com/GoogleCloudPlatform/kubernetes
@@ -82,7 +82,7 @@ BuildRequires:	golang(gopkg.in/v2/yaml)
 %build
 export KUBE_GIT_TREE_STATE="clean"
 export KUBE_GIT_COMMIT=%{commit}
-export KUBE_GIT_VERSION=v0.7.0-18-g52e165a4fd720d
+export KUBE_GIT_VERSION=v0.8.0-125-g68298f08a4980f
 
 %if 0%{?fedora}
 export KUBE_GIT_TREE_STATE="dirty"
@@ -181,6 +181,9 @@ getent passwd kube >/dev/null || useradd -r -g kube -d / -s /sbin/nologin \
 %systemd_postun
 
 %changelog
+* Fri Jan 09 2015 Eric Paris <eparis at redhat.com> - 0.8.0-125.0.git68298f0
+- Bump to upstream 68298f08a4980f95dfbf7b9f58bfec1808fb2670
+
 * Tue Dec 16 2014 Eric Paris <eparis at redhat.com> - 0.7.0-18.0.git52e165a
 - Bump to upstream 52e165a4fd720d1703ebc31bd6660e01334227b8
 
diff --git a/sources b/sources
index 7ff3bfd..e8ba4de 100644
--- a/sources
+++ b/sources
@@ -1 +1 @@
-c52274fb797691d1c9532e9ac5f2658c  kubernetes-52e165a.tar.gz
+6ff850813607d4d7cd769e22905597fd  kubernetes-68298f0.tar.gz
-- 
cgit v0.10.2


	http://pkgs.fedoraproject.org/cgit/kubernetes.git/commit/?h=f21&id=f0566ef5c85dc66755370041053f4d203a01074b


More information about the scm-commits mailing list