Skip to content

Conversation

rhamzeh
Copy link
Member

@rhamzeh rhamzeh commented Jul 7, 2025

Description

Introduce a helper method for marking flags as required for consistency and ease of developer use

References

Review Checklist

  • I have clicked on "allow edits by maintainers".
  • I have added documentation for new/changed functionality in this PR or in a PR to openfga.dev [Provide a link to any relevant PRs in the references section above]
  • The correct base branch is being used, if not main
  • I have added tests to validate that the change in functionality is working as expected

Summary by CodeRabbit

  • Refactor
    • Improved and unified the way required command-line flags are enforced across various commands, resulting in more consistent error reporting.
  • Tests
    • Added comprehensive tests to ensure reliable handling of required flags in command-line operations.

@rhamzeh rhamzeh requested a review from a team as a code owner July 7, 2025 14:48
@rhamzeh rhamzeh requested a review from Copilot July 7, 2025 14:48
Copy link
Contributor

coderabbitai bot commented Jul 7, 2025

Important

Review skipped

Auto incremental reviews are disabled on this repository.

Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Walkthrough

A new internal flags package was introduced to centralize and standardize the process of marking command-line flags as required in Cobra-based CLI commands. Multiple command files were refactored to use this package's utility functions for setting required flags, replacing direct calls and streamlining error handling. Comprehensive unit tests were added for the new package.

Changes

Files/Group Change Summary
internal/flags/flags.go, internal/flags/flags_test.go New package and test file for utility functions to set required flags on Cobra commands.
cmd/model/get.go, cmd/model/list.go, cmd/model/test.go, cmd/model/write.go Refactored to use flags.SetFlagRequired for marking flags as required; updated error handling.
cmd/store/delete.go, cmd/store/export.go, cmd/store/get.go, cmd/store/import.go Switched to flags.SetFlagRequired for required flag logic; simplified error reporting.
cmd/query/list-users.go Consolidated multiple required flag calls into one flags.SetFlagsRequired call.

Sequence Diagram(s)

sequenceDiagram
    participant CLI_Command
    participant flags_pkg as flags package
    participant Cobra

    CLI_Command->>flags_pkg: SetFlagRequired(cmd, flag, location, isPersistent)
    flags_pkg->>Cobra: cmd.MarkFlagRequired(flag) (or Persistent)
    Cobra-->>flags_pkg: success/error
    flags_pkg-->>CLI_Command: error (if any)
    CLI_Command->>CLI_Command: Print error and exit if needed
Loading
sequenceDiagram
    participant CLI_Command
    participant flags_pkg as flags package
    participant Cobra

    CLI_Command->>flags_pkg: SetFlagsRequired(cmd, [flags...], location, isPersistent)
    loop for each flag
        flags_pkg->>Cobra: cmd.MarkFlagRequired(flag) (or Persistent)
        Cobra-->>flags_pkg: success/error
    end
    flags_pkg-->>CLI_Command: Combined error (if any)
    CLI_Command->>CLI_Command: Print error and exit if needed
Loading

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.

❤️ Share
🪧 Tips

Chat

There are 3 ways to chat with CodeRabbit:

  • Review comments: Directly reply to a review comment made by CodeRabbit. Example:
    • I pushed a fix in commit <commit_id>, please review it.
    • Explain this complex logic.
    • Open a follow-up GitHub issue for this discussion.
  • Files and specific lines of code (under the "Files changed" tab): Tag @coderabbitai in a new review comment at the desired location with your query. Examples:
    • @coderabbitai explain this code block.
    • @coderabbitai modularize this function.
  • PR comments: Tag @coderabbitai in a new PR comment to ask questions about the PR branch. For the best results, please provide a very specific query, as very limited context is provided in this mode. Examples:
    • @coderabbitai gather interesting stats about this repository and render them as a table. Additionally, render a pie chart showing the language distribution in the codebase.
    • @coderabbitai read src/utils.ts and explain its main purpose.
    • @coderabbitai read the files in the src/scheduler package and generate a class diagram using mermaid and a README in the markdown format.
    • @coderabbitai help me debug CodeRabbit configuration file.

Support

Need help? Create a ticket on our support page for assistance with any issues or questions.

Note: Be mindful of the bot's finite context window. It's strongly recommended to break down tasks such as reading entire modules into smaller chunks. For a focused discussion, use review comments to chat about specific files and their changes, instead of using the PR comments.

CodeRabbit Commands (Invoked using PR comments)

  • @coderabbitai pause to pause the reviews on a PR.
  • @coderabbitai resume to resume the paused reviews.
  • @coderabbitai review to trigger an incremental review. This is useful when automatic reviews are disabled for the repository.
  • @coderabbitai full review to do a full review from scratch and review all the files again.
  • @coderabbitai summary to regenerate the summary of the PR.
  • @coderabbitai generate docstrings to generate docstrings for this PR.
  • @coderabbitai generate sequence diagram to generate a sequence diagram of the changes in this PR.
  • @coderabbitai resolve resolve all the CodeRabbit review comments.
  • @coderabbitai configuration to show the current CodeRabbit configuration for the repository.
  • @coderabbitai help to get help.

Other keywords and placeholders

  • Add @coderabbitai ignore anywhere in the PR description to prevent this PR from being reviewed.
  • Add @coderabbitai summary to generate the high-level summary at a specific location in the PR description.
  • Add @coderabbitai anywhere in the PR title to generate the title automatically.

CodeRabbit Configuration File (.coderabbit.yaml)

  • You can programmatically configure CodeRabbit by adding a .coderabbit.yaml file to the root of your repository.
  • Please see the configuration documentation for more information.
  • If your editor has YAML language server enabled, you can add the path at the top of this file to enable auto-completion and validation: # yaml-language-server: $schema=https://coderabbit.ai/integrations/schema.v2.json

Documentation and Community

  • Visit our Documentation for detailed information on how to use CodeRabbit.
  • Join our Discord Community to get help, request features, and share feedback.
  • Follow us on X/Twitter for updates and announcements.

Copilot

This comment was marked as outdated.

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1

🧹 Nitpick comments (1)
cmd/model/test.go (1)

103-106: Fix inconsistent location parameter.

The location parameter should match the actual file path for consistency with other command files.

Apply this fix:

-	if err := flags.SetFlagRequired(testCmd, "tests", "cmd/models/test", false); err != nil {
+	if err := flags.SetFlagRequired(testCmd, "tests", "cmd/model/test", false); err != nil {
📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between cf8b50b and 4ce74a1.

📒 Files selected for processing (11)
  • cmd/model/get.go (2 hunks)
  • cmd/model/list.go (2 hunks)
  • cmd/model/test.go (2 hunks)
  • cmd/model/write.go (2 hunks)
  • cmd/query/list-users.go (2 hunks)
  • cmd/store/delete.go (2 hunks)
  • cmd/store/export.go (2 hunks)
  • cmd/store/get.go (2 hunks)
  • cmd/store/import.go (2 hunks)
  • internal/flags/flags.go (1 hunks)
  • internal/flags/flags_test.go (1 hunks)
🧰 Additional context used
🧬 Code Graph Analysis (10)
cmd/model/test.go (1)
internal/flags/flags.go (1)
  • SetFlagRequired (17-29)
cmd/model/write.go (1)
internal/flags/flags.go (1)
  • SetFlagRequired (17-29)
cmd/store/get.go (1)
internal/flags/flags.go (1)
  • SetFlagRequired (17-29)
cmd/store/delete.go (1)
internal/flags/flags.go (1)
  • SetFlagRequired (17-29)
cmd/store/import.go (1)
internal/flags/flags.go (1)
  • SetFlagRequired (17-29)
cmd/model/get.go (1)
internal/flags/flags.go (1)
  • SetFlagRequired (17-29)
cmd/query/list-users.go (1)
internal/flags/flags.go (1)
  • SetFlagsRequired (34-44)
cmd/store/export.go (1)
internal/flags/flags.go (1)
  • SetFlagRequired (17-29)
cmd/model/list.go (1)
internal/flags/flags.go (1)
  • SetFlagRequired (17-29)
internal/flags/flags_test.go (2)
internal/flags/flags.go (2)
  • SetFlagRequired (17-29)
  • SetFlagsRequired (34-44)
internal/slices/contains.go (1)
  • Contains (22-30)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (5)
  • GitHub Check: Test Release Process
  • GitHub Check: Tests
  • GitHub Check: Lints
  • GitHub Check: Analyze (actions)
  • GitHub Check: Analyze (go)
🔇 Additional comments (22)
internal/flags/flags.go (3)

1-11: LGTM! Clean package structure.

The package documentation, imports, and constants are well-organized and follow Go best practices.


17-29: LGTM! Solid implementation of single flag requirement.

The function correctly handles both persistent and non-persistent flags with proper error wrapping and contextual information.


34-43: Fix potential nil error entries in error slice.

The SetFlagsRequired function pre-allocates an error slice with the same length as the flags slice, but only populates entries when errors occur. This means errors.Join() will receive nil entries, which could lead to unexpected behavior.

Apply this fix to only include actual errors:

func SetFlagsRequired(cmd *cobra.Command, flags []string, location string, isPersistent bool) error {
-	flagErrors := make([]error, len(flags))
+	var flagErrors []error

	for i, flag := range flags {
		if err := SetFlagRequired(cmd, flag, location, isPersistent); err != nil {
-			flagErrors[i] = err
+			flagErrors = append(flagErrors, err)
		}
	}

	return errors.Join(flagErrors...)
}

Likely an incorrect or invalid review comment.

cmd/store/export.go (2)

33-33: LGTM! Proper import addition.

The flags package import is correctly added and aligns with the refactoring objective.


197-200: LGTM! Correct usage of the flags helper.

The replacement of direct MarkFlagRequired call with flags.SetFlagRequired is implemented correctly with proper parameters and consistent error handling.

cmd/store/get.go (2)

29-29: LGTM! Proper import addition.

The flags package import is correctly added and follows the established pattern.


69-72: LGTM! Correct implementation of the flags helper.

The replacement correctly uses flags.SetFlagRequired with appropriate parameters and maintains consistent error handling.

cmd/model/test.go (1)

27-27: LGTM! Proper import addition.

The flags package import is correctly added and follows the established pattern.

cmd/store/delete.go (2)

28-28: LGTM! Proper import addition.

The flags package import is correctly added and maintains consistency with the refactoring effort.


76-79: LGTM! Correct implementation of the flags helper.

The replacement properly uses flags.SetFlagRequired with correct parameters and maintains the established error handling pattern.

cmd/model/write.go (1)

30-30: Good addition of the flags import.

The import correctly includes the new internal flags package to support the centralized flag handling approach.

cmd/model/list.go (2)

30-30: Good addition of the flags import.

The import correctly includes the new internal flags package to support the centralized flag handling approach.


116-119: Excellent refactoring to use the centralized flags utility.

The implementation correctly:

  • Uses the matching flag name "store-id" from the flag definition
  • Provides appropriate location context for error messages
  • Maintains consistent error handling with direct printing and exit behavior
cmd/store/import.go (2)

37-37: Good addition of the flags import.

The import correctly includes the new internal flags package to support the centralized flag handling approach.


343-346: Excellent refactoring to use the centralized flags utility.

The implementation correctly:

  • Uses the matching flag name "file" from the flag definition
  • Provides appropriate location context for error messages
  • Maintains consistent error handling with direct printing and exit behavior
cmd/model/get.go (2)

27-27: Good addition of the flags import.

The import correctly includes the new internal flags package to support the centralized flag handling approach.


81-84: Excellent refactoring to use the centralized flags utility.

The implementation correctly:

  • Uses the matching flag name "store-id" from the flag definition
  • Provides appropriate location context for error messages
  • Maintains consistent error handling with direct printing and exit behavior
cmd/query/list-users.go (2)

30-30: Good addition of the flags import.

The import correctly includes the new internal flags package to support the centralized flag handling approach.


142-145: Excellent use of the batch flag setting utility.

The implementation correctly:

  • Uses SetFlagsRequired to efficiently set multiple flags as required in a single call
  • All flag names match their definitions ("object", "relation", "user-filter")
  • Provides appropriate location context for error messages
  • Maintains consistent error handling with direct printing and exit behavior

This demonstrates a clean improvement over the previous approach of multiple individual MarkFlagRequired calls.

internal/flags/flags_test.go (3)

1-150: Excellent comprehensive test coverage!

This test file provides thorough coverage of the flags package functionality with well-structured test cases that validate:

Success scenarios: Both persistent and non-persistent flag operations
Error handling: Missing flags with proper error message validation
Edge cases: Empty/nil slices, mixed flag types
Batch operations: Multiple flag processing with partial failures
Error formatting: Consistent error message structure validation

The test naming conventions are clear and descriptive, following Go best practices. The use of testify assertions ensures robust validation, and the test structure is consistent throughout.


137-149: Well-designed test for mixed flag type scenario.

This test effectively validates the behavior when trying to mark a persistent flag as required using the non-persistent method, which should fail. The assertions correctly verify that:

  • Only the persistent flag operation fails
  • The regular flag operation succeeds
  • Error messages contain the expected context

This edge case testing demonstrates thorough understanding of the underlying Cobra flag mechanics.


123-135: Thorough validation of error joining behavior.

The test effectively validates that errors.Join properly combines multiple errors when all flags fail. The loop-based assertion ensures each individual error is present in the combined error message, which is crucial for debugging multiple flag issues.

@rhamzeh rhamzeh force-pushed the chore/introduce-flags-helper-for-consistency branch from 4ce74a1 to 22a8966 Compare July 8, 2025 19:48
@rhamzeh rhamzeh requested a review from Copilot July 9, 2025 20:25
Copy link

@Copilot Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull Request Overview

This PR centralizes flag requirement enforcement by introducing a helper in internal/flags and replaces direct MarkFlagRequired/MarkPersistentFlagRequired calls across commands for consistency.

  • Adds SetFlagRequired and SetFlagsRequired functions (with tests) to handle required flags and error formatting.
  • Updates multiple cmd/* files to use the new helpers instead of raw Cobra methods.
  • Adjusts .golangci.yaml to allow the Cobra import for the new package.

Reviewed Changes

Copilot reviewed 14 out of 14 changed files in this pull request and generated 1 comment.

Show a summary per file
File Description
internal/flags/flags.go New helper functions for marking flags required.
internal/flags/flags_test.go Tests covering various flag-required scenarios.
cmd/tuple/tuple.go Replaced inline flag requirement with helper.
cmd/store/import.go Switched to helper for file flag.
cmd/store/get.go Switched to helper for store-id flag.
cmd/store/export.go Switched to helper for store-id flag.
cmd/store/delete.go Switched to helper for store-id flag.
cmd/query/query.go Switched to helper for persistent store-id.
cmd/query/list-users.go Consolidated three flag requirements into helper.
cmd/model/write.go Switched to helper for store-id flag.
cmd/model/test.go Switched to helper for tests flag.
cmd/model/list.go Switched to helper for store-id flag.
cmd/model/get.go Switched to helper for store-id flag.
.golangci.yaml Allowed github.com/spf13/cobra in lint config.
Comments suppressed due to low confidence (2)

internal/flags/flags_test.go:68

  • [nitpick] It would be valuable to add a test that checks errors.Is(err, ErrFlagRequired) to ensure the helper properly wraps the original error for downstream error inspection.
	assert.Contains(t, err.Error(), expectedPrefix)

internal/flags/flags.go:28

  • fmt.Errorf supports only one %w verb. Having two %w directives will cause a compile error. Consider using %v or %s for the first error or use errors.Join to combine errors properly.
	return fmt.Errorf("%w - (flag: %s, file: %s): %w", ErrFlagRequired, flag, location, err)

if err != nil { //nolint:wsl
fmt.Print(err)
if err := flags.SetFlagRequired(TupleCmd, "store-id", "cmd/tuple/tuple", true); err != nil {
fmt.Printf("%v\n", err)
Copy link
Preview

Copilot AI Jul 9, 2025

Choose a reason for hiding this comment

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

[nitpick] Error messages should be written to stderr rather than stdout. Consider using fmt.Fprintln(os.Stderr, err) to ensure errors go to the correct output stream.

Suggested change
fmt.Printf("%v\n", err)
fmt.Fprintln(os.Stderr, err)

Copilot uses AI. Check for mistakes.

@rhamzeh rhamzeh marked this pull request as draft July 10, 2025 12:37
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