]> Untitled Git - lemmy-ui.git/blobdiff - src/shared/services/UserService.ts
fix toaster upon user settings change (#1802)
[lemmy-ui.git] / src / shared / services / UserService.ts
index 8d591cc3ed3c0ffa2466b878683a7c374c227dbd..70e8e9cadae7b79e8de43aa288ce14adf8031b58 100644 (file)
@@ -1,12 +1,10 @@
-// import Cookies from 'js-cookie';
-import { Err, None, Ok, Option, Result, Some } from "@sniptt/monads";
-import IsomorphicCookie from "isomorphic-cookie";
+import { isAuthPath } from "@utils/app";
+import { clearAuthCookie, isBrowser, setAuthCookie } from "@utils/browser";
+import * as cookie from "cookie";
 import jwt_decode from "jwt-decode";
 import { LoginResponse, MyUserInfo } from "lemmy-js-client";
-import { BehaviorSubject } from "rxjs";
-import { isHttps } from "../env";
-import { i18n } from "../i18next";
-import { isBrowser, toast } from "../utils";
+import { toast } from "../toast";
+import { I18NextService } from "./I18NextService";
 
 interface Claims {
   sub: number;
@@ -20,67 +18,75 @@ interface JwtInfo {
 }
 
 export class UserService {
-  private static _instance: UserService;
-  public myUserInfo: Option<MyUserInfo> = None;
-  public jwtInfo: Option<JwtInfo> = None;
-  public unreadInboxCountSub: BehaviorSubject<number> =
-    new BehaviorSubject<number>(0);
-  public unreadReportCountSub: BehaviorSubject<number> =
-    new BehaviorSubject<number>(0);
-  public unreadApplicationCountSub: BehaviorSubject<number> =
-    new BehaviorSubject<number>(0);
+  static #instance: UserService;
+  public myUserInfo?: MyUserInfo;
+  public jwtInfo?: JwtInfo;
 
   private constructor() {
-    this.setJwtInfo();
+    this.#setJwtInfo();
   }
 
-  public login(res: LoginResponse) {
-    let expires = new Date();
+  public login({
+    res,
+    showToast = true,
+  }: {
+    res: LoginResponse;
+    showToast?: boolean;
+  }) {
+    const expires = new Date();
     expires.setDate(expires.getDate() + 365);
-    res.jwt.match({
-      some: jwt => {
-        toast(i18n.t("logged_in"));
-        IsomorphicCookie.save("jwt", jwt, { expires, secure: isHttps });
-        this.setJwtInfo();
-        location.reload();
-      },
-      none: void 0,
-    });
+
+    if (isBrowser() && res.jwt) {
+      showToast && toast(I18NextService.i18n.t("logged_in"));
+      setAuthCookie(res.jwt);
+      this.#setJwtInfo();
+    }
   }
 
   public logout() {
-    this.jwtInfo = None;
-    this.myUserInfo = None;
-    IsomorphicCookie.remove("jwt"); // TODO is sometimes unreliable for some reason
-    document.cookie = "jwt=; Max-Age=0; path=/; domain=" + location.host;
-    location.reload();
+    this.jwtInfo = undefined;
+    this.myUserInfo = undefined;
+
+    if (isBrowser()) {
+      clearAuthCookie();
+    }
+
+    if (isAuthPath(location.pathname)) {
+      location.replace("/");
+    } else {
+      location.reload();
+    }
   }
 
-  public auth(throwErr = true): Result<string, string> {
-    // Can't use match to convert to result for some reason
-    let jwt = this.jwtInfo.map(j => j.jwt);
-    if (jwt.isSome()) {
-      return Ok(jwt.unwrap());
+  public auth(throwErr = false): string | undefined {
+    const jwt = this.jwtInfo?.jwt;
+
+    if (jwt) {
+      return jwt;
     } else {
-      let msg = "No JWT cookie found";
+      const msg = "No JWT cookie found";
+
       if (throwErr && isBrowser()) {
-        console.log(msg);
-        toast(i18n.t("not_logged_in"), "danger");
+        console.error(msg);
+        toast(I18NextService.i18n.t("not_logged_in"), "danger");
       }
-      return Err(msg);
+
+      return undefined;
+      // throw msg;
     }
   }
 
-  private setJwtInfo() {
-    let jwt = IsomorphicCookie.load("jwt");
+  #setJwtInfo() {
+    if (isBrowser()) {
+      const { jwt } = cookie.parse(document.cookie);
 
-    if (jwt) {
-      let jwtInfo: JwtInfo = { jwt, claims: jwt_decode(jwt) };
-      this.jwtInfo = Some(jwtInfo);
+      if (jwt) {
+        this.jwtInfo = { jwt, claims: jwt_decode(jwt) };
+      }
     }
   }
 
   public static get Instance() {
-    return this._instance || (this._instance = new this());
+    return this.#instance || (this.#instance = new this());
   }
 }