feat: add database seeding command for development onboarding#217
feat: add database seeding command for development onboarding#217sid3305 wants to merge 4 commits into
Conversation
|
Thank you for your contribution! Before we can merge this PR, we need you to sign our Contributor License Agreement. I have read the CLA and agree to its terms. You can retrigger this bot by commenting recheck in this Pull Request. Posted by the CLA Assistant Lite bot. |
📝 WalkthroughWalkthroughA new ChangesDev Data Seeder
Estimated code review effort🎯 2 (Simple) | ⏱️ ~12 minutes Possibly related issues
Poem
🚥 Pre-merge checks | ✅ 3 | ❌ 2❌ Failed checks (2 warnings)
✅ Passed checks (3 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Actionable comments posted: 4
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@cmd/seed/main.go`:
- Around line 47-62: The seed output in the main function is logging plaintext
passwords and client secrets directly, which creates a security vulnerability by
exposing sensitive credentials in CI/runtime logs. Remove or redact the lines
that print the actual password values for the Admin User and Demo User, as well
as the line that prints the actual Client Secret for the OAuth Client. Keep the
labels and structure for clarity but do not output the actual sensitive values.
- Around line 14-18: The main function in cmd/seed/main.go allows database
seeding in any environment after calling config.LoadConfig(), which is a
security risk since it inserts known admin credentials. Add an environment
validation check immediately after the config.LoadConfig() call and before
config.InitDatabase() is invoked. This check should verify that the application
is running in a development environment, and if not, log a fatal error message
and exit the process to fail closed. This ensures the seeding command cannot
accidentally run against production or other non-development databases.
- Around line 151-157: The FindByClientID method in the OAuthClientRepository is
returning raw GORM errors without distinguishing between "record not found" and
other database errors, which masks transient failures as missing clients. Define
a sentinel error constant ErrOAuthClientNotFound in the repository package,
update the FindByClientID method to detect gorm.ErrRecordNotFound and return
this sentinel error instead, and then modify the seedOAuthClient function to
explicitly check if the error from FindByClientID is not the sentinel error
(meaning it's an actual database problem) and return that error before
attempting client creation, allowing the code to only proceed with creation when
the client genuinely doesn't exist.
- Around line 119-122: The seedUsers() and seedOAuthClient() functions are
ignoring the configured bcrypt cost from cfg.Security.BcryptRounds and using
bcrypt.DefaultCost instead. Modify both seedUsers() and seedOAuthClient() to
accept a bcryptCost parameter, then update the calls to GenerateFromPassword()
in both functions to use this parameter instead of bcrypt.DefaultCost. Finally,
pass cfg.Security.BcryptRounds as an argument when calling seedUsers() and
seedOAuthClient() from the main() function to ensure the configured security
policy is applied to all seeded password hashes.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: defaults
Review profile: CHILL
Plan: Pro Plus
Run ID: 0b5b104b-4434-44de-b134-c18eebc92deb
📒 Files selected for processing (2)
Makefilecmd/seed/main.go
| existingClient, err := clientRepo.FindByClientID("dev-client") | ||
|
|
||
| if err == nil && existingClient != nil { | ||
| log.Println("OAuth client already exists") | ||
| return nil | ||
| } | ||
|
|
There was a problem hiding this comment.
🧩 Analysis chain
🏁 Script executed:
#!/bin/bash
set -euo pipefail
# Verify FindByClientID's not-found/error contract in repository code.
fd -i "oauth*repository*.go" internal/repository
rg -n -C3 'FindByClientID|Err.*NotFound|gorm\.ErrRecordNotFound' internal/repositoryRepository: roshankumar0036singh/auth-server
Length of output: 8891
🏁 Script executed:
cat -n internal/repository/oauth_client_repository.goRepository: roshankumar0036singh/auth-server
Length of output: 2279
🏁 Script executed:
sed -n '140,170p' cmd/seed/main.goRepository: roshankumar0036singh/auth-server
Length of output: 732
Define sentinel error in repository and handle non-not-found errors before client creation.
The FindByClientID method returns raw GORM errors without distinguishing between "record not found" and other errors, causing transient DB failures to be masked as "client doesn't exist". Follow the pattern established by UserRepository and TokenRepository:
- Define
var ErrOAuthClientNotFound = errors.New("oauth client not found")in the repository package - Update
FindByClientIDto checkerrors.Is(err, gorm.ErrRecordNotFound)and return the sentinel error - In
seedOAuthClient, check for non-not-found errors before the creation flow:if err != nil && !errors.Is(err, repository.ErrOAuthClientNotFound) { return err }
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@cmd/seed/main.go` around lines 151 - 157, The FindByClientID method in the
OAuthClientRepository is returning raw GORM errors without distinguishing
between "record not found" and other database errors, which masks transient
failures as missing clients. Define a sentinel error constant
ErrOAuthClientNotFound in the repository package, update the FindByClientID
method to detect gorm.ErrRecordNotFound and return this sentinel error instead,
and then modify the seedOAuthClient function to explicitly check if the error
from FindByClientID is not the sentinel error (meaning it's an actual database
problem) and return that error before attempting client creation, allowing the
code to only proceed with creation when the client genuinely doesn't exist.
|
There was a problem hiding this comment.
♻️ Duplicate comments (1)
cmd/seed/main.go (1)
163-168: 🩺 Stability & Availability | 🟠 Major | ⚡ Quick winHandle non-not-found errors before client creation.
The code doesn't handle database errors from
FindByClientID. If the lookup fails with a connection error or other database issue, the code silently continues to create the client, which may fail with a duplicate key error (if the client actually exists) or mask the real database problem.Follow the pattern from
createUserIfNotExists(lines 116-125): check for the sentinel error and return other errors immediately.Run the following script to verify the repository's error handling contract:
#!/bin/bash # Description: Check if OAuthClientRepository uses sentinel errors like UserRepository # Check if ErrOAuthClientNotFound sentinel error exists rg -n 'ErrOAuthClientNotFound' internal/repository/ # Check FindByClientID implementation ast-grep outline internal/repository/oauth_client_repository.go --match OAuthClientRepository # Compare error handling patterns between repositories rg -n -A5 'FindByClientID|FindByEmail' internal/repository/ | grep -A5 'gorm.ErrRecordNotFound'If
ErrOAuthClientNotFounddoesn't exist, add it to the repository package and updateFindByClientIDto return it when the record is not found. Then update the seed code:🔒 Suggested fix
existingClient, err := clientRepo.FindByClientID("dev-client") -if err == nil && existingClient != nil { +if err == nil { log.Println("OAuth client already exists") return nil } + +if err != repository.ErrOAuthClientNotFound { + return err +} clientSecret := os.Getenv("SEED_CLIENT_SECRET")🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@cmd/seed/main.go` around lines 163 - 168, The FindByClientID call in the seed code doesn't properly handle database errors because it only checks if the error is nil, causing the code to silently continue if other database errors occur. First, ensure that the FindByClientID method in the OAuthClientRepository returns a sentinel error (such as ErrOAuthClientNotFound) when the record is not found, similar to how UserRepository handles not-found cases. Then update the error handling logic around the FindByClientID call to follow the pattern from createUserIfNotExists by checking if the error is the sentinel not-found error and returning other non-nil errors immediately before attempting to create the client.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Duplicate comments:
In `@cmd/seed/main.go`:
- Around line 163-168: The FindByClientID call in the seed code doesn't properly
handle database errors because it only checks if the error is nil, causing the
code to silently continue if other database errors occur. First, ensure that the
FindByClientID method in the OAuthClientRepository returns a sentinel error
(such as ErrOAuthClientNotFound) when the record is not found, similar to how
UserRepository handles not-found cases. Then update the error handling logic
around the FindByClientID call to follow the pattern from createUserIfNotExists
by checking if the error is the sentinel not-found error and returning other
non-nil errors immediately before attempting to create the client.



Summary
This PR adds a database seeding utility to improve developer onboarding and local testing.
Changes
Added
cmd/seed/main.gofor development database seeding.Added a
seedtarget to the Makefile:make seedSeeds standardized development data:
admin@example.com)demo@example.com)dev-client)Runs required database migrations before seeding.
Implements idempotent behavior so the command can be safely executed multiple times without creating duplicates.
Seeded Data
Admin User
admin@example.comAdmin123!Demo User
demo@example.comDemo123!OAuth Client
Local Development Clientdev-clientdev-client-secretVerification
go test ./...passes successfully.make seedsuccessfully creates development users and OAuth client.Problem Solved
New developers can now bootstrap a local environment with ready-to-use users and OAuth credentials instead of manually creating them before testing APIs.
Summary by CodeRabbit
seedcommand to populate development data, including demo/admin users with securely hashed passwords and a pre-configured local OAuth client.developmentorlocalenvironments and requiresSEED_CLIENT_SECRETfor OAuth client setup.