diff --git a/client/src/AuthManager.js b/client/src/AuthManager.js
index 21800cc..60c903b 100644
--- a/client/src/AuthManager.js
+++ b/client/src/AuthManager.js
@@ -18,169 +18,164 @@
  */
 
 class AuthManager {
-    constructor() {
-        console.log("AuthManager()")
-        this.authenticating = false
+  constructor() {
+    console.log('AuthManager()');
+    this.authenticating = false;
 
-        this.state = {
-            initialized: false,
-            authenticated: true,
-            setupComplete: true,
-            error: false
-        }
+    this.state = {
+      initialized: false,
+      authenticated: true,
+      setupComplete: true,
+      error: false,
+    };
 
-        this.tasks = []
-        this.onAuthChanged = undefined
+    this.tasks = [];
+    this.onAuthChanged = undefined;
 
-        if (initData) {
-            console.log("Using static initData")
-            this.setInitData(initData)
-            return
-        }
+    if (initData) {
+      console.log('Using static initData');
+      this.setInitData(initData);
+      return;
     }
+  }
 
-    isAuthenticated() {
-        return this.state.authenticated
+  isAuthenticated() {
+    return this.state.authenticated;
+  }
+
+  getState() {
+    return this.state;
+  }
+
+  setInitData(data) {
+    this.authenticating = false;
+    this.state.initialized = true;
+    if (data.username) {
+      Object.assign(this.state, {
+        authenticated: true,
+        setupComplete: true,
+        error: false,
+        user: { username: data.username, type: data.type },
+      });
+    } else {
+      Object.assign(this.state, {
+        authenticated: false,
+        setupComplete: 'setupComplete' in data ? data.setupComplete : true,
+        error: false,
+      });
     }
-
-    getState() {
-        return this.state
-    }
-
-    setInitData(data) {
-        this.authenticating = false
-        this.state.initialized = true
-        if (data.username) {
-            Object.assign(this.state, {
-                authenticated: true,
-                setupComplete: true,
-                error: false,
-                user: { username: data.username, type: data.type }
-            })
-        } else {
-            Object.assign(this.state, {
-                authenticated: false,
-                setupComplete: 'setupComplete' in data ? data.setupComplete : true,
-                error: false
-            })
-        }
-        console.log("Init ended")
-        /*if (this.onAuthChanged)
+    console.log('Init ended');
+    /*if (this.onAuthChanged)
             this.onAuthChanged(this.state)*/
-    }
+  }
 
-    init(cb) {
-        this.onAuthChanged = cb
-        if (this.state.initialized || this.authenticating)
-            return
-        /*if (initData) {
+  init(cb) {
+    this.onAuthChanged = cb;
+    if (this.state.initialized || this.authenticating) return;
+    /*if (initData) {
             console.log("Using static initData")
             this.setInitData(initData)
             return
         }*/
-        this.authenticating = true
-        fetch('/auth')
-            .then(async (response) => {
-                this.authenticating = false
-                this.state.initialized = true
-                if (response.status === 200) {
-                    this.setInitData(await response.json())
-                } else if (response.status === 401) {
-                    this.setInitData(await response.json())
-                } else {
-                    this.state.error = true
-                    if (this.onAuthChanged)
-                        this.onAuthChanged(this.state)
-                }
-            }).catch(e => {
-                this.authenticating = false
-                console.log(e)
-            })
-    }
-
-    deinit() {
-        console.log("Deinit")
-        this.onAuthChanged = undefined
-    }
-
-    async setup(password) {
-        if (this.authenticating || this.state.setupComplete)
-            return
-        console.log("Starting setup")
-        this.authenticating = true
-        const response = await fetch(`/setup`, {
-            method: 'POST',
-            headers: {
-                'Accept': 'application/json',
-                'Content-Type': 'application/json'
-            },
-            body: JSON.stringify({ password })
-        })
-        console.log(response)
-        if (response.ok) {
-            console.log("Success, going home")
-            //navigate('/')
+    this.authenticating = true;
+    fetch('/auth')
+      .then(async (response) => {
+        this.authenticating = false;
+        this.state.initialized = true;
+        if (response.status === 200) {
+          this.setInitData(await response.json());
+        } else if (response.status === 401) {
+          this.setInitData(await response.json());
         } else {
+          this.state.error = true;
+          if (this.onAuthChanged) this.onAuthChanged(this.state);
         }
-        this.authenticating = false
-        this.state.setupComplete = true
-        if (this.onAuthChanged)
-            this.onAuthChanged(this.state)
-        return response.ok
-    }
+      })
+      .catch((e) => {
+        this.authenticating = false;
+        console.log(e);
+      });
+  }
 
-    authenticate(username, password) {
-        if (this.authenticating)
-            return
-        console.log("Starting authentication")
-        this.authenticating = true
-        fetch(`/auth/local?username=${encodeURIComponent(username)}&password=${encodeURIComponent(password)}`, { method:"POST" })
-            .then(response => {
-                console.log(response)
-                this.authenticating = false
-                this.state.authenticated = response.ok && response.status === 200
-                if (this.onAuthChanged)
-                    this.onAuthChanged(this.state)
-                while (this.tasks.length !== 0) {
-                    const task = this.tasks.shift()
-                    if (this.state.authenticated)
-                        fetch(task.url, task.init)
-                        .then(res => task.resolve(res))
-                        .catch(e => console.log("Error executing pending task: " + e))
-                    else
-                        task.reject(new Error("Authentication failed"))
-                }
-            }).catch(e => {
-                this.authenticating = false
-                console.log(e)
-            })
-    }
+  deinit() {
+    console.log('Deinit');
+    this.onAuthChanged = undefined;
+  }
 
-    disconnect() {
-        console.log("Disconnect")
-        this.state.authenticated = false
-        if (this.onAuthChanged)
-            this.onAuthChanged(this.state)
+  async setup(password) {
+    if (this.authenticating || this.state.setupComplete) return;
+    console.log('Starting setup');
+    this.authenticating = true;
+    const response = await fetch(`/setup`, {
+      method: 'POST',
+      headers: {
+        Accept: 'application/json',
+        'Content-Type': 'application/json',
+      },
+      body: JSON.stringify({ password }),
+    });
+    console.log(response);
+    if (response.ok) {
+      console.log('Success, going home');
+      //navigate('/')
+    } else {
     }
+    this.authenticating = false;
+    this.state.setupComplete = true;
+    if (this.onAuthChanged) this.onAuthChanged(this.state);
+    return response.ok;
+  }
 
-    fetch(url, init) {
-        console.log(`fetch ${url}`)
-        if (!this.state.authenticated) {
-            if (!init || !init.method || init.method === 'GET') {
-                return new Promise((resolve, reject) => this.tasks.push({url, init, resolve, reject}))
-            } else {
-                return new Promise((resolve, reject) => reject("Not authenticated"))
-            }
+  authenticate(username, password) {
+    if (this.authenticating) return;
+    console.log('Starting authentication');
+    this.authenticating = true;
+    fetch(`/auth/local?username=${encodeURIComponent(username)}&password=${encodeURIComponent(password)}`, {
+      method: 'POST',
+    })
+      .then((response) => {
+        console.log(response);
+        this.authenticating = false;
+        this.state.authenticated = response.ok && response.status === 200;
+        if (this.onAuthChanged) this.onAuthChanged(this.state);
+        while (this.tasks.length !== 0) {
+          const task = this.tasks.shift();
+          if (this.state.authenticated)
+            fetch(task.url, task.init)
+              .then((res) => task.resolve(res))
+              .catch((e) => console.log('Error executing pending task: ' + e));
+          else task.reject(new Error('Authentication failed'));
         }
-        return fetch(url, init)
-            .then(response => {
-                if (response.status === 401) {
-                    this.disconnect()
-                    return this.fetch(url, init)
-                }
-                return response
-            })
+      })
+      .catch((e) => {
+        this.authenticating = false;
+        console.log(e);
+      });
+  }
+
+  disconnect() {
+    console.log('Disconnect');
+    this.state.authenticated = false;
+    if (this.onAuthChanged) this.onAuthChanged(this.state);
+  }
+
+  fetch(url, init) {
+    console.log(`fetch ${url}`);
+    if (!this.state.authenticated) {
+      if (!init || !init.method || init.method === 'GET') {
+        return new Promise((resolve, reject) => this.tasks.push({ url, init, resolve, reject }));
+      } else {
+        return new Promise((resolve, reject) => reject('Not authenticated'));
+      }
     }
+    return fetch(url, init).then((response) => {
+      if (response.status === 401) {
+        this.disconnect();
+        return this.fetch(url, init);
+      }
+      return response;
+    });
+  }
 }
 
-export default new AuthManager()
\ No newline at end of file
+export default new AuthManager();
