1
0
mirror of https://github.com/lus/pasty.git synced 2023-08-10 21:13:09 +03:00

Fix buggy frontend routing

This commit is contained in:
Lukas SP
2020-08-24 18:32:14 +02:00
parent 6b0d0007e2
commit f5357a2c9d
9 changed files with 8 additions and 3 deletions

35
web/assets/js/api.js Normal file
View File

@ -0,0 +1,35 @@
// getAPIInformation returns the API information
export async function getAPIInformation() {
return await fetch(location.protocol + "//" + location.host + "/api/v1/info");
}
// getPaste retrieves a paste
export async function getPaste(id) {
return await fetch(location.protocol + "//" + location.host + "/api/v1/pastes/" + id);
}
// createPaste creates a new paste
export async function createPaste(content) {
return await fetch(location.protocol + "//" + location.host + "/api/v1/pastes", {
method: 'POST',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({
content
})
});
}
// deletePaste deletes a paste
export async function deletePaste(id, deletionToken) {
return await fetch(location.protocol + "//" + location.host + "/api/v1/pastes/" + id, {
method: 'DELETE',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({
deletionToken
})
});
}

61
web/assets/js/autoload.js Normal file
View File

@ -0,0 +1,61 @@
// Import the used modules
import * as api from "./api.js";
import * as buttons from "./buttons.js";
import * as spinner from "./spinner.js";
// Set up the buttons
buttons.setupButtons();
buttons.setupKeybinds();
// Load the API information
async function loadAPIInformation() {
const response = await api.getAPIInformation();
if (response.ok) {
const data = await response.json();
document.getElementById("version").innerText = data.version;
}
}
loadAPIInformation();
// Try to load a paste if one exists
export let PASTE_ID;
async function loadPaste() {
if (location.pathname != "/") {
// Define the paste ID and language
const split = location.pathname.replace("/", "").split(".");
const pasteID = split[0];
const language = split[1];
// Retrieve the paste from the API and redirect the user to the main page if it could not be found
const response = await api.getPaste(pasteID);
if (!response.ok) {
location.replace(location.protocol + "//" + location.host);
return;
}
const data = await response.json();
// Adjust the button states
document.getElementById("btn_save").setAttribute("disabled", true);
document.getElementById("btn_delete").removeAttribute("disabled");
document.getElementById("btn_copy").removeAttribute("disabled");
// Set the paste content to the DOM
document.getElementById("code").innerHTML = language
? hljs.highlight(language, data.content).value
: hljs.highlightAuto(data.content).value;
// Display the line numbers
const lineNumbersElement = document.getElementById("linenos");
data.content.split(/\n/).forEach(function(_currentValue, index) {
lineNumbersElement.innerHTML += "<span>" + (index + 1) + "</span>";
});
// Set the PASTE_ID variable
PASTE_ID = pasteID;
} else {
const input = document.getElementById("input");
input.classList.remove("hidden");
input.focus();
}
}
spinner.surround(loadPaste);

115
web/assets/js/buttons.js Normal file
View File

@ -0,0 +1,115 @@
// Import the used modules
import * as api from "./api.js";
import * as autoload from "./autoload.js";
import * as spinner from "./spinner.js";
// setupKeybinds initializes the keybinds for the buttons
export function setupKeybinds() {
window.onkeydown = function(event) {
// Return if the CTRL key was not pressed
if (!event.ctrlKey) return;
// Define the DOM element of the pressed button
let element = null;
switch (event.keyCode) {
case 81: {
element = document.getElementById("btn_new");
break;
}
case 83: {
element = document.getElementById("btn_save");
break;
}
case 88: {
element = document.getElementById("btn_delete");
break;
}
case 67: {
element = document.getElementById("btn_copy");
break;
}
}
// Call the onClick function of the button
if (element) {
if (element.hasAttribute("disabled")) return;
event.preventDefault();
element.click();
}
}
}
// setupButtons configures the click listeners of the buttons
export function setupButtons() {
// Define the behavior of the 'new' button
document.getElementById("btn_new").addEventListener("click", function() {
location.replace(location.protocol + "//" + location.host);
});
// Define the behavior of the 'save' button
document.getElementById("btn_save").addEventListener("click", function() {
spinner.surround(async function() {
// Return if the text area is empty
const input = document.getElementById("input");
if (!input.value) return;
// Create the paste
const response = await api.createPaste(input.value);
if (!response.ok) {
alert("Error:\n\n" + data);
return;
}
const data = await response.json();
// Redirect the user to the paste page
let address = location.protocol + "//" + location.host + "/" + data.id;
if (data.suggestedSyntaxType) address += "." + data.suggestedSyntaxType;
location.replace(address);
// TODO: Find a solution to display the deletion token
});
});
// Define the behavior of the 'delete' button
document.getElementById("btn_delete").addEventListener("click", function() {
spinner.surround(async function() {
// Ask the user for the deletion token
const deletionToken = window.prompt("Deletion Token:");
if (!deletionToken) return;
// Delete the paste
const response = await api.deletePaste(autoload.PASTE_ID, deletionToken);
const data = await response.text();
if (!response.ok) {
alert("Error:\n\n" + data);
return;
}
// Redirect the user to the main page
location.replace(location.protocol + "//" + location.host);
});
});
// Define the behavior of the 'copy' button
document.getElementById("btn_copy").addEventListener("click", function() {
spinner.surround(async function() {
// Ask for the clipboard permissions
askClipboardPermissions();
// Copy the code
await navigator.clipboard.writeText(document.getElementById("code").innerText);
});
});
}
// askClipboardPermissions asks the user for the clipboard permissions
async function askClipboardPermissions() {
try {
const state = await navigator.permissions.query({
name: "clipbaord-write"
});
return state === "granted";
} catch (error) {
return false;
}
}

19
web/assets/js/spinner.js Normal file
View File

@ -0,0 +1,19 @@
// element holds the spinners DOM element
const element = document.getElementById("spinner");
// show shows the spinner
export function show() {
element.classList.remove("hidden");
}
// hide hides the spinner
export function hide() {
element.classList.add("hidden");
}
// surround surrounds an action with a spinner
export async function surround(action) {
show();
await action();
hide();
}