Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

✨ (v3) feature: Implement new generic functions: Params, Get and Convert #2850

Merged
merged 53 commits into from
Mar 18, 2024

Conversation

dozheiny
Copy link
Contributor

@dozheiny dozheiny commented Feb 11, 2024

Description

This pull request introduces new features, Params, Get and Convert generic functions.

With the Params and Get generic functions you can parse your parameters and headers in different data types.
Also With the Convert function, you can parse your data types in what type you want, like uuid.UUID.

TODO:

  • Implement Params generic function and rewrite ctx.Params
  • Implement Get generic function and rewrite ctx.Get
  • Implement Convert generic function

This pull request will be fixed #2758

Summary by CodeRabbit

  • New Features

    • Introduced generic handling for HTTP request headers, route parameters, and query parameters to improve flexibility and usability.
    • Added a new conversion utility to safely convert string values to specified types, enhancing data handling capabilities.
  • Refactor

    • Generalized functions and type parameters across the codebase for more versatile operations.
  • Documentation

    • Updated documentation to reflect new generic approaches for parameter handling and value conversion, providing clearer guidance on utilizing these features.

@gaby
Copy link
Member

gaby commented Feb 11, 2024

What's the benchmark difference between using this and the previous implementation?

@dozheiny
Copy link
Contributor Author

What's the benchmark difference between using this and the previous implementation?

I'll implement this.

@dozheiny dozheiny changed the title 🔥 [V3] Params Generic function 🔥 (v3) feature: Implement Params generic function Feb 11, 2024
@dozheiny dozheiny changed the title 🔥 (v3) feature: Implement Params generic function ✨ (v3) feature: Implement Params generic function Feb 11, 2024
Copy link
Member

@sixcolors sixcolors left a comment

Choose a reason for hiding this comment

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

otherwise LGTM

ctx_test.go Outdated Show resolved Hide resolved
@dozheiny dozheiny requested a review from a team as a code owner February 11, 2024 21:17
@gaby
Copy link
Member

gaby commented Feb 11, 2024

Wait for #2842 to get merged. I suspect a lot of warnings will pop up

@dozheiny
Copy link
Contributor Author

Wait for #2842 to get merged. I suspect a lot of warnings will pop up

Ok. I'll wait.

@ReneWerner87 ReneWerner87 linked an issue Feb 12, 2024 that may be closed by this pull request
3 tasks
Copy link
Member

@ReneWerner87 ReneWerner87 left a comment

Choose a reason for hiding this comment

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

thx, some adjustments needed

docs/api/ctx.md Outdated Show resolved Hide resolved
docs/api/ctx.md Outdated Show resolved Hide resolved
docs/api/ctx.md Outdated Show resolved Hide resolved
docs/api/ctx.md Outdated Show resolved Hide resolved
docs/api/ctx.md Outdated Show resolved Hide resolved
docs/api/ctx.md Outdated Show resolved Hide resolved
ctx_test.go Outdated Show resolved Hide resolved
ctx_test.go Outdated Show resolved Hide resolved
utils.go Outdated Show resolved Hide resolved
@dozheiny dozheiny changed the title ✨ (v3) feature: Implement Params generic function ✨ (v3) feature: Implement Params and Get generic functions Feb 13, 2024
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.

Review Status

Actionable comments generated: 1

Configuration used: CodeRabbit UI

Commits Files that changed from the base of the PR and between b02cae9 and 0ba4911.
Files selected for processing (1)
  • ctx_test.go (6 hunks)
Files not summarized due to errors (1)
  • ctx_test.go: Error: Message exceeds token limit

Copy link

codecov bot commented Mar 5, 2024

Codecov Report

Attention: Patch coverage is 84.28571% with 11 lines in your changes are missing coverage. Please review.

Project coverage is 82.73%. Comparing base (82070cb) to head (57d29b7).

Files Patch % Lines
ctx.go 56.25% 7 Missing ⚠️
utils.go 92.59% 4 Missing ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##             main    #2850      +/-   ##
==========================================
- Coverage   82.84%   82.73%   -0.12%     
==========================================
  Files         116      116              
  Lines        8377     8385       +8     
==========================================
- Hits         6940     6937       -3     
- Misses       1098     1108      +10     
- Partials      339      340       +1     
Flag Coverage Δ
unittests 82.73% <84.28%> (-0.12%) ⬇️

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.

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.

Review Status

Actionable comments generated: 3

Configuration used: CodeRabbit UI

Commits Files that changed from the base of the PR and between 0ba4911 and b70c6b9.
Files selected for processing (1)
  • docs/api/ctx.md (4 hunks)

docs/api/ctx.md Outdated Show resolved Hide resolved
docs/api/ctx.md Show resolved Hide resolved
ctx.go Outdated Show resolved Hide resolved
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.

Review Status

Actionable comments generated: 4

Configuration used: CodeRabbit UI

Commits Files that changed from the base of the PR and between b70c6b9 and 07b2e76.
Files selected for processing (1)
  • ctx.go (4 hunks)

ctx.go Show resolved Hide resolved
ctx.go Show resolved Hide resolved
ctx.go Show resolved Hide resolved
ctx.go Show resolved Hide resolved
@ReneWerner87
Copy link
Member

@gaby @efectn @nickajacks1
can you all check again if there is still something open from your side
I have closed some hints from coderabbit to keep the overview

otherwise leave an approval so i can merge in the next days

@nickajacks1
Copy link
Member

I'll try to do a final look over this weekend

Copy link
Member

@nickajacks1 nickajacks1 left a comment

Choose a reason for hiding this comment

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

Nothing in particular stands out

docs/api/ctx.md Outdated Show resolved Hide resolved
@efectn efectn added this to the v3 milestone Mar 17, 2024
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.

Review Status

Actionable comments generated: 1

Configuration used: CodeRabbit UI

Commits Files that changed from the base of the PR and between 07b2e76 and 2f44dc1.
Files selected for processing (1)
  • ctx_test.go (6 hunks)
Files not summarized due to errors (1)
  • ctx_test.go: Error: Message exceeds token limit

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.

Review Status

Actionable comments generated: 2

Configuration used: CodeRabbit UI

Commits Files that changed from the base of the PR and between 2f44dc1 and 0230b4e.
Files selected for processing (1)
  • docs/api/ctx.md (4 hunks)

Comment on lines +1201 to +1226
In certain scenarios, it can be useful to have an alternative approach to handle different types of parameters, not
just strings. This can be achieved using a generic Query function known as `Params[V GenericType](c Ctx, key string, defaultValue ...V) V`.
This function is capable of parsing a query string and returning a value of a type that is assumed and specified by `V GenericType`.

```go title="Signature"
func (c Ctx) ParamsInt(key string) (int, error)
func Params[v GenericType](c Ctx, key string, default value ...V) V
```

```go title="Example"
// GET http://example.com/user/123
app.Get("/user/:id", func(c fiber.Ctx) error {
id, err := c.ParamsInt("id") // int 123 and no error

// ...
// Get http://example.com/user/114
app.Get("/user/:id", func(c fiber.Ctx) error{
fiber.Params[string](c, "id") // returns "114" as string.
fiber.Params[int](c, "id") // returns 114 as integer
fiber.Params[string](c, "number") // retunrs "" (default string type)
fiber.Params[int](c, "number") // returns 0 (default integer value type)
})

```

This method is equivalent of using `atoi` with ctx.Params
The generic Params function supports returning the following data types based on V GenericType:
- Integer: int, int8, int16, int32, int64
- Unsigned integer: uint, uint8, uint16, uint32, uint64
- Floating-point numbers: float32, float64
- Boolean: bool
- String: string
- Byte array: []byte
Copy link
Contributor

Choose a reason for hiding this comment

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

The introduction of generic versions for the Params and Query methods is a significant enhancement. However, it's crucial to ensure that the documentation clearly explains how to use these generic versions, including detailed examples for various data types. Additionally, consider adding a note on potential pitfalls or common mistakes to avoid when using generics in this context.

Would you like me to help with adding examples or notes on common pitfalls?

Comment on lines +2207 to +2228
## Convert
Converts a string value to a specified type, handling errors and optional default values.
This function simplifies the conversion process by encapsulating error handling and the management of default values, making your code cleaner and more consistent.
```go title="Signature"
func Convert[T any](value string, convertor func(string) (T, error), defaultValue ...T) (*T, error)
```

```go title="Example"
// GET http://example.com/id/bb70ab33-d455-4a03-8d78-d3c1dacae9ff
app.Get("/id/:id", func(c fiber.Ctx) error {
fiber.Convert(c.Params("id"), uuid.Parse) // UUID(bb70ab33-d455-4a03-8d78-d3c1dacae9ff), nil


// GET http://example.com/search?id=65f6f54221fb90e6a6b76db7
app.Get("/search", func(c fiber.Ctx) error) {
fiber.Convert(c.Query("id"), mongo.ParseObjectID) // objectid(65f6f54221fb90e6a6b76db7), nil
fiber.Convert(c.Query("id"), uuid.Parse) // uuid.Nil, error(cannot parse given uuid)
fiber.Convert(c.Query("id"), uuid.Parse, mongo.NewObjectID) // new object id generated and return nil as error.
}

// ...
})
Copy link
Contributor

Choose a reason for hiding this comment

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

The Convert function is a valuable addition, simplifying the conversion of string values to specified types with error handling. It's important to ensure that the documentation for this function is clear and includes examples of its usage in different scenarios. This will help users understand how to effectively utilize the Convert function in their applications.

Would you like assistance in drafting examples or additional documentation for the Convert function?

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.

Review Status

Actionable comments generated: 1

Configuration used: CodeRabbit UI

Commits Files that changed from the base of the PR and between 0230b4e and 57d29b7.
Files selected for processing (1)
  • ctx_test.go (6 hunks)
Files not summarized due to errors (1)
  • ctx_test.go: Error: Message exceeds token limit

Comment on lines +4862 to +4905
func Test_genericParseTypeUint8s(t *testing.T) {
t.Parallel()
type genericTypes[v GenericType] struct {
value v
str string
}

uint8s := []genericTypes[uint8]{
{
value: uint8(0),
str: "0",
},
{
value: uint8(1),
str: "1",
},
{
value: uint8(2),
str: "2",
},
{
value: uint8(3),
str: "3",
},
{
value: uint8(4),
str: "4",
},
{
value: uint8(math.MaxUint8),
str: strconv.Itoa(math.MaxUint8),
},
}

for _, test := range uint8s {
var v uint8
tt := test
t.Run("test_genericParseTypeUint8s", func(t *testing.T) {
t.Parallel()
require.Equal(t, tt.value, genericParseType(tt.str, v))
require.Equal(t, tt.value, genericParseType[uint8](tt.str, v))
})
}
}
Copy link
Contributor

Choose a reason for hiding this comment

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

The test function Test_genericParseTypeUint8s is well-structured and tests the conversion of strings to uint8 values. It's recommended to include edge cases such as the minimum and maximum values for uint8.

uint8s = append(uint8s, genericTypes[uint8]{value: math.MaxUint8, str: strconv.Itoa(math.MaxUint8)})
uint8s = append(uint8s, genericTypes[uint8]{value: 0, str: strconv.Itoa(0)})

@ReneWerner87 ReneWerner87 merged commit 43dc60f into gofiber:main Mar 18, 2024
13 of 15 checks passed
@dozheiny dozheiny deleted the v3-params branch March 18, 2024 14:16
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.

🚀 [Feature]: Implement Generic APIs for Enhanced Variable Type
6 participants