-
Notifications
You must be signed in to change notification settings - Fork 326
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
Passing the response from @on to the @after method #264
Comments
I think this is a good suggestion and the enhancement should not be too hard as we only need to pass the response to the handler here: Line 221 in efc8f08
To not break backwards compatibility, a flag could be added on the after decorator to enable/disable this feature, same way it was done with the validation for the on decorator where the flag is by default False |
The routing system of this library is not very sophisticated and could use some improvement. In the current implementation, the I'm afraid that above process might not be clear to all users of this library. In fact, the code sample that @HugoJP1 seem to indicate that this is not clear for them, as the Assume for now, return value of the class ChargePoint(cp)
@on(Action.BootNotification)
def on_boot_notification(self, charge_point_vendor: str, charge_point_model: str, **kwargs):
return call_result.BootNotificationPayload(
current_time=datetime.utcnow().isoformat(),
interval=10,
status=RegistrationStatus.accepted
)
@after(Action.BootNotification)
def after_boot_notification(self, charge_point_vendor: str, charge_point_model: str, _response: call_result.BootNotificationPayload, **kwargs):
# Invalid use of the API. This return value won't be send to the charge point.
_response.interval = 20
return _response In retrospect, the current api of One quick proposal, that I didn't thought through yet is to allow preprocessing of requests,and post-processing of response. E.g. class ChargePoint
@on(Action.BootNotification, pre=pre_boot_notification, post=post_boot_notification)
def on_boot_notification(self, charge_point_vendor: str, charge_point_model: str, **kwargs):
return call_result.BootNotificationPayload(
current_time=datetime.utcnow().isoformat(),
interval=10,
status=RegistrationStatus.accepted
)
def pre_boot_notification(self, request: call.BootNotificationPayload) -> call.BootNotificationPayload:
# Modify request here before it's passed to `@on()` handler.
return request
def post_boot_notification(self, request: call.BootNotificationPayload, response: call_result.BootNotificationPayload) -> call_result.BootNotificationPayload:
# Modify response before it's send to peer.
return response It might even be made backwards compatible. |
The point is not to modify the response and send it to the peer in the after decorator... The method decorated by the after decorator, afik, was always treated as a post processing method, where you can perform a few actions that only make sense after you have processed the message associated with the on decorator one and the intention was not to change the response that needs to be sent to the peer. I remind that the motivation for the after decorator, was because we saw the need to do post-processing and we didnt want to delay the sending of the response to the peer. This said, I think we can keep unchanged the goal of the @after decorator and just improve it a bit, by allowing to process also the response sent during process of the @on one, avoiding the user to save some context in a temp variable. |
Correct. My only concern is: is that clear for users? IMHO we should try to design an API that hard to use wrong. But assuming it's clear for them. How should we modify the current API? Something like: @after("BootNotification", inject_response=True):
async def after_boot_notification_handler(self, response, *args, **kwargs):
pass A couple of notes and questions:
|
I think with a proper doc/example, we can make it clear as I agree that currently may not be that clear...
@after("BootNotification", inject_response=True): inject_response is a keyword only argument which defaults to False to be backwards compatible. Yup, that was how I was imagining. I think your name suggestions are fine. As for the type of the data I think |
@tropxy Did you manage to do it? If so, can you share an example with us? Thanks |
I agree that the existing API is very limited. It is common that you do not want to execute the "after" method, for example, if the request handler returned/responded with "Rejected". I don't see any easy way of doing that, currently? I'm not sure we talke about the same "response", though, but as I see it, whatever the "on" handler returned, should be available in the "after" method. |
Untested idea:
|
I've created a PR which implements what has been discussed here. |
This issue is stale because it has been open for 30 days with no activity. |
Hello,
I have the following scenario:
Looking at
charge_point.py
, it looks like it is the payload from the initial call which is passed into the@after
function. What would you think of also passing through the response of the call so that it can be used for further processing?I have a workaround by using a temp variable, but thought it could be a nice feature of the library so posting here.
The text was updated successfully, but these errors were encountered: