Initial commit, basic pages and sessions.

This commit is contained in:
DebaucheryLibrarian 2023-05-29 00:54:17 +02:00
commit bc9fec207b
57 changed files with 15967 additions and 0 deletions

14
.editorconfig Executable file
View File

@ -0,0 +1,14 @@
# top-most EditorConfig file
root = true
# Unix-style newlines with a newline ending every file
[*]
end_of_line = lf
insert_final_newline = true
indent_style = tab
indent_size = 4
# Matches multiple files with brace expansion notation
# Set default charset
[*.js]
charset = utf-8

32
.eslintrc Executable file
View File

@ -0,0 +1,32 @@
{
"root": true,
"extends": ["airbnb-base", "plugin:vue/recommended"],
"parserOptions": {
"parser": "@babel/eslint-parser",
"ecmaVersion": 2019,
"sourceType": "module",
"requireConfigFile": false
},
"rules": {
"indent": ["error", "tab"],
"no-tabs": "off",
"no-unused-vars": ["error", {"argsIgnorePattern": "^_"}],
"no-console": 0,
"template-curly-spacing": "off",
"import/prefer-default-export": 0,
"max-len": 0,
"vue/no-v-html": 0,
"vue/html-indent": ["error", "tab"],
"vue/multiline-html-element-content-newline": 0,
"vue/singleline-html-element-content-newline": 0,
"vue/multi-word-component-names": 0,
"no-param-reassign": ["error", {
"props": true,
"ignorePropertyModificationsFor": ["state", "acc"]
}]
},
"globals": {
"CONFIG": "readonly",
"CLIENT_VERSION": "readonly"
}
}

6
.gitignore vendored Normal file
View File

@ -0,0 +1,6 @@
node_modules/
dist/
config/
!config/default.js
assets/js/config/
!assets/js/config/default.js

1
README.md Normal file
View File

@ -0,0 +1 @@
# shack

48
assets/css/forms.css Normal file
View File

@ -0,0 +1,48 @@
.form {
width: 100%;
max-width: 30rem;
display: flex;
flex-direction: column;
}
.form-section {
margin-bottom: 1rem;
}
.form-row {
display: flex;
flex-wrap: wrap;
margin-bottom: .5rem;
.input {
flex-grow: 1;
}
}
.form-column {
display: flex;
flex-grow: 1;
flex-direction: column;
min-width: 10rem;
}
.form-actions {
display: flex;
margin-bottom: .5rem;
justify-content: flex-end;
margin-top: .5rem;
}
.form-heading {
color: var(--primary-light-10);
margin: 0 0 .75rem 0;
}
.form-error {
background: var(--error);
color: var(--text-light);
padding: 1rem;
border-radius: .25rem;
text-align: center;
font-weight: bold;
}

44
assets/css/inputs.css Normal file
View File

@ -0,0 +1,44 @@
.input {
padding: .5rem .75rem;
font-size: 1rem;
flex-basis: 0;
border: solid 1px var(--grey-light-30);
border-radius: .25rem;
font: inherit;
&:focus {
outline: none;
border-color: var(--primary-light-30);
}
}
.button {
padding: .5rem 1rem;
border: none;
border-radius: .25rem;
background: var(--grey-light-30);
font-size: 1rem;
font-weight: bold;
&:focus {
outline: none;
}
}
.button-submit {
background: var(--primary-light-30);
color: var(--text-light);
&:hover:not(:disabled) {
background: var(--primary);
cursor: pointer;
}
&:disabled {
background: var(--shadow-weak-10);
}
}
.radio {
margin: 0 .5rem 0 0;
}

21
assets/css/markdown.css Normal file
View File

@ -0,0 +1,21 @@
.markdown-body {
margin: 0 auto;
max-width: 50rem;
flex-grow: 1;
padding: 1rem;
line-height: 1.5;
text-align: justify;
& h1 {
margin: 0;
}
& h2 {
color: var(--primary);
margin: 1rem 0 0 0;
}
& p {
margin: 0;
}
}

36
assets/css/states.css Executable file
View File

@ -0,0 +1,36 @@
.noselect {
user-select: none;
-webkit-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
-webkit-tap-highlight-color: transparent;
}
.nolist {
list-style: none;
padding: 0;
margin: 0;
li {
display: inline-block;
padding: 0;
margin: 0;
}
}
.nolink {
display: inline-block;
color: inherit;
text-decoration: none;
}
.nobar {
scrollbar-width: none;
-mis-overflow-style: none;
&::-webkit-scrollbar {
background: transparent;
width: 0px;
height: 0px;
}
}

31
assets/css/style.css Normal file
View File

@ -0,0 +1,31 @@
@import 'theme';
@import 'states';
@import 'inputs';
@import 'forms';
@import 'markdown';
html,
body,
#app {
height: 100%;
}
body {
margin: 0;
color: var(--text);
font-family: sans-serif;
}
.link {
color: var(--link);
text-decoration: none;
&:hover {
text-decoration: underline;
}
}
.heading {
margin: 0 0 1rem 0;
color: var(--primary-light-20);
}

34
assets/css/theme.css Normal file
View File

@ -0,0 +1,34 @@
:root {
--primary: hsl(300, 100%, 30%);
--primary-light-10: hsl(300, 50%, 40%);
--primary-light-20: hsl(300, 50%, 50%);
--primary-light-30: hsl(300, 50%, 60%);
--grey-dark-40: #222;
--grey-dark-30: #444;
--grey-dark-20: #666;
--grey-dark-10: #888;
--grey: #aaa;
--grey-light-10: #bbb;
--grey-light-20: #ccc;
--grey-light-30: #ddd;
--grey-light-40: #eee;
--background-dark-20: #eee;
--background-dark-10: #f8f8f8;
--background: #fff;
--shadow-weak-30: rgba(0, 0, 0, .1);
--shadow-weak-20: rgba(0, 0, 0, .2);
--shadow-weak-10: rgba(0, 0, 0, .35);
--shadow: rgba(0, 0, 0, .5);
--shadow-strong-10: rgba(0, 0, 0, .6);
--shadow-strong-20: rgba(0, 0, 0, .75);
--shadow-strong-30: rgba(0, 0, 0, .9);
--text: #222;
--text-light: #fff;
--link: #48f;
--error: #f66;
}

71
assets/img/favicon.svg Normal file
View File

@ -0,0 +1,71 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Created with Inkscape (http://www.inkscape.org/) -->
<svg
width="22.806mm"
height="22.806mm"
viewBox="0 0 22.806 22.805999"
version="1.1"
id="svg5"
sodipodi:docname="favicon.svg"
inkscape:version="1.2.2 (b0a8486541, 2022-12-01)"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns="http://www.w3.org/2000/svg"
xmlns:svg="http://www.w3.org/2000/svg">
<sodipodi:namedview
id="namedview7"
pagecolor="#ffffff"
bordercolor="#000000"
borderopacity="0.25"
inkscape:showpageshadow="2"
inkscape:pageopacity="0.0"
inkscape:pagecheckerboard="0"
inkscape:deskcolor="#d1d1d1"
inkscape:document-units="mm"
showgrid="false"
inkscape:zoom="5.4247457"
inkscape:cx="35.024683"
inkscape:cy="42.674811"
inkscape:window-width="1920"
inkscape:window-height="1020"
inkscape:window-x="0"
inkscape:window-y="32"
inkscape:window-maximized="1"
inkscape:current-layer="layer1" />
<defs
id="defs2">
<linearGradient
id="linearGradient2720"
inkscape:swatch="solid">
<stop
style="stop-color:#000000;stop-opacity:1;"
offset="0"
id="stop2718" />
</linearGradient>
</defs>
<g
inkscape:label="Layer 1"
inkscape:groupmode="layer"
id="layer1"
transform="translate(-81.250065,-117.45377)">
<g
aria-label="shack"
id="text236"
style="font-size:35.2777px;font-family:LOVES;-inkscape-font-specification:LOVES;stroke-width:0.264583"
transform="translate(1.8428824)">
<g
id="g2730"
style="stroke-width:0.265;stroke-dasharray:none">
<path
d="m 95.564404,131.63031 -4.478614,-11.07596 -4.788672,11.07596 z m 4.805896,8.62994 h -1.309132 l -3.014451,-7.44139 H 85.780355 l -3.221157,7.44139 h -1.309133 l 9.870176,-22.80648 z"
id="path2625"
style="fill:#880088;fill-opacity:1;stroke:none;stroke-width:0.265;stroke-dasharray:none;stroke-opacity:1" />
</g>
</g>
<path
style="color:#000000;fill:#880088;fill-opacity:1;-inkscape-stroke:none"
d="m 90.289784,134.44531 v 5.81446 h 1 v -4.81446 h 2.726562 v 4.81446 h 1 v -5.81446 z"
id="path2716" />
</g>
</svg>

After

Width:  |  Height:  |  Size: 2.3 KiB

83
assets/img/logo.svg Normal file
View File

@ -0,0 +1,83 @@
<svg
width="106.43599mm"
height="23.46104mm"
viewBox="0 0 106.43599 23.46104"
version="1.1"
id="svg5"
sodipodi:docname="logo.svg"
inkscape:version="1.2.2 (b0a8486541, 2022-12-01)"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns="http://www.w3.org/2000/svg"
xmlns:svg="http://www.w3.org/2000/svg">
<sodipodi:namedview
id="namedview7"
pagecolor="#ffffff"
bordercolor="#000000"
borderopacity="0.25"
inkscape:showpageshadow="2"
inkscape:pageopacity="0.0"
inkscape:pagecheckerboard="0"
inkscape:deskcolor="#d1d1d1"
inkscape:document-units="mm"
showgrid="false"
inkscape:zoom="8.2527944"
inkscape:cx="181.87779"
inkscape:cy="65.977652"
inkscape:window-width="1920"
inkscape:window-height="1020"
inkscape:window-x="0"
inkscape:window-y="32"
inkscape:window-maximized="1"
inkscape:current-layer="layer1" />
<defs
id="defs2">
<linearGradient
id="linearGradient2720"
inkscape:swatch="solid">
<stop
style="stop-color:#000000;stop-opacity:1;"
offset="0"
id="stop2718" />
</linearGradient>
</defs>
<g
inkscape:label="Layer 1"
inkscape:groupmode="layer"
id="layer1"
transform="translate(-40.339649,-117.14372)">
<g
aria-label="shack"
id="text236"
style="font-size:35.2777px;font-family:LOVES;-inkscape-font-specification:LOVES;stroke-width:0.264583">
<g
id="g2730"
style="stroke-width:0.265;stroke-dasharray:none">
<path
d="m 47.488206,140.38083 q -2.170405,0 -4.168556,-0.99907 -1.998151,-1.0163 -2.980001,-3.13503 l 1.102428,-0.46509 q 1.016301,2.15318 3.203932,2.92832 1.412486,0.49954 2.842197,0.49954 2.652718,0 4.530291,-1.48139 1.309133,-1.03352 1.378035,-2.87664 -0.05168,-2.20486 -3.152256,-4.01353 -1.291907,-0.74069 -2.56659,-1.34359 -3.858498,-1.80867 -5.787747,-4.09965 -1.102428,-1.30913 -1.102428,-2.66994 0,-1.87758 1.274682,-3.29006 1.291908,-1.41249 3.634568,-1.94648 0.98185,-0.22393 1.980925,-0.22393 0.740694,0 1.980926,0.20671 1.257457,0.18948 2.721619,1.17133 1.481388,0.98185 2.273758,2.73884 l -1.102428,0.44786 q -1.033527,-2.1704 -3.203932,-2.92832 -1.343584,-0.46509 -2.687168,-0.46509 -2.687169,0 -4.478614,1.53307 -1.188556,1.0163 -1.188556,2.82497 0.120578,1.24023 1.257457,2.37711 1.136879,1.11965 2.53214,1.98093 1.39526,0.84404 2.428787,1.2919 1.360809,0.63734 2.790521,1.49862 1.446937,0.86127 2.497688,2.06705 1.050752,1.20578 1.102428,2.8422 -0.03445,1.99815 -1.446936,3.42786 -1.412486,1.42971 -3.841273,1.92925 -0.895723,0.17225 -1.825897,0.17225 z"
id="path2621"
style="stroke-width:0.265;stroke-dasharray:none" />
<path
d="m 76.719776,140.26025 h -1.205781 v -10.7659 H 60.510638 v 10.7659 h -1.188555 v -22.77203 h 1.188555 v 10.80035 h 15.003357 v -10.80035 h 1.205781 z"
id="path2623"
style="stroke-width:0.265;stroke-dasharray:none" />
<path
d="m 95.564404,131.63031 -4.478614,-11.07596 -4.788672,11.07596 z m 4.805896,8.62994 h -1.309132 l -3.014451,-7.44139 H 85.780355 l -3.221157,7.44139 h -1.309133 l 9.870176,-22.80648 z"
id="path2625"
style="stroke-width:0.265;stroke-dasharray:none" />
<path
d="m 114.54684,140.58754 q -3.23838,0 -5.90833,-1.58474 -2.66994,-1.58474 -4.25468,-4.23746 -1.58474,-2.66994 -1.58474,-5.8911 0,-3.23838 1.58474,-5.8911 1.58474,-2.66994 4.25468,-4.25468 2.66995,-1.58474 5.90833,-1.58474 3.41064,0 6.16671,1.73976 2.77329,1.73977 4.28913,4.61642 h -1.42971 q -1.41249,-2.34266 -3.7896,-3.73792 -2.35988,-1.41248 -5.23653,-1.41248 -2.89387,0 -5.27099,1.42971 -2.37711,1.41248 -3.80682,3.80682 -1.41248,2.37711 -1.41248,5.28821 0,2.89387 1.41248,5.28821 1.42971,2.37711 3.80682,3.80682 2.37712,1.41249 5.27099,1.41249 2.66994,0 4.90925,-1.22301 2.25653,-1.22301 3.70347,-3.30728 h 1.48139 q -1.56752,2.61826 -4.22024,4.18578 -2.65271,1.55029 -5.87387,1.55029 z"
id="path2627"
style="stroke-width:0.265;stroke-dasharray:none" />
<path
d="m 130.58373,140.60476 v -23.11654 h 1.20578 v 19.03411 l 12.21284,-19.03411 h 1.41248 l -7.83757,12.21284 9.19838,10.55919 h -1.58474 l -8.26821,-9.52566 z"
id="path2629"
style="stroke-width:0.265;stroke-dasharray:none" />
</g>
</g>
<path
style="color:#000000;-inkscape-stroke:none"
d="m 88.447266,134.44531 v 5.81446 h 1 v -4.81446 h 2.726562 v 4.81446 h 1 v -5.81446 z"
id="path2716" />
</g>
</svg>

After

Width:  |  Height:  |  Size: 4.6 KiB

BIN
assets/img/logo_pixels.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 17 KiB

86
assets/js/api.js Normal file
View File

@ -0,0 +1,86 @@
const postHeaders = {
mode: 'cors',
credentials: 'same-origin',
headers: {
'Content-Type': 'application/json',
},
};
function getQuery(data) {
if (!data) {
return '';
}
return `?${new URLSearchParams(data).toString()}`;
}
export async function get(path, query = {}) {
const res = await fetch(`${path}${getQuery(query)}`);
const body = await res.json();
if (res.ok) {
return body;
}
throw new Error(body.message);
}
export async function post(path, data, { query } = {}) {
const res = await fetch(`${path}${getQuery(query)}`, {
method: 'POST',
body: JSON.stringify(data),
...postHeaders,
});
if (res.status === 204) {
return null;
}
const body = await res.json();
if (res.ok) {
return body;
}
throw new Error(body.message);
}
export async function patch(path, data, { query } = {}) {
const res = await fetch(`${path}${getQuery(query)}`, {
method: 'PATCH',
body: JSON.stringify(data),
...postHeaders,
});
if (res.status === 204) {
return null;
}
const body = await res.json();
if (res.ok) {
return body;
}
throw new Error(body.message);
}
export async function del(path, { data, query } = {}) {
const res = await fetch(`${path}${getQuery(query)}`, {
method: 'DELETE',
body: JSON.stringify(data),
...postHeaders,
});
if (res.status === 204) {
return null;
}
const body = await res.json();
if (res.ok) {
return body;
}
throw new Error(body.message);
}

4
assets/js/navigate.js Normal file
View File

@ -0,0 +1,4 @@
// centralize navigation to simplify switching between client and server routing
export default function navigate(path) {
window.location.href = path;
}

110
components/form/checkbox.vue Executable file
View File

@ -0,0 +1,110 @@
<template>
<label class="check-container noselect">
<span
v-if="label"
class="check-label"
>{{ label }}</span>
<input
v-show="false"
:id="`checkbox-${uid}`"
:checked="checked"
type="checkbox"
class="check-checkbox"
@change="$emit('change', $event.target.checked)"
>
<label
:for="`checkbox-${uid}`"
class="check"
/>
</label>
</template>
<script>
import { nanoid } from 'nanoid';
export default {
props: {
checked: {
type: Boolean,
default: false,
},
label: {
type: String,
default: null,
},
},
emits: ['change'],
data() {
return {
uid: nanoid(),
};
},
};
</script>
<style>
.check-container {
display: flex;
justify-content: space-between;
align-items: center;
cursor: pointer;
padding: .25rem 0;
}
.check {
width: 1.25rem;
height: 1.25rem;
display: flex;
align-items: center;
justify-content: center;
flex-shrink: 0;
position: relative;
border-radius: .25rem;
background-color: var(--shadow-weak-20);
cursor: pointer;
transition: background .15s ease;
&::after {
content: '';
width: .5rem;
height: .3rem;
border: solid 2px var(--text-light);
border-top: none;
border-right: none;
margin: -.2rem 0 0 0;
transform: rotateZ(-45deg) scaleX(0);
transition: transform .15s ease;
}
}
.check-cross .check::before {
content: '';
width: 100%;
height: 100%;
position: absolute;
background: url('/img/icons/cross3.svg') no-repeat center/80%;
opacity: .15;
transition: transform .1s ease;
}
.check-checkbox:checked + .check {
background: var(--primary);
&::after {
transform: rotateZ(-45deg) scaleX(1);
}
&::before {
transform: scaleX(0);
}
}
.check-label {
overflow: hidden;
text-transform: capitalize;
text-overflow: ellipsis;
margin: 0 .5rem 0 0;
}
</style>

6
knexfile.js Executable file
View File

@ -0,0 +1,6 @@
const config = require('config');
module.exports = {
client: 'pg',
connection: config.database,
};

15
log/2023-05-26.log Normal file
View File

@ -0,0 +1,15 @@
2023-05-26 22:00:04 info [/home/niels/Projects/shack/src/web/server.js] Server running at :::7477
2023-05-26 22:01:41 info [server] Server running at :::7477
2023-05-26 22:02:51 info [server] Server running at :::7477
2023-05-26 22:13:32 info [server] Server running at :::7477
2023-05-26 22:14:07 info [server] Server running at :::7477
2023-05-26 22:14:56 info [server] Server running at :::7477
2023-05-26 22:15:07 info [server] Server running at :::7477
2023-05-26 22:15:33 info [server] Server running at :::7477
2023-05-26 22:16:20 info [server] Server running at :::7477
2023-05-26 22:16:33 info [server] Server running at :::7477
2023-05-26 22:23:24 info [server] Server running at :::7477
2023-05-26 23:50:58 info [server] Server running at :::7477
2023-05-26 23:52:16 info [server] Server running at :::7477
2023-05-26 23:59:17 info [server] Server running at :::7477
2023-05-26 23:59:40 info [server] Server running at :::7477

42
log/2023-05-27.log Normal file
View File

@ -0,0 +1,42 @@
2023-05-27 00:02:12 info [server] Server running at :::7477
2023-05-27 00:02:53 info [server] Server running at :::7477
2023-05-27 00:03:46 info [server] Server running at :::7477
2023-05-27 16:31:42 info [server] Server running at :::7477
2023-05-27 17:15:42 info [server] Server running at :::7477
2023-05-27 17:24:43 info [server] Server running at :::7477
2023-05-27 17:28:55 info [server] Server running at :::7477
2023-05-27 17:30:14 info [server] Server running at :::7477
2023-05-27 17:30:48 info [server] Server running at :::7477
2023-05-27 17:31:08 info [server] Server running at :::7477
2023-05-27 17:34:32 info [server] Server running at :::7477
2023-05-27 17:53:55 info [server] Server running at :::7477
2023-05-27 22:40:18 info [server] Server running at :::7477
2023-05-27 22:48:27 info [server] Server running at :::7477
2023-05-27 23:23:00 info [server] Server running at :::7477
2023-05-27 23:29:39 info [server] Server running at :::7477
2023-05-27 23:36:51 info [server] Server running at :::7477
2023-05-27 23:41:25 info [server] Server running at :::7477
2023-05-27 23:45:38 info [server] Server running at :::7477
2023-05-27 23:46:09 info [users] Registered user admin (1, undefined, ::ffff:127.0.0.1)
2023-05-27 23:47:00 info [server] Server running at :::7477
2023-05-27 23:47:51 info [server] Server running at :::7477
2023-05-27 23:54:47 info [server] Server running at :::7477
2023-05-27 23:55:07 info [server] Server running at :::7477
2023-05-27 23:55:23 info [server] Server running at :::7477
2023-05-27 23:55:31 warn [error] Failed to fulfill request to /api/users: Username or e-mail already registered
2023-05-27 23:55:31 error [error] HttpError: Username or e-mail already registered
at createUser (/home/niels/Projects/shack/src/users.js:129:10)
at processTicksAndRejections (node:internal/process/task_queues:96:5)
at async createUserApi (/home/niels/Projects/shack/src/web/users.js:4:15)
2023-05-27 23:56:25 info [server] Server running at :::7477
2023-05-27 23:57:11 info [server] Server running at :::7477
2023-05-27 23:57:17 warn [error] Failed to fulfill request to /api/users: Username or e-mail already registered
2023-05-27 23:57:17 error [error] HttpError: Username or e-mail already registered
at createUser (/home/niels/Projects/shack/src/users.js:129:10)
at processTicksAndRejections (node:internal/process/task_queues:96:5)
at async createUserApi (/home/niels/Projects/shack/src/web/users.js:4:15)
2023-05-27 23:58:08 warn [error] Failed to fulfill request to /api/users: Username or e-mail already registered
2023-05-27 23:58:08 error [error] HttpError: Username or e-mail already registered
at createUser (/home/niels/Projects/shack/src/users.js:129:10)
at processTicksAndRejections (node:internal/process/task_queues:96:5)
at async createUserApi (/home/niels/Projects/shack/src/web/users.js:4:15)

269
log/2023-05-28.log Normal file
View File

@ -0,0 +1,269 @@
2023-05-28 00:08:00 info [server] Server running at :::7477
2023-05-28 00:11:09 info [server] Server running at :::7477
2023-05-28 00:14:04 info [server] Server running at :::7477
2023-05-28 00:21:15 info [server] Server running at :::7477
2023-05-28 00:22:47 info [server] Server running at :::7477
2023-05-28 00:36:00 info [server] Server running at :::7477
2023-05-28 00:36:38 info [server] Server running at :::7477
2023-05-28 00:39:32 info [server] Server running at :::7477
2023-05-28 00:41:42 info [server] Server running at :::7477
2023-05-28 00:44:41 info [server] Server running at :::7477
2023-05-28 01:06:18 info [server] Server running at :::7477
2023-05-28 01:06:43 info [server] Server running at :::7477
2023-05-28 01:09:47 info [server] Server running at :::7477
2023-05-28 01:10:11 info [server] Server running at :::7477
2023-05-28 01:11:03 info [server] Server running at :::7477
2023-05-28 01:11:33 info [server] Server running at :::7477
2023-05-28 01:11:46 info [server] Server running at :::7477
2023-05-28 01:12:07 info [server] Server running at :::7477
2023-05-28 01:12:37 info [server] Server running at :::7477
2023-05-28 01:15:28 info [server] Server running at :::7477
2023-05-28 01:16:12 info [server] Server running at :::7477
2023-05-28 01:17:01 info [server] Server running at :::7477
2023-05-28 01:17:28 info [server] Server running at :::7477
2023-05-28 01:17:38 info [server] Server running at :::7477
2023-05-28 01:20:33 info [server] Server running at :::7477
2023-05-28 01:22:29 info [server] Server running at :::7477
2023-05-28 01:23:20 info [server] Server running at :::7477
2023-05-28 01:23:38 info [server] Server running at :::7477
2023-05-28 01:24:21 info [server] Server running at :::7477
2023-05-28 01:24:39 info [server] Server running at :::7477
2023-05-28 01:26:25 info [server] Server running at :::7477
2023-05-28 01:28:39 info [server] Server running at :::7477
2023-05-28 01:29:11 info [server] Server running at :::7477
2023-05-28 01:30:10 info [server] Server running at :::7477
2023-05-28 01:31:36 info [server] Server running at :::7477
2023-05-28 01:31:46 info [server] Server running at :::7477
2023-05-28 01:31:47 warn [error] Failed to fulfill request to /: secret option required for sessions
2023-05-28 01:31:47 warn [error] Failed to fulfill request to /favicon.ico: secret option required for sessions
2023-05-28 01:32:32 info [server] Server running at :::7477
2023-05-28 01:32:34 warn [error] Failed to fulfill request to /: secret option required for sessions
2023-05-28 01:32:34 warn [error] Failed to fulfill request to /favicon.ico: secret option required for sessions
2023-05-28 01:32:45 info [server] Server running at :::7477
2023-05-28 01:32:56 info [server] Server running at :::7477
2023-05-28 01:34:50 info [server] Server running at :::7477
2023-05-28 01:36:08 info [server] Server running at :::7477
2023-05-28 01:36:25 info [server] Server running at :::7477
2023-05-28 02:09:21 info [server] Server running at :::7477
2023-05-28 02:11:16 info [server] Server running at :::7477
2023-05-28 02:11:58 info [server] Server running at :::7477
2023-05-28 02:13:02 info [server] Server running at :::7477
2023-05-28 02:14:03 info [server] Server running at :::7477
2023-05-28 02:18:24 info [redis] Redis module initialized
2023-05-28 02:18:25 info [server] Server running at :::7477
2023-05-28 02:19:39 info [redis] Redis module initialized
2023-05-28 02:19:39 info [server] Server running at :::7477
2023-05-28 02:20:44 info [redis] Redis module initialized
2023-05-28 02:20:44 info [server] Server running at :::7477
2023-05-28 16:06:50 info [redis] Redis module initialized
2023-05-28 16:06:50 info [server] Server running at :::7477
2023-05-28 17:45:15 info [redis] Redis module initialized
2023-05-28 17:45:16 info [server] Server running at :::7477
2023-05-28 21:22:50 info [redis] Redis module initialized
2023-05-28 21:22:51 info [server] Server running at :::7477
2023-05-28 21:25:31 info [redis] Redis module initialized
2023-05-28 21:25:31 info [server] Server running at :::7477
2023-05-28 21:25:46 info [redis] Redis module initialized
2023-05-28 21:25:46 info [server] Server running at :::7477
2023-05-28 21:25:56 warn [error] Failed to fulfill request to /api/session: Username or password incorrect
2023-05-28 21:25:56 error [error] HttpError: Username or password incorrect
at verifyPassword (/home/niels/Projects/shack/src/users.js:31:9)
at async login (/home/niels/Projects/shack/src/users.js:86:2)
at async loginApi (/home/niels/Projects/shack/src/web/users.js:7:15)
2023-05-28 21:26:02 warn [error] Failed to fulfill request to /api/session: The client is closed
2023-05-28 21:26:02 error [error] Error: The client is closed
at Commander._RedisClient_sendCommand (/home/niels/Projects/shack/node_modules/@redis/client/dist/lib/client/index.js:490:31)
at Commander.commandsExecutor (/home/niels/Projects/shack/node_modules/@redis/client/dist/lib/client/index.js:188:154)
at Commander.BaseClass.<computed> [as set] (/home/niels/Projects/shack/node_modules/@redis/client/dist/lib/commander.js:8:29)
at Object.set (/home/niels/Projects/shack/node_modules/connect-redis/dist/cjs/index.js:24:34)
at RedisStore.set (/home/niels/Projects/shack/node_modules/connect-redis/dist/cjs/index.js:71:39)
at Session.save (/home/niels/Projects/shack/node_modules/express-session/session/session.js:72:25)
at Session.save (/home/niels/Projects/shack/node_modules/express-session/index.js:406:15)
at ServerResponse.end (/home/niels/Projects/shack/node_modules/express-session/index.js:335:21)
at ServerResponse.send (/home/niels/Projects/shack/node_modules/express/lib/response.js:232:10)
at ServerResponse.response.send (/home/niels/Projects/shack/node_modules/errors/lib/errors.js:753:22)
at ServerResponse.json (/home/niels/Projects/shack/node_modules/express/lib/response.js:278:15)
at ServerResponse.send (/home/niels/Projects/shack/node_modules/express/lib/response.js:162:21)
at ServerResponse.response.send (/home/niels/Projects/shack/node_modules/errors/lib/errors.js:753:22)
at loginApi (/home/niels/Projects/shack/src/web/users.js:14:6)
2023-05-28 21:26:02 warn [error] Failed to fulfill request to /: The client is closed
2023-05-28 21:26:02 error [error] Error: The client is closed
at Commander._RedisClient_sendCommand (/home/niels/Projects/shack/node_modules/@redis/client/dist/lib/client/index.js:490:31)
at Commander.commandsExecutor (/home/niels/Projects/shack/node_modules/@redis/client/dist/lib/client/index.js:188:154)
at Commander.BaseClass.<computed> [as get] (/home/niels/Projects/shack/node_modules/@redis/client/dist/lib/commander.js:8:29)
at Object.get (/home/niels/Projects/shack/node_modules/connect-redis/dist/cjs/index.js:20:34)
at RedisStore.get (/home/niels/Projects/shack/node_modules/connect-redis/dist/cjs/index.js:53:42)
at session (/home/niels/Projects/shack/node_modules/express-session/index.js:485:11)
at handleReturn (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:24:23)
at session (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:64:7)
at Layer.handle [as handle_request] (/home/niels/Projects/shack/node_modules/express/lib/router/layer.js:95:5)
at trim_prefix (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:328:13)
at /home/niels/Projects/shack/node_modules/express/lib/router/index.js:286:9
at Function.process_params (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:346:12)
at next (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:280:10)
at Function.handle (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:175:3)
at router (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:47:12)
at Layer.handle [as handle_request] (/home/niels/Projects/shack/node_modules/express/lib/router/layer.js:95:5)
at trim_prefix (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:328:13)
at /home/niels/Projects/shack/node_modules/express/lib/router/index.js:286:9
at Function.process_params (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:346:12)
at Immediate.next (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:280:10)
at processImmediate (node:internal/timers:468:21)
2023-05-28 21:26:30 info [redis] Redis module initialized
2023-05-28 21:26:30 info [server] Server running at :::7477
2023-05-28 21:26:37 warn [error] Failed to fulfill request to /api/session: Username or password incorrect
2023-05-28 21:26:37 error [error] HttpError: Username or password incorrect
at verifyPassword (/home/niels/Projects/shack/src/users.js:31:9)
at async login (/home/niels/Projects/shack/src/users.js:86:2)
at async loginApi (/home/niels/Projects/shack/src/web/users.js:7:15)
2023-05-28 21:51:08 info [redis] Redis module initialized
2023-05-28 21:51:25 info [redis] Redis module initialized
2023-05-28 21:51:25 info [server] Server running at 0.0.0.0:7477
2023-05-28 21:55:59 info [redis] Redis module initialized
2023-05-28 21:55:59 info [server] Server running at 0.0.0.0:7477
2023-05-28 21:56:12 info [redis] Redis module initialized
2023-05-28 21:56:12 info [server] Server running at 0.0.0.0:7477
2023-05-28 22:01:38 info [redis] Redis module initialized
2023-05-28 22:01:39 info [server] Server running at 0.0.0.0:7477
2023-05-28 22:05:13 info [redis] Redis module initialized
2023-05-28 22:05:13 info [server] Server running at 0.0.0.0:7477
2023-05-28 22:06:29 info [redis] Redis module initialized
2023-05-28 22:06:30 info [server] Server running at 0.0.0.0:7477
2023-05-28 22:09:37 info [redis] Redis module initialized
2023-05-28 22:09:37 info [server] Server running at 0.0.0.0:7477
2023-05-28 22:10:01 info [redis] Redis module initialized
2023-05-28 22:10:01 info [server] Server running at 0.0.0.0:7477
2023-05-28 23:17:39 info [redis] Redis module initialized
2023-05-28 23:17:39 info [server] Server running at 0.0.0.0:7477
2023-05-28 23:19:24 info [redis] Redis module initialized
2023-05-28 23:19:25 info [server] Server running at 0.0.0.0:7477
2023-05-28 23:20:09 info [redis] Redis module initialized
2023-05-28 23:20:09 info [server] Server running at 0.0.0.0:7477
2023-05-28 23:37:14 info [redis] Redis module initialized
2023-05-28 23:37:14 info [server] Server running at 0.0.0.0:7477
2023-05-28 23:42:22 info [redis] Redis module initialized
2023-05-28 23:42:22 info [server] Server running at 0.0.0.0:7477
2023-05-28 23:49:02 info [redis] Redis module initialized
2023-05-28 23:49:02 info [server] Server running at 0.0.0.0:7477
2023-05-28 23:49:03 warn [error] Failed to fulfill request to /: [vite-plugin-ssr@0.4.126][Wrong Usage][renderPage(pageContextInit)] You passed 2 arguments but `renderPage()` accepts only one argument.'
2023-05-28 23:49:03 error [error] Error: [vite-plugin-ssr@0.4.126][Wrong Usage][renderPage(pageContextInit)] You passed 2 arguments but `renderPage()` accepts only one argument.'
at assertArguments (/home/niels/Projects/shack/node_modules/vite-plugin-ssr/dist/cjs/node/runtime/renderPage/assertArguments.js:10:29)
at renderPage (/home/niels/Projects/shack/node_modules/vite-plugin-ssr/dist/cjs/node/runtime/renderPage.js:19:43)
at defaultHandler (/home/niels/Projects/shack/src/web/default.js:10:29)
at handleReturn (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:24:23)
at defaultHandler (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:64:7)
at handleReturn (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:24:23)
at defaultHandler (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:64:7)
at Layer.handle [as handle_request] (/home/niels/Projects/shack/node_modules/express/lib/router/layer.js:95:5)
at next (/home/niels/Projects/shack/node_modules/express/lib/router/route.js:144:13)
at Route.dispatch (/home/niels/Projects/shack/node_modules/express/lib/router/route.js:114:3)
at Layer.handle [as handle_request] (/home/niels/Projects/shack/node_modules/express/lib/router/layer.js:95:5)
at /home/niels/Projects/shack/node_modules/express/lib/router/index.js:284:15
at param (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:365:14)
at param (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:376:14)
at Function.process_params (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:421:3)
at next (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:280:10)
at jsonParser (/home/niels/Projects/shack/node_modules/body-parser/lib/types/json.js:113:7)
at handleReturn (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:24:23)
at jsonParser (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:64:7)
at Layer.handle [as handle_request] (/home/niels/Projects/shack/node_modules/express/lib/router/layer.js:95:5)
at trim_prefix (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:328:13)
at /home/niels/Projects/shack/node_modules/express/lib/router/index.js:286:9
at Function.process_params (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:346:12)
at next (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:280:10)
at setIp (/home/niels/Projects/shack/src/web/ip.js:15:2)
at handleReturn (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:24:23)
at setIp (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:64:7)
at Layer.handle [as handle_request] (/home/niels/Projects/shack/node_modules/express/lib/router/layer.js:95:5)
at trim_prefix (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:328:13)
at /home/niels/Projects/shack/node_modules/express/lib/router/index.js:286:9
at Function.process_params (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:346:12)
at next (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:280:10)
at /home/niels/Projects/shack/node_modules/express-session/index.js:506:7
at RedisStore.get (/home/niels/Projects/shack/node_modules/connect-redis/dist/cjs/index.js:56:20)
2023-05-28 23:49:03 warn [error] Failed to fulfill request to /: [vite-plugin-ssr@0.4.126][Wrong Usage][renderPage(pageContextInit)] You passed 2 arguments but `renderPage()` accepts only one argument.'
2023-05-28 23:49:03 error [error] Error: [vite-plugin-ssr@0.4.126][Wrong Usage][renderPage(pageContextInit)] You passed 2 arguments but `renderPage()` accepts only one argument.'
at assertArguments (/home/niels/Projects/shack/node_modules/vite-plugin-ssr/dist/cjs/node/runtime/renderPage/assertArguments.js:10:29)
at renderPage (/home/niels/Projects/shack/node_modules/vite-plugin-ssr/dist/cjs/node/runtime/renderPage.js:19:43)
at defaultHandler (/home/niels/Projects/shack/src/web/default.js:10:29)
at handleReturn (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:24:23)
at defaultHandler (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:64:7)
at handleReturn (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:24:23)
at defaultHandler (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:64:7)
at Layer.handle [as handle_request] (/home/niels/Projects/shack/node_modules/express/lib/router/layer.js:95:5)
at next (/home/niels/Projects/shack/node_modules/express/lib/router/route.js:144:13)
at Route.dispatch (/home/niels/Projects/shack/node_modules/express/lib/router/route.js:114:3)
at Layer.handle [as handle_request] (/home/niels/Projects/shack/node_modules/express/lib/router/layer.js:95:5)
at /home/niels/Projects/shack/node_modules/express/lib/router/index.js:284:15
at param (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:365:14)
at param (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:376:14)
at Function.process_params (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:421:3)
at next (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:280:10)
at jsonParser (/home/niels/Projects/shack/node_modules/body-parser/lib/types/json.js:113:7)
at handleReturn (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:24:23)
at jsonParser (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:64:7)
at Layer.handle [as handle_request] (/home/niels/Projects/shack/node_modules/express/lib/router/layer.js:95:5)
at trim_prefix (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:328:13)
at /home/niels/Projects/shack/node_modules/express/lib/router/index.js:286:9
at Function.process_params (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:346:12)
at next (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:280:10)
at setIp (/home/niels/Projects/shack/src/web/ip.js:15:2)
at handleReturn (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:24:23)
at setIp (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:64:7)
at Layer.handle [as handle_request] (/home/niels/Projects/shack/node_modules/express/lib/router/layer.js:95:5)
at trim_prefix (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:328:13)
at /home/niels/Projects/shack/node_modules/express/lib/router/index.js:286:9
at Function.process_params (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:346:12)
at next (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:280:10)
at /home/niels/Projects/shack/node_modules/express-session/index.js:506:7
at RedisStore.get (/home/niels/Projects/shack/node_modules/connect-redis/dist/cjs/index.js:56:20)
2023-05-28 23:49:20 info [redis] Redis module initialized
2023-05-28 23:49:20 info [server] Server running at 0.0.0.0:7477
2023-05-28 23:49:21 warn [error] Failed to fulfill request to /: [vite-plugin-ssr@0.4.126][Wrong Usage][renderPage(pageContextInit)] You passed 2 arguments but `renderPage()` accepts only one argument.'
2023-05-28 23:49:21 error [error] Error: [vite-plugin-ssr@0.4.126][Wrong Usage][renderPage(pageContextInit)] You passed 2 arguments but `renderPage()` accepts only one argument.'
at assertArguments (/home/niels/Projects/shack/node_modules/vite-plugin-ssr/dist/cjs/node/runtime/renderPage/assertArguments.js:10:29)
at renderPage (/home/niels/Projects/shack/node_modules/vite-plugin-ssr/dist/cjs/node/runtime/renderPage.js:19:43)
at defaultHandler (/home/niels/Projects/shack/src/web/default.js:10:29)
at handleReturn (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:24:23)
at defaultHandler (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:64:7)
at handleReturn (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:24:23)
at defaultHandler (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:64:7)
at Layer.handle [as handle_request] (/home/niels/Projects/shack/node_modules/express/lib/router/layer.js:95:5)
at next (/home/niels/Projects/shack/node_modules/express/lib/router/route.js:144:13)
at Route.dispatch (/home/niels/Projects/shack/node_modules/express/lib/router/route.js:114:3)
at Layer.handle [as handle_request] (/home/niels/Projects/shack/node_modules/express/lib/router/layer.js:95:5)
at /home/niels/Projects/shack/node_modules/express/lib/router/index.js:284:15
at param (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:365:14)
at param (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:376:14)
at Function.process_params (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:421:3)
at next (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:280:10)
at jsonParser (/home/niels/Projects/shack/node_modules/body-parser/lib/types/json.js:113:7)
at handleReturn (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:24:23)
at jsonParser (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:64:7)
at Layer.handle [as handle_request] (/home/niels/Projects/shack/node_modules/express/lib/router/layer.js:95:5)
at trim_prefix (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:328:13)
at /home/niels/Projects/shack/node_modules/express/lib/router/index.js:286:9
at Function.process_params (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:346:12)
at next (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:280:10)
at setIp (/home/niels/Projects/shack/src/web/ip.js:15:2)
at handleReturn (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:24:23)
at setIp (/home/niels/Projects/shack/node_modules/express-promise-router/lib/express-promise-router.js:64:7)
at Layer.handle [as handle_request] (/home/niels/Projects/shack/node_modules/express/lib/router/layer.js:95:5)
at trim_prefix (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:328:13)
at /home/niels/Projects/shack/node_modules/express/lib/router/index.js:286:9
at Function.process_params (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:346:12)
at next (/home/niels/Projects/shack/node_modules/express/lib/router/index.js:280:10)
at /home/niels/Projects/shack/node_modules/express-session/index.js:506:7
at RedisStore.get (/home/niels/Projects/shack/node_modules/connect-redis/dist/cjs/index.js:56:20)
2023-05-28 23:50:21 info [redis] Redis module initialized
2023-05-28 23:50:22 info [server] Server running at 0.0.0.0:7477
2023-05-28 23:54:06 info [redis] Redis module initialized
2023-05-28 23:54:06 info [server] Server running at 0.0.0.0:7477
2023-05-28 23:55:47 info [redis] Redis module initialized
2023-05-28 23:55:47 info [server] Server running at 0.0.0.0:7477
2023-05-28 23:56:21 info [redis] Redis module initialized
2023-05-28 23:56:22 info [server] Server running at 0.0.0.0:7477
2023-05-28 23:57:23 info [redis] Redis module initialized
2023-05-28 23:57:24 info [server] Server running at 0.0.0.0:7477
2023-05-28 23:59:13 info [redis] Redis module initialized
2023-05-28 23:59:14 info [server] Server running at 0.0.0.0:7477

28
log/2023-05-29.log Normal file
View File

@ -0,0 +1,28 @@
2023-05-29 00:03:09 info [redis] Redis module initialized
2023-05-29 00:03:09 info [server] Server running at 0.0.0.0:7477
2023-05-29 00:03:23 info [redis] Redis module initialized
2023-05-29 00:03:24 info [server] Server running at 0.0.0.0:7477
2023-05-29 00:06:47 info [redis] Redis module initialized
2023-05-29 00:06:48 info [server] Server running at 0.0.0.0:7477
2023-05-29 00:11:09 info [redis] Redis module initialized
2023-05-29 00:11:10 info [server] Server running at 0.0.0.0:7477
2023-05-29 00:11:27 info [redis] Redis module initialized
2023-05-29 00:11:27 info [server] Server running at 0.0.0.0:7477
2023-05-29 00:13:14 info [redis] Redis module initialized
2023-05-29 00:13:14 info [server] Server running at 0.0.0.0:7477
2023-05-29 00:14:55 info [redis] Redis module initialized
2023-05-29 00:14:55 info [server] Server running at 0.0.0.0:7477
2023-05-29 00:15:56 info [redis] Redis module initialized
2023-05-29 00:15:56 info [server] Server running at 0.0.0.0:7477
2023-05-29 00:23:49 info [redis] Redis module initialized
2023-05-29 00:23:49 info [server] Server running at 0.0.0.0:7477
2023-05-29 00:24:16 info [redis] Redis module initialized
2023-05-29 00:24:17 info [server] Server running at 0.0.0.0:7477
2023-05-29 00:32:13 info [redis] Redis module initialized
2023-05-29 00:32:13 info [server] Server running at 0.0.0.0:7477
2023-05-29 00:34:52 info [redis] Redis module initialized
2023-05-29 00:34:53 info [server] Server running at 0.0.0.0:7477
2023-05-29 00:35:22 info [redis] Redis module initialized
2023-05-29 00:35:22 info [server] Server running at 0.0.0.0:7477
2023-05-29 00:42:59 info [redis] Redis module initialized
2023-05-29 00:42:59 info [server] Server running at 0.0.0.0:7477

View File

@ -0,0 +1,97 @@
exports.up = async function(knex) {
await knex.schema.createTable('users', (table) => {
table.increments('id');
table.text('username', 32)
.notNullable()
.unique();
table.text('email', 32)
.notNullable()
.unique();
table.text('password')
.notNullable();
table.text('name', 32);
table.text('bio', 1000);
table.specificType('ip', 'inet');
table.datetime('created_at')
.notNullable()
.defaultTo(knex.fn.now());
});
await knex.schema.createTable('shelves', (table) => {
table.increments('id');
table.text('slug')
.notNullable();
table.integer('founder_id')
.notNullable()
.references('id')
.inTable('users');
table.datetime('created_at')
.notNullable()
.defaultTo(knex.fn.now());
});
await knex.schema.createTable('shelves_settings', (table) => {
table.increments('id');
table.integer('shelf_id')
.primary()
.references('id')
.inTable('shelves');
table.text('name');
table.text('title');
table.text('description');
table.enum('view_access', ['public', 'registered', 'private'])
.notNullable()
.defaultTo('public');
table.enum('post_access', ['registered', 'private'])
.notNullable()
.defaultTo('public');
table.boolean('is_nsfw');
});
await knex.schema.createTable('posts', (table) => {
table.increments('id');
table.text('title')
.notNullable();
table.text('body');
table.text('url');
table.integer('shelf_id')
.notNullable()
.references('id')
.inTable('shelves');
table.integer('user_id')
.notNullable()
.references('id')
.inTable('users');
table.datetime('created_at')
.notNullable()
.defaultTo(knex.fn.now());
});
await knex.raw(`ALTER TABLE posts ADD CONSTRAINT post_content CHECK (body IS NOT NULL OR url IS NOT NULL)`);
};
exports.down = async function(knex) {
await knex.schema.dropTable('posts');
await knex.schema.dropTable('shelves_settings');
await knex.schema.dropTable('shelves');
await knex.schema.dropTable('users');
};

13275
package-lock.json generated Normal file

File diff suppressed because it is too large Load Diff

64
package.json Normal file
View File

@ -0,0 +1,64 @@
{
"name": "shack",
"version": "0.1.0",
"description": "Shack is a self-hosted social news aggregate",
"main": "src/web/server.js",
"repository": {
"type": "git",
"url": "https://gitea.unknown.name/DebaucheryLibrarian/shack"
},
"keywords": [
"aggregate",
"social",
"communities"
],
"author": "DebaucheryLibrarian",
"scripts": {
"dev": "npm run server",
"prod": "npm run build && npm run server:prod",
"build": "vite build",
"server": "node ./src/web/server",
"server:prod": "cross-env NODE_ENV=production node ./src/web/server",
"migrate-make": "knex-migrate generate",
"migrate": "knex-migrate up",
"rollback": "knex-migrate down"
},
"dependencies": {
"@babel/cli": "^7.21.5",
"@babel/core": "^7.21.8",
"@babel/eslint-parser": "^7.21.8",
"@babel/preset-env": "^7.21.5",
"@hcaptcha/vue3-hcaptcha": "^1.2.1",
"@vitejs/plugin-vue": "^4.0.0",
"@vue/compiler-sfc": "^3.2.33",
"@vue/server-renderer": "^3.2.33",
"bhttp": "^1.2.8",
"body-parser": "^1.20.2",
"compression": "^1.7.4",
"config": "^3.3.9",
"connect-redis": "^7.1.0",
"cross-env": "^7.0.3",
"eslint": "^8.41.0",
"eslint-config-airbnb-base": "^15.0.0",
"eslint-plugin-vue": "^9.14.0",
"express": "^4.18.1",
"express-promise-router": "^4.1.1",
"express-session": "^1.17.3",
"ip-cidr": "^3.1.0",
"knex": "^2.4.2",
"knex-migrate": "^1.7.4",
"nanoid": "^4.0.2",
"pg": "^8.11.0",
"pinia": "^2.1.3",
"redis": "^4.6.6",
"sirv": "^2.0.2",
"vite": "^4.0.3",
"vite-plugin-ssr": "^0.4.126",
"vite-plugin-vue-markdown": "^0.23.5",
"vite-svg-loader": "^4.0.0",
"vue": "^3.2.33",
"winston": "^3.9.0",
"winston-daily-rotate-file": "^4.7.1",
"yargs": "^17.7.2"
}
}

View File

@ -0,0 +1,177 @@
<template>
<div class="content">
<h2 class="heading">Create new account</h2>
<form
class="form create"
@submit.prevent="signup"
>
<div
v-if="errorMsg"
class="form-section form-error"
>{{ errorMsg }}</div>
<div class="form-section">
<div class="form-row">
<input
v-model="username"
placeholder="Username"
maxlength="32"
class="input"
>
</div>
<div class="form-row">
<input
v-model="email"
type="email"
placeholder="E-mail"
maxlength="500"
class="input"
>
</div>
<div class="form-row">
<input
v-model="password"
type="password"
minlength="8"
maxlength="500"
placeholder="Password"
class="input"
>
</div>
</div>
<div
v-if="config.captchaEnabled"
class="form-row captcha"
>
<VueHcaptcha
:sitekey="config.captchaKey"
@verify="(token) => captchaToken = token"
@expired="() => captchaToken = null"
@error="() => captchaToken = null"
/>
</div>
<div class="form-section">
<label class="check-container noselect">
<span>
<span class="description">I have read and accept the <a
href="/help/user-agreement"
target="_blank"
class="link"
>User Agreement</a></span>
</span>
<Checkbox
:checked="agreeTos"
@change="(checked) => agreeTos = checked"
/>
</label>
</div>
<div class="form-row form-actions">
<button
:disabled="!username || !email || !password || !agreeTos || (config.captchaEnabled && !captchaToken)"
class="button button-submit"
>Sign up</button>
</div>
</form>
</div>
</template>
<script setup>
import { ref } from 'vue';
import VueHcaptcha from '@hcaptcha/vue3-hcaptcha';
import Checkbox from '../../components/form/checkbox.vue';
import navigate from '../../assets/js/navigate';
import { post } from '../../assets/js/api';
const config = CONFIG;
const username = ref('');
const email = ref('');
const password = ref('');
const agreeTos = ref(false);
const captchaToken = ref(null);
const errorMsg = ref(null);
async function signup() {
try {
await post('/api/users', {
username: username.value,
email: email.value,
password: password.value,
captchaToken: captchaToken.value,
});
navigate('/account/login');
} catch (error) {
errorMsg.value = error.message;
}
}
</script>
<style scoped>
.content {
display: flex;
justify-content: center;
align-items: center;
}
.create {
background: var(--background);
padding: 1rem;
border-radius: .5rem;
}
.name {
position: relative;
.input {
padding-left: 1.65rem;
}
.prefix {
color: var(--shadow);
position: absolute;
top: 1px;
left: .25rem;
letter-spacing: .1rem;
padding: .5rem;
}
}
.access {
font-weight: bold;
margin-bottom: .75rem;
cursor: pointer;
}
.access-description {
margin: .25rem 0 0 1.25rem;
color: var(--shadow);
font-size: .9rem;
font-weight: normal;
}
.nsfw {
margin-right: .5rem;
font-weight: bold;
color: var(--error);
}
.captcha {
justify-content: center;
}
.form-actions {
justify-content: center;
}
</style>

View File

@ -0,0 +1,142 @@
<template>
<div class="content">
<h2 class="heading">Log in</h2>
<form
class="form create"
@submit.prevent="signup"
>
<div
v-if="errorMsg"
class="form-section form-error"
>{{ errorMsg }}</div>
<div class="form-section">
<div class="form-row">
<input
v-model="username"
placeholder="Username or e-mail"
maxlength="500"
class="input"
>
</div>
<div class="form-row">
<input
v-model="password"
type="password"
minlength="8"
maxlength="500"
placeholder="Password"
class="input"
>
</div>
</div>
<!--
<div
v-if="$config.public.captchaEnabled"
class="form-row captcha"
>
<VueHcaptcha
:sitekey="$config.public.captchaKey"
@verify="(token) => captchaToken = token"
@expired="() => captchaToken = null"
@error="() => captchaToken = null"
/>
</div>
-->
<div class="form-row form-actions">
<button
:disabled="!username || !password"
class="button button-submit"
>Log in</button>
</div>
</form>
</div>
</template>
<script setup>
import { ref } from 'vue';
// import VueHcaptcha from '@hcaptcha/vue3-hcaptcha';
import { post } from '../../assets/js/api';
import navigate from '../../assets/js/navigate';
const username = ref('');
const password = ref('');
const errorMsg = ref(null);
async function signup() {
try {
await post('/api/session', {
username: username.value,
password: password.value,
});
navigate('/');