Skip to content

♻️ Refactor: validate constraint by bit operation#3963

Merged
ReneWerner87 merged 1 commit intogofiber:mainfrom
ksw2000:refact-validate-constraint
Dec 25, 2025
Merged

♻️ Refactor: validate constraint by bit operation#3963
ReneWerner87 merged 1 commit intogofiber:mainfrom
ksw2000:refact-validate-constraint

Conversation

@ksw2000
Copy link
Member

@ksw2000 ksw2000 commented Dec 24, 2025

Description

Using bit operations to validate constants is more readable than using a switch statement.

Type of change

  • Code consistency (non-breaking change which improves code reliability and robustness)

Checklist

Before you submit your pull request, please make sure you meet these requirements:

  • Followed the inspiration of the Express.js framework for new functionalities, making them similar in usage.
  • Conducted a self-review of the code and provided comments for complex or critical parts.
  • Updated the documentation in the /docs/ directory for Fiber's documentation.
  • Added or updated unit tests to validate the effectiveness of the changes or new features.
  • Ensured that new and existing unit tests pass locally with the changes.
  • Verified that any new dependencies are essential and have been agreed upon by the maintainers/community.
  • Aimed for optimal performance with minimal allocations in the new code.
  • Provided benchmarks for the new code to analyze and improve upon.

@ksw2000 ksw2000 requested a review from a team as a code owner December 24, 2025 03:40
@coderabbitai
Copy link
Contributor

coderabbitai bot commented Dec 24, 2025

Walkthrough

The path.go file undergoes a type system refactoring for constraint handling. The TypeConstraint type is changed from int16 to uint16, constraint encoding shifts from sequential iota to bit-flag representation, and two new composite constraint masks are introduced to centralize data-length validation logic.

Changes

Cohort / File(s) Summary
Constraint Type & Encoding
path.go
TypeConstraint changed from int16 to uint16; noConstraint refactored from iota-based (iota + 1) to bit-flag encoding (1 << iota); enables bitwise operations for constraint validation
Composite Constraint Masks
path.go
New constants needOneData (OR-combined from minLenConstraint, maxLenConstraint, lenConstraint, minConstraint, maxConstraint, datetimeConstraint, regexConstraint) and needTwoData (OR-combined from betweenLenConstraint, rangeConstraint) introduced to group constraints by required data item counts
Validation Logic Refactoring
path.go
Constraint.CheckConstraint method refactored to use bitwise mask checks (needOneData and needTwoData) for data-length validation before the existing switch statement, centralizing prerequisite checks while preserving existing constraint verification logic

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

Poem

🐰 Bits aligned in binary grace,
Constraints dance in flag-space,
Masks of data, clean and tight—
One or two, the logic's right!
From signed depths to unsigned height,
Path.go sparkles, pure delight! ✨

Pre-merge checks and finishing touches

❌ Failed checks (1 warning)
Check name Status Explanation Resolution
Description check ⚠️ Warning The description covers the motivation and includes a relevant type-of-change selection, but omits the 'Changes introduced' section which is a required template component. Add a 'Changes introduced' section detailing what was refactored, or at minimum document the structural changes made to the constraint validation logic.
✅ Passed checks (2 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly describes the main refactoring change: replacing switch-statement validation with bit operations for constraint checking.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment

📜 Recent review details

Configuration used: Repository UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 032ff5f and f82130d.

📒 Files selected for processing (1)
  • path.go
🧰 Additional context used
📓 Path-based instructions (1)
**/*.go

📄 CodeRabbit inference engine (AGENTS.md)

Prefer github.com/gofiber/utils/v2 helpers (for example, utils.Trim) when performing common operations such as string manipulation, whenever it is practical and appropriate for the surrounding code

Files:

  • path.go
⏰ 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: unit (1.25.x, windows-latest)
  • GitHub Check: unit (1.25.x, macos-latest)
  • GitHub Check: repeated
  • GitHub Check: lint
  • GitHub Check: Compare
🔇 Additional comments (4)
path.go (4)

72-72: LGTM! Appropriate type for bit flags.

Changing from int16 to uint16 is correct for bit-flag encoding since negative values are not needed and all 16 bits are available for flags.


98-113: LGTM! Correct bit-flag encoding.

The shift from sequential iota to 1 << iota correctly implements bit-flag encoding, giving each constraint a unique bit position for efficient bitwise categorization.


115-118: LGTM! Accurate constraint categorization.

The bitmask constants correctly categorize all constraints by their data requirements:

  • needOneData: All 7 constraints requiring a single data element
  • needTwoData: Both constraints requiring two data elements

This centralization improves maintainability.


712-719: LGTM! Efficient bitwise validation.

The bitmask-based data validation correctly replaces per-case checks:

  • Uses bitwise AND to test constraint membership in each category
  • Validates minimum data requirements before the switch statement
  • Preserves existing behavior while centralizing validation logic

The refactor successfully improves code maintainability and reduces duplication.


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

Comment @coderabbitai help to get the list of available commands and usage tips.

@gemini-code-assist
Copy link
Contributor

Summary of Changes

Hello @ksw2000, I'm Gemini Code Assist1! I'm currently reviewing this pull request and will post my feedback shortly. In the meantime, here's a summary to help you and other reviewers quickly get up to speed!

This pull request refactors the internal validation mechanism for TypeConstraint parameters. By transitioning from sequential integer IDs to bitwise flags and introducing bitmask constants, the change aims to improve code readability and consistency. The core impact is seen in the CheckConstraint method, where a switch statement for data requirement validation is replaced with more efficient and expressive bitwise operations.

Highlights

  • Type Definition Change: The TypeConstraint type has been updated from int16 to uint16 to better accommodate bitwise operations.
  • Bit Flag Implementation: Constants for TypeConstraint are now initialized using bit shifting (1 << iota), transforming them into distinct bit flags.
  • New Bitmask Constants: Two new constants, needOneData and needTwoData, have been introduced as bitwise combinations to group constraints based on their data requirements.
  • Refactored Validation Logic: The CheckConstraint method's data validation logic has been refactored to replace a switch statement with more concise and efficient bitwise AND operations using the new bitmask constants.

🧠 New Feature in Public Preview: You can now enable Memory to help Gemini Code Assist learn from your team's feedback. This makes future code reviews more consistent and personalized to your project's style. Click here to enable Memory in your admin console.

Using Gemini Code Assist

The full guide for Gemini Code Assist can be found on our documentation page, here are some quick tips.

Invoking Gemini

You can request assistance from Gemini at any point by creating a comment using either /gemini <command> or @gemini-code-assist <command>. Below is a summary of the supported commands on the current page.

Feature Command Description
Code Review /gemini review Performs a code review for the current pull request in its current state.
Pull Request Summary /gemini summary Provides a summary of the current pull request in its current state.
Comment @gemini-code-assist Responds in comments when explicitly tagged, both in pull request comments and review comments.
Help /gemini help Displays a list of available commands.

Customization

To customize Gemini Code Assist for GitHub experience, repository maintainers can create a configuration file and/or provide a custom code review style guide (such as PEP-8 for Python) by creating and adding files to a .gemini/ folder in the base of the repository. Detailed instructions can be found here.

Limitations & Feedback

Gemini Code Assist may make mistakes. Please leave feedback on any instances where its feedback is incorrect or counter productive. You can react with 👍 and 👎 on @gemini-code-assist comments. If you're interested in giving your feedback about your experience with Gemini Code Assist for Github and other Google products, sign up here.

You can also get AI-powered code generation, chat, as well as code reviews directly in the IDE at no cost with the Gemini Code Assist IDE Extension.

Footnotes

  1. Review the Privacy Notices, Generative AI Prohibited Use Policy, Terms of Service, and learn how to configure Gemini Code Assist in GitHub here. Gemini can make mistakes, so double check it and use code with caution.

@ReneWerner87 ReneWerner87 added this to v3 Dec 24, 2025
@ReneWerner87 ReneWerner87 added this to the v3 milestone Dec 24, 2025
@ksw2000 ksw2000 marked this pull request as draft December 24, 2025 03:41
Copy link
Contributor

@gemini-code-assist gemini-code-assist bot left a comment

Choose a reason for hiding this comment

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

Code Review

This pull request refactors the validation of route parameter constraints to use bitwise operations instead of a switch statement. The changes are well-implemented and achieve the goal of improving code readability and maintainability. The use of 1 << iota for defining constraint types and bitmasks for checking data requirements is a clean and efficient approach. The logic is sound and no functional regressions were identified. I have one minor suggestion to improve code style. Overall, this is a solid improvement to the codebase.

@codecov
Copy link

codecov bot commented Dec 24, 2025

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 91.67%. Comparing base (032ff5f) to head (f82130d).
⚠️ Report is 2 commits behind head on main.

Additional details and impacted files
@@            Coverage Diff             @@
##             main    #3963      +/-   ##
==========================================
- Coverage   91.67%   91.67%   -0.01%     
==========================================
  Files         119      119              
  Lines       10177    10173       -4     
==========================================
- Hits         9330     9326       -4     
  Misses        536      536              
  Partials      311      311              
Flag Coverage Δ
unittests 91.67% <100.00%> (-0.01%) ⬇️

Flags with carried forward coverage won't be shown. Click here to find out more.

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

@ksw2000 ksw2000 marked this pull request as ready for review December 24, 2025 03:54
@ReneWerner87
Copy link
Member

@ksw2000 thx, can you share benchmark results in a comment

@ReneWerner87
Copy link
Member

Just noticed that we don't have any separate benchmarks for the constraints,
only the path test cases.
Maybe you could add 1-2 benchmarks so we can see the optimizations in numbers.
Otherwise, I can also merge. I'm sure the bit operators are faster.

@ReneWerner87 ReneWerner87 merged commit 912f27a into gofiber:main Dec 25, 2025
19 checks passed
@github-project-automation github-project-automation bot moved this to Done in v3 Dec 25, 2025
@ksw2000
Copy link
Member Author

ksw2000 commented Dec 30, 2025

goos: linux
goarch: amd64
pkg: github.com/gofiber/fiber/v3
cpu: AMD EPYC 7763 64-Core Processor                
                            │   old.txt   │              new.txt               │
                            │   sec/op    │   sec/op     vs base               │
CheckConstraintReg-2          283.7n ± 3%   283.5n ± 2%       ~ (p=0.945 n=50)
CheckConstraintMinLen-2       16.78n ± 3%   16.29n ± 1%  -2.89% (p=0.004 n=50)
CheckConstraintBetweenLen-2   24.58n ± 4%   24.53n ± 1%       ~ (p=0.746 n=50)
geomean                       48.91n        48.39n       -1.06%

Benchmark shows here

func BenchmarkCheckConstraintReg(b *testing.B) {
	reg, err := regexp.Compile("^[a-z0-9]([a-z0-9-]{1,61}[a-z0-9])?$")
	if err != nil {
		b.Fatal()
	}
	c := Constraint{
		RegexCompiler:     reg,
		Name:              "regex",
		Data:              []string{"^[a-z0-9]([a-z0-9-]{1,61}[a-z0-9])?$"},
		customConstraints: []CustomConstraint{},
		ID:                regexConstraint,
	}
	for i := 0; i < b.N; i++ {
		if c.CheckConstraint("12") {
			b.Fail()
		}
		if !c.CheckConstraint("test") {
			b.Fail()
		}
	}
}

func BenchmarkCheckConstraintMinLen(b *testing.B) {
	c := Constraint{
		RegexCompiler:     nil,
		Name:              "minLen",
		Data:              []string{"5"},
		customConstraints: []CustomConstraint{},
		ID:                minLenConstraint,
	}
	for i := 0; i < b.N; i++ {
		if c.CheckConstraint("123") {
			b.Fail()
		}
		if !c.CheckConstraint("12345") {
			b.Fail()
		}
	}
}

func BenchmarkCheckConstraintBetweenLen(b *testing.B) {
	c := Constraint{
		RegexCompiler:     nil,
		Name:              "betweenLen",
		Data:              []string{"2", "5"},
		customConstraints: []CustomConstraint{},
		ID:                betweenLenConstraint,
	}
	for i := 0; i < b.N; i++ {
		if c.CheckConstraint("e") {
			b.Fail()
		}
		if !c.CheckConstraint("en") {
			b.Fail()
		}
	}
}

@ReneWerner87
Copy link
Member

Thx

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

Status: Done

Development

Successfully merging this pull request may close these issues.

3 participants