Add: Post creation
This commit is contained in:
@@ -1,6 +1,7 @@
|
||||
import { sql } from '$lib/db.server';
|
||||
import { getCategoriesCachedByRef, getCategoryCached } from './category';
|
||||
import { getUser, getUsersCachedByRef } from './user';
|
||||
import { isPostgresError } from './root';
|
||||
import { getUser, getUsersCachedByRef, sqlUserFromToken } from './user';
|
||||
|
||||
/**
|
||||
* @typedef {import('$types/base').Post} Post
|
||||
@@ -174,3 +175,69 @@ export async function getPost(post_id, opts = {}) {
|
||||
*/
|
||||
return parsePostFromRow(author, category, post, withMetrics);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} token
|
||||
* @param {import('$types/base').Category} category
|
||||
* @param {string} name
|
||||
* @param {string} content
|
||||
* @returns {Promise<import('$types/status').Success | import('$types/status').Error>}
|
||||
*/
|
||||
export async function createPost(token, category, name, content) {
|
||||
const insert = sql`
|
||||
INSERT INTO doki8902.message_post (author_id, category_id, name, latest_content)
|
||||
VALUES (
|
||||
(${ sqlUserFromToken(token) }),
|
||||
${ category.id }, ${ name }, ${ content }
|
||||
)
|
||||
RETURNING id;`;
|
||||
|
||||
let result;
|
||||
|
||||
try {
|
||||
result = await insert;
|
||||
} catch (e) {
|
||||
const pgerr = isPostgresError(e);
|
||||
|
||||
switch (pgerr?.constraint_name) {
|
||||
case 'message_require_user':
|
||||
return {
|
||||
error: true,
|
||||
msg: 'User token was invalid',
|
||||
};
|
||||
|
||||
case 'post_category_id_fkey':
|
||||
return {
|
||||
error: true,
|
||||
msg: 'Post category does not exist',
|
||||
};
|
||||
|
||||
case 'content_min_length':
|
||||
return {
|
||||
error: true,
|
||||
msg: 'Post content cannot be empty',
|
||||
};
|
||||
|
||||
case 'name_min_length':
|
||||
return {
|
||||
error: true,
|
||||
msg: 'Post name cannot be empty',
|
||||
};
|
||||
|
||||
default:
|
||||
console.log(e);
|
||||
return {
|
||||
error: true,
|
||||
msg: 'Unknown error (notify dev)',
|
||||
};
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
const postId = result[0]['id'];
|
||||
|
||||
return {
|
||||
success: true,
|
||||
result: postId,
|
||||
};
|
||||
}
|
||||
|
||||
@@ -1,3 +1,14 @@
|
||||
/**
|
||||
* @param {any} e
|
||||
* @returns {import('postgres').PostgresError | null}
|
||||
*/
|
||||
export function isPostgresError(e) {
|
||||
if (e && typeof(e) === 'object' && 'name' in e && e.name === 'PostgresError') {
|
||||
return e;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* @template T
|
||||
* @param {import('node-cache')} cache
|
||||
|
||||
+81
-28
@@ -1,5 +1,5 @@
|
||||
import { createCache } from '$lib/cache.server';
|
||||
import { cacheUpdater, cachedMethod, refExtendCachedMethod } from './root';
|
||||
import { cacheUpdater, cachedMethod, isPostgresError, refExtendCachedMethod } from './root';
|
||||
import { sql } from '$lib/db.server';
|
||||
import { argon2id, hash, verify } from 'argon2';
|
||||
import { PostgresError } from 'postgres';
|
||||
@@ -33,6 +33,14 @@ function parseUserFromRow(row) {
|
||||
*/
|
||||
const updateUserCache = cacheUpdater(cache);
|
||||
|
||||
/**
|
||||
* @param {string} token
|
||||
* @returns {import('postgres').PendingQuery<import('postgres').Row[]>}
|
||||
*/
|
||||
export function sqlUserFromToken(token) {
|
||||
return sql`SELECT user_id FROM doki8902.user_session WHERE token = ${ token }`;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {number[]} user_ids
|
||||
* @returns {Promise<Result<User>>}
|
||||
@@ -49,9 +57,9 @@ export async function getUsers(user_ids) {
|
||||
if (user_ids.length == 0) return new Map();
|
||||
|
||||
const query = sql`
|
||||
SELECT id, username, join_time
|
||||
FROM doki8902.user
|
||||
WHERE id IN ${ sql(user_ids) };`;
|
||||
SELECT id, username, join_time
|
||||
FROM doki8902.user
|
||||
WHERE id IN ${ sql(user_ids) };`;
|
||||
|
||||
let users = await query;
|
||||
|
||||
@@ -100,33 +108,34 @@ export async function createUser(username, password) {
|
||||
|
||||
try {
|
||||
await insert;
|
||||
|
||||
} catch (e) {
|
||||
if (e && typeof(e) === 'object' && 'name' in e && e.name === 'PostgresError') {
|
||||
const pgerr = /** @type {PostgresError} */ (e);
|
||||
const pgerr = isPostgresError(e);
|
||||
|
||||
switch (pgerr.constraint_name) {
|
||||
case 'idx_user_username':
|
||||
return {
|
||||
error: true,
|
||||
msg: "Username taken",
|
||||
};
|
||||
switch (pgerr?.constraint_name) {
|
||||
case 'idx_user_username':
|
||||
return {
|
||||
error: true,
|
||||
msg: "Username taken",
|
||||
};
|
||||
|
||||
case 'username_length_min':
|
||||
return {
|
||||
error: true,
|
||||
msg: "Username has invalid length",
|
||||
};
|
||||
|
||||
case 'username_valid_symbols':
|
||||
return {
|
||||
error: true,
|
||||
msg: "Username contains invalid symbols",
|
||||
};
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
case 'username_length_min':
|
||||
return {
|
||||
error: true,
|
||||
msg: "Username has invalid length",
|
||||
};
|
||||
|
||||
case 'username_valid_symbols':
|
||||
return {
|
||||
error: true,
|
||||
msg: "Username contains invalid symbols",
|
||||
};
|
||||
|
||||
default:
|
||||
console.log(e);
|
||||
return {
|
||||
error: true,
|
||||
msg: 'Unknown error (notify dev)',
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -178,3 +187,47 @@ export async function createUserSession(username, password) {
|
||||
result: token[0]['token'],
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} token
|
||||
* @returns {Promise<number | import('$types/status').Error>}
|
||||
*/
|
||||
export async function getUserIDOfSession(token) {
|
||||
const query = sql`
|
||||
SELECT user_id
|
||||
FROM doki8902.user_session
|
||||
WHERE token = ${ token }`;
|
||||
|
||||
const result = await query;
|
||||
|
||||
if (result.length == 0) {
|
||||
return {
|
||||
error: true,
|
||||
msg: "Invalid user session",
|
||||
};
|
||||
}
|
||||
|
||||
return result[0]['user_id'];
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} token
|
||||
* @returns {Promise<User | import('$types/status').Error>}
|
||||
*/
|
||||
export async function getUserOfSession(token) {
|
||||
const query = sql`
|
||||
SELECT user_id
|
||||
FROM doki8902.user_session
|
||||
WHERE token = ${ token }`;
|
||||
|
||||
const result = await query;
|
||||
|
||||
if (result.length == 0) {
|
||||
return {
|
||||
error: true,
|
||||
msg: "Invalid user session",
|
||||
};
|
||||
}
|
||||
|
||||
return result[0]['user_id'];
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user