Skip to content

Bash skip empty query param fix #3290

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

Merged
merged 3 commits into from
Jul 27, 2019
Merged

Bash skip empty query param fix #3290

merged 3 commits into from
Jul 27, 2019

Conversation

ccouzens
Copy link
Contributor

@ccouzens ccouzens commented Jul 6, 2019

Skip empty params when generating URLs

I have a route with many optional query parameters.
I observed that when they weren't specified, they were still included in
the routes, but without a value or the `&` character to separate them.

Running:
```bash
bash bash_keycloak/client.sh -v --oauth2-bearer "$access_token" --host "$api_host" --dry-run realmUsersGet realm=demo_realm2 [email protected] username=foo
```

Would produce the route:
`http://localhost:8080/auth/admin/realms/demo_realm2/[email protected]=firstName=lastName=max=search=&username=foo`

After this change it produces the route:
`http://localhost:8080/auth/admin/realms/demo_realm2/[email protected]&username=foo`

Note, I haven't written much bash, so I'm not yet used to its
conventions.

PR checklist

  • Read the contribution guidelines.

  • Ran the shell script under ./bin/ to update Petstore sample so that CIs can verify the change.
    Note that ./bin/bash-petstore.sh and ./bin/openapi3/bash-petstore.sh change the same files. I have committed with the output of ./bin/bash-petstore.sh.

  • Filed the PR against the correct branch: master, 4.1.x, 5.0.x. Default: master.

  • Copied the technical committee to review the pull request if your PR is targeting a particular programming language.
    @frol @bkryza @kenjones-cisco

Description of the PR

See above

then
continue
fi;

Copy link
Member

Choose a reason for hiding this comment

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

@ccouzens I notice the following if condition in the code (line 455):

        if [[ "${collection_type}" == "" ]]; then
            local vcount=0
            for qvalue in "${parameter_values[@]}"; do
                if [[ $((vcount++)) -gt 0 ]]; then
                    parameter_value+="&"
                fi
                parameter_value+="${qparam}=${qvalue}"
            done

so what about using the following instead?

if [[ "${operation_parameters[$qparam]}" == "" ]]; then
...
done

Copy link
Contributor Author

@ccouzens ccouzens Jul 13, 2019

Choose a reason for hiding this comment

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

Hi @wing328, thanks for reviewing :)

so what about using the following instead?

if [[ "${operation_parameters[$qparam]}" == "" ]]; then
...
done

I tried it. It has a different behaviour for when a blank parameter is passed in. For example invoking the client with username=

bash bash_keycloak/client.sh -v --oauth2-bearer "$access_token" --host "$api_host" realmUsersGet realm=demo_realm2 [email protected] username=

+isset creates the path /auth/admin/realms/demo_realm2/[email protected]=.

== "" creates the path /auth/admin/realms/demo_realm2/[email protected].

I think they're both wrong.
I think if the parameter is specified but blank, it should be creating the path /auth/admin/realms/demo_realm2/[email protected]&username=.

I'll see if I can update it to get the 3rd behaviour.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

With the commit I've just pushed, it has the 3rd behaviour
(/demo_realm2/[email protected]&username=)

Copy link
Member

Choose a reason for hiding this comment

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

What about using nullable in the spec to determine the desired behavior?
If nullable is set to true, then

/demo_realm2/[email protected]&username=

otherwise (default):

/demo_realm2/[email protected]

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Would nullable be the right thing to look for? Isn't an empty string different to null?

There is a field allowEmptyValue for query params.

Default value is false.

It defaults to not allowing empty parameters.

Use of this property is NOT RECOMMENDED, as it is likely to be removed in a later revision.

I think with that warning it doesn't make sense to implement the property. Presumably when (if) it gets removed query parameters will never be allowed to be empty. I'll make the change to drop empty parameters as you originally suggested.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Copy link
Member

Choose a reason for hiding this comment

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

@ccouzens Looks like the rebase failed.

Can you ping me via https://Gitter.im (ID: wing328) when you've time so that I can help you out and get this PR merged into master soon?

ccouzens added 3 commits July 19, 2019 22:07
I'm about to make a fix to the bash generator. I'm regenerating the
samples in this commit so that the change I make isn't lost amongst
the noise.

#3290
Fix bug where empty query parameters weren't separated by ampersands.

For example, this
```bash
bash bash_keycloak/client.sh -v --oauth2-bearer "$access_token" --host "$api_host" realmUsersGet realm=demo_realm2 [email protected]
```
would generate the path
`/auth/admin/realms/demo_realm2/[email protected]=firstName=lastName=max=search=username=`.

It now puts ampersands around them to make
`/auth/admin/realms/demo_realm2/users?briefRepresentation=&[email protected]&first=&firstName=&lastName=&max=&search=&username=`

Instead of predicting if there is going to be a `parameter_value` ahead of
time, we now put in the ampersand if there is a `parameter_value` and existing
`query_request_part`.

#3290
I have a route with many optional query parameters.
I observed that when they weren't specified, they were still included in
the routes, but without a value.

Running:
```bash
bash bash_keycloak/client.sh -v --header "Authorization: Bearer $access_token" --host "$api_host" --dry-run realmUsersGet realm=demo_realm2 [email protected] username=foo
```

Would produce the route:
`http://localhost:8080/auth/admin/realms/demo_realm2/users?briefRepresentation=&[email protected]&first=&firstName=&lastName=&max=search=&username=foo`

After this change it produces the route:
``http://localhost:8080/auth/admin/realms/demo_realm2/[email protected]&username=foo

---

I discussed with @wing328 in the pull request about if empty values (eg
`username=` should produce an empty query parameter, or if the query
parameter should be removed.

We decided it should remove the query parameter.

#3290

----

The OpenAPI definition I was using:

Using:
https://github.com/ccouzens/keycloak-openapi/blob/master/keycloak/6.0.json
In particular:
```json
      "/{realm}/users": {
        "get": {
          "summary": "Get users   Returns a list of users, filtered according to query parameters",
          "parameters": [
            {
              "in": "query",
              "name": "briefRepresentation",
              "schema": {
                "type": "boolean"
              },
              "style": "form"
            },
            {
              "in": "query",
              "name": "email",
              "schema": {
                "type": "string"
              },
              "style": "form"
            },
            {
              "in": "query",
              "name": "first",
              "schema": {
                "type": "integer",
                "format": "int32"
              },
              "style": "form"
            },
            {
              "in": "query",
              "name": "firstName",
              "schema": {
                "type": "string"
              },
              "style": "form"
            },
            {
              "in": "query",
              "name": "lastName",
              "schema": {
                "type": "string"
              },
              "style": "form"
            },
            {
              "in": "query",
              "name": "max",
              "description": "Maximum results size (defaults to 100)",
              "schema": {
                "type": "integer",
                "format": "int32"
              },
              "style": "form"
            },
            {
              "in": "query",
              "name": "search",
              "description": "A String contained in username, first or last name, or email",
              "schema": {
                "type": "string"
              },
              "style": "form"
            },
            {
              "in": "query",
              "name": "username",
              "schema": {
                "type": "string"
              },
              "style": "form"
            }
          ],
```
@wing328 wing328 merged commit 6358b11 into OpenAPITools:master Jul 27, 2019
@wing328 wing328 added this to the 4.1.0 milestone Jul 27, 2019
@ccouzens ccouzens deleted the bash_query_param_fix branch July 27, 2019 13:49
@wing328
Copy link
Member

wing328 commented Aug 10, 2019

@ccouzens thanks for the PR, which has been included in the 4.1.0 release: https://twitter.com/oas_generator/status/1160000504455319553

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

Successfully merging this pull request may close these issues.

2 participants