Skip to content

Instantly share code, notes, and snippets.

@hungify
Last active May 12, 2024 08:21
Show Gist options
  • Save hungify/64304deb8aba48b01e69300367fc7dc1 to your computer and use it in GitHub Desktop.
Save hungify/64304deb8aba48b01e69300367fc7dc1 to your computer and use it in GitHub Desktop.
Refresh Token Machine (X Time before expiration)
"use client";
import dayjs from "dayjs";
import { jwtDecode } from "jwt-decode";
import { useRouter } from "next/navigation";
import { useEffect, useRef, useState } from "react";
import { useAuthContext } from "../auth/context";
export default function RefreshTokenMachine() {
const [diff, setDiff] = useState<number>(1000);
const [accessToken, setAccessToken] = useState<string | null>(null);
const prevAccessToken = useRef<string | null>(null);
const router = useRouter();
const { isAuthenticated } = useAuthContext();
useEffect(() => {
prevAccessToken.current = accessToken;
}, [accessToken]);
useEffect(() => {
if (!isAuthenticated) return;
const getRefresh = async () => {
{
const res = await fetch(
`${process.env.NEXT_PUBLIC_URL}/api/proxy/auth/refresh-token`,
{
method: "GET",
},
);
const { data } = await res.json();
const { accessToken } = data;
setAccessToken(accessToken);
const jwtPayload = jwtDecode(accessToken);
if (!jwtPayload.exp) {
router.push("/logout");
return;
}
const refreshTime = dayjs(jwtPayload.exp * 1000).subtract(5, "minutes");
const now = dayjs();
const diff = refreshTime.diff(now, "milliseconds");
setDiff(diff);
}
};
const timeoutId = setTimeout(getRefresh, diff);
return () => clearTimeout(timeoutId);
}, [isAuthenticated, diff, router]);
return (
<div>
<div>
<p>Refreshing token in {diff / 1000} seconds</p>
<code
style={{
whiteSpace: "pre-wrap",
wordBreak: "break-word",
}}
>
Access token: {accessToken}
<br />
Previous access token: {prevAccessToken.current}
</code>
</div>
</div>
);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment