Vue.use(VueMaterial.default); const getLoginMessageFromError = (json) => { switch (json.message) { case 'ERROR_REQUEST_LOGIN_INVALID': { return 'Invalid username or password.'; } case 'ERROR_ACCESS_DENIED': { return 'You are not allowed to perform this action.' } default: { return 'Unknown error. Something went wrong.' } } } const getSignupMessageFromError = (json) => { switch (json.message) { case 'ERROR_REQUEST_INVALID_DATA': { switch (json.errors[0].param) { case 'username': { return 'Invalid username. Username must be between 3 and 32 characters long, and be alphanumeric.'; } case 'password': { return 'Invalid password. Password must be at least 8 characters long and at most 128 characters.'; } case 'email': { return 'Invalid email.'; } default: { return 'Invalid value sent to server. Something went wrong.'; } } } case 'ERROR_ACCESS_DENIED': { return 'You are not allowed to perform this action.' } case 'ERROR_REQUEST_USERNAME_EXISTS': { return 'That username is taken.'; } default: { return 'Unknown error. Something went wrong.' } } }; const app = new Vue({ el: '#app', data: { usernameInput: '', emailInput: '', passwordInput: '', mode: 'SIGNUP', showSnackbarNotification: false, snackbarNotification: '', snackbarNotificationDuration: 999999, snackbarButtonText: 'Ok', successfulLogin: false, loggedInUser: {} }, mounted: async function() { const res = await fetch(`${window.location.origin}/api/v1/users/current/info`, { method: 'GET', headers: { 'Accept': 'application/json', }, credentials: 'include' }); if (res.status === 200) { const json = await res.json(); if (json.user.permissionLevel >= 1) { this.loggedInUser = json.user; this.mode = 'MANAGE'; } else { this.resetSnackbarButton(); this.notification('Your account has been suspended'); this.successfulLogin = true; } } else { this.mode = 'SIGNUP'; } }, computed: { modeName: function() { switch (this.mode) { case 'SIGNUP': { return 'Sign up'; } case 'LOGIN': { return 'Log in'; } case 'LOADING': { return 'Loading...'; } case 'MANAGE': { return this.loggedInUser.username || 'Unknown account'; } case 'NONE': { return ''; } default: { return 'Something went wrong.'; } } } }, methods: { snackbarButtonAction: function() { this.showSnackbarNotification = false; }, snackbarButtonClick: function() { this.snackbarButtonAction(); }, snackbarEditButton: function(buttonText="Ok", action) { this.snackbarButtonText = buttonText; this.snackbarButtonAction = action; }, resetSnackbarButton: function() { this.snackbarButtonText = 'Ok'; this.snackbarButtonAction = () => { this.showSnackbarNotification = false; }; }, notification: function(text) { this.snackbarNotification = text; this.showSnackbarNotification = true; }, performTokenRemoval: async function() { const res = await fetch(`${window.location.origin}/api/v1/users/browser/token/clear`, { method: 'POST', credentials: 'include' }); if (res.status === 200) { this.loggedInUser = {}; this.snackbarEditButton('Home', () => { window.location.href = `${window.location.origin}`; this.resetSnackbarButton(); this.showSnackbarNotification = false; }); this.successfulLogin = true; this.notification('Successfully logged out'); } else { this.resetSnackbarButton(); this.notification('Could not log out'); } }, navigateHome: function() { window.location.href = `${window.location.origin}`; }, performTokenCreation: async function() { const res = await fetch(`${window.location.origin}/api/v1/users/token/create`, { method: 'POST', headers: { 'Accept': 'application/json', 'Content-Type': 'application/json' }, credentials: 'include', body: JSON.stringify({ username: this.usernameInput, password: this.passwordInput, alsoSetCookie: true }) }); const json = await res.json(); if (json.error || res.status !== 200) { this.resetSnackbarButton(); this.notification(getLoginMessageFromError(json)); return; } else { document.cookie = `token=${json.token}; HTTPOnly=true; max-age=10800`; this.successfulLogin = true; this.snackbarEditButton('Home', () => { this.navigateHome(); this.resetSnackbarButton(); this.showSnackbarNotification = false; }); this.notification(`Successfully logged into account "${json.user.username}"`); this.loggedInUser = { username: json.user.username, _id: json.user._id }; return; } }, performAccountCreation: async function() { const res = await fetch(`${window.location.origin}/api/v1/users/account/create`, { method: 'POST', headers: { 'Accept': 'application/json', 'Content-Type': 'application/json' }, body: JSON.stringify({ username: this.usernameInput, email: this.emailInput, password: this.passwordInput }) }); const json = await res.json(); console.log(json); if (json.error || res.status !== 200) { this.resetSnackbarButton(); this.notification(getSignupMessageFromError(json)); return; } else { this.snackbarEditButton('Login', () => { this.mode = 'LOGIN'; this.resetSnackbarButton(); this.showSnackbarNotification = false; }); this.notification(`Account "${json.user.username}" successfully created`); return; } } } });