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

Mock does not work when URL contains slashes #1363

Closed
Marckman opened this issue Oct 8, 2024 · 5 comments
Closed

Mock does not work when URL contains slashes #1363

Marckman opened this issue Oct 8, 2024 · 5 comments

Comments

@Marckman
Copy link

Marckman commented Oct 8, 2024

Describe the bug

We are trying to mock some of our APIs via the artifact upload feature (in our case, an OpenAPI 3.x document).

I have noticed the context root in the mock URL is built by joining the document's info/title and info/version with a slash. So, in order to keep this URL as similar as possible to our actual services' URLs, I have placed a fixed api part followed by a slash and the version as the info/version field in the document, e.g. api/v1.

The actual service URL follows this format:
https://my.actual.env/myservice/api/v1/resource

Whereas the mock ends up with an URL like this:
https://microcks.foo/rest/myservice/api/v1/resource

However, when we send a request to the mock, it takes just api as the version and fails, instead of returning the expected response.

Any help would be appreciated. Also, please correct me if this has been the wrong approach all along 😅 we just need to customize the context root in our mocks.

Expected behavior

Mock returns the expected response according to what is documented in the OpenAPI contract.

Actual behavior

Mock answers with a 404 error and a plain text body like the following:
The service myservice with version api does not exist!

How to Reproduce?

  1. Create a service via the Add Direct API button in the web app, or the artifact/upload API operation.
  2. Upload an OpenAPI document which version contains a slash, e.g. api/v1. Make sure the document has enough examples for mock creation.
  3. Send a request to the mocked operation URL.

Microcks version or git rev

1.10.0

Install method (docker-compose, helm chart, operator, docker-desktop extension,...)

helm chart

Additional information

No response

Copy link

github-actions bot commented Oct 8, 2024

👋 @Marckman

Welcome to the Microcks community! 💖

Thanks and congrats 🎉 for opening your first issue here! Be sure to follow the issue template or please update it accordingly.

📢 If you're using Microcks in your organization, please add your company name to this list. 🙏 It really helps the project to gain momentum and credibility. It's a small contribution back to the project with a big impact.

If you need to know why and how to add yourself to the list, please read the blog post "Join the Microcks Adopters list and Empower the vibrant open source Community 🙌"

Hope you have a great time there!

🌟 ~~~~~~~~~ 🌟

📢 If you like Microcks, please ⭐ star ⭐ our repo to support it!

🙏 It really helps the project to gain momentum and credibility. It's a small contribution back to the project with a big impact.

@lbroudoux
Copy link
Member

Hello @Marckman,

I think reasoning from an example can help in this situation 😉 Let's imagine the following basic OpenAPI definition of your
service:

openapi: 3.0.2
info:
  title: MyService
  version: 1.0
paths:
  /resource:
    get:
      [...]

From this OpenAPI definition, Microcks will generate mock endpoints like this:
https://microcks.foo/rest/MyService/1.0/resource.
It can be seen as it is built that way:
https://{base.url}/{path} where base.url is actually https://microcks.foo/rest/MyService/1.0. The base.url is typically the thing that can change from environment to environment and that lives into environment variables or configuration properties.

Now if your current service has this kind of URL:
https://my.actual.env/MyService/api/v1/resource

You have several options the:

I hope it clarifies the situation on how Microcks is actually producing endpoint URLs.

@Marckman
Copy link
Author

Marckman commented Oct 9, 2024

Hi @lbroudoux, thanks a lot for the quick reply!
Please let me elaborate.

The actual service URL is set in stone and we cannot change it, i.e. it is always the hostname (env dependent) followed by the service name, a fixed api segment and the major version.
So the produced mock URL must be https://microcks.foo/rest/MyService/api/v1/resource, so I have tried to work around this problem following approaches similar to options 2 and 3 you just provided.

So if my spec is like this:

info:
  title: MyService
  version: api/v1
paths:
  /resource:

I get the error I mentioned in the first post. However, I have noticed versions with formats like api_v1 or api@v1 do work. I am currently looking into rewriting URLs on the ingress nginx side (replace that slash with _ or @) to make this option work.

Now, if I set the version as part of the resource:

info:
  title: MyService
  version: api
paths:
  /v1/resource:

This works really well but leads to a different problem: two major versions of the same API cannot live alongside each other (just like in the actual environments) because their "coordinates" (MyService/api) in Microcks are the same - in this case, I have noticed the previous artifact gets overwritten, forcing me to merge both specs before importing.

Finally, if the resource path is like api/v1/resource, this would leave the version empty, which I think is not allowed.

Hope this clarifies the issue a bit 🙂 Thanks again!

@lbroudoux
Copy link
Member

Ok I see what you mean but I'm afraid we cannot do something at the Microcks level as introducing version in endpoints is mandatory to avoid collision and version is of-course URL-encoded to avoid side-effect. In your situation, I would recommend adding an extra proxy in front of your Microcks instance to rewrite the URL the way you want.

You may then introduce an arbitrary version in your spec to have something like:

info:
  title: MyService
  version: 1.0
paths:
  /resource:

This would produce endpoints like https://microcks.foo/rest/MyService/1.0/resource but you'll put an Nginx or Traeffik in front of that to proxy https://my.actual.env/myservice/api/v1/resource to https://microcks.foo/rest/MyService/1.0/resource this would made the trick.

This could be a temporary situation until you realign your practices to some more standard ways like having https://my.actual.env/myservice/api being the base.url variable part as exposed before.

@Marckman
Copy link
Author

Thanks @lbroudoux.
We will keep working on the URL rewrite solution and adjust our specs accordingly.
Kind regards.

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

No branches or pull requests

2 participants