feat: add personal project list, add project settings, etc

This commit is contained in:
2024-02-24 03:55:50 +00:00
parent 49b80a2f4c
commit 751210c819
31 changed files with 877 additions and 148 deletions
+11 -8
View File
@@ -19,6 +19,7 @@ const get = async (req: Request, res: Response) => {
if (!projectData) {
return res.status(404).send("Project not found!");
}
const settings = projectData.settings || {};
const fileData = await db.query.file.findFirst({
where: and(
@@ -34,16 +35,18 @@ const get = async (req: Request, res: Response) => {
const ext = getFileExt(fileData.filename);
let content = fileData.content || "";
if (["html", "htm"].includes(ext)) {
content = await serveHtml(fileData);
}
if (!req.query.raw) {
if (["html", "htm"].includes(ext)) {
content = await serveHtml(fileData, settings);
}
if (["js", "ts", "jsx", "tsx"].includes(ext)) {
content = await serveJs(fileData);
}
if (["js", "ts", "jsx", "tsx"].includes(ext)) {
content = await serveJs(fileData, settings.js);
}
if (["css"].includes(ext)) {
content = await postcss(fileData);
if (["css"].includes(ext) && settings.css?.preprocessor === "postcss") {
content = await postcss(fileData, settings.css);
}
}
res.setHeader("Content-Type", getMimeType(fileData.filename));
+13 -4
View File
@@ -3,17 +3,26 @@ import tailwindcss from "tailwindcss";
import cssnano from "cssnano";
import { FileSchema } from "~/server/db/schema/file";
import { unpackProject } from "~/server/lib/unpack-project";
import { ProjectSettingsSchema } from "~/server/db/schema/project";
export const postcss = async (fileData: FileSchema) => {
export const postcss = async (
fileData: FileSchema,
cfg?: ProjectSettingsSchema["css"]
) => {
const content = fileData.content || "";
try {
const projectDir = await unpackProject({ ext: "ts,tsx,js,jsx,html" });
const plugins: any[] = [];
if (cfg?.tailwindcss) {
plugins.push(
tailwindcss({ content: [projectDir + "/**/*.{ts,tsx,js,jsx,html}"] })
);
}
const result = await postcssPlugin([
tailwindcss({
content: [projectDir + "/**/*.{ts,tsx,js,jsx,html}"],
}),
...plugins,
cssnano({
preset: ["default", { discardComments: { removeAll: true } }],
}),
+8 -7
View File
@@ -2,8 +2,12 @@ import db from "~/server/db";
import { FileSchema, file } from "~/server/db/schema/file";
import { and, eq, isNull } from "drizzle-orm";
import { IS_DEV } from "~/server/lib/consts";
import type { ProjectSettingsSchema } from "~/server/db/schema/project";
export const serveHtml = async (fileData: FileSchema) => {
export const serveHtml = async (
fileData: FileSchema,
settings: Partial<ProjectSettingsSchema>
) => {
const layout = await db.query.file.findFirst({
where: and(
eq(file.projectId, fileData.projectId),
@@ -24,18 +28,15 @@ export const serveHtml = async (fileData: FileSchema) => {
const firstScriptTagIdx = content.indexOf("<script", bodyOpeningTagIdx);
const injectScripts = ['<script src="/js/hook-console.js"></script>'];
// prevent direct access
if (!IS_DEV) {
// prevent direct access
injectScripts.push(
`<script>if (window === window.parent) {window.location.href = '/';}</script>`
);
}
const importMaps = [
{ name: "react", url: "https://esm.sh/[email protected]" },
{ name: "react-dom/client", url: "https://esm.sh/[email protected]/client" },
];
// js import maps
const importMaps = settings?.js?.packages || [];
if (importMaps.length > 0) {
const imports = importMaps.reduce((a: any, b) => {
a[b.name] = b.url;
+9 -3
View File
@@ -1,11 +1,17 @@
import { FileSchema } from "~/server/db/schema/file";
import { ProjectSettingsSchema } from "~/server/db/schema/project";
import { transformJs } from "~/server/lib/transform-js";
export const serveJs = async (file: FileSchema) => {
export const serveJs = async (
file: FileSchema,
cfg?: ProjectSettingsSchema["js"]
) => {
let content = file.content || "";
// transform js
content = await transformJs(content);
// transpile to es5
if (cfg?.transpiler === "swc") {
content = await transformJs(content);
}
return content;
};