fix: explicitly save session when token refresh happens
this should only affect "secondary" threads for use with real-time sync to farmOS. the belief is that when a token refresh happens in main thread, the session is auto-saved with the new token. but when a token refresh happens in secondary thread, the session was not being auto-saved with new token. so this should fix that...
This commit is contained in:
parent
78c6a8070a
commit
47d817712b
2 changed files with 30 additions and 5 deletions
|
|
@ -27,7 +27,26 @@ from pyramid import httpexceptions
|
|||
from webhelpers2.html import HTML
|
||||
|
||||
|
||||
def get_farmos_client_for_user(request):
|
||||
def get_farmos_client_for_user(request, main_thread=True):
|
||||
"""
|
||||
Make and return a new farmOS API client instance.
|
||||
|
||||
This is a wrapper around
|
||||
:meth:`~wuttafarm.farmos.handler.FarmOSHandler.get_farmos_client()`
|
||||
with conveniences to automatically handle token refresh for the
|
||||
current user session.
|
||||
|
||||
:param request: Current web request; this determines the user.
|
||||
|
||||
:param main_thread: Boolean indicating whether this client is for
|
||||
use within the main thread, or a separate one. In the latter
|
||||
case it must perform certain extra steps to help with token
|
||||
refresh. This defaults to ``True`` in which case the client is
|
||||
part of the main thread, i.e. the normal request/response
|
||||
cycle.
|
||||
|
||||
:returns: farmOS API client instance
|
||||
"""
|
||||
token = request.session.get("farmos.oauth2.token")
|
||||
if not token:
|
||||
raise httpexceptions.HTTPForbidden()
|
||||
|
|
@ -39,14 +58,14 @@ def get_farmos_client_for_user(request):
|
|||
token = dict(token)
|
||||
|
||||
def token_updater(token):
|
||||
save_farmos_oauth2_token(request, token)
|
||||
save_farmos_oauth2_token(request, token, main_thread=main_thread)
|
||||
|
||||
config = request.wutta_config
|
||||
app = config.get_app()
|
||||
return app.get_farmos_client(token=token, token_updater=token_updater)
|
||||
|
||||
|
||||
def save_farmos_oauth2_token(request, token):
|
||||
def save_farmos_oauth2_token(request, token, main_thread=True):
|
||||
"""
|
||||
Common logic for saving the given OAuth2 token within the user
|
||||
session. This function is called from 2 places:
|
||||
|
|
@ -61,6 +80,12 @@ def save_farmos_oauth2_token(request, token):
|
|||
# save token to user session
|
||||
request.session["farmos.oauth2.token"] = token
|
||||
|
||||
if not main_thread:
|
||||
# nb. must call persist() explicitly in separate thread, since
|
||||
# pyramid_beaker may not be in effect (iiuc?)
|
||||
request.session.save()
|
||||
request.session.persist()
|
||||
|
||||
|
||||
def use_farmos_style_grid_links(config):
|
||||
return config.get_bool(f"{config.appname}.farmos_style_grid_links", default=True)
|
||||
|
|
|
|||
|
|
@ -120,7 +120,7 @@ class WuttaFarmMasterView(MasterView):
|
|||
if self.app.is_farmos_mirror():
|
||||
if self.creating:
|
||||
session.flush() # need the new uuid
|
||||
client = get_farmos_client_for_user(self.request)
|
||||
client = get_farmos_client_for_user(self.request, main_thread=False)
|
||||
thread = threading.Thread(
|
||||
target=self.auto_sync_to_farmos, args=(client, obj.uuid)
|
||||
)
|
||||
|
|
@ -168,7 +168,7 @@ class WuttaFarmMasterView(MasterView):
|
|||
|
||||
# maybe delete from farmOS also
|
||||
if farmos_uuid:
|
||||
client = get_farmos_client_for_user(self.request)
|
||||
client = get_farmos_client_for_user(self.request, main_thread=False)
|
||||
# nb. must use separate thread to avoid some kind of race
|
||||
# condition (?) - seems as though maybe a "boomerang"
|
||||
# effect is happening; this seems to help anyway
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue