Skip to content

Conversation

felixlut
Copy link
Contributor

@felixlut felixlut commented Jul 23, 2023

Resolves #1777

I'll leave this a a Draft for now because of 2 reasons:

  1. I want feedback on the schema structure. It's pretty big and complex. and I want to make it as user friendly as possible. I'll post some comments in the PR where I've some ideas on what could be altered.
  2. The google/go-github version needs to be bumped before all the functionality is in place. This requires that they make a new release (v53.2.0 was released 19:th June, which is no longer up to date with the structure of the Rulesets API)
    • Eg, bypass_actors can't be used currently because its API requires all of actor_id, actor_type and bypass_mode to be set, but the library only supports two of them. They fixed it since though, see here
    • There are other examples of this as well (beta level functionality tends to change quite often I guess 😓)

The Terraform would look something like this:

# Used for adding multiple bypass_actors 
locals {
  actors = [
    # I have no idea where these id:s come from, I just created the Rule in the UI, and these where the ones
    { actor_id = 1, actor_type = "OrganizationAdmin" },
    { actor_id = 5, actor_type = "RepositoryRole" },
  ]
}

resource "github_repository_ruleset" "test" {
  repository  = "my-cool-repo"
  owner       = "my-cool-org"
  name        = "tf test rule"
  target      = "branch"
  enforcement = "disabled"
  conditions {
    include = [
      "~DEFAULT_BRANCH",
      "refs/heads/prod-*",
      "~ALL"
    ]
    exclude = ["refs/heads/dev-*"]
  }
  rule_creation = true
  # rule_update  = true # TODO: Currently broken, go-github needs a bump
  rule_deletion                = true
  rule_required_linear_history = true
  rule_required_signatures     = true
  rule_non_fast_forward        = true
  rule_required_deployments    = ["terraform"]
  rule_pull_request {
    dismiss_stale_reviews_on_push     = true
    require_code_owner_review         = true
    require_last_push_approval        = true
    required_approving_review_count   = 5
    required_review_thread_resolution = true
  }
  rule_required_status_checks {
    strict_required_status_checks_policy = true
    required_status_checks               = ["terraform-plan", "SonarQube Code Analysis:95502"]
  }
  # TODO: Currently broken, go-github needs a bump
  # dynamic bypass_actors {
  #   for_each = local.actors
  #   content {
  #     actor_id = bypass_actors.value["actor_id"]
  #     actor_type = bypass_actors.value["actor_type"]
  #   }
  # }
}

Before the change?

After the change?

Pull request checklist

  • Tests for the changes have been added (for bug fixes / features)
  • Docs have been reviewed and added / updated if needed (for bug fixes / features)

Does this introduce a breaking change?

Please see our docs on breaking changes to help!

  • Yes
  • No

felixlut and others added 19 commits July 17, 2023 21:42
…rations#1772)

Bumps [google.golang.org/grpc](https://github.com/grpc/grpc-go) from 1.50.1 to 1.53.0.
- [Release notes](https://github.com/grpc/grpc-go/releases)
- [Commits](grpc/grpc-go@v1.50.1...v1.53.0)

---
updated-dependencies:
- dependency-name: google.golang.org/grpc
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
…ions#1784)

Bumps [golang.org/x/crypto](https://github.com/golang/crypto) from 0.10.0 to 0.11.0.
- [Commits](golang/crypto@v0.10.0...v0.11.0)

---
updated-dependencies:
- dependency-name: golang.org/x/crypto
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Co-authored-by: Keegan Campbell <me@kfcampbell.com>
* Don't run go mod tidy on release

* Be more specific about releases
…ons#1785)

Bumps [golang.org/x/oauth2](https://github.com/golang/oauth2) from 0.9.0 to 0.10.0.
- [Commits](golang/oauth2@v0.9.0...v0.10.0)

---
updated-dependencies:
- dependency-name: golang.org/x/oauth2
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Co-authored-by: Keegan Campbell <me@kfcampbell.com>
Co-authored-by: Keegan Campbell <me@kfcampbell.com>
- use app_id rather than memory address
- don't mix contexts and checks

Co-authored-by: Keegan Campbell <me@kfcampbell.com>
…tegrations#1795)

Avoid causing a permanent `plan` diff by attempting to change attributes
that can no longer be modified if a repository is archived.

Fixes integrations#1793.
… destroyed (integrations#1783)

* feat: add ability to downgrade membership on destroy

* add docs

* formatting

* formatting

* check membership status before downgrading

* fix lint

* fix lint

* Update github/resource_github_membership.go

Co-authored-by: Keegan Campbell <me@kfcampbell.com>

---------

Co-authored-by: Keegan Campbell <me@kfcampbell.com>
return &schema.Resource{
Create: resourceGithubRepositoryRulesetCreateOrUpdate,
Read: resourceGithubRepositoryRulesetRead,
// Update: resourceGithubRepositoryRulesetUpdate, // TODO: Implement update, replacement fine for now
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'll leave the implementation of this until the Schema has been accepted

"repository": {
Type: schema.TypeString,
Required: true,
ForceNew: true,
Copy link
Contributor Author

@felixlut felixlut Jul 23, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All of the ForceNew: true, will be removed once Update is implemented, see previous comment

Description: "Target branches/tags. Both an inclusion and exclusion list, supporting regexes as well as ALL branches/tags and the default branch",
Elem: &schema.Resource{
Schema: map[string]*schema.Schema{
// TODO: Should the default branch + ALL branches/tags have it's own field?
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I could see an argument for having fields for both default_branch and all_branches_and_tags as boolean values to get around users needing to learn that they are referenced as ~DEFAULT_BRANCH and ~ALL.

Changing this would be trivial if anyone strongly feels they should be their own fields (updating this after this PR is merged wouldn't be difficult either, if the functionality is wanted down the line)

ForceNew: true, // TODO: Remove this when updating is implemented
Description: "Only allow users with bypass permission to create matching refs.",
},
// TODO: Borken currently. When underlying sdk gets a version bump, its fixed
Copy link
Contributor Author

@felixlut felixlut Jul 23, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe go-github needs a version bump for this one? It's a weird one though, because both the API docs and go-github expects update_allows_fetch_and_merge, but when I ping the API, I get back a response looking like this (where the update field is the most important, the rest is just there for context):

"rules": [
  {
    "type": "deletion"
  },
  {
    "type": "non_fast_forward"
  },
  {
    "type": "required_status_checks",
    "parameters": {
      "required_status_checks": [
        {
          "context": "SonarQube Code Analysis",
          "integration_id": 95502
        }
      ],
      "strict_required_status_checks_policy": true
    }
  },
  {
    "type": "pull_request",
    "parameters": {
      "require_code_owner_review": true,
      "require_last_push_approval": true,
      "dismiss_stale_reviews_on_push": true,
      "required_approving_review_count": 3,
      "required_review_thread_resolution": true
    }
  },
  {
    "type": "required_signatures"
  },
  {
    "type": "required_deployments",
    "parameters": {
      "required_deployment_environments": [
        "terraform"
      ]
    }
  },
  {
    "type": "required_linear_history"
  },
  {
    "type": "update"
  },
  {
    "type": "creation"
  }
],

I don't know why this is, or if I'm missing something. I'll look into this more later, after a bumo of go-github has been made.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Relevant discussion thread here: google/go-github#2836

},
},
},
"rule_creation": {
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

When I started implementing this, I played around with a nested rules field, which wrapped all the rule_* fields you can see below here. It proved to require a bunch of boilerplate code when implementing the actual Create/Read/Destroy logic, so I instead opted into moving them to the root, and instead using a rule_* naming convention for them.

The rule_* addition might be overkill (and requires a little bit of parsing logic in the actual implementation), but since the schema is quite large, I think it's worth having it just to make it clear that these are the rules (a creation field doesn't really mean much, rule_creation is clearer IMO) .

I'm open for feedback here though. Baking all of them into a nested structure is possible, just somewhat tedious.

},
},
},
// TODO: Broken until a bump in the underlying sdk
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As mentioned in the PR description, this one is broken currently. go-github needs a release bump. As opposed to the rule_update field, I'm confident will be solved by this bump 😓

}
rulesetConditions := github.RulesetConditions{
RefName: conditions,
// RepositoryName: &github.RulesetRepositoryConditionParameters{}, // TODO: Implement for org stuff
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It shouldn't be that hard to build on this to also implement Org level Rules. Leaving this until the schema has been finalized and go-github has been bumped

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Or another PR, idk what makes sense. We'll see

case 2:
cContext, cIntegrationId = parts[0], parts[1]
default:
// TODO: What is the prefered way of throwing errors? fmt.Errorf() or errors.New()?
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have seen both fmt.Errorf() and errors.New being used to throw errors across this project. What is the recommended way?

@felixlut felixlut changed the title Rulesets feat: github_repository_ruleset Jul 23, 2023
@felixlut felixlut changed the title feat: github_repository_ruleset feat: github_repository_ruleset WIP Jul 23, 2023
@felixlut felixlut mentioned this pull request Jul 23, 2023
1 task
@felixlut
Copy link
Contributor Author

Relevant discussion regarding the question about the update rule: google/go-github#2836

@felixlut
Copy link
Contributor Author

Closing this in favor of #1808

@felixlut felixlut closed this Jul 30, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

[FEAT]: Repository Rulesets
7 participants