Skip to content

Fix the issue encountered when the value of queries starting with '{'#555

Merged
codefromthecrypt merged 9 commits into
OpenFeign:masterfrom
zhujf1989:master
May 6, 2017
Merged

Fix the issue encountered when the value of queries starting with '{'#555
codefromthecrypt merged 9 commits into
OpenFeign:masterfrom
zhujf1989:master

Conversation

@zhujf1989

Copy link
Copy Markdown
Contributor

When using RibbonClient, the starting %7B in the value of queries would be replaced with {. For example, a request URL like http://example.com/q?p=%7Baaa%7D would become http://example.com/q?p={aaa} after passing toRequest() in feign.ribbon.LBClient.

This issue could make feign not able to play with newer versions of Tomcat after fixing CVE-2016-6816.

@codefromthecrypt

codefromthecrypt commented Apr 26, 2017 via email

Copy link
Copy Markdown

@fengchj

fengchj commented Apr 27, 2017

Copy link
Copy Markdown

i am puzzled, is this a bug?

@zhujf1989

Copy link
Copy Markdown
Contributor Author

Hi, adriancole

IMHO this is a serious issue. That makes a request with queries whose value is a json string have chance to get a response with code 400 since the request line contains "unwise" characters referring to RFC 2396. We want to use Ribbon in our project & are really appreciate that Feign can reduce our work. So we do this to make Feign suitable for wider use.

RequestTemplate.appendDirectly() is added just for RibbonClient & there is no other place to call, therefore there is no side effect to be seen.

@codefromthecrypt

Copy link
Copy Markdown

just an aside, I think there's other types of things that will probably break similarly.. iirc there was some outstanding work due to elasticsearch's query api as well.

}

/**
* Append the specified {@code value} to {@code url} without decoding or encoding. Append all

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

lots of doc. but no example. forward referencing to ribbon probably won't help people understand.

Try to shorten this to maybe two succinct sentences and an example.

Ex.

Like {@link #foo} except ..

<p> <-- note p not br and the newline break makes it easy to read, too..
ex if your input is X unless you call this method, it would become Y

import java.util.Map;
import java.util.Map.Entry;

import static feign.Util.CONTENT_LENGTH;

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

revert the re-order


@Test
public void appendDirectlytest() throws Exception {
String url = "http://test.feign.com/query?params=%7b%22int%22%3a1%2c%22string%22%3a%22str%22%7d";

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

comment why we care. ex people won't necessarily be able to understand that this is escaped json (if it is)

return new RequestTemplate()
.method(request.method())
.append(getUri().toASCIIString())
.appendDirectly(getUri().toASCIIString())

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

since this is only added for ribbon, there should be a test here.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

the junit for RibbonRequest.toRequest() has been added, please review

return new RequestTemplate()
.method(request.method())
.append(getUri().toASCIIString())
.appendDirectly(getUri().toASCIIString())

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

wait.. couldn't this be much easier by just making a request?

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

like this..

    Request toRequest() {
      return Request.create(
          request.method(),
          getUri().toASCIIString(),
          request.headers(),
          request.body(), request.charset()
      );
    }

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Using Request.create() is exactly easier to make an orignal request, thanks for reminding :) . But the old code(use append) has the logic that add the header "Content-Length" to the request. Base on keeping the old logic and code reuse, should we continue to use appendDirectly()?

@codefromthecrypt

codefromthecrypt commented Apr 30, 2017 via email

Copy link
Copy Markdown

@zhujf1989

Copy link
Copy Markdown
Contributor Author
  1. revert all the codes of RequestTemplate.appendDirectly() by using 'git revert'
  2. keep the junit test for RibbonRequest.toRequest()
  3. fix the issue by using Request.create(), and keeping the old logic(add the header 'Content-Length' manually).

final byte[] body = request.body();
final int bodyLength = body != null ? body.length : 0;
// create a new Map to avoid side effect, not to change the old headers
Map<String, Collection<String>> headers = new HashMap<String, Collection<String>>();

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

please use LinkedHashMap as this ensures tests don't flake on iteration order

assertEquals(requestOrign.charset(), requestGetFormToRequest.charset());
assertNotNull(requestOrign.headers());
assertEquals(0, requestOrign.headers().size()); // double check the baseline Request
assertNotNull(requestGetFormToRequest.headers()); // double check the baseline Request, header is not null, but empty

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

avoid checks that are duplicated from constructor (I think it isn't possible that this is null)

Request requestGetFormToRequest = ribbonRequest.toRequest();

// test the same attributes
assertEquals(requestOrign.method(), requestGetFormToRequest.method());

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

this test is kindof hard to read. Can you look at other unit tests? you'll notice we use assertj which is helpful

@codefromthecrypt

Copy link
Copy Markdown

if you don't mind, try and cleanup for merge in the next couple days so we can get this out over the weekend. Will be doing a release then. cc @jfuerth

@codefromthecrypt

Copy link
Copy Markdown

LGTM let me know if you are ready for merge

@zhujf1989

Copy link
Copy Markdown
Contributor Author

Of course! Feel free to merge it.

@codefromthecrypt codefromthecrypt merged commit 82b57a3 into OpenFeign:master May 6, 2017
phymbert pushed a commit to phymbert/feign that referenced this pull request Aug 22, 2017
…OpenFeign#555)

support the query values starting with {, when use RibbonClient。different from OpenFeign#540.
velo pushed a commit that referenced this pull request Oct 7, 2024
…#555)

support the query values starting with {, when use RibbonClient。different from #540.
velo pushed a commit that referenced this pull request Oct 8, 2024
…#555)

support the query values starting with {, when use RibbonClient。different from #540.
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