update api, add loading states
This commit is contained in:
parent
6ff45b81bf
commit
63e99885a4
4 changed files with 52 additions and 21 deletions
|
|
@ -1,3 +1,3 @@
|
||||||
# Update schema
|
# Update schema
|
||||||
|
|
||||||
`pnpm dlx openapi-typescript http://localhost:8000/openapi.json -o ./schema.d.ts`
|
`pnpm dlx openapi-typescript http://localhost:8000/openapi.json -o ./schema.ts`
|
||||||
|
|
|
||||||
|
|
@ -132,18 +132,16 @@ export interface components {
|
||||||
*/
|
*/
|
||||||
activity_state: "unknown" | "locking" | "unlocking" | "stable";
|
activity_state: "unknown" | "locking" | "unlocking" | "stable";
|
||||||
};
|
};
|
||||||
/** UserInfo */
|
|
||||||
UserInfo: {
|
|
||||||
/** Username */
|
|
||||||
username: string;
|
|
||||||
};
|
|
||||||
/** UserStatus */
|
/** UserStatus */
|
||||||
UserStatus: {
|
UserStatus: {
|
||||||
/** Is Logged In */
|
/** Is Logged In */
|
||||||
is_logged_in: boolean;
|
is_logged_in: boolean;
|
||||||
|
/** Is Authorized */
|
||||||
|
is_authorized: boolean;
|
||||||
/** Guaranteed Session Until */
|
/** Guaranteed Session Until */
|
||||||
guaranteed_session_until: string | null;
|
guaranteed_session_until: string | null;
|
||||||
user_info: components["schemas"]["UserInfo"] | null;
|
/** Username */
|
||||||
|
username: string | null;
|
||||||
};
|
};
|
||||||
/** ValidationError */
|
/** ValidationError */
|
||||||
ValidationError: {
|
ValidationError: {
|
||||||
|
|
|
||||||
|
|
@ -32,33 +32,45 @@ const auth: AuthType = {
|
||||||
}
|
}
|
||||||
|
|
||||||
const apiError: {
|
const apiError: {
|
||||||
current: "serverError" | null;
|
current: "serverError" | "networkError" | null;
|
||||||
} = {
|
} = {
|
||||||
current: null,
|
current: null,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const loading: {
|
||||||
|
doors: boolean;
|
||||||
|
auth: boolean;
|
||||||
|
} = {
|
||||||
|
doors: false,
|
||||||
|
auth: false,
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
const doors: Array<DoorType> = []
|
const doors: Array<DoorType> = []
|
||||||
|
|
||||||
function loadAuthFromLocalStorage() {
|
function loadAuthFromLocalStorage() {
|
||||||
const localAuth = JSON.parse(localStorage.getItem("auth") ?? "")
|
if (localStorage.getItem("auth")) {
|
||||||
auth.recentLogout = localAuth.recentLogout // set recentLogout true, if user was logged in before
|
const localAuth = JSON.parse(localStorage.getItem("auth")!)
|
||||||
auth.authenticated = localAuth.authenticated
|
auth.recentLogout = localAuth.recentLogout // set recentLogout true, if user was logged in before
|
||||||
auth.authorized = localAuth.authorized
|
auth.authenticated = localAuth.authenticated
|
||||||
auth.until = localAuth.until ? new Date(localAuth.until) : null
|
auth.authorized = localAuth.authorized
|
||||||
auth.username = localAuth.username
|
auth.until = localAuth.until ? new Date(localAuth.until) : null
|
||||||
|
auth.username = localAuth.username
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
async function checkUser() {
|
async function checkUser() {
|
||||||
|
loading.auth = true
|
||||||
const getUserInfo = fetcher.path("/api/user-info/").method("get").create()
|
const getUserInfo = fetcher.path("/api/user-info/").method("get").create()
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const {status, data: userInfo} = await getUserInfo({})
|
const {data: userInfo} = await getUserInfo({})
|
||||||
|
|
||||||
apiError.current = null
|
apiError.current = null
|
||||||
auth.authenticated = userInfo.is_logged_in
|
auth.authenticated = userInfo.is_logged_in
|
||||||
auth.authorized = true
|
auth.authorized = userInfo.is_authorized
|
||||||
auth.until = userInfo.guaranteed_session_until ? new Date(userInfo.guaranteed_session_until) : null
|
auth.until = userInfo.guaranteed_session_until ? new Date(userInfo.guaranteed_session_until) : null
|
||||||
auth.username = userInfo.user_info?.username ?? ""
|
auth.username = userInfo.username ?? ""
|
||||||
auth.recentLogout = false
|
auth.recentLogout = false
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
// check which operation threw the exception
|
// check which operation threw the exception
|
||||||
|
|
@ -80,15 +92,18 @@ async function checkUser() {
|
||||||
}
|
}
|
||||||
} finally {
|
} finally {
|
||||||
localStorage.setItem("auth", JSON.stringify(auth))
|
localStorage.setItem("auth", JSON.stringify(auth))
|
||||||
|
loading.auth = false
|
||||||
refresh()
|
refresh()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
async function fetchDoors() {
|
async function fetchDoors() {
|
||||||
|
loading.doors = true
|
||||||
|
refresh()
|
||||||
const getDoors = fetcher.path("/api/locks/").method("get").create()
|
const getDoors = fetcher.path("/api/locks/").method("get").create()
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const {status, data: doorInfo} = await getDoors({})
|
const {data: doorInfo} = await getDoors({})
|
||||||
|
|
||||||
apiError.current = null
|
apiError.current = null
|
||||||
while (doors.length) {
|
while (doors.length) {
|
||||||
|
|
@ -129,7 +144,15 @@ async function fetchDoors() {
|
||||||
console.error("unknown error:", error)
|
console.error("unknown error:", error)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (e instanceof Error) {
|
||||||
|
switch (e.name) {
|
||||||
|
case "TypeError":
|
||||||
|
apiError.current = "networkError"
|
||||||
|
}
|
||||||
|
}
|
||||||
} finally {
|
} finally {
|
||||||
|
loading.doors = false
|
||||||
refresh()
|
refresh()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -190,21 +213,27 @@ function refresh() {
|
||||||
const alertUnauthorized: HTMLDivElement = document.querySelector("#alert-unauthorized")!
|
const alertUnauthorized: HTMLDivElement = document.querySelector("#alert-unauthorized")!
|
||||||
const alertLoggedout: HTMLDivElement = document.querySelector("#alert-loggedout")!
|
const alertLoggedout: HTMLDivElement = document.querySelector("#alert-loggedout")!
|
||||||
const alertServerError: HTMLDivElement = document.querySelector("#alert-serverError")!
|
const alertServerError: HTMLDivElement = document.querySelector("#alert-serverError")!
|
||||||
|
const alertNetworkError: HTMLDivElement = document.querySelector("#alert-networkError")!
|
||||||
const alertDivider: HTMLDivElement = document.querySelector("#alert-divider")!
|
const alertDivider: HTMLDivElement = document.querySelector("#alert-divider")!
|
||||||
const badgeUsername: HTMLDivElement = document.querySelector("#badge-username")!
|
const badgeUsername: HTMLDivElement = document.querySelector("#badge-username")!
|
||||||
const buttonLogin: HTMLDivElement = document.querySelector("#button-login")!
|
const buttonLogin: HTMLDivElement = document.querySelector("#button-login")!
|
||||||
const usernameElement: HTMLSpanElement = badgeUsername.querySelector("#username")!
|
const usernameElement: HTMLSpanElement = badgeUsername.querySelector("#username")!
|
||||||
|
const loadingDoors: HTMLDivElement = document.querySelector("#loading-doors")!
|
||||||
|
|
||||||
alertUnauthenticated.classList.toggle("hidden", auth.authenticated)
|
alertUnauthenticated.classList.toggle("hidden", auth.authenticated || auth.recentLogout)
|
||||||
alertUnauthorized.classList.toggle("hidden", !auth.authenticated || auth.authorized)
|
alertUnauthorized.classList.toggle("hidden", !auth.authenticated || auth.authorized)
|
||||||
alertLoggedout.classList.toggle("hidden", !auth.recentLogout)
|
alertLoggedout.classList.toggle("hidden", !auth.recentLogout)
|
||||||
alertServerError.classList.toggle("hidden", apiError.current !== "serverError")
|
alertServerError.classList.toggle("hidden", apiError.current !== "serverError")
|
||||||
alertDivider.classList.toggle("hidden", auth.authenticated && auth.authorized && !auth.recentLogout && apiError.current === null)
|
alertNetworkError.classList.toggle("hidden", apiError.current !== "networkError")
|
||||||
|
alertDivider.classList.toggle("hidden", auth.authenticated && auth.authorized && !auth.recentLogout && apiError.current === null || doors.length === 0)
|
||||||
badgeUsername.classList.toggle("hidden", !auth.authenticated)
|
badgeUsername.classList.toggle("hidden", !auth.authenticated)
|
||||||
usernameElement.innerHTML = auth.username
|
usernameElement.innerHTML = auth.username
|
||||||
buttonLogin.classList.toggle("hidden", auth.authenticated)
|
buttonLogin.classList.toggle("hidden", auth.authenticated)
|
||||||
|
loadingDoors.classList.toggle("hidden", !loading.doors)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
loadAuthFromLocalStorage()
|
loadAuthFromLocalStorage()
|
||||||
fetchDoors()
|
fetchDoors()
|
||||||
checkUser()
|
checkUser()
|
||||||
|
|
|
||||||
|
|
@ -28,8 +28,10 @@ export const ui = {
|
||||||
"loggedOut.title": "Signed out",
|
"loggedOut.title": "Signed out",
|
||||||
"loggedOut.description": `Your session has expired and you have been logged out.<br>
|
"loggedOut.description": `Your session has expired and you have been logged out.<br>
|
||||||
Please log in again.`,
|
Please log in again.`,
|
||||||
"serverError.title": "Server Error",
|
"serverError.title": "Server error",
|
||||||
"serverError.description": `Please try again later.`,
|
"serverError.description": `Please try again later.`,
|
||||||
|
"networkError.title": "Network error",
|
||||||
|
"networkError.description": `Please check your network connection.`,
|
||||||
},
|
},
|
||||||
de: {
|
de: {
|
||||||
"dooris": "TüRIS <span class='text-neutral-content/50 text-xs'>(DOORIS)</span>",
|
"dooris": "TüRIS <span class='text-neutral-content/50 text-xs'>(DOORIS)</span>",
|
||||||
|
|
@ -55,5 +57,7 @@ export const ui = {
|
||||||
Melde dich erneut an.`,
|
Melde dich erneut an.`,
|
||||||
"serverError.title": "Serverfehler",
|
"serverError.title": "Serverfehler",
|
||||||
"serverError.description": `Bitte versuche es später erneut.`,
|
"serverError.description": `Bitte versuche es später erneut.`,
|
||||||
|
"networkError.title": "Netzwerkfehler",
|
||||||
|
"networkError.description": `Bitte überprüfe deine Internetverbindung.`,
|
||||||
},
|
},
|
||||||
} as const
|
} as const
|
||||||
Loading…
Add table
Add a link
Reference in a new issue