Skip to content

Conversation

@AgNess-G
Copy link

@AgNess-G AgNess-G commented Nov 21, 2025

this is to resolve - #4443

Pull Request Checklist

Please ensure your pull request meets the following requirements:

  • Open your pull request against the master branch.
  • All tests pass in available continuous integration systems (e.g., GitHub Actions).
  • Tests are added or modified as needed to cover code changes.
  • If the pull request introduces a new feature, the feature is documented in the docs/doc.md.

Thank you for contributing!

@appleboy appleboy requested review from appleboy and Copilot November 23, 2025 04:18
Copilot finished reviewing on behalf of appleboy November 23, 2025 04:22
Copy link
Contributor

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 pull request addresses path traversal vulnerabilities (PRISMA-2022-0393 and PRISMA-2022-0394) by preventing double URL decoding of path and wildcard parameters. The fix ensures that URL-encoded parameters are only decoded once, preventing attackers from using double-encoded sequences to bypass security checks.

Key Changes:

  • Modified URL unescaping logic to only decode values containing % or + characters, preventing unnecessary processing
  • Refactored countParams and countSections to use bytes.Count with zero-copy string-to-bytes conversion
  • Added comprehensive security test cases for both path parameters and wildcard parameters with various encoding scenarios

Reviewed changes

Copilot reviewed 2 out of 2 changed files in this pull request and generated 13 comments.

File Description
tree.go Updated unescape logic to prevent double-decoding; refactored count functions to remove safeUint16 helper and use bytes operations
tree_test.go Added TestSecureParameterHandling for security regression testing; removed unused imports (fmt, regexp); removed 16 existing test functions reducing overall test coverage

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

tree_test.go Outdated

// Triple encoding - should only decode once
{"/info/user%25252Fprofile", false, "/info/:user", Params{Param{Key: "user", Value: "user%252Fprofile"}}},

Copy link

Copilot AI Nov 23, 2025

Choose a reason for hiding this comment

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

[nitpick] Trailing whitespace detected. Consider removing the trailing whitespace for code cleanliness.

Suggested change

Copilot uses AI. Check for mistakes.
tree_test.go Outdated

// Mixed encoding - should only decode once
{"/info/%2Fuser%252Fprofile", false, "/info/:user", Params{Param{Key: "user", Value: "/user%2Fprofile"}}},

Copy link

Copilot AI Nov 23, 2025

Choose a reason for hiding this comment

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

[nitpick] Trailing whitespace detected. Consider removing the trailing whitespace for code cleanliness.

Suggested change

Copilot uses AI. Check for mistakes.

// No encoding - should pass through unchanged
{"/info/user", false, "/info/:user", Params{Param{Key: "user", Value: "user"}}},
}, unescape)
Copy link

Copilot AI Nov 23, 2025

Choose a reason for hiding this comment

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

[nitpick] Trailing whitespace detected. Consider removing the trailing whitespace for code cleanliness.

Copilot uses AI. Check for mistakes.
tree_test.go Outdated
checkRequests(t, tree, testRequests{
// Normal case - single encoding works as expected
{"/files/path%2Fto%2Ffile.txt", false, "/files/*filepath", Params{Param{Key: "filepath", Value: "/path/to/file.txt"}}},

Copy link

Copilot AI Nov 23, 2025

Choose a reason for hiding this comment

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

[nitpick] Trailing whitespace detected. Consider removing the trailing whitespace for code cleanliness.

Copilot uses AI. Check for mistakes.
tree_test.go Outdated

// Double encoding - should only decode once
{"/files/path%252Fto%252Ffile.txt", false, "/files/*filepath", Params{Param{Key: "filepath", Value: "/path%2Fto%2Ffile.txt"}}},

Copy link

Copilot AI Nov 23, 2025

Choose a reason for hiding this comment

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

[nitpick] Trailing whitespace detected. Consider removing the trailing whitespace for code cleanliness.

Copilot uses AI. Check for mistakes.
tree_test.go Outdated

// Double encoding - should only decode once
{"/info/user%252Fprofile", false, "/info/:user", Params{Param{Key: "user", Value: "user%2Fprofile"}}},

Copy link

Copilot AI Nov 23, 2025

Choose a reason for hiding this comment

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

[nitpick] Trailing whitespace detected. Consider removing the trailing whitespace for code cleanliness.

Copilot uses AI. Check for mistakes.
tree_test.go Outdated

// Triple encoding - should only decode once
{"/files/path%25252Fto%25252Ffile.txt", false, "/files/*filepath", Params{Param{Key: "filepath", Value: "/path%252Fto%252Ffile.txt"}}},

Copy link

Copilot AI Nov 23, 2025

Choose a reason for hiding this comment

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

[nitpick] Trailing whitespace detected. Consider removing the trailing whitespace for code cleanliness.

Copilot uses AI. Check for mistakes.
tree_test.go Outdated

// Mixed encoding - should only decode once
{"/files/%2Fpath%252Fto%2Ffile.txt", false, "/files/*filepath", Params{Param{Key: "filepath", Value: "//path%2Fto/file.txt"}}},

Copy link

Copilot AI Nov 23, 2025

Choose a reason for hiding this comment

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

[nitpick] Trailing whitespace detected. Consider removing the trailing whitespace for code cleanliness.

Copilot uses AI. Check for mistakes.
tree.go Outdated
Comment on lines 580 to 587
if unescape {
if v, err := url.QueryUnescape(path); err == nil {
val = v
// Only unescape if the value contains percent-encoded characters or plus signs
// This prevents double unescaping and potential path traversal
if strings.ContainsAny(path, "%+") {
if v, err := url.QueryUnescape(path); err == nil {
val = v
}
}
Copy link

Copilot AI Nov 23, 2025

Choose a reason for hiding this comment

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

The same unescape logic is duplicated in two places (param and catchAll cases). Consider extracting this into a helper function to reduce code duplication and make maintenance easier.

Suggested refactoring:

func unescapeValue(val string, unescape bool) string {
	if unescape && strings.ContainsAny(val, "%+") {
		if v, err := url.QueryUnescape(val); err == nil {
			return v
		}
	}
	return val
}

Then use it in both locations:

val := unescapeValue(path[:end], unescape)

Copilot uses AI. Check for mistakes.
tree.go Outdated
func countSections(path string) uint16 {
return safeUint16(strings.Count(path, "/"))
s := bytesconv.StringToBytes(path)
return uint16(bytes.Count(s, strSlash))
Copy link

Copilot AI Nov 23, 2025

Choose a reason for hiding this comment

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

Similar to countParams, this function is now missing overflow protection that was previously provided by safeUint16.

If a path has more than 65535 slashes, the cast to uint16 will silently overflow, potentially causing incorrect behavior in the routing logic.

Suggested change
return uint16(bytes.Count(s, strSlash))
count := bytes.Count(s, strSlash)
if count > 0xFFFF {
count = 0xFFFF
}
return uint16(count)

Copilot uses AI. Check for mistakes.
@codecov
Copy link

codecov bot commented Nov 24, 2025

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 96.36%. Comparing base (3dc1cd6) to head (f8b6b4a).
⚠️ Report is 220 commits behind head on master.

Additional details and impacted files
@@            Coverage Diff             @@
##           master    #4447      +/-   ##
==========================================
- Coverage   99.21%   96.36%   -2.85%     
==========================================
  Files          42       44       +2     
  Lines        3182     2975     -207     
==========================================
- Hits         3157     2867     -290     
- Misses         17       87      +70     
- Partials        8       21      +13     
Flag Coverage Δ
?
--ldflags="-checklinkname=0" -tags sonic 96.34% <100.00%> (?)
-tags go_json 96.27% <100.00%> (?)
-tags nomsgpack 96.31% <100.00%> (?)
go-1.18 ?
go-1.19 ?
go-1.20 ?
go-1.21 ?
go-1.24 96.36% <100.00%> (?)
go-1.25 96.36% <100.00%> (?)
macos-latest 96.36% <100.00%> (-2.85%) ⬇️
ubuntu-latest 96.36% <100.00%> (-2.85%) ⬇️

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.

@AgNess-G
Copy link
Author

AgNess-G commented Nov 25, 2025

@appleboy Can you please help me understand the reason of these pre-check failures?

@AgNess-G
Copy link
Author

@appleboy can you take a look please

@appleboy
Copy link
Member

@Agnes-George Please revert the changes to gin.yml

@AgNess-G
Copy link
Author

AgNess-G commented Dec 2, 2025

@appleboy can you take a look please

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.

3 participants