Blocking a REST API response until another API is called - rest

I have following scenario:
There are two API calls in an application: api1 and api2.
api1 is invoked multiple times from multiple users. I want to block all the responses of api1 calls until api2 is invoked. api2 will be invoked with a parameter which would suggest to "release" the response of a specific api1 invocation. So whenever api2 is invoked, a specific api1 call will respond which was blocked until now (there can be multiple api1 releases based on the parameter passed in api2 call).
I want to implement this in grails. I'm kind of blank how to implement this. Any ideas?
Do share if you know any other language or framework which can be used to implement this.

A solution that came to my mind is using a mutex on the api1 call and releasing it in the api2. You may have to take into account the timeout of the api1.
EDIT
Well, you can have a dictionary/map of mutex's where each call has a respective mutex. When a client calls api1, the server generates a mutex and adds it to the dictionary, also it tries to lock the mutex(which is locked by default). After that on the api2 you only need to provide the id that you used in the dictionary to unlock the mutex.

Related

Current ACS call session list and force to end it by REST

I'm integrating ACS video call into my service (NodeJs backend, React front).
I want to allow ACS video call session only for a scheduled time period, then force to end it if it is over.
However I cannot find the way of implement followings (or REST API)
list current call sessions
list participants of each sessions.
force to stop/end a session by group id or any call ID
webhooks/callback being called when the session closes and when the participant leaves session.
Could you please give me some hint or advice?
Much appreciated.
Jin
You can use the Call Automation to join or create a new call. Your app can join either as a participant of the call or act out of the call. Each option offers different capabilities described here.
The good news is that both options offer the capability to add and remove participants to/from the call:
Call Connections - Remove Participant
Server Calls - Remove Participant
If you decide to use the In-Call (App-Participant) APIs, can you specify the callbackUri in the CreateCallOptions or JoinCallOptions. On this URI, you can listen to events (webhooks) such as Participants updated and deserialize the information about them. There is a comprehensive quickstart app available on GitHub showcasing the concept of callback URIs on the call recording capabilities (see the CallRecordingController.cs and Utils.ts in the public-preview branch).
If you decide to use the Out-of-Call APIs, then you need to keep track of the participant IDs yourself.
Currently, the CallingServer SDKs are currently available only for .NET and Java so you'll have to use the REST API.

Microservices Saga pattern consumer awaits response

I would like to clarify what'd be the best way of organizing architecture.
I've got rest api and microservices architecture. I have applied the Database per Service pattern.
So let's imagine that the user wants to create an order(an e-commerce system). But users can have a credit limit. So the flow will be as below:
OrderService creates a pending order. Then push an event about it.
UserService processes that event and publishes either a credit limit exceeded event or a credit reserved event.
OrderService receives the event and changes the state of the order to either approved or canceled.
All look good. But the question is what the user will do during this simple flow?
I mean: the user makes a POST request /orders and ...
Web-service awaits until the order gets approved or canceled(includes surely timeout)?
Web-service returns 200 ok and then the user needs to check the order state with some interval?
use web sockets?
something else?
Unfortunately, Any option from above has its advantages and its disadvantages.
The challenge is that I described the simplest case. In reality, tens services(even third party) could be involved. And of course, I am expecting a high load. So the queue may be filled.
Please propose the solution to discuss. I'm greatly appreciating for an answer as well as links to production ready system documentation.
Kudos for a good question. If we look at Saga Pattern, it offers to do ACID like transactions in a distributed system but with some trade-off. One of the trade-offs is Ensuring Rollback if any of the service or entity fails to do what it was supposed to do. This can go even complex if you have more than 5 services completing a Saga. Though it will be a Highly Scalable option if you can orchestrate.
Here I will propose Following,
User Does a POST request for order
OrderService first checks with UserService regarding credit Limit (It can be a REST API call as it might be a simple DB call for UserService)
Then OrderService can act upon based on the return response from UserService
Advantages of this approach
User can see an immediate response
Less Complex to code thus testable and maintainable Code
Disadvantages of this approach
This solution will not be effective if there are too many external (third party) rest api calls
It can introduce single point of failure
The main thing is, all the options will have trade-offs. It is on you to decide which one suits you the best.
According to me
Follow the my rule - Validate First then action
Validate the order before its goes to order service on UI. You can call the userservice api on UI which gives info user can make a order or not.
Step 1. On UI call the userservice API , which validate the user credit limit
Step 2. If validation success or fail
Step 3. Take the action according to step2 result . If success call the order service if not do what you want to do (Call other service etc..)
Advantage
A good user exprience - User get the validation message "you can not make a order your limit is low" or something like that when trying to make the order. Not at the end get a message "You limit is low/or anything"
Less Complexity of code
A more microservice Arch. -
Since your are follow the microservices then if you call the userservice inside the orderservice means orderservice is dependent on it or you can say tightly bound - here your are lossing the benifit of mircroservice arch.
What happen if the userservice is down. The customer cannot make the order or if you change anything in userservice response then you have to change the orderservice also.
What you do if some more validation (to call other service) need in future before making the order.
Redirection Flexibility - Suppose if on fail of validation from userservice then you have to call other service( other independent microservice ) and if you are using the other service inside the orderservice the no of service increases as project grow
Less Request on OrderService - Request goes orderservice only when the validation is passed from the other service or other thing.
So from my point of view
Try to make microservice independent as much possible.
Validate First and action.
A good user exprience
Easy to handle load (if you think)
With all that , now you less dependent on saga.
Its only my opinion - choose what you think best according to your domain
The question is what the user will do during this
simple flow? I mean: the user makes a POST request /orders and ...
You can reply to user the created orderId with status 'pending' while your saga is running. The request should be ended in 200.
How does user get the status?
Push notification, websocket, email, sms. it is up to you to notify the user about the status of event, success, failure, waiting_for_approval.
1. Web-service awaits until the order gets approved or canceled?
2. Web-service returns 200 ok and the user check the order state with some interval?
3. use web sockets?
4. something else?
Not recommended. Saga should be asynchronous. Waiting for reply is synchronous (request/reply style).
This will work, but if your saga is long running, it might be problematic, eg: anything with validation/approval by a human.
This will work assuming you are replying 200 after order creation in pending state, one thing is that you have to make sure your websocket is active, or else, you still have to notify them through email, sms.
Unfortunately, Any option from above has its advantages and its
disadvantages.
You have to choose your poison.
The challenge is that I described the simplest case. In reality, tens
services(even third party) could be involved. And of course, I am
expecting a high load. So the queue may be filled.
Use orchestrated saga (sort like) Netflix conductor, Uber Cadence, Temporal (Similar to Cadence). This will allow you to do something as shown below. At least, easier.
A flow diagram from google shopping api and how they handle it.
Link for more: https://developers.google.com/shopping-content/guides/about-orders
There is little difference in cancelling an order because there was a problem with the credit limit vs. cancelling it because a forklift ran over the package in the logistics facility.
So a relatively simple solution is to reply with an order accepted and status 200 when the order is placed put that in a queue and let the saga run asynchronously. You should provide both an API (and UI) for the user to check the order status and proactively send status updates like billing going through (which is your fist saga) and also other sagas in the order lifecycle
Regarding how to send notifications that depends on the usage scenario (e.g. you can do a callback for a system-to-system integration, but maybe you want to send an email/sms to an end-user etc)

POST/PUT response REST in a CQRS/ES system

I'm implementing a CQRS/ES based system with a RESTful interface which is used by a webapp.
When performing certain actions e.g. creating a new profile I need to be able to check certain conditions, such as uniqueness of the profile ID, or that the person has the right to create a resource under a group. Which means I have a couple of options:
Context: POST/profiles { "email": "unique#example.com" }
From my REST API return 202 from my service with a location of the new resource where my client can poll for it. In this case, however, how do I handle errors as in effect the view will not exist or ever exist.
Create a saga on the initial request then dispatch the event. Once my service creates the view or finds the error then the result is written to the saga. When the saga has been completed return the result to the user.
From these two options - the second seems more reasonable to me, if not more complex. Is this a viable option for building RESTful request/response models on a CQRS/ES event sourced backend?
Yes, the second solution seems to better fit the business.
From what I understand from your case, from the DDD point of view, the creation of a user profile is a business process, with more than one steps (verifying the uniqueness of the profile, creating the profile and recovering from a duplicate profile situation). This process acts like an entity, it starts, runs and ends with a result (success or error). Being an entity it has an ID and it can be viewed as a REST resource. A Saga will be responsible for executing it.
So, in response to the client's request you send the URI of the process resource where the client can poll for the status. In case of error, it reads the error message. In case of success, it gets the URI of its profile.
The first solution can still be used if the use-case is simpler, if the command can be executed synchronously and the client gets the final result (error or success) as an immediate response.
From my REST API return 202 from my service with a location of the new resource where my client can poll for it. In this case, however, how do I handle errors as in effect the view will not exist or ever exist.
The usual answer here is that, as part of the 202 Accepted response, you include monitoring information
The representation sent with this response ought to describe the request's current status and point to (or embed) a status monitor that can provide the user with an estimate of when the request will be fulfilled.
In other words, a link to a resource that will change when the accepted request is finally run.
So in describing the protocol, in addition to the resource that you create, you'll also need to document the representation used when you defer the work for later, and the representation used by the monitor.
When the saga has been completed return the result to the user.
Depending on the work, that may be overkill.
Which is to say, you are raising two different questions here; one of those is whether the request should be handled synchronously (don't respond until the work is done) or asynchronously (return right away, but give the client the means to monitor progress).
The other question is how the work looks from the business layer. If you are going to need multiple transactions to make the change, and if you may need to "revert" previously committed transactions in some variants of the process, then a saga (or a process manager) makes sense.
Set Validation -- the broader term for enforcing an invariant like "uniqueness" -- is awkward. Make sure you study, and ensure that you and the business understand the impact of having a failure.

Does it violate the RESTful when I write stuff to the server on a GET call?

I would like to record user actions on my website, not only on POST requests, but on GET requests as well. For example, suppose the user tries to search for a city with the following GET request:
/search_city?name=greenville
This request would return a list of cities with the name "greenville". I'd also like to save this keyword to the server, as the "search history" for a user. I'm planning to just do the save this information during the processing of the GET call.
Is this a violation to RESTful principles? If yes, how do I do this the right way?
I see this kind of audit logging as an invisible side-effect. If the next person to call
/search_city?name=greenville
still gets the same answer then your GET is valid. A similar case would be some kind of cache building, the caller of GET doesn't (need to) know that you're doing some extra work.
Focus on the formal API - send this request get this response.
If there's some resource available in the API where the user search history is available, then it's not OK to do that, since your GET request has a visible side-effect. For instance, a client caching responses is under no obligation to know that any resource changed because he did a GET request to anything else. I think the only way to do this and stay compliant is to explicitly mark the side-effected resource as uncacheable.
In particular, the convention has been established that the GET and HEAD methods SHOULD NOT have the significance of taking an action other than retrieval. These methods ought to be considered "safe". This allows user agents to represent other methods, such as POST, PUT and DELETE, in a special way, so that the user is made aware of the fact that a possibly unsafe action is being requested.
Naturally, it is not possible to ensure that the server does not generate side-effects as a result of performing a GET request; in fact, some dynamic resources consider that a feature. The important distinction here is that the user did not request the side-effects, so therefore cannot be held accountable for them.
http://www.w3.org/Protocols/rfc2616/rfc2616-sec9.html
If that's kept only for internal usage, I guess it's fine to do it that way, but I still recommend against it.

Actions vs. CRUD in REST

Is it appropriate to perform actions with REST, other than simple create (POST), read (GET), update (PUT), and delete (DELETE)? I'm kind of new to the whole RESTful theology, so bear with me, but how should I accomplish the following:
I have a web service that needs to talk to another web service. Web service A needs to "reserve" an object on Web service B. This object has a timeout of validity, but can be deleted immediately if need be. It's essentially a glorified permissions system which requires web services to reserve a space on web service B before taking any actions.
My initial thought was to 1. enable authentication of some sort, 2. in the serverside response to a GET call, reserve the space and return the result, and 3. provide immediate "unreservation" of the object via a DELETE call. Is this still being RESTful?
Yes, it's OK to perform actions with rest. What matters is that these actions should be guided by the representations you exchange.
If you think about the way the web works (via a browser), you do this all the time: you get an HTML form that lets you choose a number of actions you can perform. Then, you submit the form (typically via POST) and the action is performed.
It's good to be able to use DELETE via a programmatic client (which is something that non-AJAX requests in browsers wouldn't support), but the overall approach of a RESTful system should be very similar to what you find for websites (i.e. the focus should be on the representations: the equivalent of web pages in your system).
GET shouldn't have side effects, so don't use GET to make the reservation itself, use something like POST instead.
No - unlikely to be restful
From your description ...
2. in the serverside response to a GET call, reserve the space and return the result
GETs should be idempotent. For this reason alone, your service is unlikely to be restful because the state of the system after the first GET is different.
You really need to consider that a Reservation is a resource and should be created with a POST to a reservations container which will return the URI of the new resource in the Location header of the HTTP response. This UrI can be used by Get to return the resource and updated with a PUT
Post should be used to extend an existing resource and Put for replacing the state of a resource. In your case, consider the Post to be updating a list of Reservations and returning the URI of the new resource (not just the I'd). Put can be used for changing the state associated with the resource identified by the UR
You're on the right track, but your reservation of the object should be with a PUT; you're PUTting a reservation on the object, i.e. changing the underlying object.
PUT is the right verb here, since you know what resource you're modifying, and it should be idempotent for multiple requests.