Skip to content

Commit

Permalink
Add JS client side refresh to fix live view issues (pow-auth/pow#271)
Browse files Browse the repository at this point in the history
  • Loading branch information
eliknebel committed Oct 21, 2020
1 parent fc43463 commit 5626b55
Show file tree
Hide file tree
Showing 3 changed files with 44 additions and 1 deletion.
5 changes: 5 additions & 0 deletions lib/oli_web/controllers/static_page_controller.ex
Original file line number Diff line number Diff line change
Expand Up @@ -4,4 +4,9 @@ defmodule OliWeb.StaticPageController do
def index(conn, _params) do
render(conn, "index.html")
end

def keep_alive(conn, _pararms) do
conn
|> send_resp(200, "Ok")
end
end
3 changes: 3 additions & 0 deletions lib/oli_web/router.ex
Original file line number Diff line number Diff line change
Expand Up @@ -125,6 +125,9 @@ defmodule OliWeb.Router do
get "/account", WorkspaceController, :account
put "/account", WorkspaceController, :update_author
post "/account/theme", WorkspaceController, :update_theme

# keep a session active by periodically calling this endpoint
get "/keep-alive", StaticPageController, :keep_alive
end

scope "/project", OliWeb do
Expand Down
37 changes: 36 additions & 1 deletion lib/oli_web/templates/layout/live.html.leex
Original file line number Diff line number Diff line change
Expand Up @@ -11,5 +11,40 @@
phx-value-key="error"><%= live_flash(@flash, :error) %></p>
<% end %>

<%= @inner_content %>
<script>
/**
* If user doesn't request server periodically (few minutes),
* the session expires and user has to re-login again. If user
* manages to request server before the time has expired, the
* cookie is updated and the timer is reset.
*
* The problem is that almost the whole website uses LiveView,
* even for navigation, which means that most of the requests
* go through WebSockets, where you can't update cookies, and
* so the session inevitably expires, even if user is actively
* using the website.
*
* As a workaround, we periodically ping the server via a
* regular AJAX requests, which resets the session cookie timer.
*
* More Info: https://github.com/danschultzer/pow/issues/271
* https://elixirforum.com/t/get-user-id-with-pow-from-session-for-live-view/24206/4
*/
if (!window.keepAlive) {
window.keepAlive = () => {
const wait = (ms) => {
return () => new Promise(resolve => {
setTimeout(resolve, ms)
})
}
fetch('/keep-alive')
.then(wait(60 * 1000 /*ms*/))
.then(keepAlive)
}
window.keepAlive()
}
</script>

<%= @inner_content %>

0 comments on commit 5626b55

Please sign in to comment.