Open Closed

Communication between two microservices #6305


User avatar
0
pvala created
  • ABP Framework version: v7.3.2
  • UI Type: Angular / Blazor Server
  • Database System: EF Core (MySQL)
  • Tiered (for MVC) or Auth Server Separated (for Angular): yes/no
  • Exception message and full stack trace:
  • Steps to reproduce the issue:

I have created a microservice called FormsService, on which I have added the FormsModule as a project. I want to call the APIs of other microservice into the FormsService microservice (specifically SaasService here). I have followed the following document to do so.

https://docs.abp.io/en/commercial/latest/startup-templates/microservice/synchronous-interservice-communication

The configuration is completed, and the required data is also seeded in the database. But when I run the whole application and try to call an API endpoint from the SaasService, I get an error in my Blazor UI project. I checked the logs of the Blazor UI project, I get the following error :

2023-12-08 20:54:02.276 +05:30 [ERR] Could not found remote action for method: System.Threading.Tasks.Task1[System.Collections.Generic.List1[G1.health.SaasService.TenantDto]] GetTenantNamesList() on the URL: https://localhost:44325 Volo.Abp.AbpException: Could not found remote action for method: System.Threading.Tasks.Task1[System.Collections.Generic.List1[G1.health.SaasService.TenantDto]] GetTenantNamesList() on the URL: https://localhost:44325 at Volo.Abp.Http.Client.DynamicProxying.ApiDescriptionFinder.FindActionAsync(HttpClient client, String baseUrl, Type serviceType, MethodInfo method) at Volo.Abp.Http.Client.DynamicProxying.DynamicHttpProxyInterceptor1.GetActionApiDescriptionModel(IAbpMethodInvocation invocation) at Volo.Abp.Http.Client.DynamicProxying.DynamicHttpProxyInterceptor1.InterceptAsync(IAbpMethodInvocation invocation) at Volo.Abp.Castle.DynamicProxy.CastleAsyncAbpInterceptorAdapter1.InterceptAsync[TResult](IInvocation invocation, IInvocationProceedInfo proceedInfo, Func3 proceed) at Castle.DynamicProxy.AsyncInterceptorBase.ProceedAsynchronous[TResult](IInvocation invocation, IInvocationProceedInfo proceedInfo) at Volo.Abp.Castle.DynamicProxy.CastleAbpMethodInvocationAdapterWithReturnValue1.ProceedAsync() at Volo.Abp.Validation.ValidationInterceptor.InterceptAsync(IAbpMethodInvocation invocation) at Volo.Abp.Castle.DynamicProxy.CastleAsyncAbpInterceptorAdapter1.InterceptAsync[TResult](IInvocation invocation, IInvocationProceedInfo proceedInfo, Func`3 proceed) at Volo.Forms.Web.Pages.Forms.CreateModalModel.OnGetAsync() in D:\G1 Health WorkSpace\Branches\DEV Branch\G1.health\services\forms\modules\Volo.Forms\src\Volo.Forms.Web\Pages\Forms\CreateModal.cshtml.cs:line 33 at Microsoft.AspNetCore.Mvc.RazorPages.Infrastructure.ExecutorFactory.GenericTaskHandlerMethod.Convert[T](Object taskAsObject) at Microsoft.AspNetCore.Mvc.RazorPages.Infrastructure.ExecutorFactory.GenericTaskHandlerMethod.Execute(Object receiver, Object[] arguments) at Microsoft.AspNetCore.Mvc.RazorPages.Infrastructure.PageActionInvoker.InvokeHandlerMethodAsync() at Microsoft.AspNetCore.Mvc.RazorPages.Infrastructure.PageActionInvoker.InvokeNextPageFilterAsync() 2023-12-08 20:54:02.316 +05:30 [INF] Executing ObjectResult, writing value of type 'Volo.Abp.Http.RemoteServiceErrorResponse'. 2023-12-08 20:54:02.322 +05:30 [INF] Executed page /Forms/CreateModal in 8739.3474ms 2023-12-08 20:54:02.322 +05:30 [INF] Executed endpoint '/Forms/CreateModal' 2023-12-08 20:54:02.323 +05:30 [INF] Request finished HTTP/2 GET https://localhost:44314/Forms/CreateModal - - - 500 - application/json;+charset=utf-8 9008.7077ms

It says that it couldn't find the API endpoint on the 44325 port, but my SaasService runs on the 44381 port. The 44325 port runs the Web Gateway application. I don't understand why the API call is redirected to the 44325 port and not 44381 port. This is the configuration I have done in my FormsService appsettings.json file,

"RemoteServices": { "AbpIdentity": { "BaseUrl": "https://localhost:44381/", "UseCurrentAccessToken": "false" } }, "IdentityClients": { "Default": { "GrantType": "client_credentials", "ClientId": "health_FormsService", "ClientSecret": "1q2w3e*", "Authority": "https://localhost:44322", "Scope": "SaasService" } }

Can you tell me why is it redirecting to the 44325 port? Or is there any configuration I am missing? I have also referred to the following ticket https://support.abp.io/QA/Questions/2268/Questions-regarding-new-microservice-design where it is stated that the Internal Gateway has been removed since last few versions. So, then which port should I be using in the above configuration to make it work? Please guide.


8 Answer(s)
  • User Avatar
    0
    gterdem created
    Senior .NET Developer

    As you can see from the documentation, all the requests from the applications are redirected to the related gateway to be re-routed to the related microservice.

    When you are making a request from the back-office application (blazor app) it redirects to the WebGateway (localhost:44325). When you make a request from the public-web application, it will redirect to the PublicWebGateway (localhost:44353). Then you need to configure the re-routing from the gateways to the related microservices. More information is at https://docs.abp.io/en/commercial/latest/startup-templates/microservice/gateways

    By the way, the scenario you explained is not related to communication between microservices.

  • User Avatar
    0
    pvala created

    You mean I have to configure the ocelot.json file right? Also, how is it different from the communication between the microservices?

  • User Avatar
    0
    pvala created

    I have already configured the ocelot.json file

    {
      "ServiceKey": "Saas Service",
      "DownstreamPathTemplate": "/api/saas/{everything}",
      "DownstreamScheme": "https",
      "DownstreamHostAndPorts": [
        {
          "Host": "localhost",
          "Port": 44381
        }
      ],
      "UpstreamPathTemplate": "/api/saas/{everything}",
      "UpstreamHttpMethod": [ "Put", "Delete", "Get", "Post" ]
    },
    

    but it still gives the same error.

  • User Avatar
    0
    pvala created

    Any updates on this?

  • User Avatar
    0
    gterdem created
    Senior .NET Developer

    When you make a request from /Forms/CreateModal, it is from the UI right? It is the back-office application (web/blazor/angular whatever).

    So, you are making a request from the application to the related microservice through the web gateway. It is not microservice-to-microservice communication. It is a client-server request.

    When you make a request from the FormsService to SaasService (or vice versa) it is the microservice-to-microservice communication. When making this kind of request, there is no gateway interaction. They directly make request to each other (if you are using synchronous communication).

  • User Avatar
    0
    pvala created

    Okay, I understood your point. So, here's a scenario, I have the saas service, which already has few endpoints created by ABP. Now to add some new endpoints, I have created a new AppService called TenantOverrideAppService and similarly the interface for the app service ITenantOverrideAppService, as well the controller TenantOverrideController. Now I am trying to call that endpoint from the Blazor application and it throws the error that it can't find the specific endpoint. While if I use the existing endpoints provided by ABP for the Saas Service, it works. So, what's the configuration that I am missing here. Anything related to proxy? Please elaborate.

  • User Avatar
    0
    pvala created

    FYI, I have added all these files manually and not using ABP Suite.

  • User Avatar
    0
    gterdem created
    Senior .NET Developer

    Yes, you need to re-generate proxy for the SaasService since you have a new endpoint now. See https://docs.abp.io/en/abp/latest/API/Static-CSharp-API-Clients#without-contracts for more information.

Made with ❤️ on ABP v9.1.0-preview. Updated on November 11, 2024, 11:11