Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
17 commits
Select commit Hold shift + click to select a range
134d759
feat(enterprise-scim): add utility functions for SCIM data sources
github-actions[bot] Feb 4, 2026
d410b1e
feat(enterprise-scim): add github_enterprise_scim_group data source
github-actions[bot] Feb 4, 2026
415e836
feat(enterprise-scim): add github_enterprise_scim_groups data source
github-actions[bot] Feb 4, 2026
7fcb201
feat(enterprise-scim): add github_enterprise_scim_user data source
github-actions[bot] Feb 4, 2026
473abfd
feat(enterprise-scim): add github_enterprise_scim_users data source
github-actions[bot] Feb 4, 2026
28c8bb7
feat(enterprise-scim): register SCIM data sources in provider
github-actions[bot] Feb 4, 2026
617f924
fix(enterprise-scim): update go-github import to v82
github-actions[bot] Feb 4, 2026
914e632
test(enterprise-scim): migrate SCIM acceptance tests to terraform-plu…
vmvarela Feb 17, 2026
85f07ce
fix(enterprise-scim): address review findings
vmvarela Feb 18, 2026
45a1821
fix(enterprise-scim): update go-github import from v82 to v83
vmvarela Feb 23, 2026
9c0ad3d
fix: update go-github import to v84 after rebase
vmvarela Mar 18, 2026
2c1658c
fix(enterprise-scim): replace "Github" with "GitHub" in page_title (#41)
vmvarela Mar 20, 2026
0e0c26d
fix(scim): use buildTwoPartID for data source IDs
vmvarela Mar 23, 2026
be76220
Merge pull request #59 from vmvarela/fix/53-scim-buildtwopartid
vmvarela Mar 23, 2026
453fde1
refactor(scim): move enterpriseSCIMMetaSchema() to util_enterprise_sc…
vmvarela Mar 23, 2026
60ba689
Merge pull request #61 from vmvarela/fix/54-scim-meta-schema-util
vmvarela Mar 23, 2026
3e8d5a1
chore(lint): exclude modernize newexpr rule for Ptr calls
vmvarela Mar 23, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions .golangci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,9 @@ linters:
- linters:
- staticcheck
text: "SA1019.*ByID.*deprecated"
- linters:
- modernize
text: "newexpr: call of Ptr"

issues:
max-issues-per-linter: 0
Expand Down
69 changes: 69 additions & 0 deletions github/data_source_github_enterprise_scim_group.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
package github

import (
"context"

"github.com/hashicorp/terraform-plugin-sdk/v2/diag"
"github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema"
)

func dataSourceGithubEnterpriseSCIMGroup() *schema.Resource {
s := enterpriseSCIMGroupSchema()
s["enterprise"] = &schema.Schema{
Description: "The enterprise slug.",
Type: schema.TypeString,
Required: true,
}
s["scim_group_id"] = &schema.Schema{
Description: "The SCIM group ID.",
Type: schema.TypeString,
Required: true,
}

return &schema.Resource{
Description: "Retrieves SCIM provisioning information for a single GitHub enterprise group.",
ReadContext: dataSourceGithubEnterpriseSCIMGroupRead,
Schema: s,
}
}

func dataSourceGithubEnterpriseSCIMGroupRead(ctx context.Context, d *schema.ResourceData, meta any) diag.Diagnostics {
client := meta.(*Owner).v3client

enterprise := d.Get("enterprise").(string)
scimGroupID := d.Get("scim_group_id").(string)

group, _, err := client.Enterprise.GetProvisionedSCIMGroup(ctx, enterprise, scimGroupID, nil)
if err != nil {
return diag.FromErr(err)
}

d.SetId(buildTwoPartID(enterprise, scimGroupID))

if err := d.Set("schemas", group.Schemas); err != nil {
return diag.FromErr(err)
}
if group.ID != nil {
if err := d.Set("id", *group.ID); err != nil {
return diag.FromErr(err)
}
}
if group.ExternalID != nil {
if err := d.Set("external_id", *group.ExternalID); err != nil {
return diag.FromErr(err)
}
}
if group.DisplayName != nil {
if err := d.Set("display_name", *group.DisplayName); err != nil {
return diag.FromErr(err)
}
}
if err := d.Set("members", flattenEnterpriseSCIMGroupMembers(group.Members)); err != nil {
return diag.FromErr(err)
}
if err := d.Set("meta", flattenEnterpriseSCIMMeta(group.Meta)); err != nil {
return diag.FromErr(err)
}

return nil
}
36 changes: 36 additions & 0 deletions github/data_source_github_enterprise_scim_group_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
package github

import (
"fmt"
"testing"

"github.com/hashicorp/terraform-plugin-testing/helper/resource"
"github.com/hashicorp/terraform-plugin-testing/knownvalue"
"github.com/hashicorp/terraform-plugin-testing/statecheck"
"github.com/hashicorp/terraform-plugin-testing/tfjsonpath"
)

func TestAccGithubEnterpriseSCIMGroupDataSource(t *testing.T) {
t.Run("reads group without error", func(t *testing.T) {
resource.Test(t, resource.TestCase{
PreCheck: func() { skipUnlessEnterprise(t) },
ProviderFactories: providerFactories,
Steps: []resource.TestStep{{
Config: fmt.Sprintf(`
data "github_enterprise_scim_groups" "all" {
enterprise = "%s"
}

data "github_enterprise_scim_group" "test" {
enterprise = "%[1]s"
scim_group_id = data.github_enterprise_scim_groups.all.resources[0].id
}
`, testAccConf.enterpriseSlug),
ConfigStateChecks: []statecheck.StateCheck{
statecheck.ExpectKnownValue("data.github_enterprise_scim_group.test", tfjsonpath.New("display_name"), knownvalue.NotNull()),
statecheck.ExpectKnownValue("data.github_enterprise_scim_group.test", tfjsonpath.New("schemas"), knownvalue.NotNull()),
},
}},
})
})
}
179 changes: 179 additions & 0 deletions github/data_source_github_enterprise_scim_groups.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,179 @@
package github

import (
"context"
"fmt"
"net/url"

"github.com/hashicorp/terraform-plugin-sdk/v2/diag"
"github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema"
"github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation"
)

func dataSourceGithubEnterpriseSCIMGroups() *schema.Resource {
return &schema.Resource{
Description: "Retrieves SCIM groups provisioned for a GitHub enterprise.",
ReadContext: dataSourceGithubEnterpriseSCIMGroupsRead,

Schema: map[string]*schema.Schema{
"enterprise": {
Description: "The enterprise slug.",
Type: schema.TypeString,
Required: true,
},
"filter": {
Description: "Optional SCIM filter. See GitHub SCIM enterprise docs for supported filters.",
Type: schema.TypeString,
Optional: true,
},
"results_per_page": {
Description: "Number of results per request (mapped to SCIM 'count'). Used while auto-fetching all pages.",
Type: schema.TypeInt,
Optional: true,
Default: 100,
ValidateDiagFunc: validation.ToDiagFunc(validation.IntBetween(1, 100)),
},

"schemas": {
Description: "SCIM response schemas.",
Type: schema.TypeList,
Computed: true,
Elem: &schema.Schema{Type: schema.TypeString},
},
"total_results": {
Description: "The total number of results returned by the SCIM endpoint.",
Type: schema.TypeInt,
Computed: true,
},
"start_index": {
Description: "The startIndex from the first SCIM page.",
Type: schema.TypeInt,
Computed: true,
},
"items_per_page": {
Description: "The itemsPerPage from the first SCIM page.",
Type: schema.TypeInt,
Computed: true,
},
"resources": {
Description: "All SCIM groups.",
Type: schema.TypeList,
Computed: true,
Elem: &schema.Resource{
Schema: enterpriseSCIMGroupSchema(),
},
},
},
}
}

func dataSourceGithubEnterpriseSCIMGroupsRead(ctx context.Context, d *schema.ResourceData, meta any) diag.Diagnostics {
client := meta.(*Owner).v3client

enterprise := d.Get("enterprise").(string)
filter := d.Get("filter").(string)
count := d.Get("results_per_page").(int)

groups, first, err := enterpriseSCIMListAllGroups(ctx, client, enterprise, filter, count)
if err != nil {
return diag.FromErr(err)
}

flat := make([]any, 0, len(groups))
for _, group := range groups {
flat = append(flat, flattenEnterpriseSCIMGroup(group))
}

id := fmt.Sprintf("%s/scim-groups", enterprise)
if filter != "" {
id = fmt.Sprintf("%s?filter=%s", id, url.QueryEscape(filter))
}

d.SetId(id)

if err := d.Set("schemas", first.Schemas); err != nil {
return diag.FromErr(err)
}
if first.TotalResults != nil {
if err := d.Set("total_results", *first.TotalResults); err != nil {
return diag.FromErr(err)
}
}
startIndex := 1
if first.StartIndex != nil && *first.StartIndex > 0 {
startIndex = *first.StartIndex
}
if err := d.Set("start_index", startIndex); err != nil {
return diag.FromErr(err)
}
itemsPerPage := count
if first.ItemsPerPage != nil && *first.ItemsPerPage > 0 {
itemsPerPage = *first.ItemsPerPage
}
if err := d.Set("items_per_page", itemsPerPage); err != nil {
return diag.FromErr(err)
}
if err := d.Set("resources", flat); err != nil {
return diag.FromErr(err)
}

return nil
}

func enterpriseSCIMGroupSchema() map[string]*schema.Schema {
return map[string]*schema.Schema{
"schemas": {
Type: schema.TypeList,
Computed: true,
Description: "SCIM schemas for this group.",
Elem: &schema.Schema{Type: schema.TypeString},
},
"id": {
Type: schema.TypeString,
Computed: true,
Description: "The SCIM group ID.",
},
"external_id": {
Type: schema.TypeString,
Computed: true,
Description: "The external ID for the group.",
},
"display_name": {
Type: schema.TypeString,
Computed: true,
Description: "The SCIM group displayName.",
},
"members": {
Type: schema.TypeList,
Computed: true,
Description: "Group members.",
Elem: &schema.Resource{Schema: enterpriseSCIMGroupMemberSchema()},
},
"meta": {
Type: schema.TypeList,
Computed: true,
Description: "Resource metadata.",
Elem: &schema.Resource{Schema: enterpriseSCIMMetaSchema()},
},
}
}

func enterpriseSCIMGroupMemberSchema() map[string]*schema.Schema {
return map[string]*schema.Schema{
"value": {
Type: schema.TypeString,
Computed: true,
Description: "Member identifier.",
},
"ref": {
Type: schema.TypeString,
Computed: true,
Description: "Member reference URL.",
},
"display_name": {
Type: schema.TypeString,
Computed: true,
Description: "Member display name.",
},
}
}
32 changes: 32 additions & 0 deletions github/data_source_github_enterprise_scim_groups_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
package github

import (
"fmt"
"testing"

"github.com/hashicorp/terraform-plugin-testing/helper/resource"
"github.com/hashicorp/terraform-plugin-testing/knownvalue"
"github.com/hashicorp/terraform-plugin-testing/statecheck"
"github.com/hashicorp/terraform-plugin-testing/tfjsonpath"
)

func TestAccGithubEnterpriseSCIMGroupsDataSource(t *testing.T) {
t.Run("lists groups without error", func(t *testing.T) {
resource.Test(t, resource.TestCase{
PreCheck: func() { skipUnlessEnterprise(t) },
ProviderFactories: providerFactories,
Steps: []resource.TestStep{{
Config: fmt.Sprintf(`
data "github_enterprise_scim_groups" "test" {
enterprise = "%s"
}
`, testAccConf.enterpriseSlug),
ConfigStateChecks: []statecheck.StateCheck{
statecheck.ExpectKnownValue("data.github_enterprise_scim_groups.test", tfjsonpath.New("total_results"), knownvalue.NotNull()),
statecheck.ExpectKnownValue("data.github_enterprise_scim_groups.test", tfjsonpath.New("schemas"), knownvalue.NotNull()),
statecheck.ExpectKnownValue("data.github_enterprise_scim_groups.test", tfjsonpath.New("resources"), knownvalue.NotNull()),
},
}},
})
})
}
Loading