Skip to content

Migrate off deprecated trait profile/status attributes - #29

Open
laurenleach wants to merge 1 commit into
mainfrom
lauren/migrate-deprecated-trait-attrs
Open

Migrate off deprecated trait profile/status attributes#29
laurenleach wants to merge 1 commit into
mainfrom
lauren/migrate-deprecated-trait-attrs

Conversation

@laurenleach

Copy link
Copy Markdown

baton-sdk v0.20.6 moved profile, status, and created_at off the trait
messages onto attributes on Resource, deprecating the trait-level options and
getters. staticcheck flags every remaining call with SA1019, so verify / lint
is red on main.

This migrates the connector to the resource-level API:

  • With{User,Group,Role,App}Profile -> WithResourceProfile
  • WithStatus / WithDetailedStatus -> WithResourceStatus
  • WithCreatedAt / WithSecretCreatedAt -> WithResourceCreatedAt
  • trait GetProfile() / GetStatus() reads -> the equivalent read on the resource

The option type changes from a *TraitOption to a ResourceOption, so the calls
move out of the trait slice and into the variadic tail of the New*Resource call.
The two status enums are numerically identical, so the values map 1:1. Non-deprecated
trait data (login, aliases, emails, secret type/expiry) is untouched.

No behavioural change intended: the deprecated options already populated the
resource-level fields. golangci-lint run ./... reports 0 issues after this
change, and the package tests pass.

baton-sdk v0.20.6 moved `profile`, `status`, and `created_at` off the trait
messages onto attributes on `Resource`, deprecating the trait-level options and
getters. staticcheck flags every remaining call with `SA1019`, so `verify / lint`
is red on `main`.

This migrates the connector to the resource-level API:

- `With{User,Group,Role,App}Profile` -> `WithResourceProfile`
- `WithStatus` / `WithDetailedStatus` -> `WithResourceStatus`
- `WithCreatedAt` / `WithSecretCreatedAt` -> `WithResourceCreatedAt`
- trait `GetProfile()` / `GetStatus()` reads -> the equivalent read on the resource

The option type changes from a `*TraitOption` to a `ResourceOption`, so the calls
move out of the trait slice and into the variadic tail of the `New*Resource` call.
The two status enums are numerically identical, so the values map 1:1. Non-deprecated
trait data (login, aliases, emails, secret type/expiry) is untouched.

No behavioural change intended: the deprecated options already populated the
resource-level fields. `golangci-lint run ./...` reports 0 issues after this
change, and the package tests pass.
Comment thread pkg/connector/users.go
safeString(user.ID),
userTraits,
rs.WithResourceProfile(profile),
rs.WithResourceStatus(v2.Status_ResourceStatus(userStatus), ""),

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

🟡 Suggestion: The v2.Status_ResourceStatus(userStatus) conversion is correct today (both enums are 0/1/2/3 for UNSPECIFIED/ENABLED/DISABLED/DELETED), but it silently depends on two independent proto enums staying numerically aligned, and it keeps the connector reading the trait-level enum it is migrating away from. Consider declaring userStatus as v2.Status_ResourceStatus with v2.Status_RESOURCE_STATUS_ENABLED / ..._DISABLED at lines 272-275 and dropping the cast. (confidence: high that this is a real maintainability concern, not a bug)

@github-actions

github-actions Bot commented Aug 7, 2026

Copy link
Copy Markdown
Contributor

Connector PR Review: Migrate off deprecated trait profile/status attributes

Blocking Issues: 0 | Suggestions: 2 | Threads Resolved: 0
Criteria: Criteria status: loaded .claude/skills/ci-review.md from trusted base 028da95d29a3.
Review mode: full
View review run

Review Summary

Scanned the full PR diff (pkg/connector/users.go, pkg/connector/groups.go; no go.mod/go.sum changes) for security and correctness. The migration is faithful: NewUserResource/NewGroupResource append With{User,Group}Trait after the caller's resource options, and syncUserTraitToResource/syncGroupTraitToResource only fill unset fields, so the resource-level profile/status set here is not overwritten; GetProfile/GetStatus prefer resource-level values with a trait fallback, so downstream reads are unchanged. v2.UserTrait_Status_Status and v2.Status_ResourceStatus are numerically identical (0/1/2/3), so the enum conversion is value-preserving, and no deprecated trait profile/status/created-at calls remain in pkg/ or cmd/. No blocking issues found.

Security Issues

None found.

Correctness Issues

None found.

Suggestions

  • pkg/connector/users.go:295v2.Status_ResourceStatus(userStatus) casts between two independent proto enums; declare userStatus as v2.Status_ResourceStatus directly instead.
  • pkg/connector/users.go:267 / pkg/connector/groups.go:284pkg/connector has no test files, so nothing guards the "no behavioural change" claim; a small table test asserting resource-level profile/status would lock in the migration.
Prompt for AI agents
Verify each finding against the current code and only fix it if needed.

## Suggestions

In `pkg/connector/users.go`:
- Around lines 272-295: `userStatus` is declared as `v2.UserTrait_Status_STATUS_ENABLED` /
  `v2.UserTrait_Status_STATUS_DISABLED` (the trait-level enum this PR is migrating away
  from) and then converted with `v2.Status_ResourceStatus(userStatus)` at the
  `rs.WithResourceStatus` call. The conversion is correct today because both enums use
  0/1/2/3, but it depends on two independent proto enums staying numerically aligned.
  Change the declaration to `userStatus := v2.Status_RESOURCE_STATUS_ENABLED` /
  `userStatus = v2.Status_RESOURCE_STATUS_DISABLED` (type `v2.Status_ResourceStatus`) and
  pass `userStatus` to `rs.WithResourceStatus` without a cast.
- Around line 267 (`parseIntoUserResource`) and `pkg/connector/groups.go` around line 284
  (`parseIntoGroupResource`): the `pkg/connector` package has no `_test.go` files, so the
  PR's "no behavioural change" claim is unverified. Add a table-driven test that builds a
  user resource from a `gocloak.User` (enabled and disabled) and a group resource from a
  `client.Group`, then asserts the resource-level `GetProfile()` fields and
  `GetStatus().GetStatus()` equal the expected values. This also pins the
  enabled/disabled -> ENABLED/DISABLED mapping.

@github-actions github-actions Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

No blocking issues found.

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.

1 participant