massive lint
This commit is contained in:
parent
3192714355
commit
5f7ac8e4a6
|
@ -7,5 +7,5 @@
|
||||||
"access": "public",
|
"access": "public",
|
||||||
"baseBranch": "main",
|
"baseBranch": "main",
|
||||||
"updateInternalDependencies": "patch",
|
"updateInternalDependencies": "patch",
|
||||||
"ignore": ["playground","starlight-playground"]
|
"ignore": ["playground", "starlight-playground"]
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,7 +5,11 @@ import { TSGhostContentAPI } from "@ts-ghost/content-api";
|
||||||
describe("content-api", () => {
|
describe("content-api", () => {
|
||||||
let api: TSGhostContentAPI;
|
let api: TSGhostContentAPI;
|
||||||
beforeEach(() => {
|
beforeEach(() => {
|
||||||
api = new TSGhostContentAPI("https://ghost.org", "59d4bf56c73c04a18c867dc3ba", "v5.0");
|
api = new TSGhostContentAPI(
|
||||||
|
"https://ghost.org",
|
||||||
|
"59d4bf56c73c04a18c867dc3ba",
|
||||||
|
"v5.0",
|
||||||
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
test("content-api", () => {
|
test("content-api", () => {
|
||||||
|
@ -14,7 +18,11 @@ describe("content-api", () => {
|
||||||
|
|
||||||
test("content-api shouldn't instantiate with an incorrect url", () => {
|
test("content-api shouldn't instantiate with an incorrect url", () => {
|
||||||
assert.throws(() => {
|
assert.throws(() => {
|
||||||
const api = new TSGhostContentAPI("ghost.org", "59d4bf56c73c04a18c867dc3ba", "v5.0");
|
const api = new TSGhostContentAPI(
|
||||||
|
"ghost.org",
|
||||||
|
"59d4bf56c73c04a18c867dc3ba",
|
||||||
|
"v5.0",
|
||||||
|
);
|
||||||
api.settings;
|
api.settings;
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
|
@ -4,10 +4,7 @@ import type { Page, Post } from "../schemas/api";
|
||||||
// LOAD ENVIRONMENT VARIABLES
|
// LOAD ENVIRONMENT VARIABLES
|
||||||
import { loadEnv } from "vite";
|
import { loadEnv } from "vite";
|
||||||
|
|
||||||
const {
|
const { CONTENT_API_KEY, CONTENT_API_URL } = loadEnv(
|
||||||
CONTENT_API_KEY,
|
|
||||||
CONTENT_API_URL
|
|
||||||
} = loadEnv(
|
|
||||||
"all",
|
"all",
|
||||||
process.cwd(),
|
process.cwd(),
|
||||||
"CONTENT_",
|
"CONTENT_",
|
||||||
|
|
|
@ -1,22 +1,22 @@
|
||||||
import { createResolver, defineIntegration } from "astro-integration-kit";
|
|
||||||
import { corePlugins } from "astro-integration-kit/plugins";
|
|
||||||
import { GhostUserConfigSchema } from "./schemas/userconfig";
|
|
||||||
import { loadEnv } from "vite";
|
|
||||||
import { AstroError } from "astro/errors";
|
|
||||||
import c from "picocolors";
|
|
||||||
import path from "node:path";
|
import path from "node:path";
|
||||||
import { fileURLToPath } from "node:url";
|
import { fileURLToPath } from "node:url";
|
||||||
|
import { createResolver, defineIntegration } from "astro-integration-kit";
|
||||||
|
import { corePlugins } from "astro-integration-kit/plugins";
|
||||||
|
import { AstroError } from "astro/errors";
|
||||||
import fse from "fs-extra";
|
import fse from "fs-extra";
|
||||||
|
import c from "picocolors";
|
||||||
|
import { loadEnv } from "vite";
|
||||||
|
import { GhostUserConfigSchema } from "./schemas/userconfig";
|
||||||
import latestVersion from "./utils/latestVersion";
|
import latestVersion from "./utils/latestVersion";
|
||||||
|
|
||||||
// Import External Integrations
|
// Import External Integrations
|
||||||
import sitemap from "@astrojs/sitemap";
|
import sitemap from "@astrojs/sitemap";
|
||||||
import robotsTxt from "astro-robots-txt";
|
import robotsTxt from "astro-robots-txt";
|
||||||
|
|
||||||
|
import ghostRSS from "./integrations/rssfeed";
|
||||||
// Import Internal Integrations
|
// Import Internal Integrations
|
||||||
import ghostOGImages from "./integrations/satoriog"
|
import ghostOGImages from "./integrations/satoriog";
|
||||||
import ghostRSS from "./integrations/rssfeed"
|
import ghostThemeProvider from "./integrations/themeprovider";
|
||||||
import ghostThemeProvider from "./integrations/themeprovider"
|
|
||||||
|
|
||||||
// Load environment variables
|
// Load environment variables
|
||||||
const ENV = loadEnv("all", process.cwd(), "CONTENT_API");
|
const ENV = loadEnv("all", process.cwd(), "CONTENT_API");
|
||||||
|
@ -24,7 +24,7 @@ const ENV = loadEnv("all", process.cwd(), "CONTENT_API");
|
||||||
/** Astro-GhostCMS Integration
|
/** Astro-GhostCMS Integration
|
||||||
* @description This integration allows you to use GhostCMS as a headless CMS for your Astro project
|
* @description This integration allows you to use GhostCMS as a headless CMS for your Astro project
|
||||||
* @see https://astro-ghostcms.xyz for the most up-to-date documentation!
|
* @see https://astro-ghostcms.xyz for the most up-to-date documentation!
|
||||||
*/
|
*/
|
||||||
export default defineIntegration({
|
export default defineIntegration({
|
||||||
name: "@matthiesenxyz/astro-ghostcms",
|
name: "@matthiesenxyz/astro-ghostcms",
|
||||||
optionsSchema: GhostUserConfigSchema,
|
optionsSchema: GhostUserConfigSchema,
|
||||||
|
@ -40,112 +40,184 @@ export default defineIntegration({
|
||||||
addVirtualImports,
|
addVirtualImports,
|
||||||
addDts,
|
addDts,
|
||||||
injectRoute,
|
injectRoute,
|
||||||
logger
|
logger,
|
||||||
}) => {
|
}) => {
|
||||||
const GhostLogger = logger.fork(c.bold(c.blue('👻 Astro-GhostCMS')));
|
const GhostLogger = logger.fork(c.bold(c.blue("👻 Astro-GhostCMS")));
|
||||||
const GhostENVLogger = logger.fork(`${c.bold(c.blue('👻 Astro-GhostCMS'))}${c.gray("/")}${c.blue('ENV Check')}`);
|
const GhostENVLogger = logger.fork(
|
||||||
const GhostIntegrationLogger = logger.fork(`${c.bold(c.blue('👻 Astro-GhostCMS'))}${c.gray("/")}${c.blue('Integrations')}`);
|
`${c.bold(c.blue("👻 Astro-GhostCMS"))}${c.gray("/")}${c.blue(
|
||||||
const GhostRouteLogger = logger.fork(`${c.bold(c.blue('👻 Astro-GhostCMS'))}${c.gray("/")}${c.blue('Router')}`);
|
"ENV Check",
|
||||||
|
)}`,
|
||||||
|
);
|
||||||
|
const GhostIntegrationLogger = logger.fork(
|
||||||
|
`${c.bold(c.blue("👻 Astro-GhostCMS"))}${c.gray("/")}${c.blue(
|
||||||
|
"Integrations",
|
||||||
|
)}`,
|
||||||
|
);
|
||||||
|
const GhostRouteLogger = logger.fork(
|
||||||
|
`${c.bold(c.blue("👻 Astro-GhostCMS"))}${c.gray("/")}${c.blue(
|
||||||
|
"Router",
|
||||||
|
)}`,
|
||||||
|
);
|
||||||
|
|
||||||
watchIntegration(resolve())
|
watchIntegration(resolve());
|
||||||
GhostLogger.info('Initializing @matthiesenxyz/astro-ghostcms...')
|
GhostLogger.info("Initializing @matthiesenxyz/astro-ghostcms...");
|
||||||
|
|
||||||
const verbose = options.fullConsoleLogs;
|
const verbose = options.fullConsoleLogs;
|
||||||
|
|
||||||
// Check for GhostCMS environment variables
|
// Check for GhostCMS environment variables
|
||||||
GhostENVLogger.info(c.bold(c.yellow('Checking for GhostCMS environment variables & user configuration')))
|
GhostENVLogger.info(
|
||||||
|
c.bold(
|
||||||
|
c.yellow(
|
||||||
|
"Checking for GhostCMS environment variables & user configuration",
|
||||||
|
),
|
||||||
|
),
|
||||||
|
);
|
||||||
if (ENV.CONTENT_API_KEY === undefined) {
|
if (ENV.CONTENT_API_KEY === undefined) {
|
||||||
GhostENVLogger.error(c.bgRed(c.bold(c.white('CONTENT_API_KEY is not set in environment variables'))))
|
GhostENVLogger.error(
|
||||||
throw new AstroError(`${name} CONTENT_API_KEY is not set in environment variables`)
|
c.bgRed(
|
||||||
|
c.bold(
|
||||||
|
c.white("CONTENT_API_KEY is not set in environment variables"),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
throw new AstroError(
|
||||||
|
`${name} CONTENT_API_KEY is not set in environment variables`,
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (options.ghostURL === undefined) {
|
if (options.ghostURL === undefined) {
|
||||||
GhostENVLogger.warn(c.bgYellow(c.bold(c.black('ghostURL is not set in user configuration falling back to environment variable'))))
|
GhostENVLogger.warn(
|
||||||
|
c.bgYellow(
|
||||||
|
c.bold(
|
||||||
|
c.black(
|
||||||
|
"ghostURL is not set in user configuration falling back to environment variable",
|
||||||
|
),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
);
|
||||||
if (ENV.CONTENT_API_URL === undefined) {
|
if (ENV.CONTENT_API_URL === undefined) {
|
||||||
GhostENVLogger.error(c.bgRed(c.bold(c.white('CONTENT_API_URL is not set in environment variables'))))
|
GhostENVLogger.error(
|
||||||
throw new AstroError(`${name} CONTENT_API_URL is not set in environment variables`)
|
c.bgRed(
|
||||||
|
c.bold(
|
||||||
|
c.white(
|
||||||
|
"CONTENT_API_URL is not set in environment variables",
|
||||||
|
),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
throw new AstroError(
|
||||||
|
`${name} CONTENT_API_URL is not set in environment variables`,
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
GhostENVLogger.info(c.bold(c.green('GhostCMS environment variables are set')))
|
GhostENVLogger.info(
|
||||||
|
c.bold(c.green("GhostCMS environment variables are set")),
|
||||||
|
);
|
||||||
|
|
||||||
// Set up Astro-GhostCMS Integrations
|
// Set up Astro-GhostCMS Integrations
|
||||||
GhostIntegrationLogger.info(c.bold(c.magenta('Configuring Enabled Integrations')))
|
GhostIntegrationLogger.info(
|
||||||
|
c.bold(c.magenta("Configuring Enabled Integrations")),
|
||||||
|
);
|
||||||
|
|
||||||
// Theme Provider
|
// Theme Provider
|
||||||
if ( !options.disableThemeProvider ) {
|
if (!options.disableThemeProvider) {
|
||||||
addIntegration(
|
addIntegration(
|
||||||
ghostThemeProvider({
|
ghostThemeProvider({
|
||||||
theme: options.ThemeProvider?.theme,
|
theme: options.ThemeProvider?.theme,
|
||||||
verbose
|
verbose,
|
||||||
})
|
}),
|
||||||
)
|
);
|
||||||
} else {
|
} else {
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
GhostIntegrationLogger.info(c.gray('Theme Provider is disabled'))
|
GhostIntegrationLogger.info(c.gray("Theme Provider is disabled"));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Satori OG Images
|
// Satori OG Images
|
||||||
if ( options.enableOGImages ) {
|
if (options.enableOGImages) {
|
||||||
addIntegration(ghostOGImages({ verbose }))
|
addIntegration(ghostOGImages({ verbose }));
|
||||||
} else {
|
} else {
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
GhostIntegrationLogger.info(c.gray('OG Image Provider is disabled'))
|
GhostIntegrationLogger.info(
|
||||||
|
c.gray("OG Image Provider is disabled"),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// RSS Feed
|
// RSS Feed
|
||||||
if ( options.enableRSSFeed ) {
|
if (options.enableRSSFeed) {
|
||||||
addIntegration(ghostRSS({ verbose }))
|
addIntegration(ghostRSS({ verbose }));
|
||||||
} else {
|
} else {
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
GhostIntegrationLogger.info(c.gray('RSS Feed is disabled'))
|
GhostIntegrationLogger.info(c.gray("RSS Feed is disabled"));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// @ASTROJS/SITEMAP
|
// @ASTROJS/SITEMAP
|
||||||
if ( !hasIntegration("@astrojs/sitemap") ) {
|
if (!hasIntegration("@astrojs/sitemap")) {
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
GhostIntegrationLogger.info(c.bold(c.magenta(`Adding ${c.blue("@astrojs/sitemap")} integration`)))
|
GhostIntegrationLogger.info(
|
||||||
|
c.bold(
|
||||||
|
c.magenta(`Adding ${c.blue("@astrojs/sitemap")} integration`),
|
||||||
|
),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
addIntegration(sitemap())
|
addIntegration(sitemap());
|
||||||
} else {
|
} else {
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
GhostIntegrationLogger.info(c.gray('@astrojs/sitemap integration already exists, skipping...'))
|
GhostIntegrationLogger.info(
|
||||||
|
c.gray(
|
||||||
|
"@astrojs/sitemap integration already exists, skipping...",
|
||||||
|
),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// ASTRO-ROBOTS-TXT
|
// ASTRO-ROBOTS-TXT
|
||||||
if ( !hasIntegration("@astro-robots-txt") ) {
|
if (!hasIntegration("@astro-robots-txt")) {
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
GhostIntegrationLogger.info(c.bold(c.magenta(`Adding ${c.blue("astro-robots-txt")} integration`)))
|
GhostIntegrationLogger.info(
|
||||||
|
c.bold(
|
||||||
|
c.magenta(`Adding ${c.blue("astro-robots-txt")} integration`),
|
||||||
|
),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
addIntegration(robotsTxt())
|
addIntegration(robotsTxt());
|
||||||
} else {
|
} else {
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
GhostIntegrationLogger.info(c.gray('astro-robots-txt integration already exists, skipping...'))
|
GhostIntegrationLogger.info(
|
||||||
|
c.gray(
|
||||||
|
"astro-robots-txt integration already exists, skipping...",
|
||||||
|
),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Set up default 404 page
|
// Set up default 404 page
|
||||||
if ( !options.disableDefault404 ) {
|
if (!options.disableDefault404) {
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
GhostRouteLogger.info(c.bold(c.cyan('Setting up default 404 page')))
|
GhostRouteLogger.info(
|
||||||
|
c.bold(c.cyan("Setting up default 404 page")),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
injectRoute({
|
injectRoute({
|
||||||
pattern: "/404",
|
pattern: "/404",
|
||||||
entrypoint: `${name}/404.astro`,
|
entrypoint: `${name}/404.astro`,
|
||||||
prerender: true
|
prerender: true,
|
||||||
})
|
});
|
||||||
} else {
|
} else {
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
GhostRouteLogger.info(c.gray('Default 404 page is disabled, Skipping...'))
|
GhostRouteLogger.info(
|
||||||
|
c.gray("Default 404 page is disabled, Skipping..."),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Add virtual imports for user configuration
|
// Add virtual imports for user configuration
|
||||||
addVirtualImports({
|
addVirtualImports({
|
||||||
'virtual:@matthiesenxyz/astro-ghostcms/config': `export default ${JSON.stringify(options)}`,
|
"virtual:@matthiesenxyz/astro-ghostcms/config": `export default ${JSON.stringify(
|
||||||
})
|
options,
|
||||||
|
)}`,
|
||||||
|
});
|
||||||
|
|
||||||
// Add types for user configuration
|
// Add types for user configuration
|
||||||
addDts({
|
addDts({
|
||||||
|
@ -153,37 +225,82 @@ export default defineIntegration({
|
||||||
content: `declare module "virtual:@matthiesenxyz/astro-ghostcms/config" {
|
content: `declare module "virtual:@matthiesenxyz/astro-ghostcms/config" {
|
||||||
const Config: import("../schemas/userconfig").GhostUserConfig;
|
const Config: import("../schemas/userconfig").GhostUserConfig;
|
||||||
export default Config;
|
export default Config;
|
||||||
}`
|
}`,
|
||||||
})
|
});
|
||||||
|
|
||||||
},
|
},
|
||||||
"astro:config:done": ({ logger }) => {
|
"astro:config:done": ({ logger }) => {
|
||||||
const GhostLogger = logger.fork(`${c.bold(c.blue('👻 Astro-GhostCMS'))}${c.gray("/")}${c.green('CONFIG')}`);
|
const GhostLogger = logger.fork(
|
||||||
GhostLogger.info(c.bold(c.green('Integration Setup & Configuration Complete')))
|
`${c.bold(c.blue("👻 Astro-GhostCMS"))}${c.gray("/")}${c.green(
|
||||||
|
"CONFIG",
|
||||||
|
)}`,
|
||||||
|
);
|
||||||
|
GhostLogger.info(
|
||||||
|
c.bold(c.green("Integration Setup & Configuration Complete")),
|
||||||
|
);
|
||||||
},
|
},
|
||||||
"astro:server:start": async ({ logger }) => {
|
"astro:server:start": async ({ logger }) => {
|
||||||
const GhostLogger = logger.fork(`${c.bold(c.blue('👻 Astro-GhostCMS'))}${c.gray("/")}${c.bold(c.green('DEV'))}`);
|
const GhostLogger = logger.fork(
|
||||||
const GhostUpdateLogger = logger.fork(`${c.bold(c.blue('👻 Astro-GhostCMS'))}${c.gray("/")}${c.bold(c.green('VERSION CHECK'))}`);
|
`${c.bold(c.blue("👻 Astro-GhostCMS"))}${c.gray("/")}${c.bold(
|
||||||
|
c.green("DEV"),
|
||||||
|
)}`,
|
||||||
|
);
|
||||||
|
const GhostUpdateLogger = logger.fork(
|
||||||
|
`${c.bold(c.blue("👻 Astro-GhostCMS"))}${c.gray("/")}${c.bold(
|
||||||
|
c.green("VERSION CHECK"),
|
||||||
|
)}`,
|
||||||
|
);
|
||||||
|
|
||||||
// Start the DEV server
|
// Start the DEV server
|
||||||
GhostLogger.info(c.bold(c.magenta('Running Astro-GhostCMS in Deveopment mode 🚀')))
|
GhostLogger.info(
|
||||||
|
c.bold(c.magenta("Running Astro-GhostCMS in Deveopment mode 🚀")),
|
||||||
|
);
|
||||||
|
|
||||||
// Check for updates
|
// Check for updates
|
||||||
const currentNPMVersion = await latestVersion("@matthiesenxyz/astro-ghostcms");
|
const currentNPMVersion = await latestVersion(
|
||||||
const packageJson = await fse.readJson(path.resolve(fileURLToPath(import.meta.url), "../../package.json"));
|
"@matthiesenxyz/astro-ghostcms",
|
||||||
|
);
|
||||||
|
const packageJson = await fse.readJson(
|
||||||
|
path.resolve(fileURLToPath(import.meta.url), "../../package.json"),
|
||||||
|
);
|
||||||
const localVersion = packageJson.version;
|
const localVersion = packageJson.version;
|
||||||
|
|
||||||
if (currentNPMVersion !== localVersion) {
|
if (currentNPMVersion !== localVersion) {
|
||||||
GhostUpdateLogger.warn(`\n${c.bgYellow(c.bold(c.black(" There is a new version of Astro-GhostCMS available! ")))}\n${c.bold(c.white(" Current Installed Version: ")) + c.bold(c.red(`${localVersion} `))} \n ${c.bold(c.white("New Available Version: "))} ${c.green(currentNPMVersion)} \n ${c.bold(c.white("Please consider updating to the latest version by running: "))} ${c.bold(c.green("npm i @matthiesenxyz/astro-ghostcms@latest"))} \n`)
|
GhostUpdateLogger.warn(
|
||||||
|
`\n${c.bgYellow(
|
||||||
|
c.bold(
|
||||||
|
c.black(
|
||||||
|
" There is a new version of Astro-GhostCMS available! ",
|
||||||
|
),
|
||||||
|
),
|
||||||
|
)}\n${
|
||||||
|
c.bold(c.white(" Current Installed Version: ")) +
|
||||||
|
c.bold(c.red(`${localVersion} `))
|
||||||
|
} \n ${c.bold(c.white("New Available Version: "))} ${c.green(
|
||||||
|
currentNPMVersion,
|
||||||
|
)} \n ${c.bold(
|
||||||
|
c.white(
|
||||||
|
"Please consider updating to the latest version by running: ",
|
||||||
|
),
|
||||||
|
)} ${c.bold(
|
||||||
|
c.green("npm i @matthiesenxyz/astro-ghostcms@latest"),
|
||||||
|
)} \n`,
|
||||||
|
);
|
||||||
} else {
|
} else {
|
||||||
GhostUpdateLogger.info(c.bold(c.green(`Astro-GhostCMS is up to date! v${localVersion}`)))
|
GhostUpdateLogger.info(
|
||||||
|
c.bold(c.green(`Astro-GhostCMS is up to date! v${localVersion}`)),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
},
|
},
|
||||||
"astro:build:done": ({ logger }) => {
|
"astro:build:done": ({ logger }) => {
|
||||||
const GhostLogger = logger.fork(`${c.bold(c.blue('👻 Astro-GhostCMS'))}${c.gray("/")}${c.bold(c.green('BUILD'))}`);
|
const GhostLogger = logger.fork(
|
||||||
GhostLogger.info(c.bold(c.magenta('Running Astro-GhostCMS in Production mode 🚀')))
|
`${c.bold(c.blue("👻 Astro-GhostCMS"))}${c.gray("/")}${c.bold(
|
||||||
}
|
c.green("BUILD"),
|
||||||
}
|
)}`,
|
||||||
}
|
);
|
||||||
})
|
GhostLogger.info(
|
||||||
|
c.bold(c.magenta("Running Astro-GhostCMS in Production mode 🚀")),
|
||||||
|
);
|
||||||
|
},
|
||||||
|
};
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
|
@ -1,3 +1,3 @@
|
||||||
import astroghostcms from './astro-ghostcms.js';
|
import astroghostcms from "./astro-ghostcms.js";
|
||||||
|
|
||||||
export default astroghostcms;
|
export default astroghostcms;
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
import { createResolver, defineIntegration } from "astro-integration-kit";
|
import { createResolver, defineIntegration } from "astro-integration-kit";
|
||||||
import { corePlugins } from "astro-integration-kit/plugins";
|
import { corePlugins } from "astro-integration-kit/plugins";
|
||||||
import c from "picocolors";
|
|
||||||
import { z } from "astro/zod";
|
import { z } from "astro/zod";
|
||||||
|
import c from "picocolors";
|
||||||
|
|
||||||
export default defineIntegration({
|
export default defineIntegration({
|
||||||
name: "@matthiesenxyz/astro-ghostcms-rss",
|
name: "@matthiesenxyz/astro-ghostcms-rss",
|
||||||
|
@ -13,17 +13,17 @@ export default defineIntegration({
|
||||||
const { resolve } = createResolver(import.meta.url);
|
const { resolve } = createResolver(import.meta.url);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
"astro:config:setup": ({
|
"astro:config:setup": ({ watchIntegration, injectRoute, logger }) => {
|
||||||
watchIntegration,
|
watchIntegration(resolve());
|
||||||
injectRoute,
|
const RSSLogger = logger.fork(
|
||||||
logger
|
`${c.bold(c.blue("👻 Astro-GhostCMS"))}${c.gray("/")}${c.blue(
|
||||||
}) => {
|
"RSSGenerator",
|
||||||
watchIntegration(resolve())
|
)}`,
|
||||||
const RSSLogger = logger.fork(`${c.bold(c.blue('👻 Astro-GhostCMS'))}${c.gray("/")}${c.blue('RSSGenerator')}`);
|
);
|
||||||
|
|
||||||
RSSLogger.info(c.bold(c.magenta('RSS Feed Enabled. Setting up...')))
|
RSSLogger.info(c.bold(c.magenta("RSS Feed Enabled. Setting up...")));
|
||||||
|
|
||||||
const rssRoute = "@matthiesenxyz/astro-ghostcms/rss-routes"
|
const rssRoute = "@matthiesenxyz/astro-ghostcms/rss-routes";
|
||||||
|
|
||||||
injectRoute({
|
injectRoute({
|
||||||
pattern: "/rss-style.xsl",
|
pattern: "/rss-style.xsl",
|
||||||
|
@ -34,15 +34,18 @@ export default defineIntegration({
|
||||||
pattern: "/rss.xml",
|
pattern: "/rss.xml",
|
||||||
entrypoint: `${rssRoute}/rss.xml.ts`,
|
entrypoint: `${rssRoute}/rss.xml.ts`,
|
||||||
});
|
});
|
||||||
|
|
||||||
},
|
},
|
||||||
"astro:config:done": ({ logger }) => {
|
"astro:config:done": ({ logger }) => {
|
||||||
const RSSLogger = logger.fork(`${c.bold(c.blue('👻 Astro-GhostCMS'))}${c.gray("/")}${c.blue('RSSGenerator')}`);
|
const RSSLogger = logger.fork(
|
||||||
|
`${c.bold(c.blue("👻 Astro-GhostCMS"))}${c.gray("/")}${c.blue(
|
||||||
|
"RSSGenerator",
|
||||||
|
)}`,
|
||||||
|
);
|
||||||
|
|
||||||
if (options.verbose) {
|
if (options.verbose) {
|
||||||
RSSLogger.info(c.bold(c.green('RSS Feed Setup Complete')))
|
RSSLogger.info(c.bold(c.green("RSS Feed Setup Complete")));
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
}
|
};
|
||||||
}
|
},
|
||||||
})
|
});
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
import { createResolver, defineIntegration } from "astro-integration-kit";
|
import { createResolver, defineIntegration } from "astro-integration-kit";
|
||||||
import { corePlugins } from "astro-integration-kit/plugins";
|
import { corePlugins } from "astro-integration-kit/plugins";
|
||||||
import c from "picocolors";
|
|
||||||
import { z } from "astro/zod";
|
import { z } from "astro/zod";
|
||||||
|
import c from "picocolors";
|
||||||
|
|
||||||
export default defineIntegration({
|
export default defineIntegration({
|
||||||
name: "@matthiesenxyz/astro-ghostcms-satoriog",
|
name: "@matthiesenxyz/astro-ghostcms-satoriog",
|
||||||
|
@ -17,15 +17,21 @@ export default defineIntegration({
|
||||||
watchIntegration,
|
watchIntegration,
|
||||||
updateConfig,
|
updateConfig,
|
||||||
injectRoute,
|
injectRoute,
|
||||||
logger
|
logger,
|
||||||
}) => {
|
}) => {
|
||||||
watchIntegration(resolve())
|
watchIntegration(resolve());
|
||||||
|
|
||||||
const SatoriLogger = logger.fork(`${c.bold(c.blue('👻 Astro-GhostCMS'))}${c.gray("/")}${c.blue('SatoriOG')}`);
|
const SatoriLogger = logger.fork(
|
||||||
|
`${c.bold(c.blue("👻 Astro-GhostCMS"))}${c.gray("/")}${c.blue(
|
||||||
|
"SatoriOG",
|
||||||
|
)}`,
|
||||||
|
);
|
||||||
|
|
||||||
SatoriLogger.info(c.bold(c.magenta('OG Image Integration Enabled. Setting up...')))
|
SatoriLogger.info(
|
||||||
|
c.bold(c.magenta("OG Image Integration Enabled. Setting up...")),
|
||||||
|
);
|
||||||
|
|
||||||
const pkgname = "@matthiesenxyz/astro-ghostcms/open-graph"
|
const pkgname = "@matthiesenxyz/astro-ghostcms/open-graph";
|
||||||
|
|
||||||
injectRoute({
|
injectRoute({
|
||||||
pattern: "/open-graph/[slug].png",
|
pattern: "/open-graph/[slug].png",
|
||||||
|
@ -58,16 +64,22 @@ export default defineIntegration({
|
||||||
});
|
});
|
||||||
|
|
||||||
updateConfig({
|
updateConfig({
|
||||||
vite: { optimizeDeps: { exclude: ["@resvg/resvg-js"] } }
|
vite: { optimizeDeps: { exclude: ["@resvg/resvg-js"] } },
|
||||||
})
|
});
|
||||||
},
|
},
|
||||||
"astro:config:done": ({ logger }) => {
|
"astro:config:done": ({ logger }) => {
|
||||||
const SatoriLogger = logger.fork(`${c.bold(c.blue('👻 Astro-GhostCMS'))}${c.gray("/")}${c.blue('SatoriOG')}`);
|
const SatoriLogger = logger.fork(
|
||||||
|
`${c.bold(c.blue("👻 Astro-GhostCMS"))}${c.gray("/")}${c.blue(
|
||||||
|
"SatoriOG",
|
||||||
|
)}`,
|
||||||
|
);
|
||||||
|
|
||||||
if (options.verbose) {
|
if (options.verbose) {
|
||||||
SatoriLogger.info(c.bold(c.green('OG Image Integration Setup Complete')))
|
SatoriLogger.info(
|
||||||
|
c.bold(c.green("OG Image Integration Setup Complete")),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
}
|
};
|
||||||
}
|
},
|
||||||
})
|
});
|
||||||
|
|
|
@ -5,12 +5,7 @@ import type {
|
||||||
InferGetStaticPropsType,
|
InferGetStaticPropsType,
|
||||||
} from "astro";
|
} from "astro";
|
||||||
import { html } from "satori-html";
|
import { html } from "satori-html";
|
||||||
import {
|
import { getAllPages, getAllPosts, getSettings, invariant } from "../../../api";
|
||||||
getAllPages,
|
|
||||||
getAllPosts,
|
|
||||||
getSettings,
|
|
||||||
invariant,
|
|
||||||
} from "../../../api";
|
|
||||||
import satoriOG from "../satori";
|
import satoriOG from "../satori";
|
||||||
|
|
||||||
export const getStaticPaths: GetStaticPaths = async () => {
|
export const getStaticPaths: GetStaticPaths = async () => {
|
||||||
|
|
|
@ -5,12 +5,7 @@ import type {
|
||||||
InferGetStaticPropsType,
|
InferGetStaticPropsType,
|
||||||
} from "astro";
|
} from "astro";
|
||||||
import { html } from "satori-html";
|
import { html } from "satori-html";
|
||||||
import {
|
import { getAllPages, getAllPosts, getSettings, invariant } from "../../../api";
|
||||||
getAllPages,
|
|
||||||
getAllPosts,
|
|
||||||
getSettings,
|
|
||||||
invariant,
|
|
||||||
} from "../../../api";
|
|
||||||
import satoriOG from "../satori";
|
import satoriOG from "../satori";
|
||||||
|
|
||||||
export const getStaticPaths: GetStaticPaths = async () => {
|
export const getStaticPaths: GetStaticPaths = async () => {
|
||||||
|
|
|
@ -5,12 +5,7 @@ import type {
|
||||||
InferGetStaticPropsType,
|
InferGetStaticPropsType,
|
||||||
} from "astro";
|
} from "astro";
|
||||||
import { html } from "satori-html";
|
import { html } from "satori-html";
|
||||||
import {
|
import { getAllPages, getAllPosts, getSettings, invariant } from "../../../api";
|
||||||
getAllPages,
|
|
||||||
getAllPosts,
|
|
||||||
getSettings,
|
|
||||||
invariant,
|
|
||||||
} from "../../../api";
|
|
||||||
import satoriOG from "../satori";
|
import satoriOG from "../satori";
|
||||||
|
|
||||||
export const getStaticPaths: GetStaticPaths = async () => {
|
export const getStaticPaths: GetStaticPaths = async () => {
|
||||||
|
|
|
@ -5,12 +5,7 @@ import type {
|
||||||
InferGetStaticPropsType,
|
InferGetStaticPropsType,
|
||||||
} from "astro";
|
} from "astro";
|
||||||
import { html } from "satori-html";
|
import { html } from "satori-html";
|
||||||
import {
|
import { getAllPages, getAllPosts, getSettings, invariant } from "../../../api";
|
||||||
getAllPages,
|
|
||||||
getAllPosts,
|
|
||||||
getSettings,
|
|
||||||
invariant,
|
|
||||||
} from "../../../api";
|
|
||||||
import satoriOG from "../satori";
|
import satoriOG from "../satori";
|
||||||
|
|
||||||
export const getStaticPaths: GetStaticPaths = async () => {
|
export const getStaticPaths: GetStaticPaths = async () => {
|
||||||
|
|
|
@ -6,7 +6,10 @@ import c from "picocolors";
|
||||||
export default defineIntegration({
|
export default defineIntegration({
|
||||||
name: "@matthiesenxyz/astro-ghostcms-themeprovider",
|
name: "@matthiesenxyz/astro-ghostcms-themeprovider",
|
||||||
optionsSchema: z.object({
|
optionsSchema: z.object({
|
||||||
theme: z.string().optional().default("@matthiesenxyz/astro-ghostcms-theme-default"),
|
theme: z
|
||||||
|
.string()
|
||||||
|
.optional()
|
||||||
|
.default("@matthiesenxyz/astro-ghostcms-theme-default"),
|
||||||
verbose: z.boolean().optional().default(false),
|
verbose: z.boolean().optional().default(false),
|
||||||
}),
|
}),
|
||||||
plugins: [...corePlugins],
|
plugins: [...corePlugins],
|
||||||
|
@ -14,22 +17,30 @@ export default defineIntegration({
|
||||||
const { resolve } = createResolver(import.meta.url);
|
const { resolve } = createResolver(import.meta.url);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
"astro:config:setup": ({
|
"astro:config:setup": ({ watchIntegration, injectRoute, logger }) => {
|
||||||
watchIntegration,
|
watchIntegration(resolve());
|
||||||
injectRoute,
|
|
||||||
logger
|
|
||||||
}) => {
|
|
||||||
watchIntegration(resolve())
|
|
||||||
|
|
||||||
const themeLogger = logger.fork(`${c.bold(c.blue('👻 Astro-GhostCMS'))}${c.gray("/")}${c.blue('Theme Provider')}`);
|
const themeLogger = logger.fork(
|
||||||
|
`${c.bold(c.blue("👻 Astro-GhostCMS"))}${c.gray("/")}${c.blue(
|
||||||
|
"Theme Provider",
|
||||||
|
)}`,
|
||||||
|
);
|
||||||
|
|
||||||
themeLogger.info(c.bold(c.magenta('Theme Provider enabled. Setting up...')))
|
themeLogger.info(
|
||||||
|
c.bold(c.magenta("Theme Provider enabled. Setting up...")),
|
||||||
|
);
|
||||||
|
|
||||||
if ( options.verbose) {
|
if (options.verbose) {
|
||||||
if ( options.theme === "@matthiesenxyz/astro-ghostcms-theme-default" ) {
|
if (options.theme === "@matthiesenxyz/astro-ghostcms-theme-default") {
|
||||||
themeLogger.info(c.blue('No theme is set, injecting default theme'))
|
themeLogger.info(
|
||||||
|
c.blue("No theme is set, injecting default theme"),
|
||||||
|
);
|
||||||
} else {
|
} else {
|
||||||
themeLogger.info(`${c.bold(c.cyan("Injecting Theme:"))} ${c.bold(c.underline(c.magenta(options.theme)))}`)
|
themeLogger.info(
|
||||||
|
`${c.bold(c.cyan("Injecting Theme:"))} ${c.bold(
|
||||||
|
c.underline(c.magenta(options.theme)),
|
||||||
|
)}`,
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -67,15 +78,18 @@ export default defineIntegration({
|
||||||
pattern: "/archives/[...page]",
|
pattern: "/archives/[...page]",
|
||||||
entrypoint: `${options.theme}/archives/[...page].astro`,
|
entrypoint: `${options.theme}/archives/[...page].astro`,
|
||||||
});
|
});
|
||||||
|
|
||||||
},
|
},
|
||||||
"astro:config:done": ({ logger }) => {
|
"astro:config:done": ({ logger }) => {
|
||||||
const themeLogger = logger.fork(`${c.bold(c.blue('👻 Astro-GhostCMS'))}${c.gray("/")}${c.blue('Theme Provider')}`);
|
const themeLogger = logger.fork(
|
||||||
|
`${c.bold(c.blue("👻 Astro-GhostCMS"))}${c.gray("/")}${c.blue(
|
||||||
|
"Theme Provider",
|
||||||
|
)}`,
|
||||||
|
);
|
||||||
|
|
||||||
if ( options.verbose ) {
|
if (options.verbose) {
|
||||||
themeLogger.info(c.bold(c.green('Provider Setup Complete')))
|
themeLogger.info(c.bold(c.green("Provider Setup Complete")));
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
}
|
};
|
||||||
}
|
},
|
||||||
})
|
});
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
import createFetchMock from "vitest-fetch-mock";
|
|
||||||
import { afterEach, beforeEach, describe, expect, test, vi } from "vitest";
|
import { afterEach, beforeEach, describe, expect, test, vi } from "vitest";
|
||||||
|
import createFetchMock from "vitest-fetch-mock";
|
||||||
|
|
||||||
import { TSGhostContentAPI } from "@ts-ghost/content-api";
|
import { TSGhostContentAPI } from "@ts-ghost/content-api";
|
||||||
|
|
||||||
|
@ -7,7 +7,8 @@ const fetchMocker = createFetchMock(vi);
|
||||||
|
|
||||||
describe("authors api .browse() Args Type-safety", () => {
|
describe("authors api .browse() Args Type-safety", () => {
|
||||||
const url = process.env.VITE_GHOST_URL || "https://my-ghost-blog.com";
|
const url = process.env.VITE_GHOST_URL || "https://my-ghost-blog.com";
|
||||||
const key = process.env.VITE_GHOST_CONTENT_API_KEY || "59d4bf56c73c04a18c867dc3ba";
|
const key =
|
||||||
|
process.env.VITE_GHOST_CONTENT_API_KEY || "59d4bf56c73c04a18c867dc3ba";
|
||||||
const api = new TSGhostContentAPI(url, key, "v5.0");
|
const api = new TSGhostContentAPI(url, key, "v5.0");
|
||||||
test(".browse() params shouldnt accept invalid params", () => {
|
test(".browse() params shouldnt accept invalid params", () => {
|
||||||
// @ts-expect-error - shouldnt accept invalid params
|
// @ts-expect-error - shouldnt accept invalid params
|
||||||
|
@ -19,19 +20,28 @@ describe("authors api .browse() Args Type-safety", () => {
|
||||||
// @ts-expect-error - order should ony contain field
|
// @ts-expect-error - order should ony contain field
|
||||||
expect(() => api.authors.browse({ order: "foo ASC" })).toThrow();
|
expect(() => api.authors.browse({ order: "foo ASC" })).toThrow();
|
||||||
// valid
|
// valid
|
||||||
expect(api.authors.browse({ order: "name ASC" }).getParams().browseParams).toStrictEqual({
|
expect(
|
||||||
|
api.authors.browse({ order: "name ASC" }).getParams().browseParams,
|
||||||
|
).toStrictEqual({
|
||||||
order: "name ASC",
|
order: "name ASC",
|
||||||
});
|
});
|
||||||
expect(api.authors.browse({ order: "name ASC,slug DESC" }).getParams().browseParams).toStrictEqual({
|
expect(
|
||||||
|
api.authors.browse({ order: "name ASC,slug DESC" }).getParams()
|
||||||
|
.browseParams,
|
||||||
|
).toStrictEqual({
|
||||||
order: "name ASC,slug DESC",
|
order: "name ASC,slug DESC",
|
||||||
});
|
});
|
||||||
expect(
|
expect(
|
||||||
api.authors.browse({ order: "name ASC,slug DESC,location ASC" }).getParams().browseParams
|
api.authors
|
||||||
|
.browse({ order: "name ASC,slug DESC,location ASC" })
|
||||||
|
.getParams().browseParams,
|
||||||
).toStrictEqual({
|
).toStrictEqual({
|
||||||
order: "name ASC,slug DESC,location ASC",
|
order: "name ASC,slug DESC,location ASC",
|
||||||
});
|
});
|
||||||
// @ts-expect-error - order should ony contain field (There is a typo in location)
|
// @ts-expect-error - order should ony contain field (There is a typo in location)
|
||||||
expect(() => api.authors.browse({ order: "name ASC,slug DESC,locaton ASC" })).toThrow();
|
expect(() =>
|
||||||
|
api.authors.browse({ order: "name ASC,slug DESC,locaton ASC" }),
|
||||||
|
).toThrow();
|
||||||
});
|
});
|
||||||
|
|
||||||
test(".browse() 'filter' params should ony accept valid field", () => {
|
test(".browse() 'filter' params should ony accept valid field", () => {
|
||||||
|
@ -39,14 +49,14 @@ describe("authors api .browse() Args Type-safety", () => {
|
||||||
api.authors.browse({
|
api.authors.browse({
|
||||||
// @ts-expect-error - order should ony contain field
|
// @ts-expect-error - order should ony contain field
|
||||||
filter: "foo:bar",
|
filter: "foo:bar",
|
||||||
})
|
}),
|
||||||
).toThrow();
|
).toThrow();
|
||||||
expect(
|
expect(
|
||||||
api.authors
|
api.authors
|
||||||
.browse({
|
.browse({
|
||||||
filter: "name:bar",
|
filter: "name:bar",
|
||||||
})
|
})
|
||||||
.getParams().browseParams
|
.getParams().browseParams,
|
||||||
).toStrictEqual({
|
).toStrictEqual({
|
||||||
filter: "name:bar",
|
filter: "name:bar",
|
||||||
});
|
});
|
||||||
|
@ -55,7 +65,7 @@ describe("authors api .browse() Args Type-safety", () => {
|
||||||
.browse({
|
.browse({
|
||||||
filter: "name:bar+slug:-test",
|
filter: "name:bar+slug:-test",
|
||||||
})
|
})
|
||||||
.getParams().browseParams
|
.getParams().browseParams,
|
||||||
).toStrictEqual({
|
).toStrictEqual({
|
||||||
filter: "name:bar+slug:-test",
|
filter: "name:bar+slug:-test",
|
||||||
});
|
});
|
||||||
|
@ -69,14 +79,18 @@ describe("authors api .browse() Args Type-safety", () => {
|
||||||
// @ts-expect-error - order should ony contain field
|
// @ts-expect-error - order should ony contain field
|
||||||
foo: true,
|
foo: true,
|
||||||
})
|
})
|
||||||
.getOutputFields()
|
.getOutputFields(),
|
||||||
).toEqual([]);
|
).toEqual([]);
|
||||||
|
|
||||||
expect(api.authors.browse().fields({ location: true }).getOutputFields()).toEqual(["location"]);
|
expect(
|
||||||
expect(api.authors.browse().fields({ name: true, website: true }).getOutputFields()).toEqual([
|
api.authors.browse().fields({ location: true }).getOutputFields(),
|
||||||
"name",
|
).toEqual(["location"]);
|
||||||
"website",
|
expect(
|
||||||
]);
|
api.authors
|
||||||
|
.browse()
|
||||||
|
.fields({ name: true, website: true })
|
||||||
|
.getOutputFields(),
|
||||||
|
).toEqual(["name", "website"]);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -84,7 +98,11 @@ describe("authors resource mocked", () => {
|
||||||
let api: TSGhostContentAPI;
|
let api: TSGhostContentAPI;
|
||||||
|
|
||||||
beforeEach(() => {
|
beforeEach(() => {
|
||||||
api = new TSGhostContentAPI("https://my-ghost-blog.com", "59d4bf56c73c04a18c867dc3ba", "v5.0");
|
api = new TSGhostContentAPI(
|
||||||
|
"https://my-ghost-blog.com",
|
||||||
|
"59d4bf56c73c04a18c867dc3ba",
|
||||||
|
"v5.0",
|
||||||
|
);
|
||||||
fetchMocker.enableMocks();
|
fetchMocker.enableMocks();
|
||||||
});
|
});
|
||||||
afterEach(() => {
|
afterEach(() => {
|
||||||
|
@ -123,7 +141,7 @@ describe("authors resource mocked", () => {
|
||||||
prev: null,
|
prev: null,
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
})
|
}),
|
||||||
);
|
);
|
||||||
const result = await browseQuery.fetch();
|
const result = await browseQuery.fetch();
|
||||||
expect(fetchMocker).toHaveBeenCalledTimes(1);
|
expect(fetchMocker).toHaveBeenCalledTimes(1);
|
||||||
|
@ -134,7 +152,7 @@ describe("authors resource mocked", () => {
|
||||||
"Content-Type": "application/json",
|
"Content-Type": "application/json",
|
||||||
"Accept-Version": "v5.0",
|
"Accept-Version": "v5.0",
|
||||||
},
|
},
|
||||||
}
|
},
|
||||||
);
|
);
|
||||||
expect(result).not.toBeUndefined();
|
expect(result).not.toBeUndefined();
|
||||||
if (result.success) {
|
if (result.success) {
|
||||||
|
|
|
@ -4,7 +4,8 @@ import { TSGhostContentAPI } from "@ts-ghost/content-api";
|
||||||
import type { Post } from "./index";
|
import type { Post } from "./index";
|
||||||
|
|
||||||
const url = process.env.VITE_GHOST_URL || "https://my-ghost-blog.com";
|
const url = process.env.VITE_GHOST_URL || "https://my-ghost-blog.com";
|
||||||
const key = process.env.VITE_GHOST_CONTENT_API_KEY || "59d4bf56c73c04a18c867dc3ba";
|
const key =
|
||||||
|
process.env.VITE_GHOST_CONTENT_API_KEY || "59d4bf56c73c04a18c867dc3ba";
|
||||||
|
|
||||||
describe("posts api .browse() Args Type-safety", () => {
|
describe("posts api .browse() Args Type-safety", () => {
|
||||||
const api = new TSGhostContentAPI(url, key, "v5.0");
|
const api = new TSGhostContentAPI(url, key, "v5.0");
|
||||||
|
@ -27,10 +28,13 @@ describe("posts api .browse() Args Type-safety", () => {
|
||||||
expect(test.getOutputFields()).toEqual(["slug", "title"]);
|
expect(test.getOutputFields()).toEqual(["slug", "title"]);
|
||||||
|
|
||||||
const fields = ["slug", "title", "foo"] as const;
|
const fields = ["slug", "title", "foo"] as const;
|
||||||
const unknownOriginFields = fields.reduce((acc, k) => {
|
const unknownOriginFields = fields.reduce(
|
||||||
|
(acc, k) => {
|
||||||
acc[k as keyof Post] = true;
|
acc[k as keyof Post] = true;
|
||||||
return acc;
|
return acc;
|
||||||
}, {} as { [k in keyof Post]?: true | undefined });
|
},
|
||||||
|
{} as { [k in keyof Post]?: true | undefined },
|
||||||
|
);
|
||||||
const result = api.posts.browse().fields(unknownOriginFields);
|
const result = api.posts.browse().fields(unknownOriginFields);
|
||||||
expect(result.getOutputFields()).toEqual(["slug", "title"]);
|
expect(result.getOutputFields()).toEqual(["slug", "title"]);
|
||||||
});
|
});
|
||||||
|
@ -46,10 +50,18 @@ describe("posts api .browse() Args Type-safety", () => {
|
||||||
// @ts-expect-error - shouldnt accept invalid params
|
// @ts-expect-error - shouldnt accept invalid params
|
||||||
expect(() => api.posts.browse({ filter: "slugg:test" })).toThrow();
|
expect(() => api.posts.browse({ filter: "slugg:test" })).toThrow();
|
||||||
// @ts-expect-error - shouldnt accept invalid params
|
// @ts-expect-error - shouldnt accept invalid params
|
||||||
expect(() => api.posts.browse({ filter: "slug:test,foo:-[bar,baz]" })).toThrow();
|
expect(() =>
|
||||||
expect(api.posts.browse({ filter: "slug:test,tags:-[bar,baz]" })).toBeDefined();
|
api.posts.browse({ filter: "slug:test,foo:-[bar,baz]" }),
|
||||||
expect(api.posts.browse({ filter: "slug:test,tags:[bar,baz]" })).toBeDefined();
|
).toThrow();
|
||||||
|
expect(
|
||||||
|
api.posts.browse({ filter: "slug:test,tags:-[bar,baz]" }),
|
||||||
|
).toBeDefined();
|
||||||
|
expect(
|
||||||
|
api.posts.browse({ filter: "slug:test,tags:[bar,baz]" }),
|
||||||
|
).toBeDefined();
|
||||||
// @ts-expect-error - shouldnt accept invalid params
|
// @ts-expect-error - shouldnt accept invalid params
|
||||||
expect(() => api.posts.browse({ filter: "slug:test,food:-[bar,baz]" })).toThrow();
|
expect(() =>
|
||||||
|
api.posts.browse({ filter: "slug:test,food:-[bar,baz]" }),
|
||||||
|
).toThrow();
|
||||||
});
|
});
|
||||||
});
|
});
|
|
@ -3,7 +3,8 @@ import { beforeEach, describe, expect, test } from "vitest";
|
||||||
import { TSGhostContentAPI } from "@ts-ghost/content-api";
|
import { TSGhostContentAPI } from "@ts-ghost/content-api";
|
||||||
|
|
||||||
const url = process.env.VITE_GHOST_URL || "https://my-ghost-blog.com";
|
const url = process.env.VITE_GHOST_URL || "https://my-ghost-blog.com";
|
||||||
const key = process.env.VITE_GHOST_CONTENT_API_KEY || "59d4bf56c73c04a18c867dc3ba";
|
const key =
|
||||||
|
process.env.VITE_GHOST_CONTENT_API_KEY || "59d4bf56c73c04a18c867dc3ba";
|
||||||
|
|
||||||
describe("settings integration tests browse", () => {
|
describe("settings integration tests browse", () => {
|
||||||
let api: TSGhostContentAPI;
|
let api: TSGhostContentAPI;
|
||||||
|
@ -24,7 +25,9 @@ describe("settings integration tests browse", () => {
|
||||||
expect(settings.title).toBe("Astro Starter");
|
expect(settings.title).toBe("Astro Starter");
|
||||||
expect(settings.description).toBe("Thoughts, stories and ideas.");
|
expect(settings.description).toBe("Thoughts, stories and ideas.");
|
||||||
expect(settings.logo).toBeNull();
|
expect(settings.logo).toBeNull();
|
||||||
expect(settings.cover_image).toBe("https://static.ghost.org/v4.0.0/images/publication-cover.jpg");
|
expect(settings.cover_image).toBe(
|
||||||
|
"https://static.ghost.org/v4.0.0/images/publication-cover.jpg",
|
||||||
|
);
|
||||||
expect(settings.icon).toBeNull();
|
expect(settings.icon).toBeNull();
|
||||||
expect(settings.lang).toBe("en");
|
expect(settings.lang).toBe("en");
|
||||||
expect(settings.timezone).toBe("Etc/UTC");
|
expect(settings.timezone).toBe("Etc/UTC");
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
import { expect, describe, it } from "vitest";
|
import { describe, expect, it } from "vitest";
|
||||||
import { GhostUserConfigSchema } from "./userconfig";
|
import { GhostUserConfigSchema } from "./userconfig";
|
||||||
|
|
||||||
describe("GhostUserConfigSchema", () => {
|
describe("GhostUserConfigSchema", () => {
|
||||||
|
|
|
@ -18,12 +18,17 @@ export const GhostUserConfigSchema = z.object({
|
||||||
* @default false
|
* @default false
|
||||||
*/
|
*/
|
||||||
disableThemeProvider: z.boolean().optional().default(false),
|
disableThemeProvider: z.boolean().optional().default(false),
|
||||||
ThemeProvider: z.object({
|
ThemeProvider: z
|
||||||
|
.object({
|
||||||
/** OPTIONAL - Set the theme you want to use
|
/** OPTIONAL - Set the theme you want to use
|
||||||
* @default "@matthiesenxyz/astro-ghostcms-theme-default"
|
* @default "@matthiesenxyz/astro-ghostcms-theme-default"
|
||||||
*/
|
*/
|
||||||
theme: z.string().optional().default("@matthiesenxyz/astro-ghostcms-theme-default"),
|
theme: z
|
||||||
}).optional(),
|
.string()
|
||||||
|
.optional()
|
||||||
|
.default("@matthiesenxyz/astro-ghostcms-theme-default"),
|
||||||
|
})
|
||||||
|
.optional(),
|
||||||
/** Allows the user to disable the provided 404 page */
|
/** Allows the user to disable the provided 404 page */
|
||||||
disableDefault404: z.boolean().optional().default(false),
|
disableDefault404: z.boolean().optional().default(false),
|
||||||
/** Allows the user to disable the provided RSS Feed */
|
/** Allows the user to disable the provided RSS Feed */
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
/// <reference types="vitest" />
|
/// <reference types="vitest" />
|
||||||
/// <reference types="vite/client" />
|
/// <reference types="vite/client" />
|
||||||
import { defineProject } from 'vitest/config'
|
import { defineProject } from "vitest/config";
|
||||||
|
|
||||||
export default defineProject({
|
export default defineProject({
|
||||||
test: {
|
test: {
|
||||||
|
@ -9,4 +9,4 @@ export default defineProject({
|
||||||
watchExclude: [".*\\/node_modules\\/.*", ".*\\/build\\/.*"],
|
watchExclude: [".*\\/node_modules\\/.*", ".*\\/build\\/.*"],
|
||||||
exclude: ["node_modules", "dist", ".idea", ".git", ".cache"],
|
exclude: ["node_modules", "dist", ".idea", ".git", ".cache"],
|
||||||
},
|
},
|
||||||
})
|
});
|
||||||
|
|
|
@ -1,16 +1,16 @@
|
||||||
import { defineConfig } from "astro/config";
|
|
||||||
import ghostcms from "@matthiesenxyz/astro-ghostcms";
|
import ghostcms from "@matthiesenxyz/astro-ghostcms";
|
||||||
import UnoCSS from 'unocss/astro';
|
import { defineConfig } from "astro/config";
|
||||||
|
import UnoCSS from "unocss/astro";
|
||||||
|
|
||||||
// https://astro.build/config
|
// https://astro.build/config
|
||||||
export default defineConfig({
|
export default defineConfig({
|
||||||
site: "https://example.xyz/",
|
site: "https://example.xyz/",
|
||||||
trailingSlash: 'ignore',
|
trailingSlash: "ignore",
|
||||||
integrations: [
|
integrations: [
|
||||||
UnoCSS({ injectReset: true }),
|
UnoCSS({ injectReset: true }),
|
||||||
ghostcms({
|
ghostcms({
|
||||||
theme: "@matthiesenxyz/astro-ghostcms-brutalbyelian",
|
theme: "@matthiesenxyz/astro-ghostcms-brutalbyelian",
|
||||||
ghostURL: "https://ghostdemo.matthiesen.xyz",
|
ghostURL: "https://ghostdemo.matthiesen.xyz",
|
||||||
})
|
}),
|
||||||
],
|
],
|
||||||
});
|
});
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
/// <reference types="astro/client" />
|
/// <reference types="astro/client" />
|
||||||
interface ImportMetaEnv {
|
interface ImportMetaEnv {
|
||||||
readonly CONTENT_API_KEY: string
|
readonly CONTENT_API_KEY: string;
|
||||||
readonly CONTENT_API_URL: string
|
readonly CONTENT_API_URL: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
interface ImportMeta {
|
interface ImportMeta {
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
import brutalTheme from '@matthiesenxyz/astro-ghostcms-brutalbyelian';
|
import brutalTheme from "@matthiesenxyz/astro-ghostcms-brutalbyelian";
|
||||||
import { defineConfig } from 'unocss';
|
import { defineConfig } from "unocss";
|
||||||
|
|
||||||
export default defineConfig({
|
export default defineConfig({
|
||||||
presets: [ brutalTheme() ],
|
presets: [brutalTheme()],
|
||||||
});
|
});
|
||||||
|
|
|
@ -1,91 +1,126 @@
|
||||||
import type { StarlightPlugin, StarlightUserConfig } from '@astrojs/starlight/types'
|
import type {
|
||||||
import type { AstroIntegrationLogger } from 'astro'
|
StarlightPlugin,
|
||||||
import { type StarlightGhostConfig, validateConfig } from './src/schemas/config'
|
StarlightUserConfig,
|
||||||
import { vitePluginStarlightGhostConfig } from './src/integrations/vite'
|
} from "@astrojs/starlight/types";
|
||||||
import { facebook, getSettings, invariant, twitter } from './src/utils/api'
|
import type { AstroIntegrationLogger } from "astro";
|
||||||
|
import { vitePluginStarlightGhostConfig } from "./src/integrations/vite";
|
||||||
|
import {
|
||||||
|
type StarlightGhostConfig,
|
||||||
|
validateConfig,
|
||||||
|
} from "./src/schemas/config";
|
||||||
|
import { facebook, getSettings, invariant, twitter } from "./src/utils/api";
|
||||||
|
|
||||||
const settings = await getSettings()
|
const settings = await getSettings();
|
||||||
|
|
||||||
export type { StarlightGhostConfig }
|
export type { StarlightGhostConfig };
|
||||||
|
|
||||||
export default function starlightGhostCMS(userConfig?: StarlightGhostConfig): StarlightPlugin {
|
export default function starlightGhostCMS(
|
||||||
const config: StarlightGhostConfig = validateConfig(userConfig)
|
userConfig?: StarlightGhostConfig,
|
||||||
invariant(settings, "Settings not available... check your api key/url")
|
): StarlightPlugin {
|
||||||
|
const config: StarlightGhostConfig = validateConfig(userConfig);
|
||||||
|
invariant(settings, "Settings not available... check your api key/url");
|
||||||
|
|
||||||
return {
|
return {
|
||||||
name: '@matthiesenxyz/starlight-ghostcms-plugin',
|
name: "@matthiesenxyz/starlight-ghostcms-plugin",
|
||||||
hooks: {
|
hooks: {
|
||||||
setup({ astroConfig, addIntegration, config: starlightConfig, logger, updateConfig: updateStarlightConfig }) {
|
setup({
|
||||||
|
astroConfig,
|
||||||
|
addIntegration,
|
||||||
|
config: starlightConfig,
|
||||||
|
logger,
|
||||||
|
updateConfig: updateStarlightConfig,
|
||||||
|
}) {
|
||||||
updateStarlightConfig({
|
updateStarlightConfig({
|
||||||
social: {
|
social: {
|
||||||
...starlightConfig.social,
|
...starlightConfig.social,
|
||||||
rss: `${astroConfig.site}/rss.xml`,
|
rss: `${astroConfig.site}/rss.xml`,
|
||||||
twitter: twitter(settings.twitter?settings.twitter:""),
|
twitter: twitter(settings.twitter ? settings.twitter : ""),
|
||||||
facebook: facebook(settings.facebook?settings.facebook:""),
|
facebook: facebook(settings.facebook ? settings.facebook : ""),
|
||||||
},
|
},
|
||||||
components: {
|
components: {
|
||||||
...starlightConfig.components,
|
...starlightConfig.components,
|
||||||
...overrideStarlightComponent(starlightConfig.components, logger, 'MarkdownContent'),
|
...overrideStarlightComponent(
|
||||||
...overrideStarlightComponent(starlightConfig.components, logger, 'Sidebar'),
|
starlightConfig.components,
|
||||||
...overrideStarlightComponent(starlightConfig.components, logger, "SiteTitle"),
|
logger,
|
||||||
}
|
"MarkdownContent",
|
||||||
})
|
),
|
||||||
|
...overrideStarlightComponent(
|
||||||
|
starlightConfig.components,
|
||||||
|
logger,
|
||||||
|
"Sidebar",
|
||||||
|
),
|
||||||
|
...overrideStarlightComponent(
|
||||||
|
starlightConfig.components,
|
||||||
|
logger,
|
||||||
|
"SiteTitle",
|
||||||
|
),
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
addIntegration({
|
addIntegration({
|
||||||
name: '@matthiesenxyz/starlight-ghostcms',
|
name: "@matthiesenxyz/starlight-ghostcms",
|
||||||
hooks: {
|
hooks: {
|
||||||
'astro:config:setup': ({ injectRoute, updateConfig }) => {
|
"astro:config:setup": ({ injectRoute, updateConfig }) => {
|
||||||
injectRoute({
|
injectRoute({
|
||||||
pattern: '/blog',
|
pattern: "/blog",
|
||||||
entrypoint: '@matthiesenxyz/starlight-ghostcms/routes/index.astro',
|
entrypoint:
|
||||||
|
"@matthiesenxyz/starlight-ghostcms/routes/index.astro",
|
||||||
prerender: true,
|
prerender: true,
|
||||||
})
|
});
|
||||||
injectRoute({
|
injectRoute({
|
||||||
pattern: '/blog/[slug]',
|
pattern: "/blog/[slug]",
|
||||||
entrypoint: '@matthiesenxyz/starlight-ghostcms/routes/[slug].astro',
|
entrypoint:
|
||||||
|
"@matthiesenxyz/starlight-ghostcms/routes/[slug].astro",
|
||||||
prerender: true,
|
prerender: true,
|
||||||
})
|
});
|
||||||
injectRoute({
|
injectRoute({
|
||||||
pattern: '/blog/about',
|
pattern: "/blog/about",
|
||||||
entrypoint: '@matthiesenxyz/starlight-ghostcms/routes/about.astro',
|
entrypoint:
|
||||||
|
"@matthiesenxyz/starlight-ghostcms/routes/about.astro",
|
||||||
prerender: true,
|
prerender: true,
|
||||||
})
|
});
|
||||||
injectRoute({
|
injectRoute({
|
||||||
pattern: '/blog/authors',
|
pattern: "/blog/authors",
|
||||||
entrypoint: '@matthiesenxyz/starlight-ghostcms/routes/authors.astro',
|
entrypoint:
|
||||||
})
|
"@matthiesenxyz/starlight-ghostcms/routes/authors.astro",
|
||||||
|
});
|
||||||
injectRoute({
|
injectRoute({
|
||||||
pattern: '/rss.xml',
|
pattern: "/rss.xml",
|
||||||
entrypoint: '@matthiesenxyz/starlight-ghostcms/routes/rss.xml.ts'
|
entrypoint:
|
||||||
})
|
"@matthiesenxyz/starlight-ghostcms/routes/rss.xml.ts",
|
||||||
|
});
|
||||||
|
|
||||||
updateConfig({
|
updateConfig({
|
||||||
vite: {
|
vite: {
|
||||||
plugins: [vitePluginStarlightGhostConfig(config)],
|
plugins: [vitePluginStarlightGhostConfig(config)],
|
||||||
},
|
},
|
||||||
})
|
});
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
}
|
|
||||||
},
|
},
|
||||||
}
|
},
|
||||||
|
});
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
function overrideStarlightComponent(
|
function overrideStarlightComponent(
|
||||||
components: StarlightUserConfig['components'],
|
components: StarlightUserConfig["components"],
|
||||||
logger: AstroIntegrationLogger,
|
logger: AstroIntegrationLogger,
|
||||||
component: keyof NonNullable<StarlightUserConfig['components']>,
|
component: keyof NonNullable<StarlightUserConfig["components"]>,
|
||||||
) {
|
) {
|
||||||
if (components?.[component]) {
|
if (components?.[component]) {
|
||||||
logger.warn(`It looks like you already have a \`${component}\` component override in your Starlight configuration.`)
|
logger.warn(
|
||||||
logger.warn(`To use \`starlight-ghostcms\`, remove the override for the \`${component}\` component.\n`)
|
`It looks like you already have a \`${component}\` component override in your Starlight configuration.`,
|
||||||
logger.warn("This Warning can be ignored if you know what your doing ;)")
|
);
|
||||||
|
logger.warn(
|
||||||
|
`To use \`starlight-ghostcms\`, remove the override for the \`${component}\` component.\n`,
|
||||||
|
);
|
||||||
|
logger.warn("This Warning can be ignored if you know what your doing ;)");
|
||||||
|
|
||||||
return {}
|
return {};
|
||||||
}
|
}
|
||||||
|
|
||||||
return {
|
return {
|
||||||
[component]: `@matthiesenxyz/starlight-ghostcms/overrides/${component}.astro`,
|
[component]: `@matthiesenxyz/starlight-ghostcms/overrides/${component}.astro`,
|
||||||
}
|
};
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,22 +1,24 @@
|
||||||
import type { ViteUserConfig } from 'astro'
|
import type { ViteUserConfig } from "astro";
|
||||||
|
|
||||||
import type { StarlightGhostConfig } from '../schemas/config.ts'
|
import type { StarlightGhostConfig } from "../schemas/config.ts";
|
||||||
|
|
||||||
// Expose the starlight-blog plugin configuration.
|
// Expose the starlight-blog plugin configuration.
|
||||||
export function vitePluginStarlightGhostConfig(config: StarlightGhostConfig): VitePlugin {
|
export function vitePluginStarlightGhostConfig(
|
||||||
const moduleId = 'virtual:starlight-ghost-config'
|
config: StarlightGhostConfig,
|
||||||
const resolvedModuleId = `\0${moduleId}`
|
): VitePlugin {
|
||||||
const moduleContent = `export default ${JSON.stringify(config)}`
|
const moduleId = "virtual:starlight-ghost-config";
|
||||||
|
const resolvedModuleId = `\0${moduleId}`;
|
||||||
|
const moduleContent = `export default ${JSON.stringify(config)}`;
|
||||||
|
|
||||||
return {
|
return {
|
||||||
name: 'vite-plugin-starlight-ghost-config',
|
name: "vite-plugin-starlight-ghost-config",
|
||||||
load(id) {
|
load(id) {
|
||||||
return id === resolvedModuleId ? moduleContent : undefined
|
return id === resolvedModuleId ? moduleContent : undefined;
|
||||||
},
|
},
|
||||||
resolveId(id) {
|
resolveId(id) {
|
||||||
return id === moduleId ? resolvedModuleId : undefined
|
return id === moduleId ? resolvedModuleId : undefined;
|
||||||
},
|
},
|
||||||
}
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
type VitePlugin = NonNullable<ViteUserConfig['plugins']>[number]
|
type VitePlugin = NonNullable<ViteUserConfig["plugins"]>[number];
|
||||||
|
|
|
@ -1,15 +1,19 @@
|
||||||
import { z } from 'astro/zod';
|
import type { AstroBuiltinAttributes } from "astro";
|
||||||
import type { AstroBuiltinAttributes } from 'astro';
|
import type { HTMLAttributes } from "astro/types";
|
||||||
import type { HTMLAttributes } from 'astro/types';
|
import { z } from "astro/zod";
|
||||||
|
|
||||||
const linkHTMLAttributesSchema = z.record(
|
const linkHTMLAttributesSchema = z.record(
|
||||||
z.union([z.string(), z.number(), z.boolean(), z.undefined()])
|
z.union([z.string(), z.number(), z.boolean(), z.undefined()]),
|
||||||
) as z.Schema<Omit<HTMLAttributes<'a'>, keyof AstroBuiltinAttributes | 'children'>>;
|
) as z.Schema<
|
||||||
|
Omit<HTMLAttributes<"a">, keyof AstroBuiltinAttributes | "children">
|
||||||
|
>;
|
||||||
export type LinkHTMLAttributes = z.infer<typeof linkHTMLAttributesSchema>;
|
export type LinkHTMLAttributes = z.infer<typeof linkHTMLAttributesSchema>;
|
||||||
|
|
||||||
const badgeSchema = () =>
|
const badgeSchema = () =>
|
||||||
z.object({
|
z.object({
|
||||||
variant: z.enum(['note', 'danger', 'success', 'caution', 'tip', 'default']).default('default'),
|
variant: z
|
||||||
|
.enum(["note", "danger", "success", "caution", "tip", "default"])
|
||||||
|
.default("default"),
|
||||||
text: z.string(),
|
text: z.string(),
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -17,8 +21,8 @@ export const BadgeConfigSchema = () =>
|
||||||
z
|
z
|
||||||
.union([z.string(), badgeSchema()])
|
.union([z.string(), badgeSchema()])
|
||||||
.transform((badge) => {
|
.transform((badge) => {
|
||||||
if (typeof badge === 'string') {
|
if (typeof badge === "string") {
|
||||||
return { variant: 'default' as const, text: badge };
|
return { variant: "default" as const, text: badge };
|
||||||
}
|
}
|
||||||
return badge;
|
return badge;
|
||||||
})
|
})
|
||||||
|
@ -27,7 +31,7 @@ export const BadgeConfigSchema = () =>
|
||||||
export type Badge = z.output<ReturnType<typeof badgeSchema>>;
|
export type Badge = z.output<ReturnType<typeof badgeSchema>>;
|
||||||
|
|
||||||
export interface Link {
|
export interface Link {
|
||||||
type: 'link';
|
type: "link";
|
||||||
label: string;
|
label: string;
|
||||||
href: string;
|
href: string;
|
||||||
isCurrent: boolean;
|
isCurrent: boolean;
|
||||||
|
@ -36,7 +40,7 @@ export interface Link {
|
||||||
}
|
}
|
||||||
|
|
||||||
interface Group {
|
interface Group {
|
||||||
type: 'group';
|
type: "group";
|
||||||
label: string;
|
label: string;
|
||||||
entries: (Link | Group)[];
|
entries: (Link | Group)[];
|
||||||
collapsed: boolean;
|
collapsed: boolean;
|
||||||
|
|
|
@ -5,17 +5,17 @@ import { getAllPosts, getSettings, invariant } from "../utils/api";
|
||||||
const posts = await getAllPosts();
|
const posts = await getAllPosts();
|
||||||
const settings = await getSettings();
|
const settings = await getSettings();
|
||||||
|
|
||||||
import config from 'virtual:starlight-ghost-config';
|
import config from "virtual:starlight-ghost-config";
|
||||||
|
|
||||||
export async function GET({ site }: APIContext) {
|
export async function GET({ site }: APIContext) {
|
||||||
invariant(settings,"Settings is not defined")
|
invariant(settings, "Settings is not defined");
|
||||||
const title = config.title;
|
const title = config.title;
|
||||||
const description = config.rssDescription;
|
const description = config.rssDescription;
|
||||||
const ghostSite = settings.url
|
const ghostSite = settings.url;
|
||||||
return rss({
|
return rss({
|
||||||
title: title,
|
title: title,
|
||||||
description: description,
|
description: description,
|
||||||
site: site?site:ghostSite,
|
site: site ? site : ghostSite,
|
||||||
items: posts.map((post) => ({
|
items: posts.map((post) => ({
|
||||||
title: post.title,
|
title: post.title,
|
||||||
pubDate: new Date(
|
pubDate: new Date(
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
import { AstroError } from 'astro/errors'
|
import { AstroError } from "astro/errors";
|
||||||
import { z } from 'astro/zod'
|
import { z } from "astro/zod";
|
||||||
|
|
||||||
const configSchema = z
|
const configSchema = z
|
||||||
.object({
|
.object({
|
||||||
|
@ -14,37 +14,39 @@ const configSchema = z
|
||||||
/**
|
/**
|
||||||
* The title of the blog.
|
* The title of the blog.
|
||||||
*/
|
*/
|
||||||
title: z.string().default('Blog'),
|
title: z.string().default("Blog"),
|
||||||
/**
|
/**
|
||||||
* The description of the blog on the RSS Feed.
|
* The description of the blog on the RSS Feed.
|
||||||
*/
|
*/
|
||||||
rssDescription: z.string().default('My Awesome Starlight-GhostCMS Blog'),
|
rssDescription: z.string().default("My Awesome Starlight-GhostCMS Blog"),
|
||||||
/**
|
/**
|
||||||
* Turn on and off "Powered by Ghost"
|
* Turn on and off "Powered by Ghost"
|
||||||
*/
|
*/
|
||||||
supportGhost: z.boolean().default(true),
|
supportGhost: z.boolean().default(true),
|
||||||
})
|
})
|
||||||
.default({})
|
.default({});
|
||||||
|
|
||||||
export function validateConfig(userConfig: unknown): StarlightGhostConfig {
|
export function validateConfig(userConfig: unknown): StarlightGhostConfig {
|
||||||
const config = configSchema.safeParse(userConfig)
|
const config = configSchema.safeParse(userConfig);
|
||||||
|
|
||||||
if (!config.success) {
|
if (!config.success) {
|
||||||
const errors = config.error.flatten()
|
const errors = config.error.flatten();
|
||||||
|
|
||||||
throw new AstroError(
|
throw new AstroError(
|
||||||
`Invalid starlight-GhostCMS configuration:
|
`Invalid starlight-GhostCMS configuration:
|
||||||
|
|
||||||
${errors.formErrors.map((formError) => ` - ${formError}`).join('\n')}
|
${errors.formErrors.map((formError) => ` - ${formError}`).join("\n")}
|
||||||
${Object.entries(errors.fieldErrors)
|
${Object.entries(errors.fieldErrors)
|
||||||
.map(([fieldName, fieldErrors]) => ` - ${fieldName}: ${fieldErrors.join(' - ')}`)
|
.map(
|
||||||
.join('\n')}
|
([fieldName, fieldErrors]) => ` - ${fieldName}: ${fieldErrors.join(" - ")}`,
|
||||||
|
)
|
||||||
|
.join("\n")}
|
||||||
`,
|
`,
|
||||||
"See the error report above for more informations.\n\nIf you believe this is a bug, please file an issue at https://github.com/matthiesenxyz/astro-ghostcms/issues/new/choose",
|
"See the error report above for more informations.\n\nIf you believe this is a bug, please file an issue at https://github.com/matthiesenxyz/astro-ghostcms/issues/new/choose",
|
||||||
)
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
return config.data
|
return config.data;
|
||||||
}
|
}
|
||||||
|
|
||||||
export type StarlightGhostConfig = z.infer<typeof configSchema>
|
export type StarlightGhostConfig = z.infer<typeof configSchema>;
|
||||||
|
|
|
@ -1,8 +1,8 @@
|
||||||
import { TS_API } from "./content-api";
|
|
||||||
import type { Page, Post } from "./content-api/schemas";
|
|
||||||
import type { ContentAPICredentials } from './content-api/content-api'
|
|
||||||
// LOAD ENVIRONMENT VARIABLES
|
// LOAD ENVIRONMENT VARIABLES
|
||||||
import { loadEnv } from "vite";
|
import { loadEnv } from "vite";
|
||||||
|
import { TS_API } from "./content-api";
|
||||||
|
import type { ContentAPICredentials } from "./content-api/content-api";
|
||||||
|
import type { Page, Post } from "./content-api/schemas";
|
||||||
import { invariant } from "./invariant.js";
|
import { invariant } from "./invariant.js";
|
||||||
|
|
||||||
const { CONTENT_API_KEY, CONTENT_API_URL } = loadEnv(
|
const { CONTENT_API_KEY, CONTENT_API_URL } = loadEnv(
|
||||||
|
@ -11,17 +11,11 @@ const { CONTENT_API_KEY, CONTENT_API_URL } = loadEnv(
|
||||||
"CONTENT_",
|
"CONTENT_",
|
||||||
);
|
);
|
||||||
|
|
||||||
invariant(
|
invariant(CONTENT_API_KEY, "CONTENT_API_KEY Missing from .env");
|
||||||
CONTENT_API_KEY,
|
invariant(CONTENT_API_URL, "CONTENT_API_URL Missing from .env");
|
||||||
"CONTENT_API_KEY Missing from .env"
|
|
||||||
)
|
|
||||||
invariant(
|
|
||||||
CONTENT_API_URL,
|
|
||||||
"CONTENT_API_URL Missing from .env"
|
|
||||||
)
|
|
||||||
|
|
||||||
const key:ContentAPICredentials["key"] = CONTENT_API_KEY;
|
const key: ContentAPICredentials["key"] = CONTENT_API_KEY;
|
||||||
const url:ContentAPICredentials["url"] = CONTENT_API_URL;
|
const url: ContentAPICredentials["url"] = CONTENT_API_URL;
|
||||||
const version = "v5.0";
|
const version = "v5.0";
|
||||||
const api = new TS_API(url, key, version);
|
const api = new TS_API(url, key, version);
|
||||||
|
|
||||||
|
@ -73,13 +67,14 @@ export const getAllPosts = async () => {
|
||||||
return posts;
|
return posts;
|
||||||
};
|
};
|
||||||
|
|
||||||
export const getSluggedPost = async (slug:string) => {
|
export const getSluggedPost = async (slug: string) => {
|
||||||
const results = await api.posts
|
const results = await api.posts
|
||||||
.read({slug: slug})
|
.read({ slug: slug })
|
||||||
.include({
|
.include({
|
||||||
authors: true,
|
authors: true,
|
||||||
tags: true,
|
tags: true,
|
||||||
}).fetch()
|
})
|
||||||
|
.fetch();
|
||||||
|
|
||||||
if (!results.success) {
|
if (!results.success) {
|
||||||
throw new Error(results.errors.map((e) => e.message).join(", "));
|
throw new Error(results.errors.map((e) => e.message).join(", "));
|
||||||
|
@ -106,13 +101,14 @@ export const getAllPages = async () => {
|
||||||
return pages;
|
return pages;
|
||||||
};
|
};
|
||||||
|
|
||||||
export const getSluggedPage = async (slug:string) => {
|
export const getSluggedPage = async (slug: string) => {
|
||||||
const results = await api.pages
|
const results = await api.pages
|
||||||
.read({slug: slug})
|
.read({ slug: slug })
|
||||||
.include({
|
.include({
|
||||||
authors: true,
|
authors: true,
|
||||||
tags: true,
|
tags: true,
|
||||||
}).fetch()
|
})
|
||||||
|
.fetch();
|
||||||
|
|
||||||
if (!results.success) {
|
if (!results.success) {
|
||||||
throw new Error(results.errors.map((e) => e.message).join(", "));
|
throw new Error(results.errors.map((e) => e.message).join(", "));
|
||||||
|
|
|
@ -1,21 +1,21 @@
|
||||||
export function isAnyBlogPage(slug: string) {
|
export function isAnyBlogPage(slug: string) {
|
||||||
return slug.match(/^blog(\/?$|\/.+\/?$)/) !== null
|
return slug.match(/^blog(\/?$|\/.+\/?$)/) !== null;
|
||||||
}
|
}
|
||||||
|
|
||||||
export function isBlogRoot(slug: string) {
|
export function isBlogRoot(slug: string) {
|
||||||
return slug === 'blog'
|
return slug === "blog";
|
||||||
}
|
}
|
||||||
|
|
||||||
export function isAnyBlogPostPage(slug: string) {
|
export function isAnyBlogPostPage(slug: string) {
|
||||||
return slug.match(/^blog\/(?!(\d+\/?|tags\/.+)$).+$/) !== null
|
return slug.match(/^blog\/(?!(\d+\/?|tags\/.+)$).+$/) !== null;
|
||||||
}
|
}
|
||||||
|
|
||||||
export function isBlogPostPage(slug: string, postSlug: string) {
|
export function isBlogPostPage(slug: string, postSlug: string) {
|
||||||
return slug === postSlug
|
return slug === postSlug;
|
||||||
}
|
}
|
||||||
|
|
||||||
export function isBlogTagsPage(slug: string, tag: string) {
|
export function isBlogTagsPage(slug: string, tag: string) {
|
||||||
return slug === `blog/tags/${tag}`
|
return slug === `blog/tags/${tag}`;
|
||||||
}
|
}
|
||||||
|
|
||||||
export function getPageProps(title: string): StarlightPageProps {
|
export function getPageProps(title: string): StarlightPageProps {
|
||||||
|
@ -23,11 +23,11 @@ export function getPageProps(title: string): StarlightPageProps {
|
||||||
frontmatter: {
|
frontmatter: {
|
||||||
title,
|
title,
|
||||||
},
|
},
|
||||||
}
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
interface StarlightPageProps {
|
interface StarlightPageProps {
|
||||||
frontmatter: {
|
frontmatter: {
|
||||||
title: string
|
title: string;
|
||||||
}
|
};
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
declare module 'virtual:starlight/user-config' {
|
declare module "virtual:starlight/user-config" {
|
||||||
const Config: import('@astrojs/starlight/types').StarlightConfig
|
const Config: import("@astrojs/starlight/types").StarlightConfig;
|
||||||
|
|
||||||
export default Config
|
export default Config;
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
declare module 'virtual:starlight-ghost-config' {
|
declare module "virtual:starlight-ghost-config" {
|
||||||
const StarlightGhostConfig: import('./src/schemas/config').StarlightGhostConfig
|
const StarlightGhostConfig: import("./src/schemas/config").StarlightGhostConfig;
|
||||||
|
|
||||||
export default StarlightGhostConfig
|
export default StarlightGhostConfig;
|
||||||
}
|
}
|
||||||
|
|
|
@ -12,7 +12,7 @@ export default defineConfig({
|
||||||
ghostcms({
|
ghostcms({
|
||||||
ghostURL: "https://ghostdemo.matthiesen.xyz",
|
ghostURL: "https://ghostdemo.matthiesen.xyz",
|
||||||
ThemeProvider: {
|
ThemeProvider: {
|
||||||
theme: '@matthiesenxyz/astro-ghostcms-brutalbyelian',
|
theme: "@matthiesenxyz/astro-ghostcms-brutalbyelian",
|
||||||
},
|
},
|
||||||
}),
|
}),
|
||||||
],
|
],
|
||||||
|
|
|
@ -1,33 +1,33 @@
|
||||||
import { defineConfig } from 'astro/config';
|
import starlight from "@astrojs/starlight";
|
||||||
import starlight from '@astrojs/starlight';
|
import starlightGhostCMS from "@matthiesenxyz/starlight-ghostcms";
|
||||||
import starlightGhostCMS from '@matthiesenxyz/starlight-ghostcms';
|
import { defineConfig } from "astro/config";
|
||||||
|
|
||||||
// https://astro.build/config
|
// https://astro.build/config
|
||||||
export default defineConfig({
|
export default defineConfig({
|
||||||
site: "http://localhost:4321",
|
site: "http://localhost:4321",
|
||||||
integrations: [
|
integrations: [
|
||||||
starlight({
|
starlight({
|
||||||
title: 'My Docs',
|
title: "My Docs",
|
||||||
plugins: [
|
plugins: [
|
||||||
starlightGhostCMS({
|
starlightGhostCMS({
|
||||||
title: "Demo Blog",
|
title: "Demo Blog",
|
||||||
rssDescription: "Starlight Playground"
|
rssDescription: "Starlight Playground",
|
||||||
})
|
}),
|
||||||
],
|
],
|
||||||
social: {
|
social: {
|
||||||
github: 'https://github.com/withastro/starlight',
|
github: "https://github.com/withastro/starlight",
|
||||||
},
|
},
|
||||||
sidebar: [
|
sidebar: [
|
||||||
{
|
{
|
||||||
label: 'Guides',
|
label: "Guides",
|
||||||
items: [
|
items: [
|
||||||
// Each item here is one entry in the navigation menu.
|
// Each item here is one entry in the navigation menu.
|
||||||
{ label: 'Example Guide', link: '/guides/example/' },
|
{ label: "Example Guide", link: "/guides/example/" },
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
label: 'Reference',
|
label: "Reference",
|
||||||
autogenerate: { directory: 'reference' },
|
autogenerate: { directory: "reference" },
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
}),
|
}),
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
import { defineCollection } from 'astro:content';
|
import { docsSchema } from "@astrojs/starlight/schema";
|
||||||
import { docsSchema } from '@astrojs/starlight/schema';
|
import { defineCollection } from "astro:content";
|
||||||
|
|
||||||
export const collections = {
|
export const collections = {
|
||||||
docs: defineCollection({ schema: docsSchema() }),
|
docs: defineCollection({ schema: docsSchema() }),
|
||||||
|
|
Loading…
Reference in New Issue