Repository: honeycombio/terraform-provider-honeycombio (language: python)

Issue:
feat: environment management support
Adds the ability to manage a team's Environments ✨ by introducing a pair of data sources and a shiny new resource.

---
- To see the specific tasks where the Asana app for GitHub is being used, see below:
  - https://app.asana.com/0/0/1207759682365320
feat: key management support
Adds V2 API client support and a new V2 API resource `honeycombio_api_key` to the provider. Includes docs updates for the new provider-level config. options as well as the new resource.

Left a few follow-up "TODOs" (and removed use of `context.TODO()` so I could find the actual TODOs more easily 🙃).

This is larger than I'd initially suspected: allowing the provider to work "v1+v2", "v1 only", or "v2 only" required a fair bit of initialization plumbing updates but I have tried to cover that off with test cases.

- Closes #5 

---
- To see the specific tasks where the Asana app for GitHub is being used, see below:
  - https://app.asana.com/0/0/1207448260357674


Discussion / hints:
## [Codecov](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/501?dropdown=coverage&src=pr&el=h1&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) Report
Attention: Patch coverage is `75.81395%` with `104 lines` in your changes missing coverage. Please review.
> Project coverage is 80.10%. Comparing base [(`3ecd18f`)](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/commit/3ecd18f37ae0e8cab9165d912ac740af8bc72db9?dropdown=coverage&el=desc&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) to head [(`72fe570`)](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/commit/72fe5709e87f98d6f3b2edeab925d954c431145f?dropdown=coverage&el=desc&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio).

| [Files](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/501?dropdown=coverage&src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) | Patch % | Lines |
|---|---|---|
| [internal/provider/environment\_resource.go](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/501?src=pr&el=tree&filepath=internal%2Fprovider%2Fenvironment_resource.go&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio#diff-aW50ZXJuYWwvcHJvdmlkZXIvZW52aXJvbm1lbnRfcmVzb3VyY2UuZ28=) | 72.19% | [38 Missing and 14 partials :warning: ](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/501?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) |
| [client/v2/environments.go](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/501?src=pr&el=tree&filepath=client%2Fv2%2Fenvironments.go&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio#diff-Y2xpZW50L3YyL2Vudmlyb25tZW50cy5nbw==) | 57.74% | [21 Missing and 9 partials :warning: ](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/501?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) |
| [internal/provider/environments\_data\_source.go](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/501?src=pr&el=tree&filepath=internal%2Fprovider%2Fenvironments_data_source.go&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio#diff-aW50ZXJuYWwvcHJvdmlkZXIvZW52aXJvbm1lbnRzX2RhdGFfc291cmNlLmdv) | 80.00% | [7 Missing and 5 partials :warning: ](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/501?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) |
| [internal/provider/environment\_data\_source.go](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/501?src=pr&el=tree&filepath=internal%2Fprovider%2Fenvironment_data_source.go&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio#diff-aW50ZXJuYWwvcHJvdmlkZXIvZW52aXJvbm1lbnRfZGF0YV9zb3VyY2UuZ28=) | 89.85% | [4 Missing and 3 partials :warning: ](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/501?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) |
| [internal/provider/provider.go](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/501?src=pr&el=tree&filepath=internal%2Fprovider%2Fprovider.go&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio#diff-aW50ZXJuYWwvcHJvdmlkZXIvcHJvdmlkZXIuZ28=) | 60.00% | [0 Missing and 2 partials :warning: ](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/501?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) |
| [internal/provider/api\_key\_resource.go](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/501?src=pr&el=tree&filepath=internal%2Fprovider%2Fapi_key_resource.go&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio#diff-aW50ZXJuYWwvcHJvdmlkZXIvYXBpX2tleV9yZXNvdXJjZS5nbw==) | 0.00% | [1 Missing :warning: ](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/501?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) |

<details><summary>Additional details and impacted files</summary>


```diff
@@            Coverage Diff             @@
##             main     #501      +/-   ##
==========================================
- Coverage   80.36%   80.10%   -0.26%     
==========================================
  Files          67       72       +5     
  Lines        5174     5554     +380     
==========================================
+ Hits         4158     4449     +291     
- Misses        753      812      +59     
- Partials      263      293      +30     
```

</details>

[:umbrella: View full report in Codecov by Sentry](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/501?dropdown=coverage&src=pr&el=continue&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio).   
:loudspeaker: Have feedback on the report? [Share it here](https://about.codecov.io/codecov-pr-comment-feedback/?utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio).

## [Codecov](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?dropdown=coverage&src=pr&el=h1&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) Report
Attention: Patch coverage is `66.10577%` with `282 lines` in your changes missing coverage. Please review.
> Project coverage is 80.36%. Comparing base [(`58def89`)](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/commit/58def89bfc47d398eaf90cd27e2db1016cc4d0e2?dropdown=coverage&el=desc&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) to head [(`22c2e50`)](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/commit/22c2e5044c56c8b9e49ef3c954f45c5612caaae1?dropdown=coverage&el=desc&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio).

| [Files](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?dropdown=coverage&src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) | Patch % | Lines |
|---|---|---|
| [internal/provider/api\_key\_resource.go](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&filepath=internal%2Fprovider%2Fapi_key_resource.go&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio#diff-aW50ZXJuYWwvcHJvdmlkZXIvYXBpX2tleV9yZXNvdXJjZS5nbw==) | 77.61% | [33 Missing and 14 partials :warning: ](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) |
| [internal/provider/provider.go](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&filepath=internal%2Fprovider%2Fprovider.go&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio#diff-aW50ZXJuYWwvcHJvdmlkZXIvcHJvdmlkZXIuZ28=) | 70.43% | [27 Missing and 7 partials :warning: ](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) |
| [client/v2/client.go](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&filepath=client%2Fv2%2Fclient.go&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio#diff-Y2xpZW50L3YyL2NsaWVudC5nbw==) | 76.04% | [14 Missing and 9 partials :warning: ](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) |
| [client/v2/api\_keys.go](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&filepath=client%2Fv2%2Fapi_keys.go&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio#diff-Y2xpZW50L3YyL2FwaV9rZXlzLmdv) | 66.10% | [10 Missing and 10 partials :warning: ](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) |
| [client/v2/pagination.go](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&filepath=client%2Fv2%2Fpagination.go&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio#diff-Y2xpZW50L3YyL3BhZ2luYXRpb24uZ28=) | 66.10% | [10 Missing and 10 partials :warning: ](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) |
| [client/errors.go](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&filepath=client%2Ferrors.go&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio#diff-Y2xpZW50L2Vycm9ycy5nbw==) | 69.23% | [8 Missing and 4 partials :warning: ](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) |
| [honeycombio/resource\_derived\_column.go](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&filepath=honeycombio%2Fresource_derived_column.go&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio#diff-aG9uZXljb21iaW8vcmVzb3VyY2VfZGVyaXZlZF9jb2x1bW4uZ28=) | 33.33% | [7 Missing and 3 partials :warning: ](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) |
| [honeycombio/resource\_column.go](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&filepath=honeycombio%2Fresource_column.go&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio#diff-aG9uZXljb21iaW8vcmVzb3VyY2VfY29sdW1uLmdv) | 30.76% | [6 Missing and 3 partials :warning: ](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) |
| [honeycombio/resource\_marker\_setting.go](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&filepath=honeycombio%2Fresource_marker_setting.go&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio#diff-aG9uZXljb21iaW8vcmVzb3VyY2VfbWFya2VyX3NldHRpbmcuZ28=) | 30.76% | [6 Missing and 3 partials :warning: ](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) |
| [honeycombio/resource\_slo.go](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&filepath=honeycombio%2Fresource_slo.go&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio#diff-aG9uZXljb21iaW8vcmVzb3VyY2Vfc2xvLmdv) | 30.76% | [6 Missing and 3 partials :warning: ](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) |
| ... and [23 more](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?src=pr&el=tree-more&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio) | |

<details><summary>Additional details and impacted files</summary>


```diff
@@            Coverage Diff             @@
##             main     #496      +/-   ##
==========================================
- Coverage   82.62%   80.36%   -2.27%     
==========================================
  Files          63       67       +4     
  Lines        4478     5174     +696     
==========================================
+ Hits         3700     4158     +458     
- Misses        607      753     +146     
- Partials      171      263      +92     
```

</details>

[:umbrella: View full report in Codecov by Sentry](https://app.codecov.io/gh/honeycombio/terraform-provider-honeycombio/pull/496?dropdown=coverage&src=pr&el=continue&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio).   
:loudspeaker: Have feedback on the report? [Share it here](https://about.codecov.io/codecov-pr-comment-feedback/?utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=honeycombio).


Fix patch:
diff --git a/.github/workflows/ci.yaml b/.github/workflows/ci.yaml
index 9df1cb3e..83687b39 100644
--- a/.github/workflows/ci.yaml
+++ b/.github/workflows/ci.yaml
@@ -64,7 +64,6 @@ jobs:
           HONEYCOMB_KEY_ID: ${{ secrets.HONEYCOMB_KEY_ID }}
           HONEYCOMB_KEY_SECRET: ${{ secrets.HONEYCOMB_KEY_SECRET }}
           HONEYCOMB_DATASET: testacc
-          HONEYCOMB_ENVIRONMENT_ID: hcaen_01j1d7t02zf7wgw7q89z3t60vf # TODO: remove and do a lookup or create in tests
         run: go test -v -coverprofile=client-coverage.txt -covermode=atomic ./client/...
 
       - uses: hashicorp/setup-terraform@v3
@@ -79,7 +78,6 @@ jobs:
           HONEYCOMB_KEY_ID: ${{ secrets.HONEYCOMB_KEY_ID }}
           HONEYCOMB_KEY_SECRET: ${{ secrets.HONEYCOMB_KEY_SECRET }}
           HONEYCOMB_DATASET: testacc
-          HONEYCOMB_ENVIRONMENT_ID: hcaen_01j1d7t02zf7wgw7q89z3t60vf # TODO: remove and do a lookup or create in tests
           TF_ACC: 1
           TF_ACC_TERRAFORM_VERSION: ${{ env.TERRAFORM_VERSION }}
         run: go test -v -coverprofile=tf-coverage.txt -covermode=atomic ./internal/... ./honeycombio/...
@@ -121,7 +119,6 @@ jobs:
           HONEYCOMB_KEY_ID: ${{ secrets.HONEYCOMB_KEY_ID_EU }}
           HONEYCOMB_KEY_SECRET: ${{ secrets.HONEYCOMB_KEY_SECRET_EU }}
           HONEYCOMB_DATASET: testacc
-          HONEYCOMB_ENVIRONMENT_ID: hcben_01hvp28qbgzaeebbz29qvbb7gt # TODO: remove and do a lookup or create in tests
         run: go test -v -coverprofile=client-coverage.txt -covermode=atomic ./client/...
 
       - uses: hashicorp/setup-terraform@v3
@@ -137,7 +134,6 @@ jobs:
           HONEYCOMB_KEY_ID: ${{ secrets.HONEYCOMB_KEY_ID_EU }}
           HONEYCOMB_KEY_SECRET: ${{ secrets.HONEYCOMB_KEY_SECRET_EU }}
           HONEYCOMB_DATASET: testacc
-          HONEYCOMB_ENVIRONMENT_ID: hcben_01hvp28qbgzaeebbz29qvbb7gt # TODO: remove and do a lookup or create in tests
           TF_ACC: 1
           TF_ACC_TERRAFORM_VERSION: ${{ env.TERRAFORM_VERSION }}
         run: go test -v -coverprofile=tf-coverage.txt -covermode=atomic ./internal/... ./honeycombio/...


Test patch:
diff --git a/client/v2/api_keys_test.go b/client/v2/api_keys_test.go
index e949d066..8df805e6 100644
--- a/client/v2/api_keys_test.go
+++ b/client/v2/api_keys_test.go
@@ -4,7 +4,6 @@ import (
 	"context"
 	"fmt"
 	"math"
-	"os"
 	"testing"
 	"time"
 
@@ -18,15 +17,14 @@ import (
 func TestClient_APIKeys(t *testing.T) {
 	ctx := context.Background()
 	c := newTestClient(t)
-	// TODO: use the environments API
-	testEnvironmentID := os.Getenv("HONEYCOMB_ENVIRONMENT_ID")
+	env := newTestEnvironment(ctx, t, c)
 
 	// create a new key
 	k, err := c.APIKeys.Create(ctx, &APIKey{
 		Name:    helper.ToPtr("test key"),
 		KeyType: "ingest",
 		Environment: &Environment{
-			ID: testEnvironmentID,
+			ID: env.ID,
 		},
 		Permissions: &APIKeyPermissions{
 			CreateDatasets: true,
@@ -77,8 +75,7 @@ func TestClient_APIKeys(t *testing.T) {
 func TestClient_APIKeys_Pagination(t *testing.T) {
 	ctx := context.Background()
 	c := newTestClient(t)
-	// TODO: use the environments API
-	testEnvironmentID := os.Getenv("HONEYCOMB_ENVIRONMENT_ID")
+	env := newTestEnvironment(ctx, t, c)
 
 	// create a bunch of keys
 	numKeys := int(math.Floor(1.5 * float64(defaultPageSize)))
@@ -88,7 +85,7 @@ func TestClient_APIKeys_Pagination(t *testing.T) {
 			Name:    helper.ToPtr(fmt.Sprintf("test.%d", i)),
 			KeyType: "ingest",
 			Environment: &Environment{
-				ID: testEnvironmentID,
+				ID: env.ID,
 			},
 		})
 		require.NoError(t, err)
diff --git a/client/v2/client_test.go b/client/v2/client_test.go
index 6ccfb75d..20481971 100644
--- a/client/v2/client_test.go
+++ b/client/v2/client_test.go
@@ -10,6 +10,8 @@ import (
 	"github.com/stretchr/testify/require"
 
 	hnyclient "github.com/honeycombio/terraform-provider-honeycombio/client"
+	"github.com/honeycombio/terraform-provider-honeycombio/internal/helper"
+	"github.com/honeycombio/terraform-provider-honeycombio/internal/helper/test"
 )
 
 const (
@@ -136,3 +138,29 @@ func newTestClient(t *testing.T) *Client {
 
 	return c
 }
+
+// newTestEnvironment creates a new Environment with a random name and description
+// for testing purposes.
+// The Environment is automatically deleted when the test completes.
+func newTestEnvironment(ctx context.Context, t *testing.T, c *Client) *Environment {
+	t.Helper()
+
+	env, err := c.Environments.Create(ctx, &Environment{
+		Name:        test.RandomStringWithPrefix("test.", 20),
+		Description: helper.ToPtr(test.RandomString(50)),
+	})
+	require.NoError(t, err)
+
+	t.Cleanup(func() {
+		// disable deletion protection and delete the Environment
+		c.Environments.Update(context.Background(), &Environment{
+			ID: env.ID,
+			Settings: &EnvironmentSettings{
+				DeleteProtected: helper.ToPtr(false),
+			},
+		})
+		c.Environments.Delete(ctx, env.ID)
+	})
+
+	return env
+}
diff --git a/internal/provider/api_key_resource_test.go b/internal/provider/api_key_resource_test.go
index 13f676e5..df1721c3 100644
--- a/internal/provider/api_key_resource_test.go
+++ b/internal/provider/api_key_resource_test.go
@@ -11,8 +11,9 @@ import (
 
 func TestAcc_APIKeyResource(t *testing.T) {
 	t.Parallel()
-
-	envID := testAccEnvironment()
+	ctx := context.Background()
+	c := testAccV2Client(t)
+	env := testAccEnvironment(ctx, t, c)
 
 	t.Run("happy path", func(t *testing.T) {
 		resource.Test(t, resource.TestCase{
@@ -20,27 +21,27 @@ func TestAcc_APIKeyResource(t *testing.T) {
 			ProtoV5ProviderFactories: testAccProtoV5MuxServerFactory,
 			Steps: []resource.TestStep{
 				{
-					Config: testAccConfigBasicAPIKeyTest("test key", "false", envID),
+					Config: testAccConfigBasicAPIKeyTest("test key", "false", env.ID),
 					Check: resource.ComposeAggregateTestCheckFunc(
 						testAccEnsureAPIKeyExists(t, "honeycombio_api_key.test"),
 						resource.TestCheckResourceAttrSet("honeycombio_api_key.test", "id"),
 						resource.TestCheckResourceAttrSet("honeycombio_api_key.test", "secret"),
 						resource.TestCheckResourceAttr("honeycombio_api_key.test", "name", "test key"),
 						resource.TestCheckResourceAttr("honeycombio_api_key.test", "type", "ingest"),
-						resource.TestCheckResourceAttr("honeycombio_api_key.test", "environment_id", envID),
+						resource.TestCheckResourceAttr("honeycombio_api_key.test", "environment_id", env.ID),
 						resource.TestCheckResourceAttr("honeycombio_api_key.test", "disabled", "false"),
 						resource.TestCheckResourceAttr("honeycombio_api_key.test", "permissions.0.create_datasets", "true"),
 					),
 				},
 				{ // now update the name and disabled state
-					Config: testAccConfigBasicAPIKeyTest("updated test key", "true", envID),
+					Config: testAccConfigBasicAPIKeyTest("updated test key", "true", env.ID),
 					Check: resource.ComposeAggregateTestCheckFunc(
 						testAccEnsureAPIKeyExists(t, "honeycombio_api_key.test"),
 						resource.TestCheckResourceAttrSet("honeycombio_api_key.test", "id"),
 						resource.TestCheckResourceAttrSet("honeycombio_api_key.test", "secret"),
 						resource.TestCheckResourceAttr("honeycombio_api_key.test", "name", "updated test key"),
 						resource.TestCheckResourceAttr("honeycombio_api_key.test", "type", "ingest"),
-						resource.TestCheckResourceAttr("honeycombio_api_key.test", "environment_id", envID),
+						resource.TestCheckResourceAttr("honeycombio_api_key.test", "environment_id", env.ID),
 						resource.TestCheckResourceAttr("honeycombio_api_key.test", "disabled", "true"),
 						resource.TestCheckResourceAttr("honeycombio_api_key.test", "permissions.0.create_datasets", "true"),
 					),
@@ -61,14 +62,14 @@ resource "honeycombio_api_key" "test" {
   type = "ingest"
 
   environment_id = "%s"
-}`, envID),
+}`, env.ID),
 					Check: resource.ComposeAggregateTestCheckFunc(
 						testAccEnsureAPIKeyExists(t, "honeycombio_api_key.test"),
 						resource.TestCheckResourceAttrSet("honeycombio_api_key.test", "id"),
 						resource.TestCheckResourceAttrSet("honeycombio_api_key.test", "secret"),
 						resource.TestCheckResourceAttr("honeycombio_api_key.test", "name", "test key"),
 						resource.TestCheckResourceAttr("honeycombio_api_key.test", "type", "ingest"),
-						resource.TestCheckResourceAttr("honeycombio_api_key.test", "environment_id", envID),
+						resource.TestCheckResourceAttr("honeycombio_api_key.test", "environment_id", env.ID),
 						resource.TestCheckResourceAttr("honeycombio_api_key.test", "disabled", "false"),
 					),
 				},
diff --git a/internal/provider/environment_data_source_test.go b/internal/provider/environment_data_source_test.go
index 87a7f141..4fab3bfc 100644
--- a/internal/provider/environment_data_source_test.go
+++ b/internal/provider/environment_data_source_test.go
@@ -6,32 +6,12 @@ import (
 	"testing"
 
 	"github.com/hashicorp/terraform-plugin-testing/helper/resource"
-	"github.com/stretchr/testify/require"
-
-	v2client "github.com/honeycombio/terraform-provider-honeycombio/client/v2"
-	"github.com/honeycombio/terraform-provider-honeycombio/internal/helper"
-	"github.com/honeycombio/terraform-provider-honeycombio/internal/helper/test"
 )
 
 func TestAcc_EnvironmentDataSource(t *testing.T) {
 	ctx := context.Background()
 	c := testAccV2Client(t)
-
-	env, err := c.Environments.Create(ctx, &v2client.Environment{
-		Name:        test.RandomStringWithPrefix("test.", 20),
-		Description: helper.ToPtr("test environment"),
-	})
-	require.NoError(t, err)
-
-	t.Cleanup(func() {
-		c.Environments.Update(ctx, &v2client.Environment{
-			ID: env.ID,
-			Settings: &v2client.EnvironmentSettings{
-				DeleteProtected: helper.ToPtr(false),
-			},
-		})
-		c.Environments.Delete(ctx, env.ID)
-	})
+	env := testAccEnvironment(ctx, t, c)
 
 	resource.Test(t, resource.TestCase{
 		PreCheck:                 testAccPreCheckV2API(t),
diff --git a/internal/provider/environments_data_source_test.go b/internal/provider/environments_data_source_test.go
index 561ba5a5..89d535cd 100644
--- a/internal/provider/environments_data_source_test.go
+++ b/internal/provider/environments_data_source_test.go
@@ -6,11 +6,8 @@ import (
 	"testing"
 
 	"github.com/hashicorp/terraform-plugin-testing/helper/resource"
-	"github.com/stretchr/testify/require"
 
 	v2client "github.com/honeycombio/terraform-provider-honeycombio/client/v2"
-	"github.com/honeycombio/terraform-provider-honeycombio/internal/helper"
-	"github.com/honeycombio/terraform-provider-honeycombio/internal/helper/test"
 )
 
 func TestAcc_EnvironmentsDatasource(t *testing.T) {
@@ -21,31 +18,13 @@ func TestAcc_EnvironmentsDatasource(t *testing.T) {
 	// create a bunch of environments
 	testEnvs := make([]*v2client.Environment, numEnvs+1)
 	for i := 0; i < numEnvs; i++ {
-		e, err := c.Environments.Create(ctx, &v2client.Environment{
-			Name: test.RandomStringWithPrefix("test.", 20),
-		})
-		require.NoError(t, err)
+		e := testAccEnvironment(ctx, t, c)
 		testEnvs[i] = e
 	}
 	// one additional with a different prefix for filter testing
-	e, err := c.Environments.Create(ctx, &v2client.Environment{
-		Name: "test." + test.RandomString(20),
-	})
-	require.NoError(t, err)
+	e := testAccEnvironment(ctx, t, c)
 	testEnvs[numEnvs] = e
 
-	t.Cleanup(func() {
-		for _, e := range testEnvs {
-			c.Environments.Update(ctx, &v2client.Environment{
-				ID: e.ID,
-				Settings: &v2client.EnvironmentSettings{
-					DeleteProtected: helper.ToPtr(false),
-				},
-			})
-			c.Environments.Delete(ctx, e.ID)
-		}
-	})
-
 	resource.Test(t, resource.TestCase{
 		PreCheck:                 testAccPreCheckV2API(t),
 		ProtoV5ProviderFactories: testAccProtoV5ProviderFactory,
diff --git a/internal/provider/provider_test.go b/internal/provider/provider_test.go
index 6b62a468..2f102acd 100644
--- a/internal/provider/provider_test.go
+++ b/internal/provider/provider_test.go
@@ -11,10 +11,13 @@ import (
 	"github.com/hashicorp/terraform-plugin-mux/tf5muxserver"
 	"github.com/hashicorp/terraform-plugin-testing/helper/resource"
 	"github.com/joho/godotenv"
+	"github.com/stretchr/testify/require"
 
 	"github.com/honeycombio/terraform-provider-honeycombio/client"
 	v2client "github.com/honeycombio/terraform-provider-honeycombio/client/v2"
 	"github.com/honeycombio/terraform-provider-honeycombio/honeycombio"
+	"github.com/honeycombio/terraform-provider-honeycombio/internal/helper"
+	"github.com/honeycombio/terraform-provider-honeycombio/internal/helper/test"
 )
 
 func init() {
@@ -68,9 +71,6 @@ func testAccPreCheckV2API(t *testing.T) func() {
 		if _, ok := os.LookupEnv("HONEYCOMB_KEY_SECRET"); !ok {
 			t.Fatalf("environment variable HONEYCOMB_KEY_SECRET must be set to run acceptance tests")
 		}
-		if _, ok := os.LookupEnv("HONEYCOMB_ENVIRONMENT_ID"); !ok {
-			t.Fatalf("environment variable HONEYCOMB_ENVIRONMENT_ID must be set to run acceptance tests")
-		}
 	}
 }
 
@@ -78,9 +78,30 @@ func testAccDataset() string {
 	return os.Getenv("HONEYCOMB_DATASET")
 }
 
-func testAccEnvironment() string {
-	// TODO: replace with looking up the environment by name or doing a create at test start
-	return os.Getenv("HONEYCOMB_ENVIRONMENT_ID")
+// newTestEnvirionment creates a new Environment with a random name and description
+// for testing purposes.
+// The Environment is automatically deleted when the test completes.
+func testAccEnvironment(ctx context.Context, t *testing.T, c *v2client.Client) *v2client.Environment {
+	t.Helper()
+
+	env, err := c.Environments.Create(ctx, &v2client.Environment{
+		Name:        test.RandomStringWithPrefix("test.", 20),
+		Description: helper.ToPtr(test.RandomString(50)),
+	})
+	require.NoError(t, err)
+
+	t.Cleanup(func() {
+		// disable deletion protection and delete the Environment
+		c.Environments.Update(context.Background(), &v2client.Environment{
+			ID: env.ID,
+			Settings: &v2client.EnvironmentSettings{
+				DeleteProtected: helper.ToPtr(false),
+			},
+		})
+		c.Environments.Delete(ctx, env.ID)
+	})
+
+	return env
 }
 
 func testAccClient(t *testing.T) *client.Client {
@@ -112,15 +133,9 @@ func TestAcc_Configuration(t *testing.T) {
 					Config: `
 data "honeycombio_datasets" "all" {}
 
-# TODO: replace with v2-client data source
-resource "honeycombio_api_key" "test" {
-  name = "test"
-  type = "ingest"
-
-  environment_id = "1"
-}`,
-					PlanOnly:           true,
-					ExpectNonEmptyPlan: true,
+data "honeycombio_environments" "all" {}
+`,
+					PlanOnly: true,
 				},
 			},
 		})
@@ -150,16 +165,8 @@ resource "honeycombio_api_key" "test" {
 					PreConfig: func() {
 						t.Setenv("HONEYCOMB_API_KEY", "")
 					},
-					Config: `
-# TODO: replace with v2-client data source
-resource "honeycombio_api_key" "test" {
-  name = "test"
-  type = "ingest"
-
-  environment_id = "1"
-}`,
-					PlanOnly:           true,
-					ExpectNonEmptyPlan: true,
+					Config:   `data "honeycombio_environments" "all" {}`,
+					PlanOnly: true,
 				},
 			},
 		})
@@ -174,14 +181,7 @@ resource "honeycombio_api_key" "test" {
 						t.Setenv("HONEYCOMB_API_KEY", "")
 						t.Setenv("HONEYCOMB_KEY_SECRET", "")
 					},
-					Config: `
-# TODO: replace with v2-client data source
-resource "honeycombio_api_key" "test" {
-  name = "test"
-  type = "ingest"
-
-  environment_id = "1"
-}`,
+					Config:      `data "honeycombio_environments" "all" {}`,
 					PlanOnly:    true,
 					ExpectError: regexp.MustCompile(`provider requires both a Honeycomb API Key ID and Secret`),
 				},
@@ -216,14 +216,7 @@ resource "honeycombio_api_key" "test" {
 						t.Setenv("HONEYCOMB_KEY_ID", "")
 						t.Setenv("HONEYCOMB_KEY_SECRET", "")
 					},
-					Config: `
-# TODO: replace with v2-client data source
-resource "honeycombio_api_key" "test" {
-  name = "test"
-  type = "ingest"
-
-  environment_id = "1"
-}`,
+					Config:      `data "honeycombio_environments" "all" {}`,
 					ExpectError: regexp.MustCompile(`No v2 API client configured`),
 				},
 			},