kyma-project / kyma

Kyma is an opinionated set of Kubernetes-based modular building blocks, including all necessary capabilities to develop and run enterprise-grade cloud-native applications.
https://kyma-project.io
Apache License 2.0
1.52k stars 405 forks source link

Application Connector API Gateway for OData #2466

Closed akrausesap closed 5 years ago

akrausesap commented 5 years ago

Description

Dear Colleagues,

Using legacy OData APIs via the Application Connector API Gateway causes some incompatibilities. Whilst in the OData v4 URL conventions (http://docs.oasis-open.org/odata/odata/v4.01/cs01/part2-url-conventions/odata-v4.01-cs01-part2-url-conventions.html#sec_URLComponents) it is clearly defined that http://host/service/People('O''Neil') and its encoded equivalent http://host/service/People%28%27O%27%27Neil%27%29 are both valid urls identifying a Person with ID O''Neil in OData v2 it is not clearly defined. Hence some backends are only accepting http://host/service/People('O''Neil'). The current implementation of the application connector always applies URL Encoding to calls and hence makes invoking OData Services on these environments impossible. An example of such a system would be SAP C4C. Please enable accessing such systems.

Thanks

Andreas

Expected result

URL http://host/service/People('O''Neil') is passed unchanged

Actual result

URL http://host/service/People('O''Neil') is encoded to http://host/service/People%28%27O%27%27Neil%27%29

Steps to reproduce N/A

Troubleshooting N/A

lszymik commented 5 years ago

We need to investigate it and see what can we do with it. In the first phase please treat it as spike and we will discuss what to do with it later. Because we have a limited amount of time.

lszymik commented 5 years ago

I am trying to reproduce that issue.

So far I have added the HTTPBin service registration:

{
  "provider": "lszymik",
  "name": "Ping the HTTP Bin service",
  "description": "The HTTPBin service",
  "shortDescription": "Test HTTPBin API",
  "api": {
    "targetUrl": "https://httpbin.org",
    "spec": {}
  },
  "events": {
    "spec": {
      "asyncapi": "1.0.0",
      "info": {
        "title": "HTTPBin Events",
        "version": "1.0.0",
        "description": "HTTPBin Events"
      },
      "baseTopic": "com.http.bin",
      "topics": {
        "getInfo.v1": {
          "subscribe": {
            "summary": "Get info event",
            "payload": {
              "type": "object",
              "properties": {
                "properties": {
                  "id": {
                    "title": "message",
                    "description": "This is additional message which can be propagated",
                    "type": "string"
                  }
                }
              }
            }
          }
        }
      }
    }
  }
}

Then I also have following Lambda exposed over HTTP:

const request = require('request');

module.exports = { main: function (event, context) {

    return new Promise((resolve, reject) => {
        const url = `${process.env.GATEWAY_URL}/anything/People('O''Neil')`;
        const options = {
            url: url,
        };

        sendReq(url, resolve, reject)
    })
} }

function sendReq(url, resolve, reject) {
    request.get(url, { json: true }, (error, response, body) => {
        console.log(body)
        if(error){
            resolve(error)
        }
        resolve(body)
    })
}
{
    "name": "calculate-promotion",
    "version": "0.0.1",
    "dependencies": {
      "request": "^2.85.0"
    }
}

I am doing the following call:

http GET https://httpbin-production.lszymik1.kyma.ga/

and the result is

HTTP/1.1 200 OK
access-control-allow-origin: *
content-length: 343
content-type: application/json; charset=utf-8
date: Wed, 13 Mar 2019 12:51:32 GMT
etag: W/"157-GVt7AQErDjFvmYzBUipPr14dBnU"
server: envoy
x-envoy-upstream-service-time: 567
x-powered-by: Express

{
    "args": {},
    "data": "",
    "files": {},
    "form": {},
    "headers": {
        "Accept": "application/json",
        "Accept-Encoding": "gzip",
        "Host": "httpbin.org",
        "X-B3-Sampled": "1",
        "X-B3-Spanid": "7d662435e1f32eb0",
        "X-B3-Traceid": "7d662435e1f32eb0"
    },
    "json": null,
    "method": "GET",
    "origin": "127.0.0.1, 34.76.173.203, 127.0.0.1",
    "url": "https://httpbin.org/anything/People('O''Neil')"
}
Szymongib commented 5 years ago

Hello, we tried to call https://httpbin.org/anything/People('O''Neil') directly through our Application Gateway and URL was not encoded. In case of calling Application Gateway with lambda provided by @lszymik the URL was encoded to https://httpbin.org/anything/People(%27O%27%27Neil%27) which as we found out was the cause of "request": "^2.85.0" library used in a lambda function.

@akrausesap Could you provide some more information about how do you make call to Application Connector? Are you using a lambda of some kind? and if so could you provide the code making HTTP request?

akrausesap commented 5 years ago

Hello @Szymongib,

I have used a generated client that is likely to be axios based. However I have also done a port forwarding of the Application Gateway using kubectl port-forward -n kyma-integration svc/re-<service name goes here> 8081:80 and then used postman to better understand the issue. More tracing on the client side jointly with @lszymik yielded your assessment is spot on correct. Let's close it :-).

Thanks

Andreas

lszymik commented 5 years ago

The investigation revealed that encoding was applied by the client calling the API Gateway service. Therefore, we are closing that issue.