Add a new page to Volttron Central - volttron

I have a standalone HTML page with jQuery. The jQuery is used to do AJAX call to the Python backend. I need to integrate it with Volttron Central. I have looked at the documentation but there is no section talking about this. I think it would be nice to have this kind of info in the doc.
My current approach is to convert the backend Python to be a Volttron agent but I don't know how to integrate the front end HTML page with VC.
Any suggestion where to start? Thanks.

When you have an agent that is going to register its own endpoint you should do that during the onstart signal. The following was extracted from the volttron central agent. It shows how to register an endpoint that is dynamic(uses volttron rpc as the endpoint) as well as static(where the html is simply served). I have removed the un-necessary bits for this example.
onstart volttron central code
For clarity MASTER_WEB and VOLTTRON_CENTRAL are unique identifiers for those specific agents running on the volttron instance.
#Core.receiver('onstart')
def _starting(self, sender, **kwargs):
""" Starting of the platform
:param sender:
:param kwargs:
:return:
"""
...
# Registers dynamic route.
self.vip.rpc.call(MASTER_WEB, 'register_agent_route',
r'^/jsonrpc.*',
self.core.identity,
'jsonrpc').get(timeout=30)
# Registers static route.
self.vip.rpc.call(MASTER_WEB, 'register_path_route', VOLTTRON_CENTRAL,
r'^/.*', self._webroot).get(timeout=30)
Since you added the route onstart you should also remove it when the agent is stopped. onstop referenced code
#Core.receiver("onstop")
def stopping(self, sender, **kwargs):
'''
Release subscription to the message bus because we are no longer able
to respond to messages now.
'''
try:
# unsubscribes to all topics that we are subscribed to.
self.vip.pubsub.unsubscribe(peer='pubsub', prefix=None, callback=None)
except KeyError:
# means that the agent didn't start up properly so the pubsub
# subscriptions never got finished.
pass

Related

How to develop locally with service worker?

Instead of generating a build every time I make a change, I want to use the service worker while developing. I've already managed to use the https protocol with a valid certificate, but the service worker doesn't install it. I imagine it is related to the following error "No matching service worker detected. You may need to reload the page, or check that the service worker for the current page also controls the start of the URL from the manifest."

Not able to create events using Microsoft Graph SDK

I am trying to create an Event using Microsoft Graph SDK, as following the document #
https://learn.microsoft.com/en-us/graph/api/user-post-events?view=graph-rest-beta&tabs=csharp
1.Created "authProvider"
2.Created GraphClient with above AuthProvider
3.Creating Event using
The event is not creating also no exception/error is throwing, Could any one help me here?
This is happening because this call is being made with same transactionId frequently. It avoids unnecessary retries on the server.
It is an optional parameter , just comment out this property and try again. It should work.
Note : This identifier specified by a client app for the server , to avoid redundant POST operations in case of client retries to create the same event and also useful when low network connectivity causes the client to time out before receiving a response from the server for the client's prior create-event request.
More info is required here, as the reply from Allen Wu stated. without any details I would focus my efforts on the authprovider piece and azure app registration piece. as the rest of the example is just sending a post request to graph api.
but what is recommended really depends on what type of application you are trying to build. eg. is it a service daemon, a web app, mobile app, desktop app, single page app, etc.

webapp2 Sessions: How do sessions work conceptually?

I wish to implement sessions in webapp2. From research, I have found this code sample using webapp2_extra.sessions, and a few articles which mentions deprecated or unmaintained session libraries.
I currently lack the knowledge of how sessions work conceptually. This is what I understand so far:
We can include a dispatch() method to a request handler which allows us to create/update a session object; it is during the login phase of the app, the session is created. (Question: how is session stored? In the app's memory or in datastore?)
When a user makes a request to the app, the dispatch() method checks to see if an existing session exists for the user. (Question: How exactly does this validation work? Is there a token inside the request.body or cookie that sessions look for?)
When a user logs out, the session is deleted.
Is my understanding correct? Or perhaps I am missing something important? There seems to be little guidance on this subject on the internet. Thank you for the assistance.
Technically the dispatch() method is not added, it's just overwriting the one that webapp2.RequestHandler already provides, extending it to add session support. If you take a closer look at that method you see that it still calls the original one to do the actual dispatching:
# Dispatch the request.
webapp2.RequestHandler.dispatch(self)
Which could be re-written, if you want, as:
super(BaseHandler, self).dispatch()
All that the extended dispatch() does is picking up the session info from the store making it available to the handler code before dispatching the request (which BTW includes the request processing) and saving it back afterwards, when the request processing completes (when changes to the session info may have been done). For every request! Simply a way to persist info across requests.
The session support is simply that - support - your app is still the one responsible for controlling what info is stored in the webapp2's session dictionary, when is that info added/modified/deleted and how is that info used.
In other words webapp2 itself has no clue what's login/logout/user session, etc (So no, nothing that you mention in #1, #2 and #3 happens in webapp2 itself). It is your app's responsibility to:
set/delete inside the session dictionary the info that represents your "user session" (whatever that means for your app) - typically in the user login/logout request handlers, respectively
use that info as it sees fit while handling incoming requests between the login and the logout one - when the info from the session dictionary represents the "current user session".
For storing the session info webapp2 supports cookies (default), memcache and datastore (ndb). From Sessions:
It has three built-in backends: secure cookies, memcache and
datastore. New backends can be added extending
CustomBackendSessionFactory.
The session store can provide multiple sessions using different keys,
even using different backends in the same request, through the method
SessionStore.get_session(). By default it returns a session using
the default key from configuration.

Calling a #RPC method outside of volttron

Say I have a running volttron agent with a #RPC decorated method (if that's relevant). Are there any ways to call that method from outside of the volttron platform? (In my case from a django web server)
An agent may register endpoints on the VOLTTRON web service. A callback may be setup for the endpoint as needed.
The web service must be enabled and the agent needs to pass "enable_web=True" to the base agent constructor.
You can find the documentation and examples here: http://volttron.readthedocs.io/en/develop/specifications/webframework.html
Along with what kyle-monson mentions, you also have to run Volttron using the bind argument. This will expose the registered endpoints on the bind arg given.
e.g `volttron -vv --bind-web-address "https://127.0.0.1:7080"
OR specify the bind-web-address in the ~/.volttron/config
[volttron]
message-bus = rmq
bind-web-address = https://127.0.0.1:7080
Then you can send HTTP POST request to https://127.0.0.1:7080/rpc-method-name
rpc-method-name in the request URL being the registered method using self.vip.web.register_endpoint("/rpc-method-name", self.call_back_method_for_endpoint)
The call back method takes in two parameters "env" and "data"
For more details on this two parameters check the docs here

GAE behavior when relocating an application to another server

Two questions:
Does Google App Engine send any kind of message to an application just before relocating it to another server?
If so, what is that message?
No it doesnt. It doesnt relocate either, old instances keep running (and eventually stop when idle for long enough) while new ones are spawned.
There are times when App Engine needs to move your instance to a different machine to improve load distribution.
When App Engine needs to turn down a manual scaling instance it first
notifies the instance. There are two ways to receive this
notification. First, the is_shutting_down() method from
google.appengine.api.runtime begins returning true. Second, if you
have registered a shutdown hook, it will be called. It's a good idea
to register a shutdown hook in your start request. After the
notification is issued, existing requests are given 30 seconds to
complete, and new requests immediately return 404.
If an instance is
handling a request, App Engine pauses the request and runs the
shutdown hook. If there is no active request, App Engine sends an
/_ah/stop request, which runs the shutdown hook. The /_ah/stop request
bypasses normal handling logic and cannot be handled by user code; its
sole purpose is to invoke the shutdown hook. If you raise an exception
in your shutdown hook while handling another request, it will bubble
up into the request, where you can catch it.
The following code sample demonstrates a basic shutdown hook:
from google.appengine.api import apiproxy_stub_map
from google.appengine.api import runtime
def my_shutdown_hook():
apiproxy_stub_map.apiproxy.CancelApiCalls()
save_state()
# May want to raise an exception
runtime.set_shutdown_hook(my_shutdown_hook)
Alternatively, the following sample demonstrates how to use the is_shutting_down() method:
while more_work_to_do and not runtime.is_shutting_down():
do_some_work()
save_state()
More details here: https://developers.google.com/appengine/docs/python/modules/#Python_Instance_states

Resources